443
by dcoles
Added Forum application along with unmodifed version of phpBB3 "Olympus" 3.0.0 |
1 |
<?php
|
2 |
/**
|
|
3 |
*
|
|
4 |
* @package VC
|
|
5 |
* @version $Id: captcha_gd.php,v 1.23 2007/10/05 14:36:32 acydburn Exp $
|
|
6 |
* @copyright (c) 2006 phpBB Group
|
|
7 |
* @license http://opensource.org/licenses/gpl-license.php GNU Public License
|
|
8 |
*
|
|
9 |
*/
|
|
10 |
||
11 |
/**
|
|
12 |
* @ignore
|
|
13 |
*/
|
|
14 |
if (!defined('IN_PHPBB')) |
|
15 |
{
|
|
16 |
exit; |
|
17 |
}
|
|
18 |
||
19 |
/**
|
|
20 |
* Original Author - Xore (Robert Hetzler)
|
|
21 |
* With contributions from Neothermic
|
|
22 |
*
|
|
23 |
* @package VC
|
|
24 |
*/
|
|
25 |
class captcha |
|
26 |
{
|
|
27 |
var $width = 360; |
|
28 |
var $height = 96; |
|
29 |
||
30 |
/**
|
|
31 |
* Create the image containing $code with a seed of $seed
|
|
32 |
*/
|
|
33 |
function execute($code, $seed) |
|
34 |
{
|
|
35 |
global $config; |
|
36 |
srand($seed); |
|
37 |
mt_srand($seed); |
|
38 |
||
39 |
// Create image
|
|
40 |
$img = imagecreatetruecolor($this->width, $this->height); |
|
41 |
||
42 |
// Generate colours
|
|
43 |
$colour = new colour_manager($img, array( |
|
44 |
'random' => true, |
|
45 |
'min_value' => 60, |
|
46 |
), 'hsv'); |
|
47 |
||
48 |
$scheme = $colour->colour_scheme('background', false); |
|
49 |
$scheme = $colour->mono_range($scheme, 10, false); |
|
50 |
shuffle($scheme); |
|
51 |
||
52 |
$bg_colours = array_splice($scheme, mt_rand(6, 12)); |
|
53 |
||
54 |
// Generate code characters
|
|
55 |
$characters = $sizes = $bounding_boxes = array(); |
|
56 |
$width_avail = $this->width - 15; |
|
57 |
$code_len = strlen($code); |
|
58 |
||
59 |
$captcha_bitmaps = $this->captcha_bitmaps(); |
|
60 |
for ($i = 0; $i < $code_len; ++$i) |
|
61 |
{
|
|
62 |
$characters[$i] = new char_cube3d($captcha_bitmaps, $code[$i]); |
|
63 |
||
64 |
list($min, $max) = $characters[$i]->range(); |
|
65 |
$sizes[$i] = mt_rand($min, $max); |
|
66 |
||
67 |
$box = $characters[$i]->dimensions($sizes[$i]); |
|
68 |
$width_avail -= ($box[2] - $box[0]); |
|
69 |
$bounding_boxes[$i] = $box; |
|
70 |
}
|
|
71 |
||
72 |
// Redistribute leftover x-space
|
|
73 |
$offset = array(); |
|
74 |
for ($i = 0; $i < $code_len; ++$i) |
|
75 |
{
|
|
76 |
$denom = ($code_len - $i); |
|
77 |
$denom = max(1.3, $denom); |
|
78 |
$offset[$i] = mt_rand(0, (1.5 * $width_avail) / $denom); |
|
79 |
$width_avail -= $offset[$i]; |
|
80 |
}
|
|
81 |
||
82 |
if ($config['captcha_gd_x_grid']) |
|
83 |
{
|
|
84 |
$grid = (int) $config['captcha_gd_x_grid']; |
|
85 |
for ($y = 0; $y < $this->height; $y += mt_rand($grid - 2, $grid + 2)) |
|
86 |
{
|
|
87 |
$current_colour = $scheme[array_rand($scheme)]; |
|
88 |
imageline($img, mt_rand(0,4), mt_rand($y - 3, $y), mt_rand($this->width - 5, $this->width), mt_rand($y - 3, $y), $current_colour); |
|
89 |
}
|
|
90 |
}
|
|
91 |
||
92 |
if ($config['captcha_gd_y_grid']) |
|
93 |
{
|
|
94 |
$grid = (int) $config['captcha_gd_y_grid']; |
|
95 |
for ($x = 0; $x < $this->width; $x += mt_rand($grid - 2, $grid + 2)) |
|
96 |
{
|
|
97 |
$current_colour = $scheme[array_rand($scheme)]; |
|
98 |
imagedashedline($img, mt_rand($x -3, $x + 3), mt_rand(0, 4), mt_rand($x -3, $x + 3), mt_rand($this->height - 5, $this->height), $current_colour); |
|
99 |
}
|
|
100 |
}
|
|
101 |
||
102 |
$xoffset = 5; |
|
103 |
for ($i = 0; $i < $code_len; ++$i) |
|
104 |
{
|
|
105 |
$dimm = $bounding_boxes[$i]; |
|
106 |
$xoffset += ($offset[$i] - $dimm[0]); |
|
107 |
$yoffset = mt_rand(-$dimm[1], $this->height - $dimm[3]); |
|
108 |
||
109 |
$characters[$i]->drawchar($sizes[$i], $xoffset, $yoffset, $img, $colour->get_resource('background'), $scheme); |
|
110 |
$xoffset += $dimm[2]; |
|
111 |
}
|
|
112 |
||
113 |
if ($config['captcha_gd_foreground_noise']) |
|
114 |
{
|
|
115 |
$this->noise_line($img, 0, 0, $this->width, $this->height, $colour->get_resource('background'), $scheme, $bg_colours); |
|
116 |
}
|
|
117 |
||
118 |
// Send image
|
|
119 |
header('Content-Type: image/png'); |
|
120 |
header('Cache-control: no-cache, no-store'); |
|
121 |
imagepng($img); |
|
122 |
imagedestroy($img); |
|
123 |
}
|
|
124 |
||
125 |
/**
|
|
126 |
* Noise line
|
|
127 |
*/
|
|
128 |
function noise_line($img, $min_x, $min_y, $max_x, $max_y, $bg, $font, $non_font) |
|
129 |
{
|
|
130 |
imagesetthickness($img, 2); |
|
131 |
||
132 |
$x1 = $min_x; |
|
133 |
$x2 = $max_x; |
|
134 |
$y1 = $min_y; |
|
135 |
$y2 = $min_y; |
|
136 |
||
137 |
do
|
|
138 |
{
|
|
139 |
$line = array_merge( |
|
140 |
array_fill(0, mt_rand(30, 60), $non_font[array_rand($non_font)]), |
|
141 |
array_fill(0, mt_rand(30, 60), $bg) |
|
142 |
);
|
|
143 |
||
144 |
imagesetstyle($img, $line); |
|
145 |
imageline($img, $x1, $y1, $x2, $y2, IMG_COLOR_STYLED); |
|
146 |
||
147 |
$y1 += mt_rand(12, 35); |
|
148 |
$y2 += mt_rand(12, 35); |
|
149 |
}
|
|
150 |
while ($y1 < $max_y && $y2 < $max_y); |
|
151 |
||
152 |
$x1 = $min_x; |
|
153 |
$x2 = $min_x; |
|
154 |
$y1 = $min_y; |
|
155 |
$y2 = $max_y; |
|
156 |
||
157 |
do
|
|
158 |
{
|
|
159 |
$line = array_merge( |
|
160 |
array_fill(0, mt_rand(30, 60), $non_font[array_rand($non_font)]), |
|
161 |
array_fill(0, mt_rand(30, 60), $bg) |
|
162 |
);
|
|
163 |
||
164 |
imagesetstyle($img, $line); |
|
165 |
imageline($img, $x1, $y1, $x2, $y2, IMG_COLOR_STYLED); |
|
166 |
||
167 |
$x1 += mt_rand(20, 35); |
|
168 |
$x2 += mt_rand(20, 35); |
|
169 |
}
|
|
170 |
while ($x1 < $max_x && $x2 < $max_x); |
|
171 |
imagesetthickness($img, 1); |
|
172 |
}
|
|
173 |
||
174 |
/**
|
|
175 |
* Return bitmaps
|
|
176 |
*/
|
|
177 |
function captcha_bitmaps() |
|
178 |
{
|
|
179 |
return array( |
|
180 |
'width' => 9, |
|
181 |
'height' => 15, |
|
182 |
'data' => array( |
|
183 |
||
184 |
'A' => array( |
|
185 |
array(0,0,0,0,1,0,0,0,0), |
|
186 |
array(0,0,0,1,0,1,0,0,0), |
|
187 |
array(0,0,0,1,0,1,0,0,0), |
|
188 |
array(0,0,0,1,0,1,0,0,0), |
|
189 |
array(0,0,1,0,0,0,1,0,0), |
|
190 |
array(0,0,1,0,0,0,1,0,0), |
|
191 |
array(0,0,1,0,0,0,1,0,0), |
|
192 |
array(0,1,0,0,0,0,0,1,0), |
|
193 |
array(0,1,0,0,0,0,0,1,0), |
|
194 |
array(0,1,1,1,1,1,1,1,0), |
|
195 |
array(0,1,0,0,0,0,0,1,0), |
|
196 |
array(1,0,0,0,0,0,0,0,1), |
|
197 |
array(1,0,0,0,0,0,0,0,1), |
|
198 |
array(1,0,0,0,0,0,0,0,1), |
|
199 |
array(1,0,0,0,0,0,0,0,1), |
|
200 |
),
|
|
201 |
'B' => array( |
|
202 |
array(1,1,1,1,1,1,1,0,0), |
|
203 |
array(1,0,0,0,0,0,0,1,0), |
|
204 |
array(1,0,0,0,0,0,0,0,1), |
|
205 |
array(1,0,0,0,0,0,0,0,1), |
|
206 |
array(1,0,0,0,0,0,0,0,1), |
|
207 |
array(1,0,0,0,0,0,0,0,1), |
|
208 |
array(1,0,0,0,0,0,0,1,0), |
|
209 |
array(1,1,1,1,1,1,1,0,0), |
|
210 |
array(1,0,0,0,0,0,0,1,0), |
|
211 |
array(1,0,0,0,0,0,0,0,1), |
|
212 |
array(1,0,0,0,0,0,0,0,1), |
|
213 |
array(1,0,0,0,0,0,0,0,1), |
|
214 |
array(1,0,0,0,0,0,0,0,1), |
|
215 |
array(1,0,0,0,0,0,0,1,0), |
|
216 |
array(1,1,1,1,1,1,1,0,0), |
|
217 |
),
|
|
218 |
'C' => array( |
|
219 |
array(0,0,1,1,1,1,1,0,0), |
|
220 |
array(0,1,0,0,0,0,0,1,0), |
|
221 |
array(1,0,0,0,0,0,0,0,1), |
|
222 |
array(1,0,0,0,0,0,0,0,1), |
|
223 |
array(1,0,0,0,0,0,0,0,0), |
|
224 |
array(1,0,0,0,0,0,0,0,0), |
|
225 |
array(1,0,0,0,0,0,0,0,0), |
|
226 |
array(1,0,0,0,0,0,0,0,0), |
|
227 |
array(1,0,0,0,0,0,0,0,0), |
|
228 |
array(1,0,0,0,0,0,0,0,0), |
|
229 |
array(1,0,0,0,0,0,0,0,0), |
|
230 |
array(1,0,0,0,0,0,0,0,1), |
|
231 |
array(1,0,0,0,0,0,0,0,1), |
|
232 |
array(0,1,0,0,0,0,0,1,0), |
|
233 |
array(0,0,1,1,1,1,1,0,0), |
|
234 |
),
|
|
235 |
'D' => array( |
|
236 |
array(1,1,1,1,1,1,1,0,0), |
|
237 |
array(1,0,0,0,0,0,0,1,0), |
|
238 |
array(1,0,0,0,0,0,0,0,1), |
|
239 |
array(1,0,0,0,0,0,0,0,1), |
|
240 |
array(1,0,0,0,0,0,0,0,1), |
|
241 |
array(1,0,0,0,0,0,0,0,1), |
|
242 |
array(1,0,0,0,0,0,0,0,1), |
|
243 |
array(1,0,0,0,0,0,0,0,1), |
|
244 |
array(1,0,0,0,0,0,0,0,1), |
|
245 |
array(1,0,0,0,0,0,0,0,1), |
|
246 |
array(1,0,0,0,0,0,0,0,1), |
|
247 |
array(1,0,0,0,0,0,0,0,1), |
|
248 |
array(1,0,0,0,0,0,0,0,1), |
|
249 |
array(1,0,0,0,0,0,0,1,0), |
|
250 |
array(1,1,1,1,1,1,1,0,0), |
|
251 |
),
|
|
252 |
'E' => array( |
|
253 |
array(1,1,1,1,1,1,1,1,1), |
|
254 |
array(1,0,0,0,0,0,0,0,0), |
|
255 |
array(1,0,0,0,0,0,0,0,0), |
|
256 |
array(1,0,0,0,0,0,0,0,0), |
|
257 |
array(1,0,0,0,0,0,0,0,0), |
|
258 |
array(1,0,0,0,0,0,0,0,0), |
|
259 |
array(1,0,0,0,0,0,0,0,0), |
|
260 |
array(1,1,1,1,1,1,1,1,0), |
|
261 |
array(1,0,0,0,0,0,0,0,0), |
|
262 |
array(1,0,0,0,0,0,0,0,0), |
|
263 |
array(1,0,0,0,0,0,0,0,0), |
|
264 |
array(1,0,0,0,0,0,0,0,0), |
|
265 |
array(1,0,0,0,0,0,0,0,0), |
|
266 |
array(1,0,0,0,0,0,0,0,0), |
|
267 |
array(1,1,1,1,1,1,1,1,1), |
|
268 |
),
|
|
269 |
'F' => array( |
|
270 |
array(1,1,1,1,1,1,1,1,1), |
|
271 |
array(1,0,0,0,0,0,0,0,0), |
|
272 |
array(1,0,0,0,0,0,0,0,0), |
|
273 |
array(1,0,0,0,0,0,0,0,0), |
|
274 |
array(1,0,0,0,0,0,0,0,0), |
|
275 |
array(1,0,0,0,0,0,0,0,0), |
|
276 |
array(1,0,0,0,0,0,0,0,0), |
|
277 |
array(1,1,1,1,1,1,1,0,0), |
|
278 |
array(1,0,0,0,0,0,0,0,0), |
|
279 |
array(1,0,0,0,0,0,0,0,0), |
|
280 |
array(1,0,0,0,0,0,0,0,0), |
|
281 |
array(1,0,0,0,0,0,0,0,0), |
|
282 |
array(1,0,0,0,0,0,0,0,0), |
|
283 |
array(1,0,0,0,0,0,0,0,0), |
|
284 |
array(1,0,0,0,0,0,0,0,0), |
|
285 |
),
|
|
286 |
'G' => array( |
|
287 |
array(0,0,1,1,1,1,1,0,0), |
|
288 |
array(0,1,0,0,0,0,0,1,0), |
|
289 |
array(1,0,0,0,0,0,0,0,1), |
|
290 |
array(1,0,0,0,0,0,0,0,0), |
|
291 |
array(1,0,0,0,0,0,0,0,0), |
|
292 |
array(1,0,0,0,0,0,0,0,0), |
|
293 |
array(1,0,0,0,0,0,0,0,0), |
|
294 |
array(1,0,0,0,0,0,0,0,0), |
|
295 |
array(1,0,0,0,0,0,1,1,1), |
|
296 |
array(1,0,0,0,0,0,0,0,1), |
|
297 |
array(1,0,0,0,0,0,0,0,1), |
|
298 |
array(1,0,0,0,0,0,0,0,1), |
|
299 |
array(1,0,0,0,0,0,0,0,1), |
|
300 |
array(0,1,0,0,0,0,0,1,0), |
|
301 |
array(0,0,1,1,1,1,1,0,0), |
|
302 |
),
|
|
303 |
'H' => array( |
|
304 |
array(1,0,0,0,0,0,0,0,1), |
|
305 |
array(1,0,0,0,0,0,0,0,1), |
|
306 |
array(1,0,0,0,0,0,0,0,1), |
|
307 |
array(1,0,0,0,0,0,0,0,1), |
|
308 |
array(1,0,0,0,0,0,0,0,1), |
|
309 |
array(1,0,0,0,0,0,0,0,1), |
|
310 |
array(1,0,0,0,0,0,0,0,1), |
|
311 |
array(1,1,1,1,1,1,1,1,1), |
|
312 |
array(1,0,0,0,0,0,0,0,1), |
|
313 |
array(1,0,0,0,0,0,0,0,1), |
|
314 |
array(1,0,0,0,0,0,0,0,1), |
|
315 |
array(1,0,0,0,0,0,0,0,1), |
|
316 |
array(1,0,0,0,0,0,0,0,1), |
|
317 |
array(1,0,0,0,0,0,0,0,1), |
|
318 |
array(1,0,0,0,0,0,0,0,1), |
|
319 |
),
|
|
320 |
'I' => array( |
|
321 |
array(1,1,1,1,1,1,1,1,1), |
|
322 |
array(0,0,0,0,1,0,0,0,0), |
|
323 |
array(0,0,0,0,1,0,0,0,0), |
|
324 |
array(0,0,0,0,1,0,0,0,0), |
|
325 |
array(0,0,0,0,1,0,0,0,0), |
|
326 |
array(0,0,0,0,1,0,0,0,0), |
|
327 |
array(0,0,0,0,1,0,0,0,0), |
|
328 |
array(0,0,0,0,1,0,0,0,0), |
|
329 |
array(0,0,0,0,1,0,0,0,0), |
|
330 |
array(0,0,0,0,1,0,0,0,0), |
|
331 |
array(0,0,0,0,1,0,0,0,0), |
|
332 |
array(0,0,0,0,1,0,0,0,0), |
|
333 |
array(0,0,0,0,1,0,0,0,0), |
|
334 |
array(0,0,0,0,1,0,0,0,0), |
|
335 |
array(1,1,1,1,1,1,1,1,1), |
|
336 |
),
|
|
337 |
'J' => array( |
|
338 |
array(1,1,1,1,1,1,1,1,1), |
|
339 |
array(0,0,0,0,0,1,0,0,0), |
|
340 |
array(0,0,0,0,0,1,0,0,0), |
|
341 |
array(0,0,0,0,0,1,0,0,0), |
|
342 |
array(0,0,0,0,0,1,0,0,0), |
|
343 |
array(0,0,0,0,0,1,0,0,0), |
|
344 |
array(0,0,0,0,0,1,0,0,0), |
|
345 |
array(0,0,0,0,0,1,0,0,0), |
|
346 |
array(0,0,0,0,0,1,0,0,0), |
|
347 |
array(0,0,0,0,0,1,0,0,0), |
|
348 |
array(0,0,0,0,0,1,0,0,0), |
|
349 |
array(1,0,0,0,0,1,0,0,0), |
|
350 |
array(1,0,0,0,0,1,0,0,0), |
|
351 |
array(0,1,0,0,1,0,0,0,0), |
|
352 |
array(0,0,1,1,0,0,0,0,0), |
|
353 |
),
|
|
354 |
'K' => array( // New 'K', supplied by NeoThermic |
|
355 |
array(1,0,0,0,0,0,0,0,1), |
|
356 |
array(1,0,0,0,0,0,0,1,0), |
|
357 |
array(1,0,0,0,0,0,1,0,0), |
|
358 |
array(1,0,0,0,0,1,0,0,0), |
|
359 |
array(1,0,0,0,1,0,0,0,0), |
|
360 |
array(1,0,0,1,0,0,0,0,0), |
|
361 |
array(1,0,1,0,0,0,0,0,0), |
|
362 |
array(1,1,0,0,0,0,0,0,0), |
|
363 |
array(1,0,1,0,0,0,0,0,0), |
|
364 |
array(1,0,0,1,0,0,0,0,0), |
|
365 |
array(1,0,0,0,1,0,0,0,0), |
|
366 |
array(1,0,0,0,0,1,0,0,0), |
|
367 |
array(1,0,0,0,0,0,1,0,0), |
|
368 |
array(1,0,0,0,0,0,0,1,0), |
|
369 |
array(1,0,0,0,0,0,0,0,1), |
|
370 |
),
|
|
371 |
'L' => array( |
|
372 |
array(0,0,0,0,0,0,0,0,0), |
|
373 |
array(1,0,0,0,0,0,0,0,0), |
|
374 |
array(1,0,0,0,0,0,0,0,0), |
|
375 |
array(1,0,0,0,0,0,0,0,0), |
|
376 |
array(1,0,0,0,0,0,0,0,0), |
|
377 |
array(1,0,0,0,0,0,0,0,0), |
|
378 |
array(1,0,0,0,0,0,0,0,0), |
|
379 |
array(1,0,0,0,0,0,0,0,0), |
|
380 |
array(1,0,0,0,0,0,0,0,0), |
|
381 |
array(1,0,0,0,0,0,0,0,0), |
|
382 |
array(1,0,0,0,0,0,0,0,0), |
|
383 |
array(1,0,0,0,0,0,0,0,0), |
|
384 |
array(1,0,0,0,0,0,0,0,0), |
|
385 |
array(1,0,0,0,0,0,0,0,0), |
|
386 |
array(1,1,1,1,1,1,1,1,1), |
|
387 |
),
|
|
388 |
'M' => array( |
|
389 |
array(1,1,0,0,0,0,0,1,1), |
|
390 |
array(1,1,0,0,0,0,0,1,1), |
|
391 |
array(1,0,1,0,0,0,1,0,1), |
|
392 |
array(1,0,1,0,0,0,1,0,1), |
|
393 |
array(1,0,1,0,0,0,1,0,1), |
|
394 |
array(1,0,0,1,0,1,0,0,1), |
|
395 |
array(1,0,0,1,0,1,0,0,1), |
|
396 |
array(1,0,0,1,0,1,0,0,1), |
|
397 |
array(1,0,0,0,1,0,0,0,1), |
|
398 |
array(1,0,0,0,1,0,0,0,1), |
|
399 |
array(1,0,0,0,0,0,0,0,1), |
|
400 |
array(1,0,0,0,0,0,0,0,1), |
|
401 |
array(1,0,0,0,0,0,0,0,1), |
|
402 |
array(1,0,0,0,0,0,0,0,1), |
|
403 |
array(1,0,0,0,0,0,0,0,1), |
|
404 |
),
|
|
405 |
'N' => array( |
|
406 |
array(1,1,0,0,0,0,0,0,1), |
|
407 |
array(1,1,0,0,0,0,0,0,1), |
|
408 |
array(1,0,1,0,0,0,0,0,1), |
|
409 |
array(1,0,1,0,0,0,0,0,1), |
|
410 |
array(1,0,0,1,0,0,0,0,1), |
|
411 |
array(1,0,0,1,0,0,0,0,1), |
|
412 |
array(1,0,0,0,1,0,0,0,1), |
|
413 |
array(1,0,0,0,1,0,0,0,1), |
|
414 |
array(1,0,0,0,1,0,0,0,1), |
|
415 |
array(1,0,0,0,0,1,0,0,1), |
|
416 |
array(1,0,0,0,0,1,0,0,1), |
|
417 |
array(1,0,0,0,0,0,1,0,1), |
|
418 |
array(1,0,0,0,0,0,1,0,1), |
|
419 |
array(1,0,0,0,0,0,0,1,1), |
|
420 |
array(1,0,0,0,0,0,0,1,1), |
|
421 |
),
|
|
422 |
'O' => array( |
|
423 |
array(0,0,1,1,1,1,1,0,0), |
|
424 |
array(0,1,0,0,0,0,0,1,0), |
|
425 |
array(1,0,0,0,0,0,0,0,1), |
|
426 |
array(1,0,0,0,0,0,0,0,1), |
|
427 |
array(1,0,0,0,0,0,0,0,1), |
|
428 |
array(1,0,0,0,0,0,0,0,1), |
|
429 |
array(1,0,0,0,0,0,0,0,1), |
|
430 |
array(1,0,0,0,0,0,0,0,1), |
|
431 |
array(1,0,0,0,0,0,0,0,1), |
|
432 |
array(1,0,0,0,0,0,0,0,1), |
|
433 |
array(1,0,0,0,0,0,0,0,1), |
|
434 |
array(1,0,0,0,0,0,0,0,1), |
|
435 |
array(1,0,0,0,0,0,0,0,1), |
|
436 |
array(0,1,0,0,0,0,0,1,0), |
|
437 |
array(0,0,1,1,1,1,1,0,0), |
|
438 |
),
|
|
439 |
'P' => array( |
|
440 |
array(1,1,1,1,1,1,1,0,0), |
|
441 |
array(1,0,0,0,0,0,0,1,0), |
|
442 |
array(1,0,0,0,0,0,0,0,1), |
|
443 |
array(1,0,0,0,0,0,0,0,1), |
|
444 |
array(1,0,0,0,0,0,0,0,1), |
|
445 |
array(1,0,0,0,0,0,0,0,1), |
|
446 |
array(1,0,0,0,0,0,0,1,0), |
|
447 |
array(1,1,1,1,1,1,1,0,0), |
|
448 |
array(1,0,0,0,0,0,0,0,0), |
|
449 |
array(1,0,0,0,0,0,0,0,0), |
|
450 |
array(1,0,0,0,0,0,0,0,0), |
|
451 |
array(1,0,0,0,0,0,0,0,0), |
|
452 |
array(1,0,0,0,0,0,0,0,0), |
|
453 |
array(1,0,0,0,0,0,0,0,0), |
|
454 |
array(1,0,0,0,0,0,0,0,0), |
|
455 |
),
|
|
456 |
'Q' => array( |
|
457 |
array(0,0,1,1,1,1,1,0,0), |
|
458 |
array(0,1,0,0,0,0,0,1,0), |
|
459 |
array(1,0,0,0,0,0,0,0,1), |
|
460 |
array(1,0,0,0,0,0,0,0,1), |
|
461 |
array(1,0,0,0,0,0,0,0,1), |
|
462 |
array(1,0,0,0,0,0,0,0,1), |
|
463 |
array(1,0,0,0,0,0,0,0,1), |
|
464 |
array(1,0,0,0,0,0,0,0,1), |
|
465 |
array(1,0,0,0,0,0,0,0,1), |
|
466 |
array(1,0,0,0,0,0,0,0,1), |
|
467 |
array(1,0,0,0,0,0,0,0,1), |
|
468 |
array(1,0,0,0,0,1,0,0,1), |
|
469 |
array(1,0,0,0,0,0,1,0,1), |
|
470 |
array(0,1,0,0,0,0,0,1,0), |
|
471 |
array(0,0,1,1,1,1,1,0,1), |
|
472 |
),
|
|
473 |
'R' => array( |
|
474 |
array(1,1,1,1,1,1,1,0,0), |
|
475 |
array(1,0,0,0,0,0,0,1,0), |
|
476 |
array(1,0,0,0,0,0,0,0,1), |
|
477 |
array(1,0,0,0,0,0,0,0,1), |
|
478 |
array(1,0,0,0,0,0,0,0,1), |
|
479 |
array(1,0,0,0,0,0,0,0,1), |
|
480 |
array(1,0,0,0,0,0,0,1,0), |
|
481 |
array(1,1,1,1,1,1,1,0,0), |
|
482 |
array(1,1,1,0,0,0,0,0,0), |
|
483 |
array(1,0,0,1,0,0,0,0,0), |
|
484 |
array(1,0,0,0,1,0,0,0,0), |
|
485 |
array(1,0,0,0,0,1,0,0,0), |
|
486 |
array(1,0,0,0,0,0,1,0,0), |
|
487 |
array(1,0,0,0,0,0,0,1,0), |
|
488 |
array(1,0,0,0,0,0,0,0,1), |
|
489 |
),
|
|
490 |
'S' => array( |
|
491 |
array(0,0,1,1,1,1,1,0,0), |
|
492 |
array(0,1,0,0,0,0,0,1,0), |
|
493 |
array(1,0,0,0,0,0,0,0,1), |
|
494 |
array(1,0,0,0,0,0,0,0,0), |
|
495 |
array(1,0,0,0,0,0,0,0,0), |
|
496 |
array(1,0,0,0,0,0,0,0,0), |
|
497 |
array(0,1,0,0,0,0,0,0,0), |
|
498 |
array(0,0,1,1,1,1,1,0,0), |
|
499 |
array(0,0,0,0,0,0,0,1,0), |
|
500 |
array(0,0,0,0,0,0,0,0,1), |
|
501 |
array(0,0,0,0,0,0,0,0,1), |
|
502 |
array(0,0,0,0,0,0,0,0,1), |
|
503 |
array(1,0,0,0,0,0,0,0,1), |
|
504 |
array(0,1,0,0,0,0,0,1,0), |
|
505 |
array(0,0,1,1,1,1,1,0,0), |
|
506 |
),
|
|
507 |
'T' => array( |
|
508 |
array(1,1,1,1,1,1,1,1,1), |
|
509 |
array(0,0,0,0,1,0,0,0,0), |
|
510 |
array(0,0,0,0,1,0,0,0,0), |
|
511 |
array(0,0,0,0,1,0,0,0,0), |
|
512 |
array(0,0,0,0,1,0,0,0,0), |
|
513 |
array(0,0,0,0,1,0,0,0,0), |
|
514 |
array(0,0,0,0,1,0,0,0,0), |
|
515 |
array(0,0,0,0,1,0,0,0,0), |
|
516 |
array(0,0,0,0,1,0,0,0,0), |
|
517 |
array(0,0,0,0,1,0,0,0,0), |
|
518 |
array(0,0,0,0,1,0,0,0,0), |
|
519 |
array(0,0,0,0,1,0,0,0,0), |
|
520 |
array(0,0,0,0,1,0,0,0,0), |
|
521 |
array(0,0,0,0,1,0,0,0,0), |
|
522 |
array(0,0,0,0,1,0,0,0,0), |
|
523 |
),
|
|
524 |
'U' => array( |
|
525 |
array(1,0,0,0,0,0,0,0,1), |
|
526 |
array(1,0,0,0,0,0,0,0,1), |
|
527 |
array(1,0,0,0,0,0,0,0,1), |
|
528 |
array(1,0,0,0,0,0,0,0,1), |
|
529 |
array(1,0,0,0,0,0,0,0,1), |
|
530 |
array(1,0,0,0,0,0,0,0,1), |
|
531 |
array(1,0,0,0,0,0,0,0,1), |
|
532 |
array(1,0,0,0,0,0,0,0,1), |
|
533 |
array(1,0,0,0,0,0,0,0,1), |
|
534 |
array(1,0,0,0,0,0,0,0,1), |
|
535 |
array(1,0,0,0,0,0,0,0,1), |
|
536 |
array(1,0,0,0,0,0,0,0,1), |
|
537 |
array(1,0,0,0,0,0,0,0,1), |
|
538 |
array(0,1,0,0,0,0,0,1,0), |
|
539 |
array(0,0,1,1,1,1,1,0,0), |
|
540 |
),
|
|
541 |
'V' => array( |
|
542 |
array(1,0,0,0,0,0,0,0,1), |
|
543 |
array(1,0,0,0,0,0,0,0,1), |
|
544 |
array(1,0,0,0,0,0,0,0,1), |
|
545 |
array(0,1,0,0,0,0,0,1,0), |
|
546 |
array(0,1,0,0,0,0,0,1,0), |
|
547 |
array(0,1,0,0,0,0,0,1,0), |
|
548 |
array(0,0,1,0,0,0,1,0,0), |
|
549 |
array(0,0,1,0,0,0,1,0,0), |
|
550 |
array(0,0,1,0,0,0,1,0,0), |
|
551 |
array(0,0,1,0,0,0,1,0,0), |
|
552 |
array(0,0,0,1,0,1,0,0,0), |
|
553 |
array(0,0,0,1,0,1,0,0,0), |
|
554 |
array(0,0,0,1,0,1,0,0,0), |
|
555 |
array(0,0,0,0,1,0,0,0,0), |
|
556 |
array(0,0,0,0,1,0,0,0,0), |
|
557 |
),
|
|
558 |
'W' => array( // New 'W', supplied by MHobbit |
|
559 |
array(1,0,0,0,0,0,0,0,1), |
|
560 |
array(1,0,0,0,0,0,0,0,1), |
|
561 |
array(1,0,0,0,0,0,0,0,1), |
|
562 |
array(1,0,0,0,0,0,0,0,1), |
|
563 |
array(1,0,0,0,0,0,0,0,1), |
|
564 |
array(1,0,0,0,1,0,0,0,1), |
|
565 |
array(1,0,0,0,1,0,0,0,1), |
|
566 |
array(1,0,0,1,0,1,0,0,1), |
|
567 |
array(1,0,0,1,0,1,0,0,1), |
|
568 |
array(1,0,0,1,0,1,0,0,1), |
|
569 |
array(1,0,1,0,0,0,1,0,1), |
|
570 |
array(1,0,1,0,0,0,1,0,1), |
|
571 |
array(1,0,1,0,0,0,1,0,1), |
|
572 |
array(1,1,0,0,0,0,0,1,1), |
|
573 |
array(1,1,0,0,0,0,0,1,1), |
|
574 |
),
|
|
575 |
'X' => array( |
|
576 |
array(1,0,0,0,0,0,0,0,1), |
|
577 |
array(1,0,0,0,0,0,0,0,1), |
|
578 |
array(0,1,0,0,0,0,0,1,0), |
|
579 |
array(0,1,0,0,0,0,0,1,0), |
|
580 |
array(0,0,1,0,0,0,1,0,0), |
|
581 |
array(0,0,0,1,0,1,0,0,0), |
|
582 |
array(0,0,0,1,0,1,0,0,0), |
|
583 |
array(0,0,0,0,1,0,0,0,0), |
|
584 |
array(0,0,0,1,0,1,0,0,0), |
|
585 |
array(0,0,0,1,0,1,0,0,0), |
|
586 |
array(0,0,1,0,0,0,1,0,0), |
|
587 |
array(0,1,0,0,0,0,1,0,0), |
|
588 |
array(0,1,0,0,0,0,0,1,0), |
|
589 |
array(1,0,0,0,0,0,0,0,1), |
|
590 |
array(1,0,0,0,0,0,0,0,1), |
|
591 |
),
|
|
592 |
'Y' => array( |
|
593 |
array(1,0,0,0,0,0,0,0,1), |
|
594 |
array(1,0,0,0,0,0,0,0,1), |
|
595 |
array(0,1,0,0,0,0,0,1,0), |
|
596 |
array(0,1,0,0,0,0,0,1,0), |
|
597 |
array(0,0,1,0,0,0,1,0,0), |
|
598 |
array(0,0,1,0,0,0,1,0,0), |
|
599 |
array(0,0,0,1,0,1,0,0,0), |
|
600 |
array(0,0,0,0,1,0,0,0,0), |
|
601 |
array(0,0,0,0,1,0,0,0,0), |
|
602 |
array(0,0,0,0,1,0,0,0,0), |
|
603 |
array(0,0,0,0,1,0,0,0,0), |
|
604 |
array(0,0,0,0,1,0,0,0,0), |
|
605 |
array(0,0,0,0,1,0,0,0,0), |
|
606 |
array(0,0,0,0,1,0,0,0,0), |
|
607 |
array(0,0,0,0,1,0,0,0,0), |
|
608 |
),
|
|
609 |
'Z' => array( // New 'Z' supplied by Anon |
|
610 |
array(1,1,1,1,1,1,1,1,1), |
|
611 |
array(1,0,0,0,0,0,0,0,1), |
|
612 |
array(0,0,0,0,0,0,0,0,1), |
|
613 |
array(0,0,0,0,0,0,0,1,0), |
|
614 |
array(0,0,0,0,0,0,1,0,0), |
|
615 |
array(0,0,0,0,0,1,0,0,0), |
|
616 |
array(0,0,0,0,0,1,0,0,0), |
|
617 |
array(0,0,0,0,1,0,0,0,0), |
|
618 |
array(0,0,0,1,0,0,0,0,0), |
|
619 |
array(0,0,0,1,0,0,0,0,0), |
|
620 |
array(0,0,1,0,0,0,0,0,0), |
|
621 |
array(0,1,0,0,0,0,0,0,0), |
|
622 |
array(1,0,0,0,0,0,0,0,0), |
|
623 |
array(1,0,0,0,0,0,0,0,1), |
|
624 |
array(1,1,1,1,1,1,1,1,1), |
|
625 |
),
|
|
626 |
'1' => array( |
|
627 |
array(0,0,0,1,1,0,0,0,0), |
|
628 |
array(0,0,1,0,1,0,0,0,0), |
|
629 |
array(0,1,0,0,1,0,0,0,0), |
|
630 |
array(0,0,0,0,1,0,0,0,0), |
|
631 |
array(0,0,0,0,1,0,0,0,0), |
|
632 |
array(0,0,0,0,1,0,0,0,0), |
|
633 |
array(0,0,0,0,1,0,0,0,0), |
|
634 |
array(0,0,0,0,1,0,0,0,0), |
|
635 |
array(0,0,0,0,1,0,0,0,0), |
|
636 |
array(0,0,0,0,1,0,0,0,0), |
|
637 |
array(0,0,0,0,1,0,0,0,0), |
|
638 |
array(0,0,0,0,1,0,0,0,0), |
|
639 |
array(0,0,0,0,1,0,0,0,0), |
|
640 |
array(0,0,0,0,1,0,0,0,0), |
|
641 |
array(0,1,1,1,1,1,1,1,0), |
|
642 |
),
|
|
643 |
'2' => array( // New '2' supplied by Anon |
|
644 |
array(0,0,0,1,1,1,0,0,0), |
|
645 |
array(0,0,1,0,0,0,1,0,0), |
|
646 |
array(0,1,0,0,0,0,1,1,0), |
|
647 |
array(0,0,0,0,0,0,0,0,1), |
|
648 |
array(0,0,0,0,0,0,0,0,1), |
|
649 |
array(0,0,0,0,0,0,0,1,1), |
|
650 |
array(0,0,0,0,0,0,0,1,0), |
|
651 |
array(0,0,0,0,0,0,1,0,0), |
|
652 |
array(0,0,0,0,0,1,0,0,0), |
|
653 |
array(0,0,0,0,1,0,0,0,0), |
|
654 |
array(0,0,0,1,0,0,0,0,0), |
|
655 |
array(0,0,1,0,0,0,0,0,0), |
|
656 |
array(0,1,0,0,0,0,0,0,0), |
|
657 |
array(1,1,1,1,1,1,1,1,1), |
|
658 |
array(0,0,0,0,0,0,0,0,0), |
|
659 |
),
|
|
660 |
'3' => array( |
|
661 |
array(0,0,1,1,1,1,1,0,0), |
|
662 |
array(0,1,0,0,0,0,0,1,0), |
|
663 |
array(1,0,0,0,0,0,0,0,1), |
|
664 |
array(0,0,0,0,0,0,0,0,1), |
|
665 |
array(0,0,0,0,0,0,0,0,1), |
|
666 |
array(0,0,0,0,0,0,0,0,1), |
|
667 |
array(0,0,0,0,0,0,0,1,0), |
|
668 |
array(0,0,0,0,0,1,1,0,0), |
|
669 |
array(0,0,0,0,0,0,0,1,0), |
|
670 |
array(0,0,0,0,0,0,0,0,1), |
|
671 |
array(0,0,0,0,0,0,0,0,1), |
|
672 |
array(0,0,0,0,0,0,0,0,1), |
|
673 |
array(1,0,0,0,0,0,0,0,1), |
|
674 |
array(0,1,0,0,0,0,0,1,0), |
|
675 |
array(0,0,1,1,1,1,1,0,0), |
|
676 |
),
|
|
677 |
'4' => array( |
|
678 |
array(0,0,0,0,0,0,1,1,0), |
|
679 |
array(0,0,0,0,0,1,0,1,0), |
|
680 |
array(0,0,0,0,1,0,0,1,0), |
|
681 |
array(0,0,0,1,0,0,0,1,0), |
|
682 |
array(0,0,1,0,0,0,0,1,0), |
|
683 |
array(0,1,0,0,0,0,0,1,0), |
|
684 |
array(1,0,0,0,0,0,0,1,0), |
|
685 |
array(1,0,0,0,0,0,0,1,0), |
|
686 |
array(1,1,1,1,1,1,1,1,1), |
|
687 |
array(0,0,0,0,0,0,0,1,0), |
|
688 |
array(0,0,0,0,0,0,0,1,0), |
|
689 |
array(0,0,0,0,0,0,0,1,0), |
|
690 |
array(0,0,0,0,0,0,0,1,0), |
|
691 |
array(0,0,0,0,0,0,0,1,0), |
|
692 |
array(0,0,0,0,0,0,0,1,0), |
|
693 |
),
|
|
694 |
'5' => array( |
|
695 |
array(1,1,1,1,1,1,1,1,1), |
|
696 |
array(1,0,0,0,0,0,0,0,0), |
|
697 |
array(1,0,0,0,0,0,0,0,0), |
|
698 |
array(1,0,0,0,0,0,0,0,0), |
|
699 |
array(1,0,0,0,0,0,0,0,0), |
|
700 |
array(0,1,0,0,0,0,0,0,0), |
|
701 |
array(0,0,1,1,1,1,1,0,0), |
|
702 |
array(0,0,0,0,0,0,0,1,0), |
|
703 |
array(0,0,0,0,0,0,0,0,1), |
|
704 |
array(0,0,0,0,0,0,0,0,1), |
|
705 |
array(0,0,0,0,0,0,0,0,1), |
|
706 |
array(0,0,0,0,0,0,0,0,1), |
|
707 |
array(1,0,0,0,0,0,0,0,1), |
|
708 |
array(0,1,0,0,0,0,0,1,0), |
|
709 |
array(0,0,1,1,1,1,1,0,0), |
|
710 |
),
|
|
711 |
'6' => array( |
|
712 |
array(0,0,1,1,1,1,1,0,0), |
|
713 |
array(0,1,0,0,0,0,0,1,0), |
|
714 |
array(1,0,0,0,0,0,0,0,1), |
|
715 |
array(1,0,0,0,0,0,0,0,1), |
|
716 |
array(1,0,0,0,0,0,0,0,0), |
|
717 |
array(1,0,0,0,0,0,0,0,0), |
|
718 |
array(1,0,0,1,1,1,1,0,0), |
|
719 |
array(1,0,1,0,0,0,0,1,0), |
|
720 |
array(1,1,0,0,0,0,0,0,1), |
|
721 |
array(1,0,0,0,0,0,0,0,1), |
|
722 |
array(1,0,0,0,0,0,0,0,1), |
|
723 |
array(1,0,0,0,0,0,0,0,1), |
|
724 |
array(1,0,0,0,0,0,0,0,1), |
|
725 |
array(0,1,0,0,0,0,0,1,0), |
|
726 |
array(0,0,1,1,1,1,1,0,0), |
|
727 |
),
|
|
728 |
'7' => array( |
|
729 |
array(1,1,1,1,1,1,1,1,1), |
|
730 |
array(0,0,0,0,0,0,0,0,1), |
|
731 |
array(0,0,0,0,0,0,0,1,0), |
|
732 |
array(0,0,0,0,0,0,0,1,0), |
|
733 |
array(0,0,0,0,0,0,1,0,0), |
|
734 |
array(0,0,0,0,0,1,0,0,0), |
|
735 |
array(0,0,0,0,0,1,0,0,0), |
|
736 |
array(0,0,0,0,1,0,0,0,0), |
|
737 |
array(0,0,0,1,0,0,0,0,0), |
|
738 |
array(0,0,0,1,0,0,0,0,0), |
|
739 |
array(0,0,1,0,0,0,0,0,0), |
|
740 |
array(0,1,0,0,0,0,0,0,0), |
|
741 |
array(0,1,0,0,0,0,0,0,0), |
|
742 |
array(1,0,0,0,0,0,0,0,0), |
|
743 |
array(1,0,0,0,0,0,0,0,0), |
|
744 |
),
|
|
745 |
'8' => array( |
|
746 |
array(0,0,1,1,1,1,1,0,0), |
|
747 |
array(0,1,0,0,0,0,0,1,0), |
|
748 |
array(1,0,0,0,0,0,0,0,1), |
|
749 |
array(1,0,0,0,0,0,0,0,1), |
|
750 |
array(1,0,0,0,0,0,0,0,1), |
|
751 |
array(1,0,0,0,0,0,0,0,1), |
|
752 |
array(0,1,0,0,0,0,0,1,0), |
|
753 |
array(0,0,1,1,1,1,1,0,0), |
|
754 |
array(0,1,0,0,0,0,0,1,0), |
|
755 |
array(1,0,0,0,0,0,0,0,1), |
|
756 |
array(1,0,0,0,0,0,0,0,1), |
|
757 |
array(1,0,0,0,0,0,0,0,1), |
|
758 |
array(1,0,0,0,0,0,0,0,1), |
|
759 |
array(0,1,0,0,0,0,0,1,0), |
|
760 |
array(0,0,1,1,1,1,1,0,0), |
|
761 |
),
|
|
762 |
'9' => array( |
|
763 |
array(0,0,1,1,1,1,1,0,0), |
|
764 |
array(0,1,0,0,0,0,0,1,0), |
|
765 |
array(1,0,0,0,0,0,0,0,1), |
|
766 |
array(1,0,0,0,0,0,0,0,1), |
|
767 |
array(1,0,0,0,0,0,0,0,1), |
|
768 |
array(1,0,0,0,0,0,0,0,1), |
|
769 |
array(1,0,0,0,0,0,0,1,1), |
|
770 |
array(0,1,0,0,0,0,1,0,1), |
|
771 |
array(0,0,1,1,1,1,0,0,1), |
|
772 |
array(0,0,0,0,0,0,0,0,1), |
|
773 |
array(0,0,0,0,0,0,0,0,1), |
|
774 |
array(1,0,0,0,0,0,0,0,1), |
|
775 |
array(1,0,0,0,0,0,0,0,1), |
|
776 |
array(0,1,0,0,0,0,0,1,0), |
|
777 |
array(0,0,1,1,1,1,1,0,0), |
|
778 |
),
|
|
779 |
)
|
|
780 |
);
|
|
781 |
}
|
|
782 |
}
|
|
783 |
||
784 |
/**
|
|
785 |
* @package VC
|
|
786 |
*/
|
|
787 |
class char_cube3d |
|
788 |
{
|
|
789 |
var $bitmap; |
|
790 |
var $bitmap_width; |
|
791 |
var $bitmap_height; |
|
792 |
||
793 |
var $basis_matrix = array(array(1, 0, 0), array(0, 1, 0), array(0, 0, 1)); |
|
794 |
var $abs_x = array(1, 0); |
|
795 |
var $abs_y = array(0, 1); |
|
796 |
var $x = 0; |
|
797 |
var $y = 1; |
|
798 |
var $z = 2; |
|
799 |
var $letter = ''; |
|
800 |
||
801 |
/**
|
|
802 |
*/
|
|
803 |
function char_cube3d(&$bitmaps, $letter) |
|
804 |
{
|
|
805 |
$this->bitmap = $bitmaps['data'][$letter]; |
|
806 |
$this->bitmap_width = $bitmaps['width']; |
|
807 |
$this->bitmap_height = $bitmaps['height']; |
|
808 |
||
809 |
$this->basis_matrix[0][0] = mt_rand(-600, 600); |
|
810 |
$this->basis_matrix[0][1] = mt_rand(-600, 600); |
|
811 |
$this->basis_matrix[0][2] = (mt_rand(0, 1) * 2000) - 1000; |
|
812 |
$this->basis_matrix[1][0] = mt_rand(-1000, 1000); |
|
813 |
$this->basis_matrix[1][1] = mt_rand(-1000, 1000); |
|
814 |
$this->basis_matrix[1][2] = mt_rand(-1000, 1000); |
|
815 |
||
816 |
$this->normalize($this->basis_matrix[0]); |
|
817 |
$this->normalize($this->basis_matrix[1]); |
|
818 |
$this->basis_matrix[2] = $this->cross_product($this->basis_matrix[0], $this->basis_matrix[1]); |
|
819 |
$this->normalize($this->basis_matrix[2]); |
|
820 |
||
821 |
// $this->basis_matrix[1] might not be (probably isn't) orthogonal to $basis_matrix[0]
|
|
822 |
$this->basis_matrix[1] = $this->cross_product($this->basis_matrix[0], $this->basis_matrix[2]); |
|
823 |
$this->normalize($this->basis_matrix[1]); |
|
824 |
||
825 |
// Make sure our cube is facing into the canvas (assuming +z == in)
|
|
826 |
for ($i = 0; $i < 3; ++$i) |
|
827 |
{
|
|
828 |
if ($this->basis_matrix[$i][2] < 0) |
|
829 |
{
|
|
830 |
$this->basis_matrix[$i][0] *= -1; |
|
831 |
$this->basis_matrix[$i][1] *= -1; |
|
832 |
$this->basis_matrix[$i][2] *= -1; |
|
833 |
}
|
|
834 |
}
|
|
835 |
||
836 |
// Force our "z" basis vector to be the one with greatest absolute z value
|
|
837 |
$this->x = 0; |
|
838 |
$this->y = 1; |
|
839 |
$this->z = 2; |
|
840 |
||
841 |
// Swap "y" with "z"
|
|
842 |
if ($this->basis_matrix[1][2] > $this->basis_matrix[2][2]) |
|
843 |
{
|
|
844 |
$this->z = 1; |
|
845 |
$this->y = 2; |
|
846 |
}
|
|
847 |
||
848 |
// Swap "x" with "z"
|
|
849 |
if ($this->basis_matrix[0][2] > $this->basis_matrix[$this->z][2]) |
|
850 |
{
|
|
851 |
$this->x = $this->z; |
|
852 |
$this->z = 0; |
|
853 |
}
|
|
854 |
||
855 |
// Still need to determine which of $x,$y are which.
|
|
856 |
// wrong orientation if y's y-component is less than it's x-component
|
|
857 |
// likewise if x's x-component is less than it's y-component
|
|
858 |
// if they disagree, go with the one with the greater weight difference.
|
|
859 |
// rotate if positive
|
|
860 |
$weight = (abs($this->basis_matrix[$this->x][1]) - abs($this->basis_matrix[$this->x][0])) + (abs($this->basis_matrix[$this->y][0]) - abs($this->basis_matrix[$this->y][1])); |
|
861 |
||
862 |
// Swap "x" with "y"
|
|
863 |
if ($weight > 0) |
|
864 |
{
|
|
865 |
list($this->x, $this->y) = array($this->y, $this->x); |
|
866 |
}
|
|
867 |
||
868 |
$this->abs_x = array($this->basis_matrix[$this->x][0], $this->basis_matrix[$this->x][1]); |
|
869 |
$this->abs_y = array($this->basis_matrix[$this->y][0], $this->basis_matrix[$this->y][1]); |
|
870 |
||
871 |
if ($this->abs_x[0] < 0) |
|
872 |
{
|
|
873 |
$this->abs_x[0] *= -1; |
|
874 |
$this->abs_x[1] *= -1; |
|
875 |
}
|
|
876 |
||
877 |
if ($this->abs_y[1] > 0) |
|
878 |
{
|
|
879 |
$this->abs_y[0] *= -1; |
|
880 |
$this->abs_y[1] *= -1; |
|
881 |
}
|
|
882 |
||
883 |
$this->letter = $letter; |
|
884 |
}
|
|
885 |
||
886 |
/**
|
|
887 |
* Draw a character
|
|
888 |
*/
|
|
889 |
function drawchar($scale, $xoff, $yoff, $img, $background, $colours) |
|
890 |
{
|
|
891 |
$width = $this->bitmap_width; |
|
892 |
$height = $this->bitmap_height; |
|
893 |
$bitmap = $this->bitmap; |
|
894 |
||
895 |
$colour1 = $colours[array_rand($colours)]; |
|
896 |
$colour2 = $colours[array_rand($colours)]; |
|
897 |
||
898 |
$swapx = ($this->basis_matrix[$this->x][0] > 0); |
|
899 |
$swapy = ($this->basis_matrix[$this->y][1] < 0); |
|
900 |
||
901 |
for ($y = 0; $y < $height; ++$y) |
|
902 |
{
|
|
903 |
for ($x = 0; $x < $width; ++$x) |
|
904 |
{
|
|
905 |
$xp = ($swapx) ? ($width - $x - 1) : $x; |
|
906 |
$yp = ($swapy) ? ($height - $y - 1) : $y; |
|
907 |
||
908 |
if ($bitmap[$height - $yp - 1][$xp]) |
|
909 |
{
|
|
910 |
$dx = $this->scale($this->abs_x, ($xp - ($swapx ? ($width / 2) : ($width / 2) - 1)) * $scale); |
|
911 |
$dy = $this->scale($this->abs_y, ($yp - ($swapy ? ($height / 2) : ($height / 2) - 1)) * $scale); |
|
912 |
$xo = $xoff + $dx[0] + $dy[0]; |
|
913 |
$yo = $yoff + $dx[1] + $dy[1]; |
|
914 |
||
915 |
$origin = array(0, 0, 0); |
|
916 |
$xvec = $this->scale($this->basis_matrix[$this->x], $scale); |
|
917 |
$yvec = $this->scale($this->basis_matrix[$this->y], $scale); |
|
918 |
$face_corner = $this->sum2($xvec, $yvec); |
|
919 |
||
920 |
$zvec = $this->scale($this->basis_matrix[$this->z], $scale); |
|
921 |
$x_corner = $this->sum2($xvec, $zvec); |
|
922 |
$y_corner = $this->sum2($yvec, $zvec); |
|
923 |
||
924 |
imagefilledpolygon($img, $this->gen_poly($xo, $yo, $origin, $xvec, $x_corner,$zvec), 4, $colour1); |
|
925 |
imagefilledpolygon($img, $this->gen_poly($xo, $yo, $origin, $yvec, $y_corner,$zvec), 4, $colour2); |
|
926 |
||
927 |
$face = $this->gen_poly($xo, $yo, $origin, $xvec, $face_corner, $yvec); |
|
928 |
||
929 |
imagefilledpolygon($img, $face, 4, $background); |
|
930 |
imagepolygon($img, $face, 4, $colour1); |
|
931 |
}
|
|
932 |
}
|
|
933 |
}
|
|
934 |
}
|
|
935 |
||
936 |
/*
|
|
937 |
* return a roughly acceptable range of sizes for rendering with this texttype
|
|
938 |
*/
|
|
939 |
function range() |
|
940 |
{
|
|
941 |
return array(3, 4); |
|
942 |
}
|
|
943 |
||
944 |
/**
|
|
945 |
* Vector length
|
|
946 |
*/
|
|
947 |
function vectorlen($vector) |
|
948 |
{
|
|
949 |
return sqrt(pow($vector[0], 2) + pow($vector[1], 2) + pow($vector[2], 2)); |
|
950 |
}
|
|
951 |
||
952 |
/**
|
|
953 |
* Normalize
|
|
954 |
*/
|
|
955 |
function normalize(&$vector, $length = 1) |
|
956 |
{
|
|
957 |
$length = (( $length < 1) ? 1 : $length); |
|
958 |
$length /= $this->vectorlen($vector); |
|
959 |
$vector[0] *= $length; |
|
960 |
$vector[1] *= $length; |
|
961 |
$vector[2] *= $length; |
|
962 |
}
|
|
963 |
||
964 |
/**
|
|
965 |
*/
|
|
966 |
function cross_product($vector1, $vector2) |
|
967 |
{
|
|
968 |
$retval = array(0, 0, 0); |
|
969 |
$retval[0] = (($vector1[1] * $vector2[2]) - ($vector1[2] * $vector2[1])); |
|
970 |
$retval[1] = -(($vector1[0] * $vector2[2]) - ($vector1[2] * $vector2[0])); |
|
971 |
$retval[2] = (($vector1[0] * $vector2[1]) - ($vector1[1] * $vector2[0])); |
|
972 |
||
973 |
return $retval; |
|
974 |
}
|
|
975 |
||
976 |
/**
|
|
977 |
*/
|
|
978 |
function sum($vector1, $vector2) |
|
979 |
{
|
|
980 |
return array($vector1[0] + $vector2[0], $vector1[1] + $vector2[1], $vector1[2] + $vector2[2]); |
|
981 |
}
|
|
982 |
||
983 |
/**
|
|
984 |
*/
|
|
985 |
function sum2($vector1, $vector2) |
|
986 |
{
|
|
987 |
return array($vector1[0] + $vector2[0], $vector1[1] + $vector2[1]); |
|
988 |
}
|
|
989 |
||
990 |
/**
|
|
991 |
*/
|
|
992 |
function scale($vector, $length) |
|
993 |
{
|
|
994 |
if (sizeof($vector) == 2) |
|
995 |
{
|
|
996 |
return array($vector[0] * $length, $vector[1] * $length); |
|
997 |
}
|
|
998 |
||
999 |
return array($vector[0] * $length, $vector[1] * $length, $vector[2] * $length); |
|
1000 |
}
|
|
1001 |
||
1002 |
/**
|
|
1003 |
*/
|
|
1004 |
function gen_poly($xoff, $yoff, &$vec1, &$vec2, &$vec3, &$vec4) |
|
1005 |
{
|
|
1006 |
$poly = array(); |
|
1007 |
$poly[0] = $xoff + $vec1[0]; |
|
1008 |
$poly[1] = $yoff + $vec1[1]; |
|
1009 |
$poly[2] = $xoff + $vec2[0]; |
|
1010 |
$poly[3] = $yoff + $vec2[1]; |
|
1011 |
$poly[4] = $xoff + $vec3[0]; |
|
1012 |
$poly[5] = $yoff + $vec3[1]; |
|
1013 |
$poly[6] = $xoff + $vec4[0]; |
|
1014 |
$poly[7] = $yoff + $vec4[1]; |
|
1015 |
||
1016 |
return $poly; |
|
1017 |
}
|
|
1018 |
||
1019 |
/**
|
|
1020 |
* dimensions
|
|
1021 |
*/
|
|
1022 |
function dimensions($size) |
|
1023 |
{
|
|
1024 |
$xn = $this->scale($this->basis_matrix[$this->x], -($this->bitmap_width / 2) * $size); |
|
1025 |
$xp = $this->scale($this->basis_matrix[$this->x], ($this->bitmap_width / 2) * $size); |
|
1026 |
$yn = $this->scale($this->basis_matrix[$this->y], -($this->bitmap_height / 2) * $size); |
|
1027 |
$yp = $this->scale($this->basis_matrix[$this->y], ($this->bitmap_height / 2) * $size); |
|
1028 |
||
1029 |
$p = array(); |
|
1030 |
$p[0] = $this->sum2($xn, $yn); |
|
1031 |
$p[1] = $this->sum2($xp, $yn); |
|
1032 |
$p[2] = $this->sum2($xp, $yp); |
|
1033 |
$p[3] = $this->sum2($xn, $yp); |
|
1034 |
||
1035 |
$min_x = $max_x = $p[0][0]; |
|
1036 |
$min_y = $max_y = $p[0][1]; |
|
1037 |
||
1038 |
for ($i = 1; $i < 4; ++$i) |
|
1039 |
{
|
|
1040 |
$min_x = ($min_x > $p[$i][0]) ? $p[$i][0] : $min_x; |
|
1041 |
$min_y = ($min_y > $p[$i][1]) ? $p[$i][1] : $min_y; |
|
1042 |
$max_x = ($max_x < $p[$i][0]) ? $p[$i][0] : $max_x; |
|
1043 |
$max_y = ($max_y < $p[$i][1]) ? $p[$i][1] : $max_y; |
|
1044 |
}
|
|
1045 |
||
1046 |
return array($min_x, $min_y, $max_x, $max_y); |
|
1047 |
}
|
|
1048 |
}
|
|
1049 |
||
1050 |
/**
|
|
1051 |
* @package VC
|
|
1052 |
*/
|
|
1053 |
class colour_manager |
|
1054 |
{
|
|
1055 |
var $img; |
|
1056 |
var $mode; |
|
1057 |
var $colours; |
|
1058 |
var $named_colours; |
|
1059 |
||
1060 |
/**
|
|
1061 |
* Create the colour manager, link it to the image resource
|
|
1062 |
*/
|
|
1063 |
function colour_manager($img, $background = false, $mode = 'ahsv') |
|
1064 |
{
|
|
1065 |
$this->img = $img; |
|
1066 |
$this->mode = $mode; |
|
1067 |
$this->colours = array(); |
|
1068 |
$this->named_colours = array(); |
|
1069 |
||
1070 |
if ($background !== false) |
|
1071 |
{
|
|
1072 |
$bg = $this->allocate_named('background', $background); |
|
1073 |
imagefill($this->img, 0, 0, $bg); |
|
1074 |
}
|
|
1075 |
}
|
|
1076 |
||
1077 |
/**
|
|
1078 |
* Lookup a named colour resource
|
|
1079 |
*/
|
|
1080 |
function get_resource($named_colour) |
|
1081 |
{
|
|
1082 |
if (isset($this->named_colours[$named_colour])) |
|
1083 |
{
|
|
1084 |
return $this->named_colours[$named_colour]; |
|
1085 |
}
|
|
1086 |
||
1087 |
if (isset($this->named_rgb[$named_colour])) |
|
1088 |
{
|
|
1089 |
return $this->allocate_named($named_colour, $this->named_rgb[$named_colour], 'rgb'); |
|
1090 |
}
|
|
1091 |
||
1092 |
return false; |
|
1093 |
}
|
|
1094 |
||
1095 |
/**
|
|
1096 |
* Assign a name to a colour resource
|
|
1097 |
*/
|
|
1098 |
function name_colour($name, $resource) |
|
1099 |
{
|
|
1100 |
$this->named_colours[$name] = $resource; |
|
1101 |
}
|
|
1102 |
||
1103 |
/**
|
|
1104 |
* names and allocates a colour resource
|
|
1105 |
*/
|
|
1106 |
function allocate_named($name, $colour, $mode = false) |
|
1107 |
{
|
|
1108 |
$resource = $this->allocate($colour, $mode); |
|
1109 |
||
1110 |
if ($resource !== false) |
|
1111 |
{
|
|
1112 |
$this->name_colour($name, $resource); |
|
1113 |
}
|
|
1114 |
return $resource; |
|
1115 |
}
|
|
1116 |
||
1117 |
/**
|
|
1118 |
* allocates a specified colour into the image
|
|
1119 |
*/
|
|
1120 |
function allocate($colour, $mode = false) |
|
1121 |
{
|
|
1122 |
if ($mode === false) |
|
1123 |
{
|
|
1124 |
$mode = $this->mode; |
|
1125 |
}
|
|
1126 |
||
1127 |
if (!is_array($colour)) |
|
1128 |
{
|
|
1129 |
if (isset($this->named_rgb[$colour])) |
|
1130 |
{
|
|
1131 |
return $this->allocate_named($colour, $this->named_rgb[$colour], 'rgb'); |
|
1132 |
}
|
|
1133 |
||
1134 |
if (!is_int($colour)) |
|
1135 |
{
|
|
1136 |
return false; |
|
1137 |
}
|
|
1138 |
||
1139 |
$mode = 'rgb'; |
|
1140 |
$colour = array(255 & ($colour >> 16), 255 & ($colour >> 8), 255 & $colour); |
|
1141 |
}
|
|
1142 |
||
1143 |
if (isset($colour['mode'])) |
|
1144 |
{
|
|
1145 |
$mode = $colour['mode']; |
|
1146 |
unset($colour['mode']); |
|
1147 |
}
|
|
1148 |
||
1149 |
if (isset($colour['random'])) |
|
1150 |
{
|
|
1151 |
unset($colour['random']); |
|
1152 |
// everything else is params
|
|
1153 |
return $this->random_colour($colour, $mode); |
|
1154 |
}
|
|
1155 |
||
1156 |
$rgb = colour_manager::model_convert($colour, $mode, 'rgb'); |
|
1157 |
$store = ($this->mode == 'rgb') ? $rgb : colour_manager::model_convert($colour, $mode, $this->mode); |
|
1158 |
$resource = imagecolorallocate($this->img, $rgb[0], $rgb[1], $rgb[2]); |
|
1159 |
$this->colours[$resource] = $store; |
|
1160 |
||
1161 |
return $resource; |
|
1162 |
}
|
|
1163 |
||
1164 |
/**
|
|
1165 |
* randomly generates a colour, with optional params
|
|
1166 |
*/
|
|
1167 |
function random_colour($params = array(), $mode = false) |
|
1168 |
{
|
|
1169 |
if ($mode === false) |
|
1170 |
{
|
|
1171 |
$mode = $this->mode; |
|
1172 |
}
|
|
1173 |
||
1174 |
switch ($mode) |
|
1175 |
{
|
|
1176 |
case 'rgb': |
|
1177 |
// @TODO random rgb generation. do we intend to do this, or is it just too tedious?
|
|
1178 |
break; |
|
1179 |
||
1180 |
case 'ahsv': |
|
1181 |
case 'hsv': |
|
1182 |
default: |
|
1183 |
||
1184 |
$default_params = array( |
|
1185 |
'hue_bias' => false, // degree / 'r'/'g'/'b'/'c'/'m'/'y' /'o' |
|
1186 |
'hue_range' => false, // if hue bias, then difference range +/- from bias |
|
1187 |
'min_saturation' => 30, // 0 - 100 |
|
1188 |
'max_saturation' => 80, // 0 - 100 |
|
1189 |
'min_value' => 30, // 0 - 100 |
|
1190 |
'max_value' => 80, // 0 - 100 |
|
1191 |
);
|
|
1192 |
||
1193 |
$alt = ($mode == 'ahsv') ? true : false; |
|
1194 |
$params = array_merge($default_params, $params); |
|
1195 |
||
1196 |
$min_hue = 0; |
|
1197 |
$max_hue = 359; |
|
1198 |
$min_saturation = max(0, $params['min_saturation']); |
|
1199 |
$max_saturation = min(100, $params['max_saturation']); |
|
1200 |
$min_value = max(0, $params['min_value']); |
|
1201 |
$max_value = min(100, $params['max_value']); |
|
1202 |
||
1203 |
if ($params['hue_bias'] !== false) |
|
1204 |
{
|
|
1205 |
if (is_numeric($params['hue_bias'])) |
|
1206 |
{
|
|
1207 |
$h = intval($params['hue_bias']) % 360; |
|
1208 |
}
|
|
1209 |
else
|
|
1210 |
{
|
|
1211 |
switch ($params['hue_bias']) |
|
1212 |
{
|
|
1213 |
case 'o': |
|
1214 |
$h = $alt ? 60 : 30; |
|
1215 |
break; |
|
1216 |
||
1217 |
case 'y': |
|
1218 |
$h = $alt ? 120 : 60; |
|
1219 |
break; |
|
1220 |
||
1221 |
case 'g': |
|
1222 |
$h = $alt ? 180 : 120; |
|
1223 |
break; |
|
1224 |
||
1225 |
case 'c': |
|
1226 |
$h = $alt ? 210 : 180; |
|
1227 |
break; |
|
1228 |
||
1229 |
case 'b': |
|
1230 |
$h = 240; |
|
1231 |
break; |
|
1232 |
||
1233 |
case 'm': |
|
1234 |
$h = 300; |
|
1235 |
break; |
|
1236 |
||
1237 |
case 'r': |
|
1238 |
default: |
|
1239 |
$h = 0; |
|
1240 |
break; |
|
1241 |
}
|
|
1242 |
}
|
|
1243 |
||
1244 |
$min_hue = $h + 360; |
|
1245 |
$max_hue = $h + 360; |
|
1246 |
||
1247 |
if ($params['hue_range']) |
|
1248 |
{
|
|
1249 |
$min_hue -= min(180, $params['hue_range']); |
|
1250 |
$max_hue += min(180, $params['hue_range']); |
|
1251 |
}
|
|
1252 |
}
|
|
1253 |
||
1254 |
$h = mt_rand($min_hue, $max_hue); |
|
1255 |
$s = mt_rand($min_saturation, $max_saturation); |
|
1256 |
$v = mt_rand($min_value, $max_value); |
|
1257 |
||
1258 |
return $this->allocate(array($h, $s, $v), $mode); |
|
1259 |
||
1260 |
break; |
|
1261 |
}
|
|
1262 |
}
|
|
1263 |
||
1264 |
/**
|
|
1265 |
*/
|
|
1266 |
function colour_scheme($resource, $include_original = true) |
|
1267 |
{
|
|
1268 |
$mode = 'hsv'; |
|
1269 |
||
1270 |
if (($pre = $this->get_resource($resource)) !== false) |
|
1271 |
{
|
|
1272 |
$resource = $pre; |
|
1273 |
}
|
|
1274 |
||
1275 |
$colour = colour_manager::model_convert($this->colours[$resource], $this->mode, $mode); |
|
1276 |
$results = ($include_original) ? array($resource) : array(); |
|
1277 |
$colour2 = $colour3 = $colour4 = $colour; |
|
1278 |
$colour2[0] += 150; |
|
1279 |
$colour3[0] += 180; |
|
1280 |
$colour4[0] += 210; |
|
1281 |
||
1282 |
||
1283 |
$results[] = $this->allocate($colour2, $mode); |
|
1284 |
$results[] = $this->allocate($colour3, $mode); |
|
1285 |
$results[] = $this->allocate($colour4, $mode); |
|
1286 |
||
1287 |
return $results; |
|
1288 |
}
|
|
1289 |
||
1290 |
/**
|
|
1291 |
*/
|
|
1292 |
function mono_range($resource, $count = 5, $include_original = true) |
|
1293 |
{
|
|
1294 |
if (is_array($resource)) |
|
1295 |
{
|
|
1296 |
$results = array(); |
|
1297 |
for ($i = 0, $size = sizeof($resource); $i < $size; ++$i) |
|
1298 |
{
|
|
1299 |
$results = array_merge($results, $this->mono_range($resource[$i], $count, $include_original)); |
|
1300 |
}
|
|
1301 |
return $results; |
|
1302 |
}
|
|
1303 |
||
1304 |
$mode = (in_array($this->mode, array('hsv', 'ahsv'), true) ? $this->mode : 'ahsv'); |
|
1305 |
if (($pre = $this->get_resource($resource)) !== false) |
|
1306 |
{
|
|
1307 |
$resource = $pre; |
|
1308 |
}
|
|
1309 |
||
1310 |
$colour = colour_manager::model_convert($this->colours[$resource], $this->mode, $mode); |
|
1311 |
||
1312 |
$results = array(); |
|
1313 |
if ($include_original) |
|
1314 |
{
|
|
1315 |
$results[] = $resource; |
|
1316 |
$count--; |
|
1317 |
}
|
|
1318 |
||
1319 |
// This is a hard problem. I chicken out and try to maintain readability at the cost of less randomness.
|
|
1320 |
||
1321 |
while ($count > 0) |
|
1322 |
{
|
|
1323 |
$colour[1] = ($colour[1] + mt_rand(40,60)) % 99; |
|
1324 |
$colour[2] = ($colour[2] + mt_rand(40,60)); |
|
1325 |
$results[] = $this->allocate($colour, $mode); |
|
1326 |
$count--; |
|
1327 |
}
|
|
1328 |
return $results; |
|
1329 |
}
|
|
1330 |
||
1331 |
/**
|
|
1332 |
* Convert from one colour model to another
|
|
1333 |
*/
|
|
1334 |
function model_convert($colour, $from_model, $to_model) |
|
1335 |
{
|
|
1336 |
if ($from_model == $to_model) |
|
1337 |
{
|
|
1338 |
return $colour; |
|
1339 |
}
|
|
1340 |
||
1341 |
switch ($to_model) |
|
1342 |
{
|
|
1343 |
case 'hsv': |
|
1344 |
||
1345 |
switch ($from_model) |
|
1346 |
{
|
|
1347 |
case 'ahsv': |
|
1348 |
return colour_manager::ah2h($colour); |
|
1349 |
break; |
|
1350 |
||
1351 |
case 'rgb': |
|
1352 |
return colour_manager::rgb2hsv($colour); |
|
1353 |
break; |
|
1354 |
}
|
|
1355 |
break; |
|
1356 |
||
1357 |
case 'ahsv': |
|
1358 |
||
1359 |
switch ($from_model) |
|
1360 |
{
|
|
1361 |
case 'hsv': |
|
1362 |
return colour_manager::h2ah($colour); |
|
1363 |
break; |
|
1364 |
||
1365 |
case 'rgb': |
|
1366 |
return colour_manager::h2ah(colour_manager::rgb2hsv($colour)); |
|
1367 |
break; |
|
1368 |
}
|
|
1369 |
break; |
|
1370 |
||
1371 |
case 'rgb': |
|
1372 |
switch ($from_model) |
|
1373 |
{
|
|
1374 |
case 'hsv': |
|
1375 |
return colour_manager::hsv2rgb($colour); |
|
1376 |
break; |
|
1377 |
||
1378 |
case 'ahsv': |
|
1379 |
return colour_manager::hsv2rgb(colour_manager::ah2h($colour)); |
|
1380 |
break; |
|
1381 |
}
|
|
1382 |
break; |
|
1383 |
}
|
|
1384 |
return false; |
|
1385 |
}
|
|
1386 |
||
1387 |
/**
|
|
1388 |
* Slightly altered from wikipedia's algorithm
|
|
1389 |
*/
|
|
1390 |
function hsv2rgb($hsv) |
|
1391 |
{
|
|
1392 |
colour_manager::normalize_hue($hsv[0]); |
|
1393 |
||
1394 |
$h = $hsv[0]; |
|
1395 |
$s = min(1, max(0, $hsv[1] / 100)); |
|
1396 |
$v = min(1, max(0, $hsv[2] / 100)); |
|
1397 |
||
1398 |
// calculate hue sector
|
|
1399 |
$hi = floor($hsv[0] / 60); |
|
1400 |
||
1401 |
// calculate opposite colour
|
|
1402 |
$p = $v * (1 - $s); |
|
1403 |
||
1404 |
// calculate distance between hex vertices
|
|
1405 |
$f = ($h / 60) - $hi; |
|
1406 |
||
1407 |
// coming in or going out?
|
|
1408 |
if (!($hi & 1)) |
|
1409 |
{
|
|
1410 |
$f = 1 - $f; |
|
1411 |
}
|
|
1412 |
||
1413 |
// calculate adjacent colour
|
|
1414 |
$q = $v * (1 - ($f * $s)); |
|
1415 |
||
1416 |
switch ($hi) |
|
1417 |
{
|
|
1418 |
case 0: |
|
1419 |
$rgb = array($v, $q, $p); |
|
1420 |
break; |
|
1421 |
||
1422 |
case 1: |
|
1423 |
$rgb = array($q, $v, $p); |
|
1424 |
break; |
|
1425 |
||
1426 |
case 2: |
|
1427 |
$rgb = array($p, $v, $q); |
|
1428 |
break; |
|
1429 |
||
1430 |
case 3: |
|
1431 |
$rgb = array($p, $q, $v); |
|
1432 |
break; |
|
1433 |
||
1434 |
case 4: |
|
1435 |
$rgb = array($q, $p, $v); |
|
1436 |
break; |
|
1437 |
||
1438 |
case 5: |
|
1439 |
$rgb = array($v, $p, $q); |
|
1440 |
break; |
|
1441 |
||
1442 |
default: |
|
1443 |
return array(0, 0, 0); |
|
1444 |
break; |
|
1445 |
}
|
|
1446 |
||
1447 |
return array(255 * $rgb[0], 255 * $rgb[1], 255 * $rgb[2]); |
|
1448 |
}
|
|
1449 |
||
1450 |
/**
|
|
1451 |
* (more than) Slightly altered from wikipedia's algorithm
|
|
1452 |
*/
|
|
1453 |
function rgb2hsv($rgb) |
|
1454 |
{
|
|
1455 |
$r = min(255, max(0, $rgb[0])); |
|
1456 |
$g = min(255, max(0, $rgb[1])); |
|
1457 |
$b = min(255, max(0, $rgb[2])); |
|
1458 |
$max = max($r, $g, $b); |
|
1459 |
$min = min($r, $g, $b); |
|
1460 |
||
1461 |
$v = $max / 255; |
|
1462 |
$s = (!$max) ? 0 : 1 - ($min / $max); |
|
1463 |
||
1464 |
// if max - min is 0, we want hue to be 0 anyway.
|
|
1465 |
$h = $max - $min; |
|
1466 |
||
1467 |
if ($h) |
|
1468 |
{
|
|
1469 |
switch ($max) |
|
1470 |
{
|
|
1471 |
case $g: |
|
1472 |
$h = 120 + (60 * ($b - $r) / $h); |
|
1473 |
break; |
|
1474 |
||
1475 |
case $b: |
|
1476 |
$h = 240 + (60 * ($r - $g) / $h); |
|
1477 |
break; |
|
1478 |
||
1479 |
case $r: |
|
1480 |
$h = 360 + (60 * ($g - $b) / $h); |
|
1481 |
break; |
|
1482 |
}
|
|
1483 |
}
|
|
1484 |
colour_manager::normalize_hue($h); |
|
1485 |
||
1486 |
return array($h, $s * 100, $v * 100); |
|
1487 |
}
|
|
1488 |
||
1489 |
/**
|
|
1490 |
*/
|
|
1491 |
function normalize_hue(&$hue) |
|
1492 |
{
|
|
1493 |
$hue %= 360; |
|
1494 |
||
1495 |
if ($hue < 0) |
|
1496 |
{
|
|
1497 |
$hue += 360; |
|
1498 |
}
|
|
1499 |
}
|
|
1500 |
||
1501 |
/**
|
|
1502 |
* Alternate hue to hue
|
|
1503 |
*/
|
|
1504 |
function ah2h($ahue) |
|
1505 |
{
|
|
1506 |
if (is_array($ahue)) |
|
1507 |
{
|
|
1508 |
$ahue[0] = colour_manager::ah2h($ahue[0]); |
|
1509 |
return $ahue; |
|
1510 |
}
|
|
1511 |
colour_manager::normalize_hue($ahue); |
|
1512 |
||
1513 |
// blue through red is already ok
|
|
1514 |
if ($ahue >= 240) |
|
1515 |
{
|
|
1516 |
return $ahue; |
|
1517 |
}
|
|
1518 |
||
1519 |
// ahue green is at 180
|
|
1520 |
if ($ahue >= 180) |
|
1521 |
{
|
|
1522 |
// return (240 - (2 * (240 - $ahue)));
|
|
1523 |
return (2 * $ahue) - 240; // equivalent |
|
1524 |
}
|
|
1525 |
||
1526 |
// ahue yellow is at 120 (RYB rather than RGB)
|
|
1527 |
if ($ahue >= 120) |
|
1528 |
{
|
|
1529 |
return $ahue - 60; |
|
1530 |
}
|
|
1531 |
||
1532 |
return $ahue / 2; |
|
1533 |
}
|
|
1534 |
||
1535 |
/**
|
|
1536 |
* hue to Alternate hue
|
|
1537 |
*/
|
|
1538 |
function h2ah($hue) |
|
1539 |
{
|
|
1540 |
if (is_array($hue)) |
|
1541 |
{
|
|
1542 |
$hue[0] = colour_manager::h2ah($hue[0]); |
|
1543 |
return $hue; |
|
1544 |
}
|
|
1545 |
colour_manager::normalize_hue($hue); |
|
1546 |
||
1547 |
// blue through red is already ok
|
|
1548 |
if ($hue >= 240) |
|
1549 |
{
|
|
1550 |
return $hue; |
|
1551 |
}
|
|
1552 |
else if ($hue <= 60) |
|
1553 |
{
|
|
1554 |
return $hue * 2; |
|
1555 |
}
|
|
1556 |
else if ($hue <= 120) |
|
1557 |
{
|
|
1558 |
return $hue + 60; |
|
1559 |
}
|
|
1560 |
else
|
|
1561 |
{
|
|
1562 |
return ($hue + 240) / 2; |
|
1563 |
}
|
|
1564 |
}
|
|
1565 |
}
|
|
1566 |
||
1567 |
?>
|