Exemplo n.º 1
0
GrVertexLayout GrDrawTarget::GetRectVertexLayout(const GrRect* srcRects[]) {
    if (NULL == srcRects) {
        return 0;
    }

    GrVertexLayout layout = 0;
    for (int i = 0; i < GrDrawState::kNumStages; ++i) {
        int numTC = 0;
        if (NULL != srcRects[i]) {
            layout |= StageTexCoordVertexLayoutBit(i, numTC);
            ++numTC;
        }
    }
    return layout;
}
Exemplo n.º 2
0
GrVertexLayout GrDrawTarget::GetRectVertexLayout(StageMask stageMask, 
                                                 const GrRect* srcRects[]) {
    GrVertexLayout layout = 0;

    for (int i = 0; i < GrDrawState::kNumStages; ++i) {
        int numTC = 0;
        if (stageMask & (1 << i)) {
            if (NULL != srcRects && NULL != srcRects[i]) {
                layout |= StageTexCoordVertexLayoutBit(i, numTC);
                ++numTC;
            } else {
                layout |= StagePosAsTexCoordVertexLayoutBit(i);
            }
        }
    }
    return layout;
}
Exemplo n.º 3
0
void GrDrawTarget::VertexLayoutUnitTest() {
    // Ensure that our globals mask arrays are correct
    GrVertexLayout stageTexCoordMasks[GrDrawState::kNumStages];
    GrVertexLayout texCoordMasks[GrDrawState::kMaxTexCoords];
    gen_mask_arrays(stageTexCoordMasks, texCoordMasks);
    for (int s = 0; s < GrDrawState::kNumStages; ++s) {
        GrAssert(stageTexCoordMasks[s] == gStageTexCoordMasks[s]);
    }
    for (int t = 0; t < GrDrawState::kMaxTexCoords; ++t) {
        GrAssert(texCoordMasks[t] == gTexCoordMasks[t]);
    }

    // not necessarily exhaustive
    static bool run;
    if (!run) {
        run = true;
        for (int s = 0; s < GrDrawState::kNumStages; ++s) {

            GrVertexLayout stageMask = 0;
            for (int t = 0; t < GrDrawState::kMaxTexCoords; ++t) {
                stageMask |= StageTexCoordVertexLayoutBit(s,t);
            }
            GrAssert(1 == GrDrawState::kMaxTexCoords ||
                     !check_layout(stageMask));
            GrAssert(gStageTexCoordMasks[s] == stageMask);
            GrAssert(!check_layout(stageMask));
        }
        for (int t = 0; t < GrDrawState::kMaxTexCoords; ++t) {
            GrVertexLayout tcMask = 0;
            GrAssert(!VertexUsesTexCoordIdx(t, 0));
            for (int s = 0; s < GrDrawState::kNumStages; ++s) {
                tcMask |= StageTexCoordVertexLayoutBit(s,t);
                GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask));
                GrAssert(VertexUsesTexCoordIdx(t, tcMask));
                GrAssert(2*sizeof(GrPoint) == VertexSize(tcMask));
                GrAssert(t == VertexTexCoordsForStage(s, tcMask));
                for (int s2 = s + 1; s2 < GrDrawState::kNumStages; ++s2) {
                    GrAssert(-1 == VertexTexCoordsForStage(s2, tcMask));

                #if GR_DEBUG
                    GrVertexLayout posAsTex = tcMask;
                #endif
                    GrAssert(0 == VertexStageCoordOffset(s2, posAsTex));
                    GrAssert(2*sizeof(GrPoint) == VertexSize(posAsTex));
                    GrAssert(-1 == VertexTexCoordsForStage(s2, posAsTex));
                    GrAssert(-1 == VertexEdgeOffset(posAsTex));
                }
                GrAssert(-1 == VertexEdgeOffset(tcMask));
                GrAssert(-1 == VertexColorOffset(tcMask));
                GrAssert(-1 == VertexCoverageOffset(tcMask));
            #if GR_DEBUG
                GrVertexLayout withColor = tcMask | kColor_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexCoverageOffset(withColor));
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withColor));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withColor));
            #if GR_DEBUG
                GrVertexLayout withEdge = tcMask | kEdge_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexColorOffset(withEdge));
                GrAssert(2*sizeof(GrPoint) == VertexEdgeOffset(withEdge));
                GrAssert(4*sizeof(GrPoint) == VertexSize(withEdge));
            #if GR_DEBUG
                GrVertexLayout withColorAndEdge = withColor | kEdge_VertexLayoutBit;
            #endif
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withColorAndEdge));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexEdgeOffset(withColorAndEdge));
                GrAssert(4*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withColorAndEdge));
            #if GR_DEBUG
                GrVertexLayout withCoverage = tcMask | kCoverage_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexColorOffset(withCoverage));
                GrAssert(2*sizeof(GrPoint) == VertexCoverageOffset(withCoverage));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withCoverage));
            #if GR_DEBUG
                GrVertexLayout withCoverageAndColor = tcMask | kCoverage_VertexLayoutBit |
                                                      kColor_VertexLayoutBit;
            #endif
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withCoverageAndColor));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexCoverageOffset(withCoverageAndColor));
                GrAssert(2*sizeof(GrPoint) + 2 * sizeof(GrColor) == VertexSize(withCoverageAndColor));
            }
            GrAssert(gTexCoordMasks[t] == tcMask);
            GrAssert(check_layout(tcMask));

            int stageOffsets[GrDrawState::kNumStages];
            int colorOffset;
            int edgeOffset;
            int coverageOffset;
            int size;
            size = VertexSizeAndOffsetsByStage(tcMask,
                                               stageOffsets, &colorOffset,
                                               &coverageOffset, &edgeOffset);
            GrAssert(2*sizeof(GrPoint) == size);
            GrAssert(-1 == colorOffset);
            GrAssert(-1 == coverageOffset);
            GrAssert(-1 == edgeOffset);
            for (int s = 0; s < GrDrawState::kNumStages; ++s) {
                GrAssert(sizeof(GrPoint) == stageOffsets[s]);
                GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask));
            }
        }
    }
}
Exemplo n.º 4
0
bool GrGpuGLShaders::programUnitTest() {

    GrGLSLGeneration glslGeneration = 
            GrGetGLSLGeneration(this->glBinding(), this->glInterface());
    static const int STAGE_OPTS[] = {
        0,
        StageDesc::kNoPerspective_OptFlagBit,
        StageDesc::kIdentity_CoordMapping
    };
    static const int IN_CONFIG_FLAGS[] = {
        StageDesc::kNone_InConfigFlag,
        StageDesc::kSwapRAndB_InConfigFlag,
        StageDesc::kSwapRAndB_InConfigFlag |
        StageDesc::kMulRGBByAlpha_RoundUp_InConfigFlag,
        StageDesc::kMulRGBByAlpha_RoundDown_InConfigFlag,
        StageDesc::kSmearAlpha_InConfigFlag,
        StageDesc::kSmearRed_InConfigFlag,
    };
    GrGLProgram program;
    ProgramDesc& pdesc = program.fProgramDesc;

    static const int NUM_TESTS = 512;

    GrRandom random;
    for (int t = 0; t < NUM_TESTS; ++t) {

#if 0
        GrPrintf("\nTest Program %d\n-------------\n", t);
        static const int stop = -1;
        if (t == stop) {
            int breakpointhere = 9;
        }
#endif

        pdesc.fVertexLayout = 0;
        pdesc.fEmitsPointSize = random.nextF() > .5f;
        pdesc.fColorInput = random_int(&random, ProgramDesc::kColorInputCnt);
        pdesc.fCoverageInput = random_int(&random, ProgramDesc::kColorInputCnt);

        pdesc.fColorFilterXfermode = random_int(&random, SkXfermode::kCoeffModesCnt);

        pdesc.fFirstCoverageStage = random_int(&random, GrDrawState::kNumStages);

        pdesc.fVertexLayout |= random_bool(&random) ?
                                    GrDrawTarget::kCoverage_VertexLayoutBit :
                                    0;

#if GR_GL_EXPERIMENTAL_GS
        pdesc.fExperimentalGS = this->getCaps().fGeometryShaderSupport &&
                                random_bool(&random);
#endif
        pdesc.fOutputConfig =  random_int(&random, ProgramDesc::kOutputConfigCnt);

        bool edgeAA = random_bool(&random);
        if (edgeAA) {
            pdesc.fVertexLayout |= GrDrawTarget::kEdge_VertexLayoutBit;
            if (this->getCaps().fShaderDerivativeSupport) {
                pdesc.fVertexEdgeType = (GrDrawState::VertexEdgeType) random_int(&random, GrDrawState::kVertexEdgeTypeCnt);
            } else {
                pdesc.fVertexEdgeType = GrDrawState::kHairLine_EdgeType;
            }
        } else {
        }

        pdesc.fColorMatrixEnabled = random_bool(&random);

        if (this->getCaps().fDualSourceBlendingSupport) {
            pdesc.fDualSrcOutput = random_int(&random, ProgramDesc::kDualSrcOutputCnt);
        } else {
            pdesc.fDualSrcOutput = ProgramDesc::kNone_DualSrcOutput;
        }

        GrCustomStage* customStages[GrDrawState::kNumStages];

        for (int s = 0; s < GrDrawState::kNumStages; ++s) {
            // enable the stage?
            if (random_bool(&random)) {
                // use separate tex coords?
                if (random_bool(&random)) {
                    int t = random_int(&random, GrDrawState::kMaxTexCoords);
                    pdesc.fVertexLayout |= StageTexCoordVertexLayoutBit(s, t);
                } else {
                    pdesc.fVertexLayout |= StagePosAsTexCoordVertexLayoutBit(s);
                }
            }
            // use text-formatted verts?
            if (random_bool(&random)) {
                pdesc.fVertexLayout |= kTextFormat_VertexLayoutBit;
            }
            StageDesc& stage = pdesc.fStages[s];

            stage.fCustomStageKey = 0;
            customStages[s] = NULL;

            stage.fOptFlags = STAGE_OPTS[random_int(&random, GR_ARRAY_COUNT(STAGE_OPTS))];
            stage.fInConfigFlags = IN_CONFIG_FLAGS[random_int(&random, GR_ARRAY_COUNT(IN_CONFIG_FLAGS))];
            stage.fCoordMapping =  random_int(&random, StageDesc::kCoordMappingCnt);
            stage.fFetchMode = random_int(&random, StageDesc::kFetchModeCnt);
            // convolution shaders don't work with persp tex matrix
            if (stage.fFetchMode == StageDesc::kConvolution_FetchMode ||
                stage.fFetchMode == StageDesc::kDilate_FetchMode ||
                stage.fFetchMode == StageDesc::kErode_FetchMode) {
                stage.fOptFlags |= StageDesc::kNoPerspective_OptFlagBit;
            }
            stage.setEnabled(VertexUsesStage(s, pdesc.fVertexLayout));
            static const uint32_t kMulByAlphaMask =
                StageDesc::kMulRGBByAlpha_RoundUp_InConfigFlag |
                StageDesc::kMulRGBByAlpha_RoundDown_InConfigFlag;

            switch (stage.fFetchMode) {
                case StageDesc::kSingle_FetchMode:
                    stage.fKernelWidth = 0;
                    break;
                case StageDesc::kConvolution_FetchMode:
                case StageDesc::kDilate_FetchMode:
                case StageDesc::kErode_FetchMode:
                    stage.fKernelWidth = random_int(&random, 2, 8);
                    stage.fInConfigFlags &= ~kMulByAlphaMask;
                    break;
                case StageDesc::k2x2_FetchMode:
                    stage.fKernelWidth = 0;
                    stage.fInConfigFlags &= ~kMulByAlphaMask;
                    break;
            }

            // TODO: is there a more elegant way to express this?
            if (stage.fFetchMode == StageDesc::kConvolution_FetchMode) {
                int direction = random_int(&random, 2);
                float kernel[MAX_KERNEL_WIDTH];
                for (int i = 0; i < stage.fKernelWidth; i++) {
                    kernel[i] = random.nextF();
                }
                customStages[s] = new GrConvolutionEffect(
                    (GrSamplerState::FilterDirection)direction,
                    stage.fKernelWidth, kernel);
                stage.fCustomStageKey =
                    customStages[s]->getFactory()->stageKey(customStages[s]);
            }
        }
        CachedData cachedData;
        if (!program.genProgram(this->glContextInfo(), customStages,
                                &cachedData)) {
            return false;
        }
        DeleteProgram(this->glInterface(), &cachedData);
    }
    return true;
}
Exemplo n.º 5
0
bool GrGpuGL::programUnitTest() {

    GrTextureDesc dummyDesc;
    dummyDesc.fConfig = kSkia8888_PM_GrPixelConfig;
    dummyDesc.fWidth = 34;
    dummyDesc.fHeight = 18;
    SkAutoTUnref<GrTexture> dummyTexture1(this->createTexture(dummyDesc, NULL, 0));
    dummyDesc.fConfig = kAlpha_8_GrPixelConfig;
    dummyDesc.fWidth = 16;
    dummyDesc.fHeight = 22;
    SkAutoTUnref<GrTexture> dummyTexture2(this->createTexture(dummyDesc, NULL, 0));

    // GrGLSLGeneration glslGeneration =
            GrGetGLSLGeneration(this->glBinding(), this->glInterface());
    static const int STAGE_OPTS[] = {
        0,
        StageDesc::kNoPerspective_OptFlagBit,
    };
    static const int IN_CONFIG_FLAGS[] = {
        StageDesc::kNone_InConfigFlag,
        StageDesc::kSmearAlpha_InConfigFlag,
    };

    static const int NUM_TESTS = 512;

    GrRandom random;
    for (int t = 0; t < NUM_TESTS; ++t) {

#if 0
        GrPrintf("\nTest Program %d\n-------------\n", t);
        static const int stop = -1;
        if (t == stop) {
            int breakpointhere = 9;
        }
#endif

        ProgramDesc pdesc;
        pdesc.fVertexLayout = 0;
        pdesc.fEmitsPointSize = random.nextF() > .5f;
        pdesc.fColorInput = random_int(&random, ProgramDesc::kColorInputCnt);
        pdesc.fCoverageInput = random_int(&random, ProgramDesc::kColorInputCnt);

        pdesc.fColorFilterXfermode = random_int(&random, SkXfermode::kCoeffModesCnt);

        pdesc.fFirstCoverageStage = random_int(&random, GrDrawState::kNumStages);

        pdesc.fVertexLayout |= random_bool(&random) ?
                                    GrDrawTarget::kCoverage_VertexLayoutBit :
                                    0;

#if GR_GL_EXPERIMENTAL_GS
        pdesc.fExperimentalGS = this->getCaps().geometryShaderSupport() &&
                                random_bool(&random);
#endif

        bool edgeAA = random_bool(&random);
        if (edgeAA) {
            pdesc.fVertexLayout |= GrDrawTarget::kEdge_VertexLayoutBit;
            if (this->getCaps().shaderDerivativeSupport()) {
                pdesc.fVertexEdgeType = (GrDrawState::VertexEdgeType) random_int(&random, GrDrawState::kVertexEdgeTypeCnt);
            } else {
                pdesc.fVertexEdgeType = GrDrawState::kHairLine_EdgeType;
            }
        } else {
        }

        pdesc.fColorMatrixEnabled = random_bool(&random);

        if (this->getCaps().dualSourceBlendingSupport()) {
            pdesc.fDualSrcOutput = random_int(&random, ProgramDesc::kDualSrcOutputCnt);
        } else {
            pdesc.fDualSrcOutput = ProgramDesc::kNone_DualSrcOutput;
        }

        SkAutoTUnref<const GrCustomStage> customStages[GrDrawState::kNumStages];

        for (int s = 0; s < GrDrawState::kNumStages; ++s) {
            StageDesc& stage = pdesc.fStages[s];
            // enable the stage?
            if (random_bool(&random)) {
                // use separate tex coords?
                if (random_bool(&random)) {
                    int t = random_int(&random, GrDrawState::kMaxTexCoords);
                    pdesc.fVertexLayout |= StageTexCoordVertexLayoutBit(s, t);
                }
                stage.setEnabled(true);
            }
            // use text-formatted verts?
            if (random_bool(&random)) {
                pdesc.fVertexLayout |= kTextFormat_VertexLayoutBit;
            }

            stage.fCustomStageKey = 0;

            stage.fOptFlags |= STAGE_OPTS[random_int(&random, GR_ARRAY_COUNT(STAGE_OPTS))];
            stage.fInConfigFlags = IN_CONFIG_FLAGS[random_int(&random, GR_ARRAY_COUNT(IN_CONFIG_FLAGS))];

            if (stage.isEnabled()) {
                GrTexture* dummyTextures[] = {dummyTexture1.get(), dummyTexture2.get()};
                customStages[s].reset(create_random_effect(&stage,
                                                           &random,
                                                           getContext(),
                                                           dummyTextures));
                if (NULL != customStages[s]) {
                    stage.fCustomStageKey =
                        customStages[s]->getFactory().glStageKey(*customStages[s], this->glCaps());
                }
            }
        }
        GR_STATIC_ASSERT(sizeof(customStages) ==
                         GrDrawState::kNumStages * sizeof(GrCustomStage*));
        const GrCustomStage** stages = reinterpret_cast<const GrCustomStage**>(&customStages);
        SkAutoTUnref<GrGLProgram> program(GrGLProgram::Create(this->glContextInfo(),
                                                              pdesc,
                                                              stages));
        if (NULL == program.get()) {
            return false;
        }
    }
    return true;
}
Exemplo n.º 6
0
bool GrGpuGLShaders::programUnitTest() {

    GrGLSLGeneration glslGeneration =
        GetGLSLGeneration(this->glBinding(), this->glInterface());
    static const int STAGE_OPTS[] = {
        0,
        StageDesc::kNoPerspective_OptFlagBit,
        StageDesc::kIdentity_CoordMapping
    };
    static const int IN_CONFIG_FLAGS[] = {
        StageDesc::kNone_InConfigFlag,
        StageDesc::kSwapRAndB_InConfigFlag,
        StageDesc::kSwapRAndB_InConfigFlag | StageDesc::kMulRGBByAlpha_InConfigFlag,
        StageDesc::kMulRGBByAlpha_InConfigFlag,
        StageDesc::kSmearAlpha_InConfigFlag,
    };
    GrGLProgram program;
    ProgramDesc& pdesc = program.fProgramDesc;

    static const int NUM_TESTS = 512;

    GrRandom random;
    for (int t = 0; t < NUM_TESTS; ++t) {

#if 0
        GrPrintf("\nTest Program %d\n-------------\n", t);
        static const int stop = -1;
        if (t == stop) {
            int breakpointhere = 9;
        }
#endif

        pdesc.fVertexLayout = 0;
        pdesc.fEmitsPointSize = random.nextF() > .5f;
        pdesc.fColorInput = random_int(&random, ProgramDesc::kColorInputCnt);

        pdesc.fColorFilterXfermode = random_int(&random, SkXfermode::kCoeffModesCnt);

        pdesc.fFirstCoverageStage = random_int(&random, GrDrawState::kNumStages);

        pdesc.fVertexLayout |= random_bool(&random) ?
                               GrDrawTarget::kCoverage_VertexLayoutBit :
                               0;

#if GR_GL_EXPERIMENTAL_GS
        pdesc.fExperimentalGS = this->getCaps().fGeometryShaderSupport &&
                                random_bool(&random);
#endif
        pdesc.fOutputPM =  random_int(&random, ProgramDesc::kOutputPMCnt);

        bool edgeAA = random_bool(&random);
        if (edgeAA) {
            bool vertexEdgeAA = random_bool(&random);
            if (vertexEdgeAA) {
                pdesc.fVertexLayout |= GrDrawTarget::kEdge_VertexLayoutBit;
                if (this->getCaps().fShaderDerivativeSupport) {
                    pdesc.fVertexEdgeType = random_bool(&random) ?
                                            GrDrawState::kHairQuad_EdgeType :
                                            GrDrawState::kHairLine_EdgeType;
                } else {
                    pdesc.fVertexEdgeType = GrDrawState::kHairLine_EdgeType;
                }
                pdesc.fEdgeAANumEdges = 0;
            } else {
                pdesc.fEdgeAANumEdges = random_int(&random, 1, this->getMaxEdges());
                pdesc.fEdgeAAConcave = random_bool(&random);
            }
        } else {
            pdesc.fEdgeAANumEdges = 0;
        }

        if (this->getCaps().fDualSourceBlendingSupport) {
            pdesc.fDualSrcOutput = random_int(&random, ProgramDesc::kDualSrcOutputCnt);
        } else {
            pdesc.fDualSrcOutput = ProgramDesc::kNone_DualSrcOutput;
        }

        for (int s = 0; s < GrDrawState::kNumStages; ++s) {
            // enable the stage?
            if (random_bool(&random)) {
                // use separate tex coords?
                if (random_bool(&random)) {
                    int t = random_int(&random, GrDrawState::kMaxTexCoords);
                    pdesc.fVertexLayout |= StageTexCoordVertexLayoutBit(s, t);
                } else {
                    pdesc.fVertexLayout |= StagePosAsTexCoordVertexLayoutBit(s);
                }
            }
            // use text-formatted verts?
            if (random_bool(&random)) {
                pdesc.fVertexLayout |= kTextFormat_VertexLayoutBit;
            }
            StageDesc& stage = pdesc.fStages[s];
            stage.fOptFlags = STAGE_OPTS[random_int(&random, GR_ARRAY_COUNT(STAGE_OPTS))];
            stage.fInConfigFlags = IN_CONFIG_FLAGS[random_int(&random, GR_ARRAY_COUNT(IN_CONFIG_FLAGS))];
            stage.fCoordMapping =  random_int(&random, StageDesc::kCoordMappingCnt);
            stage.fFetchMode = random_int(&random, StageDesc::kFetchModeCnt);
            // convolution shaders don't work with persp tex matrix
            if (stage.fFetchMode == StageDesc::kConvolution_FetchMode) {
                stage.fOptFlags |= StageDesc::kNoPerspective_OptFlagBit;
            }
            stage.setEnabled(VertexUsesStage(s, pdesc.fVertexLayout));
            switch (stage.fFetchMode) {
            case StageDesc::kSingle_FetchMode:
                stage.fKernelWidth = 0;
                break;
            case StageDesc::kConvolution_FetchMode:
                stage.fKernelWidth = random_int(&random, 2, 8);
                stage.fInConfigFlags &= ~StageDesc::kMulRGBByAlpha_InConfigFlag;
                break;
            case StageDesc::k2x2_FetchMode:
                stage.fKernelWidth = 0;
                stage.fInConfigFlags &= ~StageDesc::kMulRGBByAlpha_InConfigFlag;
                break;
            }
        }
        CachedData cachedData;
        if (!program.genProgram(this->glInterface(),
                                glslGeneration,
                                &cachedData)) {
            return false;
        }
        DeleteProgram(this->glInterface(), &cachedData);
    }
    return true;
}
Exemplo n.º 7
0
void GrDrawTarget::VertexLayoutUnitTest() {
    // not necessarily exhaustive
    static bool run;
    if (!run) {
        run = true;
        for (int s = 0; s < kNumStages; ++s) {

            GrAssert(!VertexUsesStage(s, 0));
            GrAssert(-1 == VertexStageCoordOffset(s, 0));
            GrVertexLayout stageMask = 0;
            for (int t = 0; t < kMaxTexCoords; ++t) {
                stageMask |= StageTexCoordVertexLayoutBit(s,t);
            }
            GrAssert(1 == kMaxTexCoords || !check_layout(stageMask));
            GrAssert(stage_tex_coord_mask(s) == stageMask);
            stageMask |= StagePosAsTexCoordVertexLayoutBit(s);
            GrAssert(stage_mask(s) == stageMask);
            GrAssert(!check_layout(stageMask));
        }
        for (int t = 0; t < kMaxTexCoords; ++t) {
            GrVertexLayout tcMask = 0;
            GrAssert(!VertexUsesTexCoordIdx(t, 0));
            for (int s = 0; s < kNumStages; ++s) {
                tcMask |= StageTexCoordVertexLayoutBit(s,t);
                GrAssert(VertexUsesStage(s, tcMask));
                GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask));
                GrAssert(VertexUsesTexCoordIdx(t, tcMask));
                GrAssert(2*sizeof(GrPoint) == VertexSize(tcMask));
                GrAssert(t == VertexTexCoordsForStage(s, tcMask));
                for (int s2 = s + 1; s2 < kNumStages; ++s2) {
                    GrAssert(-1 == VertexStageCoordOffset(s2, tcMask));
                    GrAssert(!VertexUsesStage(s2, tcMask));
                    GrAssert(-1 == VertexTexCoordsForStage(s2, tcMask));

                #if GR_DEBUG
                    GrVertexLayout posAsTex = tcMask | StagePosAsTexCoordVertexLayoutBit(s2);
                #endif
                    GrAssert(0 == VertexStageCoordOffset(s2, posAsTex));
                    GrAssert(VertexUsesStage(s2, posAsTex));
                    GrAssert(2*sizeof(GrPoint) == VertexSize(posAsTex));
                    GrAssert(-1 == VertexTexCoordsForStage(s2, posAsTex));
                    GrAssert(-1 == VertexEdgeOffset(posAsTex));
                }
                GrAssert(-1 == VertexEdgeOffset(tcMask));
                GrAssert(-1 == VertexColorOffset(tcMask));
                GrAssert(-1 == VertexCoverageOffset(tcMask));
            #if GR_DEBUG
                GrVertexLayout withColor = tcMask | kColor_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexCoverageOffset(withColor));
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withColor));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withColor));
            #if GR_DEBUG
                GrVertexLayout withEdge = tcMask | kEdge_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexColorOffset(withEdge));
                GrAssert(2*sizeof(GrPoint) == VertexEdgeOffset(withEdge));
                GrAssert(4*sizeof(GrPoint) == VertexSize(withEdge));
            #if GR_DEBUG
                GrVertexLayout withColorAndEdge = withColor | kEdge_VertexLayoutBit;
            #endif
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withColorAndEdge));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexEdgeOffset(withColorAndEdge));
                GrAssert(4*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withColorAndEdge));
            #if GR_DEBUG
                GrVertexLayout withCoverage = tcMask | kCoverage_VertexLayoutBit;
            #endif
                GrAssert(-1 == VertexColorOffset(withCoverage));
                GrAssert(2*sizeof(GrPoint) == VertexCoverageOffset(withCoverage));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withCoverage));
            #if GR_DEBUG
                GrVertexLayout withCoverageAndColor = tcMask | kCoverage_VertexLayoutBit |
                                                      kColor_VertexLayoutBit;
            #endif
                GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withCoverageAndColor));
                GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexCoverageOffset(withCoverageAndColor));
                GrAssert(2*sizeof(GrPoint) + 2 * sizeof(GrColor) == VertexSize(withCoverageAndColor));
            }
            GrAssert(tex_coord_idx_mask(t) == tcMask);
            GrAssert(check_layout(tcMask));

            int stageOffsets[kNumStages];
            int colorOffset;
            int edgeOffset;
            int coverageOffset;
            int size;
            size = VertexSizeAndOffsetsByStage(tcMask, stageOffsets, &colorOffset,
                                               &coverageOffset, &edgeOffset);
            GrAssert(2*sizeof(GrPoint) == size);
            GrAssert(-1 == colorOffset);
            GrAssert(-1 == coverageOffset);
            GrAssert(-1 == edgeOffset);
            for (int s = 0; s < kNumStages; ++s) {
                GrAssert(VertexUsesStage(s, tcMask));
                GrAssert(sizeof(GrPoint) == stageOffsets[s]);
                GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask));
            }
        }
    }
}
Exemplo n.º 8
0
bool GrGpuGLShaders::programUnitTest() {

    GrGLProgram::GLSLVersion glslVersion = 
            get_glsl_version(this->glBinding(), this->glInterface());
    static const int STAGE_OPTS[] = {
        0,
        StageDesc::kNoPerspective_OptFlagBit,
        StageDesc::kIdentity_CoordMapping
    };
    GrGLProgram program;
    ProgramDesc& pdesc = program.fProgramDesc;

    static const int NUM_TESTS = 512;

    // GrRandoms nextU() values have patterns in the low bits
    // So using nextU() % array_count might never take some values.
    GrRandom random;
    for (int t = 0; t < NUM_TESTS; ++t) {

#if 0
        GrPrintf("\nTest Program %d\n-------------\n", t);
        static const int stop = -1;
        if (t == stop) {
            int breakpointhere = 9;
        }
#endif

        pdesc.fVertexLayout = 0;
        pdesc.fEmitsPointSize = random.nextF() > .5f;
        pdesc.fColorType = static_cast<int>(random.nextF() *
                                            ProgramDesc::kColorTypeCnt);

        int idx = (int)(random.nextF() * (SkXfermode::kCoeffModesCnt));
        pdesc.fColorFilterXfermode = (SkXfermode::Mode)idx;

        idx = (int)(random.nextF() * (GrDrawState::kNumStages + 1));
        pdesc.fFirstCoverageStage = idx;

        pdesc.fVertexLayout |= (random.nextF() > .5f) ?
                                    GrDrawTarget::kCoverage_VertexLayoutBit :
                                    0;

#if GR_GL_EXPERIMENTAL_GS
        pdesc.fExperimentalGS = this->getCaps().fGeometryShaderSupport &&
                                random.nextF() > .5f;
#endif

        bool edgeAA = random.nextF() > .5f;
        if (edgeAA) {
            bool vertexEdgeAA = random.nextF() > .5f;
            if (vertexEdgeAA) {
                pdesc.fVertexLayout |= GrDrawTarget::kEdge_VertexLayoutBit;
                if (this->getCaps().fShaderDerivativeSupport) {
                    pdesc.fVertexEdgeType = random.nextF() > 0.5f ?
                        GrDrawState::kHairQuad_EdgeType :
                        GrDrawState::kHairLine_EdgeType;
                } else {
                    pdesc.fVertexEdgeType = GrDrawState::kHairLine_EdgeType;
                }
                pdesc.fEdgeAANumEdges = 0;
            } else {
                pdesc.fEdgeAANumEdges =  static_cast<int>(1 + random.nextF() *
                                                          this->getMaxEdges());
                pdesc.fEdgeAAConcave = random.nextF() > .5f;
            }
        } else {
            pdesc.fEdgeAANumEdges = 0;
        }

        if (this->getCaps().fDualSourceBlendingSupport) {
            pdesc.fDualSrcOutput =
               (ProgramDesc::DualSrcOutput)
               (int)(random.nextF() * ProgramDesc::kDualSrcOutputCnt);
        } else {
            pdesc.fDualSrcOutput = ProgramDesc::kNone_DualSrcOutput;
        }

        for (int s = 0; s < GrDrawState::kNumStages; ++s) {
            // enable the stage?
            if (random.nextF() > .5f) {
                // use separate tex coords?
                if (random.nextF() > .5f) {
                    int t = (int)(random.nextF() * GrDrawState::kMaxTexCoords);
                    pdesc.fVertexLayout |= StageTexCoordVertexLayoutBit(s, t);
                } else {
                    pdesc.fVertexLayout |= StagePosAsTexCoordVertexLayoutBit(s);
                }
            }
            // use text-formatted verts?
            if (random.nextF() > .5f) {
                pdesc.fVertexLayout |= kTextFormat_VertexLayoutBit;
            }
            idx = (int)(random.nextF() * GR_ARRAY_COUNT(STAGE_OPTS));
            StageDesc& stage = pdesc.fStages[s];
            stage.fOptFlags = STAGE_OPTS[idx];
            stage.fModulation = random_val(&random, StageDesc::kModulationCnt);
            stage.fCoordMapping =  random_val(&random, StageDesc::kCoordMappingCnt);
            stage.fFetchMode = random_val(&random, StageDesc::kFetchModeCnt);
            // convolution shaders don't work with persp tex matrix
            if (stage.fFetchMode == StageDesc::kConvolution_FetchMode) {
                stage.fOptFlags |= StageDesc::kNoPerspective_OptFlagBit;
            }
            stage.setEnabled(VertexUsesStage(s, pdesc.fVertexLayout));
            stage.fKernelWidth = static_cast<int8_t>(4 * random.nextF() + 2);
        }
        CachedData cachedData;
        if (!program.genProgram(this->glInterface(),
                                glslVersion,
                                &cachedData)) {
            return false;
        }
        DeleteProgram(this->glInterface(), &cachedData);
    }
    return true;
}