1 /* 2 * Copyright 2017 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #include "include/core/SkTypes.h" 9 10 #if defined(SK_ENABLE_SVG) 11 12 #include "include/core/SkCanvas.h" 13 #include "include/core/SkRect.h" 14 #include "include/core/SkStream.h" 15 #include "modules/skshaper/utils/FactoryHelpers.h" 16 #include "modules/svg/include/SkSVGDOM.h" 17 #include "modules/svg/include/SkSVGNode.h" 18 #include "src/core/SkOSFile.h" 19 #include "src/utils/SkOSPath.h" 20 #include "src/xml/SkDOM.h" 21 #include "tools/Resources.h" 22 #include "tools/fonts/FontToolUtils.h" 23 #include "tools/viewer/Slide.h" 24 25 namespace { 26 class AnimatedSVGSlide : public Slide { 27 inline static constexpr auto kAnimationIterations = 5; 28 enum State { 29 kZoomIn, 30 kScroll, 31 kZoomOut 32 }; 33 sk_sp<SkSVGDOM> fDom; 34 const char* fResource = nullptr; 35 State fState = kZoomIn; 36 int fAnimationLoop = kAnimationIterations; 37 SkScalar fDelta = 1; 38 39 public: AnimatedSVGSlide(const char * r,const char * n)40 AnimatedSVGSlide(const char* r, const char* n) : fResource(r) { fName = n; } 41 load(SkScalar w,SkScalar h)42 void load(SkScalar w, SkScalar h) override { 43 SkASSERT(fResource); 44 auto data = GetResourceAsData(fResource); 45 if (!data) { 46 SkDebugf("Resource not found: \"%s\"\n", fResource); 47 return; 48 } 49 SkMemoryStream svgStream(std::move(data)); 50 51 fDom = SkSVGDOM::Builder() 52 .setFontManager(ToolUtils::TestFontMgr()) 53 .setTextShapingFactory(SkShapers::BestAvailable()) 54 .make(svgStream); 55 if (fDom) { 56 fDom->setContainerSize(SkSize::Make(w, h)); 57 } 58 } 59 draw(SkCanvas * canvas)60 void draw(SkCanvas* canvas) override { 61 if (fDom) { 62 canvas->setMatrix(SkMatrix::Scale(3, 3)); 63 canvas->clipRect(SkRect::MakeLTRB(0, 0, 400, 400)); 64 switch (fState) { 65 case kZoomIn: 66 fDelta += 0.2f; 67 canvas->scale(fDelta, fDelta); 68 break; 69 case kScroll: 70 if (fAnimationLoop > kAnimationIterations/2) { 71 fDelta += 80.f; 72 } else { 73 fDelta -= 80.f; 74 } 75 canvas->scale(fDelta, fDelta); 76 canvas->translate(fDelta, 0); 77 break; 78 case kZoomOut: 79 fDelta += 0.2f; 80 canvas->scale(fDelta, fDelta); 81 break; 82 } 83 84 fDom->render(canvas); 85 } 86 } 87 resize(SkScalar w,SkScalar h)88 void resize(SkScalar w, SkScalar h) override { 89 if (fDom) { 90 fDom->setContainerSize(SkSize::Make(w, h)); 91 } 92 } 93 animate(double nanos)94 bool animate(double nanos) override { 95 if (!fDom) { 96 return false; 97 } 98 99 --fAnimationLoop; 100 if (fAnimationLoop == 0) { 101 fAnimationLoop = kAnimationIterations; 102 switch (fState) { 103 case kZoomIn: 104 fState = kScroll; 105 fDelta = 0; 106 break; 107 case kScroll: 108 fState = kZoomOut; 109 fDelta = 2; 110 break; 111 case kZoomOut: 112 fState = kZoomIn; 113 fDelta = 1; 114 break; 115 } 116 } 117 return true; 118 } 119 }; 120 } // namespace 121 122 DEF_SLIDE( return new AnimatedSVGSlide("Cowboy.svg", "SampleCowboy"); ) 123 124 #endif // defined(SK_ENABLE_SVG) 125