1 /*
2 * Copyright 2015 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 "DecodeFile.h"
9 #include "SampleCode.h"
10 #include "Resources.h"
11 #include "SkCanvas.h"
12 #include "SkLightingShader.h"
13 #include "SkNormalSource.h"
14 #include "SkPoint3.h"
15
create_lights(SkScalar angle,SkScalar blue)16 static sk_sp<SkLights> create_lights(SkScalar angle, SkScalar blue) {
17
18 const SkVector3 dir = SkVector3::Make(SkScalarSin(angle)*SkScalarSin(SK_ScalarPI*0.25f),
19 SkScalarCos(angle)*SkScalarSin(SK_ScalarPI*0.25f),
20 SkScalarCos(SK_ScalarPI*0.25f));
21
22 SkLights::Builder builder;
23
24 builder.add(SkLights::Light::MakeDirectional(SkColor3f::Make(1.0f, 1.0f, blue), dir));
25 builder.setAmbientLightColor(SkColor3f::Make(0.1f, 0.1f, 0.1f));
26
27 return builder.finish();
28 }
29
30 ////////////////////////////////////////////////////////////////////////////
31
32 class LightingView : public SampleView {
33 public:
34 SkBitmap fDiffuseBitmap;
35 SkBitmap fNormalBitmap;
36 SkScalar fLightAngle;
37 SkScalar fColorFactor;
38
LightingView()39 LightingView() {
40 SkString diffusePath = GetResourcePath("brickwork-texture.jpg");
41 decode_file(diffusePath.c_str(), &fDiffuseBitmap);
42 SkString normalPath = GetResourcePath("brickwork_normal-map.jpg");
43 decode_file(normalPath.c_str(), &fNormalBitmap);
44
45 fLightAngle = 0.0f;
46 fColorFactor = 0.0f;
47 }
48
49 protected:
50 // overrides from SkEventSink
onQuery(SkEvent * evt)51 bool onQuery(SkEvent* evt) override {
52 if (SampleCode::TitleQ(*evt)) {
53 SampleCode::TitleR(evt, "Lighting");
54 return true;
55 }
56 return this->INHERITED::onQuery(evt);
57 }
58
onDrawContent(SkCanvas * canvas)59 void onDrawContent(SkCanvas* canvas) override {
60 fLightAngle += 0.015f;
61 fColorFactor += 0.01f;
62 if (fColorFactor > 1.0f) {
63 fColorFactor = 0.0f;
64 }
65
66 sk_sp<SkLights> lights(create_lights(fLightAngle, fColorFactor));
67 SkPaint paint;
68 sk_sp<SkShader> normalMap = SkShader::MakeBitmapShader(fNormalBitmap,
69 SkShader::kClamp_TileMode, SkShader::kClamp_TileMode, nullptr);
70 sk_sp<SkNormalSource> normalSource = SkNormalSource::MakeFromNormalMap(
71 std::move(normalMap), SkMatrix::I());
72 sk_sp<SkShader> diffuseShader = SkShader::MakeBitmapShader(fDiffuseBitmap,
73 SkShader::kClamp_TileMode, SkShader::kClamp_TileMode, nullptr);
74 paint.setShader(SkLightingShader::Make(std::move(diffuseShader), std::move(normalSource),
75 std::move(lights)));
76 paint.setColor(SK_ColorBLACK);
77
78 SkRect r = SkRect::MakeWH((SkScalar)fDiffuseBitmap.width(),
79 (SkScalar)fDiffuseBitmap.height());
80 canvas->drawRect(r, paint);
81
82 // so we're constantly updating
83 this->inval(nullptr);
84 }
85
onFindClickHandler(SkScalar x,SkScalar y,unsigned modi)86 SkView::Click* onFindClickHandler(SkScalar x, SkScalar y, unsigned modi) override {
87 this->inval(nullptr);
88 return this->INHERITED::onFindClickHandler(x, y, modi);
89 }
90
91 private:
92 typedef SampleView INHERITED;
93 };
94
95 //////////////////////////////////////////////////////////////////////////////
96
MyFactory()97 static SkView* MyFactory() { return new LightingView; }
98 static SkViewRegister reg(MyFactory);
99