PluginProbe
Post Grid Gutenberg Blocks – PostX / 5.1.0
Post Grid Gutenberg Blocks – PostX v5.1.0
5.1.1 5.1.0 5.0.41 5.0.39 5.0.38 5.0.37 5.0.36 5.0.35 5.0.34 5.0.33 5.0.32 5.0.31 5.0.30 5.0.29 5.0.28 5.0.27 5.0.26 5.0.25 5.0.23 5.0.24 5.0.22 5.0.21 5.0.20 5.0.19 5.0.18 All 240 releases
ultimate-post / addons / custom_font / Custom_Font.php

Custom_Font.php in Post Grid Gutenberg Blocks – PostX 5.1.0, at addons/custom_font/Custom_Font.php

381 lines 18.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 namespace ULTP;
3
4 defined( 'ABSPATH' ) || exit;
5
6 class Custom_Font {
7 public function __construct() {
8 $this->custom_font_post_type_callback();
9 add_action( 'add_meta_boxes', array( $this, 'init_metabox_callback' ) );
10 add_action( 'save_post', array( $this, 'metabox_save_data' ) );
11 add_filter( 'manage_ultp_custom_font_posts_columns', array( $this, 'templates_table_head' ) );
12 add_action( 'manage_ultp_custom_font_posts_custom_column', array( $this, 'templates_table_content' ), 10, 2 );
13 add_filter( 'upload_mimes', array( $this, 'add_file_types_to_uploads' ) );
14 add_filter( 'wp_check_filetype_and_ext', array( $this, 'font_correct_filetypes' ), 10, 5 );
15 add_filter( 'wp_handle_upload_prefilter', array( $this, 'sanitize_svg_upload' ) );
16 add_filter( 'wp_handle_sideload_prefilter', array( $this, 'sanitize_svg_upload' ) );
17 add_filter( 'enter_title_here', array( $this, 'update_custom_font_title' ), 10, 2 );
18 }
19
20 public function update_custom_font_title( $title, $post ) {
21 if ( isset( $post->post_type ) && 'ultp_custom_font' === $post->post_type ) {
22 return __( 'Add Font Family Name', 'ultimate-post' );
23 }
24 return $title;
25 }
26
27 public function font_correct_filetypes( $data, $file, $filename, $mimes, $real_mime ) {
28 if ( ! empty( $data['ext'] ) && ! empty( $data['type'] ) ) {
29 return $data;
30 }
31
32 $wp_file_type = wp_check_filetype( $filename, $mimes );
33
34 if ( 'ttf' === $wp_file_type['ext'] ) {
35 $data['ext'] = 'ttf';
36 $data['type'] = 'font/ttf';
37 }
38 return $data;
39 }
40
41
42 public function add_file_types_to_uploads( $file_types ) {
43 if ( 'ultp_custom_font' == get_post_type() || current_user_can( 'manage_options' ) ) {
44 $new_filetypes = array();
45 $new_filetypes['woff'] = 'font/woff';
46 $new_filetypes['woff2'] = 'font/woff2';
47 $new_filetypes['ttf'] = 'font/ttf';
48 $new_filetypes['eot'] = 'font/ttf';
49 // SVG only for a custom font, where every upload is sanitized by sanitize_svg_upload().
50 if ( $this->is_custom_font_upload() ) {
51 $new_filetypes['svg'] = 'image/svg+xml';
52 }
53 $file_types = array_merge( $file_types, $new_filetypes );
54 return $file_types;
55 } else {
56 return $file_types;
57 }
58 }
59
60 /**
61 * Whether the current request uploads to, or edits, a custom font the user may edit.
62 *
63 * Uploads from the font screen's media modal send the font as `post_id`; async-upload.php
64 * checks its own nonce and refuses a `post_id` the user cannot edit. The screen itself is
65 * recognised by the global post.
66 *
67 * @return bool
68 */
69 private function is_custom_font_upload() {
70 if ( ! current_user_can( 'manage_options' ) ) {
71 return false;
72 }
73 $post_id = isset( $_REQUEST['post_id'] ) ? absint( $_REQUEST['post_id'] ) : 0; // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read only to choose the context; async-upload.php verifies the media-form nonce.
74 if ( ! $post_id ) {
75 $post_id = (int) get_the_ID();
76 }
77 return $post_id > 0 && 'ultp_custom_font' === get_post_type( $post_id ) && current_user_can( 'edit_post', $post_id );
78 }
79
80
81 /**
82 * Clean an SVG uploaded to a custom font.
83 *
84 * Only runs for custom font uploads, the one place this add-on allows SVG. The file keeps
85 * only its font markup; an SVG that is not a font is refused. SVG uploads anywhere else
86 * are not touched here: WordPress refuses them unless another plugin allows SVG.
87 *
88 * @param array $file Upload data from `$_FILES`.
89 * @return array
90 */
91 public function sanitize_svg_upload( $file ) {
92 if ( empty( $file['name'] ) || empty( $file['tmp_name'] ) || ! empty( $file['error'] ) ) {
93 return $file;
94 }
95 if ( 'svg' !== strtolower( pathinfo( $file['name'], PATHINFO_EXTENSION ) ) ) {
96 return $file;
97 }
98 if ( ! $this->is_custom_font_upload() ) {
99 return $file;
100 }
101
102 require_once __DIR__ . '/Svg_Font_Sanitizer.php';
103 $sanitized = Svg_Font_Sanitizer::sanitize_file( $file['tmp_name'] );
104 if ( is_wp_error( $sanitized ) ) {
105 $file['error'] = $sanitized->get_error_message();
106 }
107 return $file;
108 }
109
110 /**
111 * Font weight as stored and printed: 100-900 in steps of 100, normal or bold.
112 *
113 * @param string $weight Raw weight.
114 * @return string
115 */
116 public static function sanitize_font_weight( $weight ) {
117 $weight = strtolower( trim( (string) $weight ) );
118 if ( in_array( $weight, array( 'normal', 'bold', '100', '200', '300', '400', '500', '600', '700', '800', '900' ), true ) ) {
119 return $weight;
120 }
121 return 'normal';
122 }
123
124 /**
125 * Font family name safe to print inside a CSS string or a style attribute.
126 *
127 * @param string $font_name Post title of the font.
128 * @return string
129 */
130 public static function sanitize_font_family( $font_name ) {
131 return str_replace( array( '"', '\\', ';', '{', '}', '<', '>' ), '', (string) $font_name );
132 }
133
134 // Template Heading Add
135 public function templates_table_head( $defaults ) {
136 $type_array = array(
137 'preview' => '<span class="ultp-custom-font-preview-th">' . __( 'Preview', 'ultimate-post' ) . '</span>',
138 'woff' => __( 'WOFF', 'ultimate-post' ),
139 'woff2' => __( 'WOFF2', 'ultimate-post' ),
140 'ttf' => __( 'TTF', 'ultimate-post' ),
141 'svg' => __( 'SVG', 'ultimate-post' ),
142 'eot' => __( 'EOT', 'ultimate-post' ),
143 );
144 $defaults['title'] = __( 'Font Family', 'ultimate-post' );
145 array_splice( $defaults, 2, 0, $type_array );
146
147 return $defaults;
148 }
149
150
151 // Get Font Face
152 public function get_font_face( $settings, $font_name ) {
153 $font_src = array();
154 if ( $settings['woff'] ) {
155 array_push( $font_src, 'url(' . esc_url( $settings['woff'] ) . ') format("woff")' );
156 }
157 if ( $settings['woff2'] ) {
158 array_push( $font_src, 'url(' . esc_url( $settings['woff2'] ) . ') format("woff2")' );
159 }
160 if ( $settings['ttf'] ) {
161 array_push( $font_src, 'url(' . esc_url( $settings['ttf'] ) . ') format("TrueType")' );
162 }
163 if ( $settings['svg'] ) {
164 array_push( $font_src, 'url(' . esc_url( $settings['svg'] ) . ') format("svg")' );
165 }
166 if ( $settings['eot'] ) {
167 array_push( $font_src, 'url(' . esc_url( $settings['eot'] ) . ') format("eot")' );
168 }
169 $font_face = '@font-face {
170 font-family: "' . self::sanitize_font_family( $font_name ) . '";
171 font-weight: ' . self::sanitize_font_weight( isset( $settings['weight'] ) ? $settings['weight'] : '' ) . ';
172 src: ' . implode( ', ', $font_src ) . ';
173 }';
174
175 return $font_face;
176 }
177
178
179 // Column Content
180 public function templates_table_content( $column_id, $post_id ) {
181 $woff = $woff2 = $ttf = $svg = $eot = false;
182 $settings = get_post_meta( $post_id, '__font_settings', true );
183
184 if ( $settings ) {
185 foreach ( $settings as $key => $value ) {
186 if ( $value['woff'] ) {
187 $woff = true; }
188 if ( $value['woff2'] ) {
189 $woff2 = true; }
190 if ( $value['ttf'] ) {
191 $ttf = true; }
192 if ( $value['svg'] ) {
193 $svg = true; }
194 if ( $value['eot'] ) {
195 $eot = true; }
196 }
197 $font_face = $this->get_font_face( $settings[0], get_the_title( $post_id ) );
198 echo '<style type="text/css">' . $font_face . '</style>'; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- CSS from get_font_face(): URLs pass esc_url(), family and weight pass sanitize_font_family()/sanitize_font_weight().
199
200 switch ( $column_id ) {
201 case 0:
202 echo '<span class="ultp-custom-font-preview" style="font-family: ' . esc_attr( get_the_title( $post_id ) ) . '">' . esc_html__( 'The quick brown fox jumps over the lazy dog.', 'ultimate-post' ) . '</span>';
203 break;
204 case 1:
205 echo '<span class="dashicons ' . ( $woff ? 'dashicons-yes' : 'dashicons-no-alt' ) . '"></span>';
206 break;
207 case 2:
208 echo '<span class="dashicons ' . ( $woff2 ? 'dashicons-yes' : 'dashicons-no-alt' ) . '"></span>';
209 break;
210 case 3:
211 echo '<span class="dashicons ' . ( $ttf ? 'dashicons-yes' : 'dashicons-no-alt' ) . '"></span>';
212 break;
213 case 4:
214 echo '<span class="dashicons ' . ( $svg ? 'dashicons-yes' : 'dashicons-no-alt' ) . '"></span>';
215 break;
216 case 5:
217 echo '<span class="dashicons ' . ( $eot ? 'dashicons-yes' : 'dashicons-no-alt' ) . '"></span>';
218 break;
219 default:
220 break;
221 }
222 }
223 }
224
225
226 function init_metabox_callback() {
227 add_meta_box(
228 'ultp-custom-font-id',
229 __( 'Font Vaiations', 'ultimate-post' ),
230 array( $this, 'custom_font_callback' ),
231 'ultp_custom_font',
232 'advanced'
233 );
234 }
235
236
237 function set_data( $arr = array(), $font_name = '' ) {
238 ?>
239 <div class="ultp-custom-font-container ultp-custom-font<?php echo empty( $arr ) ? '-copy' : ''; ?>">
240 <div class="ultp-custom-font-heading">
241 <div>
242 <label class="font-label"><?php echo esc_html__( 'Weight: ', 'ultimate-post' ); ?> <span class="ultp-custom-font-weight"> <?php echo esc_html( isset( $arr['weight'] ) ? $arr['weight'] : '' ); ?> </span></label>
243 <select name="weight[]">
244 <?php $weight = isset( $arr['weight'] ) ? $arr['weight'] : ''; ?>
245 <option <?php selected( $weight, 'normal' ); ?> value="normal"><?php echo esc_html__( 'Normal', 'ultimate-post' ); ?></option>
246 <option <?php selected( $weight, '100' ); ?> value="100"><?php echo esc_html__( '100', 'ultimate-post' ); ?></option>
247 <option <?php selected( $weight, '200' ); ?> value="200"><?php echo esc_html__( '200', 'ultimate-post' ); ?></option>
248 <option <?php selected( $weight, '300' ); ?> value="300"><?php echo esc_html__( '300', 'ultimate-post' ); ?></option>
249 <option <?php selected( $weight, '400' ); ?> value="400"><?php echo esc_html__( '400', 'ultimate-post' ); ?></option>
250 <option <?php selected( $weight, '500' ); ?> value="500"><?php echo esc_html__( '500', 'ultimate-post' ); ?></option>
251 <option <?php selected( $weight, '600' ); ?> value="600"><?php echo esc_html__( '600', 'ultimate-post' ); ?></option>
252 <option <?php selected( $weight, '700' ); ?> value="700"><?php echo esc_html__( '700', 'ultimate-post' ); ?></option>
253 <option <?php selected( $weight, '800' ); ?> value="800"><?php echo esc_html__( '800', 'ultimate-post' ); ?></option>
254 <option <?php selected( $weight, '900' ); ?> value="900"><?php echo esc_html__( '900', 'ultimate-post' ); ?></option>
255 </select>
256 </div>
257 <?php
258 $preview_style = '';
259 if ( ! empty( $arr ) ) {
260 $font_face = $this->get_font_face( $arr, $font_name );
261 echo '<style type="text/css">' . $font_face . '</style>'; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- CSS from get_font_face(): URLs pass esc_url(), family and weight pass sanitize_font_family()/sanitize_font_weight().
262 $preview_style = 'font-family: "' . self::sanitize_font_family( $font_name ) . '"; font-weight: ' . self::sanitize_font_weight( isset( $arr['weight'] ) ? $arr['weight'] : '' );
263 }
264 ?>
265 <span <?php echo '' !== $preview_style ? 'style="' . esc_attr( $preview_style ) . '"' : ''; ?> class="ultp-custom-font-preview"><?php echo esc_html__( 'The quick brown fox jumps over the lazy dog', 'ultimate-post' ); ?></span>
266 <div class="ultp-custom-font-actions">
267 <span class="ultp-custom-font-edit"><span class="dashicons dashicons-edit"></span><?php echo esc_html__( 'Edit', 'ultimate-post' ); ?></span>
268 <span class="ultp-custom-font-close"><span class="dashicons dashicons-no-alt"></span><?php echo esc_html__( 'Close', 'ultimate-post' ); ?></span>
269 <span class="ultp-custom-font-delete"><span class="dashicons dashicons-trash"></span><?php echo esc_html__( 'Delete', 'ultimate-post' ); ?></span>
270 </div>
271 </div>
272 <div class="ultp-custom-font-content">
273 <div class="ultp-font-file-list">
274 <label><?php echo esc_html__( 'WOFF File', 'ultimate-post' ); ?></label>
275 <input type="text" name="woff[]" value="<?php echo esc_attr( isset( $arr['woff'] ) ? $arr['woff'] : '' ); ?>" placeholder="<?php echo esc_html__( 'The web open Font Format, Used by Modern Browsers', 'ultimate-post' ); ?>"/>
276 <span class="button ultp-font-upload"><span class="dashicons dashicons-upload"></span><?php echo esc_html__( 'Upload', 'ultimate-post' ); ?></span>
277 </div>
278 <div class="ultp-font-file-list">
279 <label><?php echo esc_html__( 'WOFF2 File', 'ultimate-post' ); ?></label>
280 <input type="text" name="woff2[]" value="<?php echo esc_attr( isset( $arr['woff2'] ) ? $arr['woff2'] : '' ); ?>" placeholder="<?php echo esc_html__( 'The web open Font Format 2, Used by Super Modern Browsers', 'ultimate-post' ); ?>"/>
281 <span class="button ultp-font-upload"><span class="dashicons dashicons-upload"></span><?php echo esc_html__( 'Upload', 'ultimate-post' ); ?></span>
282 </div>
283 <div class="ultp-font-file-list">
284 <label><?php echo esc_html__( 'TTF File', 'ultimate-post' ); ?></label>
285 <input type="text" name="ttf[]" value="<?php echo esc_attr( isset( $arr['ttf'] ) ? $arr['ttf'] : '' ); ?>" placeholder="<?php echo esc_html__( 'TrueType Fonts, Used for better supporting Safari, Android, iOS', 'ultimate-post' ); ?>"/>
286 <span class="button ultp-font-upload"><span class="dashicons dashicons-upload"></span><?php echo esc_html__( 'Upload', 'ultimate-post' ); ?></span>
287 </div>
288 <div class="ultp-font-file-list">
289 <label><?php echo esc_html__( 'SVG File', 'ultimate-post' ); ?></label>
290 <input type="text" name="svg[]" value="<?php echo esc_attr( isset( $arr['svg'] ) ? $arr['svg'] : '' ); ?>" placeholder="<?php echo esc_html__( 'SVG font allow SVG to be used as glyphs when displaying text, Used by Legacy iOS', 'ultimate-post' ); ?>"/>
291 <span class="button ultp-font-upload"><span class="dashicons dashicons-upload"></span><?php echo esc_html__( 'Upload', 'ultimate-post' ); ?></span>
292 </div>
293 <div class="ultp-font-file-list">
294 <label><?php echo esc_html__( 'EOT File', 'ultimate-post' ); ?></label>
295 <input type="text" name="eot[]" value="<?php echo esc_attr( isset( $arr['eot'] ) ? $arr['eot'] : '' ); ?>" placeholder="<?php echo esc_html__( 'Embedded OpenType, Used by IE6-IE9 Browsers', 'ultimate-post' ); ?>"/>
296 <span class="button ultp-font-upload"><span class="dashicons dashicons-upload"></span><?php echo esc_html__( 'Upload', 'ultimate-post' ); ?></span>
297 </div>
298 </div>
299 </div>
300 <?php
301 }
302
303
304 function custom_font_callback( $post ) {
305 wp_nonce_field( 'font_meta_box', 'custom_font_nonce' );
306 $settings = get_post_meta( $post->ID, '__font_settings', true );
307
308 $this->set_data(); // Set Empty Data
309
310 if ( is_array( $settings ) && ! empty( $settings ) ) {
311 foreach ( $settings as $key => $val ) {
312 $this->set_data( $val, $post->post_title );
313 }
314 }
315 echo '<span class="button ultp-font-variation-action">' . esc_html__( 'Add Variation', 'ultimate-post' ) . '</span>';
316 }
317
318
319 function metabox_save_data( $post_id ) {
320 if ( ! isset( $_POST['custom_font_nonce'] ) ) {
321 return; }
322 if ( ! wp_verify_nonce( sanitize_key( wp_unslash( $_POST['custom_font_nonce'] ) ), 'font_meta_box' ) ) {
323 return; }
324
325 $arr = array();
326 if ( isset( $_POST['weight'] ) && is_array( $_POST['weight'] ) ) {
327 foreach ($_POST['weight'] as $i => $value) { //phpcs:ignore
328 if ( isset( $_POST['weight'][ $i ] ) &&
329 ( ! empty( $_POST['woff'][ $i ] ) ||
330 ! empty( $_POST['woff2'][ $i ] ) ||
331 ! empty( $_POST['ttf'][ $i ] ) ||
332 ! empty( $_POST['svg'][ $i ] ) ||
333 ! empty( $_POST['eot'][ $i ] ) ) ) {
334 $temp = array();
335 $temp['weight'] = self::sanitize_font_weight( sanitize_text_field( $_POST['weight'][ $i ] ) ); // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
336 $temp['woff'] = isset( $_POST['woff'][ $i ] ) ? sanitize_text_field( $_POST['woff'][ $i ] ) : ''; // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
337 $temp['woff2'] = isset( $_POST['woff2'][ $i ] ) ? sanitize_text_field( $_POST['woff2'][ $i ] ) : ''; // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
338 $temp['ttf'] = isset( $_POST['ttf'][ $i ] ) ? sanitize_text_field( $_POST['ttf'][ $i ] ) : ''; // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
339 $temp['svg'] = isset( $_POST['svg'][ $i ] ) ? sanitize_text_field( $_POST['svg'][ $i ] ) : ''; // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
340 $temp['eot'] = isset( $_POST['eot'][ $i ] ) ? sanitize_text_field( $_POST['eot'][ $i ] ) : ''; // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.MissingUnslash -- update_post_meta() unslashes; unslashing here would strip backslashes twice.
341 $arr[] = $temp;
342 }
343 }
344 update_post_meta( $post_id, '__font_settings', $arr );
345 }
346 }
347
348 // Templates Post Type Register
349 public function custom_font_post_type_callback() {
350 $labels = array(
351 'name' => _x( 'Custom Fonts', 'Custom Font', 'ultimate-post' ),
352 'singular_name' => _x( 'Saved Custom Font', 'Custom Font', 'ultimate-post' ),
353 'menu_name' => __( 'Saved Custom Font', 'ultimate-post' ),
354 'parent_item_colon' => __( 'Parent Custom Font', 'ultimate-post' ),
355 'all_items' => __( 'Saved Custom Font', 'ultimate-post' ),
356 'view_item' => __( 'View Custom Font', 'ultimate-post' ),
357 'add_new_item' => __( 'Add New', 'ultimate-post' ),
358 'add_new' => __( 'Add New', 'ultimate-post' ),
359 'edit_item' => __( 'Edit Custom Font', 'ultimate-post' ),
360 'update_item' => __( 'Update Custom Font', 'ultimate-post' ),
361 'search_items' => __( 'Search Custom Font', 'ultimate-post' ),
362 'not_found' => __( 'No Custom Font Found', 'ultimate-post' ),
363 'not_found_in_trash' => __( 'Not Custom Font found in Trash', 'ultimate-post' ),
364 );
365 $args = array(
366 'labels' => $labels,
367 'show_in_rest' => true,
368 'supports' => array( 'title' ),
369 'hierarchical' => false,
370 'public' => false,
371 'rewrite' => false,
372 'show_ui' => true,
373 'show_in_menu' => false,
374 'show_in_nav_menus' => false,
375 'exclude_from_search' => true,
376 'capability_type' => 'page',
377 );
378 register_post_type( 'ultp_custom_font', $args );
379 }
380 }
381