Make WordPress Core

Ticket #55695: script-loader.php

File script-loader.php, 110.9 KB (added by maycon3, 4 years ago)
Line 
1<?php
2/**
3 * WordPress scripts and styles default loader.
4 *
5 * Several constants are used to manage the loading, concatenating and compression of scripts and CSS:
6 * define('SCRIPT_DEBUG', true); loads the development (non-minified) versions of all scripts and CSS, and disables compression and concatenation,
7 * define('CONCATENATE_SCRIPTS', false); disables compression and concatenation of scripts and CSS,
8 * define('COMPRESS_SCRIPTS', false); disables compression of scripts,
9 * define('COMPRESS_CSS', false); disables compression of CSS,
10 * define('ENFORCE_GZIP', true); forces gzip for compression (default is deflate).
11 *
12 * The globals $concatenate_scripts, $compress_scripts and $compress_css can be set by plugins
13 * to temporarily override the above settings. Also a compression test is run once and the result is saved
14 * as option 'can_compress_scripts' (0/1). The test will run again if that option is deleted.
15 *
16 * @package WordPress
17 */
18
19/** WordPress Dependency Class */
20require ABSPATH . WPINC . '/class-wp-dependency.php';
21
22/** WordPress Dependencies Class */
23require ABSPATH . WPINC . '/class.wp-dependencies.php';
24
25/** WordPress Scripts Class */
26require ABSPATH . WPINC . '/class.wp-scripts.php';
27
28/** WordPress Scripts Functions */
29require ABSPATH . WPINC . '/functions.wp-scripts.php';
30
31/** WordPress Styles Class */
32require ABSPATH . WPINC . '/class.wp-styles.php';
33
34/** WordPress Styles Functions */
35require ABSPATH . WPINC . '/functions.wp-styles.php';
36
37/**
38 * Registers TinyMCE scripts.
39 *
40 * @since 5.0.0
41 *
42 * @global string $tinymce_version
43 * @global bool $concatenate_scripts
44 * @global bool $compress_scripts
45 *
46 * @param WP_Scripts $scripts WP_Scripts object.
47 * @param bool $force_uncompressed Whether to forcibly prevent gzip compression. Default false.
48 */
49function wp_register_tinymce_scripts( $scripts, $force_uncompressed = false ) {
50 global $tinymce_version, $concatenate_scripts, $compress_scripts;
51
52 $suffix = wp_scripts_get_suffix();
53 $dev_suffix = wp_scripts_get_suffix( 'dev' );
54
55 script_concat_settings();
56
57 $compressed = $compress_scripts && $concatenate_scripts && isset( $_SERVER['HTTP_ACCEPT_ENCODING'] )
58 && false !== stripos( $_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip' ) && ! $force_uncompressed;
59
60 // Load tinymce.js when running from /src, otherwise load wp-tinymce.js.gz (in production)
61 // or tinymce.min.js (when SCRIPT_DEBUG is true).
62 if ( $compressed ) {
63 $scripts->add( 'wp-tinymce', includes_url( 'js/tinymce/' ) . 'wp-tinymce.js', array(), $tinymce_version );
64 } else {
65 $scripts->add( 'wp-tinymce-root', includes_url( 'js/tinymce/' ) . "tinymce$dev_suffix.js", array(), $tinymce_version );
66 $scripts->add( 'wp-tinymce', includes_url( 'js/tinymce/' ) . "plugins/compat3x/plugin$dev_suffix.js", array( 'wp-tinymce-root' ), $tinymce_version );
67 }
68
69 $scripts->add( 'wp-tinymce-lists', includes_url( "js/tinymce/plugins/lists/plugin$suffix.js" ), array( 'wp-tinymce' ), $tinymce_version );
70}
71
72/**
73 * Registers all the WordPress vendor scripts that are in the standardized
74 * `js/dist/vendor/` location.
75 *
76 * For the order of `$scripts->add` see `wp_default_scripts`.
77 *
78 * @since 5.0.0
79 *
80 * @global WP_Locale $wp_locale WordPress date and time locale object.
81 *
82 * @param WP_Scripts $scripts WP_Scripts object.
83 */
84function wp_default_packages_vendor( $scripts ) {
85 global $wp_locale;
86
87 $suffix = wp_scripts_get_suffix();
88
89 $vendor_scripts = array(
90 'react' => array( 'wp-polyfill' ),
91 'react-dom' => array( 'react' ),
92 'regenerator-runtime',
93 'moment',
94 'lodash',
95 'wp-polyfill-fetch',
96 'wp-polyfill-formdata',
97 'wp-polyfill-node-contains',
98 'wp-polyfill-url',
99 'wp-polyfill-dom-rect',
100 'wp-polyfill-element-closest',
101 'wp-polyfill-object-fit',
102 'wp-polyfill' => array( 'regenerator-runtime' ),
103 );
104
105 $vendor_scripts_versions = array(
106 'react' => '17.0.1',
107 'react-dom' => '17.0.1',
108 'regenerator-runtime' => '0.13.9',
109 'moment' => '2.29.1',
110 'lodash' => '4.17.19',
111 'wp-polyfill-fetch' => '3.6.2',
112 'wp-polyfill-formdata' => '4.0.0',
113 'wp-polyfill-node-contains' => '3.105.0',
114 'wp-polyfill-url' => '3.6.4',
115 'wp-polyfill-dom-rect' => '3.104.0',
116 'wp-polyfill-element-closest' => '2.0.2',
117 'wp-polyfill-object-fit' => '2.3.5',
118 'wp-polyfill' => '3.15.0',
119 );
120
121 foreach ( $vendor_scripts as $handle => $dependencies ) {
122 if ( is_string( $dependencies ) ) {
123 $handle = $dependencies;
124 $dependencies = array();
125 }
126
127 $path = "/wp-includes/js/dist/vendor/$handle$suffix.js";
128 $version = $vendor_scripts_versions[ $handle ];
129
130 $scripts->add( $handle, $path, $dependencies, $version, 1 );
131 }
132
133 did_action( 'init' ) && $scripts->add_inline_script( 'lodash', 'window.lodash = _.noConflict();' );
134
135 did_action( 'init' ) && $scripts->add_inline_script(
136 'moment',
137 sprintf(
138 "moment.updateLocale( '%s', %s );",
139 get_user_locale(),
140 wp_json_encode(
141 array(
142 'months' => array_values( $wp_locale->month ),
143 'monthsShort' => array_values( $wp_locale->month_abbrev ),
144 'weekdays' => array_values( $wp_locale->weekday ),
145 'weekdaysShort' => array_values( $wp_locale->weekday_abbrev ),
146 'week' => array(
147 'dow' => (int) get_option( 'start_of_week', 0 ),
148 ),
149 'longDateFormat' => array(
150 'LT' => get_option( 'time_format', __( 'g:i a' ) ),
151 'LTS' => null,
152 'L' => null,
153 'LL' => get_option( 'date_format', __( 'F j, Y' ) ),
154 'LLL' => __( 'F j, Y g:i a' ),
155 'LLLL' => null,
156 ),
157 )
158 )
159 ),
160 'after'
161 );
162}
163
164/**
165 * Returns contents of an inline script used in appending polyfill scripts for
166 * browsers which fail the provided tests. The provided array is a mapping from
167 * a condition to verify feature support to its polyfill script handle.
168 *
169 * @since 5.0.0
170 *
171 * @param WP_Scripts $scripts WP_Scripts object.
172 * @param array $tests Features to detect.
173 * @return string Conditional polyfill inline script.
174 */
175function wp_get_script_polyfill( $scripts, $tests ) {
176 $polyfill = '';
177 foreach ( $tests as $test => $handle ) {
178 if ( ! array_key_exists( $handle, $scripts->registered ) ) {
179 continue;
180 }
181
182 $src = $scripts->registered[ $handle ]->src;
183 $ver = $scripts->registered[ $handle ]->ver;
184
185 if ( ! preg_match( '|^(https?:)?//|', $src ) && ! ( $scripts->content_url && 0 === strpos( $src, $scripts->content_url ) ) ) {
186 $src = $scripts->base_url . $src;
187 }
188
189 if ( ! empty( $ver ) ) {
190 $src = add_query_arg( 'ver', $ver, $src );
191 }
192
193 /** This filter is documented in wp-includes/class.wp-scripts.php */
194 $src = esc_url( apply_filters( 'script_loader_src', $src, $handle ) );
195
196 if ( ! $src ) {
197 continue;
198 }
199
200 $polyfill .= (
201 // Test presence of feature...
202 '( ' . $test . ' ) || ' .
203 /*
204 * ...appending polyfill on any failures. Cautious viewers may balk
205 * at the `document.write`. Its caveat of synchronous mid-stream
206 * blocking write is exactly the behavior we need though.
207 */
208 'document.write( \'<script src="' .
209 $src .
210 '"></scr\' + \'ipt>\' );'
211 );
212 }
213
214 return $polyfill;
215}
216
217/**
218 * Registers all the WordPress packages scripts that are in the standardized
219 * `js/dist/` location.
220 *
221 * For the order of `$scripts->add` see `wp_default_scripts`.
222 *
223 * @since 5.0.0
224 *
225 * @param WP_Scripts $scripts WP_Scripts object.
226 */
227function wp_default_packages_scripts( $scripts ) {
228 $suffix = wp_scripts_get_suffix();
229
230 /*
231 * Expects multidimensional array like:
232 *
233 * 'a11y.js' => array('dependencies' => array(...), 'version' => '...'),
234 * 'annotations.js' => array('dependencies' => array(...), 'version' => '...'),
235 * 'api-fetch.js' => array(...
236 */
237 $assets = include ABSPATH . WPINC . '/assets/script-loader-packages.php';
238
239 foreach ( $assets as $package_name => $package_data ) {
240 $basename = basename( $package_name, '.js' );
241 $handle = 'wp-' . $basename;
242 $path = "/wp-includes/js/dist/{$basename}{$suffix}.js";
243
244 if ( ! empty( $package_data['dependencies'] ) ) {
245 $dependencies = $package_data['dependencies'];
246 } else {
247 $dependencies = array();
248 }
249
250 // Add dependencies that cannot be detected and generated by build tools.
251 switch ( $handle ) {
252 case 'wp-block-library':
253 array_push( $dependencies, 'editor' );
254 break;
255 case 'wp-edit-post':
256 array_push( $dependencies, 'media-models', 'media-views', 'postbox', 'wp-dom-ready' );
257 break;
258 }
259
260 $scripts->add( $handle, $path, $dependencies, $package_data['version'], 1 );
261
262 if ( in_array( 'wp-i18n', $dependencies, true ) ) {
263 $scripts->set_translations( $handle );
264 }
265
266 /*
267 * Manually set the text direction localization after wp-i18n is printed.
268 * This ensures that wp.i18n.isRTL() returns true in RTL languages.
269 * We cannot use $scripts->set_translations( 'wp-i18n' ) to do this
270 * because WordPress prints a script's translations *before* the script,
271 * which means, in the case of wp-i18n, that wp.i18n.setLocaleData()
272 * is called before wp.i18n is defined.
273 */
274 if ( 'wp-i18n' === $handle ) {
275 $ltr = _x( 'ltr', 'text direction' );
276 $script = sprintf( "wp.i18n.setLocaleData( { 'text direction\u0004ltr': [ '%s' ] } );", $ltr );
277 $scripts->add_inline_script( $handle, $script, 'after' );
278 }
279 }
280}
281
282/**
283 * Adds inline scripts required for the WordPress JavaScript packages.
284 *
285 * @since 5.0.0
286 *
287 * @global WP_Locale $wp_locale WordPress date and time locale object.
288 *
289 * @param WP_Scripts $scripts WP_Scripts object.
290 */
291function wp_default_packages_inline_scripts( $scripts ) {
292 global $wp_locale;
293
294 if ( isset( $scripts->registered['wp-api-fetch'] ) ) {
295 $scripts->registered['wp-api-fetch']->deps[] = 'wp-hooks';
296 }
297 $scripts->add_inline_script(
298 'wp-api-fetch',
299 sprintf(
300 'wp.apiFetch.use( wp.apiFetch.createRootURLMiddleware( "%s" ) );',
301 esc_url_raw( get_rest_url() )
302 ),
303 'after'
304 );
305 $scripts->add_inline_script(
306 'wp-api-fetch',
307 implode(
308 "\n",
309 array(
310 sprintf(
311 'wp.apiFetch.nonceMiddleware = wp.apiFetch.createNonceMiddleware( "%s" );',
312 ( wp_installing() && ! is_multisite() ) ? '' : wp_create_nonce( 'wp_rest' )
313 ),
314 'wp.apiFetch.use( wp.apiFetch.nonceMiddleware );',
315 'wp.apiFetch.use( wp.apiFetch.mediaUploadMiddleware );',
316 sprintf(
317 'wp.apiFetch.nonceEndpoint = "%s";',
318 admin_url( 'admin-ajax.php?action=rest-nonce' )
319 ),
320 )
321 ),
322 'after'
323 );
324 $scripts->add_inline_script(
325 'wp-data',
326 implode(
327 "\n",
328 array(
329 '( function() {',
330 ' var userId = ' . get_current_user_ID() . ';',
331 ' var storageKey = "WP_DATA_USER_" + userId;',
332 ' wp.data',
333 ' .use( wp.data.plugins.persistence, { storageKey: storageKey } );',
334 ' wp.data.plugins.persistence.__unstableMigrate( { storageKey: storageKey } );',
335 '} )();',
336 )
337 )
338 );
339
340 // Calculate the timezone abbr (EDT, PST) if possible.
341 $timezone_string = get_option( 'timezone_string', 'UTC' );
342 $timezone_abbr = '';
343
344 if ( ! empty( $timezone_string ) ) {
345 $timezone_date = new DateTime( 'now', new DateTimeZone( $timezone_string ) );
346 $timezone_abbr = $timezone_date->format( 'T' );
347 }
348
349 $scripts->add_inline_script(
350 'wp-date',
351 sprintf(
352 'wp.date.setSettings( %s );',
353 wp_json_encode(
354 array(
355 'l10n' => array(
356 'locale' => get_user_locale(),
357 'months' => array_values( $wp_locale->month ),
358 'monthsShort' => array_values( $wp_locale->month_abbrev ),
359 'weekdays' => array_values( $wp_locale->weekday ),
360 'weekdaysShort' => array_values( $wp_locale->weekday_abbrev ),
361 'meridiem' => (object) $wp_locale->meridiem,
362 'relative' => array(
363 /* translators: %s: Duration. */
364 'future' => __( '%s from now' ),
365 /* translators: %s: Duration. */
366 'past' => __( '%s ago' ),
367 ),
368 ),
369 'formats' => array(
370 /* translators: Time format, see https://www.php.net/manual/datetime.format.php */
371 'time' => get_option( 'time_format', __( 'g:i a' ) ),
372 /* translators: Date format, see https://www.php.net/manual/datetime.format.php */
373 'date' => get_option( 'date_format', __( 'F j, Y' ) ),
374 /* translators: Date/Time format, see https://www.php.net/manual/datetime.format.php */
375 'datetime' => __( 'F j, Y g:i a' ),
376 /* translators: Abbreviated date/time format, see https://www.php.net/manual/datetime.format.php */
377 'datetimeAbbreviated' => __( 'M j, Y g:i a' ),
378 ),
379 'timezone' => array(
380 'offset' => get_option( 'gmt_offset', 0 ),
381 'string' => $timezone_string,
382 'abbr' => $timezone_abbr,
383 ),
384 )
385 )
386 ),
387 'after'
388 );
389
390 // Loading the old editor and its config to ensure the classic block works as expected.
391 $scripts->add_inline_script(
392 'editor',
393 'window.wp.oldEditor = window.wp.editor;',
394 'after'
395 );
396
397 /*
398 * wp-editor module is exposed as window.wp.editor.
399 * Problem: there is quite some code expecting window.wp.oldEditor object available under window.wp.editor.
400 * Solution: fuse the two objects together to maintain backward compatibility.
401 * For more context, see https://github.com/WordPress/gutenberg/issues/33203.
402 */
403 $scripts->add_inline_script(
404 'wp-editor',
405 'Object.assign( window.wp.editor, window.wp.oldEditor );',
406 'after'
407 );
408}
409
410/**
411 * Adds inline scripts required for the TinyMCE in the block editor.
412 *
413 * These TinyMCE init settings are used to extend and override the default settings
414 * from `_WP_Editors::default_settings()` for the Classic block.
415 *
416 * @since 5.0.0
417 *
418 * @global WP_Scripts $wp_scripts
419 */
420function wp_tinymce_inline_scripts() {
421 global $wp_scripts;
422
423 /** This filter is documented in wp-includes/class-wp-editor.php */
424 $editor_settings = apply_filters( 'wp_editor_settings', array( 'tinymce' => true ), 'classic-block' );
425
426 $tinymce_plugins = array(
427 'charmap',
428 'colorpicker',
429 'hr',
430 'lists',
431 'media',
432 'paste',
433 'tabfocus',
434 'textcolor',
435 'fullscreen',
436 'wordpress',
437 'wpautoresize',
438 'wpeditimage',
439 'wpemoji',
440 'wpgallery',
441 'wplink',
442 'wpdialogs',
443 'wptextpattern',
444 'wpview',
445 );
446
447 /** This filter is documented in wp-includes/class-wp-editor.php */
448 $tinymce_plugins = apply_filters( 'tiny_mce_plugins', $tinymce_plugins, 'classic-block' );
449 $tinymce_plugins = array_unique( $tinymce_plugins );
450
451 $disable_captions = false;
452 // Runs after `tiny_mce_plugins` but before `mce_buttons`.
453 /** This filter is documented in wp-admin/includes/media.php */
454 if ( apply_filters( 'disable_captions', '' ) ) {
455 $disable_captions = true;
456 }
457
458 $toolbar1 = array(
459 'formatselect',
460 'bold',
461 'italic',
462 'bullist',
463 'numlist',
464 'blockquote',
465 'alignleft',
466 'aligncenter',
467 'alignright',
468 'link',
469 'unlink',
470 'wp_more',
471 'spellchecker',
472 'wp_add_media',
473 'wp_adv',
474 );
475
476 /** This filter is documented in wp-includes/class-wp-editor.php */
477 $toolbar1 = apply_filters( 'mce_buttons', $toolbar1, 'classic-block' );
478
479 $toolbar2 = array(
480 'strikethrough',
481 'hr',
482 'forecolor',
483 'pastetext',
484 'removeformat',
485 'charmap',
486 'outdent',
487 'indent',
488 'undo',
489 'redo',
490 'wp_help',
491 );
492
493 /** This filter is documented in wp-includes/class-wp-editor.php */
494 $toolbar2 = apply_filters( 'mce_buttons_2', $toolbar2, 'classic-block' );
495 /** This filter is documented in wp-includes/class-wp-editor.php */
496 $toolbar3 = apply_filters( 'mce_buttons_3', array(), 'classic-block' );
497 /** This filter is documented in wp-includes/class-wp-editor.php */
498 $toolbar4 = apply_filters( 'mce_buttons_4', array(), 'classic-block' );
499 /** This filter is documented in wp-includes/class-wp-editor.php */
500 $external_plugins = apply_filters( 'mce_external_plugins', array(), 'classic-block' );
501
502 $tinymce_settings = array(
503 'plugins' => implode( ',', $tinymce_plugins ),
504 'toolbar1' => implode( ',', $toolbar1 ),
505 'toolbar2' => implode( ',', $toolbar2 ),
506 'toolbar3' => implode( ',', $toolbar3 ),
507 'toolbar4' => implode( ',', $toolbar4 ),
508 'external_plugins' => wp_json_encode( $external_plugins ),
509 'classic_block_editor' => true,
510 );
511
512 if ( $disable_captions ) {
513 $tinymce_settings['wpeditimage_disable_captions'] = true;
514 }
515
516 if ( ! empty( $editor_settings['tinymce'] ) && is_array( $editor_settings['tinymce'] ) ) {
517 array_merge( $tinymce_settings, $editor_settings['tinymce'] );
518 }
519
520 /** This filter is documented in wp-includes/class-wp-editor.php */
521 $tinymce_settings = apply_filters( 'tiny_mce_before_init', $tinymce_settings, 'classic-block' );
522
523 // Do "by hand" translation from PHP array to js object.
524 // Prevents breakage in some custom settings.
525 $init_obj = '';
526 foreach ( $tinymce_settings as $key => $value ) {
527 if ( is_bool( $value ) ) {
528 $val = $value ? 'true' : 'false';
529 $init_obj .= $key . ':' . $val . ',';
530 continue;
531 } elseif ( ! empty( $value ) && is_string( $value ) && (
532 ( '{' === $value[0] && '}' === $value[ strlen( $value ) - 1 ] ) ||
533 ( '[' === $value[0] && ']' === $value[ strlen( $value ) - 1 ] ) ||
534 preg_match( '/^\(?function ?\(/', $value ) ) ) {
535 $init_obj .= $key . ':' . $value . ',';
536 continue;
537 }
538 $init_obj .= $key . ':"' . $value . '",';
539 }
540
541 $init_obj = '{' . trim( $init_obj, ' ,' ) . '}';
542
543 $script = 'window.wpEditorL10n = {
544 tinymce: {
545 baseURL: ' . wp_json_encode( includes_url( 'js/tinymce' ) ) . ',
546 suffix: ' . ( SCRIPT_DEBUG ? '""' : '".min"' ) . ',
547 settings: ' . $init_obj . ',
548 }
549 }';
550
551 $wp_scripts->add_inline_script( 'wp-block-library', $script, 'before' );
552}
553
554/**
555 * Registers all the WordPress packages scripts.
556 *
557 * @since 5.0.0
558 *
559 * @param WP_Scripts $scripts WP_Scripts object.
560 */
561function wp_default_packages( $scripts ) {
562 wp_default_packages_vendor( $scripts );
563 wp_register_tinymce_scripts( $scripts );
564 wp_default_packages_scripts( $scripts );
565
566 if ( did_action( 'init' ) ) {
567 wp_default_packages_inline_scripts( $scripts );
568 }
569}
570
571/**
572 * Returns the suffix that can be used for the scripts.
573 *
574 * There are two suffix types, the normal one and the dev suffix.
575 *
576 * @since 5.0.0
577 *
578 * @param string $type The type of suffix to retrieve.
579 * @return string The script suffix.
580 */
581function wp_scripts_get_suffix( $type = '' ) {
582 static $suffixes;
583
584 if ( null === $suffixes ) {
585 // Include an unmodified $wp_version.
586 require ABSPATH . WPINC . '/version.php';
587
588 $develop_src = false !== strpos( $wp_version, '-src' );
589
590 if ( ! defined( 'SCRIPT_DEBUG' ) ) {
591 define( 'SCRIPT_DEBUG', $develop_src );
592 }
593 $suffix = SCRIPT_DEBUG ? '' : '.min';
594 $dev_suffix = $develop_src ? '' : '.min';
595
596 $suffixes = array(
597 'suffix' => $suffix,
598 'dev_suffix' => $dev_suffix,
599 );
600 }
601
602 if ( 'dev' === $type ) {
603 return $suffixes['dev_suffix'];
604 }
605
606 return $suffixes['suffix'];
607}
608
609/**
610 * Register all WordPress scripts.
611 *
612 * Localizes some of them.
613 * args order: `$scripts->add( 'handle', 'url', 'dependencies', 'query-string', 1 );`
614 * when last arg === 1 queues the script for the footer
615 *
616 * @since 2.6.0
617 *
618 * @param WP_Scripts $scripts WP_Scripts object.
619 */
620function wp_default_scripts( $scripts ) {
621 $suffix = wp_scripts_get_suffix();
622 $dev_suffix = wp_scripts_get_suffix( 'dev' );
623 $guessurl = site_url();
624
625 if ( ! $guessurl ) {
626 $guessed_url = true;
627 $guessurl = wp_guess_url();
628 }
629
630 $scripts->base_url = $guessurl;
631 $scripts->content_url = defined( 'WP_CONTENT_URL' ) ? WP_CONTENT_URL : '';
632 $scripts->default_version = get_bloginfo( 'version' );
633 $scripts->default_dirs = array( '/wp-admin/js/', '/wp-includes/js/' );
634
635 $scripts->add( 'utils', "/wp-includes/js/utils$suffix.js" );
636 did_action( 'init' ) && $scripts->localize(
637 'utils',
638 'userSettings',
639 array(
640 'url' => (string) SITECOOKIEPATH,
641 'uid' => (string) get_current_user_id(),
642 'time' => (string) time(),
643 'secure' => (string) ( 'https' === parse_url( site_url(), PHP_URL_SCHEME ) ),
644 )
645 );
646
647 $scripts->add( 'common', "/wp-admin/js/common$suffix.js", array( 'jquery', 'hoverIntent', 'utils' ), false, 1 );
648 $scripts->set_translations( 'common' );
649
650 $scripts->add( 'wp-sanitize', "/wp-includes/js/wp-sanitize$suffix.js", array(), false, 1 );
651
652 $scripts->add( 'sack', "/wp-includes/js/tw-sack$suffix.js", array(), '1.6.1', 1 );
653
654 $scripts->add( 'quicktags', "/wp-includes/js/quicktags$suffix.js", array(), false, 1 );
655 did_action( 'init' ) && $scripts->localize(
656 'quicktags',
657 'quicktagsL10n',
658 array(
659 'closeAllOpenTags' => __( 'Close all open tags' ),
660 'closeTags' => __( 'close tags' ),
661 'enterURL' => __( 'Enter the URL' ),
662 'enterImageURL' => __( 'Enter the URL of the image' ),
663 'enterImageDescription' => __( 'Enter a description of the image' ),
664 'textdirection' => __( 'text direction' ),
665 'toggleTextdirection' => __( 'Toggle Editor Text Direction' ),
666 'dfw' => __( 'Distraction-free writing mode' ),
667 'strong' => __( 'Bold' ),
668 'strongClose' => __( 'Close bold tag' ),
669 'em' => __( 'Italic' ),
670 'emClose' => __( 'Close italic tag' ),
671 'link' => __( 'Insert link' ),
672 'blockquote' => __( 'Blockquote' ),
673 'blockquoteClose' => __( 'Close blockquote tag' ),
674 'del' => __( 'Deleted text (strikethrough)' ),
675 'delClose' => __( 'Close deleted text tag' ),
676 'ins' => __( 'Inserted text' ),
677 'insClose' => __( 'Close inserted text tag' ),
678 'image' => __( 'Insert image' ),
679 'ul' => __( 'Bulleted list' ),
680 'ulClose' => __( 'Close bulleted list tag' ),
681 'ol' => __( 'Numbered list' ),
682 'olClose' => __( 'Close numbered list tag' ),
683 'li' => __( 'List item' ),
684 'liClose' => __( 'Close list item tag' ),
685 'code' => __( 'Code' ),
686 'codeClose' => __( 'Close code tag' ),
687 'more' => __( 'Insert Read More tag' ),
688 )
689 );
690
691 $scripts->add( 'colorpicker', "/wp-includes/js/colorpicker$suffix.js", array( 'prototype' ), '3517m' );
692
693 $scripts->add( 'editor', "/wp-admin/js/editor$suffix.js", array( 'utils', 'jquery' ), false, 1 );
694
695 $scripts->add( 'clipboard', "/wp-includes/js/clipboard$suffix.js", array(), false, 1 );
696
697 $scripts->add( 'wp-ajax-response', "/wp-includes/js/wp-ajax-response$suffix.js", array( 'jquery' ), false, 1 );
698 did_action( 'init' ) && $scripts->localize(
699 'wp-ajax-response',
700 'wpAjax',
701 array(
702 'noPerm' => __( 'Sorry, you are not allowed to do that.' ),
703 'broken' => __( 'Something went wrong.' ),
704 )
705 );
706
707 $scripts->add( 'wp-api-request', "/wp-includes/js/api-request$suffix.js", array( 'jquery' ), false, 1 );
708 // `wpApiSettings` is also used by `wp-api`, which depends on this script.
709 did_action( 'init' ) && $scripts->localize(
710 'wp-api-request',
711 'wpApiSettings',
712 array(
713 'root' => esc_url_raw( get_rest_url() ),
714 'nonce' => ( wp_installing() && ! is_multisite() ) ? '' : wp_create_nonce( 'wp_rest' ),
715 'versionString' => 'wp/v2/',
716 )
717 );
718
719 $scripts->add( 'wp-pointer', "/wp-includes/js/wp-pointer$suffix.js", array( 'jquery-ui-core' ), false, 1 );
720 $scripts->set_translations( 'wp-pointer' );
721
722 $scripts->add( 'autosave', "/wp-includes/js/autosave$suffix.js", array( 'heartbeat' ), false, 1 );
723
724 $scripts->add( 'heartbeat', "/wp-includes/js/heartbeat$suffix.js", array( 'jquery', 'wp-hooks' ), false, 1 );
725 did_action( 'init' ) && $scripts->localize(
726 'heartbeat',
727 'heartbeatSettings',
728 /**
729 * Filters the Heartbeat settings.
730 *
731 * @since 3.6.0
732 *
733 * @param array $settings Heartbeat settings array.
734 */
735 apply_filters( 'heartbeat_settings', array() )
736 );
737
738 $scripts->add( 'wp-auth-check', "/wp-includes/js/wp-auth-check$suffix.js", array( 'heartbeat' ), false, 1 );
739 $scripts->set_translations( 'wp-auth-check' );
740
741 $scripts->add( 'wp-lists', "/wp-includes/js/wp-lists$suffix.js", array( 'wp-ajax-response', 'jquery-color' ), false, 1 );
742
743 // WordPress no longer uses or bundles Prototype or script.aculo.us. These are now pulled from an external source.
744 $scripts->add( 'prototype', 'https://ajax.googleapis.com/ajax/libs/prototype/1.7.1.0/prototype.js', array(), '1.7.1' );
745 $scripts->add( 'scriptaculous-root', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/scriptaculous.js', array( 'prototype' ), '1.9.0' );
746 $scripts->add( 'scriptaculous-builder', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/builder.js', array( 'scriptaculous-root' ), '1.9.0' );
747 $scripts->add( 'scriptaculous-dragdrop', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/dragdrop.js', array( 'scriptaculous-builder', 'scriptaculous-effects' ), '1.9.0' );
748 $scripts->add( 'scriptaculous-effects', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/effects.js', array( 'scriptaculous-root' ), '1.9.0' );
749 $scripts->add( 'scriptaculous-slider', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/slider.js', array( 'scriptaculous-effects' ), '1.9.0' );
750 $scripts->add( 'scriptaculous-sound', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/sound.js', array( 'scriptaculous-root' ), '1.9.0' );
751 $scripts->add( 'scriptaculous-controls', 'https://ajax.googleapis.com/ajax/libs/scriptaculous/1.9.0/controls.js', array( 'scriptaculous-root' ), '1.9.0' );
752 $scripts->add( 'scriptaculous', false, array( 'scriptaculous-dragdrop', 'scriptaculous-slider', 'scriptaculous-controls' ) );
753
754 // Not used in core, replaced by Jcrop.js.
755 $scripts->add( 'cropper', '/wp-includes/js/crop/cropper.js', array( 'scriptaculous-dragdrop' ) );
756
757 // jQuery.
758 // The unminified jquery.js and jquery-migrate.js are included to facilitate debugging.
759 $scripts->add( 'jquery', false, array( 'jquery-core', 'jquery-migrate' ), '3.6.0' );
760 $scripts->add( 'jquery-core', "/wp-includes/js/jquery/jquery$suffix.js", array(), '3.6.0' );
761 $scripts->add( 'jquery-migrate', "/wp-includes/js/jquery/jquery-migrate$suffix.js", array(), '3.3.2' );
762
763 // Full jQuery UI.
764 // The build process in 1.12.1 has changed significantly.
765 // In order to keep backwards compatibility, and to keep the optimized loading,
766 // the source files were flattened and included with some modifications for AMD loading.
767 // A notable change is that 'jquery-ui-core' now contains 'jquery-ui-position' and 'jquery-ui-widget'.
768 $scripts->add( 'jquery-ui-core', "/wp-includes/js/jquery/ui/core$suffix.js", array( 'jquery' ), '1.13.1', 1 );
769 $scripts->add( 'jquery-effects-core', "/wp-includes/js/jquery/ui/effect$suffix.js", array( 'jquery' ), '1.13.1', 1 );
770
771 $scripts->add( 'jquery-effects-blind', "/wp-includes/js/jquery/ui/effect-blind$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
772 $scripts->add( 'jquery-effects-bounce', "/wp-includes/js/jquery/ui/effect-bounce$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
773 $scripts->add( 'jquery-effects-clip', "/wp-includes/js/jquery/ui/effect-clip$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
774 $scripts->add( 'jquery-effects-drop', "/wp-includes/js/jquery/ui/effect-drop$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
775 $scripts->add( 'jquery-effects-explode', "/wp-includes/js/jquery/ui/effect-explode$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
776 $scripts->add( 'jquery-effects-fade', "/wp-includes/js/jquery/ui/effect-fade$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
777 $scripts->add( 'jquery-effects-fold', "/wp-includes/js/jquery/ui/effect-fold$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
778 $scripts->add( 'jquery-effects-highlight', "/wp-includes/js/jquery/ui/effect-highlight$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
779 $scripts->add( 'jquery-effects-puff', "/wp-includes/js/jquery/ui/effect-puff$suffix.js", array( 'jquery-effects-core', 'jquery-effects-scale' ), '1.13.1', 1 );
780 $scripts->add( 'jquery-effects-pulsate', "/wp-includes/js/jquery/ui/effect-pulsate$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
781 $scripts->add( 'jquery-effects-scale', "/wp-includes/js/jquery/ui/effect-scale$suffix.js", array( 'jquery-effects-core', 'jquery-effects-size' ), '1.13.1', 1 );
782 $scripts->add( 'jquery-effects-shake', "/wp-includes/js/jquery/ui/effect-shake$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
783 $scripts->add( 'jquery-effects-size', "/wp-includes/js/jquery/ui/effect-size$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
784 $scripts->add( 'jquery-effects-slide', "/wp-includes/js/jquery/ui/effect-slide$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
785 $scripts->add( 'jquery-effects-transfer', "/wp-includes/js/jquery/ui/effect-transfer$suffix.js", array( 'jquery-effects-core' ), '1.13.1', 1 );
786
787 // Widgets
788 $scripts->add( 'jquery-ui-accordion', "/wp-includes/js/jquery/ui/accordion$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
789 $scripts->add( 'jquery-ui-autocomplete', "/wp-includes/js/jquery/ui/autocomplete$suffix.js", array( 'jquery-ui-menu', 'wp-a11y' ), '1.13.1', 1 );
790 $scripts->add( 'jquery-ui-button', "/wp-includes/js/jquery/ui/button$suffix.js", array( 'jquery-ui-core', 'jquery-ui-controlgroup', 'jquery-ui-checkboxradio' ), '1.13.1', 1 );
791 $scripts->add( 'jquery-ui-datepicker', "/wp-includes/js/jquery/ui/datepicker$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
792 $scripts->add( 'jquery-ui-dialog', "/wp-includes/js/jquery/ui/dialog$suffix.js", array( 'jquery-ui-resizable', 'jquery-ui-draggable', 'jquery-ui-button' ), '1.13.1', 1 );
793 $scripts->add( 'jquery-ui-menu', "/wp-includes/js/jquery/ui/menu$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
794 $scripts->add( 'jquery-ui-mouse', "/wp-includes/js/jquery/ui/mouse$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
795 $scripts->add( 'jquery-ui-progressbar', "/wp-includes/js/jquery/ui/progressbar$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
796 $scripts->add( 'jquery-ui-selectmenu', "/wp-includes/js/jquery/ui/selectmenu$suffix.js", array( 'jquery-ui-menu' ), '1.13.1', 1 );
797 $scripts->add( 'jquery-ui-slider', "/wp-includes/js/jquery/ui/slider$suffix.js", array( 'jquery-ui-mouse' ), '1.13.1', 1 );
798 $scripts->add( 'jquery-ui-spinner', "/wp-includes/js/jquery/ui/spinner$suffix.js", array( 'jquery-ui-button' ), '1.13.1', 1 );
799 $scripts->add( 'jquery-ui-tabs', "/wp-includes/js/jquery/ui/tabs$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
800 $scripts->add( 'jquery-ui-tooltip', "/wp-includes/js/jquery/ui/tooltip$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
801
802 // New in 1.12.1
803 $scripts->add( 'jquery-ui-checkboxradio', "/wp-includes/js/jquery/ui/checkboxradio$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
804 $scripts->add( 'jquery-ui-controlgroup', "/wp-includes/js/jquery/ui/controlgroup$suffix.js", array( 'jquery-ui-core' ), '1.13.1', 1 );
805
806 // Interactions
807 $scripts->add( 'jquery-ui-draggable', "/wp-includes/js/jquery/ui/draggable$suffix.js", array( 'jquery-ui-mouse' ), '1.13.1', 1 );
808 $scripts->add( 'jquery-ui-droppable', "/wp-includes/js/jquery/ui/droppable$suffix.js", array( 'jquery-ui-draggable' ), '1.13.1', 1 );
809 $scripts->add( 'jquery-ui-resizable', "/wp-includes/js/jquery/ui/resizable$suffix.js", array( 'jquery-ui-mouse' ), '1.13.1', 1 );
810 $scripts->add( 'jquery-ui-selectable', "/wp-includes/js/jquery/ui/selectable$suffix.js", array( 'jquery-ui-mouse' ), '1.13.1', 1 );
811 $scripts->add( 'jquery-ui-sortable', "/wp-includes/js/jquery/ui/sortable$suffix.js", array( 'jquery-ui-mouse' ), '1.13.1', 1 );
812
813 // As of 1.12.1 `jquery-ui-position` and `jquery-ui-widget` are part of `jquery-ui-core`.
814 // Listed here for back-compat.
815 $scripts->add( 'jquery-ui-position', false, array( 'jquery-ui-core' ), '1.13.1', 1 );
816 $scripts->add( 'jquery-ui-widget', false, array( 'jquery-ui-core' ), '1.13.1', 1 );
817
818 // Strings for 'jquery-ui-autocomplete' live region messages.
819 did_action( 'init' ) && $scripts->localize(
820 'jquery-ui-autocomplete',
821 'uiAutocompleteL10n',
822 array(
823 'noResults' => __( 'No results found.' ),
824 /* translators: Number of results found when using jQuery UI Autocomplete. */
825 'oneResult' => __( '1 result found. Use up and down arrow keys to navigate.' ),
826 /* translators: %d: Number of results found when using jQuery UI Autocomplete. */
827 'manyResults' => __( '%d results found. Use up and down arrow keys to navigate.' ),
828 'itemSelected' => __( 'Item selected.' ),
829 )
830 );
831
832 // Deprecated, not used in core, most functionality is included in jQuery 1.3.
833 $scripts->add( 'jquery-form', "/wp-includes/js/jquery/jquery.form$suffix.js", array( 'jquery' ), '4.3.0', 1 );
834
835 // jQuery plugins.
836 $scripts->add( 'jquery-color', '/wp-includes/js/jquery/jquery.color.min.js', array( 'jquery' ), '2.1.2', 1 );
837 $scripts->add( 'schedule', '/wp-includes/js/jquery/jquery.schedule.js', array( 'jquery' ), '20m', 1 );
838 $scripts->add( 'jquery-query', '/wp-includes/js/jquery/jquery.query.js', array( 'jquery' ), '2.2.3', 1 );
839 $scripts->add( 'jquery-serialize-object', '/wp-includes/js/jquery/jquery.serialize-object.js', array( 'jquery' ), '0.2-wp', 1 );
840 $scripts->add( 'jquery-hotkeys', "/wp-includes/js/jquery/jquery.hotkeys$suffix.js", array( 'jquery' ), '0.0.2m', 1 );
841 $scripts->add( 'jquery-table-hotkeys', "/wp-includes/js/jquery/jquery.table-hotkeys$suffix.js", array( 'jquery', 'jquery-hotkeys' ), false, 1 );
842 $scripts->add( 'jquery-touch-punch', '/wp-includes/js/jquery/jquery.ui.touch-punch.js', array( 'jquery-ui-core', 'jquery-ui-mouse' ), '0.2.2', 1 );
843
844 // Not used any more, registered for backward compatibility.
845 $scripts->add( 'suggest', "/wp-includes/js/jquery/suggest$suffix.js", array( 'jquery' ), '1.1-20110113', 1 );
846
847 // Masonry v2 depended on jQuery. v3 does not. The older jquery-masonry handle is a shiv.
848 // It sets jQuery as a dependency, as the theme may have been implicitly loading it this way.
849 $scripts->add( 'imagesloaded', '/wp-includes/js/imagesloaded.min.js', array(), '4.1.4', 1 );
850 $scripts->add( 'masonry', '/wp-includes/js/masonry.min.js', array( 'imagesloaded' ), '4.2.2', 1 );
851 $scripts->add( 'jquery-masonry', '/wp-includes/js/jquery/jquery.masonry.min.js', array( 'jquery', 'masonry' ), '3.1.2b', 1 );
852
853 $scripts->add( 'thickbox', '/wp-includes/js/thickbox/thickbox.js', array( 'jquery' ), '3.1-20121105', 1 );
854 did_action( 'init' ) && $scripts->localize(
855 'thickbox',
856 'thickboxL10n',
857 array(
858 'next' => __( 'Next &gt;' ),
859 'prev' => __( '&lt; Prev' ),
860 'image' => __( 'Image' ),
861 'of' => __( 'of' ),
862 'close' => __( 'Close' ),
863 'noiframes' => __( 'This feature requires inline frames. You have iframes disabled or your browser does not support them.' ),
864 'loadingAnimation' => includes_url( 'js/thickbox/loadingAnimation.gif' ),
865 )
866 );
867
868 $scripts->add( 'jcrop', '/wp-includes/js/jcrop/jquery.Jcrop.min.js', array( 'jquery' ), '0.9.12' );
869
870 $scripts->add( 'swfobject', '/wp-includes/js/swfobject.js', array(), '2.2-20120417' );
871
872 // Error messages for Plupload.
873 $uploader_l10n = array(
874 'queue_limit_exceeded' => __( 'You have attempted to queue too many files.' ),
875 /* translators: %s: File name. */
876 'file_exceeds_size_limit' => __( '%s exceeds the maximum upload size for this site.' ),
877 'zero_byte_file' => __( 'This file is empty. Please try another.' ),
878 'invalid_filetype' => __( 'Sorry, you are not allowed to upload this file type.' ),
879 'not_an_image' => __( 'This file is not an image. Please try another.' ),
880 'image_memory_exceeded' => __( 'Memory exceeded. Please try another smaller file.' ),
881 'image_dimensions_exceeded' => __( 'This is larger than the maximum size. Please try another.' ),
882 'default_error' => __( 'An error occurred in the upload. Please try again later.' ),
883 'missing_upload_url' => __( 'There was a configuration error. Please contact the server administrator.' ),
884 'upload_limit_exceeded' => __( 'You may only upload 1 file.' ),
885 'http_error' => __( 'Unexpected response from the server. The file may have been uploaded successfully. Check in the Media Library or reload the page.' ),
886 'http_error_image' => __( 'The server cannot process the image. This can happen if the server is busy or does not have enough resources to complete the task. Uploading a smaller image may help. Suggested maximum size is 2560 pixels.' ),
887 'upload_failed' => __( 'Upload failed.' ),
888 /* translators: 1: Opening link tag, 2: Closing link tag. */
889 'big_upload_failed' => __( 'Please try uploading this file with the %1$sbrowser uploader%2$s.' ),
890 /* translators: %s: File name. */
891 'big_upload_queued' => __( '%s exceeds the maximum upload size for the multi-file uploader when used in your browser.' ),
892 'io_error' => __( 'IO error.' ),
893 'security_error' => __( 'Security error.' ),
894 'file_cancelled' => __( 'File canceled.' ),
895 'upload_stopped' => __( 'Upload stopped.' ),
896 'dismiss' => __( 'Dismiss' ),
897 'crunching' => __( 'Crunching&hellip;' ),
898 'deleted' => __( 'moved to the Trash.' ),
899 /* translators: %s: File name. */
900 'error_uploading' => __( '&#8220;%s&#8221; has failed to upload.' ),
901 'unsupported_image' => __( 'This image cannot be displayed in a web browser. For best results convert it to JPEG before uploading.' ),
902 'noneditable_image' => __( 'This image cannot be processed by the web server. Convert it to JPEG or PNG before uploading.' ),
903 'file_url_copied' => __( 'The file URL has been copied to your clipboard' ),
904 );
905
906 $scripts->add( 'moxiejs', "/wp-includes/js/plupload/moxie$suffix.js", array(), '1.3.5' );
907 $scripts->add( 'plupload', "/wp-includes/js/plupload/plupload$suffix.js", array( 'moxiejs' ), '2.1.9' );
908 // Back compat handles:
909 foreach ( array( 'all', 'html5', 'flash', 'silverlight', 'html4' ) as $handle ) {
910 $scripts->add( "plupload-$handle", false, array( 'plupload' ), '2.1.1' );
911 }
912
913 $scripts->add( 'plupload-handlers', "/wp-includes/js/plupload/handlers$suffix.js", array( 'clipboard', 'jquery', 'plupload', 'underscore', 'wp-a11y', 'wp-i18n' ) );
914 did_action( 'init' ) && $scripts->localize( 'plupload-handlers', 'pluploadL10n', $uploader_l10n );
915
916 $scripts->add( 'wp-plupload', "/wp-includes/js/plupload/wp-plupload$suffix.js", array( 'plupload', 'jquery', 'json2', 'media-models' ), false, 1 );
917 did_action( 'init' ) && $scripts->localize( 'wp-plupload', 'pluploadL10n', $uploader_l10n );
918
919 // Keep 'swfupload' for back-compat.
920 $scripts->add( 'swfupload', '/wp-includes/js/swfupload/swfupload.js', array(), '2201-20110113' );
921 $scripts->add( 'swfupload-all', false, array( 'swfupload' ), '2201' );
922 $scripts->add( 'swfupload-handlers', "/wp-includes/js/swfupload/handlers$suffix.js", array( 'swfupload-all', 'jquery' ), '2201-20110524' );
923 did_action( 'init' ) && $scripts->localize( 'swfupload-handlers', 'swfuploadL10n', $uploader_l10n );
924
925 $scripts->add( 'comment-reply', "/wp-includes/js/comment-reply$suffix.js", array(), false, 1 );
926
927 $scripts->add( 'json2', "/wp-includes/js/json2$suffix.js", array(), '2015-05-03' );
928 did_action( 'init' ) && $scripts->add_data( 'json2', 'conditional', 'lt IE 8' );
929
930 $scripts->add( 'underscore', "/wp-includes/js/underscore$dev_suffix.js", array(), '1.13.1', 1 );
931 $scripts->add( 'backbone', "/wp-includes/js/backbone$dev_suffix.js", array( 'underscore', 'jquery' ), '1.4.0', 1 );
932
933 $scripts->add( 'wp-util', "/wp-includes/js/wp-util$suffix.js", array( 'underscore', 'jquery' ), false, 1 );
934 did_action( 'init' ) && $scripts->localize(
935 'wp-util',
936 '_wpUtilSettings',
937 array(
938 'ajax' => array(
939 'url' => admin_url( 'admin-ajax.php', 'relative' ),
940 ),
941 )
942 );
943
944 $scripts->add( 'wp-backbone', "/wp-includes/js/wp-backbone$suffix.js", array( 'backbone', 'wp-util' ), false, 1 );
945
946 $scripts->add( 'revisions', "/wp-admin/js/revisions$suffix.js", array( 'wp-backbone', 'jquery-ui-slider', 'hoverIntent' ), false, 1 );
947
948 $scripts->add( 'imgareaselect', "/wp-includes/js/imgareaselect/jquery.imgareaselect$suffix.js", array( 'jquery' ), false, 1 );
949
950 $scripts->add( 'mediaelement', false, array( 'jquery', 'mediaelement-core', 'mediaelement-migrate' ), '4.2.16', 1 );
951 $scripts->add( 'mediaelement-core', "/wp-includes/js/mediaelement/mediaelement-and-player$suffix.js", array(), '4.2.16', 1 );
952 $scripts->add( 'mediaelement-migrate', "/wp-includes/js/mediaelement/mediaelement-migrate$suffix.js", array(), false, 1 );
953
954 did_action( 'init' ) && $scripts->add_inline_script(
955 'mediaelement-core',
956 sprintf(
957 'var mejsL10n = %s;',
958 wp_json_encode(
959 array(
960 'language' => strtolower( strtok( determine_locale(), '_-' ) ),
961 'strings' => array(
962 'mejs.download-file' => __( 'Download File' ),
963 'mejs.install-flash' => __( 'You are using a browser that does not have Flash player enabled or installed. Please turn on your Flash player plugin or download the latest version from https://get.adobe.com/flashplayer/' ),
964 'mejs.fullscreen' => __( 'Fullscreen' ),
965 'mejs.play' => __( 'Play' ),
966 'mejs.pause' => __( 'Pause' ),
967 'mejs.time-slider' => __( 'Time Slider' ),
968 'mejs.time-help-text' => __( 'Use Left/Right Arrow keys to advance one second, Up/Down arrows to advance ten seconds.' ),
969 'mejs.live-broadcast' => __( 'Live Broadcast' ),
970 'mejs.volume-help-text' => __( 'Use Up/Down Arrow keys to increase or decrease volume.' ),
971 'mejs.unmute' => __( 'Unmute' ),
972 'mejs.mute' => __( 'Mute' ),
973 'mejs.volume-slider' => __( 'Volume Slider' ),
974 'mejs.video-player' => __( 'Video Player' ),
975 'mejs.audio-player' => __( 'Audio Player' ),
976 'mejs.captions-subtitles' => __( 'Captions/Subtitles' ),
977 'mejs.captions-chapters' => __( 'Chapters' ),
978 'mejs.none' => __( 'None' ),
979 'mejs.afrikaans' => __( 'Afrikaans' ),
980 'mejs.albanian' => __( 'Albanian' ),
981 'mejs.arabic' => __( 'Arabic' ),
982 'mejs.belarusian' => __( 'Belarusian' ),
983 'mejs.bulgarian' => __( 'Bulgarian' ),
984 'mejs.catalan' => __( 'Catalan' ),
985 'mejs.chinese' => __( 'Chinese' ),
986 'mejs.chinese-simplified' => __( 'Chinese (Simplified)' ),
987 'mejs.chinese-traditional' => __( 'Chinese (Traditional)' ),
988 'mejs.croatian' => __( 'Croatian' ),
989 'mejs.czech' => __( 'Czech' ),
990 'mejs.danish' => __( 'Danish' ),
991 'mejs.dutch' => __( 'Dutch' ),
992 'mejs.english' => __( 'English' ),
993 'mejs.estonian' => __( 'Estonian' ),
994 'mejs.filipino' => __( 'Filipino' ),
995 'mejs.finnish' => __( 'Finnish' ),
996 'mejs.french' => __( 'French' ),
997 'mejs.galician' => __( 'Galician' ),
998 'mejs.german' => __( 'German' ),
999 'mejs.greek' => __( 'Greek' ),
1000 'mejs.haitian-creole' => __( 'Haitian Creole' ),
1001 'mejs.hebrew' => __( 'Hebrew' ),
1002 'mejs.hindi' => __( 'Hindi' ),
1003 'mejs.hungarian' => __( 'Hungarian' ),
1004 'mejs.icelandic' => __( 'Icelandic' ),
1005 'mejs.indonesian' => __( 'Indonesian' ),
1006 'mejs.irish' => __( 'Irish' ),
1007 'mejs.italian' => __( 'Italian' ),
1008 'mejs.japanese' => __( 'Japanese' ),
1009 'mejs.korean' => __( 'Korean' ),
1010 'mejs.latvian' => __( 'Latvian' ),
1011 'mejs.lithuanian' => __( 'Lithuanian' ),
1012 'mejs.macedonian' => __( 'Macedonian' ),
1013 'mejs.malay' => __( 'Malay' ),
1014 'mejs.maltese' => __( 'Maltese' ),
1015 'mejs.norwegian' => __( 'Norwegian' ),
1016 'mejs.persian' => __( 'Persian' ),
1017 'mejs.polish' => __( 'Polish' ),
1018 'mejs.portuguese' => __( 'Portuguese' ),
1019 'mejs.romanian' => __( 'Romanian' ),
1020 'mejs.russian' => __( 'Russian' ),
1021 'mejs.serbian' => __( 'Serbian' ),
1022 'mejs.slovak' => __( 'Slovak' ),
1023 'mejs.slovenian' => __( 'Slovenian' ),
1024 'mejs.spanish' => __( 'Spanish' ),
1025 'mejs.swahili' => __( 'Swahili' ),
1026 'mejs.swedish' => __( 'Swedish' ),
1027 'mejs.tagalog' => __( 'Tagalog' ),
1028 'mejs.thai' => __( 'Thai' ),
1029 'mejs.turkish' => __( 'Turkish' ),
1030 'mejs.ukrainian' => __( 'Ukrainian' ),
1031 'mejs.vietnamese' => __( 'Vietnamese' ),
1032 'mejs.welsh' => __( 'Welsh' ),
1033 'mejs.yiddish' => __( 'Yiddish' ),
1034 ),
1035 )
1036 )
1037 ),
1038 'before'
1039 );
1040
1041 $scripts->add( 'mediaelement-vimeo', '/wp-includes/js/mediaelement/renderers/vimeo.min.js', array( 'mediaelement' ), '4.2.16', 1 );
1042 $scripts->add( 'wp-mediaelement', "/wp-includes/js/mediaelement/wp-mediaelement$suffix.js", array( 'mediaelement' ), false, 1 );
1043 $mejs_settings = array(
1044 'pluginPath' => includes_url( 'js/mediaelement/', 'relative' ),
1045 'classPrefix' => 'mejs-',
1046 'stretching' => 'responsive',
1047 );
1048 did_action( 'init' ) && $scripts->localize(
1049 'mediaelement',
1050 '_wpmejsSettings',
1051 /**
1052 * Filters the MediaElement configuration settings.
1053 *
1054 * @since 4.4.0
1055 *
1056 * @param array $mejs_settings MediaElement settings array.
1057 */
1058 apply_filters( 'mejs_settings', $mejs_settings )
1059 );
1060
1061 $scripts->add( 'wp-codemirror', '/wp-includes/js/codemirror/codemirror.min.js', array(), '5.29.1-alpha-ee20357' );
1062 $scripts->add( 'csslint', '/wp-includes/js/codemirror/csslint.js', array(), '1.0.5' );
1063 $scripts->add( 'esprima', '/wp-includes/js/codemirror/esprima.js', array(), '4.0.0' );
1064 $scripts->add( 'jshint', '/wp-includes/js/codemirror/fakejshint.js', array( 'esprima' ), '2.9.5' );
1065 $scripts->add( 'jsonlint', '/wp-includes/js/codemirror/jsonlint.js', array(), '1.6.2' );
1066 $scripts->add( 'htmlhint', '/wp-includes/js/codemirror/htmlhint.js', array(), '0.9.14-xwp' );
1067 $scripts->add( 'htmlhint-kses', '/wp-includes/js/codemirror/htmlhint-kses.js', array( 'htmlhint' ) );
1068 $scripts->add( 'code-editor', "/wp-admin/js/code-editor$suffix.js", array( 'jquery', 'wp-codemirror', 'underscore' ) );
1069 $scripts->add( 'wp-theme-plugin-editor', "/wp-admin/js/theme-plugin-editor$suffix.js", array( 'common', 'wp-util', 'wp-sanitize', 'jquery', 'jquery-ui-core', 'wp-a11y', 'underscore' ) );
1070 $scripts->set_translations( 'wp-theme-plugin-editor' );
1071
1072 $scripts->add( 'wp-playlist', "/wp-includes/js/mediaelement/wp-playlist$suffix.js", array( 'wp-util', 'backbone', 'mediaelement' ), false, 1 );
1073
1074 $scripts->add( 'zxcvbn-async', "/wp-includes/js/zxcvbn-async$suffix.js", array(), '1.0' );
1075 did_action( 'init' ) && $scripts->localize(
1076 'zxcvbn-async',
1077 '_zxcvbnSettings',
1078 array(
1079 'src' => empty( $guessed_url ) ? includes_url( '/js/zxcvbn.min.js' ) : $scripts->base_url . '/wp-includes/js/zxcvbn.min.js',
1080 )
1081 );
1082
1083 $scripts->add( 'password-strength-meter', "/wp-admin/js/password-strength-meter$suffix.js", array( 'jquery', 'zxcvbn-async' ), false, 1 );
1084 did_action( 'init' ) && $scripts->localize(
1085 'password-strength-meter',
1086 'pwsL10n',
1087 array(
1088 'unknown' => _x( 'Password strength unknown', 'password strength' ),
1089 'short' => _x( 'Very weak', 'password strength' ),
1090 'bad' => _x( 'Weak', 'password strength' ),
1091 'good' => _x( 'Medium', 'password strength' ),
1092 'strong' => _x( 'Strong', 'password strength' ),
1093 'mismatch' => _x( 'Mismatch', 'password mismatch' ),
1094 )
1095 );
1096 $scripts->set_translations( 'password-strength-meter' );
1097
1098 $scripts->add( 'application-passwords', "/wp-admin/js/application-passwords$suffix.js", array( 'jquery', 'wp-util', 'wp-api-request', 'wp-date', 'wp-i18n', 'wp-hooks' ), false, 1 );
1099 $scripts->set_translations( 'application-passwords' );
1100
1101 $scripts->add( 'auth-app', "/wp-admin/js/auth-app$suffix.js", array( 'jquery', 'wp-api-request', 'wp-i18n', 'wp-hooks' ), false, 1 );
1102 $scripts->set_translations( 'auth-app' );
1103
1104 $scripts->add( 'user-profile', "/wp-admin/js/user-profile$suffix.js", array( 'jquery', 'password-strength-meter', 'wp-util' ), false, 1 );
1105 $scripts->set_translations( 'user-profile' );
1106 $user_id = isset( $_GET['user_id'] ) ? (int) $_GET['user_id'] : 0;
1107 did_action( 'init' ) && $scripts->localize(
1108 'user-profile',
1109 'userProfileL10n',
1110 array(
1111 'user_id' => $user_id,
1112 'nonce' => ( wp_installing() && ! is_multisite() ) ? '' : wp_create_nonce( 'reset-password-for-' . $user_id ),
1113 )
1114 );
1115
1116 $scripts->add( 'language-chooser', "/wp-admin/js/language-chooser$suffix.js", array( 'jquery' ), false, 1 );
1117
1118 $scripts->add( 'user-suggest', "/wp-admin/js/user-suggest$suffix.js", array( 'jquery-ui-autocomplete' ), false, 1 );
1119
1120 $scripts->add( 'admin-bar', "/wp-includes/js/admin-bar$suffix.js", array( 'hoverintent-js' ), false, 1 );
1121
1122 $scripts->add( 'wplink', "/wp-includes/js/wplink$suffix.js", array( 'jquery', 'wp-a11y' ), false, 1 );
1123 did_action( 'init' ) && $scripts->localize(
1124 'wplink',
1125 'wpLinkL10n',
1126 array(
1127 'title' => __( 'Insert/edit link' ),
1128 'update' => __( 'Update' ),
1129 'save' => __( 'Add Link' ),
1130 'noTitle' => __( '(no title)' ),
1131 'noMatchesFound' => __( 'No results found.' ),
1132 'linkSelected' => __( 'Link selected.' ),
1133 'linkInserted' => __( 'Link inserted.' ),
1134 /* translators: Minimum input length in characters to start searching posts in the "Insert/edit link" modal. */
1135 'minInputLength' => (int) _x( '3', 'minimum input length for searching post links' ),
1136 )
1137 );
1138
1139 $scripts->add( 'wpdialogs', "/wp-includes/js/wpdialog$suffix.js", array( 'jquery-ui-dialog' ), false, 1 );
1140
1141 $scripts->add( 'word-count', "/wp-admin/js/word-count$suffix.js", array(), false, 1 );
1142
1143 $scripts->add( 'media-upload', "/wp-admin/js/media-upload$suffix.js", array( 'thickbox', 'shortcode' ), false, 1 );
1144
1145 $scripts->add( 'hoverIntent', "/wp-includes/js/hoverIntent$suffix.js", array( 'jquery' ), '1.10.2', 1 );
1146
1147 // JS-only version of hoverintent (no dependencies).
1148 $scripts->add( 'hoverintent-js', '/wp-includes/js/hoverintent-js.min.js', array(), '2.2.1', 1 );
1149
1150 $scripts->add( 'customize-base', "/wp-includes/js/customize-base$suffix.js", array( 'jquery', 'json2', 'underscore' ), false, 1 );
1151 $scripts->add( 'customize-loader', "/wp-includes/js/customize-loader$suffix.js", array( 'customize-base' ), false, 1 );
1152 $scripts->add( 'customize-preview', "/wp-includes/js/customize-preview$suffix.js", array( 'wp-a11y', 'customize-base' ), false, 1 );
1153 $scripts->add( 'customize-models', '/wp-includes/js/customize-models.js', array( 'underscore', 'backbone' ), false, 1 );
1154 $scripts->add( 'customize-views', '/wp-includes/js/customize-views.js', array( 'jquery', 'underscore', 'imgareaselect', 'customize-models', 'media-editor', 'media-views' ), false, 1 );
1155 $scripts->add( 'customize-controls', "/wp-admin/js/customize-controls$suffix.js", array( 'customize-base', 'wp-a11y', 'wp-util', 'jquery-ui-core' ), false, 1 );
1156 did_action( 'init' ) && $scripts->localize(
1157 'customize-controls',
1158 '_wpCustomizeControlsL10n',
1159 array(
1160 'activate' => __( 'Activate &amp; Publish' ),
1161 'save' => __( 'Save &amp; Publish' ), // @todo Remove as not required.
1162 'publish' => __( 'Publish' ),
1163 'published' => __( 'Published' ),
1164 'saveDraft' => __( 'Save Draft' ),
1165 'draftSaved' => __( 'Draft Saved' ),
1166 'updating' => __( 'Updating' ),
1167 'schedule' => _x( 'Schedule', 'customizer changeset action/button label' ),
1168 'scheduled' => _x( 'Scheduled', 'customizer changeset status' ),
1169 'invalid' => __( 'Invalid' ),
1170 'saveBeforeShare' => __( 'Please save your changes in order to share the preview.' ),
1171 'futureDateError' => __( 'You must supply a future date to schedule.' ),
1172 'saveAlert' => __( 'The changes you made will be lost if you navigate away from this page.' ),
1173 'saved' => __( 'Saved' ),
1174 'cancel' => __( 'Cancel' ),
1175 'close' => __( 'Close' ),
1176 'action' => __( 'Action' ),
1177 'discardChanges' => __( 'Discard changes' ),
1178 'cheatin' => __( 'Something went wrong.' ),
1179 'notAllowedHeading' => __( 'You need a higher level of permission.' ),
1180 'notAllowed' => __( 'Sorry, you are not allowed to customize this site.' ),
1181 'previewIframeTitle' => __( 'Site Preview' ),
1182 'loginIframeTitle' => __( 'Session expired' ),
1183 'collapseSidebar' => _x( 'Hide Controls', 'label for hide controls button without length constraints' ),
1184 'expandSidebar' => _x( 'Show Controls', 'label for hide controls button without length constraints' ),
1185 'untitledBlogName' => __( '(Untitled)' ),
1186 'unknownRequestFail' => __( 'Looks like something&#8217;s gone wrong. Wait a couple seconds, and then try again.' ),
1187 'themeDownloading' => __( 'Downloading your new theme&hellip;' ),
1188 'themePreviewWait' => __( 'Setting up your live preview. This may take a bit.' ),
1189 'revertingChanges' => __( 'Reverting unpublished changes&hellip;' ),
1190 'trashConfirm' => __( 'Are you sure you want to discard your unpublished changes?' ),
1191 /* translators: %s: Display name of the user who has taken over the changeset in customizer. */
1192 'takenOverMessage' => __( '%s has taken over and is currently customizing.' ),
1193 /* translators: %s: URL to the Customizer to load the autosaved version. */
1194 'autosaveNotice' => __( 'There is a more recent autosave of your changes than the one you are previewing. <a href="%s">Restore the autosave</a>' ),
1195 'videoHeaderNotice' => __( 'This theme doesn&#8217;t support video headers on this page. Navigate to the front page or another page that supports video headers.' ),
1196 // Used for overriding the file types allowed in Plupload.
1197 'allowedFiles' => __( 'Allowed Files' ),
1198 'customCssError' => array(
1199 /* translators: %d: Error count. */
1200 'singular' => _n( 'There is %d error which must be fixed before you can save.', 'There are %d errors which must be fixed before you can save.', 1 ),
1201 /* translators: %d: Error count. */
1202 'plural' => _n( 'There is %d error which must be fixed before you can save.', 'There are %d errors which must be fixed before you can save.', 2 ),
1203 // @todo This is lacking, as some languages have a dedicated dual form. For proper handling of plurals in JS, see #20491.
1204 ),
1205 'pageOnFrontError' => __( 'Homepage and posts page must be different.' ),
1206 'saveBlockedError' => array(
1207 /* translators: %s: Number of invalid settings. */
1208 'singular' => _n( 'Unable to save due to %s invalid setting.', 'Unable to save due to %s invalid settings.', 1 ),
1209 /* translators: %s: Number of invalid settings. */
1210 'plural' => _n( 'Unable to save due to %s invalid setting.', 'Unable to save due to %s invalid settings.', 2 ),
1211 // @todo This is lacking, as some languages have a dedicated dual form. For proper handling of plurals in JS, see #20491.
1212 ),
1213 'scheduleDescription' => __( 'Schedule your customization changes to publish ("go live") at a future date.' ),
1214 'themePreviewUnavailable' => __( 'Sorry, you can&#8217;t preview new themes when you have changes scheduled or saved as a draft. Please publish your changes, or wait until they publish to preview new themes.' ),
1215 'themeInstallUnavailable' => sprintf(
1216 /* translators: %s: URL to Add Themes admin screen. */
1217 __( 'You won&#8217;t be able to install new themes from here yet since your install requires SFTP credentials. For now, please <a href="%s">add themes in the admin</a>.' ),
1218 esc_url( admin_url( 'theme-install.php' ) )
1219 ),
1220 'publishSettings' => __( 'Publish Settings' ),
1221 'invalidDate' => __( 'Invalid date.' ),
1222 'invalidValue' => __( 'Invalid value.' ),
1223 'blockThemeNotification' => sprintf(
1224 /* translators: 1: Link to Site Editor documentation on HelpHub, 2: HTML button. */
1225 __( 'Hurray! Your theme supports Full Site Editing with blocks. <a href="%1$s">Tell me more</a>. %2$s' ),
1226 __( 'https://wordpress.org/support/article/site-editor/' ),
1227 sprintf(
1228 '<button type="button" data-action="%1$s" class="button switch-to-editor">%2$s</button>',
1229 esc_url( admin_url( 'site-editor.php' ) ),
1230 __( 'Use Site Editor' )
1231 )
1232 ),
1233 )
1234 );
1235 $scripts->add( 'customize-selective-refresh', "/wp-includes/js/customize-selective-refresh$suffix.js", array( 'jquery', 'wp-util', 'customize-preview' ), false, 1 );
1236
1237 $scripts->add( 'customize-widgets', "/wp-admin/js/customize-widgets$suffix.js", array( 'jquery', 'jquery-ui-sortable', 'jquery-ui-droppable', 'wp-backbone', 'customize-controls' ), false, 1 );
1238 $scripts->add( 'customize-preview-widgets', "/wp-includes/js/customize-preview-widgets$suffix.js", array( 'jquery', 'wp-util', 'customize-preview', 'customize-selective-refresh' ), false, 1 );
1239
1240 $scripts->add( 'customize-nav-menus', "/wp-admin/js/customize-nav-menus$suffix.js", array( 'jquery', 'wp-backbone', 'customize-controls', 'accordion', 'nav-menu', 'wp-sanitize' ), false, 1 );
1241 $scripts->add( 'customize-preview-nav-menus', "/wp-includes/js/customize-preview-nav-menus$suffix.js", array( 'jquery', 'wp-util', 'customize-preview', 'customize-selective-refresh' ), false, 1 );
1242
1243 $scripts->add( 'wp-custom-header', "/wp-includes/js/wp-custom-header$suffix.js", array( 'wp-a11y' ), false, 1 );
1244
1245 $scripts->add( 'accordion', "/wp-admin/js/accordion$suffix.js", array( 'jquery' ), false, 1 );
1246
1247 $scripts->add( 'shortcode', "/wp-includes/js/shortcode$suffix.js", array( 'underscore' ), false, 1 );
1248 $scripts->add( 'media-models', "/wp-includes/js/media-models$suffix.js", array( 'wp-backbone' ), false, 1 );
1249 did_action( 'init' ) && $scripts->localize(
1250 'media-models',
1251 '_wpMediaModelsL10n',
1252 array(
1253 'settings' => array(
1254 'ajaxurl' => admin_url( 'admin-ajax.php', 'relative' ),
1255 'post' => array( 'id' => 0 ),
1256 ),
1257 )
1258 );
1259
1260 $scripts->add( 'wp-embed', "/wp-includes/js/wp-embed$suffix.js", array(), false, 1 );
1261
1262 // To enqueue media-views or media-editor, call wp_enqueue_media().
1263 // Both rely on numerous settings, styles, and templates to operate correctly.
1264 $scripts->add( 'media-views', "/wp-includes/js/media-views$suffix.js", array( 'utils', 'media-models', 'wp-plupload', 'jquery-ui-sortable', 'wp-mediaelement', 'wp-api-request', 'wp-a11y', 'clipboard' ), false, 1 );
1265 $scripts->set_translations( 'media-views' );
1266
1267 $scripts->add( 'media-editor', "/wp-includes/js/media-editor$suffix.js", array( 'shortcode', 'media-views' ), false, 1 );
1268 $scripts->set_translations( 'media-editor' );
1269 $scripts->add( 'media-audiovideo', "/wp-includes/js/media-audiovideo$suffix.js", array( 'media-editor' ), false, 1 );
1270 $scripts->add( 'mce-view', "/wp-includes/js/mce-view$suffix.js", array( 'shortcode', 'jquery', 'media-views', 'media-audiovideo' ), false, 1 );
1271
1272 $scripts->add( 'wp-api', "/wp-includes/js/wp-api$suffix.js", array( 'jquery', 'backbone', 'underscore', 'wp-api-request' ), false, 1 );
1273
1274 if ( is_admin() ) {
1275 $scripts->add( 'admin-tags', "/wp-admin/js/tags$suffix.js", array( 'jquery', 'wp-ajax-response' ), false, 1 );
1276 $scripts->set_translations( 'admin-tags' );
1277
1278 $scripts->add( 'admin-comments', "/wp-admin/js/edit-comments$suffix.js", array( 'wp-lists', 'quicktags', 'jquery-query' ), false, 1 );
1279 $scripts->set_translations( 'admin-comments' );
1280 did_action( 'init' ) && $scripts->localize(
1281 'admin-comments',
1282 'adminCommentsSettings',
1283 array(
1284 'hotkeys_highlight_first' => isset( $_GET['hotkeys_highlight_first'] ),
1285 'hotkeys_highlight_last' => isset( $_GET['hotkeys_highlight_last'] ),
1286 )
1287 );
1288
1289 $scripts->add( 'xfn', "/wp-admin/js/xfn$suffix.js", array( 'jquery' ), false, 1 );
1290
1291 $scripts->add( 'postbox', "/wp-admin/js/postbox$suffix.js", array( 'jquery-ui-sortable', 'wp-a11y' ), false, 1 );
1292 $scripts->set_translations( 'postbox' );
1293
1294 $scripts->add( 'tags-box', "/wp-admin/js/tags-box$suffix.js", array( 'jquery', 'tags-suggest' ), false, 1 );
1295 $scripts->set_translations( 'tags-box' );
1296
1297 $scripts->add( 'tags-suggest', "/wp-admin/js/tags-suggest$suffix.js", array( 'jquery-ui-autocomplete', 'wp-a11y' ), false, 1 );
1298 $scripts->set_translations( 'tags-suggest' );
1299
1300 $scripts->add( 'post', "/wp-admin/js/post$suffix.js", array( 'suggest', 'wp-lists', 'postbox', 'tags-box', 'underscore', 'word-count', 'wp-a11y', 'wp-sanitize', 'clipboard' ), false, 1 );
1301 $scripts->set_translations( 'post' );
1302
1303 $scripts->add( 'editor-expand', "/wp-admin/js/editor-expand$suffix.js", array( 'jquery', 'underscore' ), false, 1 );
1304
1305 $scripts->add( 'link', "/wp-admin/js/link$suffix.js", array( 'wp-lists', 'postbox' ), false, 1 );
1306
1307 $scripts->add( 'comment', "/wp-admin/js/comment$suffix.js", array( 'jquery', 'postbox' ), false, 1 );
1308 $scripts->set_translations( 'comment' );
1309
1310 $scripts->add( 'admin-gallery', "/wp-admin/js/gallery$suffix.js", array( 'jquery-ui-sortable' ) );
1311
1312 $scripts->add( 'admin-widgets', "/wp-admin/js/widgets$suffix.js", array( 'jquery-ui-sortable', 'jquery-ui-draggable', 'jquery-ui-droppable', 'wp-a11y' ), false, 1 );
1313 $scripts->set_translations( 'admin-widgets' );
1314
1315 $scripts->add( 'media-widgets', "/wp-admin/js/widgets/media-widgets$suffix.js", array( 'jquery', 'media-models', 'media-views', 'wp-api-request' ) );
1316 $scripts->add_inline_script( 'media-widgets', 'wp.mediaWidgets.init();', 'after' );
1317
1318 $scripts->add( 'media-audio-widget', "/wp-admin/js/widgets/media-audio-widget$suffix.js", array( 'media-widgets', 'media-audiovideo' ) );
1319 $scripts->add( 'media-image-widget', "/wp-admin/js/widgets/media-image-widget$suffix.js", array( 'media-widgets' ) );
1320 $scripts->add( 'media-gallery-widget', "/wp-admin/js/widgets/media-gallery-widget$suffix.js", array( 'media-widgets' ) );
1321 $scripts->add( 'media-video-widget', "/wp-admin/js/widgets/media-video-widget$suffix.js", array( 'media-widgets', 'media-audiovideo', 'wp-api-request' ) );
1322 $scripts->add( 'text-widgets', "/wp-admin/js/widgets/text-widgets$suffix.js", array( 'jquery', 'backbone', 'editor', 'wp-util', 'wp-a11y' ) );
1323 $scripts->add( 'custom-html-widgets', "/wp-admin/js/widgets/custom-html-widgets$suffix.js", array( 'jquery', 'backbone', 'wp-util', 'jquery-ui-core', 'wp-a11y' ) );
1324
1325 $scripts->add( 'theme', "/wp-admin/js/theme$suffix.js", array( 'wp-backbone', 'wp-a11y', 'customize-base' ), false, 1 );
1326
1327 $scripts->add( 'inline-edit-post', "/wp-admin/js/inline-edit-post$suffix.js", array( 'jquery', 'tags-suggest', 'wp-a11y' ), false, 1 );
1328 $scripts->set_translations( 'inline-edit-post' );
1329
1330 $scripts->add( 'inline-edit-tax', "/wp-admin/js/inline-edit-tax$suffix.js", array( 'jquery', 'wp-a11y' ), false, 1 );
1331 $scripts->set_translations( 'inline-edit-tax' );
1332
1333 $scripts->add( 'plugin-install', "/wp-admin/js/plugin-install$suffix.js", array( 'jquery', 'jquery-ui-core', 'thickbox' ), false, 1 );
1334 $scripts->set_translations( 'plugin-install' );
1335
1336 $scripts->add( 'site-health', "/wp-admin/js/site-health$suffix.js", array( 'clipboard', 'jquery', 'wp-util', 'wp-a11y', 'wp-api-request', 'wp-url', 'wp-i18n', 'wp-hooks' ), false, 1 );
1337 $scripts->set_translations( 'site-health' );
1338
1339 $scripts->add( 'privacy-tools', "/wp-admin/js/privacy-tools$suffix.js", array( 'jquery', 'wp-a11y' ), false, 1 );
1340 $scripts->set_translations( 'privacy-tools' );
1341
1342 $scripts->add( 'updates', "/wp-admin/js/updates$suffix.js", array( 'common', 'jquery', 'wp-util', 'wp-a11y', 'wp-sanitize' ), false, 1 );
1343 $scripts->set_translations( 'updates' );
1344 did_action( 'init' ) && $scripts->localize(
1345 'updates',
1346 '_wpUpdatesSettings',
1347 array(
1348 'ajax_nonce' => wp_create_nonce( 'updates' ),
1349 )
1350 );
1351
1352 $scripts->add( 'farbtastic', '/wp-admin/js/farbtastic.js', array( 'jquery' ), '1.2' );
1353
1354 $scripts->add( 'iris', '/wp-admin/js/iris.min.js', array( 'jquery-ui-draggable', 'jquery-ui-slider', 'jquery-touch-punch' ), '1.1.1', 1 );
1355 $scripts->add( 'wp-color-picker', "/wp-admin/js/color-picker$suffix.js", array( 'iris' ), false, 1 );
1356 $scripts->set_translations( 'wp-color-picker' );
1357
1358 $scripts->add( 'dashboard', "/wp-admin/js/dashboard$suffix.js", array( 'jquery', 'admin-comments', 'postbox', 'wp-util', 'wp-a11y', 'wp-date' ), false, 1 );
1359 $scripts->set_translations( 'dashboard' );
1360
1361 $scripts->add( 'list-revisions', "/wp-includes/js/wp-list-revisions$suffix.js" );
1362
1363 $scripts->add( 'media-grid', "/wp-includes/js/media-grid$suffix.js", array( 'media-editor' ), false, 1 );
1364 $scripts->add( 'media', "/wp-admin/js/media$suffix.js", array( 'jquery' ), false, 1 );
1365 $scripts->set_translations( 'media' );
1366
1367 $scripts->add( 'image-edit', "/wp-admin/js/image-edit$suffix.js", array( 'jquery', 'jquery-ui-core', 'json2', 'imgareaselect', 'wp-a11y' ), false, 1 );
1368 $scripts->set_translations( 'image-edit' );
1369
1370 $scripts->add( 'set-post-thumbnail', "/wp-admin/js/set-post-thumbnail$suffix.js", array( 'jquery' ), false, 1 );
1371 $scripts->set_translations( 'set-post-thumbnail' );
1372
1373 /*
1374 * Navigation Menus: Adding underscore as a dependency to utilize _.debounce
1375 * see https://core.trac.wordpress.org/ticket/42321
1376 */
1377 $scripts->add( 'nav-menu', "/wp-admin/js/nav-menu$suffix.js", array( 'jquery-ui-sortable', 'jquery-ui-draggable', 'jquery-ui-droppable', 'wp-lists', 'postbox', 'json2', 'underscore' ) );
1378 $scripts->set_translations( 'nav-menu' );
1379
1380 $scripts->add( 'custom-header', '/wp-admin/js/custom-header.js', array( 'jquery-masonry' ), false, 1 );
1381 $scripts->add( 'custom-background', "/wp-admin/js/custom-background$suffix.js", array( 'wp-color-picker', 'media-views' ), false, 1 );
1382 $scripts->add( 'media-gallery', "/wp-admin/js/media-gallery$suffix.js", array( 'jquery' ), false, 1 );
1383
1384 $scripts->add( 'svg-painter', '/wp-admin/js/svg-painter.js', array( 'jquery' ), false, 1 );
1385 }
1386}
1387
1388/**
1389 * Assign default styles to $styles object.
1390 *
1391 * Nothing is returned, because the $styles parameter is passed by reference.
1392 * Meaning that whatever object is passed will be updated without having to
1393 * reassign the variable that was passed back to the same value. This saves
1394 * memory.
1395 *
1396 * Adding default styles is not the only task, it also assigns the base_url
1397 * property, the default version, and text direction for the object.
1398 *
1399 * @since 2.6.0
1400 *
1401 * @global array $editor_styles
1402 *
1403 * @param WP_Styles $styles
1404 */
1405function wp_default_styles( $styles ) {
1406 global $editor_styles;
1407
1408 // Include an unmodified $wp_version.
1409 require ABSPATH . WPINC . '/version.php';
1410
1411 if ( ! defined( 'SCRIPT_DEBUG' ) ) {
1412 define( 'SCRIPT_DEBUG', false !== strpos( $wp_version, '-src' ) );
1413 }
1414
1415 $guessurl = site_url();
1416
1417 if ( ! $guessurl ) {
1418 $guessurl = wp_guess_url();
1419 }
1420
1421 $styles->base_url = $guessurl;
1422 $styles->content_url = defined( 'WP_CONTENT_URL' ) ? WP_CONTENT_URL : '';
1423 $styles->default_version = get_bloginfo( 'version' );
1424 $styles->text_direction = function_exists( 'is_rtl' ) && is_rtl() ? 'rtl' : 'ltr';
1425 $styles->default_dirs = array( '/wp-admin/', '/wp-includes/css/' );
1426
1427 // Open Sans is no longer used by core, but may be relied upon by themes and plugins.
1428 $open_sans_font_url = '';
1429
1430 /*
1431 * translators: If there are characters in your language that are not supported
1432 * by Open Sans, translate this to 'off'. Do not translate into your own language.
1433 */
1434 if ( 'off' !== _x( 'on', 'Open Sans font: on or off' ) ) {
1435 $subsets = 'latin,latin-ext';
1436
1437 /*
1438 * translators: To add an additional Open Sans character subset specific to your language,
1439 * translate this to 'greek', 'cyrillic' or 'vietnamese'. Do not translate into your own language.
1440 */
1441 $subset = _x( 'no-subset', 'Open Sans font: add new subset (greek, cyrillic, vietnamese)' );
1442
1443 if ( 'cyrillic' === $subset ) {
1444 $subsets .= ',cyrillic,cyrillic-ext';
1445 } elseif ( 'greek' === $subset ) {
1446 $subsets .= ',greek,greek-ext';
1447 } elseif ( 'vietnamese' === $subset ) {
1448 $subsets .= ',vietnamese';
1449 }
1450
1451 // Hotlink Open Sans, for now.
1452 $open_sans_font_url = "https://fonts.googleapis.com/css?family=Open+Sans:300italic,400italic,600italic,300,400,600&subset=$subsets&display=fallback";
1453 }
1454
1455 // Register a stylesheet for the selected admin color scheme.
1456 $styles->add( 'colors', true, array( 'wp-admin', 'buttons' ) );
1457
1458 $suffix = SCRIPT_DEBUG ? '' : '.min';
1459
1460 // Admin CSS.
1461 $styles->add( 'common', "/wp-admin/css/common$suffix.css" );
1462 $styles->add( 'forms', "/wp-admin/css/forms$suffix.css" );
1463 $styles->add( 'admin-menu', "/wp-admin/css/admin-menu$suffix.css" );
1464 $styles->add( 'dashboard', "/wp-admin/css/dashboard$suffix.css" );
1465 $styles->add( 'list-tables', "/wp-admin/css/list-tables$suffix.css" );
1466 $styles->add( 'edit', "/wp-admin/css/edit$suffix.css" );
1467 $styles->add( 'revisions', "/wp-admin/css/revisions$suffix.css" );
1468 $styles->add( 'media', "/wp-admin/css/media$suffix.css" );
1469 $styles->add( 'themes', "/wp-admin/css/themes$suffix.css" );
1470 $styles->add( 'about', "/wp-admin/css/about$suffix.css" );
1471 $styles->add( 'nav-menus', "/wp-admin/css/nav-menus$suffix.css" );
1472 $styles->add( 'widgets', "/wp-admin/css/widgets$suffix.css", array( 'wp-pointer' ) );
1473 $styles->add( 'site-icon', "/wp-admin/css/site-icon$suffix.css" );
1474 $styles->add( 'l10n', "/wp-admin/css/l10n$suffix.css" );
1475 $styles->add( 'code-editor', "/wp-admin/css/code-editor$suffix.css", array( 'wp-codemirror' ) );
1476 $styles->add( 'site-health', "/wp-admin/css/site-health$suffix.css" );
1477
1478 $styles->add( 'wp-admin', false, array( 'dashicons', 'common', 'forms', 'admin-menu', 'dashboard', 'list-tables', 'edit', 'revisions', 'media', 'themes', 'about', 'nav-menus', 'widgets', 'site-icon', 'l10n' ) );
1479
1480 $styles->add( 'login', "/wp-admin/css/login$suffix.css", array( 'dashicons', 'buttons', 'forms', 'l10n' ) );
1481 $styles->add( 'install', "/wp-admin/css/install$suffix.css", array( 'dashicons', 'buttons', 'forms', 'l10n' ) );
1482 $styles->add( 'wp-color-picker', "/wp-admin/css/color-picker$suffix.css" );
1483 $styles->add( 'customize-controls', "/wp-admin/css/customize-controls$suffix.css", array( 'wp-admin', 'colors', 'imgareaselect' ) );
1484 $styles->add( 'customize-widgets', "/wp-admin/css/customize-widgets$suffix.css", array( 'wp-admin', 'colors' ) );
1485 $styles->add( 'customize-nav-menus', "/wp-admin/css/customize-nav-menus$suffix.css", array( 'wp-admin', 'colors' ) );
1486
1487 // Common dependencies.
1488 $styles->add( 'buttons', "/wp-includes/css/buttons$suffix.css" );
1489 $styles->add( 'dashicons', "/wp-includes/css/dashicons$suffix.css" );
1490
1491 // Includes CSS.
1492 $styles->add( 'admin-bar', "/wp-includes/css/admin-bar$suffix.css", array( 'dashicons' ) );
1493 $styles->add( 'wp-auth-check', "/wp-includes/css/wp-auth-check$suffix.css", array( 'dashicons' ) );
1494 $styles->add( 'editor-buttons', "/wp-includes/css/editor$suffix.css", array( 'dashicons' ) );
1495 $styles->add( 'media-views', "/wp-includes/css/media-views$suffix.css", array( 'buttons', 'dashicons', 'wp-mediaelement' ) );
1496 $styles->add( 'wp-pointer', "/wp-includes/css/wp-pointer$suffix.css", array( 'dashicons' ) );
1497 $styles->add( 'customize-preview', "/wp-includes/css/customize-preview$suffix.css", array( 'dashicons' ) );
1498 $styles->add( 'wp-embed-template-ie', "/wp-includes/css/wp-embed-template-ie$suffix.css" );
1499 $styles->add_data( 'wp-embed-template-ie', 'conditional', 'lte IE 8' );
1500
1501 // External libraries and friends.
1502 $styles->add( 'imgareaselect', '/wp-includes/js/imgareaselect/imgareaselect.css', array(), '0.9.8' );
1503 $styles->add( 'wp-jquery-ui-dialog', "/wp-includes/css/jquery-ui-dialog$suffix.css", array( 'dashicons' ) );
1504 $styles->add( 'mediaelement', '/wp-includes/js/mediaelement/mediaelementplayer-legacy.min.css', array(), '4.2.16' );
1505 $styles->add( 'wp-mediaelement', "/wp-includes/js/mediaelement/wp-mediaelement$suffix.css", array( 'mediaelement' ) );
1506 $styles->add( 'thickbox', '/wp-includes/js/thickbox/thickbox.css', array( 'dashicons' ) );
1507 $styles->add( 'wp-codemirror', '/wp-includes/js/codemirror/codemirror.min.css', array(), '5.29.1-alpha-ee20357' );
1508
1509 // Deprecated CSS.
1510 $styles->add( 'deprecated-media', "/wp-admin/css/deprecated-media$suffix.css" );
1511 $styles->add( 'farbtastic', "/wp-admin/css/farbtastic$suffix.css", array(), '1.3u1' );
1512 $styles->add( 'jcrop', '/wp-includes/js/jcrop/jquery.Jcrop.min.css', array(), '0.9.12' );
1513 $styles->add( 'colors-fresh', false, array( 'wp-admin', 'buttons' ) ); // Old handle.
1514 $styles->add( 'open-sans', $open_sans_font_url ); // No longer used in core as of 4.6.
1515
1516 // Noto Serif is no longer used by core, but may be relied upon by themes and plugins.
1517 $fonts_url = '';
1518
1519 /*
1520 * translators: Use this to specify the proper Google Font name and variants
1521 * to load that is supported by your language. Do not translate.
1522 * Set to 'off' to disable loading.
1523 */
1524 $font_family = _x( 'Noto Serif:400,400i,700,700i', 'Google Font Name and Variants' );
1525 if ( 'off' !== $font_family ) {
1526 $fonts_url = 'https://fonts.googleapis.com/css?family=' . urlencode( $font_family );
1527 }
1528 $styles->add( 'wp-editor-font', $fonts_url ); // No longer used in core as of 5.7.
1529 $block_library_theme_path = WPINC . "/css/dist/block-library/theme$suffix.css";
1530 $styles->add( 'wp-block-library-theme', "/$block_library_theme_path" );
1531 $styles->add_data( 'wp-block-library-theme', 'path', ABSPATH . $block_library_theme_path );
1532
1533 $styles->add(
1534 'wp-reset-editor-styles',
1535 "/wp-includes/css/dist/block-library/reset$suffix.css",
1536 array( 'common', 'forms' ) // Make sure the reset is loaded after the default WP Admin styles.
1537 );
1538
1539 $styles->add(
1540 'wp-editor-classic-layout-styles',
1541 "/wp-includes/css/dist/edit-post/classic$suffix.css",
1542 array()
1543 );
1544
1545 $wp_edit_blocks_dependencies = array(
1546 'wp-components',
1547 'wp-editor',
1548 // This need to be added before the block library styles,
1549 // The block library styles override the "reset" styles.
1550 'wp-reset-editor-styles',
1551 'wp-block-library',
1552 'wp-reusable-blocks',
1553 );
1554
1555 // Only load the default layout and margin styles for themes without theme.json file.
1556 if ( ! WP_Theme_JSON_Resolver::theme_has_support() ) {
1557 $wp_edit_blocks_dependencies[] = 'wp-editor-classic-layout-styles';
1558 }
1559
1560 if ( ! is_array( $editor_styles ) || count( $editor_styles ) === 0 ) {
1561 // Include opinionated block styles if no $editor_styles are declared, so the editor never appears broken.
1562 $wp_edit_blocks_dependencies[] = 'wp-block-library-theme';
1563 }
1564
1565 $styles->add(
1566 'wp-edit-blocks',
1567 "/wp-includes/css/dist/block-library/editor$suffix.css",
1568 $wp_edit_blocks_dependencies
1569 );
1570
1571 $package_styles = array(
1572 'block-editor' => array( 'wp-components' ),
1573 'block-library' => array(),
1574 'block-directory' => array(),
1575 'components' => array(),
1576 'edit-post' => array(
1577 'wp-components',
1578 'wp-block-editor',
1579 'wp-editor',
1580 'wp-edit-blocks',
1581 'wp-block-library',
1582 'wp-nux',
1583 ),
1584 'editor' => array(
1585 'wp-components',
1586 'wp-block-editor',
1587 'wp-nux',
1588 'wp-reusable-blocks',
1589 ),
1590 'format-library' => array(),
1591 'list-reusable-blocks' => array( 'wp-components' ),
1592 'reusable-blocks' => array( 'wp-components' ),
1593 'nux' => array( 'wp-components' ),
1594 'widgets' => array(
1595 'wp-components',
1596 ),
1597 'edit-widgets' => array(
1598 'wp-widgets',
1599 'wp-block-editor',
1600 'wp-edit-blocks',
1601 'wp-block-library',
1602 'wp-reusable-blocks',
1603 ),
1604 'customize-widgets' => array(
1605 'wp-widgets',
1606 'wp-block-editor',
1607 'wp-edit-blocks',
1608 'wp-block-library',
1609 'wp-reusable-blocks',
1610 ),
1611 'edit-site' => array(
1612 'wp-components',
1613 'wp-block-editor',
1614 'wp-edit-blocks',
1615 ),
1616 );
1617
1618 foreach ( $package_styles as $package => $dependencies ) {
1619 $handle = 'wp-' . $package;
1620 $path = "/wp-includes/css/dist/$package/style$suffix.css";
1621
1622 if ( 'block-library' === $package && wp_should_load_separate_core_block_assets() ) {
1623 $path = "/wp-includes/css/dist/$package/common$suffix.css";
1624 }
1625 $styles->add( $handle, $path, $dependencies );
1626 $styles->add_data( $handle, 'path', ABSPATH . $path );
1627 }
1628
1629 // RTL CSS.
1630 $rtl_styles = array(
1631 // Admin CSS.
1632 'common',
1633 'forms',
1634 'admin-menu',
1635 'dashboard',
1636 'list-tables',
1637 'edit',
1638 'revisions',
1639 'media',
1640 'themes',
1641 'about',
1642 'nav-menus',
1643 'widgets',
1644 'site-icon',
1645 'l10n',
1646 'install',
1647 'wp-color-picker',
1648 'customize-controls',
1649 'customize-widgets',
1650 'customize-nav-menus',
1651 'customize-preview',
1652 'login',
1653 'site-health',
1654 // Includes CSS.
1655 'buttons',
1656 'admin-bar',
1657 'wp-auth-check',
1658 'editor-buttons',
1659 'media-views',
1660 'wp-pointer',
1661 'wp-jquery-ui-dialog',
1662 // Package styles.
1663 'wp-reset-editor-styles',
1664 'wp-editor-classic-layout-styles',
1665 'wp-block-library-theme',
1666 'wp-edit-blocks',
1667 'wp-block-editor',
1668 'wp-block-library',
1669 'wp-block-directory',
1670 'wp-components',
1671 'wp-customize-widgets',
1672 'wp-edit-post',
1673 'wp-edit-site',
1674 'wp-edit-widgets',
1675 'wp-editor',
1676 'wp-format-library',
1677 'wp-list-reusable-blocks',
1678 'wp-reusable-blocks',
1679 'wp-nux',
1680 'wp-widgets',
1681 // Deprecated CSS.
1682 'deprecated-media',
1683 'farbtastic',
1684 );
1685
1686 foreach ( $rtl_styles as $rtl_style ) {
1687 $styles->add_data( $rtl_style, 'rtl', 'replace' );
1688 if ( $suffix ) {
1689 $styles->add_data( $rtl_style, 'suffix', $suffix );
1690 }
1691 }
1692}
1693
1694/**
1695 * Reorder JavaScript scripts array to place prototype before jQuery.
1696 *
1697 * @since 2.3.1
1698 *
1699 * @param array $js_array JavaScript scripts array
1700 * @return array Reordered array, if needed.
1701 */
1702function wp_prototype_before_jquery( $js_array ) {
1703 $prototype = array_search( 'prototype', $js_array, true );
1704
1705 if ( false === $prototype ) {
1706 return $js_array;
1707 }
1708
1709 $jquery = array_search( 'jquery', $js_array, true );
1710
1711 if ( false === $jquery ) {
1712 return $js_array;
1713 }
1714
1715 if ( $prototype < $jquery ) {
1716 return $js_array;
1717 }
1718
1719 unset( $js_array[ $prototype ] );
1720
1721 array_splice( $js_array, $jquery, 0, 'prototype' );
1722
1723 return $js_array;
1724}
1725
1726/**
1727 * Load localized data on print rather than initialization.
1728 *
1729 * These localizations require information that may not be loaded even by init.
1730 *
1731 * @since 2.5.0
1732 */
1733function wp_just_in_time_script_localization() {
1734
1735 wp_localize_script(
1736 'autosave',
1737 'autosaveL10n',
1738 array(
1739 'autosaveInterval' => AUTOSAVE_INTERVAL,
1740 'blog_id' => get_current_blog_id(),
1741 )
1742 );
1743
1744 wp_localize_script(
1745 'mce-view',
1746 'mceViewL10n',
1747 array(
1748 'shortcodes' => ! empty( $GLOBALS['shortcode_tags'] ) ? array_keys( $GLOBALS['shortcode_tags'] ) : array(),
1749 )
1750 );
1751
1752 wp_localize_script(
1753 'word-count',
1754 'wordCountL10n',
1755 array(
1756 /*
1757 * translators: If your word count is based on single characters (e.g. East Asian characters),
1758 * enter 'characters_excluding_spaces' or 'characters_including_spaces'. Otherwise, enter 'words'.
1759 * Do not translate into your own language.
1760 */
1761 'type' => _x( 'words', 'Word count type. Do not translate!' ),
1762 'shortcodes' => ! empty( $GLOBALS['shortcode_tags'] ) ? array_keys( $GLOBALS['shortcode_tags'] ) : array(),
1763 )
1764 );
1765}
1766
1767/**
1768 * Localizes the jQuery UI datepicker.
1769 *
1770 * @since 4.6.0
1771 *
1772 * @link https://api.jqueryui.com/datepicker/#options
1773 *
1774 * @global WP_Locale $wp_locale WordPress date and time locale object.
1775 */
1776function wp_localize_jquery_ui_datepicker() {
1777 global $wp_locale;
1778
1779 if ( ! wp_script_is( 'jquery-ui-datepicker', 'enqueued' ) ) {
1780 return;
1781 }
1782
1783 // Convert the PHP date format into jQuery UI's format.
1784 $datepicker_date_format = str_replace(
1785 array(
1786 'd',
1787 'j',
1788 'l',
1789 'z', // Day.
1790 'F',
1791 'M',
1792 'n',
1793 'm', // Month.
1794 'Y',
1795 'y', // Year.
1796 ),
1797 array(
1798 'dd',
1799 'd',
1800 'DD',
1801 'o',
1802 'MM',
1803 'M',
1804 'm',
1805 'mm',
1806 'yy',
1807 'y',
1808 ),
1809 get_option( 'date_format' )
1810 );
1811
1812 $datepicker_defaults = wp_json_encode(
1813 array(
1814 'closeText' => __( 'Close' ),
1815 'currentText' => __( 'Today' ),
1816 'monthNames' => array_values( $wp_locale->month ),
1817 'monthNamesShort' => array_values( $wp_locale->month_abbrev ),
1818 'nextText' => __( 'Next' ),
1819 'prevText' => __( 'Previous' ),
1820 'dayNames' => array_values( $wp_locale->weekday ),
1821 'dayNamesShort' => array_values( $wp_locale->weekday_abbrev ),
1822 'dayNamesMin' => array_values( $wp_locale->weekday_initial ),
1823 'dateFormat' => $datepicker_date_format,
1824 'firstDay' => absint( get_option( 'start_of_week' ) ),
1825 'isRTL' => $wp_locale->is_rtl(),
1826 )
1827 );
1828
1829 wp_add_inline_script( 'jquery-ui-datepicker', "jQuery(function(jQuery){jQuery.datepicker.setDefaults({$datepicker_defaults});});" );
1830}
1831
1832/**
1833 * Localizes community events data that needs to be passed to dashboard.js.
1834 *
1835 * @since 4.8.0
1836 */
1837function wp_localize_community_events() {
1838 if ( ! wp_script_is( 'dashboard' ) ) {
1839 return;
1840 }
1841
1842 require_once ABSPATH . 'wp-admin/includes/class-wp-community-events.php';
1843
1844 $user_id = get_current_user_id();
1845 $saved_location = get_user_option( 'community-events-location', $user_id );
1846 $saved_ip_address = isset( $saved_location['ip'] ) ? $saved_location['ip'] : false;
1847 $current_ip_address = WP_Community_Events::get_unsafe_client_ip();
1848
1849 /*
1850 * If the user's location is based on their IP address, then update their
1851 * location when their IP address changes. This allows them to see events
1852 * in their current city when travelling. Otherwise, they would always be
1853 * shown events in the city where they were when they first loaded the
1854 * Dashboard, which could have been months or years ago.
1855 */
1856 if ( $saved_ip_address && $current_ip_address && $current_ip_address !== $saved_ip_address ) {
1857 $saved_location['ip'] = $current_ip_address;
1858 update_user_meta( $user_id, 'community-events-location', $saved_location );
1859 }
1860
1861 $events_client = new WP_Community_Events( $user_id, $saved_location );
1862
1863 wp_localize_script(
1864 'dashboard',
1865 'communityEventsData',
1866 array(
1867 'nonce' => wp_create_nonce( 'community_events' ),
1868 'cache' => $events_client->get_cached_events(),
1869 'time_format' => get_option( 'time_format' ),
1870 )
1871 );
1872}
1873
1874/**
1875 * Administration Screen CSS for changing the styles.
1876 *
1877 * If installing the 'wp-admin/' directory will be replaced with './'.
1878 *
1879 * The $_wp_admin_css_colors global manages the Administration Screens CSS
1880 * stylesheet that is loaded. The option that is set is 'admin_color' and is the
1881 * color and key for the array. The value for the color key is an object with
1882 * a 'url' parameter that has the URL path to the CSS file.
1883 *
1884 * The query from $src parameter will be appended to the URL that is given from
1885 * the $_wp_admin_css_colors array value URL.
1886 *
1887 * @since 2.6.0
1888 *
1889 * @global array $_wp_admin_css_colors
1890 *
1891 * @param string $src Source URL.
1892 * @param string $handle Either 'colors' or 'colors-rtl'.
1893 * @return string|false URL path to CSS stylesheet for Administration Screens.
1894 */
1895function wp_style_loader_src( $src, $handle ) {
1896 global $_wp_admin_css_colors;
1897
1898 if ( wp_installing() ) {
1899 return preg_replace( '#^wp-admin/#', './', $src );
1900 }
1901
1902 if ( 'colors' === $handle ) {
1903 $color = get_user_option( 'admin_color' );
1904
1905 if ( empty( $color ) || ! isset( $_wp_admin_css_colors[ $color ] ) ) {
1906 $color = 'fresh';
1907 }
1908
1909 $color = $_wp_admin_css_colors[ $color ];
1910 $url = $color->url;
1911
1912 if ( ! $url ) {
1913 return false;
1914 }
1915
1916 $parsed = parse_url( $src );
1917 if ( isset( $parsed['query'] ) && $parsed['query'] ) {
1918 wp_parse_str( $parsed['query'], $qv );
1919 $url = add_query_arg( $qv, $url );
1920 }
1921
1922 return $url;
1923 }
1924
1925 return $src;
1926}
1927
1928/**
1929 * Prints the script queue in the HTML head on admin pages.
1930 *
1931 * Postpones the scripts that were queued for the footer.
1932 * print_footer_scripts() is called in the footer to print these scripts.
1933 *
1934 * @since 2.8.0
1935 *
1936 * @see wp_print_scripts()
1937 *
1938 * @global bool $concatenate_scripts
1939 *
1940 * @return array
1941 */
1942function print_head_scripts() {
1943 global $concatenate_scripts;
1944
1945 if ( ! did_action( 'wp_print_scripts' ) ) {
1946 /** This action is documented in wp-includes/functions.wp-scripts.php */
1947 do_action( 'wp_print_scripts' );
1948 }
1949
1950 $wp_scripts = wp_scripts();
1951
1952 script_concat_settings();
1953 $wp_scripts->do_concat = $concatenate_scripts;
1954 $wp_scripts->do_head_items();
1955
1956 /**
1957 * Filters whether to print the head scripts.
1958 *
1959 * @since 2.8.0
1960 *
1961 * @param bool $print Whether to print the head scripts. Default true.
1962 */
1963 if ( apply_filters( 'print_head_scripts', true ) ) {
1964 _print_scripts();
1965 }
1966
1967 $wp_scripts->reset();
1968 return $wp_scripts->done;
1969}
1970
1971/**
1972 * Prints the scripts that were queued for the footer or too late for the HTML head.
1973 *
1974 * @since 2.8.0
1975 *
1976 * @global WP_Scripts $wp_scripts
1977 * @global bool $concatenate_scripts
1978 *
1979 * @return array
1980 */
1981function print_footer_scripts() {
1982 global $wp_scripts, $concatenate_scripts;
1983
1984 if ( ! ( $wp_scripts instanceof WP_Scripts ) ) {
1985 return array(); // No need to run if not instantiated.
1986 }
1987 script_concat_settings();
1988 $wp_scripts->do_concat = $concatenate_scripts;
1989 $wp_scripts->do_footer_items();
1990
1991 /**
1992 * Filters whether to print the footer scripts.
1993 *
1994 * @since 2.8.0
1995 *
1996 * @param bool $print Whether to print the footer scripts. Default true.
1997 */
1998 if ( apply_filters( 'print_footer_scripts', true ) ) {
1999 _print_scripts();
2000 }
2001
2002 $wp_scripts->reset();
2003 return $wp_scripts->done;
2004}
2005
2006/**
2007 * Print scripts (internal use only)
2008 *
2009 * @ignore
2010 *
2011 * @global WP_Scripts $wp_scripts
2012 * @global bool $compress_scripts
2013 */
2014function _print_scripts() {
2015 global $wp_scripts, $compress_scripts;
2016
2017 $zip = $compress_scripts ? 1 : 0;
2018 if ( $zip && defined( 'ENFORCE_GZIP' ) && ENFORCE_GZIP ) {
2019 $zip = 'gzip';
2020 }
2021
2022 $concat = trim( $wp_scripts->concat, ', ' );
2023 $type_attr = current_theme_supports( 'html5', 'script' ) ? '' : " type='text/javascript'";
2024
2025 if ( $concat ) {
2026 if ( ! empty( $wp_scripts->print_code ) ) {
2027 echo "\n<script{$type_attr}>\n";
2028 echo "/* <![CDATA[ */\n"; // Not needed in HTML 5.
2029 echo $wp_scripts->print_code;
2030 echo "/* ]]> */\n";
2031 echo "</script>\n";
2032 }
2033
2034 $concat = str_split( $concat, 128 );
2035 $concatenated = '';
2036
2037 foreach ( $concat as $key => $chunk ) {
2038 $concatenated .= "&load%5Bchunk_{$key}%5D={$chunk}";
2039 }
2040
2041 $src = $wp_scripts->base_url . "/wp-admin/load-scripts.php?c={$zip}" . $concatenated . '&ver=' . $wp_scripts->default_version;
2042 echo "<script{$type_attr} src='" . esc_attr( $src ) . "'></script>\n";
2043 }
2044
2045 if ( ! empty( $wp_scripts->print_html ) ) {
2046 echo $wp_scripts->print_html;
2047 }
2048}
2049
2050/**
2051 * Prints the script queue in the HTML head on the front end.
2052 *
2053 * Postpones the scripts that were queued for the footer.
2054 * wp_print_footer_scripts() is called in the footer to print these scripts.
2055 *
2056 * @since 2.8.0
2057 *
2058 * @global WP_Scripts $wp_scripts
2059 *
2060 * @return array
2061 */
2062function wp_print_head_scripts() {
2063 global $wp_scripts;
2064
2065 if ( ! did_action( 'wp_print_scripts' ) ) {
2066 /** This action is documented in wp-includes/functions.wp-scripts.php */
2067 do_action( 'wp_print_scripts' );
2068 }
2069
2070 if ( ! ( $wp_scripts instanceof WP_Scripts ) ) {
2071 return array(); // No need to run if nothing is queued.
2072 }
2073
2074 return print_head_scripts();
2075}
2076
2077/**
2078 * Private, for use in *_footer_scripts hooks
2079 *
2080 * @since 3.3.0
2081 */
2082function _wp_footer_scripts() {
2083 print_late_styles();
2084 print_footer_scripts();
2085}
2086
2087/**
2088 * Hooks to print the scripts and styles in the footer.
2089 *
2090 * @since 2.8.0
2091 */
2092function wp_print_footer_scripts() {
2093 /**
2094 * Fires when footer scripts are printed.
2095 *
2096 * @since 2.8.0
2097 */
2098 do_action( 'wp_print_footer_scripts' );
2099}
2100
2101/**
2102 * Wrapper for do_action( 'wp_enqueue_scripts' ).
2103 *
2104 * Allows plugins to queue scripts for the front end using wp_enqueue_script().
2105 * Runs first in wp_head() where all is_home(), is_page(), etc. functions are available.
2106 *
2107 * @since 2.8.0
2108 */
2109function wp_enqueue_scripts() {
2110 /**
2111 * Fires when scripts and styles are enqueued.
2112 *
2113 * @since 2.8.0
2114 */
2115 do_action( 'wp_enqueue_scripts' );
2116}
2117
2118/**
2119 * Prints the styles queue in the HTML head on admin pages.
2120 *
2121 * @since 2.8.0
2122 *
2123 * @global bool $concatenate_scripts
2124 *
2125 * @return array
2126 */
2127function print_admin_styles() {
2128 global $concatenate_scripts;
2129
2130 $wp_styles = wp_styles();
2131
2132 script_concat_settings();
2133 $wp_styles->do_concat = $concatenate_scripts;
2134 $wp_styles->do_items( false );
2135
2136 /**
2137 * Filters whether to print the admin styles.
2138 *
2139 * @since 2.8.0
2140 *
2141 * @param bool $print Whether to print the admin styles. Default true.
2142 */
2143 if ( apply_filters( 'print_admin_styles', true ) ) {
2144 _print_styles();
2145 }
2146
2147 $wp_styles->reset();
2148 return $wp_styles->done;
2149}
2150
2151/**
2152 * Prints the styles that were queued too late for the HTML head.
2153 *
2154 * @since 3.3.0
2155 *
2156 * @global WP_Styles $wp_styles
2157 * @global bool $concatenate_scripts
2158 *
2159 * @return array|void
2160 */
2161function print_late_styles() {
2162 global $wp_styles, $concatenate_scripts;
2163
2164 if ( ! ( $wp_styles instanceof WP_Styles ) ) {
2165 return;
2166 }
2167
2168 script_concat_settings();
2169 $wp_styles->do_concat = $concatenate_scripts;
2170 $wp_styles->do_footer_items();
2171
2172 /**
2173 * Filters whether to print the styles queued too late for the HTML head.
2174 *
2175 * @since 3.3.0
2176 *
2177 * @param bool $print Whether to print the 'late' styles. Default true.
2178 */
2179 if ( apply_filters( 'print_late_styles', true ) ) {
2180 _print_styles();
2181 }
2182
2183 $wp_styles->reset();
2184 return $wp_styles->done;
2185}
2186
2187/**
2188 * Print styles (internal use only)
2189 *
2190 * @ignore
2191 * @since 3.3.0
2192 *
2193 * @global bool $compress_css
2194 */
2195function _print_styles() {
2196 global $compress_css;
2197
2198 $wp_styles = wp_styles();
2199
2200 $zip = $compress_css ? 1 : 0;
2201 if ( $zip && defined( 'ENFORCE_GZIP' ) && ENFORCE_GZIP ) {
2202 $zip = 'gzip';
2203 }
2204
2205 $concat = trim( $wp_styles->concat, ', ' );
2206 $type_attr = current_theme_supports( 'html5', 'style' ) ? '' : ' type="text/css"';
2207
2208 if ( $concat ) {
2209 $dir = $wp_styles->text_direction;
2210 $ver = $wp_styles->default_version;
2211
2212 $concat = str_split( $concat, 128 );
2213 $concatenated = '';
2214
2215 foreach ( $concat as $key => $chunk ) {
2216 $concatenated .= "&load%5Bchunk_{$key}%5D={$chunk}";
2217 }
2218
2219 $href = $wp_styles->base_url . "/wp-admin/load-styles.php?c={$zip}&dir={$dir}" . $concatenated . '&ver=' . $ver;
2220 echo "<link rel='stylesheet' href='" . esc_attr( $href ) . "'{$type_attr} media='all' />\n";
2221
2222 if ( ! empty( $wp_styles->print_code ) ) {
2223 echo "<style{$type_attr}>\n";
2224 echo $wp_styles->print_code;
2225 echo "\n</style>\n";
2226 }
2227 }
2228
2229 if ( ! empty( $wp_styles->print_html ) ) {
2230 echo $wp_styles->print_html;
2231 }
2232}
2233
2234/**
2235 * Determine the concatenation and compression settings for scripts and styles.
2236 *
2237 * @since 2.8.0
2238 *
2239 * @global bool $concatenate_scripts
2240 * @global bool $compress_scripts
2241 * @global bool $compress_css
2242 */
2243function script_concat_settings() {
2244 global $concatenate_scripts, $compress_scripts, $compress_css;
2245
2246 $compressed_output = ( ini_get( 'zlib.output_compression' ) || 'ob_gzhandler' === ini_get( 'output_handler' ) );
2247
2248 $can_compress_scripts = ! wp_installing() && get_site_option( 'can_compress_scripts' );
2249
2250 if ( ! isset( $concatenate_scripts ) ) {
2251 $concatenate_scripts = defined( 'CONCATENATE_SCRIPTS' ) ? CONCATENATE_SCRIPTS : true;
2252 if ( ( ! is_admin() && ! did_action( 'login_init' ) ) || ( defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ) ) {
2253 $concatenate_scripts = false;
2254 }
2255 }
2256
2257 if ( ! isset( $compress_scripts ) ) {
2258 $compress_scripts = defined( 'COMPRESS_SCRIPTS' ) ? COMPRESS_SCRIPTS : true;
2259 if ( $compress_scripts && ( ! $can_compress_scripts || $compressed_output ) ) {
2260 $compress_scripts = false;
2261 }
2262 }
2263
2264 if ( ! isset( $compress_css ) ) {
2265 $compress_css = defined( 'COMPRESS_CSS' ) ? COMPRESS_CSS : true;
2266 if ( $compress_css && ( ! $can_compress_scripts || $compressed_output ) ) {
2267 $compress_css = false;
2268 }
2269 }
2270}
2271
2272/**
2273 * Handles the enqueueing of block scripts and styles that are common to both
2274 * the editor and the front-end.
2275 *
2276 * @since 5.0.0
2277 */
2278function wp_common_block_scripts_and_styles() {
2279 if ( is_admin() && ! wp_should_load_block_editor_scripts_and_styles() ) {
2280 return;
2281 }
2282
2283 wp_enqueue_style( 'wp-block-library' );
2284
2285 if ( current_theme_supports( 'wp-block-styles' ) ) {
2286 if ( wp_should_load_separate_core_block_assets() ) {
2287 $suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? 'css' : 'min.css';
2288 $files = glob( __DIR__ . "/blocks/**/theme.$suffix" );
2289 foreach ( $files as $path ) {
2290 $block_name = basename( dirname( $path ) );
2291 if ( is_rtl() && file_exists( __DIR__ . "/blocks/$block_name/theme-rtl.$suffix" ) ) {
2292 $path = __DIR__ . "/blocks/$block_name/theme-rtl.$suffix";
2293 }
2294 wp_add_inline_style( "wp-block-{$block_name}", file_get_contents( $path ) );
2295 }
2296 } else {
2297 wp_enqueue_style( 'wp-block-library-theme' );
2298 }
2299 }
2300
2301 /**
2302 * Fires after enqueuing block assets for both editor and front-end.
2303 *
2304 * Call `add_action` on any hook before 'wp_enqueue_scripts'.
2305 *
2306 * In the function call you supply, simply use `wp_enqueue_script` and
2307 * `wp_enqueue_style` to add your functionality to the Gutenberg editor.
2308 *
2309 * @since 5.0.0
2310 */
2311 do_action( 'enqueue_block_assets' );
2312}
2313
2314/**
2315 * Enqueues the global styles defined via theme.json.
2316 *
2317 * @since 5.8.0
2318 */
2319function wp_enqueue_global_styles() {
2320 $separate_assets = wp_should_load_separate_core_block_assets();
2321 $is_block_theme = wp_is_block_theme();
2322 $is_classic_theme = ! $is_block_theme;
2323
2324 /*
2325 * Global styles should be printed in the head when loading all styles combined.
2326 * The footer should only be used to print global styles for classic themes with separate core assets enabled.
2327 *
2328 * See https://core.trac.wordpress.org/ticket/53494.
2329 */
2330 if (
2331 ( $is_block_theme && doing_action( 'wp_footer' ) ) ||
2332 ( $is_classic_theme && doing_action( 'wp_footer' ) && ! $separate_assets ) ||
2333 ( $is_classic_theme && doing_action( 'wp_enqueue_scripts' ) && $separate_assets )
2334 ) {
2335 return;
2336 }
2337
2338 $stylesheet = wp_get_global_stylesheet();
2339
2340 if ( empty( $stylesheet ) ) {
2341 return;
2342 }
2343
2344 wp_register_style( 'global-styles', false, array(), true, true );
2345 wp_add_inline_style( 'global-styles', $stylesheet );
2346 wp_enqueue_style( 'global-styles' );
2347}
2348
2349/**
2350 * Render the SVG filters supplied by theme.json.
2351 *
2352 * Note that this doesn't render the per-block user-defined
2353 * filters which are handled by wp_render_duotone_support,
2354 * but it should be rendered before the filtered content
2355 * in the body to satisfy Safari's rendering quirks.
2356 *
2357 * @since 5.9.1
2358 */
2359function wp_global_styles_render_svg_filters() {
2360 /*
2361 * When calling via the in_admin_header action, we only want to render the
2362 * SVGs on block editor pages.
2363 */
2364 if (
2365 is_admin() &&
2366 ! get_current_screen()->is_block_editor()
2367 ) {
2368 return;
2369 }
2370
2371 $filters = wp_get_global_styles_svg_filters();
2372 if ( ! empty( $filters ) ) {
2373 echo $filters;
2374 }
2375}
2376
2377/**
2378 * Checks if the editor scripts and styles for all registered block types
2379 * should be enqueued on the current screen.
2380 *
2381 * @since 5.6.0
2382 *
2383 * @global WP_Screen $current_screen WordPress current screen object.
2384 *
2385 * @return bool Whether scripts and styles should be enqueued.
2386 */
2387function wp_should_load_block_editor_scripts_and_styles() {
2388 global $current_screen;
2389
2390 $is_block_editor_screen = ( $current_screen instanceof WP_Screen ) && $current_screen->is_block_editor();
2391
2392 /**
2393 * Filters the flag that decides whether or not block editor scripts and styles
2394 * are going to be enqueued on the current screen.
2395 *
2396 * @since 5.6.0
2397 *
2398 * @param bool $is_block_editor_screen Current value of the flag.
2399 */
2400 return apply_filters( 'should_load_block_editor_scripts_and_styles', $is_block_editor_screen );
2401}
2402
2403/**
2404 * Checks whether separate styles should be loaded for core blocks on-render.
2405 *
2406 * When this function returns true, other functions ensure that core blocks
2407 * only load their assets on-render, and each block loads its own, individual
2408 * assets. Third-party blocks only load their assets when rendered.
2409 *
2410 * When this function returns false, all core block assets are loaded regardless
2411 * of whether they are rendered in a page or not, because they are all part of
2412 * the `block-library/style.css` file. Assets for third-party blocks are always
2413 * enqueued regardless of whether they are rendered or not.
2414 *
2415 * This only affects front end and not the block editor screens.
2416 *
2417 * @see wp_enqueue_registered_block_scripts_and_styles()
2418 * @see register_block_style_handle()
2419 *
2420 * @since 5.8.0
2421 *
2422 * @return bool Whether separate assets will be loaded.
2423 */
2424function wp_should_load_separate_core_block_assets() {
2425 if ( is_admin() || is_feed() || ( defined( 'REST_REQUEST' ) && REST_REQUEST ) ) {
2426 return false;
2427 }
2428
2429 /**
2430 * Filters whether block styles should be loaded separately.
2431 *
2432 * Returning false loads all core block assets, regardless of whether they are rendered
2433 * in a page or not. Returning true loads core block assets only when they are rendered.
2434 *
2435 * @since 5.8.0
2436 *
2437 * @param bool $load_separate_assets Whether separate assets will be loaded.
2438 * Default false (all block assets are loaded, even when not used).
2439 */
2440 return apply_filters( 'should_load_separate_core_block_assets', false );
2441}
2442
2443/**
2444 * Enqueues registered block scripts and styles, depending on current rendered
2445 * context (only enqueuing editor scripts while in context of the editor).
2446 *
2447 * @since 5.0.0
2448 *
2449 * @global WP_Screen $current_screen WordPress current screen object.
2450 */
2451function wp_enqueue_registered_block_scripts_and_styles() {
2452 global $current_screen;
2453
2454 if ( wp_should_load_separate_core_block_assets() ) {
2455 return;
2456 }
2457
2458 $load_editor_scripts = is_admin() && wp_should_load_block_editor_scripts_and_styles();
2459
2460 $block_registry = WP_Block_Type_Registry::get_instance();
2461 foreach ( $block_registry->get_all_registered() as $block_name => $block_type ) {
2462 // Front-end styles.
2463 if ( ! empty( $block_type->style ) ) {
2464 wp_enqueue_style( $block_type->style );
2465 }
2466
2467 // Front-end script.
2468 if ( ! empty( $block_type->script ) ) {
2469 wp_enqueue_script( $block_type->script );
2470 }
2471
2472 // Editor styles.
2473 if ( $load_editor_scripts && ! empty( $block_type->editor_style ) ) {
2474 wp_enqueue_style( $block_type->editor_style );
2475 }
2476
2477 // Editor script.
2478 if ( $load_editor_scripts && ! empty( $block_type->editor_script ) ) {
2479 wp_enqueue_script( $block_type->editor_script );
2480 }
2481 }
2482}
2483
2484/**
2485 * Function responsible for enqueuing the styles required for block styles functionality on the editor and on the frontend.
2486 *
2487 * @since 5.3.0
2488 *
2489 * @global WP_Styles $wp_styles
2490 */
2491function enqueue_block_styles_assets() {
2492 global $wp_styles;
2493
2494 $block_styles = WP_Block_Styles_Registry::get_instance()->get_all_registered();
2495
2496 foreach ( $block_styles as $block_name => $styles ) {
2497 foreach ( $styles as $style_properties ) {
2498 if ( isset( $style_properties['style_handle'] ) ) {
2499
2500 // If the site loads separate styles per-block, enqueue the stylesheet on render.
2501 if ( wp_should_load_separate_core_block_assets() ) {
2502 add_filter(
2503 'render_block',
2504 function( $html, $block ) use ( $block_name, $style_properties ) {
2505 if ( $block['blockName'] === $block_name ) {
2506 wp_enqueue_style( $style_properties['style_handle'] );
2507 }
2508 return $html;
2509 },
2510 10,
2511 2
2512 );
2513 } else {
2514 wp_enqueue_style( $style_properties['style_handle'] );
2515 }
2516 }
2517 if ( isset( $style_properties['inline_style'] ) ) {
2518
2519 // Default to "wp-block-library".
2520 $handle = 'wp-block-library';
2521
2522 // If the site loads separate styles per-block, check if the block has a stylesheet registered.
2523 if ( wp_should_load_separate_core_block_assets() ) {
2524 $block_stylesheet_handle = generate_block_asset_handle( $block_name, 'style' );
2525
2526 if ( isset( $wp_styles->registered[ $block_stylesheet_handle ] ) ) {
2527 $handle = $block_stylesheet_handle;
2528 }
2529 }
2530
2531 // Add inline styles to the calculated handle.
2532 wp_add_inline_style( $handle, $style_properties['inline_style'] );
2533 }
2534 }
2535 }
2536}
2537
2538/**
2539 * Function responsible for enqueuing the assets required for block styles functionality on the editor.
2540 *
2541 * @since 5.3.0
2542 */
2543function enqueue_editor_block_styles_assets() {
2544 $block_styles = WP_Block_Styles_Registry::get_instance()->get_all_registered();
2545
2546 $register_script_lines = array( '( function() {' );
2547 foreach ( $block_styles as $block_name => $styles ) {
2548 foreach ( $styles as $style_properties ) {
2549 $block_style = array(
2550 'name' => $style_properties['name'],
2551 'label' => $style_properties['label'],
2552 );
2553 if ( isset( $style_properties['is_default'] ) ) {
2554 $block_style['isDefault'] = $style_properties['is_default'];
2555 }
2556 $register_script_lines[] = sprintf(
2557 ' wp.blocks.registerBlockStyle( \'%s\', %s );',
2558 $block_name,
2559 wp_json_encode( $block_style )
2560 );
2561 }
2562 }
2563 $register_script_lines[] = '} )();';
2564 $inline_script = implode( "\n", $register_script_lines );
2565
2566 wp_register_script( 'wp-block-styles', false, array( 'wp-blocks' ), true, true );
2567 wp_add_inline_script( 'wp-block-styles', $inline_script );
2568 wp_enqueue_script( 'wp-block-styles' );
2569}
2570
2571/**
2572 * Enqueues the assets required for the block directory within the block editor.
2573 *
2574 * @since 5.5.0
2575 */
2576function wp_enqueue_editor_block_directory_assets() {
2577 wp_enqueue_script( 'wp-block-directory' );
2578 wp_enqueue_style( 'wp-block-directory' );
2579}
2580
2581/**
2582 * Enqueues the assets required for the format library within the block editor.
2583 *
2584 * @since 5.8.0
2585 */
2586function wp_enqueue_editor_format_library_assets() {
2587 wp_enqueue_script( 'wp-format-library' );
2588 wp_enqueue_style( 'wp-format-library' );
2589}
2590
2591/**
2592 * Sanitizes an attributes array into an attributes string to be placed inside a `<script>` tag.
2593 *
2594 * Automatically injects type attribute if needed.
2595 * Used by {@see wp_get_script_tag()} and {@see wp_get_inline_script_tag()}.
2596 *
2597 * @since 5.7.0
2598 *
2599 * @param array $attributes Key-value pairs representing `<script>` tag attributes.
2600 * @return string String made of sanitized `<script>` tag attributes.
2601 */
2602function wp_sanitize_script_attributes( $attributes ) {
2603 $html5_script_support = ! is_admin() && ! current_theme_supports( 'html5', 'script' );
2604 $attributes_string = '';
2605
2606 // If HTML5 script tag is supported, only the attribute name is added
2607 // to $attributes_string for entries with a boolean value, and that are true.
2608 foreach ( $attributes as $attribute_name => $attribute_value ) {
2609 if ( is_bool( $attribute_value ) ) {
2610 if ( $attribute_value ) {
2611 $attributes_string .= $html5_script_support ? sprintf( ' %1$s="%2$s"', esc_attr( $attribute_name ), esc_attr( $attribute_name ) ) : ' ' . esc_attr( $attribute_name );
2612 }
2613 } else {
2614 $attributes_string .= sprintf( ' %1$s="%2$s"', esc_attr( $attribute_name ), esc_attr( $attribute_value ) );
2615 }
2616 }
2617
2618 return $attributes_string;
2619}
2620
2621/**
2622 * Formats `<script>` loader tags.
2623 *
2624 * It is possible to inject attributes in the `<script>` tag via the {@see 'wp_script_attributes'} filter.
2625 * Automatically injects type attribute if needed.
2626 *
2627 * @since 5.7.0
2628 *
2629 * @param array $attributes Key-value pairs representing `<script>` tag attributes.
2630 * @return string String containing `<script>` opening and closing tags.
2631 */
2632function wp_get_script_tag( $attributes ) {
2633 if ( ! isset( $attributes['type'] ) && ! is_admin() && ! current_theme_supports( 'html5', 'script' ) ) {
2634 $attributes['type'] = 'text/javascript';
2635 }
2636 /**
2637 * Filters attributes to be added to a script tag.
2638 *
2639 * @since 5.7.0
2640 *
2641 * @param array $attributes Key-value pairs representing `<script>` tag attributes.
2642 * Only the attribute name is added to the `<script>` tag for
2643 * entries with a boolean value, and that are true.
2644 */
2645 $attributes = apply_filters( 'wp_script_attributes', $attributes );
2646
2647 return sprintf( "<script%s></script>\n", wp_sanitize_script_attributes( $attributes ) );
2648}
2649
2650/**
2651 * Prints formatted `<script>` loader tag.
2652 *
2653 * It is possible to inject attributes in the `<script>` tag via the {@see 'wp_script_attributes'} filter.
2654 * Automatically injects type attribute if needed.
2655 *
2656 * @since 5.7.0
2657 *
2658 * @param array $attributes Key-value pairs representing `<script>` tag attributes.
2659 */
2660function wp_print_script_tag( $attributes ) {
2661 echo wp_get_script_tag( $attributes );
2662}
2663
2664/**
2665 * Wraps inline JavaScript in `<script>` tag.
2666 *
2667 * It is possible to inject attributes in the `<script>` tag via the {@see 'wp_script_attributes'} filter.
2668 * Automatically injects type attribute if needed.
2669 *
2670 * @since 5.7.0
2671 *
2672 * @param string $javascript Inline JavaScript code.
2673 * @param array $attributes Optional. Key-value pairs representing `<script>` tag attributes.
2674 * @return string String containing inline JavaScript code wrapped around `<script>` tag.
2675 */
2676function wp_get_inline_script_tag( $javascript, $attributes = array() ) {
2677 if ( ! isset( $attributes['type'] ) && ! is_admin() && ! current_theme_supports( 'html5', 'script' ) ) {
2678 $attributes['type'] = 'text/javascript';
2679 }
2680 /**
2681 * Filters attributes to be added to a script tag.
2682 *
2683 * @since 5.7.0
2684 *
2685 * @param array $attributes Key-value pairs representing `<script>` tag attributes.
2686 * Only the attribute name is added to the `<script>` tag for
2687 * entries with a boolean value, and that are true.
2688 * @param string $javascript Inline JavaScript code.
2689 */
2690 $attributes = apply_filters( 'wp_inline_script_attributes', $attributes, $javascript );
2691
2692 $javascript = "\n" . trim( $javascript, "\n\r " ) . "\n";
2693
2694 return sprintf( "<script%s>%s</script>\n", wp_sanitize_script_attributes( $attributes ), $javascript );
2695}
2696
2697/**
2698 * Prints inline JavaScript wrapped in `<script>` tag.
2699 *
2700 * It is possible to inject attributes in the `<script>` tag via the {@see 'wp_script_attributes'} filter.
2701 * Automatically injects type attribute if needed.
2702 *
2703 * @since 5.7.0
2704 *
2705 * @param string $javascript Inline JavaScript code.
2706 * @param array $attributes Optional. Key-value pairs representing `<script>` tag attributes.
2707 */
2708function wp_print_inline_script_tag( $javascript, $attributes = array() ) {
2709 echo wp_get_inline_script_tag( $javascript, $attributes );
2710}
2711
2712/**
2713 * Allows small styles to be inlined.
2714 *
2715 * This improves performance and sustainability, and is opt-in. Stylesheets can opt in
2716 * by adding `path` data using `wp_style_add_data`, and defining the file's absolute path:
2717 *
2718 * wp_style_add_data( $style_handle, 'path', $file_path );
2719 *
2720 * @since 5.8.0
2721 *
2722 * @global WP_Styles $wp_styles
2723 */
2724function wp_maybe_inline_styles() {
2725 global $wp_styles;
2726
2727 $total_inline_limit = 20000;
2728 /**
2729 * The maximum size of inlined styles in bytes.
2730 *
2731 * @since 5.8.0
2732 *
2733 * @param int $total_inline_limit The file-size threshold, in bytes. Default 20000.
2734 */
2735 $total_inline_limit = apply_filters( 'styles_inline_size_limit', $total_inline_limit );
2736
2737 $styles = array();
2738
2739 // Build an array of styles that have a path defined.
2740 if (!is_null( $wp_styles) and !is_null( $wp_styles->queue)) {
2741 foreach ( $wp_styles->queue as $handle ) {
2742 if ( wp_styles()->get_data( $handle, 'path' ) && file_exists( $wp_styles->registered[ $handle ]->extra['path'] ) ) {
2743 $styles[] = array(
2744 'handle' => $handle,
2745 'src' => $wp_styles->registered[ $handle ]->src,
2746 'path' => $wp_styles->registered[ $handle ]->extra['path'],
2747 'size' => filesize( $wp_styles->registered[ $handle ]->extra['path'] ),
2748 );
2749 }
2750 }
2751 }
2752
2753 if ( ! empty( $styles ) ) {
2754 // Reorder styles array based on size.
2755 usort(
2756 $styles,
2757 static function( $a, $b ) {
2758 return ( $a['size'] <= $b['size'] ) ? -1 : 1;
2759 }
2760 );
2761
2762 /*
2763 * The total inlined size.
2764 *
2765 * On each iteration of the loop, if a style gets added inline the value of this var increases
2766 * to reflect the total size of inlined styles.
2767 */
2768 $total_inline_size = 0;
2769
2770 // Loop styles.
2771 foreach ( $styles as $style ) {
2772
2773 // Size check. Since styles are ordered by size, we can break the loop.
2774 if ( $total_inline_size + $style['size'] > $total_inline_limit ) {
2775 break;
2776 }
2777
2778 // Get the styles if we don't already have them.
2779 $style['css'] = file_get_contents( $style['path'] );
2780
2781 // Check if the style contains relative URLs that need to be modified.
2782 // URLs relative to the stylesheet's path should be converted to relative to the site's root.
2783 $style['css'] = _wp_normalize_relative_css_links( $style['css'], $style['src'] );
2784
2785 // Set `src` to `false` and add styles inline.
2786 $wp_styles->registered[ $style['handle'] ]->src = false;
2787 if ( empty( $wp_styles->registered[ $style['handle'] ]->extra['after'] ) ) {
2788 $wp_styles->registered[ $style['handle'] ]->extra['after'] = array();
2789 }
2790 array_unshift( $wp_styles->registered[ $style['handle'] ]->extra['after'], $style['css'] );
2791
2792 // Add the styles size to the $total_inline_size var.
2793 $total_inline_size += (int) $style['size'];
2794 }
2795 }
2796}
2797
2798/**
2799 * Make URLs relative to the WordPress installation.
2800 *
2801 * @since 5.9.0
2802 * @access private
2803 *
2804 * @param string $css The CSS to make URLs relative to the WordPress installation.
2805 * @param string $stylesheet_url The URL to the stylesheet.
2806 *
2807 * @return string The CSS with URLs made relative to the WordPress installation.
2808 */
2809function _wp_normalize_relative_css_links( $css, $stylesheet_url ) {
2810 $has_src_results = preg_match_all( '#url\s*\(\s*[\'"]?\s*([^\'"\)]+)#', $css, $src_results );
2811 if ( $has_src_results ) {
2812 // Loop through the URLs to find relative ones.
2813 foreach ( $src_results[1] as $src_index => $src_result ) {
2814 // Skip if this is an absolute URL.
2815 if ( 0 === strpos( $src_result, 'http' ) || 0 === strpos( $src_result, '//' ) ) {
2816 continue;
2817 }
2818
2819 // Skip if the URL is an HTML ID.
2820 if ( str_starts_with( $src_result, '#' ) ) {
2821 continue;
2822 }
2823
2824 // Skip if the URL is a data URI.
2825 if ( str_starts_with( $src_result, 'data:' ) ) {
2826 continue;
2827 }
2828
2829 // Build the absolute URL.
2830 $absolute_url = dirname( $stylesheet_url ) . '/' . $src_result;
2831 $absolute_url = str_replace( '/./', '/', $absolute_url );
2832 // Convert to URL related to the site root.
2833 $relative_url = wp_make_link_relative( $absolute_url );
2834
2835 // Replace the URL in the CSS.
2836 $css = str_replace(
2837 $src_results[0][ $src_index ],
2838 str_replace( $src_result, $relative_url, $src_results[0][ $src_index ] ),
2839 $css
2840 );
2841 }
2842 }
2843
2844 return $css;
2845}
2846
2847/**
2848 * Inject the block editor assets that need to be loaded into the editor's iframe as an inline script.
2849 *
2850 * @since 5.8.0
2851 */
2852function wp_add_iframed_editor_assets_html() {
2853 global $pagenow;
2854
2855 if ( ! wp_should_load_block_editor_scripts_and_styles() ) {
2856 return;
2857 }
2858
2859 $script_handles = array();
2860 $style_handles = array(
2861 'wp-block-editor',
2862 'wp-block-library',
2863 'wp-block-library-theme',
2864 'wp-edit-blocks',
2865 );
2866
2867 if ( 'widgets.php' === $pagenow || 'customize.php' === $pagenow ) {
2868 $style_handles[] = 'wp-widgets';
2869 $style_handles[] = 'wp-edit-widgets';
2870 }
2871
2872 $block_registry = WP_Block_Type_Registry::get_instance();
2873
2874 foreach ( $block_registry->get_all_registered() as $block_type ) {
2875 if ( ! empty( $block_type->style ) ) {
2876 $style_handles[] = $block_type->style;
2877 }
2878
2879 if ( ! empty( $block_type->editor_style ) ) {
2880 $style_handles[] = $block_type->editor_style;
2881 }
2882
2883 if ( ! empty( $block_type->script ) ) {
2884 $script_handles[] = $block_type->script;
2885 }
2886 }
2887
2888 $style_handles = array_unique( $style_handles );
2889 $done = wp_styles()->done;
2890
2891 ob_start();
2892
2893 // We do not need reset styles for the iframed editor.
2894 wp_styles()->done = array( 'wp-reset-editor-styles' );
2895 wp_styles()->do_items( $style_handles );
2896 wp_styles()->done = $done;
2897
2898 $styles = ob_get_clean();
2899
2900 $script_handles = array_unique( $script_handles );
2901 $done = wp_scripts()->done;
2902
2903 ob_start();
2904
2905 wp_scripts()->done = array();
2906 wp_scripts()->do_items( $script_handles );
2907 wp_scripts()->done = $done;
2908
2909 $scripts = ob_get_clean();
2910
2911 $editor_assets = wp_json_encode(
2912 array(
2913 'styles' => $styles,
2914 'scripts' => $scripts,
2915 )
2916 );
2917
2918 echo "<script>window.__editorAssets = $editor_assets</script>";
2919}
2920
2921/**
2922 * Function that enqueues the CSS Custom Properties coming from theme.json.
2923 *
2924 * @since 5.9.0
2925 */
2926function wp_enqueue_global_styles_css_custom_properties() {
2927 wp_register_style( 'global-styles-css-custom-properties', false, array(), true, true );
2928 wp_add_inline_style( 'global-styles-css-custom-properties', wp_get_global_stylesheet( array( 'variables' ) ) );
2929 wp_enqueue_style( 'global-styles-css-custom-properties' );
2930}
2931
2932/**
2933 * This function takes care of adding inline styles
2934 * in the proper place, depending on the theme in use.
2935 *
2936 * @since 5.9.1
2937 *
2938 * For block themes, it's loaded in the head.
2939 * For classic ones, it's loaded in the body
2940 * because the wp_head action happens before
2941 * the render_block.
2942 *
2943 * @link https://core.trac.wordpress.org/ticket/53494.
2944 *
2945 * @param string $style String containing the CSS styles to be added.
2946 */
2947function wp_enqueue_block_support_styles( $style ) {
2948 $action_hook_name = 'wp_footer';
2949 if ( wp_is_block_theme() ) {
2950 $action_hook_name = 'wp_head';
2951 }
2952 add_action(
2953 $action_hook_name,
2954 static function () use ( $style ) {
2955 echo "<style>$style</style>\n";
2956 }
2957 );
2958}