1+ <?php
2+
3+ // This is a PLUGIN TEMPLATE for Textpattern CMS.
4+
5+ // Copy this file to a new name like abc_myplugin.php. Edit the code, then
6+ // run this file at the command line to produce a plugin for distribution:
7+ // $ php abc_myplugin.php > abc_myplugin-0.1.txt
8+
9+ // Plugin name is optional. If unset, it will be extracted from the current
10+ // file name. Plugin names should start with a three letter prefix which is
11+ // unique and reserved for each plugin author ("abc" is just an example).
12+ // Uncomment and edit this line to override:
13+ $ plugin ['name ' ] = 'kuo_webp ' ;
14+
15+ // Allow raw HTML help, as opposed to Textile.
16+ // 0 = Plugin help is in Textile format, no raw HTML allowed (default).
17+ // 1 = Plugin help is in raw HTML. Not recommended.
18+ # $plugin['allow_html_help'] = 1;
19+
20+ $ plugin ['version ' ] = '0.1 ' ;
21+ $ plugin ['author ' ] = 'Pete ' ;
22+ $ plugin ['author_uri ' ] = 'https://textpattern.fi/ ' ;
23+ $ plugin ['description ' ] = 'Create WebP versions of images. ' ;
24+
25+ // Plugin load order:
26+ // The default value of 5 would fit most plugins, while for instance comment
27+ // spam evaluators or URL redirectors would probably want to run earlier
28+ // (1...4) to prepare the environment for everything else that follows.
29+ // Values 6...9 should be considered for plugins which would work late.
30+ // This order is user-overrideable.
31+ $ plugin ['order ' ] = '9 ' ;
32+
33+ // Plugin 'type' defines where the plugin is loaded
34+ // 0 = public : only on the public side of the website (default)
35+ // 1 = public+admin : on both the public and admin side
36+ // 2 = library : only when include_plugin() or require_plugin() is called
37+ // 3 = admin : only on the admin side (no AJAX)
38+ // 4 = admin+ajax : only on the admin side (AJAX supported)
39+ // 5 = public+admin+ajax : on both the public and admin side (AJAX supported)
40+ $ plugin ['type ' ] = '3 ' ;
41+
42+ // Plugin "flags" signal the presence of optional capabilities to the core plugin loader.
43+ // Use an appropriately OR-ed combination of these flags.
44+ // The four high-order bits 0xf000 are available for this plugin's private use
45+ if (!defined ('PLUGIN_HAS_PREFS ' )) define ('PLUGIN_HAS_PREFS ' , 0x0001 ); // This plugin wants to receive "plugin_prefs.{$plugin['name']}" events
46+ if (!defined ('PLUGIN_LIFECYCLE_NOTIFY ' )) define ('PLUGIN_LIFECYCLE_NOTIFY ' , 0x0002 ); // This plugin wants to receive "plugin_lifecycle.{$plugin['name']}" events
47+
48+ $ plugin ['flags ' ] = '0 ' ;
49+
50+ // Plugin 'textpack' is optional. It provides i18n strings to be used in conjunction with gTxt().
51+ // Syntax:
52+ // ## arbitrary comment
53+ // #@event
54+ // #@language ISO-LANGUAGE-CODE
55+ // abc_string_name => Localized String
56+
57+ /** Uncomment me, if you need a textpack
58+ $plugin['textpack'] = <<< EOT
59+ #@admin
60+ #@language en-gb
61+ abc_sample_string => Sample String
62+ abc_one_more => One more
63+ #@language de-de
64+ abc_sample_string => Beispieltext
65+ abc_one_more => Noch einer
66+ EOT;
67+ **/
68+ // End of textpack
69+
70+ if (!defined ('txpinterface ' ))
71+ @include_once ('zem_tpl.php ' );
72+
73+ # --- BEGIN PLUGIN CODE ---
74+ register_callback (
75+ 'kuo_webp_cta ' ,
76+ 'image_ui ' ,
77+ 'image_edit '
78+ );
79+
80+ register_callback (
81+ 'kuo_webp_launcher ' ,
82+ 'image_ui ' ,
83+ 'image_edit '
84+ );
85+
86+ function kuo_webp_cta () {
87+
88+ global $ img_dir ;
89+
90+ $ result = array ();
91+
92+ $ image = safe_row (
93+ '* ' ,
94+ 'txp_image ' ,
95+ 'id = ' .intval ($ _GET ['id ' ]),
96+ false
97+ );
98+
99+ if (strcmp ($ image ['ext ' ],'.webp ' ) != 0 ) {
100+
101+ $ result [] = href (
102+ '💾 WebP ' ,
103+ '?event=image&step=image_edit&id= ' .$ _GET ['id ' ].'&action=webp ' ,
104+ 'title="⟳ Create or recreate WebP files" '
105+ );
106+ }
107+
108+ $ webp = array (
109+ 'full ' =>IMPATH .$ image ['id ' ].'.webp ' ,
110+ 'thumbnail ' =>IMPATH .$ image ['id ' ].'t.webp ' ,
111+ );
112+
113+ if (file_exists ($ webp ['full ' ])) {
114+
115+ $ result [] = href (
116+ '🖼 Full size ' ,
117+ ihu.$ img_dir .'/ ' .$ image ['id ' ].'.webp ' ,
118+ 'target="_new" rel="prefetch" '
119+ );
120+ }
121+
122+ if (file_exists ($ webp ['thumbnail ' ])) {
123+
124+ $ result [] = href (
125+ '🖼 Thumbnail ' ,
126+ ihu.$ img_dir .'/ ' .$ image ['id ' ].'t.webp ' ,
127+ 'target="_new" '
128+ );
129+ }
130+
131+ echo implode (
132+ ' ' ,
133+ $ result
134+ );
135+ }
136+
137+ function kuo_webp_launcher () {
138+
139+ $ image = safe_row (
140+ '* ' ,
141+ 'txp_image ' ,
142+ 'id = ' .intval ($ _GET ['id ' ]),
143+ false
144+ );
145+
146+ if (
147+ (isset ($ _GET ['action ' ]))
148+ &&
149+ (strcmp ($ _GET ['action ' ],'webp ' ) == 0 )
150+ &&
151+ (!empty ($ image ))
152+ ) {
153+
154+ $ source ['full ' ] = IMPATH .$ image ['id ' ].$ image ['ext ' ];
155+ $ new ['full ' ] = IMPATH .kuo_extension_changer ($ image ['id ' ].$ image ['ext ' ]);
156+
157+ $ type = kuo_image_type ($ source ['full ' ]);
158+ $ isAcceptedType = kuo_is_accepted_type ($ type );
159+
160+ # Copying the original image.
161+ if ($ isAcceptedType ) {
162+
163+ kuo_webp_processor (
164+ $ type ,
165+ $ source ['full ' ],
166+ $ new ['full ' ]
167+ );
168+ }
169+
170+ if (
171+ (isset ($ image ['thumbnail ' ]))
172+ &&
173+ ($ image ['thumbnail ' ] == 1 )
174+ ) {
175+
176+ $ source ['thumbnail ' ] = IMPATH .$ image ['id ' ].'t ' .$ image ['ext ' ];
177+ $ new ['thumbnail ' ] = IMPATH .kuo_extension_changer ($ image ['id ' ].'t ' .$ image ['ext ' ]);
178+ }
179+
180+ # Optionally copying the thumbnail.
181+ if (isset ($ new ['thumbnail ' ],$ source ['thumbnail ' ])) {
182+
183+ $ type = kuo_image_type ($ source ['thumbnail ' ]);
184+ $ isAcceptedType = kuo_is_accepted_type ($ type );
185+
186+ if ($ isAcceptedType ) {
187+
188+ kuo_webp_processor (
189+ $ type ,
190+ $ source ['thumbnail ' ],
191+ $ new ['thumbnail ' ]
192+ );
193+ }
194+ }
195+
196+ if (!headers_sent ()) {
197+
198+ header ('Location: ?event=image&step=image_edit&id= ' .$ _GET ['id ' ]);
199+ }
200+ }
201+ }
202+
203+ function kuo_image_type (string $ file ):string {
204+
205+ $ result = '' ;
206+
207+ $ image = getimagesize ($ file );
208+
209+ if (isset ($ image ['mime ' ])) {
210+
211+ $ result = $ image ['mime ' ];
212+ $ result = strtolower ($ result );
213+ }
214+
215+ return $ result ;
216+ }
217+
218+ function kuo_is_accepted_type (string $ type ):bool {
219+
220+ $ result = false ;
221+
222+ static $ accepted = array (
223+ 'image/avif ' ,
224+ 'image/bmp ' ,
225+ 'image/gif ' ,
226+ 'image/jpg ' ,
227+ 'image/jpeg ' ,
228+ 'image/png ' ,
229+ 'image/tga ' ,
230+ );
231+
232+ if (in_array ($ type ,$ accepted ,true )) {
233+
234+ $ result = true ;
235+ }
236+
237+ return $ result ;
238+ }
239+
240+ function kuo_extension_changer (string $ file ,string $ extension = 'webp ' ):string {
241+
242+ $ name = pathinfo (
243+ $ file ,
244+ PATHINFO_FILENAME
245+ );
246+
247+ return $ name .'. ' .$ extension ;
248+ }
249+
250+ function kuo_webp_processor (string $ type ,string $ original ,string $ new ):bool {
251+
252+ $ result = false ;
253+
254+ if (
255+ (strcmp ($ type ,'image/avif ' ) == 0 )
256+ &&
257+ (function_exists ('imagecreatefromavif ' ))
258+ ) {
259+
260+ $ image = imagecreatefromavif ($ original );
261+ }
262+ elseif (
263+ (strcmp ($ type ,'image/bmp ' ) == 0 )
264+ &&
265+ (function_exists ('imagecreatefrombmp ' ))
266+ ) {
267+
268+ $ image = imagecreatefrombmp ($ original );
269+ }
270+ elseif (
271+ (strcmp ($ type ,'image/gif ' ) == 0 )
272+ &&
273+ (function_exists ('imagecreatefromgif ' ))
274+ ) {
275+
276+ $ image = imagecreatefromgif ($ original );
277+ }
278+ elseif (
279+ (in_array ($ type ,array ('image/jpg ' ,'image/jpeg ' ),true ))
280+ &&
281+ (function_exists ('imagecreatefromjpeg ' ))
282+ ) {
283+
284+ $ image = imagecreatefromjpeg ($ original );
285+ }
286+ elseif (
287+ (strcmp ($ type ,'image/png ' ) == 0 )
288+ &&
289+ (function_exists ('imagecreatefrompng ' ))
290+ ) {
291+
292+ $ image = imagecreatefrompng ($ original );
293+ }
294+ elseif (
295+ (strcmp ($ type ,'image/tga ' ) == 0 )
296+ &&
297+ (function_exists ('imagecreatefromtga ' ))
298+ ) {
299+
300+ $ image = imagecreatefromtga ($ original );
301+ }
302+
303+ if (
304+ (isset ($ image ))
305+ &&
306+ (is_resource ($ image ))
307+ ) {
308+
309+ imagepalettetotruecolor ($ image );
310+
311+ imagealphablending (
312+ $ image ,
313+ true
314+ );
315+
316+ imagesavealpha (
317+ $ image ,
318+ true
319+ );
320+
321+ imagewebp (
322+ $ image ,
323+ $ new ,
324+ 100
325+ );
326+
327+ $ result = imagedestroy ($ image );
328+ }
329+
330+ return $ result ;
331+ }
332+ # --- END PLUGIN CODE ---
333+ if (0 ) {
334+ ?>
335+ <!--
336+ # --- BEGIN PLUGIN HELP ---
337+ Original image file and thumbnail of it can be copied in WebP format.
338+ # --- END PLUGIN HELP ---
339+ -->
340+ <?php
341+ }
342+ ?>
0 commit comments