static void test_get_basename(skiatest::Reporter* reporter) { SkString result; SkString path("/path/basename"); sk_tools::get_basename(&result, path); REPORTER_ASSERT(reporter, result.equals("basename")); result.reset(); path.set("/path/dir/"); sk_tools::get_basename(&result, path); REPORTER_ASSERT(reporter, result.equals("dir")); result.reset(); path.set("path"); sk_tools::get_basename(&result, path); REPORTER_ASSERT(reporter, result.equals("path")); #if defined(SK_BUILD_FOR_WIN) result.reset(); path.set("path\\winbasename"); sk_tools::get_basename(&result, path); REPORTER_ASSERT(reporter, result.equals("winbasename")); result.reset(); path.set("path\\windir\\"); sk_tools::get_basename(&result, path); REPORTER_ASSERT(reporter, result.equals("windir")); #endif }
static bool parse_option_bool(const SkString& value, bool* outBool) { if (value.equals("true")) { *outBool = true; return true; } if (value.equals("false")) { *outBool = false; return true; } return false; }
static bool parse_option_gpu_api(const SkString& value, SkCommandLineConfigGpu::ContextType* outContextType) { if (value.equals("native")) { *outContextType = GrContextFactory::kNative_GLContextType; return true; } if (value.equals("gl")) { *outContextType = GrContextFactory::kGL_GLContextType; return true; } if (value.equals("gles")) { *outContextType = GrContextFactory::kGLES_GLContextType; return true; } if (value.equals("debug")) { *outContextType = GrContextFactory::kDebug_GLContextType; return true; } if (value.equals("null")) { *outContextType = GrContextFactory::kNull_GLContextType; return true; } #if SK_ANGLE #ifdef SK_BUILD_FOR_WIN if (value.equals("angle")) { *outContextType = GrContextFactory::kANGLE_GLContextType; return true; } #endif if (value.equals("angle-gl")) { *outContextType = GrContextFactory::kANGLE_GL_GLContextType; return true; } #endif #if SK_COMMAND_BUFFER if (value.equals("commandbuffer")) { *outContextType = GrContextFactory::kCommandBufferES2_GLContextType; return true; } if (value.equals("commandbuffer3")) { *outContextType = GrContextFactory::kCommandBufferES3_GLContextType; return true; } #endif #if SK_MESA if (value.equals("mesa")) { *outContextType = GrContextFactory::kMESA_GLContextType; return true; } #endif return false; }
void Viewer::onUIStateChanged(const SkString& stateName, const SkString& stateValue) { // For those who will add more features to handle the state change in this function: // After the change, please call updateUIState no notify the frontend (e.g., Android app). // For example, after slide change, updateUIState is called inside setupCurrentSlide; // after backend change, updateUIState is called in this function. if (stateName.equals(kSlideStateName)) { int previousSlide = fCurrentSlide; fCurrentSlide = 0; for(auto slide : fSlides) { if (slide->getName().equals(stateValue)) { setupCurrentSlide(previousSlide); break; } fCurrentSlide++; } if (fCurrentSlide >= fSlides.count()) { fCurrentSlide = previousSlide; SkDebugf("Slide not found: %s", stateValue.c_str()); } } else if (stateName.equals(kBackendStateName)) { for (int i = 0; i < sk_app::Window::kBackendTypeCount; i++) { if (stateValue.equals(kBackendTypeStrings[i])) { if (fBackendType != i) { fBackendType = (sk_app::Window::BackendType)i; fWindow->detach(); fWindow->attach(fBackendType, DisplayParams()); fWindow->inval(); updateTitle(); updateUIState(); } break; } } } else if (stateName.equals(kSoftkeyStateName)) { if (!stateValue.equals(kSoftkeyHint)) { fCommands.onSoftkey(stateValue); updateUIState(); // This is still needed to reset the value to kSoftkeyHint } } else if (stateName.equals(kSplitScreenStateName)) { bool newSplitScreen = stateValue.equals(kON); if (newSplitScreen != fSplitScreen) { fSplitScreen = newSplitScreen; fWindow->inval(); updateUIState(); } } else if (stateName.equals(kRefreshStateName)) { // This state is actually NOT in the UI state. // We use this to allow Android to quickly set bool fRefresh. fRefresh = stateValue.equals(kON); } else { SkDebugf("Unknown stateName: %s", stateName.c_str()); } }
static void test_filepath_creation(skiatest::Reporter* reporter) { SkString result; SkString filename("test"); SkString dir("test/path"); sk_tools::make_filepath(&result, dir, filename); REPORTER_ASSERT(reporter, result.equals("test/path/test")); }
void SkPDFMetadata::SetMetadataByKey(const SkString& key, const SkString& value, SkDocument::PDFMetadata* metadata) { for (const auto keyValuePtr : gMetadataKeys) { if (key.equals(keyValuePtr.key)) { metadata->*(keyValuePtr.valuePtr) = value; } } }
void runTest(skiatest::Reporter* reporter) { SkAutoTDelete<SkAdvancedTypefaceMetrics::AdvanceMetric<int16_t> > result; result.reset(getAdvanceData((void*)this, fAdvancesLen, fSubset, fSubsetLen, getAdvance)); SkString stringResult = stringify_advance_data(result); if (!stringResult.equals(fExpected)) { ERRORF(reporter, "Expected: %s\n Result: %s\n", fExpected, stringResult.c_str()); } }
/** * Test SkOSPath::Join, SkOSPath::Basename, and SkOSPath::Dirname. * Will use SkOSPath::Join to append filename to dir, test that it works correctly, * and tests using SkOSPath::Basename on the result. * @param reporter Reporter for test conditions. * @param dir String representing the path to a folder. May or may not * end with SkOSPath::SEPARATOR. * @param filename String representing the basename of a file. Must NOT * contain SkOSPath::SEPARATOR. */ static void test_dir_with_file(skiatest::Reporter* reporter, SkString dir, SkString filename) { // If filename contains SkOSPath::SEPARATOR, the tests will fail. SkASSERT(!filename.contains(SkOSPath::SEPARATOR)); // Tests for SkOSPath::Join and SkOSPath::Basename // fullName should be "dir<SkOSPath::SEPARATOR>file" SkString fullName = SkOSPath::Join(dir.c_str(), filename.c_str()); // fullName should be the combined size of dir and file, plus one if // dir did not include the final path separator. size_t expectedSize = dir.size() + filename.size(); if (!dir.endsWith(SkOSPath::SEPARATOR) && !dir.isEmpty()) { expectedSize++; } REPORTER_ASSERT(reporter, fullName.size() == expectedSize); SkString basename = SkOSPath::Basename(fullName.c_str()); SkString dirname = SkOSPath::Dirname(fullName.c_str()); // basename should be the same as filename REPORTER_ASSERT(reporter, basename.equals(filename)); // dirname should be the same as dir with any trailing seperators removed. // Except when the the string is just "/". SkString strippedDir = dir; while (strippedDir.size() > 2 && strippedDir[strippedDir.size() - 1] == SkOSPath::SEPARATOR) { strippedDir.remove(strippedDir.size() - 1, 1); } if (!dirname.equals(strippedDir)) { SkDebugf("OOUCH %s %s %s\n", dir.c_str(), strippedDir.c_str(), dirname.c_str()); } REPORTER_ASSERT(reporter, dirname.equals(strippedDir)); // basename will not contain a path separator REPORTER_ASSERT(reporter, !basename.contains(SkOSPath::SEPARATOR)); // Now take the basename of filename, which should be the same as filename. basename = SkOSPath::Basename(filename.c_str()); REPORTER_ASSERT(reporter, basename.equals(filename)); }
bool match(const SkString& filename, SkFILEWStream* stream, TestResult* result) { if (fIndex < fResults.count()) { *result = fResults[fIndex++]; SkASSERT(filename.equals(result->fFilename)); SkString outStr(result->status()); stream->write(outStr.c_str(), outStr.size()); stream->flush(); return true; } return false; }
static bool parse_option_gpu_color(const SkString& value, SkColorType* outColorType, sk_sp<SkColorSpace>* outColorSpace) { if (value.equals("8888")) { *outColorType = kN32_SkColorType; *outColorSpace = nullptr; return true; } if (value.equals("f16")) { *outColorType = kRGBA_F16_SkColorType; *outColorSpace = SkColorSpace::NewNamed(SkColorSpace::kSRGB_Named); return true; } if (value.equals("srgb")) { *outColorType = kN32_SkColorType; *outColorSpace = SkColorSpace::NewNamed(SkColorSpace::kSRGB_Named); return true; } return false; }
const char* platform_font_name(const char* name) { SkString platform = major_platform_os_name(); int index; if (!strcmp(name, "serif")) { index = 0; } else if (!strcmp(name, "san-serif")) { index = 1; } else if (!strcmp(name, "monospace")) { index = 2; } else { return name; } if (platform.equals("Mac")) { return gStandardFontNames[0][index]; } if (platform.equals("iOS")) { return gStandardFontNames[1][index]; } if (platform.equals("Win")) { return gStandardFontNames[2][index]; } if (platform.equals("Ubuntu")) { return gStandardFontNames[3][index]; } if (platform.equals("Android")) { return gStandardFontNames[4][index]; } if (platform.equals("ChromeOS")) { return gStandardFontNames[5][index]; } return name; }
void runTest(skiatest::Reporter* reporter) { SkAdvancedTypefaceMetrics metrics; metrics.setGlyphWidths( fAdvancesLen, fSubset, fSubsetLen, std::function<bool(int, int16_t*)>([this](int gId, int16_t* advance) { if (gId >= 0 && gId < fAdvancesLen) { *advance = fAdvances[gId]; return true; } return false; })); SkString stringResult = stringify_advance_data(metrics.fGlyphWidths); if (!stringResult.equals(fExpected)) { ERRORF(reporter, "Expected: %s\n Result: %s\n", fExpected, stringResult.c_str()); } }
void Viewer::onUIStateChanged(const SkString& stateName, const SkString& stateValue) { // Currently, we only recognize the Slide state if (stateName.equals(kSlideStateName)) { int previousSlide = fCurrentSlide; fCurrentSlide = 0; for(auto slide : fSlides) { if (slide->getName().equals(stateValue)) { setupCurrentSlide(previousSlide); break; } fCurrentSlide++; } if (fCurrentSlide >= fSlides.count()) { fCurrentSlide = previousSlide; SkDebugf("Slide not found: %s", stateValue.c_str()); } } else { SkDebugf("Unknown stateName: %s", stateName.c_str()); } }
static int whitelist_name_index(const SkTypeface* tf) { SkString fontNameStr; SkAutoTUnref<SkTypeface::LocalizedStrings> nameIter( SkOTUtils::LocalizedStrings_NameTable::CreateForFamilyNames(*tf)); SkTypeface::LocalizedString familyNameLocalized; while (nameIter->next(&familyNameLocalized)) { fontNameStr = familyNameLocalized.fString; // check against permissible list of names for (int i = 0; i < whitelistCount; ++i) { if (fontNameStr.equals(whitelist[i].fFontName)) { return i; } } } #if WHITELIST_DEBUG SkAutoTUnref<SkTypeface::LocalizedStrings> debugIter( SkOTUtils::LocalizedStrings_NameTable::CreateForFamilyNames(*tf)); while (debugIter->next(&familyNameLocalized)) { SkDebugf("no match fontName=\"%s\"\n", familyNameLocalized.fString.c_str()); } #endif return -1; }
static void TestString(skiatest::Reporter* reporter) { SkString a; SkString b((size_t)0); SkString c(""); SkString d(NULL, 0); REPORTER_ASSERT(reporter, a.isEmpty()); REPORTER_ASSERT(reporter, a == b && a == c && a == d); a.set("hello"); b.set("hellox", 5); c.set(a); d.resize(5); memcpy(d.writable_str(), "helloz", 5); REPORTER_ASSERT(reporter, !a.isEmpty()); REPORTER_ASSERT(reporter, a.size() == 5); REPORTER_ASSERT(reporter, a == b && a == c && a == d); REPORTER_ASSERT(reporter, a.equals("hello", 5)); REPORTER_ASSERT(reporter, a.equals("hello")); REPORTER_ASSERT(reporter, !a.equals("help")); SkString e(a); SkString f("hello"); SkString g("helloz", 5); REPORTER_ASSERT(reporter, a == e && a == f && a == g); b.set("world"); c = b; REPORTER_ASSERT(reporter, a != b && a != c && b == c); a.append(" world"); e.append("worldz", 5); e.insert(5, " "); f.set("world"); f.prepend("hello "); REPORTER_ASSERT(reporter, a.equals("hello world") && a == e && a == f); a.reset(); b.resize(0); REPORTER_ASSERT(reporter, a.isEmpty() && b.isEmpty() && a == b); a.set("a"); a.set("ab"); a.set("abc"); a.set("abcd"); a.set(""); a.appendS64(72036854775808LL, 0); REPORTER_ASSERT(reporter, a.equals("72036854775808")); a.set(""); a.appendS64(-1844674407370LL, 0); REPORTER_ASSERT(reporter, a.equals("-1844674407370")); a.set(""); a.appendS64(73709551616LL, 15); REPORTER_ASSERT(reporter, a.equals("000073709551616")); a.set(""); a.appendS64(-429496729612LL, 15); REPORTER_ASSERT(reporter, a.equals("-000429496729612")); }
static void TestString(skiatest::Reporter* reporter) { SkString a; SkString b((size_t)0); SkString c(""); SkString d(NULL, 0); REPORTER_ASSERT(reporter, a.isEmpty()); REPORTER_ASSERT(reporter, a == b && a == c && a == d); a.set("hello"); b.set("hellox", 5); c.set(a); d.resize(5); memcpy(d.writable_str(), "helloz", 5); REPORTER_ASSERT(reporter, !a.isEmpty()); REPORTER_ASSERT(reporter, a.size() == 5); REPORTER_ASSERT(reporter, a == b && a == c && a == d); REPORTER_ASSERT(reporter, a.equals("hello", 5)); REPORTER_ASSERT(reporter, a.equals("hello")); REPORTER_ASSERT(reporter, !a.equals("help")); SkString e(a); SkString f("hello"); SkString g("helloz", 5); REPORTER_ASSERT(reporter, a == e && a == f && a == g); b.set("world"); c = b; REPORTER_ASSERT(reporter, a != b && a != c && b == c); a.append(" world"); e.append("worldz", 5); e.insert(5, " "); f.set("world"); f.prepend("hello "); REPORTER_ASSERT(reporter, a.equals("hello world") && a == e && a == f); a.reset(); b.resize(0); REPORTER_ASSERT(reporter, a.isEmpty() && b.isEmpty() && a == b); a.set("a"); a.set("ab"); a.set("abc"); a.set("abcd"); a.set(""); a.appendS64(72036854775808LL, 0); REPORTER_ASSERT(reporter, a.equals("72036854775808")); a.set(""); a.appendS64(-1844674407370LL, 0); REPORTER_ASSERT(reporter, a.equals("-1844674407370")); a.set(""); a.appendS64(73709551616LL, 15); REPORTER_ASSERT(reporter, a.equals("000073709551616")); a.set(""); a.appendS64(-429496729612LL, 15); REPORTER_ASSERT(reporter, a.equals("-000429496729612")); static const struct { SkScalar fValue; const char* fString; } gRec[] = { { 0, "0" }, { SK_Scalar1, "1" }, { -SK_Scalar1, "-1" }, { SK_Scalar1/2, "0.5" }, #ifdef SK_SCALAR_IS_FLOAT { 3.4028234e38f, "3.4028235e+38" }, { -3.4028234e38f, "-3.4028235e+38" }, #endif }; for (size_t i = 0; i < SK_ARRAY_COUNT(gRec); i++) { a.reset(); a.appendScalar(gRec[i].fValue); REPORTER_ASSERT(reporter, a.size() <= SkStrAppendScalar_MaxSize); // SkDebugf(" received <%s> expected <%s>\n", a.c_str(), gRec[i].fString); REPORTER_ASSERT(reporter, a.equals(gRec[i].fString)); } }
bool SkSVGPaint::writeChangedAttributes(SkSVGParser& parser, SkSVGPaint& current, bool* changed) { SkSVGPaint& lastState = parser.fLastFlush; for (int index = kInitial + 1; index < kTerminal; index++) { if (changed[index] == false) continue; SkString* topAttr = current[index]; size_t attrLength = topAttr->size(); if (attrLength == 0) continue; const char* attrValue = topAttr->c_str(); SkString* lastAttr = lastState[index]; switch(index) { case kClipPath: case kClipRule: case kEnableBackground: break; case kFill: if (topAttr->equals("none") == false && lastAttr->equals("none") == true) parser._addAttribute("stroke", "false"); goto fillStrokeAttrCommon; case kFillRule: case kFilter: case kFontFamily: break; case kFontSize: parser._addAttributeLen("textSize", attrValue, attrLength); break; case kLetterSpacing: parser._addAttributeLen("textTracking", attrValue, attrLength); break; case kMask: break; case kOpacity: break; case kStopColor: break; case kStopOpacity: break; case kStroke: if (topAttr->equals("none") == false && lastAttr->equals("none") == true) parser._addAttribute("stroke", "true"); fillStrokeAttrCommon: if (strncmp(attrValue, "url(", 4) == 0) { SkASSERT(attrValue[4] == '#'); const char* idStart = attrValue + 5; const char* idEnd = strrchr(attrValue, ')'); SkASSERT(idStart < idEnd); SkString id(idStart, idEnd - idStart); SkSVGElement* found; if (strncmp(id.c_str(), "mask", 4) != 0) { bool itsFound = parser.fIDs.find(id.c_str(), &found); SkASSERT(itsFound); SkASSERT(found->getType() == SkSVGType_LinearGradient || found->getType() == SkSVGType_RadialGradient); } parser._addAttribute("shader", id.c_str()); } break; case kStroke_Dasharray: break; case kStroke_Linecap: parser._addAttributeLen("strokeCap", attrValue, attrLength); break; case kStroke_Linejoin: parser._addAttributeLen("strokeJoin", attrValue, attrLength); break; case kStroke_Miterlimit: parser._addAttributeLen("strokeMiter", attrValue, attrLength); break; case kStroke_Width: parser._addAttributeLen("strokeWidth", attrValue, attrLength); case kStyle: case kTransform: break; default: SkASSERT(0); return false; } } return true; }
bool SkSVGPaint::flush(SkSVGParser& parser, bool isFlushable, bool isDef) { SkSVGPaint current; SkSVGPaint* walking = parser.fHead; int index; while (walking != NULL) { for (index = kInitial + 1; index < kTerminal; index++) { SkString* lastAttr = (*walking)[index]; if (lastAttr->size() == 0) continue; if (current[index]->size() > 0) continue; current[index]->set(*lastAttr); } walking = walking->fNext; } bool paintChanged = false; SkSVGPaint& lastState = parser.fLastFlush; if (isFlushable == false) { if (isDef == true) { if (current.f_mask.size() > 0 && current.f_mask.equals(lastState.f_mask) == false) { SkSVGElement* found; const char* idStart = strchr(current.f_mask.c_str(), '#'); SkASSERT(idStart); SkString id(idStart + 1, strlen(idStart) - 2); bool itsFound = parser.fIDs.find(id.c_str(), &found); SkASSERT(itsFound); SkSVGElement* gradient = found->getGradient(); if (gradient) { gradient->write(parser, current.f_fill); gradient->write(parser, current.f_stroke); } } } goto setLast; } { bool changed[kTerminal]; memset(changed, 0, sizeof(changed)); for (index = kInitial + 1; index < kTerminal; index++) { if (index == kTransform || index == kClipPath || index == kStopColor || index == kStopOpacity || index == kClipRule || index == kFillRule) continue; SkString* lastAttr = lastState[index]; SkString* currentAttr = current[index]; paintChanged |= changed[index] = lastAttr->equals(*currentAttr) == false; } if (paintChanged) { if (current.f_mask.size() > 0) { if (current.f_fill.equals("none") == false && strncmp(current.f_fill.c_str(), "url(#", 5) != 0) { SkASSERT(current.f_fill.c_str()[0] == '#'); SkString replacement("url(#mask"); replacement.append(current.f_fill.c_str() + 1); replacement.appendUnichar(')'); current.f_fill.set(replacement); } if (current.f_stroke.equals("none") == false && strncmp(current.f_stroke.c_str(), "url(#", 5) != 0) { SkASSERT(current.f_stroke.c_str()[0] == '#'); SkString replacement("url(#mask"); replacement.append(current.f_stroke.c_str() + 1); replacement.appendUnichar(')'); current.f_stroke.set(replacement); } } if (current.f_fill.equals("none") && current.f_stroke.equals("none")) current.f_opacity.set("0"); if (parser.fSuppressPaint == false) { parser._startElement("paint"); bool success = writeChangedAttributes(parser, current, changed); if (success == false) return paintChanged; success = writeChangedElements(parser, current, changed); if (success == false) return paintChanged; parser._endElement(); // paint } } } setLast: for (index = kInitial + 1; index < kTerminal; index++) { SkString* lastAttr = lastState[index]; SkString* currentAttr = current[index]; lastAttr->set(*currentAttr); } return paintChanged; }
bool SkSVGPaint::writeChangedElements(SkSVGParser& parser, SkSVGPaint& current, bool* changed) { SkSVGPaint& lastState = parser.fLastFlush; for (int index = kInitial + 1; index < kTerminal; index++) { SkString* topAttr = current[index]; size_t attrLength = topAttr->size(); if (attrLength == 0) continue; const char* attrValue = topAttr->c_str(); SkString* lastAttr = lastState[index]; switch(index) { case kClipPath: case kClipRule: // !!! need to add this outside of paint break; case kEnableBackground: // !!! don't know what to do with this break; case kFill: goto addColor; case kFillRule: case kFilter: break; case kFontFamily: parser._startElement("typeface"); parser._addAttributeLen("fontName", attrValue, attrLength); parser._endElement(); // typeface break; case kFontSize: case kLetterSpacing: break; case kMask: case kOpacity: if (changed[kStroke] == false && changed[kFill] == false) { parser._startElement("color"); SkString& opacity = current.f_opacity; parser._addAttributeLen("color", parser.fLastColor.c_str(), parser.fLastColor.size()); parser._addAttributeLen("alpha", opacity.c_str(), opacity.size()); parser._endElement(); // color } break; case kStopColor: break; case kStopOpacity: break; case kStroke: addColor: if (strncmp(lastAttr->c_str(), "url(", 4) == 0 && strncmp(attrValue, "url(", 4) != 0) { parser._startElement("shader"); parser._endElement(); } if (topAttr->equals(*lastAttr)) continue; { bool urlRef = strncmp(attrValue, "url(", 4) == 0; bool colorNone = strcmp(attrValue, "none") == 0; bool lastEqual = parser.fLastColor.equals(attrValue, attrLength); bool newColor = urlRef == false && colorNone == false && lastEqual == false; if (newColor || changed[kOpacity]) { parser._startElement("color"); if (newColor || changed[kOpacity]) { parser._addAttributeLen("color", attrValue, attrLength); parser.fLastColor.set(attrValue, attrLength); } if (changed[kOpacity]) { SkString& opacity = current.f_opacity; parser._addAttributeLen("alpha", opacity.c_str(), opacity.size()); } parser._endElement(); // color } } break; case kStroke_Dasharray: parser._startElement("dash"); SkSVGParser::ConvertToArray(*topAttr); parser._addAttribute("intervals", topAttr->c_str()); parser._endElement(); // dash break; case kStroke_Linecap: case kStroke_Linejoin: case kStroke_Miterlimit: case kStroke_Width: case kStyle: case kTransform: break; default: SkASSERT(0); return false; } } return true; }
void ParseConfigs(const SkCommandLineFlags::StringArray& configs, SkCommandLineConfigArray* outResult) { outResult->reset(); for (int i = 0; i < configs.count(); ++i) { SkString extendedBackend; SkString extendedOptions; SkString simpleBackend; SkTArray<SkString> vias; SkString tag(configs[i]); SkTArray<SkString> parts; SkStrSplit(tag.c_str(), "(", kStrict_SkStrSplitMode, &parts); if (parts.count() == 2) { SkTArray<SkString> parts2; SkStrSplit(parts[1].c_str(), ")", kStrict_SkStrSplitMode, &parts2); if (parts2.count() == 2 && parts2[1].isEmpty()) { SkStrSplit(parts[0].c_str(), "-", kStrict_SkStrSplitMode, &vias); if (vias.count()) { extendedBackend = vias[vias.count() - 1]; vias.pop_back(); } else { extendedBackend = parts[0]; } extendedOptions = parts2[0]; simpleBackend.printf("%s(%s)", extendedBackend.c_str(), extendedOptions.c_str()); } } if (extendedBackend.isEmpty()) { simpleBackend = tag; SkStrSplit(tag.c_str(), "-", kStrict_SkStrSplitMode, &vias); if (vias.count()) { simpleBackend = vias[vias.count() - 1]; vias.pop_back(); } // Note: no #if SK_ANGLE: this is a special rule in the via-tag grammar. if (vias.count() && simpleBackend.equals("gl") && vias[vias.count() - 1].equals("angle")) { simpleBackend = "angle-gl"; vias.pop_back(); } for (auto& predefinedConfig : gPredefinedConfigs) { if (simpleBackend.equals(predefinedConfig.predefinedConfig)) { extendedBackend = predefinedConfig.backend; extendedOptions = predefinedConfig.options; break; } } } SkCommandLineConfig* parsedConfig = nullptr; #if SK_SUPPORT_GPU if (extendedBackend.equals("gpu")) { parsedConfig = parse_command_line_config_gpu(tag, vias, extendedOptions); } #endif if (!parsedConfig) { parsedConfig = new SkCommandLineConfig(tag, simpleBackend, vias); } outResult->emplace_back(parsedConfig); } }