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 | |
8 | #include "src/core/SkRasterPipeline.h" |
9 | #include "src/core/SkReadBuffer.h" |
10 | #include "src/core/SkWriteBuffer.h" |
11 | #include "src/shaders/gradients/SkRadialGradient.h" |
12 | |
13 | namespace { |
14 | |
15 | SkMatrix rad_to_unit_matrix(const SkPoint& center, SkScalar radius) { |
16 | SkScalar inv = SkScalarInvert(radius); |
17 | |
18 | SkMatrix matrix; |
19 | matrix.setTranslate(-center.fX, -center.fY); |
20 | matrix.postScale(inv, inv); |
21 | return matrix; |
22 | } |
23 | |
24 | } // namespace |
25 | |
26 | ///////////////////////////////////////////////////////////////////// |
27 | |
28 | SkRadialGradient::SkRadialGradient(const SkPoint& center, SkScalar radius, const Descriptor& desc) |
29 | : SkGradientShaderBase(desc, rad_to_unit_matrix(center, radius)) |
30 | , fCenter(center) |
31 | , fRadius(radius) { |
32 | } |
33 | |
34 | SkShader::GradientType SkRadialGradient::asAGradient(GradientInfo* info) const { |
35 | if (info) { |
36 | commonAsAGradient(info); |
37 | info->fPoint[0] = fCenter; |
38 | info->fRadius[0] = fRadius; |
39 | } |
40 | return kRadial_GradientType; |
41 | } |
42 | |
43 | sk_sp<SkFlattenable> SkRadialGradient::CreateProc(SkReadBuffer& buffer) { |
44 | DescriptorScope desc; |
45 | if (!desc.unflatten(buffer)) { |
46 | return nullptr; |
47 | } |
48 | const SkPoint center = buffer.readPoint(); |
49 | const SkScalar radius = buffer.readScalar(); |
50 | return SkGradientShader::MakeRadial(center, radius, desc.fColors, std::move(desc.fColorSpace), |
51 | desc.fPos, desc.fCount, desc.fTileMode, desc.fGradFlags, |
52 | desc.fLocalMatrix); |
53 | } |
54 | |
55 | void SkRadialGradient::flatten(SkWriteBuffer& buffer) const { |
56 | this->INHERITED::flatten(buffer); |
57 | buffer.writePoint(fCenter); |
58 | buffer.writeScalar(fRadius); |
59 | } |
60 | |
61 | void SkRadialGradient::appendGradientStages(SkArenaAlloc*, SkRasterPipeline* p, |
62 | SkRasterPipeline*) const { |
63 | p->append(SkRasterPipeline::xy_to_radius); |
64 | } |
65 | |
66 | skvm::F32 SkRadialGradient::transformT(skvm::Builder* p, skvm::Uniforms*, |
67 | skvm::F32 x, skvm::F32 y, skvm::I32* mask) const { |
68 | return sqrt(x*x + y*y); |
69 | } |
70 | |
71 | ///////////////////////////////////////////////////////////////////// |
72 | |
73 | #if SK_SUPPORT_GPU |
74 | |
75 | #include "src/gpu/gradients/GrGradientShader.h" |
76 | |
77 | std::unique_ptr<GrFragmentProcessor> SkRadialGradient::asFragmentProcessor( |
78 | const GrFPArgs& args) const { |
79 | return GrGradientShader::MakeRadial(*this, args); |
80 | } |
81 | |
82 | #endif |
83 | |