imagefiltersgraph.cpp 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. /*
  2. * Copyright 2012 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. #include "gm/gm.h"
  8. #include "include/core/SkBitmap.h"
  9. #include "include/core/SkBlendMode.h"
  10. #include "include/core/SkCanvas.h"
  11. #include "include/core/SkColor.h"
  12. #include "include/core/SkColorFilter.h"
  13. #include "include/core/SkImage.h"
  14. #include "include/core/SkImageFilter.h"
  15. #include "include/core/SkPaint.h"
  16. #include "include/core/SkPoint.h"
  17. #include "include/core/SkRect.h"
  18. #include "include/core/SkRefCnt.h"
  19. #include "include/core/SkScalar.h"
  20. #include "include/core/SkSize.h"
  21. #include "include/core/SkString.h"
  22. #include "include/effects/SkArithmeticImageFilter.h"
  23. #include "include/effects/SkBlurImageFilter.h"
  24. #include "include/effects/SkColorFilterImageFilter.h"
  25. #include "include/effects/SkImageSource.h"
  26. #include "include/effects/SkMatrixConvolutionImageFilter.h"
  27. #include "include/effects/SkMergeImageFilter.h"
  28. #include "include/effects/SkMorphologyImageFilter.h"
  29. #include "include/effects/SkOffsetImageFilter.h"
  30. #include "include/effects/SkXfermodeImageFilter.h"
  31. #include "tools/ToolUtils.h"
  32. #include <utility>
  33. class ImageFiltersGraphGM : public skiagm::GM {
  34. public:
  35. ImageFiltersGraphGM() {}
  36. protected:
  37. SkString onShortName() override {
  38. return SkString("imagefiltersgraph");
  39. }
  40. SkISize onISize() override { return SkISize::Make(600, 150); }
  41. void onOnceBeforeDraw() override {
  42. fImage = SkImage::MakeFromBitmap(
  43. ToolUtils::create_string_bitmap(100, 100, SK_ColorWHITE, 20, 70, 96, "e"));
  44. }
  45. void onDraw(SkCanvas* canvas) override {
  46. canvas->clear(SK_ColorBLACK);
  47. {
  48. sk_sp<SkImageFilter> bitmapSource(SkImageSource::Make(fImage));
  49. sk_sp<SkColorFilter> cf(SkColorFilters::Blend(SK_ColorRED,
  50. SkBlendMode::kSrcIn));
  51. sk_sp<SkImageFilter> blur(SkBlurImageFilter::Make(4.0f, 4.0f, std::move(bitmapSource)));
  52. sk_sp<SkImageFilter> erode(SkErodeImageFilter::Make(4, 4, blur));
  53. sk_sp<SkImageFilter> color(SkColorFilterImageFilter::Make(std::move(cf),
  54. std::move(erode)));
  55. sk_sp<SkImageFilter> merge(SkMergeImageFilter::Make(blur, color));
  56. SkPaint paint;
  57. paint.setImageFilter(std::move(merge));
  58. canvas->drawPaint(paint);
  59. canvas->translate(SkIntToScalar(100), 0);
  60. }
  61. {
  62. sk_sp<SkImageFilter> morph(SkDilateImageFilter::Make(5, 5, nullptr));
  63. float matrix[20] = { 1, 0, 0, 0, 0,
  64. 0, 1, 0, 0, 0,
  65. 0, 0, 1, 0, 0,
  66. 0, 0, 0, 0.5f, 0 };
  67. sk_sp<SkColorFilter> matrixFilter(SkColorFilters::Matrix(matrix));
  68. sk_sp<SkImageFilter> colorMorph(SkColorFilterImageFilter::Make(std::move(matrixFilter),
  69. std::move(morph)));
  70. SkPaint paint;
  71. paint.setImageFilter(SkXfermodeImageFilter::Make(SkBlendMode::kSrcOver,
  72. std::move(colorMorph)));
  73. DrawClippedImage(canvas, fImage.get(), paint);
  74. canvas->translate(SkIntToScalar(100), 0);
  75. }
  76. {
  77. float matrix[20] = { 1, 0, 0, 0, 0,
  78. 0, 1, 0, 0, 0,
  79. 0, 0, 1, 0, 0,
  80. 0, 0, 0, 0.5f, 0 };
  81. sk_sp<SkColorFilter> matrixCF(SkColorFilters::Matrix(matrix));
  82. sk_sp<SkImageFilter> matrixFilter(SkColorFilterImageFilter::Make(std::move(matrixCF),
  83. nullptr));
  84. sk_sp<SkImageFilter> offsetFilter(SkOffsetImageFilter::Make(10.0f, 10.f,
  85. matrixFilter));
  86. SkPaint paint;
  87. paint.setImageFilter(SkArithmeticImageFilter::Make(
  88. 0, 1, 1, 0, true, std::move(matrixFilter), std::move(offsetFilter), nullptr));
  89. DrawClippedImage(canvas, fImage.get(), paint);
  90. canvas->translate(SkIntToScalar(100), 0);
  91. }
  92. {
  93. sk_sp<SkImageFilter> blur(SkBlurImageFilter::Make(SkIntToScalar(10),
  94. SkIntToScalar(10),
  95. nullptr));
  96. SkImageFilter::CropRect cropRect(SkRect::MakeWH(SkIntToScalar(95), SkIntToScalar(100)));
  97. SkPaint paint;
  98. paint.setImageFilter(
  99. SkXfermodeImageFilter::Make(SkBlendMode::kSrcIn, std::move(blur), nullptr,
  100. &cropRect));
  101. DrawClippedImage(canvas, fImage.get(), paint);
  102. canvas->translate(SkIntToScalar(100), 0);
  103. }
  104. {
  105. // Dilate -> matrix convolution.
  106. // This tests that a filter using asFragmentProcessor (matrix
  107. // convolution) correctly handles a non-zero source offset
  108. // (supplied by the dilate).
  109. sk_sp<SkImageFilter> dilate(SkDilateImageFilter::Make(5, 5, nullptr));
  110. SkScalar kernel[9] = {
  111. SkIntToScalar(-1), SkIntToScalar( -1 ), SkIntToScalar(-1),
  112. SkIntToScalar(-1), SkIntToScalar( 7 ), SkIntToScalar(-1),
  113. SkIntToScalar(-1), SkIntToScalar( -1 ), SkIntToScalar(-1),
  114. };
  115. SkISize kernelSize = SkISize::Make(3, 3);
  116. SkScalar gain = 1.0f, bias = SkIntToScalar(0);
  117. SkIPoint kernelOffset = SkIPoint::Make(1, 1);
  118. auto tileMode = SkMatrixConvolutionImageFilter::kClamp_TileMode;
  119. bool convolveAlpha = false;
  120. sk_sp<SkImageFilter> convolve(SkMatrixConvolutionImageFilter::Make(kernelSize,
  121. kernel,
  122. gain,
  123. bias,
  124. kernelOffset,
  125. tileMode,
  126. convolveAlpha,
  127. std::move(dilate)));
  128. SkPaint paint;
  129. paint.setImageFilter(std::move(convolve));
  130. DrawClippedImage(canvas, fImage.get(), paint);
  131. canvas->translate(SkIntToScalar(100), 0);
  132. }
  133. {
  134. // Test that crop offsets are absolute, not relative to the parent's crop rect.
  135. sk_sp<SkColorFilter> cf1(SkColorFilters::Blend(SK_ColorBLUE, SkBlendMode::kSrcIn));
  136. sk_sp<SkColorFilter> cf2(SkColorFilters::Blend(SK_ColorGREEN, SkBlendMode::kSrcIn));
  137. SkImageFilter::CropRect outerRect(SkRect::MakeXYWH(SkIntToScalar(10), SkIntToScalar(10),
  138. SkIntToScalar(80), SkIntToScalar(80)));
  139. SkImageFilter::CropRect innerRect(SkRect::MakeXYWH(SkIntToScalar(20), SkIntToScalar(20),
  140. SkIntToScalar(60), SkIntToScalar(60)));
  141. sk_sp<SkImageFilter> color1(SkColorFilterImageFilter::Make(std::move(cf1),
  142. nullptr,
  143. &outerRect));
  144. sk_sp<SkImageFilter> color2(SkColorFilterImageFilter::Make(std::move(cf2),
  145. std::move(color1),
  146. &innerRect));
  147. SkPaint paint;
  148. paint.setImageFilter(std::move(color2));
  149. paint.setColor(SK_ColorRED);
  150. canvas->drawRect(SkRect::MakeXYWH(0, 0, 100, 100), paint);
  151. canvas->translate(SkIntToScalar(100), 0);
  152. }
  153. }
  154. private:
  155. static void DrawClippedImage(SkCanvas* canvas, const SkImage* image, const SkPaint& paint) {
  156. canvas->save();
  157. canvas->clipRect(SkRect::MakeIWH(image->width(), image->height()));
  158. canvas->drawImage(image, 0, 0, &paint);
  159. canvas->restore();
  160. }
  161. sk_sp<SkImage> fImage;
  162. typedef GM INHERITED;
  163. };
  164. ///////////////////////////////////////////////////////////////////////////////
  165. DEF_GM(return new ImageFiltersGraphGM;)