blob: 2962d0f971e0ceccc12368b32ee44eaf65f9d0f6 [file] [log] [blame]
Romain Guy55a384c2009-08-12 10:58:02 -07001// Copyright (C) 2009 The Android Open Source Project
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15#pragma version(1)
16#pragma stateVertex(PVBackground)
17#pragma stateFragment(PFBackground)
18#pragma stateFragmentStore(PFSBackground)
19
20#define RSID_STATE 0
21#define RSID_FRAME_COUNT 0
22#define RSID_BLADES_COUNT 1
23#define RSID_WIDTH 2
24#define RSID_HEIGHT 3
25
26#define RSID_BLADES 1
27#define BLADE_STRUCT_FIELDS_COUNT 12
28#define BLADE_STRUCT_ANGLE 0
29#define BLADE_STRUCT_SIZE 1
30#define BLADE_STRUCT_XPOS 2
31#define BLADE_STRUCT_YPOS 3
32#define BLADE_STRUCT_OFFSET 4
33#define BLADE_STRUCT_SCALE 5
34#define BLADE_STRUCT_LENGTHX 6
35#define BLADE_STRUCT_LENGTHY 7
36#define BLADE_STRUCT_HARDNESS 8
37#define BLADE_STRUCT_H 9
38#define BLADE_STRUCT_S 10
39#define BLADE_STRUCT_B 11
40
41#define TESSELATION 2.0f
42
43#define MAX_BEND 0.09f
44
45#define MIDNIGHT 0.0f
46#define MORNING 0.375f
47#define AFTERNOON 0.6f
48#define DUSK 0.8f
49
50#define SECONDS_IN_DAY 24.0f * 3600.0f
51
52#define PI 3.1415926f
53
54#define REAL_TIME 0
55
56float time(int frameCount) {
57 if (REAL_TIME) {
58 return (hour() * 3600.0f + minute() * 60.0f + second()) / SECONDS_IN_DAY;
59 }
60 return (frameCount % 180) / 180.0f;
61}
62
63void alpha(float a) {
64 color(1.0f, 1.0f, 1.0f, a);
65}
66
67void drawNight(int width, int height) {
68 bindProgramFragment(NAMED_PFNight);
69 bindTexture(NAMED_PFNight, 0, NAMED_TNight);
70 drawQuadTexCoords(
71 0.0f, -32.0f, 0.0f,
72 0.0f, 1.0f,
73 width, -32.0f, 0.0f,
74 2.0f, 1.0f,
75 width, 1024.0f - 32.0f, 0.0f,
76 2.0f, 0.0f,
77 0.0f, 1024.0f - 32.0f, 0.0f,
78 0.0f, 0.0f);
79 bindProgramFragment(NAMED_PFBackground);
80}
81
82void drawSunrise(int width, int height) {
83 bindTexture(NAMED_PFBackground, 0, NAMED_TSunrise);
84 drawRect(0.0f, 0.0f, width, height, 0.0f);
85}
86
87void drawNoon(int width, int height) {
88 bindTexture(NAMED_PFBackground, 0, NAMED_TSky);
89 drawRect(0.0f, 0.0f, width, height, 0.0f);
90}
91
92void drawSunset(int width, int height) {
93 bindTexture(NAMED_PFBackground, 0, NAMED_TSunset);
94 drawRect(0.0f, 0.0f, width, height, 0.0f);
95}
96
97void drawBlade(int index, float now, int frameCount) {
98 float *bladeStruct = loadArrayF(RSID_BLADES, index);
99 float offset = bladeStruct[BLADE_STRUCT_OFFSET];
100 float scale = bladeStruct[BLADE_STRUCT_SCALE];
101 float angle = bladeStruct[BLADE_STRUCT_ANGLE];
102 float hardness = bladeStruct[BLADE_STRUCT_HARDNESS];
103
104 float xpos = bladeStruct[BLADE_STRUCT_XPOS];
105 float ypos = bladeStruct[BLADE_STRUCT_YPOS];
106
107 float lengthX = bladeStruct[BLADE_STRUCT_LENGTHX];
108 float lengthY = bladeStruct[BLADE_STRUCT_LENGTHY];
109
110 int size = bladeStruct[BLADE_STRUCT_SIZE];
111
112 float h = bladeStruct[BLADE_STRUCT_H];
113 float s = bladeStruct[BLADE_STRUCT_S];
114 float b = bladeStruct[BLADE_STRUCT_B];
115
116 float newB = 1.0f;
117 if (now >= MIDNIGHT && now < MORNING) {
118 newB = now / MORNING;
119 }
120
121 if (now >= AFTERNOON && now < DUSK) {
122 newB = 1.0f - normf(AFTERNOON, DUSK, now);
123 }
124
125 if (now >= DUSK) {
126 newB = 0.0f;
127 }
128
129 hsb(h, s, lerpf(0, b, newB), 1.0f);
130
131 float newAngle = turbulencef2(xpos * 0.006f, frameCount * 0.006f, 4.0f) - 0.5f;
132 newAngle /= 2.0f;
133 angle = clampf(angle + (newAngle + offset - angle) * 0.15f, -MAX_BEND, MAX_BEND);
134
135 float currentAngle = PI / 2.0f;
136
137 float bottomX = xpos;
138 float bottomY = ypos;
139
140 int i = size * TESSELATION;
141 float lx = lengthX / TESSELATION;
142 float ly = lengthY / TESSELATION;
143 float ss = 4.0f / i + scale / TESSELATION;
144 float sh = 0.5f / TESSELATION;
145 float d = angle * hardness / TESSELATION;
146
147 for ( ; i > 0; i--) {
148 float topX = bottomX - cosf(currentAngle) * size * lx;
149 float topY = bottomY - sinf(currentAngle) * size * ly;
150 currentAngle += d;
151
152 float spi = (i - 1) * ss;
153 float si = i * ss;
154
155 drawQuad(topX + spi, topY, 0.0f,
156 topX - spi, topY, 0.0f,
157 bottomX - si, bottomY + sh, 0.0f,
158 bottomX + si, bottomY + sh, 0.0f);
159
160 bottomX = topX;
161 bottomY = topY;
162 }
163
164 storeF(RSID_BLADES, index + BLADE_STRUCT_ANGLE, angle);
165}
166
167void drawBlades(float now, int frameCount) {
168 // For anti-aliasing
169 bindTexture(NAMED_PFBackground, 0, NAMED_TAa);
170
171 int bladesCount = loadI32(RSID_STATE, RSID_BLADES_COUNT);
172 int count = bladesCount * BLADE_STRUCT_FIELDS_COUNT;
173
174 int i = 0;
175 for ( ; i < count; i += BLADE_STRUCT_FIELDS_COUNT) {
176 drawBlade(i, now, frameCount);
177 }
178}
179
180int main(int launchID) {
181 int width = loadI32(RSID_STATE, RSID_WIDTH);
182 int height = loadI32(RSID_STATE, RSID_HEIGHT);
183
184 int frameCount = loadI32(RSID_STATE, RSID_FRAME_COUNT);
185 float now = time(frameCount);
186 alpha(1.0f);
187
188 if (now >= MIDNIGHT && now < MORNING) {
189 drawNight(width, height);
190 alpha(normf(MIDNIGHT, MORNING, now));
191 drawSunrise(width, height);
192 } else if (now >= MORNING && now < AFTERNOON) {
193 drawSunrise(width, height);
194 alpha(normf(MORNING, AFTERNOON, now));
195 drawNoon(width, height);
196 } else if (now >= AFTERNOON && now < DUSK) {
197 drawNoon(width, height);
198 alpha(normf(AFTERNOON, DUSK, now));
199 drawSunset(width, height);
200 } else if (now >= DUSK) {
201 drawNight(width, height);
202 alpha(1.0f - normf(DUSK, 1.0f, now));
203 drawSunset(width, height);
204 }
205
206 drawBlades(now, frameCount);
207
208 frameCount++;
209 storeI32(RSID_STATE, RSID_FRAME_COUNT, frameCount);
210
211 return 1;
212}