1: <?php
2:
3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58:
59: $plugin_description = gettext('Attaches “Image effects” to images and thumbnails.');
60: $plugin_author = "Stephen Billard (sbillard)";
61:
62: $option_interface = 'image_effects';
63:
64: zp_register_filter('standard_image_html', 'image_effects::std_images');
65: zp_register_filter('custom_image_html', 'image_effects::custom_images');
66: zp_register_filter('standard_album_thumb_html', 'image_effects::std_album_thumbs');
67: zp_register_filter('standard_image_thumb_html', 'image_effects::std_image_thumbs');
68: zp_register_filter('custom_album_thumb_html', 'image_effects::custom_album_thumbs');
69:
70: if (defined('OFFSET_PATH') && OFFSET_PATH == 0) {
71: zp_register_filter('theme_head', 'image_effects::effectsJS');
72: }
73:
74: class image_effects {
75:
76: var $effects = NULL;
77:
78: function __construct() {
79: $effect = getPluginFiles('*.txt', 'image_effects');
80: foreach ($this->effects = array_keys($effect) as $suffix) {
81: setOptionDefault('image_effects_random_' . $suffix, 1);
82: }
83: }
84:
85: 86: 87: 88: 89:
90: function getOptionsSupported() {
91: $list = array('random' => '!');
92: $docs = array();
93: $effenberger = array('bevel', 'corner', 'crippleedge', 'curl', 'filmed', 'glossy', 'instant', 'reflex', 'slided', 'sphere');
94: foreach ($this->effects as $effect) {
95: $rand[$effect] = 'image_effects_random_' . $effect;
96: $effectdata = image_effects::getEffect($effect);
97: $list[$effect] = $effect;
98: $docs[chr(0) . $effect] = array('key' => 'image_effect_' . $effect, 'order' => $effect, 'type' => OPTION_TYPE_CUSTOM);
99: if (array_key_exists('source', $effectdata)) {
100: $docs[chr(0) . $effect]['desc'] = $effectdata['source'];
101: } else {
102: $docs[chr(0) . $effect]['desc'] = gettext('No acknowledgement');
103: }
104: if (array_key_exists('error', $effectdata)) {
105: $docs[chr(0) . $effect]['desc'] .= '<p class="notebox">' . $effectdata['error'] . '</p>';
106: query('DELETE FROM ' . prefix('options') . ' WHERE `name`="image_custom_random_' . $effect . '"');
107: if (in_array($effect, $effenberger)) {
108: $docs[chr(0) . $effect]['desc'] .= '<p class="notebox">' . gettext('<strong>Note:</strong> Although this plugin supports <em>Effenberger effects</em>, due to licensing considerations no <em>Effenberger effects</em> scripts are included. See <a href="http://www.netzgesta.de/cvi/">CVI Astonishing Image Effects</a> by Christian Effenberger to select and download effects.') . '</p>';
109: }
110: }
111: }
112: if (count($list) == 0) {
113: return array(gettext('No effects') => array('key' => 'image_effect_none', 'type' => OPTION_TYPE_CUSTOM,
114: 'desc' => ''));
115: }
116: foreach (array('image_std_images', 'image_custom_images', 'image_std_image_thumbs', 'image_std_album_thumbs', 'image_custom_image_thumbs', 'image_custom_album_thumbs') as $option) {
117: $effect = getOption($option);
118: if ($effect && $effect != '!' && !array_key_exists($effect, $list)) {
119: $error[$effect] = '<p class="errorbox">' . sprintf(gettext('<strong>Error:</strong> <em>%s</em> effect no longer exists.'), $effect) . '</p>';
120: }
121: }
122: $std = array(gettext('Images (standard)') => array('key' => 'image_std_images', 'type' => OPTION_TYPE_SELECTOR,
123: 'order' => 0,
124: 'selections' => $list, 'null_selection' => gettext('none'),
125: 'desc' => gettext('Apply <em>effect</em> to images shown via the <code>printDefaultSizedImage()</code> function.')),
126: gettext('Images (custom)') => array('key' => 'image_custom_images', 'type' => OPTION_TYPE_SELECTOR,
127: 'order' => 0,
128: 'selections' => $list, 'null_selection' => gettext('none'),
129: 'desc' => gettext('Apply <em>effect</em> to images shown via the custom image functions.')),
130: gettext('Image thumbnails (standard)') => array('key' => 'image_std_image_thumbs', 'type' => OPTION_TYPE_SELECTOR,
131: 'order' => 0,
132: 'selections' => $list, 'null_selection' => gettext('none'),
133: 'desc' => gettext('Apply <em>effect</em> to images shown via the <code>printImageThumb()</code> function.')),
134: gettext('Album thumbnails (standard)') => array('key' => 'image_std_album_thumbs', 'type' => OPTION_TYPE_SELECTOR,
135: 'order' => 0,
136: 'selections' => $list, 'null_selection' => gettext('none'),
137: 'desc' => gettext('Apply <em>effect</em> to images shown via the <code>printAlbumThumbImage()</code> function.')),
138: gettext('Image thumbnails (custom)') => array('key' => 'image_custom_image_thumbs', 'type' => OPTION_TYPE_SELECTOR,
139: 'order' => 0,
140: 'selections' => $list, 'null_selection' => gettext('none'),
141: 'desc' => gettext('Apply <em>effect</em> to images shown via the custom image functions when <em>thumbstandin</em> is set.')),
142: gettext('Album thumbnails (custom)') => array('key' => 'image_custom_album_thumbs', 'type' => OPTION_TYPE_SELECTOR,
143: 'order' => 0,
144: 'selections' => $list, 'null_selection' => gettext('none'),
145: 'desc' => gettext('Apply <em>effect</em> to images shown via the <code>printCustomAlbumThumbImage()</code> function.')),
146: gettext('Random pool') => array('key' => 'image_effects_random_', 'type' => OPTION_TYPE_CHECKBOX_UL,
147: 'order' => 1,
148: 'checkboxes' => $rand,
149: 'desc' => gettext('Pool of effects for the <em>random</em> effect selection.')),
150: 8 => array('type' => OPTION_TYPE_NOTE,
151: 'order' => 8.9,
152: 'desc' => '<hr />'),
153: chr(0) => array('key' => 'image_effects_docs', 'type' => OPTION_TYPE_CUSTOM,
154: 'order' => 9,
155: 'desc' => '<em>' . gettext('Acknowledgments') . '</em>')
156: );
157:
158: ksort($docs);
159: return array_merge($std, $docs);
160: }
161:
162: 163: 164: 165: 166: 167:
168: function handleOption($option, $currentValue) {
169: switch ($option) {
170: case 'image_effect_none':
171: gettext('No image effects found.');
172: break;
173: case 'image_effects_docs':
174: echo '<em>' . gettext('Effect') . '</em>';
175: break;
176: default:
177: echo str_replace('image_effect_', '', $option);
178: break;
179: }
180: }
181:
182: static function effectsJS() {
183: global $_image_effects_random;
184: $effectlist = array_keys(getPluginFiles('*.txt', 'image_effects'));
185: shuffle($effectlist);
186: $common = array();
187: do {
188: $_image_effects_random = array_shift($effectlist);
189: if (getOption('image_effects_random_' . $_image_effects_random)) {
190: $effectdata = image_effects::getEffect($_image_effects_random);
191: $invalid_effect = $effectdata && array_key_exists('error', $effectdata);
192: } else {
193: $invalid_effect = true;
194: }
195: } while ($_image_effects_random && $invalid_effect);
196:
197: if (!$_image_effects_random)
198: echo "<br />random effect empty!";
199:
200: $selected_effects = array_unique(array(getOption('image_std_images'), getOption('image_custom_images'),
201: getOption('image_std_album_thumbs'), getOption('image_std_image_thumbs'),
202: getOption('image_custom_album_thumbs'), $_image_effects_random));
203: if (false !== $key = array_search('!', $selected_effects)) {
204: unset($selected_effects[$key]);
205: }
206: if (count($selected_effects) > 0) {
207: foreach ($selected_effects as $effect) {
208: $effectdata = image_effects::getEffect($effect);
209: if (array_key_exists('head', $effectdata)) {
210: $common_data = trim($effectdata['head']);
211: while ($common_data) {
212: $i = strcspn($common_data, '= >');
213: if ($i === false) {
214: $common_data = '';
215: } else {
216: $tag = '</' . trim(substr($common_data, 1, $i)) . '>';
217: $k = strpos($common_data, '>');
218: $j = strpos($common_data, $tag, $k + 1);
219: if ($j === false) {
220: $j = strpos($common_data, '/>');
221: if ($j === false) {
222: $common_data = '';
223: } else {
224: $j = $j + 2;
225: }
226: } else {
227: $j = $j + strlen($tag);
228: }
229: if ($j === false) {
230: $common_data = '';
231: } else {
232: $common_element = substr($common_data, 0, $j);
233: $common_data = trim(substr($common_data, strlen($common_element)));
234: $common_element = trim($common_element);
235: if (!in_array($common_element, $common)) {
236: $common[] = $common_element;
237: }
238: }
239: }
240: }
241: }
242: }
243: if (!empty($common)) {
244: echo implode("\n", $common);
245: }
246: }
247: }
248:
249: private static function getEffect($effect) {
250: global $image_effects;
251: $effectdata = array();
252: $file = getPlugin('image_effects/' . internalToFilesystem($effect) . '.txt');
253: if (file_exists($file)) {
254: $text = file_get_contents($file);
255: foreach (array('head', 'class', 'extra', 'validate', 'common', 'source') as $tag) {
256: $i = strpos($text, '<' . $tag . '>');
257: if ($i !== false) {
258: $j = strpos($text, '</' . $tag . '>');
259: if ($j !== false) {
260: $effectdata[$tag] = str_replace('%ZENFOLDER%', ZENFOLDER, str_replace('%SERVERPATH%', SERVERPATH, str_replace('%USER_PLUGIN_FOLDER%', USER_PLUGIN_FOLDER, str_replace('%PLUGIN_FOLDER%', PLUGIN_FOLDER, str_replace('%WEBPATH%', WEBPATH, substr($text, $s = $i + strlen($tag) + 2, $j - $s))))));
261: }
262: }
263: }
264: if (empty($effectdata)) {
265: return array('error' => sprintf(gettext('<strong>Warning:</strong> <em>%1$s</em> invalid effect definition file'), $effect));
266: }
267: if (array_key_exists('validate', $effectdata)) {
268: $effectdata['error'] = array();
269: foreach (explode(';', $effectdata['validate']) as $file) {
270: $file = trim($file);
271: if ($file && !file_exists($file)) {
272: $effectdata['error'][] = basename($file);
273: }
274: }
275: if (count($effectdata['error']) > 0) {
276: $effectdata['error'] = sprintf(ngettext('<strong>Warning:</strong> <em>%1$s</em> missing effect component: %2$s', '<strong>Warning:</strong><em>%1$s</em> missing effect components: %2$s', count($effectdata['error'])), $effect, implode(', ', $effectdata['error']));
277: } else {
278: unset($effectdata['error']);
279: }
280: unset($effectdata['validate']);
281: }
282: $image_effects[$effect] = $effectdata;
283: return $effectdata;
284: } else {
285: return array('error' => sprintf(gettext('<strong>Warning:</strong> <em>%1$s</em> missing effect definition file'), $effect));
286: }
287: }
288:
289: private static function insertClass($html, $effect) {
290: global $_image_effects_random;
291: if ($effect == '!') {
292: $effect = $_image_effects_random;
293: }
294: $effectData = image_effects::getEffect($effect);
295: if (array_key_exists('error', $effectData)) {
296: $html .= '<span class="errorbox">' . $effectData['error'] . "</span>\n";
297: } else {
298: if (array_key_exists('class', $effectData)) {
299: $i = strpos($html, '<img');
300: if ($i !== false) {
301: $i = strpos($html, 'class=', $i);
302: if ($i === false) {
303: $i = strpos($html, '/>');
304: $html = substr($html, 0, $i) . 'class="' . $effectData['class'] . '" ' . substr($html, $i);
305: } else {
306: $quote = substr($html, $i + 6, 1);
307: $i = strpos($html, $quote, $i + 7);
308: $html = substr($html, 0, $i) . ' ' . $effectData['class'] . substr($html, $i);
309: }
310: }
311: }
312: if (array_key_exists('extra', $effectData)) {
313: $i = strpos($html, '/>');
314: $html = substr($html, 0, $i) . ' ' . $effectData['extra'] . ' ' . substr($html, $i);
315: }
316: }
317: return $html;
318: }
319:
320: static function std_images($html) {
321: if ($effect = getOption('image_std_images')) {
322: $html = image_effects::insertClass($html, $effect);
323: }
324: return $html;
325: }
326:
327: static function custom_images($html, $thumbstandin) {
328: if ($thumbstandin) {
329: if ($effect = getOption('image_custom_image_thumbs')) {
330: $html = image_effects::insertClass($html, $effect);
331: }
332: } else {
333: if ($effect = getOption('image_custom_images')) {
334: $html = image_effects::insertClass($html, $effect);
335: }
336: }
337: return $html;
338: }
339:
340: static function std_album_thumbs($html) {
341: if ($effect = getOption('image_std_album_thumbs')) {
342: $html = image_effects::insertClass($html, $effect);
343: }
344: return $html;
345: }
346:
347: static function std_image_thumbs($html) {
348: if ($effect = getOption('image_std_image_thumbs')) {
349: $html = image_effects::insertClass($html, $effect);
350: }
351: return $html;
352: }
353:
354: static function custom_album_thumbs($html) {
355: if ($effect = getOption('image_custom_album_thumbs')) {
356: $html = image_effects::insertClass($html, $effect);
357: }
358: return $html;
359: }
360:
361: }
362:
363: ?>