Add Site Editor and PHP changes from Gutenberg 10.1 - 11.9
- First pass at adding the site editor from the Gutenberg plugin to wp-admin/site-editor.php. - Adds miscellaneous PHP changes from Gutenberg 10.1 - 11.9. Follows [52042]. See #54337. Props youknowriad, aristath, hellofromtonya, gziolo. Built from https://develop.svn.wordpress.org/trunk@52069 git-svn-id: http://core.svn.wordpress.org/trunk@51661 1a063a9b-81f0-0310-95a4-ce76da25c4cd
This commit is contained in:
parent
84dae82fd3
commit
c421e9b34a
|
@ -202,8 +202,24 @@ if ( ! is_multisite() && current_user_can( 'update_themes' ) ) {
|
|||
/* translators: %s: Number of available theme updates. */
|
||||
$submenu['themes.php'][5] = array( sprintf( __( 'Themes %s' ), $count ), $appearance_cap, 'themes.php' );
|
||||
|
||||
if ( wp_is_block_template_theme() ) {
|
||||
$submenu['themes.php'][6] = array(
|
||||
sprintf(
|
||||
/* translators: %s: "beta" label */
|
||||
__( 'Editor %s' ),
|
||||
'<span class="awaiting-mod">' . __( 'beta' ) . '</span>'
|
||||
),
|
||||
'edit_theme_options',
|
||||
'site-editor.php',
|
||||
);
|
||||
}
|
||||
|
||||
// Hide Customize link on block themes unless a plugin or theme is using
|
||||
// customize_register to add a setting.
|
||||
if ( ! wp_is_block_template_theme() || has_action( 'customize_register' ) ) {
|
||||
$customize_url = add_query_arg( 'return', urlencode( remove_query_arg( wp_removable_query_args(), wp_unslash( $_SERVER['REQUEST_URI'] ) ) ), 'customize.php' );
|
||||
$submenu['themes.php'][6] = array( __( 'Customize' ), 'customize', esc_url( $customize_url ), '', 'hide-if-no-customize' );
|
||||
$submenu['themes.php'][7] = array( __( 'Customize' ), 'customize', esc_url( $customize_url ), '', 'hide-if-no-customize' );
|
||||
}
|
||||
|
||||
if ( current_theme_supports( 'menus' ) || current_theme_supports( 'widgets' ) ) {
|
||||
$submenu['themes.php'][10] = array( __( 'Menus' ), 'edit_theme_options', 'nav-menus.php' );
|
||||
|
|
|
@ -0,0 +1,115 @@
|
|||
<?php
|
||||
/**
|
||||
* Site Editor administration screen.
|
||||
*
|
||||
* @package WordPress
|
||||
* @subpackage Administration
|
||||
*/
|
||||
|
||||
global $post, $editor_styles;
|
||||
|
||||
/** WordPress Administration Bootstrap */
|
||||
require_once __DIR__ . '/admin.php';
|
||||
|
||||
if ( ! current_user_can( 'edit_theme_options' ) ) {
|
||||
wp_die(
|
||||
'<h1>' . __( 'You need a higher level of permission.' ) . '</h1>' .
|
||||
'<p>' . __( 'Sorry, you are not allowed to edit theme options on this site.' ) . '</p>',
|
||||
403
|
||||
);
|
||||
}
|
||||
|
||||
if ( ! wp_is_block_template_theme() ) {
|
||||
wp_die( __( 'The theme you are currently using is not compatible with Full Site Editing.' ) );
|
||||
}
|
||||
|
||||
// Used in the HTML title tag.
|
||||
$title = __( 'Editor (beta)' );
|
||||
$parent_file = 'themes.php';
|
||||
|
||||
// Flag that we're loading the block editor.
|
||||
$current_screen = get_current_screen();
|
||||
$current_screen->is_block_editor( true );
|
||||
|
||||
$block_editor_context = new WP_Block_Editor_Context();
|
||||
|
||||
$active_global_styles_id = WP_Theme_JSON_Resolver::get_user_custom_post_type_id();
|
||||
$active_theme = wp_get_theme()->get_stylesheet();
|
||||
$preload_paths = array(
|
||||
array( '/wp/v2/media', 'OPTIONS' ),
|
||||
'/',
|
||||
'/wp/v2/types?context=edit',
|
||||
'/wp/v2/taxonomies?context=edit',
|
||||
'/wp/v2/pages?context=edit',
|
||||
'/wp/v2/categories?context=edit',
|
||||
'/wp/v2/posts?context=edit',
|
||||
'/wp/v2/tags?context=edit',
|
||||
'/wp/v2/templates?context=edit',
|
||||
'/wp/v2/template-parts?context=edit',
|
||||
'/wp/v2/settings',
|
||||
'/wp/v2/themes?context=edit&status=active',
|
||||
'/wp/v2/global-styles/' . $active_global_styles_id . '?context=edit',
|
||||
'/wp/v2/global-styles/' . $active_global_styles_id,
|
||||
'/wp/v2/themes/' . $active_theme . '/global-styles',
|
||||
);
|
||||
block_editor_rest_api_preload( $preload_paths, $block_editor_context );
|
||||
|
||||
$editor_settings = get_block_editor_settings(
|
||||
array(
|
||||
'siteUrl' => site_url(),
|
||||
'postsPerPage' => get_option( 'posts_per_page' ),
|
||||
'styles' => get_block_editor_theme_styles(),
|
||||
'defaultTemplateTypes' => get_default_block_template_types(),
|
||||
'defaultTemplatePartAreas' => get_allowed_block_template_part_areas(),
|
||||
'__experimentalBlockPatterns' => WP_Block_Patterns_Registry::get_instance()->get_all_registered(),
|
||||
'__experimentalBlockPatternCategories' => WP_Block_Pattern_Categories_Registry::get_instance()->get_all_registered(),
|
||||
),
|
||||
$block_editor_context
|
||||
);
|
||||
|
||||
wp_add_inline_script(
|
||||
'wp-edit-site',
|
||||
sprintf(
|
||||
'wp.domReady( function() {
|
||||
wp.editSite.initialize( "site-editor", %s );
|
||||
} );',
|
||||
wp_json_encode( $editor_settings )
|
||||
)
|
||||
);
|
||||
|
||||
// Preload server-registered block schemas.
|
||||
wp_add_inline_script(
|
||||
'wp-blocks',
|
||||
'wp.blocks.unstable__bootstrapServerSideBlockDefinitions(' . wp_json_encode( get_block_editor_server_block_settings() ) . ');'
|
||||
);
|
||||
|
||||
wp_add_inline_script(
|
||||
'wp-blocks',
|
||||
sprintf( 'wp.blocks.setCategories( %s );', wp_json_encode( get_block_categories( $post ) ) ),
|
||||
'after'
|
||||
);
|
||||
|
||||
wp_enqueue_script( 'wp-edit-site' );
|
||||
wp_enqueue_script( 'wp-format-library' );
|
||||
wp_enqueue_style( 'wp-edit-site' );
|
||||
wp_enqueue_style( 'wp-format-library' );
|
||||
wp_enqueue_media();
|
||||
|
||||
if (
|
||||
current_theme_supports( 'wp-block-styles' ) ||
|
||||
( ! is_array( $editor_styles ) || count( $editor_styles ) === 0 )
|
||||
) {
|
||||
wp_enqueue_style( 'wp-block-library-theme' );
|
||||
}
|
||||
|
||||
/** This action is documented in wp-admin/edit-form-blocks.php */
|
||||
do_action( 'enqueue_block_editor_assets' );
|
||||
|
||||
require_once ABSPATH . 'wp-admin/admin-header.php';
|
||||
?>
|
||||
|
||||
<div id="site-editor" class="edit-site"></div>
|
||||
|
||||
<?php
|
||||
|
||||
require_once ABSPATH . 'wp-admin/admin-footer.php';
|
File diff suppressed because one or more lines are too long
|
@ -9,7 +9,7 @@ return array(
|
|||
'title' => _x( 'Image at left', 'Block pattern title' ),
|
||||
'blockTypes' => array( 'core/query' ),
|
||||
'categories' => array( 'query' ),
|
||||
'content' => '<!-- wp:query {"query":{"perPage":1,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
'content' => '<!-- wp:query {"query":{"perPage":3,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
<div class="wp-block-query">
|
||||
<!-- wp:post-template -->
|
||||
<!-- wp:columns {"align":"wide"} -->
|
||||
|
|
|
@ -9,7 +9,7 @@ return array(
|
|||
'title' => _x( 'Small image and title', 'Block pattern title' ),
|
||||
'blockTypes' => array( 'core/query' ),
|
||||
'categories' => array( 'query' ),
|
||||
'content' => '<!-- wp:query {"query":{"perPage":1,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
'content' => '<!-- wp:query {"query":{"perPage":3,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
<div class="wp-block-query">
|
||||
<!-- wp:post-template -->
|
||||
<!-- wp:columns {"verticalAlignment":"center"} -->
|
||||
|
|
|
@ -9,7 +9,7 @@ return array(
|
|||
'title' => _x( 'Standard', 'Block pattern title' ),
|
||||
'blockTypes' => array( 'core/query' ),
|
||||
'categories' => array( 'query' ),
|
||||
'content' => '<!-- wp:query {"query":{"perPage":1,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
'content' => '<!-- wp:query {"query":{"perPage":3,"pages":0,"offset":0,"postType":"post","categoryIds":[],"tagIds":[],"order":"desc","orderBy":"date","author":"","search":"","exclude":[],"sticky":"","inherit":false}} -->
|
||||
<div class="wp-block-query">
|
||||
<!-- wp:post-template -->
|
||||
<!-- wp:post-title {"isLink":true} /-->
|
||||
|
|
|
@ -63,8 +63,23 @@ function wp_apply_border_support( $block_type, $block_attributes ) {
|
|||
wp_has_border_feature_support( $block_type, 'radius' ) &&
|
||||
isset( $block_attributes['style']['border']['radius'] )
|
||||
) {
|
||||
$border_radius = (int) $block_attributes['style']['border']['radius'];
|
||||
$styles[] = sprintf( 'border-radius: %dpx;', $border_radius );
|
||||
$border_radius = $block_attributes['style']['border']['radius'];
|
||||
|
||||
if ( is_array( $border_radius ) ) {
|
||||
// We have individual border radius corner values.
|
||||
foreach ( $border_radius as $key => $radius ) {
|
||||
// Convert CamelCase corner name to kebab-case.
|
||||
$corner = strtolower( preg_replace( '/(?<!^)[A-Z]/', '-$0', $key ) );
|
||||
$styles[] = sprintf( 'border-%s-radius: %s;', $corner, $radius );
|
||||
}
|
||||
} else {
|
||||
// This check handles original unitless implementation.
|
||||
if ( is_numeric( $border_radius ) ) {
|
||||
$border_radius .= 'px';
|
||||
}
|
||||
|
||||
$styles[] = sprintf( 'border-radius: %s;', $border_radius );
|
||||
}
|
||||
}
|
||||
|
||||
// Border style.
|
||||
|
@ -81,8 +96,14 @@ function wp_apply_border_support( $block_type, $block_attributes ) {
|
|||
wp_has_border_feature_support( $block_type, 'width' ) &&
|
||||
isset( $block_attributes['style']['border']['width'] )
|
||||
) {
|
||||
$border_width = intval( $block_attributes['style']['border']['width'] );
|
||||
$styles[] = sprintf( 'border-width: %dpx;', $border_width );
|
||||
$border_width = $block_attributes['style']['border']['width'];
|
||||
|
||||
// This check handles original unitless implementation.
|
||||
if ( is_numeric( $border_width ) ) {
|
||||
$border_width .= 'px';
|
||||
}
|
||||
|
||||
$styles[] = sprintf( 'border-width: %s;', $border_width );
|
||||
}
|
||||
|
||||
// Border color.
|
||||
|
|
|
@ -99,7 +99,7 @@ function wp_apply_colors_support( $block_type, $block_attributes ) {
|
|||
}
|
||||
// Apply color class or inline style.
|
||||
if ( $has_named_text_color ) {
|
||||
$classes[] = sprintf( 'has-%s-color', $block_attributes['textColor'] );
|
||||
$classes[] = sprintf( 'has-%s-color', _wp_to_kebab_case( $block_attributes['textColor'] ) );
|
||||
} elseif ( $has_custom_text_color ) {
|
||||
$styles[] = sprintf( 'color: %s;', $block_attributes['style']['color']['text'] );
|
||||
}
|
||||
|
@ -116,7 +116,7 @@ function wp_apply_colors_support( $block_type, $block_attributes ) {
|
|||
}
|
||||
// Apply background color classes or styles.
|
||||
if ( $has_named_background_color ) {
|
||||
$classes[] = sprintf( 'has-%s-background-color', $block_attributes['backgroundColor'] );
|
||||
$classes[] = sprintf( 'has-%s-background-color', _wp_to_kebab_case( $block_attributes['backgroundColor'] ) );
|
||||
} elseif ( $has_custom_background_color ) {
|
||||
$styles[] = sprintf( 'background-color: %s;', $block_attributes['style']['color']['background'] );
|
||||
}
|
||||
|
@ -132,7 +132,7 @@ function wp_apply_colors_support( $block_type, $block_attributes ) {
|
|||
}
|
||||
// Apply required background class.
|
||||
if ( $has_named_gradient ) {
|
||||
$classes[] = sprintf( 'has-%s-gradient-background', $block_attributes['gradient'] );
|
||||
$classes[] = sprintf( 'has-%s-gradient-background', _wp_to_kebab_case( $block_attributes['gradient'] ) );
|
||||
} elseif ( $has_custom_gradient ) {
|
||||
$styles[] = sprintf( 'background: %s;', $block_attributes['style']['color']['gradient'] );
|
||||
}
|
||||
|
|
|
@ -0,0 +1,92 @@
|
|||
<?php
|
||||
/**
|
||||
* Dimensions block support flag.
|
||||
*
|
||||
* This does not include the `spacing` block support even though that visually
|
||||
* appears under the "Dimensions" panel in the editor. It remains in its
|
||||
* original `spacing.php` file for backwards compatibility.
|
||||
*
|
||||
* @package WordPress
|
||||
* @since 5.9.0
|
||||
*/
|
||||
|
||||
/**
|
||||
* Registers the style block attribute for block types that support it.
|
||||
*
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param WP_Block_Type $block_type Block Type.
|
||||
*/
|
||||
function wp_register_dimensions_support( $block_type ) {
|
||||
// Setup attributes and styles within that if needed.
|
||||
if ( ! $block_type->attributes ) {
|
||||
$block_type->attributes = array();
|
||||
}
|
||||
|
||||
// Check for existing style attribute definition e.g. from block.json.
|
||||
if ( array_key_exists( 'style', $block_type->attributes ) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$has_dimensions_support = block_has_support( $block_type, array( '__experimentalDimensions' ), false );
|
||||
// Future block supports such as height & width will be added here.
|
||||
|
||||
if ( $has_dimensions_support ) {
|
||||
$block_type->attributes['style'] = array(
|
||||
'type' => 'object',
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Add CSS classes for block dimensions to the incoming attributes array.
|
||||
* This will be applied to the block markup in the front-end.
|
||||
*
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param WP_Block_Type $block_type Block Type.
|
||||
* @param array $block_attributes Block attributes.
|
||||
*
|
||||
* @return array Block dimensions CSS classes and inline styles.
|
||||
*/
|
||||
function wp_apply_dimensions_support( $block_type, $block_attributes ) { // phpcs:ignore VariableAnalysis.CodeAnalysis.VariableAnalysis.UnusedVariable
|
||||
if ( wp_skip_dimensions_serialization( $block_type ) ) {
|
||||
return array();
|
||||
}
|
||||
|
||||
$styles = array();
|
||||
|
||||
// Height support to be added in near future.
|
||||
// Width support to be added in near future.
|
||||
|
||||
return empty( $styles ) ? array() : array( 'style' => implode( ' ', $styles ) );
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks whether serialization of the current block's dimensions properties
|
||||
* should occur.
|
||||
*
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param WP_Block_type $block_type Block type.
|
||||
*
|
||||
* @return boolean Whether to serialize spacing support styles & classes.
|
||||
*/
|
||||
function wp_skip_dimensions_serialization( $block_type ) {
|
||||
$dimensions_support = _wp_array_get( $block_type->supports, array( '__experimentalDimensions' ), false );
|
||||
return is_array( $dimensions_support ) &&
|
||||
array_key_exists( '__experimentalSkipSerialization', $dimensions_support ) &&
|
||||
$dimensions_support['__experimentalSkipSerialization'];
|
||||
}
|
||||
|
||||
// Register the block support.
|
||||
WP_Block_Supports::get_instance()->register(
|
||||
'dimensions',
|
||||
array(
|
||||
'register_attribute' => 'wp_register_dimensions_support',
|
||||
'apply' => 'wp_apply_dimensions_support',
|
||||
)
|
||||
);
|
|
@ -266,7 +266,7 @@ function wp_tinycolor_string_to_rgb( $color_str ) {
|
|||
|
||||
$hsla_regexp = '/^hsla' . $permissive_match4 . '$/';
|
||||
if ( preg_match( $hsla_regexp, $color_str, $match ) ) {
|
||||
return wp_tinycolor_hsl_to_rgb(
|
||||
$rgb = wp_tinycolor_hsl_to_rgb(
|
||||
array(
|
||||
'h' => $match[1],
|
||||
's' => $match[2],
|
||||
|
@ -384,13 +384,16 @@ function wp_register_duotone_support( $block_type ) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the duotone filter SVG and returns the CSS filter property to
|
||||
* reference the rendered SVG.
|
||||
*
|
||||
* @since 5.9.0
|
||||
*
|
||||
* @access private
|
||||
|
||||
* @param array $preset Duotone preset value as seen in theme.json.
|
||||
*
|
||||
* @return string Duotone CSS filter property.
|
||||
*/
|
||||
function wp_render_duotone_filter_preset( $preset ) {
|
||||
|
@ -460,13 +463,11 @@ function wp_render_duotone_filter_preset( $preset ) {
|
|||
}
|
||||
|
||||
add_action(
|
||||
/*
|
||||
* Safari doesn't render SVG filters defined in data URIs,
|
||||
* and SVG filters won't render in the head of a document,
|
||||
* so the next best place to put the SVG is in the footer.
|
||||
*/
|
||||
// Safari doesn't render SVG filters defined in data URIs,
|
||||
// and SVG filters won't render in the head of a document,
|
||||
// so the next best place to put the SVG is in the footer.
|
||||
is_admin() ? 'admin_footer' : 'wp_footer',
|
||||
static function () use ( $svg ) {
|
||||
function () use ( $svg ) {
|
||||
echo $svg;
|
||||
}
|
||||
);
|
||||
|
@ -502,84 +503,38 @@ function wp_render_duotone_support( $block_content, $block ) {
|
|||
return $block_content;
|
||||
}
|
||||
|
||||
$duotone_colors = $block['attrs']['style']['color']['duotone'];
|
||||
|
||||
$duotone_values = array(
|
||||
'r' => array(),
|
||||
'g' => array(),
|
||||
'b' => array(),
|
||||
$filter_preset = array(
|
||||
'slug' => uniqid(),
|
||||
'colors' => $block['attrs']['style']['color']['duotone'],
|
||||
);
|
||||
foreach ( $duotone_colors as $color_str ) {
|
||||
$color = wp_tinycolor_string_to_rgb( $color_str );
|
||||
$filter_property = wp_render_duotone_filter_preset( $filter_preset );
|
||||
$filter_id = 'wp-duotone-' . $filter_preset['slug'];
|
||||
|
||||
$duotone_values['r'][] = $color['r'] / 255;
|
||||
$duotone_values['g'][] = $color['g'] / 255;
|
||||
$duotone_values['b'][] = $color['b'] / 255;
|
||||
$scope = '.' . $filter_id;
|
||||
$selectors = explode( ',', $duotone_support );
|
||||
$scoped = array();
|
||||
foreach ( $selectors as $sel ) {
|
||||
$scoped[] = $scope . ' ' . trim( $sel );
|
||||
}
|
||||
$selector = implode( ', ', $scoped );
|
||||
|
||||
$duotone_id = 'wp-duotone-filter-' . uniqid();
|
||||
// !important is needed because these styles render before global styles,
|
||||
// and they should be overriding the duotone filters set by global styles.
|
||||
$filter_style = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG
|
||||
? $selector . " {\n\tfilter: " . $filter_property . " !important;\n}\n"
|
||||
: $selector . '{filter:' . $filter_property . ' !important;}';
|
||||
|
||||
$selectors = explode( ',', $duotone_support );
|
||||
$selectors_scoped = array_map(
|
||||
static function ( $selector ) use ( $duotone_id ) {
|
||||
return '.' . $duotone_id . ' ' . trim( $selector );
|
||||
},
|
||||
$selectors
|
||||
);
|
||||
$selectors_group = implode( ', ', $selectors_scoped );
|
||||
|
||||
ob_start();
|
||||
|
||||
?>
|
||||
|
||||
<style>
|
||||
<?php echo $selectors_group; ?> {
|
||||
filter: url( <?php echo esc_url( '#' . $duotone_id ); ?> );
|
||||
}
|
||||
</style>
|
||||
|
||||
<svg
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
viewBox="0 0 0 0"
|
||||
width="0"
|
||||
height="0"
|
||||
focusable="false"
|
||||
role="none"
|
||||
style="visibility: hidden; position: absolute; left: -9999px; overflow: hidden;"
|
||||
>
|
||||
<defs>
|
||||
<filter id="<?php echo esc_attr( $duotone_id ); ?>">
|
||||
<feColorMatrix
|
||||
type="matrix"
|
||||
<?php // phpcs:disable Generic.WhiteSpace.DisallowSpaceIndent ?>
|
||||
values=".299 .587 .114 0 0
|
||||
.299 .587 .114 0 0
|
||||
.299 .587 .114 0 0
|
||||
0 0 0 1 0"
|
||||
<?php // phpcs:enable Generic.WhiteSpace.DisallowSpaceIndent ?>
|
||||
/>
|
||||
<feComponentTransfer color-interpolation-filters="sRGB" >
|
||||
<feFuncR type="table" tableValues="<?php echo esc_attr( implode( ' ', $duotone_values['r'] ) ); ?>" />
|
||||
<feFuncG type="table" tableValues="<?php echo esc_attr( implode( ' ', $duotone_values['g'] ) ); ?>" />
|
||||
<feFuncB type="table" tableValues="<?php echo esc_attr( implode( ' ', $duotone_values['b'] ) ); ?>" />
|
||||
</feComponentTransfer>
|
||||
</filter>
|
||||
</defs>
|
||||
</svg>
|
||||
|
||||
<?php
|
||||
|
||||
$duotone = ob_get_clean();
|
||||
wp_register_style( $filter_id, false, array(), true, true );
|
||||
wp_add_inline_style( $filter_id, $filter_style );
|
||||
wp_enqueue_style( $filter_id );
|
||||
|
||||
// Like the layout hook, this assumes the hook only applies to blocks with a single wrapper.
|
||||
$content = preg_replace(
|
||||
return preg_replace(
|
||||
'/' . preg_quote( 'class="', '/' ) . '/',
|
||||
'class="' . $duotone_id . ' ',
|
||||
'class="' . $filter_id . ' ',
|
||||
$block_content,
|
||||
1
|
||||
);
|
||||
|
||||
return $content . $duotone;
|
||||
}
|
||||
|
||||
// Register the block support.
|
||||
|
|
|
@ -17,6 +17,10 @@
|
|||
* @return string Filtered block content.
|
||||
*/
|
||||
function wp_render_elements_support( $block_content, $block ) {
|
||||
if ( ! $block_content ) {
|
||||
return $block_content;
|
||||
}
|
||||
|
||||
$link_color = null;
|
||||
if ( ! empty( $block['attrs'] ) ) {
|
||||
$link_color = _wp_array_get( $block['attrs'], array( 'style', 'elements', 'link', 'color', 'text' ), null );
|
||||
|
@ -42,7 +46,7 @@ function wp_render_elements_support( $block_content, $block ) {
|
|||
}
|
||||
$link_color_declaration = esc_html( safecss_filter_attr( "color: $link_color" ) );
|
||||
|
||||
$style = "<style>.$class_name a{" . $link_color_declaration . " !important;}</style>\n";
|
||||
$style = "<style>.$class_name a{" . $link_color_declaration . ";}</style>\n";
|
||||
|
||||
// Like the layout hook this assumes the hook only applies to blocks with a single wrapper.
|
||||
// Retrieve the opening tag of the first HTML element.
|
||||
|
@ -64,8 +68,19 @@ function wp_render_elements_support( $block_content, $block ) {
|
|||
$content = substr_replace( $block_content, ' class="' . $class_name . '"', $first_element_offset + strlen( $first_element ) - 1, 0 );
|
||||
}
|
||||
|
||||
return $content . $style;
|
||||
/*
|
||||
* Ideally styles should be loaded in the head, but blocks may be parsed
|
||||
* after that, so loading in the footer for now.
|
||||
* See https://core.trac.wordpress.org/ticket/53494.
|
||||
*/
|
||||
add_action(
|
||||
'wp_footer',
|
||||
static function () use ( $style ) {
|
||||
echo $style;
|
||||
}
|
||||
);
|
||||
|
||||
return $content;
|
||||
}
|
||||
|
||||
add_filter( 'render_block', 'wp_render_elements_support', 10, 2 );
|
||||
|
|
|
@ -29,6 +29,106 @@ function wp_register_layout_support( $block_type ) {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates the CSS corresponding to the provided layout.
|
||||
*
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param string $selector CSS selector.
|
||||
* @param array $layout Layout object. The one that is passed has already checked the existance of default block layout.
|
||||
* @param boolean $has_block_gap_support Whether the theme has support for the block gap.
|
||||
*
|
||||
* @return string CSS style.
|
||||
*/
|
||||
function wp_get_layout_style( $selector, $layout, $has_block_gap_support = false ) {
|
||||
$layout_type = isset( $layout['type'] ) ? $layout['type'] : 'default';
|
||||
|
||||
$style = '';
|
||||
if ( 'default' === $layout_type ) {
|
||||
$content_size = isset( $layout['contentSize'] ) ? $layout['contentSize'] : null;
|
||||
$wide_size = isset( $layout['wideSize'] ) ? $layout['wideSize'] : null;
|
||||
|
||||
$all_max_width_value = $content_size ? $content_size : $wide_size;
|
||||
$wide_max_width_value = $wide_size ? $wide_size : $content_size;
|
||||
|
||||
// Make sure there is a single CSS rule, and all tags are stripped for security.
|
||||
// TODO: Use `safecss_filter_attr` instead - once https://core.trac.wordpress.org/ticket/46197 is patched.
|
||||
$all_max_width_value = wp_strip_all_tags( explode( ';', $all_max_width_value )[0] );
|
||||
$wide_max_width_value = wp_strip_all_tags( explode( ';', $wide_max_width_value )[0] );
|
||||
|
||||
$style = '';
|
||||
if ( $content_size || $wide_size ) {
|
||||
$style = "$selector > * {";
|
||||
$style .= 'max-width: ' . esc_html( $all_max_width_value ) . ';';
|
||||
$style .= 'margin-left: auto !important;';
|
||||
$style .= 'margin-right: auto !important;';
|
||||
$style .= '}';
|
||||
|
||||
$style .= "$selector > .alignwide { max-width: " . esc_html( $wide_max_width_value ) . ';}';
|
||||
$style .= "$selector .alignfull { max-width: none; }";
|
||||
}
|
||||
|
||||
$style .= "$selector .alignleft { float: left; margin-right: 2em; }";
|
||||
$style .= "$selector .alignright { float: right; margin-left: 2em; }";
|
||||
if ( $has_block_gap_support ) {
|
||||
$style .= "$selector > * { margin-top: 0; margin-bottom: 0; }";
|
||||
$style .= "$selector > * + * { margin-top: var( --wp--style--block-gap ); margin-bottom: 0; }";
|
||||
}
|
||||
} elseif ( 'flex' === $layout_type ) {
|
||||
$layout_orientation = isset( $layout['orientation'] ) ? $layout['orientation'] : 'horizontal';
|
||||
|
||||
$justify_content_options = array(
|
||||
'left' => 'flex-start',
|
||||
'right' => 'flex-end',
|
||||
'center' => 'center',
|
||||
);
|
||||
|
||||
if ( 'horizontal' === $layout_orientation ) {
|
||||
$justify_content_options += array( 'space-between' => 'space-between' );
|
||||
}
|
||||
|
||||
$flex_wrap_options = array( 'wrap', 'nowrap' );
|
||||
$flex_wrap = ! empty( $layout['flexWrap'] ) && in_array( $layout['flexWrap'], $flex_wrap_options, true ) ?
|
||||
$layout['flexWrap'] :
|
||||
'wrap';
|
||||
|
||||
$style = "$selector {";
|
||||
$style .= 'display: flex;';
|
||||
if ( $has_block_gap_support ) {
|
||||
$style .= 'gap: var( --wp--style--block-gap, 0.5em );';
|
||||
} else {
|
||||
$style .= 'gap: 0.5em;';
|
||||
}
|
||||
$style .= "flex-wrap: $flex_wrap;";
|
||||
$style .= 'align-items: center;';
|
||||
if ( 'horizontal' === $layout_orientation ) {
|
||||
$style .= 'align-items: center;';
|
||||
/**
|
||||
* Add this style only if is not empty for backwards compatibility,
|
||||
* since we intend to convert blocks that had flex layout implemented
|
||||
* by custom css.
|
||||
*/
|
||||
if ( ! empty( $layout['justifyContent'] ) && array_key_exists( $layout['justifyContent'], $justify_content_options ) ) {
|
||||
$style .= "justify-content: {$justify_content_options[ $layout['justifyContent'] ]};";
|
||||
// --justification-setting allows children to inherit the value regardless or row or column direction.
|
||||
$style .= "--justification-setting: {$justify_content_options[ $layout['justifyContent'] ]};";
|
||||
}
|
||||
} else {
|
||||
$style .= 'flex-direction: column;';
|
||||
if ( ! empty( $layout['justifyContent'] ) && array_key_exists( $layout['justifyContent'], $justify_content_options ) ) {
|
||||
$style .= "align-items: {$justify_content_options[ $layout['justifyContent'] ]};";
|
||||
$style .= "--justification-setting: {$justify_content_options[ $layout['justifyContent'] ]};";
|
||||
}
|
||||
}
|
||||
$style .= '}';
|
||||
|
||||
$style .= "$selector > * { margin: 0; }";
|
||||
}
|
||||
|
||||
return $style;
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the layout config to the block wrapper.
|
||||
*
|
||||
|
@ -42,47 +142,25 @@ function wp_register_layout_support( $block_type ) {
|
|||
function wp_render_layout_support_flag( $block_content, $block ) {
|
||||
$block_type = WP_Block_Type_Registry::get_instance()->get_registered( $block['blockName'] );
|
||||
$support_layout = block_has_support( $block_type, array( '__experimentalLayout' ), false );
|
||||
if ( ! $support_layout || ! isset( $block['attrs']['layout'] ) ) {
|
||||
|
||||
if ( ! $support_layout ) {
|
||||
return $block_content;
|
||||
}
|
||||
|
||||
$used_layout = $block['attrs']['layout'];
|
||||
$block_gap = wp_get_global_settings( array( 'spacing', 'blockGap' ) );
|
||||
$default_layout = wp_get_global_settings( array( 'layout' ) );
|
||||
$has_block_gap_support = isset( $block_gap ) ? null !== $block_gap : false;
|
||||
$default_block_layout = _wp_array_get( $block_type->supports, array( '__experimentalLayout', 'default' ), array() );
|
||||
$used_layout = isset( $block['attrs']['layout'] ) ? $block['attrs']['layout'] : $default_block_layout;
|
||||
if ( isset( $used_layout['inherit'] ) && $used_layout['inherit'] ) {
|
||||
$tree = WP_Theme_JSON_Resolver::get_merged_data();
|
||||
$default_layout = _wp_array_get( $tree->get_settings(), array( 'layout' ) );
|
||||
if ( ! $default_layout ) {
|
||||
return $block_content;
|
||||
}
|
||||
$used_layout = $default_layout;
|
||||
}
|
||||
|
||||
$id = uniqid();
|
||||
$content_size = isset( $used_layout['contentSize'] ) ? $used_layout['contentSize'] : null;
|
||||
$wide_size = isset( $used_layout['wideSize'] ) ? $used_layout['wideSize'] : null;
|
||||
|
||||
$all_max_width_value = $content_size ? $content_size : $wide_size;
|
||||
$wide_max_width_value = $wide_size ? $wide_size : $content_size;
|
||||
|
||||
// Make sure there is a single CSS rule, and all tags are stripped for security.
|
||||
$all_max_width_value = safecss_filter_attr( explode( ';', $all_max_width_value )[0] );
|
||||
$wide_max_width_value = safecss_filter_attr( explode( ';', $wide_max_width_value )[0] );
|
||||
|
||||
$style = '';
|
||||
if ( $content_size || $wide_size ) {
|
||||
$style = ".wp-container-$id > * {";
|
||||
$style .= 'max-width: ' . esc_html( $all_max_width_value ) . ';';
|
||||
$style .= 'margin-left: auto !important;';
|
||||
$style .= 'margin-right: auto !important;';
|
||||
$style .= '}';
|
||||
|
||||
$style .= ".wp-container-$id > .alignwide { max-width: " . esc_html( $wide_max_width_value ) . ';}';
|
||||
|
||||
$style .= ".wp-container-$id .alignfull { max-width: none; }";
|
||||
}
|
||||
|
||||
$style .= ".wp-container-$id .alignleft { float: left; margin-right: 2em; }";
|
||||
$style .= ".wp-container-$id .alignright { float: right; margin-left: 2em; }";
|
||||
|
||||
$id = uniqid();
|
||||
$style = wp_get_layout_style( ".wp-container-$id", $used_layout, $has_block_gap_support );
|
||||
// This assumes the hook only applies to blocks with a single wrapper.
|
||||
// I think this is a reasonable limitation for that particular hook.
|
||||
$content = preg_replace(
|
||||
|
@ -92,7 +170,19 @@ function wp_render_layout_support_flag( $block_content, $block ) {
|
|||
1
|
||||
);
|
||||
|
||||
return $content . '<style>' . $style . '</style>';
|
||||
/*
|
||||
* Ideally styles should be loaded in the head, but blocks may be parsed
|
||||
* after that, so loading in the footer for now.
|
||||
* See https://core.trac.wordpress.org/ticket/53494.
|
||||
*/
|
||||
add_action(
|
||||
'wp_footer',
|
||||
static function () use ( $style ) {
|
||||
echo '<style>' . $style . '</style>';
|
||||
}
|
||||
);
|
||||
|
||||
return $content;
|
||||
}
|
||||
|
||||
// Register the block support.
|
||||
|
@ -123,7 +213,8 @@ function wp_restore_group_inner_container( $block_content, $block ) {
|
|||
if (
|
||||
'core/group' !== $block['blockName'] ||
|
||||
WP_Theme_JSON_Resolver::theme_has_support() ||
|
||||
1 === preg_match( $group_with_inner_container_regex, $block_content )
|
||||
1 === preg_match( $group_with_inner_container_regex, $block_content ) ||
|
||||
( isset( $block['attrs']['layout']['type'] ) && 'default' !== $block['attrs']['layout']['type'] )
|
||||
) {
|
||||
return $block_content;
|
||||
}
|
||||
|
|
|
@ -1,6 +1,9 @@
|
|||
<?php
|
||||
/**
|
||||
* Spacing block support flag.
|
||||
|
||||
* For backwards compatibility, this remains separate to the dimensions.php
|
||||
* block support despite both belonging under a single panel in the editor.
|
||||
*
|
||||
* @package WordPress
|
||||
* @since 5.8.0
|
||||
|
@ -42,25 +45,33 @@ function wp_register_spacing_support( $block_type ) {
|
|||
* @return array Block spacing CSS classes and inline styles.
|
||||
*/
|
||||
function wp_apply_spacing_support( $block_type, $block_attributes ) {
|
||||
$has_padding_support = wp_has_spacing_feature_support( $block_type, 'padding' );
|
||||
$has_margin_support = wp_has_spacing_feature_support( $block_type, 'margin' );
|
||||
if ( wp_skip_spacing_serialization( $block_type ) ) {
|
||||
return array();
|
||||
}
|
||||
|
||||
$has_padding_support = block_has_support( $block_type, array( 'spacing', 'padding' ), false );
|
||||
$has_margin_support = block_has_support( $block_type, array( 'spacing', 'margin' ), false );
|
||||
$styles = array();
|
||||
|
||||
if ( $has_padding_support ) {
|
||||
$padding_value = _wp_array_get( $block_attributes, array( 'style', 'spacing', 'padding' ), null );
|
||||
if ( null !== $padding_value ) {
|
||||
if ( is_array( $padding_value ) ) {
|
||||
foreach ( $padding_value as $key => $value ) {
|
||||
$styles[] = sprintf( 'padding-%s: %s;', $key, $value );
|
||||
}
|
||||
} elseif ( null !== $padding_value ) {
|
||||
$styles[] = sprintf( 'padding: %s;', $padding_value );
|
||||
}
|
||||
}
|
||||
|
||||
if ( $has_margin_support ) {
|
||||
$margin_value = _wp_array_get( $block_attributes, array( 'style', 'spacing', 'margin' ), null );
|
||||
if ( null !== $margin_value ) {
|
||||
if ( is_array( $margin_value ) ) {
|
||||
foreach ( $margin_value as $key => $value ) {
|
||||
$styles[] = sprintf( 'margin-%s: %s;', $key, $value );
|
||||
}
|
||||
} elseif ( null !== $margin_value ) {
|
||||
$styles[] = sprintf( 'margin: %s;', $margin_value );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -68,20 +79,75 @@ function wp_apply_spacing_support( $block_type, $block_attributes ) {
|
|||
}
|
||||
|
||||
/**
|
||||
* Checks whether the current block type supports the spacing feature requested.
|
||||
* Checks whether serialization of the current block's spacing properties should
|
||||
* occur.
|
||||
*
|
||||
* @since 5.8.0
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param WP_Block_Type $block_type Block type to check for support.
|
||||
* @param string $feature Name of the feature to check support for.
|
||||
* @param mixed $default Fallback value for feature support. Default false.
|
||||
* @return bool Whether the feature is supported.
|
||||
* @param WP_Block_Type $block_type Block type.
|
||||
*
|
||||
* @return boolean Whether to serialize spacing support styles & classes.
|
||||
*/
|
||||
function wp_has_spacing_feature_support( $block_type, $feature, $default = false ) {
|
||||
// Check if the specific feature has been opted into individually
|
||||
// via nested flag under `spacing`.
|
||||
return block_has_support( $block_type, array( 'spacing', $feature ), $default );
|
||||
function wp_skip_spacing_serialization( $block_type ) {
|
||||
$spacing_support = _wp_array_get( $block_type->supports, array( 'spacing' ), false );
|
||||
|
||||
return is_array( $spacing_support ) &&
|
||||
array_key_exists( '__experimentalSkipSerialization', $spacing_support ) &&
|
||||
$spacing_support['__experimentalSkipSerialization'];
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the spacing gap support to the block wrapper, to ensure
|
||||
* that the CSS variable is rendered in all environments.
|
||||
*
|
||||
* @since 5.9.0
|
||||
* @access private
|
||||
*
|
||||
* @param string $block_content Rendered block content.
|
||||
* @param array $block Block object.
|
||||
* @return string Filtered block content.
|
||||
*/
|
||||
function wp_render_spacing_gap_support( $block_content, $block ) {
|
||||
$block_type = WP_Block_Type_Registry::get_instance()->get_registered( $block['blockName'] );
|
||||
$has_gap_support = block_has_support( $block_type, array( 'spacing', 'blockGap' ), false );
|
||||
if ( ! $has_gap_support || ! isset( $block['attrs']['style']['spacing']['blockGap'] ) ) {
|
||||
return $block_content;
|
||||
}
|
||||
|
||||
$gap_value = $block['attrs']['style']['spacing']['blockGap'];
|
||||
|
||||
// Skip if gap value contains unsupported characters.
|
||||
// Regex for CSS value borrowed from `safecss_filter_attr`, and used here
|
||||
// because we only want to match against the value, not the CSS attribute.
|
||||
if ( preg_match( '%[\\\(&=}]|/\*%', $gap_value ) ) {
|
||||
return $block_content;
|
||||
}
|
||||
|
||||
$style = sprintf(
|
||||
'--wp--style--block-gap: %s',
|
||||
esc_attr( $gap_value )
|
||||
);
|
||||
|
||||
// Attempt to update an existing style attribute on the wrapper element.
|
||||
$injected_style = preg_replace(
|
||||
'/^([^>.]+?)(' . preg_quote( 'style="', '/' ) . ')(?=.+?>)/',
|
||||
'$1$2' . $style . '; ',
|
||||
$block_content,
|
||||
1
|
||||
);
|
||||
|
||||
// If there is no existing style attribute, add one to the wrapper element.
|
||||
if ( $injected_style === $block_content ) {
|
||||
$injected_style = preg_replace(
|
||||
'/<([a-zA-Z0-9]+)([ >])/',
|
||||
'<$1 style="' . $style . '"$2',
|
||||
$block_content,
|
||||
1
|
||||
);
|
||||
};
|
||||
|
||||
return $injected_style;
|
||||
}
|
||||
|
||||
// Register the block support.
|
||||
|
@ -92,3 +158,5 @@ WP_Block_Supports::get_instance()->register(
|
|||
'apply' => 'wp_apply_spacing_support',
|
||||
)
|
||||
);
|
||||
|
||||
add_filter( 'render_block', 'wp_render_spacing_gap_support', 10, 2 );
|
||||
|
|
|
@ -28,6 +28,7 @@ function wp_register_typography_support( $block_type ) {
|
|||
$has_font_size_support = _wp_array_get( $typography_supports, array( 'fontSize' ), false );
|
||||
$has_font_style_support = _wp_array_get( $typography_supports, array( '__experimentalFontStyle' ), false );
|
||||
$has_font_weight_support = _wp_array_get( $typography_supports, array( '__experimentalFontWeight' ), false );
|
||||
$has_letter_spacing_support = _wp_array_get( $typography_supports, array( '__experimentalLetterSpacing' ), false );
|
||||
$has_line_height_support = _wp_array_get( $typography_supports, array( 'lineHeight' ), false );
|
||||
$has_text_decoration_support = _wp_array_get( $typography_supports, array( '__experimentalTextDecoration' ), false );
|
||||
$has_text_transform_support = _wp_array_get( $typography_supports, array( '__experimentalTextTransform' ), false );
|
||||
|
@ -36,6 +37,7 @@ function wp_register_typography_support( $block_type ) {
|
|||
|| $has_font_size_support
|
||||
|| $has_font_style_support
|
||||
|| $has_font_weight_support
|
||||
|| $has_letter_spacing_support
|
||||
|| $has_line_height_support
|
||||
|| $has_text_decoration_support
|
||||
|| $has_text_transform_support;
|
||||
|
@ -93,6 +95,7 @@ function wp_apply_typography_support( $block_type, $block_attributes ) {
|
|||
$has_font_size_support = _wp_array_get( $typography_supports, array( 'fontSize' ), false );
|
||||
$has_font_style_support = _wp_array_get( $typography_supports, array( '__experimentalFontStyle' ), false );
|
||||
$has_font_weight_support = _wp_array_get( $typography_supports, array( '__experimentalFontWeight' ), false );
|
||||
$has_letter_spacing_support = _wp_array_get( $typography_supports, array( '__experimentalLetterSpacing' ), false );
|
||||
$has_line_height_support = _wp_array_get( $typography_supports, array( 'lineHeight' ), false );
|
||||
$has_text_decoration_support = _wp_array_get( $typography_supports, array( '__experimentalTextDecoration' ), false );
|
||||
$has_text_transform_support = _wp_array_get( $typography_supports, array( '__experimentalTextTransform' ), false );
|
||||
|
@ -102,24 +105,28 @@ function wp_apply_typography_support( $block_type, $block_attributes ) {
|
|||
$has_custom_font_size = isset( $block_attributes['style']['typography']['fontSize'] );
|
||||
|
||||
if ( $has_named_font_size ) {
|
||||
$classes[] = sprintf( 'has-%s-font-size', $block_attributes['fontSize'] );
|
||||
$classes[] = sprintf( 'has-%s-font-size', _wp_to_kebab_case( $block_attributes['fontSize'] ) );
|
||||
} elseif ( $has_custom_font_size ) {
|
||||
$styles[] = sprintf( 'font-size: %s;', $block_attributes['style']['typography']['fontSize'] );
|
||||
}
|
||||
}
|
||||
|
||||
if ( $has_font_family_support ) {
|
||||
$has_font_family = isset( $block_attributes['style']['typography']['fontFamily'] );
|
||||
if ( $has_font_family ) {
|
||||
$font_family = $block_attributes['style']['typography']['fontFamily'];
|
||||
if ( strpos( $font_family, 'var:preset|font-family' ) !== false ) {
|
||||
// Get the name from the string and add proper styles.
|
||||
$index_to_splice = strrpos( $font_family, '|' ) + 1;
|
||||
$font_family_name = substr( $font_family, $index_to_splice );
|
||||
$styles[] = sprintf( 'font-family: var(--wp--preset--font-family--%s);', $font_family_name );
|
||||
} else {
|
||||
$styles[] = sprintf( 'font-family: %s;', $block_attributes['style']['typography']['fontFamily'] );
|
||||
$has_named_font_family = array_key_exists( 'fontFamily', $block_attributes );
|
||||
$has_custom_font_family = isset( $block_attributes['style']['typography']['fontFamily'] );
|
||||
|
||||
if ( $has_named_font_family ) {
|
||||
$classes[] = sprintf( 'has-%s-font-family', _wp_to_kebab_case( $block_attributes['fontFamily'] ) );
|
||||
} elseif ( $has_custom_font_family ) {
|
||||
// Before using classes, the value was serialized as a CSS Custom Property.
|
||||
// We don't need this code path when it lands in core.
|
||||
$font_family_custom = $block_attributes['style']['typography']['fontFamily'];
|
||||
if ( strpos( $font_family_custom, 'var:preset|font-family' ) !== false ) {
|
||||
$index_to_splice = strrpos( $font_family_custom, '|' ) + 1;
|
||||
$font_family_slug = _wp_to_kebab_case( substr( $font_family_custom, $index_to_splice ) );
|
||||
$font_family_custom = sprintf( 'var(--wp--preset--font-family--%s)', $font_family_slug );
|
||||
}
|
||||
$styles[] = sprintf( 'font-family: %s;', $font_family_custom );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -158,6 +165,13 @@ function wp_apply_typography_support( $block_type, $block_attributes ) {
|
|||
}
|
||||
}
|
||||
|
||||
if ( $has_letter_spacing_support ) {
|
||||
$letter_spacing_style = wp_typography_get_css_variable_inline_style( $block_attributes, 'letterSpacing', 'letter-spacing' );
|
||||
if ( $letter_spacing_style ) {
|
||||
$styles[] = $letter_spacing_style;
|
||||
}
|
||||
}
|
||||
|
||||
if ( ! empty( $classes ) ) {
|
||||
$attributes['class'] = implode( ' ', $classes );
|
||||
}
|
||||
|
|
|
@ -1182,3 +1182,117 @@ function get_query_pagination_arrow( $block, $is_next ) {
|
|||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Enqueue a stylesheet for a specific block.
|
||||
*
|
||||
* If the theme has opted-in to separate-styles loading,
|
||||
* then the stylesheet will be enqueued on-render,
|
||||
* otherwise when the block inits.
|
||||
*
|
||||
* @param string $block_name The block-name, including namespace.
|
||||
* @param array $args An array of arguments [handle,src,deps,ver,media].
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function wp_enqueue_block_style( $block_name, $args ) {
|
||||
$args = wp_parse_args(
|
||||
$args,
|
||||
array(
|
||||
'handle' => '',
|
||||
'src' => '',
|
||||
'deps' => array(),
|
||||
'ver' => false,
|
||||
'media' => 'all',
|
||||
)
|
||||
);
|
||||
|
||||
/**
|
||||
* Callback function to register and enqueue styles.
|
||||
*
|
||||
* @param string $content When the callback is used for the render_block filter,
|
||||
* the content needs to be returned so the function parameter
|
||||
* is to ensure the content exists.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
$callback = static function( $content ) use ( $args ) {
|
||||
// Register the stylesheet.
|
||||
if ( ! empty( $args['src'] ) ) {
|
||||
wp_register_style( $args['handle'], $args['src'], $args['deps'], $args['ver'], $args['media'] );
|
||||
}
|
||||
|
||||
// Add `path` data if provided.
|
||||
if ( isset( $args['path'] ) ) {
|
||||
wp_style_add_data( $args['handle'], 'path', $args['path'] );
|
||||
|
||||
// Get the RTL file path.
|
||||
$rtl_file_path = str_replace( '.css', '-rtl.css', $args['path'] );
|
||||
|
||||
// Add RTL stylesheet.
|
||||
if ( file_exists( $rtl_file_path ) ) {
|
||||
wp_style_add_data( $args['hanle'], 'rtl', 'replace' );
|
||||
|
||||
if ( is_rtl() ) {
|
||||
wp_style_add_data( $args['handle'], 'path', $rtl_file_path );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Enqueue the stylesheet.
|
||||
wp_enqueue_style( $args['handle'] );
|
||||
|
||||
return $content;
|
||||
};
|
||||
|
||||
$hook = did_action( 'wp_enqueue_scripts' ) ? 'wp_footer' : 'wp_enqueue_scripts';
|
||||
if ( wp_should_load_separate_core_block_assets() ) {
|
||||
$hook = "render_block_$block_name";
|
||||
}
|
||||
|
||||
/*
|
||||
* The filter's callback here is an anonymous function because
|
||||
* using a named function in this case is not possible.
|
||||
*
|
||||
* The function cannot be unhooked, however, users are still able
|
||||
* to dequeue the stylesheets registered/enqueued by the callback
|
||||
* which is why in this case, using an anonymous function
|
||||
* was deemed acceptable.
|
||||
*/
|
||||
add_filter( $hook, $callback );
|
||||
|
||||
// Enqueue assets in the editor.
|
||||
add_action( 'enqueue_block_assets', $callback );
|
||||
}
|
||||
|
||||
/**
|
||||
* Allow multiple block styles.
|
||||
*
|
||||
* @param array $metadata Metadata for registering a block type.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
function _wp_multiple_block_styles( $metadata ) {
|
||||
foreach ( array( 'style', 'editorStyle' ) as $key ) {
|
||||
if ( ! empty( $metadata[ $key ] ) && is_array( $metadata[ $key ] ) ) {
|
||||
$default_style = array_shift( $metadata[ $key ] );
|
||||
foreach ( $metadata[ $key ] as $handle ) {
|
||||
$args = array( 'handle' => $handle );
|
||||
if ( 0 === strpos( $handle, 'file:' ) && isset( $metadata['file'] ) ) {
|
||||
$style_path = remove_block_asset_path_prefix( $handle );
|
||||
$args = array(
|
||||
'handle' => sanitize_key( "{$metadata['name']}-{$style_path}" ),
|
||||
'src' => plugins_url( $style_path, $metadata['file'] ),
|
||||
);
|
||||
}
|
||||
|
||||
wp_enqueue_block_style( $metadata['name'], $args );
|
||||
}
|
||||
|
||||
// Only return the 1st item in the array.
|
||||
$metadata[ $key ] = $default_style;
|
||||
}
|
||||
}
|
||||
return $metadata;
|
||||
}
|
||||
add_filter( 'block_type_metadata', '_wp_multiple_block_styles' );
|
||||
|
|
|
@ -15,29 +15,38 @@ require ABSPATH . WPINC . '/blocks/latest-comments.php';
|
|||
require ABSPATH . WPINC . '/blocks/latest-posts.php';
|
||||
require ABSPATH . WPINC . '/blocks/legacy-widget.php';
|
||||
require ABSPATH . WPINC . '/blocks/loginout.php';
|
||||
require ABSPATH . WPINC . '/blocks/navigation-area.php';
|
||||
require ABSPATH . WPINC . '/blocks/navigation-link.php';
|
||||
require ABSPATH . WPINC . '/blocks/navigation-submenu.php';
|
||||
require ABSPATH . WPINC . '/blocks/navigation.php';
|
||||
require ABSPATH . WPINC . '/blocks/page-list.php';
|
||||
require ABSPATH . WPINC . '/blocks/pattern.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-author.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-comments.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-content.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-date.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-excerpt.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-featured-image.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-navigation-link.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-template.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-terms.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-title.php';
|
||||
require ABSPATH . WPINC . '/blocks/post-template.php';
|
||||
require ABSPATH . WPINC . '/blocks/query.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-pagination.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-pagination-next.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-pagination-numbers.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-pagination-previous.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-pagination.php';
|
||||
require ABSPATH . WPINC . '/blocks/query-title.php';
|
||||
require ABSPATH . WPINC . '/blocks/query.php';
|
||||
require ABSPATH . WPINC . '/blocks/rss.php';
|
||||
require ABSPATH . WPINC . '/blocks/search.php';
|
||||
require ABSPATH . WPINC . '/blocks/shortcode.php';
|
||||
require ABSPATH . WPINC . '/blocks/site-tagline.php';
|
||||
require ABSPATH . WPINC . '/blocks/site-logo.php';
|
||||
require ABSPATH . WPINC . '/blocks/site-tagline.php';
|
||||
require ABSPATH . WPINC . '/blocks/site-title.php';
|
||||
require ABSPATH . WPINC . '/blocks/social-link.php';
|
||||
require ABSPATH . WPINC . '/blocks/tag-cloud.php';
|
||||
require ABSPATH . WPINC . '/blocks/template-part.php';
|
||||
require ABSPATH . WPINC . '/blocks/term-description.php';
|
||||
|
||||
/**
|
||||
* Registers core block types using metadata files.
|
||||
|
|
|
@ -0,0 +1,21 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/navigation-area` block.
|
||||
*
|
||||
* @package gutenberg
|
||||
*/
|
||||
|
||||
/**
|
||||
* Registers the `core/navigation-area` block on the server.
|
||||
*/
|
||||
function register_block_core_navigation_area() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/navigation-area',
|
||||
array(
|
||||
'provides_context' => array(
|
||||
'navigationArea' => 'area',
|
||||
),
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_navigation_area' );
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/navigation-area",
|
||||
"title": "Navigation Area",
|
||||
"category": "theme",
|
||||
"description": "Define a navigation area for your theme. The navigation block associated with this area will be automatically displayed.",
|
||||
"keywords": [
|
||||
"menu",
|
||||
"navigation",
|
||||
"links",
|
||||
"location"
|
||||
],
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"area": {
|
||||
"type": "string",
|
||||
"default": "primary"
|
||||
}
|
||||
},
|
||||
"providesContext": {
|
||||
"navigationArea": "area"
|
||||
},
|
||||
"supports": {
|
||||
"html": false,
|
||||
"inserter": true
|
||||
}
|
||||
}
|
|
@ -0,0 +1,350 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/navigation-link` block.
|
||||
*
|
||||
* @package gutenberg
|
||||
*/
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the colors
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $context Navigation block context.
|
||||
* @param array $attributes Block attributes.
|
||||
* @return array Colors CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_link_build_css_colors( $context, $attributes ) {
|
||||
$colors = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
$is_sub_menu = isset( $attributes['isTopLevelLink'] ) ? ( ! $attributes['isTopLevelLink'] ) : false;
|
||||
|
||||
// Text color.
|
||||
$named_text_color = null;
|
||||
$custom_text_color = null;
|
||||
|
||||
if ( $is_sub_menu && array_key_exists( 'customOverlayTextColor', $context ) ) {
|
||||
$custom_text_color = $context['customOverlayTextColor'];
|
||||
} elseif ( $is_sub_menu && array_key_exists( 'overlayTextColor', $context ) ) {
|
||||
$named_text_color = $context['overlayTextColor'];
|
||||
} elseif ( array_key_exists( 'customTextColor', $context ) ) {
|
||||
$custom_text_color = $context['customTextColor'];
|
||||
} elseif ( array_key_exists( 'textColor', $context ) ) {
|
||||
$named_text_color = $context['textColor'];
|
||||
} elseif ( isset( $context['style']['color']['text'] ) ) {
|
||||
$custom_text_color = $context['style']['color']['text'];
|
||||
}
|
||||
|
||||
// If has text color.
|
||||
if ( ! is_null( $named_text_color ) ) {
|
||||
// Add the color class.
|
||||
array_push( $colors['css_classes'], 'has-text-color', sprintf( 'has-%s-color', $named_text_color ) );
|
||||
} elseif ( ! is_null( $custom_text_color ) ) {
|
||||
// Add the custom color inline style.
|
||||
$colors['css_classes'][] = 'has-text-color';
|
||||
$colors['inline_styles'] .= sprintf( 'color: %s;', $custom_text_color );
|
||||
}
|
||||
|
||||
// Background color.
|
||||
$named_background_color = null;
|
||||
$custom_background_color = null;
|
||||
|
||||
if ( $is_sub_menu && array_key_exists( 'customOverlayBackgroundColor', $context ) ) {
|
||||
$custom_background_color = $context['customOverlayBackgroundColor'];
|
||||
} elseif ( $is_sub_menu && array_key_exists( 'overlayBackgroundColor', $context ) ) {
|
||||
$named_background_color = $context['overlayBackgroundColor'];
|
||||
} elseif ( array_key_exists( 'customBackgroundColor', $context ) ) {
|
||||
$custom_background_color = $context['customBackgroundColor'];
|
||||
} elseif ( array_key_exists( 'backgroundColor', $context ) ) {
|
||||
$named_background_color = $context['backgroundColor'];
|
||||
} elseif ( isset( $context['style']['color']['background'] ) ) {
|
||||
$custom_background_color = $context['style']['color']['background'];
|
||||
}
|
||||
|
||||
// If has background color.
|
||||
if ( ! is_null( $named_background_color ) ) {
|
||||
// Add the background-color class.
|
||||
array_push( $colors['css_classes'], 'has-background', sprintf( 'has-%s-background-color', $named_background_color ) );
|
||||
} elseif ( ! is_null( $custom_background_color ) ) {
|
||||
// Add the custom background-color inline style.
|
||||
$colors['css_classes'][] = 'has-background';
|
||||
$colors['inline_styles'] .= sprintf( 'background-color: %s;', $custom_background_color );
|
||||
}
|
||||
|
||||
return $colors;
|
||||
}
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the font sizes
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $context Navigation block context.
|
||||
* @return array Font size CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_link_build_css_font_sizes( $context ) {
|
||||
// CSS classes.
|
||||
$font_sizes = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
$has_named_font_size = array_key_exists( 'fontSize', $context );
|
||||
$has_custom_font_size = isset( $context['style']['typography']['fontSize'] );
|
||||
|
||||
if ( $has_named_font_size ) {
|
||||
// Add the font size class.
|
||||
$font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] );
|
||||
} elseif ( $has_custom_font_size ) {
|
||||
// Add the custom font size inline style.
|
||||
$font_sizes['inline_styles'] = sprintf( 'font-size: %spx;', $context['style']['typography']['fontSize'] );
|
||||
}
|
||||
|
||||
return $font_sizes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the top-level submenu SVG chevron icon.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
function block_core_navigation_link_render_submenu_icon() {
|
||||
return '<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" role="img" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the `core/navigation-link` block.
|
||||
*
|
||||
* @param array $attributes The block attributes.
|
||||
* @param array $content The saved content.
|
||||
* @param array $block The parsed block.
|
||||
*
|
||||
* @return string Returns the post content with the legacy widget added.
|
||||
*/
|
||||
function render_block_core_navigation_link( $attributes, $content, $block ) {
|
||||
$navigation_link_has_id = isset( $attributes['id'] ) && is_numeric( $attributes['id'] );
|
||||
$is_post_type = isset( $attributes['kind'] ) && 'post-type' === $attributes['kind'];
|
||||
$is_post_type = $is_post_type || isset( $attributes['type'] ) && ( 'post' === $attributes['type'] || 'page' === $attributes['type'] );
|
||||
|
||||
// Don't render the block's subtree if it is a draft or if the ID does not exist.
|
||||
if ( $is_post_type && $navigation_link_has_id ) {
|
||||
$post = get_post( $attributes['id'] );
|
||||
if ( ! $post || 'publish' !== $post->post_status ) {
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
// Don't render the block's subtree if it has no label.
|
||||
if ( empty( $attributes['label'] ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$colors = block_core_navigation_link_build_css_colors( $block->context, $attributes );
|
||||
$font_sizes = block_core_navigation_link_build_css_font_sizes( $block->context );
|
||||
$classes = array_merge(
|
||||
$colors['css_classes'],
|
||||
$font_sizes['css_classes']
|
||||
);
|
||||
$style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] );
|
||||
|
||||
$css_classes = trim( implode( ' ', $classes ) );
|
||||
$has_submenu = count( $block->inner_blocks ) > 0;
|
||||
$is_active = ! empty( $attributes['id'] ) && ( get_the_ID() === $attributes['id'] );
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes(
|
||||
array(
|
||||
'class' => $css_classes . ' wp-block-navigation-item' . ( $has_submenu ? ' has-child' : '' ) .
|
||||
( $is_active ? ' current-menu-item' : '' ),
|
||||
'style' => $style_attribute,
|
||||
)
|
||||
);
|
||||
$html = '<li ' . $wrapper_attributes . '>' .
|
||||
'<a class="wp-block-navigation-item__content" ';
|
||||
|
||||
// Start appending HTML attributes to anchor tag.
|
||||
if ( isset( $attributes['url'] ) ) {
|
||||
$html .= ' href="' . esc_url( $attributes['url'] ) . '"';
|
||||
}
|
||||
|
||||
if ( $is_active ) {
|
||||
$html .= ' aria-current="page"';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['opensInNewTab'] ) && true === $attributes['opensInNewTab'] ) {
|
||||
$html .= ' target="_blank" ';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['rel'] ) ) {
|
||||
$html .= ' rel="' . esc_attr( $attributes['rel'] ) . '"';
|
||||
} elseif ( isset( $attributes['nofollow'] ) && $attributes['nofollow'] ) {
|
||||
$html .= ' rel="nofollow"';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['title'] ) ) {
|
||||
$html .= ' title="' . esc_attr( $attributes['title'] ) . '"';
|
||||
}
|
||||
|
||||
// End appending HTML attributes to anchor tag.
|
||||
|
||||
// Start anchor tag content.
|
||||
$html .= '>' .
|
||||
// Wrap title with span to isolate it from submenu icon.
|
||||
'<span class="wp-block-navigation-item__label">';
|
||||
|
||||
if ( isset( $attributes['label'] ) ) {
|
||||
$html .= wp_kses(
|
||||
$attributes['label'],
|
||||
array(
|
||||
'code' => array(),
|
||||
'em' => array(),
|
||||
'img' => array(
|
||||
'scale' => array(),
|
||||
'class' => array(),
|
||||
'style' => array(),
|
||||
'src' => array(),
|
||||
'alt' => array(),
|
||||
),
|
||||
's' => array(),
|
||||
'span' => array(
|
||||
'style' => array(),
|
||||
),
|
||||
'strong' => array(),
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
$html .= '</span>';
|
||||
|
||||
if ( isset( $block->context['showSubmenuIcon'] ) && $block->context['showSubmenuIcon'] && $has_submenu ) {
|
||||
// The submenu icon can be hidden by a CSS rule on the Navigation Block.
|
||||
$html .= '<span class="wp-block-navigation__submenu-icon">' . block_core_navigation_link_render_submenu_icon() . '</span>';
|
||||
}
|
||||
|
||||
$html .= '</a>';
|
||||
// End anchor tag content.
|
||||
|
||||
if ( $has_submenu ) {
|
||||
$inner_blocks_html = '';
|
||||
foreach ( $block->inner_blocks as $inner_block ) {
|
||||
$inner_blocks_html .= $inner_block->render();
|
||||
}
|
||||
|
||||
$html .= sprintf(
|
||||
'<ul class="wp-block-navigation__submenu-container">%s</ul>',
|
||||
$inner_blocks_html
|
||||
);
|
||||
}
|
||||
|
||||
$html .= '</li>';
|
||||
|
||||
return $html;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a navigation link variation
|
||||
*
|
||||
* @param WP_Taxonomy|WP_Post_Type $entity post type or taxonomy entity.
|
||||
* @param string $kind string of value 'taxonomy' or 'post-type'.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
function build_variation_for_navigation_link( $entity, $kind ) {
|
||||
$title = '';
|
||||
$description = '';
|
||||
|
||||
if ( property_exists( $entity->labels, 'item_link' ) ) {
|
||||
$title = $entity->labels->item_link;
|
||||
}
|
||||
if ( property_exists( $entity->labels, 'item_link_description' ) ) {
|
||||
$description = $entity->labels->item_link_description;
|
||||
}
|
||||
|
||||
$variation = array(
|
||||
'name' => $entity->name,
|
||||
'title' => $title,
|
||||
'description' => $description,
|
||||
'attributes' => array(
|
||||
'type' => $entity->name,
|
||||
'kind' => $kind,
|
||||
),
|
||||
);
|
||||
|
||||
// Tweak some value for the variations.
|
||||
$variation_overrides = array(
|
||||
'post_tag' => array(
|
||||
'name' => 'tag',
|
||||
'attributes' => array(
|
||||
'type' => 'tag',
|
||||
'kind' => $kind,
|
||||
),
|
||||
),
|
||||
'post_format' => array(
|
||||
// The item_link and item_link_description for post formats is the
|
||||
// same as for tags, so need to be overridden.
|
||||
'title' => __( 'Post Format Link' ),
|
||||
'description' => __( 'A link to a post format' ),
|
||||
'attributes' => array(
|
||||
'type' => 'post_format',
|
||||
'kind' => $kind,
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
if ( array_key_exists( $entity->name, $variation_overrides ) ) {
|
||||
$variation = array_merge(
|
||||
$variation,
|
||||
$variation_overrides[ $entity->name ]
|
||||
);
|
||||
}
|
||||
|
||||
return $variation;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the navigation link block.
|
||||
*
|
||||
* @uses render_block_core_navigation()
|
||||
* @throws WP_Error An WP_Error exception parsing the block definition.
|
||||
*/
|
||||
function register_block_core_navigation_link() {
|
||||
$post_types = get_post_types( array( 'show_in_nav_menus' => true ), 'objects' );
|
||||
$taxonomies = get_taxonomies( array( 'show_in_nav_menus' => true ), 'objects' );
|
||||
|
||||
// Use two separate arrays as a way to order the variations in the UI.
|
||||
// Known variations (like Post Link and Page Link) are added to the
|
||||
// `built_ins` array. Variations for custom post types and taxonomies are
|
||||
// added to the `variations` array and will always appear after `built-ins.
|
||||
$built_ins = array();
|
||||
$variations = array();
|
||||
|
||||
if ( $post_types ) {
|
||||
foreach ( $post_types as $post_type ) {
|
||||
$variation = build_variation_for_navigation_link( $post_type, 'post-type' );
|
||||
if ( $post_type->_builtin ) {
|
||||
$built_ins[] = $variation;
|
||||
} else {
|
||||
$variations[] = $variation;
|
||||
}
|
||||
}
|
||||
}
|
||||
if ( $taxonomies ) {
|
||||
foreach ( $taxonomies as $taxonomy ) {
|
||||
$variation = build_variation_for_navigation_link( $taxonomy, 'taxonomy' );
|
||||
if ( $taxonomy->_builtin ) {
|
||||
$built_ins[] = $variation;
|
||||
} else {
|
||||
$variations[] = $variation;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/navigation-link',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_navigation_link',
|
||||
'variations' => array_merge( $built_ins, $variations ),
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_navigation_link' );
|
|
@ -0,0 +1,65 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/navigation-link",
|
||||
"title": "Custom Link",
|
||||
"category": "design",
|
||||
"parent": [
|
||||
"core/navigation"
|
||||
],
|
||||
"description": "Add a page, link, or another item to your navigation.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"label": {
|
||||
"type": "string"
|
||||
},
|
||||
"type": {
|
||||
"type": "string"
|
||||
},
|
||||
"description": {
|
||||
"type": "string"
|
||||
},
|
||||
"rel": {
|
||||
"type": "string"
|
||||
},
|
||||
"id": {
|
||||
"type": "number"
|
||||
},
|
||||
"opensInNewTab": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"url": {
|
||||
"type": "string"
|
||||
},
|
||||
"title": {
|
||||
"type": "string"
|
||||
},
|
||||
"kind": {
|
||||
"type": "string"
|
||||
},
|
||||
"isTopLevelLink": {
|
||||
"type": "boolean"
|
||||
}
|
||||
},
|
||||
"usesContext": [
|
||||
"textColor",
|
||||
"customTextColor",
|
||||
"backgroundColor",
|
||||
"customBackgroundColor",
|
||||
"overlayTextColor",
|
||||
"customOverlayTextColor",
|
||||
"overlayBackgroundColor",
|
||||
"customOverlayBackgroundColor",
|
||||
"fontSize",
|
||||
"customFontSize",
|
||||
"showSubmenuIcon",
|
||||
"style"
|
||||
],
|
||||
"supports": {
|
||||
"reusable": false,
|
||||
"html": false,
|
||||
"__experimentalSlashInserter": true
|
||||
},
|
||||
"editorStyle": "wp-block-navigation-link-editor",
|
||||
"style": "wp-block-navigation-link"
|
||||
}
|
|
@ -0,0 +1,163 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
/**
|
||||
* Submenus.
|
||||
*/
|
||||
.wp-block-navigation .has-child {
|
||||
cursor: pointer;
|
||||
}
|
||||
.wp-block-navigation .has-child .wp-block-navigation__submenu-container {
|
||||
z-index: 28;
|
||||
}
|
||||
.wp-block-navigation .has-child:hover .wp-block-navigation__submenu-container {
|
||||
z-index: 29;
|
||||
}
|
||||
.wp-block-navigation .has-child.is-selected > .wp-block-navigation__submenu-container, .wp-block-navigation .has-child.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
visibility: visible !important;
|
||||
opacity: 1 !important;
|
||||
min-width: 200px !important;
|
||||
height: auto !important;
|
||||
width: auto !important;
|
||||
}
|
||||
|
||||
/**
|
||||
* Navigation Items.
|
||||
*/
|
||||
.wp-block-navigation-item .wp-block-navigation-item__content {
|
||||
cursor: text;
|
||||
}
|
||||
.wp-block-navigation-item.is-editing, .wp-block-navigation-item.is-selected {
|
||||
min-width: 20px;
|
||||
}
|
||||
.wp-block-navigation-item .block-list-appender {
|
||||
margin-top: 16px;
|
||||
margin-left: auto;
|
||||
margin-bottom: 16px;
|
||||
margin-right: 16px;
|
||||
}
|
||||
|
||||
/**
|
||||
* Menu item setup state. Is shown when a menu item has no URL configured.
|
||||
*/
|
||||
.wp-block-navigation-link__placeholder {
|
||||
position: relative;
|
||||
text-decoration: none !important;
|
||||
box-shadow: none !important;
|
||||
background-image: none !important;
|
||||
}
|
||||
.wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span {
|
||||
--wp-underline-color: var(--wp-admin-theme-color);
|
||||
background-image: linear-gradient(-45deg, transparent 20%, var(--wp-underline-color) 30%, var(--wp-underline-color) 36%, transparent 46%), linear-gradient(-135deg, transparent 54%, var(--wp-underline-color) 64%, var(--wp-underline-color) 70%, transparent 80%);
|
||||
background-position: 100% 100%;
|
||||
background-size: 6px 3px;
|
||||
background-repeat: repeat-x;
|
||||
padding-bottom: 0.1em;
|
||||
}
|
||||
.is-dark-theme .wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span {
|
||||
--wp-underline-color: #fff;
|
||||
}
|
||||
.wp-block-navigation-link__placeholder.wp-block-navigation-item__content {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Link Control Transforms
|
||||
*/
|
||||
.link-control-transform {
|
||||
border-top: 1px solid #ccc;
|
||||
padding: 0 16px 8px 16px;
|
||||
}
|
||||
|
||||
.link-control-transform__subheading {
|
||||
font-size: 11px;
|
||||
text-transform: uppercase;
|
||||
font-weight: 500;
|
||||
color: #1e1e1e;
|
||||
margin-bottom: 1.5em;
|
||||
}
|
||||
|
||||
.link-control-transform__items {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
.link-control-transform__item {
|
||||
flex-basis: 33%;
|
||||
flex-direction: column;
|
||||
gap: 8px;
|
||||
height: auto;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation .has-child{cursor:pointer}.wp-block-navigation .has-child .wp-block-navigation__submenu-container{z-index:28}.wp-block-navigation .has-child:hover .wp-block-navigation__submenu-container{z-index:29}.wp-block-navigation .has-child.has-child-selected>.wp-block-navigation__submenu-container,.wp-block-navigation .has-child.is-selected>.wp-block-navigation__submenu-container{visibility:visible!important;opacity:1!important;min-width:200px!important;height:auto!important;width:auto!important}.wp-block-navigation-item .wp-block-navigation-item__content{cursor:text}.wp-block-navigation-item.is-editing,.wp-block-navigation-item.is-selected{min-width:20px}.wp-block-navigation-item .block-list-appender{margin:16px 16px 16px auto}.wp-block-navigation-link__placeholder{position:relative;text-decoration:none!important;box-shadow:none!important;background-image:none!important}.wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span{--wp-underline-color:var(--wp-admin-theme-color);background-image:linear-gradient(-45deg,transparent 20%,var(--wp-underline-color) 30%,var(--wp-underline-color) 36%,transparent 46%),linear-gradient(-135deg,transparent 54%,var(--wp-underline-color) 64%,var(--wp-underline-color) 70%,transparent 80%);background-position:100% 100%;background-size:6px 3px;background-repeat:repeat-x;padding-bottom:.1em}.is-dark-theme .wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span{--wp-underline-color:#fff}.wp-block-navigation-link__placeholder.wp-block-navigation-item__content{cursor:pointer}.link-control-transform{border-top:1px solid #ccc;padding:0 16px 8px}.link-control-transform__subheading{font-size:11px;text-transform:uppercase;font-weight:500;color:#1e1e1e;margin-bottom:1.5em}.link-control-transform__items{display:flex;justify-content:space-between}.link-control-transform__item{flex-basis:33%;flex-direction:column;gap:8px;height:auto}
|
|
@ -0,0 +1,163 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
/**
|
||||
* Submenus.
|
||||
*/
|
||||
.wp-block-navigation .has-child {
|
||||
cursor: pointer;
|
||||
}
|
||||
.wp-block-navigation .has-child .wp-block-navigation__submenu-container {
|
||||
z-index: 28;
|
||||
}
|
||||
.wp-block-navigation .has-child:hover .wp-block-navigation__submenu-container {
|
||||
z-index: 29;
|
||||
}
|
||||
.wp-block-navigation .has-child.is-selected > .wp-block-navigation__submenu-container, .wp-block-navigation .has-child.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
visibility: visible !important;
|
||||
opacity: 1 !important;
|
||||
min-width: 200px !important;
|
||||
height: auto !important;
|
||||
width: auto !important;
|
||||
}
|
||||
|
||||
/**
|
||||
* Navigation Items.
|
||||
*/
|
||||
.wp-block-navigation-item .wp-block-navigation-item__content {
|
||||
cursor: text;
|
||||
}
|
||||
.wp-block-navigation-item.is-editing, .wp-block-navigation-item.is-selected {
|
||||
min-width: 20px;
|
||||
}
|
||||
.wp-block-navigation-item .block-list-appender {
|
||||
margin-top: 16px;
|
||||
margin-right: auto;
|
||||
margin-bottom: 16px;
|
||||
margin-left: 16px;
|
||||
}
|
||||
|
||||
/**
|
||||
* Menu item setup state. Is shown when a menu item has no URL configured.
|
||||
*/
|
||||
.wp-block-navigation-link__placeholder {
|
||||
position: relative;
|
||||
text-decoration: none !important;
|
||||
box-shadow: none !important;
|
||||
background-image: none !important;
|
||||
}
|
||||
.wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span {
|
||||
--wp-underline-color: var(--wp-admin-theme-color);
|
||||
background-image: linear-gradient(45deg, transparent 20%, var(--wp-underline-color) 30%, var(--wp-underline-color) 36%, transparent 46%), linear-gradient(135deg, transparent 54%, var(--wp-underline-color) 64%, var(--wp-underline-color) 70%, transparent 80%);
|
||||
background-position: 0 100%;
|
||||
background-size: 6px 3px;
|
||||
background-repeat: repeat-x;
|
||||
padding-bottom: 0.1em;
|
||||
}
|
||||
.is-dark-theme .wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span {
|
||||
--wp-underline-color: #fff;
|
||||
}
|
||||
.wp-block-navigation-link__placeholder.wp-block-navigation-item__content {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Link Control Transforms
|
||||
*/
|
||||
.link-control-transform {
|
||||
border-top: 1px solid #ccc;
|
||||
padding: 0 16px 8px 16px;
|
||||
}
|
||||
|
||||
.link-control-transform__subheading {
|
||||
font-size: 11px;
|
||||
text-transform: uppercase;
|
||||
font-weight: 500;
|
||||
color: #1e1e1e;
|
||||
margin-bottom: 1.5em;
|
||||
}
|
||||
|
||||
.link-control-transform__items {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
.link-control-transform__item {
|
||||
flex-basis: 33%;
|
||||
flex-direction: column;
|
||||
gap: 8px;
|
||||
height: auto;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation .has-child{cursor:pointer}.wp-block-navigation .has-child .wp-block-navigation__submenu-container{z-index:28}.wp-block-navigation .has-child:hover .wp-block-navigation__submenu-container{z-index:29}.wp-block-navigation .has-child.has-child-selected>.wp-block-navigation__submenu-container,.wp-block-navigation .has-child.is-selected>.wp-block-navigation__submenu-container{visibility:visible!important;opacity:1!important;min-width:200px!important;height:auto!important;width:auto!important}.wp-block-navigation-item .wp-block-navigation-item__content{cursor:text}.wp-block-navigation-item.is-editing,.wp-block-navigation-item.is-selected{min-width:20px}.wp-block-navigation-item .block-list-appender{margin:16px auto 16px 16px}.wp-block-navigation-link__placeholder{position:relative;text-decoration:none!important;box-shadow:none!important;background-image:none!important}.wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span{--wp-underline-color:var(--wp-admin-theme-color);background-image:linear-gradient(45deg,transparent 20%,var(--wp-underline-color) 30%,var(--wp-underline-color) 36%,transparent 46%),linear-gradient(135deg,transparent 54%,var(--wp-underline-color) 64%,var(--wp-underline-color) 70%,transparent 80%);background-position:0 100%;background-size:6px 3px;background-repeat:repeat-x;padding-bottom:.1em}.is-dark-theme .wp-block-navigation-link__placeholder .wp-block-navigation-link__placeholder-text span{--wp-underline-color:#fff}.wp-block-navigation-link__placeholder.wp-block-navigation-item__content{cursor:pointer}.link-control-transform{border-top:1px solid #ccc;padding:0 16px 8px}.link-control-transform__subheading{font-size:11px;text-transform:uppercase;font-weight:500;color:#1e1e1e;margin-bottom:1.5em}.link-control-transform__items{display:flex;justify-content:space-between}.link-control-transform__item{flex-basis:33%;flex-direction:column;gap:8px;height:auto}
|
|
@ -0,0 +1,80 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation .wp-block-navigation-item__label {
|
||||
word-break: normal;
|
||||
overflow-wrap: break-word;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation .wp-block-navigation-item__label{word-break:normal;overflow-wrap:break-word}
|
|
@ -0,0 +1,80 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation .wp-block-navigation-item__label {
|
||||
word-break: normal;
|
||||
overflow-wrap: break-word;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation .wp-block-navigation-item__label{word-break:normal;overflow-wrap:break-word}
|
|
@ -0,0 +1,300 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/navigation-submenu` block.
|
||||
*
|
||||
* @package gutenberg
|
||||
*/
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the colors
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $context Navigation block context.
|
||||
* @param array $attributes Block attributes.
|
||||
* @return array Colors CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_submenu_build_css_colors( $context, $attributes ) {
|
||||
$colors = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
$is_sub_menu = isset( $attributes['isTopLevelLink'] ) ? ( ! $attributes['isTopLevelLink'] ) : false;
|
||||
|
||||
// Text color.
|
||||
$named_text_color = null;
|
||||
$custom_text_color = null;
|
||||
|
||||
if ( $is_sub_menu && array_key_exists( 'customOverlayTextColor', $context ) ) {
|
||||
$custom_text_color = $context['customOverlayTextColor'];
|
||||
} elseif ( $is_sub_menu && array_key_exists( 'overlayTextColor', $context ) ) {
|
||||
$named_text_color = $context['overlayTextColor'];
|
||||
} elseif ( array_key_exists( 'customTextColor', $context ) ) {
|
||||
$custom_text_color = $context['customTextColor'];
|
||||
} elseif ( array_key_exists( 'textColor', $context ) ) {
|
||||
$named_text_color = $context['textColor'];
|
||||
} elseif ( isset( $context['style']['color']['text'] ) ) {
|
||||
$custom_text_color = $context['style']['color']['text'];
|
||||
}
|
||||
|
||||
// If has text color.
|
||||
if ( ! is_null( $named_text_color ) ) {
|
||||
// Add the color class.
|
||||
array_push( $colors['css_classes'], 'has-text-color', sprintf( 'has-%s-color', $named_text_color ) );
|
||||
} elseif ( ! is_null( $custom_text_color ) ) {
|
||||
// Add the custom color inline style.
|
||||
$colors['css_classes'][] = 'has-text-color';
|
||||
$colors['inline_styles'] .= sprintf( 'color: %s;', $custom_text_color );
|
||||
}
|
||||
|
||||
// Background color.
|
||||
$named_background_color = null;
|
||||
$custom_background_color = null;
|
||||
|
||||
if ( $is_sub_menu && array_key_exists( 'customOverlayBackgroundColor', $context ) ) {
|
||||
$custom_background_color = $context['customOverlayBackgroundColor'];
|
||||
} elseif ( $is_sub_menu && array_key_exists( 'overlayBackgroundColor', $context ) ) {
|
||||
$named_background_color = $context['overlayBackgroundColor'];
|
||||
} elseif ( array_key_exists( 'customBackgroundColor', $context ) ) {
|
||||
$custom_background_color = $context['customBackgroundColor'];
|
||||
} elseif ( array_key_exists( 'backgroundColor', $context ) ) {
|
||||
$named_background_color = $context['backgroundColor'];
|
||||
} elseif ( isset( $context['style']['color']['background'] ) ) {
|
||||
$custom_background_color = $context['style']['color']['background'];
|
||||
}
|
||||
|
||||
// If has background color.
|
||||
if ( ! is_null( $named_background_color ) ) {
|
||||
// Add the background-color class.
|
||||
array_push( $colors['css_classes'], 'has-background', sprintf( 'has-%s-background-color', $named_background_color ) );
|
||||
} elseif ( ! is_null( $custom_background_color ) ) {
|
||||
// Add the custom background-color inline style.
|
||||
$colors['css_classes'][] = 'has-background';
|
||||
$colors['inline_styles'] .= sprintf( 'background-color: %s;', $custom_background_color );
|
||||
}
|
||||
|
||||
return $colors;
|
||||
}
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the font sizes
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $context Navigation block context.
|
||||
* @return array Font size CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_submenu_build_css_font_sizes( $context ) {
|
||||
// CSS classes.
|
||||
$font_sizes = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
$has_named_font_size = array_key_exists( 'fontSize', $context );
|
||||
$has_custom_font_size = isset( $context['style']['typography']['fontSize'] );
|
||||
|
||||
if ( $has_named_font_size ) {
|
||||
// Add the font size class.
|
||||
$font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] );
|
||||
} elseif ( $has_custom_font_size ) {
|
||||
// Add the custom font size inline style.
|
||||
$font_sizes['inline_styles'] = sprintf( 'font-size: %spx;', $context['style']['typography']['fontSize'] );
|
||||
}
|
||||
|
||||
return $font_sizes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the top-level submenu SVG chevron icon.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
function block_core_navigation_submenu_render_submenu_icon() {
|
||||
return '<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" role="img" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the `core/navigation-submenu` block.
|
||||
*
|
||||
* @param array $attributes The block attributes.
|
||||
* @param string $content The saved content.
|
||||
* @param object $block The parsed block.
|
||||
*
|
||||
* @return string Returns the post content with the legacy widget added.
|
||||
*/
|
||||
function render_block_core_navigation_submenu( $attributes, $content, $block ) {
|
||||
|
||||
$navigation_link_has_id = isset( $attributes['id'] ) && is_numeric( $attributes['id'] );
|
||||
$is_post_type = isset( $attributes['kind'] ) && 'post-type' === $attributes['kind'];
|
||||
$is_post_type = $is_post_type || isset( $attributes['type'] ) && ( 'post' === $attributes['type'] || 'page' === $attributes['type'] );
|
||||
|
||||
// Don't render the block's subtree if it is a draft.
|
||||
if ( $is_post_type && $navigation_link_has_id && 'publish' !== get_post_status( $attributes['id'] ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
// Don't render the block's subtree if it has no label.
|
||||
if ( empty( $attributes['label'] ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$colors = block_core_navigation_submenu_build_css_colors( $block->context, $attributes );
|
||||
$font_sizes = block_core_navigation_submenu_build_css_font_sizes( $block->context );
|
||||
$classes = array_merge(
|
||||
$colors['css_classes'],
|
||||
$font_sizes['css_classes']
|
||||
);
|
||||
$style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] );
|
||||
|
||||
$css_classes = trim( implode( ' ', $classes ) );
|
||||
$has_submenu = count( $block->inner_blocks ) > 0;
|
||||
$is_active = ! empty( $attributes['id'] ) && ( get_the_ID() === $attributes['id'] );
|
||||
|
||||
$class_name = ! empty( $attributes['className'] ) ? implode( ' ', (array) $attributes['className'] ) : false;
|
||||
|
||||
if ( false !== $class_name ) {
|
||||
$css_classes .= ' ' . $class_name;
|
||||
}
|
||||
|
||||
$show_submenu_indicators = isset( $block->context['showSubmenuIcon'] ) && $block->context['showSubmenuIcon'];
|
||||
$open_on_click = isset( $block->context['openSubmenusOnClick'] ) && $block->context['openSubmenusOnClick'];
|
||||
$open_on_hover_and_click = isset( $block->context['openSubmenusOnClick'] ) && ! $block->context['openSubmenusOnClick'] &&
|
||||
$show_submenu_indicators;
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes(
|
||||
array(
|
||||
'class' => $css_classes . ' wp-block-navigation-item' . ( $has_submenu ? ' has-child' : '' ) .
|
||||
( $open_on_click ? ' open-on-click' : '' ) . ( $open_on_hover_and_click ? ' open-on-hover-click' : '' ) .
|
||||
( $is_active ? ' current-menu-item' : '' ),
|
||||
'style' => $style_attribute,
|
||||
)
|
||||
);
|
||||
$html = '<li ' . $wrapper_attributes . '>';
|
||||
|
||||
// If Submenus open on hover, we render an anchor tag with attributes.
|
||||
// If submenu icons are set to show, we also render a submenu button, so the submenu can be opened on click.
|
||||
if ( ! $open_on_click ) {
|
||||
$item_url = isset( $attributes['url'] ) ? esc_url( $attributes['url'] ) : '';
|
||||
// Start appending HTML attributes to anchor tag.
|
||||
$html .= '<a class="wp-block-navigation-item__content" href="' . $item_url . '"';
|
||||
|
||||
if ( $is_active ) {
|
||||
$html .= ' aria-current="page"';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['opensInNewTab'] ) && true === $attributes['opensInNewTab'] ) {
|
||||
$html .= ' target="_blank" ';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['rel'] ) ) {
|
||||
$html .= ' rel="' . esc_attr( $attributes['rel'] ) . '"';
|
||||
} elseif ( isset( $attributes['nofollow'] ) && $attributes['nofollow'] ) {
|
||||
$html .= ' rel="nofollow"';
|
||||
}
|
||||
|
||||
if ( isset( $attributes['title'] ) ) {
|
||||
$html .= ' title="' . esc_attr( $attributes['title'] ) . '"';
|
||||
}
|
||||
|
||||
$html .= '>';
|
||||
// End appending HTML attributes to anchor tag.
|
||||
|
||||
if ( isset( $attributes['label'] ) ) {
|
||||
$html .= wp_kses(
|
||||
$attributes['label'],
|
||||
array(
|
||||
'code' => array(),
|
||||
'em' => array(),
|
||||
'img' => array(
|
||||
'scale' => array(),
|
||||
'class' => array(),
|
||||
'style' => array(),
|
||||
'src' => array(),
|
||||
'alt' => array(),
|
||||
),
|
||||
's' => array(),
|
||||
'span' => array(
|
||||
'style' => array(),
|
||||
),
|
||||
'strong' => array(),
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
$html .= '</a>';
|
||||
// End anchor tag content.
|
||||
|
||||
if ( $show_submenu_indicators ) {
|
||||
// The submenu icon is rendered in a button here
|
||||
// so that there's a clickable elment to open the submenu.
|
||||
$html .= '<button class="wp-block-navigation__submenu-icon wp-block-navigation-submenu__toggle" aria-expanded="false">' . block_core_navigation_submenu_render_submenu_icon() . '</button>';
|
||||
}
|
||||
} else {
|
||||
// If menus open on click, we render the parent as a button.
|
||||
$html .= '<button class="wp-block-navigation-item__content wp-block-navigation-submenu__toggle" aria-expanded="false">';
|
||||
|
||||
// Wrap title with span to isolate it from submenu icon.
|
||||
$html .= '<span class="wp-block-navigation-item__label">';
|
||||
|
||||
if ( isset( $attributes['label'] ) ) {
|
||||
$html .= wp_kses(
|
||||
$attributes['label'],
|
||||
array(
|
||||
'code' => array(),
|
||||
'em' => array(),
|
||||
'img' => array(
|
||||
'scale' => array(),
|
||||
'class' => array(),
|
||||
'style' => array(),
|
||||
'src' => array(),
|
||||
'alt' => array(),
|
||||
),
|
||||
's' => array(),
|
||||
'span' => array(
|
||||
'style' => array(),
|
||||
),
|
||||
'strong' => array(),
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
$html .= '</span>';
|
||||
|
||||
$html .= '<span class="wp-block-navigation__submenu-icon">' . block_core_navigation_submenu_render_submenu_icon() . '</span>';
|
||||
|
||||
$html .= '</button>';
|
||||
|
||||
}
|
||||
|
||||
if ( $has_submenu ) {
|
||||
$inner_blocks_html = '';
|
||||
foreach ( $block->inner_blocks as $inner_block ) {
|
||||
$inner_blocks_html .= $inner_block->render();
|
||||
}
|
||||
|
||||
$html .= sprintf(
|
||||
'<ul class="wp-block-navigation__submenu-container">%s</ul>',
|
||||
$inner_blocks_html
|
||||
);
|
||||
}
|
||||
|
||||
$html .= '</li>';
|
||||
|
||||
return $html;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the navigation submenu block.
|
||||
*
|
||||
* @uses render_block_core_navigation_submenu()
|
||||
* @throws WP_Error An WP_Error exception parsing the block definition.
|
||||
*/
|
||||
function register_block_core_navigation_submenu() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/navigation-submenu',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_navigation_submenu',
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_navigation_submenu' );
|
|
@ -0,0 +1,65 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/navigation-submenu",
|
||||
"title": "Submenu",
|
||||
"category": "design",
|
||||
"parent": [
|
||||
"core/navigation"
|
||||
],
|
||||
"description": "Add a submenu to your navigation.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"label": {
|
||||
"type": "string"
|
||||
},
|
||||
"type": {
|
||||
"type": "string"
|
||||
},
|
||||
"description": {
|
||||
"type": "string"
|
||||
},
|
||||
"rel": {
|
||||
"type": "string"
|
||||
},
|
||||
"id": {
|
||||
"type": "number"
|
||||
},
|
||||
"opensInNewTab": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"url": {
|
||||
"type": "string"
|
||||
},
|
||||
"title": {
|
||||
"type": "string"
|
||||
},
|
||||
"kind": {
|
||||
"type": "string"
|
||||
},
|
||||
"isTopLevelItem": {
|
||||
"type": "boolean"
|
||||
}
|
||||
},
|
||||
"usesContext": [
|
||||
"textColor",
|
||||
"customTextColor",
|
||||
"backgroundColor",
|
||||
"customBackgroundColor",
|
||||
"overlayTextColor",
|
||||
"customOverlayTextColor",
|
||||
"overlayBackgroundColor",
|
||||
"customOverlayBackgroundColor",
|
||||
"fontSize",
|
||||
"customFontSize",
|
||||
"showSubmenuIcon",
|
||||
"openSubmenusOnClick",
|
||||
"style"
|
||||
],
|
||||
"supports": {
|
||||
"reusable": false,
|
||||
"html": false
|
||||
},
|
||||
"editorStyle": "wp-block-navigation-submenu-editor",
|
||||
"style": "wp-block-navigation-submenu"
|
||||
}
|
|
@ -0,0 +1,107 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation-submenu {
|
||||
display: block;
|
||||
}
|
||||
.wp-block-navigation-submenu .wp-block-navigation__submenu-container {
|
||||
z-index: 28;
|
||||
}
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
visibility: visible !important;
|
||||
opacity: 1 !important;
|
||||
min-width: 200px !important;
|
||||
height: auto !important;
|
||||
width: auto !important;
|
||||
position: absolute;
|
||||
right: -1px;
|
||||
top: 100%;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
right: 100%;
|
||||
top: -1px;
|
||||
}
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container::before, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
left: 100%;
|
||||
height: 100%;
|
||||
display: block;
|
||||
width: 0.5em;
|
||||
background: transparent;
|
||||
}
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation-submenu{display:block}.wp-block-navigation-submenu .wp-block-navigation__submenu-container{z-index:28}.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container{visibility:visible!important;opacity:1!important;min-width:200px!important;height:auto!important;width:auto!important;position:absolute;right:-1px;top:100%}@media (min-width:782px){.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container{right:100%;top:-1px}.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container:before,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container:before{content:"";position:absolute;left:100%;height:100%;display:block;width:.5em;background:transparent}}
|
|
@ -0,0 +1,107 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation-submenu {
|
||||
display: block;
|
||||
}
|
||||
.wp-block-navigation-submenu .wp-block-navigation__submenu-container {
|
||||
z-index: 28;
|
||||
}
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
visibility: visible !important;
|
||||
opacity: 1 !important;
|
||||
min-width: 200px !important;
|
||||
height: auto !important;
|
||||
width: auto !important;
|
||||
position: absolute;
|
||||
left: -1px;
|
||||
top: 100%;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
left: 100%;
|
||||
top: -1px;
|
||||
}
|
||||
.wp-block-navigation-submenu.is-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container::before, .wp-block-navigation-submenu.has-child-selected > .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
right: 100%;
|
||||
height: 100%;
|
||||
display: block;
|
||||
width: 0.5em;
|
||||
background: transparent;
|
||||
}
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation-submenu{display:block}.wp-block-navigation-submenu .wp-block-navigation__submenu-container{z-index:28}.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container{visibility:visible!important;opacity:1!important;min-width:200px!important;height:auto!important;width:auto!important;position:absolute;left:-1px;top:100%}@media (min-width:782px){.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container{left:100%;top:-1px}.wp-block-navigation-submenu.has-child-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container:before,.wp-block-navigation-submenu.is-selected>.wp-block-navigation__submenu-container .wp-block-navigation__submenu-container:before{content:"";position:absolute;right:100%;height:100%;display:block;width:.5em;background:transparent}}
|
|
@ -0,0 +1,95 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation-submenu {
|
||||
position: relative;
|
||||
display: flex;
|
||||
}
|
||||
.wp-block-navigation-submenu .wp-block-navigation__submenu-icon svg {
|
||||
stroke: currentColor;
|
||||
}
|
||||
|
||||
button.wp-block-navigation-item__content {
|
||||
background-color: transparent;
|
||||
border: none;
|
||||
color: currentColor;
|
||||
font-size: inherit;
|
||||
font-family: inherit;
|
||||
}
|
||||
|
||||
.wp-block-navigation-submenu__toggle {
|
||||
cursor: pointer;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation-submenu{position:relative;display:flex}.wp-block-navigation-submenu .wp-block-navigation__submenu-icon svg{stroke:currentColor}button.wp-block-navigation-item__content{background-color:initial;border:none;color:currentColor;font-size:inherit;font-family:inherit}.wp-block-navigation-submenu__toggle{cursor:pointer}
|
|
@ -0,0 +1,95 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation-submenu {
|
||||
position: relative;
|
||||
display: flex;
|
||||
}
|
||||
.wp-block-navigation-submenu .wp-block-navigation__submenu-icon svg {
|
||||
stroke: currentColor;
|
||||
}
|
||||
|
||||
button.wp-block-navigation-item__content {
|
||||
background-color: transparent;
|
||||
border: none;
|
||||
color: currentColor;
|
||||
font-size: inherit;
|
||||
font-family: inherit;
|
||||
}
|
||||
|
||||
.wp-block-navigation-submenu__toggle {
|
||||
cursor: pointer;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-navigation-submenu{position:relative;display:flex}.wp-block-navigation-submenu .wp-block-navigation__submenu-icon svg{stroke:currentColor}button.wp-block-navigation-item__content{background-color:initial;border:none;color:currentColor;font-size:inherit;font-family:inherit}.wp-block-navigation-submenu__toggle{cursor:pointer}
|
|
@ -0,0 +1,429 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/navigation` block.
|
||||
*
|
||||
* @package gutenberg
|
||||
*/
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the colors
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $attributes Navigation block attributes.
|
||||
* @return array Colors CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_build_css_colors( $attributes ) {
|
||||
$colors = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
// Text color.
|
||||
$has_named_text_color = array_key_exists( 'textColor', $attributes );
|
||||
$has_custom_text_color = array_key_exists( 'customTextColor', $attributes );
|
||||
|
||||
// If has text color.
|
||||
if ( $has_custom_text_color || $has_named_text_color ) {
|
||||
// Add has-text-color class.
|
||||
$colors['css_classes'][] = 'has-text-color';
|
||||
}
|
||||
|
||||
if ( $has_named_text_color ) {
|
||||
// Add the color class.
|
||||
$colors['css_classes'][] = sprintf( 'has-%s-color', $attributes['textColor'] );
|
||||
} elseif ( $has_custom_text_color ) {
|
||||
// Add the custom color inline style.
|
||||
$colors['inline_styles'] .= sprintf( 'color: %s;', $attributes['customTextColor'] );
|
||||
}
|
||||
|
||||
// Background color.
|
||||
$has_named_background_color = array_key_exists( 'backgroundColor', $attributes );
|
||||
$has_custom_background_color = array_key_exists( 'customBackgroundColor', $attributes );
|
||||
|
||||
// If has background color.
|
||||
if ( $has_custom_background_color || $has_named_background_color ) {
|
||||
// Add has-background class.
|
||||
$colors['css_classes'][] = 'has-background';
|
||||
}
|
||||
|
||||
if ( $has_named_background_color ) {
|
||||
// Add the background-color class.
|
||||
$colors['css_classes'][] = sprintf( 'has-%s-background-color', $attributes['backgroundColor'] );
|
||||
} elseif ( $has_custom_background_color ) {
|
||||
// Add the custom background-color inline style.
|
||||
$colors['inline_styles'] .= sprintf( 'background-color: %s;', $attributes['customBackgroundColor'] );
|
||||
}
|
||||
|
||||
return $colors;
|
||||
}
|
||||
|
||||
/**
|
||||
* Build an array with CSS classes and inline styles defining the font sizes
|
||||
* which will be applied to the navigation markup in the front-end.
|
||||
*
|
||||
* @param array $attributes Navigation block attributes.
|
||||
* @return array Font size CSS classes and inline styles.
|
||||
*/
|
||||
function block_core_navigation_build_css_font_sizes( $attributes ) {
|
||||
// CSS classes.
|
||||
$font_sizes = array(
|
||||
'css_classes' => array(),
|
||||
'inline_styles' => '',
|
||||
);
|
||||
|
||||
$has_named_font_size = array_key_exists( 'fontSize', $attributes );
|
||||
$has_custom_font_size = array_key_exists( 'customFontSize', $attributes );
|
||||
|
||||
if ( $has_named_font_size ) {
|
||||
// Add the font size class.
|
||||
$font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $attributes['fontSize'] );
|
||||
} elseif ( $has_custom_font_size ) {
|
||||
// Add the custom font size inline style.
|
||||
$font_sizes['inline_styles'] = sprintf( 'font-size: %spx;', $attributes['customFontSize'] );
|
||||
}
|
||||
|
||||
return $font_sizes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the menu items for a WordPress menu location.
|
||||
*
|
||||
* @param string $location The menu location.
|
||||
* @return array Menu items for the location.
|
||||
*/
|
||||
function gutenberg_get_menu_items_at_location( $location ) {
|
||||
if ( empty( $location ) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Build menu data. The following approximates the code in
|
||||
// `wp_nav_menu()` and `gutenberg_output_block_nav_menu`.
|
||||
|
||||
// Find the location in the list of locations, returning early if the
|
||||
// location can't be found.
|
||||
$locations = get_nav_menu_locations();
|
||||
if ( ! isset( $locations[ $location ] ) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get the menu from the location, returning early if there is no
|
||||
// menu or there was an error.
|
||||
$menu = wp_get_nav_menu_object( $locations[ $location ] );
|
||||
if ( ! $menu || is_wp_error( $menu ) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$menu_items = wp_get_nav_menu_items( $menu->term_id, array( 'update_post_term_cache' => false ) );
|
||||
_wp_menu_item_classes_by_context( $menu_items );
|
||||
|
||||
return $menu_items;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sorts a standard array of menu items into a nested structure keyed by the
|
||||
* id of the parent menu.
|
||||
*
|
||||
* @param array $menu_items Menu items to sort.
|
||||
* @return array An array keyed by the id of the parent menu where each element
|
||||
* is an array of menu items that belong to that parent.
|
||||
*/
|
||||
function gutenberg_sort_menu_items_by_parent_id( $menu_items ) {
|
||||
$sorted_menu_items = array();
|
||||
foreach ( (array) $menu_items as $menu_item ) {
|
||||
$sorted_menu_items[ $menu_item->menu_order ] = $menu_item;
|
||||
}
|
||||
unset( $menu_items, $menu_item );
|
||||
|
||||
$menu_items_by_parent_id = array();
|
||||
foreach ( $sorted_menu_items as $menu_item ) {
|
||||
$menu_items_by_parent_id[ $menu_item->menu_item_parent ][] = $menu_item;
|
||||
}
|
||||
|
||||
return $menu_items_by_parent_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Turns menu item data into a nested array of parsed blocks
|
||||
*
|
||||
* @param array $menu_items An array of menu items that represent
|
||||
* an individual level of a menu.
|
||||
* @param array $menu_items_by_parent_id An array keyed by the id of the
|
||||
* parent menu where each element is an
|
||||
* array of menu items that belong to
|
||||
* that parent.
|
||||
* @return array An array of parsed block data.
|
||||
*/
|
||||
function gutenberg_parse_blocks_from_menu_items( $menu_items, $menu_items_by_parent_id ) {
|
||||
if ( empty( $menu_items ) ) {
|
||||
return array();
|
||||
}
|
||||
|
||||
$blocks = array();
|
||||
|
||||
foreach ( $menu_items as $menu_item ) {
|
||||
$class_name = ! empty( $menu_item->classes ) ? implode( ' ', (array) $menu_item->classes ) : null;
|
||||
$id = ( null !== $menu_item->object_id && 'custom' !== $menu_item->object ) ? $menu_item->object_id : null;
|
||||
$opens_in_new_tab = null !== $menu_item->target && '_blank' === $menu_item->target;
|
||||
$rel = ( null !== $menu_item->xfn && '' !== $menu_item->xfn ) ? $menu_item->xfn : null;
|
||||
$kind = null !== $menu_item->type ? str_replace( '_', '-', $menu_item->type ) : 'custom';
|
||||
|
||||
$block = array(
|
||||
'blockName' => 'core/navigation-link',
|
||||
'attrs' => array(
|
||||
'className' => $class_name,
|
||||
'description' => $menu_item->description,
|
||||
'id' => $id,
|
||||
'kind' => $kind,
|
||||
'label' => $menu_item->title,
|
||||
'opensInNewTab' => $opens_in_new_tab,
|
||||
'rel' => $rel,
|
||||
'title' => $menu_item->attr_title,
|
||||
'type' => $menu_item->object,
|
||||
'url' => $menu_item->url,
|
||||
),
|
||||
);
|
||||
|
||||
$block['innerBlocks'] = gutenberg_parse_blocks_from_menu_items(
|
||||
isset( $menu_items_by_parent_id[ $menu_item->ID ] )
|
||||
? $menu_items_by_parent_id[ $menu_item->ID ]
|
||||
: array(),
|
||||
$menu_items_by_parent_id
|
||||
);
|
||||
|
||||
$blocks[] = $block;
|
||||
}
|
||||
|
||||
return $blocks;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the top-level submenu SVG chevron icon.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
function block_core_navigation_render_submenu_icon() {
|
||||
return '<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" role="img" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the `core/navigation` block on server.
|
||||
*
|
||||
* @param array $attributes The block attributes.
|
||||
* @param array $content The saved content.
|
||||
* @param array $block The parsed block.
|
||||
*
|
||||
* @return string Returns the post content with the legacy widget added.
|
||||
*/
|
||||
function render_block_core_navigation( $attributes, $content, $block ) {
|
||||
/**
|
||||
* Deprecated:
|
||||
* The rgbTextColor and rgbBackgroundColor attributes
|
||||
* have been deprecated in favor of
|
||||
* customTextColor and customBackgroundColor ones.
|
||||
* Move the values from old attrs to the new ones.
|
||||
*/
|
||||
if ( isset( $attributes['rgbTextColor'] ) && empty( $attributes['textColor'] ) ) {
|
||||
$attributes['customTextColor'] = $attributes['rgbTextColor'];
|
||||
}
|
||||
|
||||
if ( isset( $attributes['rgbBackgroundColor'] ) && empty( $attributes['backgroundColor'] ) ) {
|
||||
$attributes['customBackgroundColor'] = $attributes['rgbBackgroundColor'];
|
||||
}
|
||||
|
||||
unset( $attributes['rgbTextColor'], $attributes['rgbBackgroundColor'] );
|
||||
|
||||
/**
|
||||
* This is for backwards compatibility after `isResponsive` attribute has been removed.
|
||||
*/
|
||||
$has_old_responsive_attribute = ! empty( $attributes['isResponsive'] ) && $attributes['isResponsive'];
|
||||
$is_responsive_menu = isset( $attributes['overlayMenu'] ) && 'never' !== $attributes['overlayMenu'] || $has_old_responsive_attribute;
|
||||
$should_load_view_script = ! wp_script_is( 'wp-block-navigation-view' ) && ( $is_responsive_menu || $attributes['openSubmenusOnClick'] || $attributes['showSubmenuIcon'] );
|
||||
if ( $should_load_view_script ) {
|
||||
wp_enqueue_script( 'wp-block-navigation-view' );
|
||||
}
|
||||
|
||||
$inner_blocks = $block->inner_blocks;
|
||||
|
||||
// If `__unstableLocation` is defined, create inner blocks from the classic menu assigned to that location.
|
||||
if ( empty( $inner_blocks ) && array_key_exists( '__unstableLocation', $attributes ) ) {
|
||||
$menu_items = gutenberg_get_menu_items_at_location( $attributes['__unstableLocation'] );
|
||||
if ( empty( $menu_items ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$menu_items_by_parent_id = gutenberg_sort_menu_items_by_parent_id( $menu_items );
|
||||
$parsed_blocks = gutenberg_parse_blocks_from_menu_items( $menu_items_by_parent_id[0], $menu_items_by_parent_id );
|
||||
$inner_blocks = new WP_Block_List( $parsed_blocks, $attributes );
|
||||
}
|
||||
|
||||
if ( ! empty( $block->context['navigationArea'] ) ) {
|
||||
$area = $block->context['navigationArea'];
|
||||
$mapping = get_option( 'fse_navigation_areas', array() );
|
||||
if ( ! empty( $mapping[ $area ] ) ) {
|
||||
$attributes['navigationMenuId'] = $mapping[ $area ];
|
||||
}
|
||||
}
|
||||
|
||||
// Load inner blocks from the navigation post.
|
||||
if ( array_key_exists( 'navigationMenuId', $attributes ) ) {
|
||||
$navigation_post = get_post( $attributes['navigationMenuId'] );
|
||||
if ( ! isset( $navigation_post ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$parsed_blocks = parse_blocks( $navigation_post->post_content );
|
||||
|
||||
// 'parse_blocks' includes a null block with '\n\n' as the content when
|
||||
// it encounters whitespace. This code strips it.
|
||||
$compacted_blocks = array_filter(
|
||||
$parsed_blocks,
|
||||
function( $block ) {
|
||||
return isset( $block['blockName'] );
|
||||
}
|
||||
);
|
||||
|
||||
// TODO - this uses the full navigation block attributes for the
|
||||
// context which could be refined.
|
||||
$inner_blocks = new WP_Block_List( $compacted_blocks, $attributes );
|
||||
}
|
||||
|
||||
if ( empty( $inner_blocks ) ) {
|
||||
return '';
|
||||
}
|
||||
$colors = block_core_navigation_build_css_colors( $attributes );
|
||||
$font_sizes = block_core_navigation_build_css_font_sizes( $attributes );
|
||||
$classes = array_merge(
|
||||
$colors['css_classes'],
|
||||
$font_sizes['css_classes'],
|
||||
$is_responsive_menu ? array( 'is-responsive' ) : array()
|
||||
);
|
||||
|
||||
$inner_blocks_html = '';
|
||||
$is_list_open = false;
|
||||
foreach ( $inner_blocks as $inner_block ) {
|
||||
if ( ( 'core/navigation-link' === $inner_block->name || 'core/home-link' === $inner_block->name || 'core/site-title' === $inner_block->name || 'core/site-logo' === $inner_block->name || 'core/navigation-submenu' === $inner_block->name ) && ! $is_list_open ) {
|
||||
$is_list_open = true;
|
||||
$inner_blocks_html .= '<ul class="wp-block-navigation__container">';
|
||||
}
|
||||
if ( 'core/navigation-link' !== $inner_block->name && 'core/home-link' !== $inner_block->name && 'core/site-title' !== $inner_block->name && 'core/site-logo' !== $inner_block->name && 'core/navigation-submenu' !== $inner_block->name && $is_list_open ) {
|
||||
$is_list_open = false;
|
||||
$inner_blocks_html .= '</ul>';
|
||||
}
|
||||
if ( 'core/site-title' === $inner_block->name || 'core/site-logo' === $inner_block->name ) {
|
||||
$inner_blocks_html .= '<li class="wp-block-navigation-item">' . $inner_block->render() . '</li>';
|
||||
} else {
|
||||
$inner_blocks_html .= $inner_block->render();
|
||||
}
|
||||
}
|
||||
|
||||
if ( $is_list_open ) {
|
||||
$inner_blocks_html .= '</ul>';
|
||||
}
|
||||
|
||||
$block_styles = isset( $attributes['styles'] ) ? $attributes['styles'] : '';
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes(
|
||||
array(
|
||||
'class' => implode( ' ', $classes ),
|
||||
'style' => $block_styles . $colors['inline_styles'] . $font_sizes['inline_styles'],
|
||||
)
|
||||
);
|
||||
|
||||
$modal_unique_id = uniqid();
|
||||
|
||||
// Determine whether or not navigation elements should be wrapped in the markup required to make it responsive,
|
||||
// return early if they don't.
|
||||
if ( ! $is_responsive_menu ) {
|
||||
return sprintf(
|
||||
'<nav %1$s>%2$s</nav>',
|
||||
$wrapper_attributes,
|
||||
$inner_blocks_html
|
||||
);
|
||||
}
|
||||
|
||||
$is_hidden_by_default = isset( $attributes['overlayMenu'] ) && 'always' === $attributes['overlayMenu'];
|
||||
|
||||
$responsive_container_classes = array(
|
||||
'wp-block-navigation__responsive-container',
|
||||
$is_hidden_by_default ? 'hidden-by-default' : '',
|
||||
);
|
||||
$open_button_classes = array(
|
||||
'wp-block-navigation__responsive-container-open',
|
||||
$is_hidden_by_default ? 'always-shown' : '',
|
||||
);
|
||||
|
||||
$responsive_container_markup = sprintf(
|
||||
'<button aria-expanded="false" aria-haspopup="true" aria-label="%3$s" class="%6$s" data-micromodal-trigger="modal-%1$s"><svg width="24" height="24" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" role="img" aria-hidden="true" focusable="false"><rect x="4" y="7.5" width="16" height="1.5" /><rect x="4" y="15" width="16" height="1.5" /></svg></button>
|
||||
<div class="%5$s" id="modal-%1$s" aria-hidden="true">
|
||||
<div class="wp-block-navigation__responsive-close" tabindex="-1" data-micromodal-close>
|
||||
<div class="wp-block-navigation__responsive-dialog" role="dialog" aria-modal="true" aria-labelledby="modal-%1$s-title" >
|
||||
<button aria-label="%4$s" data-micromodal-close class="wp-block-navigation__responsive-container-close"><svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" width="24" height="24" role="img" aria-hidden="true" focusable="false"><path d="M13 11.8l6.1-6.3-1-1-6.1 6.2-6.1-6.2-1 1 6.1 6.3-6.5 6.7 1 1 6.5-6.6 6.5 6.6 1-1z"></path></svg></button>
|
||||
<div class="wp-block-navigation__responsive-container-content" id="modal-%1$s-content">
|
||||
%2$s
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>',
|
||||
$modal_unique_id,
|
||||
$inner_blocks_html,
|
||||
__( 'Open menu' ), // Open button label.
|
||||
__( 'Close menu' ), // Close button label.
|
||||
implode( ' ', $responsive_container_classes ),
|
||||
implode( ' ', $open_button_classes )
|
||||
);
|
||||
|
||||
return sprintf(
|
||||
'<nav %1$s>%2$s</nav>',
|
||||
$wrapper_attributes,
|
||||
$responsive_container_markup
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the navigation block.
|
||||
*
|
||||
* @uses render_block_core_navigation()
|
||||
* @throws WP_Error An WP_Error exception parsing the block definition.
|
||||
*/
|
||||
function register_block_core_navigation() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/navigation',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_navigation',
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
add_action( 'init', 'register_block_core_navigation' );
|
||||
|
||||
/**
|
||||
* Filter that changes the parsed attribute values of navigation blocks contain typographic presets to contain the values directly.
|
||||
*
|
||||
* @param array $parsed_block The block being rendered.
|
||||
* @return array The block being rendered without typographic presets.
|
||||
*/
|
||||
function block_core_navigation_typographic_presets_backcompatibility( $parsed_block ) {
|
||||
if ( 'core/navigation' === $parsed_block['blockName'] ) {
|
||||
$attribute_to_prefix_map = array(
|
||||
'fontStyle' => 'var:preset|font-style|',
|
||||
'fontWeight' => 'var:preset|font-weight|',
|
||||
'textDecoration' => 'var:preset|text-decoration|',
|
||||
'textTransform' => 'var:preset|text-transform|',
|
||||
);
|
||||
foreach ( $attribute_to_prefix_map as $style_attribute => $prefix ) {
|
||||
if ( ! empty( $parsed_block['attrs']['style']['typography'][ $style_attribute ] ) ) {
|
||||
$prefix_len = strlen( $prefix );
|
||||
$attribute_value = &$parsed_block['attrs']['style']['typography'][ $style_attribute ];
|
||||
if ( 0 === strncmp( $attribute_value, $prefix, $prefix_len ) ) {
|
||||
$attribute_value = substr( $attribute_value, $prefix_len );
|
||||
}
|
||||
if ( 'textDecoration' === $style_attribute && 'strikethrough' === $attribute_value ) {
|
||||
$attribute_value = 'line-through';
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return $parsed_block;
|
||||
}
|
||||
|
||||
add_filter( 'render_block_data', 'block_core_navigation_typographic_presets_backcompatibility' );
|
|
@ -0,0 +1,124 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/navigation",
|
||||
"title": "Navigation",
|
||||
"category": "theme",
|
||||
"description": "A collection of blocks that allow visitors to get around your site.",
|
||||
"keywords": [
|
||||
"menu",
|
||||
"navigation",
|
||||
"links"
|
||||
],
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"navigationMenuId": {
|
||||
"type": "number"
|
||||
},
|
||||
"textColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"customTextColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"rgbTextColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"backgroundColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"customBackgroundColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"rgbBackgroundColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"showSubmenuIcon": {
|
||||
"type": "boolean",
|
||||
"default": true
|
||||
},
|
||||
"openSubmenusOnClick": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"overlayMenu": {
|
||||
"type": "string",
|
||||
"default": "mobile"
|
||||
},
|
||||
"__unstableLocation": {
|
||||
"type": "string"
|
||||
},
|
||||
"overlayBackgroundColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"customOverlayBackgroundColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"overlayTextColor": {
|
||||
"type": "string"
|
||||
},
|
||||
"customOverlayTextColor": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"usesContext": [ "navigationArea" ],
|
||||
"providesContext": {
|
||||
"textColor": "textColor",
|
||||
"customTextColor": "customTextColor",
|
||||
"backgroundColor": "backgroundColor",
|
||||
"customBackgroundColor": "customBackgroundColor",
|
||||
"overlayTextColor": "overlayTextColor",
|
||||
"customOverlayTextColor": "customOverlayTextColor",
|
||||
"overlayBackgroundColor": "overlayBackgroundColor",
|
||||
"customOverlayBackgroundColor": "customOverlayBackgroundColor",
|
||||
"fontSize": "fontSize",
|
||||
"customFontSize": "customFontSize",
|
||||
"showSubmenuIcon": "showSubmenuIcon",
|
||||
"openSubmenusOnClick": "openSubmenusOnClick",
|
||||
"style": "style",
|
||||
"orientation": "orientation"
|
||||
},
|
||||
"supports": {
|
||||
"align": [
|
||||
"wide",
|
||||
"full"
|
||||
],
|
||||
"anchor": true,
|
||||
"html": false,
|
||||
"inserter": true,
|
||||
"typography": {
|
||||
"fontSize": true,
|
||||
"lineHeight": true,
|
||||
"__experimentalFontStyle": true,
|
||||
"__experimentalFontWeight": true,
|
||||
"__experimentalTextTransform": true,
|
||||
"__experimentalFontFamily": true,
|
||||
"__experimentalTextDecoration": true,
|
||||
"__experimentalDefaultControls": {
|
||||
"fontSize": true
|
||||
}
|
||||
},
|
||||
"spacing": {
|
||||
"blockGap": true,
|
||||
"units": [
|
||||
"px",
|
||||
"em",
|
||||
"rem",
|
||||
"vh",
|
||||
"vw"
|
||||
],
|
||||
"__experimentalDefaultControls": {
|
||||
"blockGap": true
|
||||
}
|
||||
},
|
||||
"__experimentalLayout": {
|
||||
"allowSwitching": false,
|
||||
"allowInheriting": false,
|
||||
"default": {
|
||||
"type": "flex"
|
||||
}
|
||||
}
|
||||
},
|
||||
"viewScript": "file:./view.min.js",
|
||||
"editorStyle": "wp-block-navigation-editor",
|
||||
"style": "wp-block-navigation"
|
||||
}
|
|
@ -0,0 +1,491 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
/**
|
||||
* Editor only CSS.
|
||||
*/
|
||||
.editor-styles-wrapper .wp-block-navigation ul {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
margin-right: 0;
|
||||
padding-right: 0;
|
||||
}
|
||||
.editor-styles-wrapper .wp-block-navigation .wp-block-navigation-item.wp-block {
|
||||
margin-right: revert;
|
||||
margin-left: revert;
|
||||
}
|
||||
|
||||
.wp-block-navigation-item__label {
|
||||
display: inline;
|
||||
}
|
||||
|
||||
/**
|
||||
* Submenus.
|
||||
*/
|
||||
.wp-block-navigation__container.is-parent-of-selected-block {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.wp-block-navigation__container,
|
||||
.wp-block-navigation-item {
|
||||
background-color: inherit;
|
||||
}
|
||||
|
||||
.wp-block-navigation:not(.is-selected):not(.has-child-selected) .has-child:hover > .wp-block-navigation__submenu-container {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
.has-child.is-selected > .wp-block-navigation__submenu-container, .has-child.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
display: flex;
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
.is-dragging-components-draggable .has-child.is-dragging-within > .wp-block-navigation__submenu-container {
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
.is-editing > .wp-block-navigation__container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.is-dragging-components-draggable .wp-block-navigation-link > .wp-block-navigation__container {
|
||||
opacity: 1;
|
||||
visibility: hidden;
|
||||
}
|
||||
.is-dragging-components-draggable .wp-block-navigation-link > .wp-block-navigation__container .block-editor-block-draggable-chip-wrapper {
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
/**
|
||||
* Colors Selector component
|
||||
*/
|
||||
.block-library-colors-selector {
|
||||
width: auto;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__toggle {
|
||||
display: block;
|
||||
margin: 0 auto;
|
||||
padding: 3px;
|
||||
width: auto;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__icon-container {
|
||||
height: 30px;
|
||||
position: relative;
|
||||
margin: 0 auto;
|
||||
padding: 3px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
border-radius: 4px;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection {
|
||||
margin-right: auto;
|
||||
margin-left: auto;
|
||||
border-radius: 11px;
|
||||
box-shadow: inset 0 0 0 1px rgba(0, 0, 0, 0.2);
|
||||
width: 22px;
|
||||
min-width: 22px;
|
||||
height: 22px;
|
||||
min-height: 22px;
|
||||
line-height: 20px;
|
||||
padding: 2px;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection > svg {
|
||||
min-width: auto !important;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection.has-text-color > svg,
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection.has-text-color > svg path {
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.block-library-colors-selector__popover .color-palette-controller-container {
|
||||
padding: 16px;
|
||||
}
|
||||
.block-library-colors-selector__popover .components-base-control__label {
|
||||
height: 20px;
|
||||
line-height: 20px;
|
||||
}
|
||||
.block-library-colors-selector__popover .component-color-indicator {
|
||||
float: left;
|
||||
margin-top: 2px;
|
||||
}
|
||||
.block-library-colors-selector__popover .components-panel__body-title {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.wp-block-navigation .block-editor-button-block-appender {
|
||||
justify-content: flex-start;
|
||||
}
|
||||
|
||||
/**
|
||||
* Setup state
|
||||
*/
|
||||
.components-placeholder.wp-block-navigation-placeholder {
|
||||
outline: none;
|
||||
padding: 0;
|
||||
box-shadow: none;
|
||||
background: none;
|
||||
min-height: 0;
|
||||
color: inherit;
|
||||
}
|
||||
.components-placeholder.wp-block-navigation-placeholder .components-placeholder__fieldset {
|
||||
font-size: inherit;
|
||||
}
|
||||
.components-placeholder.wp-block-navigation-placeholder .components-placeholder__fieldset .components-button {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.is-selected .components-placeholder.wp-block-navigation-placeholder {
|
||||
color: #1e1e1e;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder .components-spinner {
|
||||
margin-top: -4px;
|
||||
margin-right: 4px;
|
||||
vertical-align: middle;
|
||||
margin-left: 7px;
|
||||
}
|
||||
|
||||
@keyframes loadingpulse {
|
||||
0% {
|
||||
opacity: 1;
|
||||
}
|
||||
50% {
|
||||
opacity: 0.5;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
flex-wrap: nowrap;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview.is-loading {
|
||||
animation: loadingpulse 1s linear infinite;
|
||||
animation-delay: 0.5s;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item {
|
||||
position: relative;
|
||||
min-width: 72px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item::before {
|
||||
display: block;
|
||||
content: "";
|
||||
border-radius: 2px;
|
||||
background: currentColor;
|
||||
height: 16px;
|
||||
width: 100%;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon {
|
||||
height: 24px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon svg {
|
||||
fill: currentColor;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item,
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon {
|
||||
opacity: 0.3;
|
||||
}
|
||||
.wp-block-navigation.is-selected .wp-block-navigation-placeholder__preview:not(.is-loading) {
|
||||
display: flex;
|
||||
opacity: 0;
|
||||
width: 0;
|
||||
overflow: hidden;
|
||||
flex-wrap: nowrap;
|
||||
flex: 0;
|
||||
}
|
||||
.is-vertical.is-selected .wp-block-navigation-placeholder__preview:not(.is-loading), .wp-block-navigation.is-selected .is-small .wp-block-navigation-placeholder__preview:not(.is-loading), .wp-block-navigation.is-selected .is-medium .wp-block-navigation-placeholder__preview:not(.is-loading) {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder__controls {
|
||||
padding: 8px;
|
||||
border-radius: 2px;
|
||||
background-color: #fff;
|
||||
box-shadow: inset 0 0 0 1px #1e1e1e;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
display: none;
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
float: right;
|
||||
width: 100%;
|
||||
}
|
||||
.is-large .wp-block-navigation-placeholder__controls {
|
||||
padding: 4px 8px;
|
||||
}
|
||||
.wp-block-navigation.is-selected .wp-block-navigation-placeholder__controls {
|
||||
display: flex;
|
||||
}
|
||||
.is-small .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions, .is-medium .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions, .is-vertical .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions {
|
||||
flex-direction: column;
|
||||
}
|
||||
.is-selected.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
display: inline-flex;
|
||||
padding: 12px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__icon {
|
||||
margin-left: 12px;
|
||||
height: 36px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
margin-left: 12px;
|
||||
padding: 0;
|
||||
align-items: center;
|
||||
justify-content: flex-start;
|
||||
line-height: 0;
|
||||
margin-right: 5px;
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator svg {
|
||||
margin-left: 4px;
|
||||
}
|
||||
.is-vertical .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
margin-bottom: 4px;
|
||||
margin-right: 0;
|
||||
}
|
||||
.is-large .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
display: inline-flex;
|
||||
}
|
||||
|
||||
.is-vertical .wp-block-navigation-placeholder,
|
||||
.is-vertical .wp-block-navigation-placeholder__preview,
|
||||
.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
min-height: 156px;
|
||||
}
|
||||
|
||||
.is-vertical .wp-block-navigation-placeholder__preview,
|
||||
.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder__actions {
|
||||
display: flex;
|
||||
font-size: 13px;
|
||||
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen-Sans, Ubuntu, Cantarell, "Helvetica Neue", sans-serif;
|
||||
}
|
||||
.wp-block-navigation-placeholder__actions .components-button.components-dropdown-menu__toggle.has-icon {
|
||||
padding: 6px 12px 6px 4px;
|
||||
display: flex;
|
||||
flex-direction: row-reverse;
|
||||
}
|
||||
.wp-block-navigation-placeholder__actions .components-dropdown,
|
||||
.wp-block-navigation-placeholder__actions > .components-button {
|
||||
margin-left: 12px;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mobile menu.
|
||||
*/
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container:not(.is-menu-open) .components-button.wp-block-navigation__responsive-container-close {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
position: fixed;
|
||||
top: 155px;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 93px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
right: 36px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 960px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
right: 160px;
|
||||
}
|
||||
}
|
||||
|
||||
@media (min-width: 782px) {
|
||||
.has-fixed-toolbar .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 141px;
|
||||
}
|
||||
}
|
||||
|
||||
.is-mobile-preview .wp-block-navigation__responsive-container.is-menu-open,
|
||||
.is-tablet-preview .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 141px;
|
||||
}
|
||||
|
||||
.is-sidebar-opened .wp-block-navigation__responsive-container.is-menu-open {
|
||||
left: 280px;
|
||||
}
|
||||
|
||||
.is-fullscreen-mode .wp-block-navigation__responsive-container.is-menu-open {
|
||||
right: 0;
|
||||
top: 155px;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.is-fullscreen-mode .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 61px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.is-fullscreen-mode .has-fixed-toolbar .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 109px;
|
||||
}
|
||||
}
|
||||
.is-fullscreen-mode .is-mobile-preview .wp-block-navigation__responsive-container.is-menu-open,
|
||||
.is-fullscreen-mode .is-tablet-preview .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 109px;
|
||||
}
|
||||
|
||||
body.editor-styles-wrapper .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 0;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
right: 0;
|
||||
}
|
||||
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-close {
|
||||
pointer-events: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-close .wp-block-navigation__responsive-container-close,
|
||||
.wp-block-navigation__responsive-close .block-editor-block-list__layout * {
|
||||
pointer-events: all;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__responsive-close .wp-block-pages-list__item__link {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.components-button.wp-block-navigation__responsive-container-open.wp-block-navigation__responsive-container-open,
|
||||
.components-button.wp-block-navigation__responsive-container-close.wp-block-navigation__responsive-container-close {
|
||||
padding: 0;
|
||||
height: auto;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.is-menu-open .wp-block-navigation__responsive-container-content * .block-list-appender {
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
@keyframes fadein {
|
||||
0% {
|
||||
opacity: 0;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes {
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes .components-spinner {
|
||||
position: absolute;
|
||||
top: calc(50% - 18px / 2);
|
||||
right: calc(50% - 18px / 2);
|
||||
opacity: 0;
|
||||
animation: 0.5s linear 2s normal forwards fadein;
|
||||
}
|
||||
|
||||
@keyframes fadeouthalf {
|
||||
0% {
|
||||
opacity: 1;
|
||||
}
|
||||
100% {
|
||||
opacity: 0.5;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes-overlay.is-saving {
|
||||
opacity: 1;
|
||||
animation: 0.5s linear 2s normal forwards fadeouthalf;
|
||||
}
|
||||
|
||||
.wp-block-navigation-delete-menu-button {
|
||||
width: 100%;
|
||||
justify-content: center;
|
||||
margin-bottom: 16px;
|
||||
}
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,491 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
/**
|
||||
* Editor only CSS.
|
||||
*/
|
||||
.editor-styles-wrapper .wp-block-navigation ul {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
margin-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
.editor-styles-wrapper .wp-block-navigation .wp-block-navigation-item.wp-block {
|
||||
margin-left: revert;
|
||||
margin-right: revert;
|
||||
}
|
||||
|
||||
.wp-block-navigation-item__label {
|
||||
display: inline;
|
||||
}
|
||||
|
||||
/**
|
||||
* Submenus.
|
||||
*/
|
||||
.wp-block-navigation__container.is-parent-of-selected-block {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.wp-block-navigation__container,
|
||||
.wp-block-navigation-item {
|
||||
background-color: inherit;
|
||||
}
|
||||
|
||||
.wp-block-navigation:not(.is-selected):not(.has-child-selected) .has-child:hover > .wp-block-navigation__submenu-container {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
.has-child.is-selected > .wp-block-navigation__submenu-container, .has-child.has-child-selected > .wp-block-navigation__submenu-container {
|
||||
display: flex;
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
.is-dragging-components-draggable .has-child.is-dragging-within > .wp-block-navigation__submenu-container {
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
.is-editing > .wp-block-navigation__container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.is-dragging-components-draggable .wp-block-navigation-link > .wp-block-navigation__container {
|
||||
opacity: 1;
|
||||
visibility: hidden;
|
||||
}
|
||||
.is-dragging-components-draggable .wp-block-navigation-link > .wp-block-navigation__container .block-editor-block-draggable-chip-wrapper {
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
/**
|
||||
* Colors Selector component
|
||||
*/
|
||||
.block-library-colors-selector {
|
||||
width: auto;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__toggle {
|
||||
display: block;
|
||||
margin: 0 auto;
|
||||
padding: 3px;
|
||||
width: auto;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__icon-container {
|
||||
height: 30px;
|
||||
position: relative;
|
||||
margin: 0 auto;
|
||||
padding: 3px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
border-radius: 4px;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection {
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
border-radius: 11px;
|
||||
box-shadow: inset 0 0 0 1px rgba(0, 0, 0, 0.2);
|
||||
width: 22px;
|
||||
min-width: 22px;
|
||||
height: 22px;
|
||||
min-height: 22px;
|
||||
line-height: 20px;
|
||||
padding: 2px;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection > svg {
|
||||
min-width: auto !important;
|
||||
}
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection.has-text-color > svg,
|
||||
.block-library-colors-selector .block-library-colors-selector__state-selection.has-text-color > svg path {
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.block-library-colors-selector__popover .color-palette-controller-container {
|
||||
padding: 16px;
|
||||
}
|
||||
.block-library-colors-selector__popover .components-base-control__label {
|
||||
height: 20px;
|
||||
line-height: 20px;
|
||||
}
|
||||
.block-library-colors-selector__popover .component-color-indicator {
|
||||
float: right;
|
||||
margin-top: 2px;
|
||||
}
|
||||
.block-library-colors-selector__popover .components-panel__body-title {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.wp-block-navigation .block-editor-button-block-appender {
|
||||
justify-content: flex-start;
|
||||
}
|
||||
|
||||
/**
|
||||
* Setup state
|
||||
*/
|
||||
.components-placeholder.wp-block-navigation-placeholder {
|
||||
outline: none;
|
||||
padding: 0;
|
||||
box-shadow: none;
|
||||
background: none;
|
||||
min-height: 0;
|
||||
color: inherit;
|
||||
}
|
||||
.components-placeholder.wp-block-navigation-placeholder .components-placeholder__fieldset {
|
||||
font-size: inherit;
|
||||
}
|
||||
.components-placeholder.wp-block-navigation-placeholder .components-placeholder__fieldset .components-button {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.is-selected .components-placeholder.wp-block-navigation-placeholder {
|
||||
color: #1e1e1e;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder .components-spinner {
|
||||
margin-top: -4px;
|
||||
margin-left: 4px;
|
||||
vertical-align: middle;
|
||||
margin-right: 7px;
|
||||
}
|
||||
|
||||
@keyframes loadingpulse {
|
||||
0% {
|
||||
opacity: 1;
|
||||
}
|
||||
50% {
|
||||
opacity: 0.5;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
flex-wrap: nowrap;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview.is-loading {
|
||||
animation: loadingpulse 1s linear infinite;
|
||||
animation-delay: 0.5s;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item {
|
||||
position: relative;
|
||||
min-width: 72px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item::before {
|
||||
display: block;
|
||||
content: "";
|
||||
border-radius: 2px;
|
||||
background: currentColor;
|
||||
height: 16px;
|
||||
width: 100%;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon {
|
||||
height: 24px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon svg {
|
||||
fill: currentColor;
|
||||
}
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-item.wp-block-navigation-item,
|
||||
.wp-block-navigation-placeholder__preview .wp-block-navigation-placeholder__preview-search-icon {
|
||||
opacity: 0.3;
|
||||
}
|
||||
.wp-block-navigation.is-selected .wp-block-navigation-placeholder__preview:not(.is-loading) {
|
||||
display: flex;
|
||||
opacity: 0;
|
||||
width: 0;
|
||||
overflow: hidden;
|
||||
flex-wrap: nowrap;
|
||||
flex: 0;
|
||||
}
|
||||
.is-vertical.is-selected .wp-block-navigation-placeholder__preview:not(.is-loading), .wp-block-navigation.is-selected .is-small .wp-block-navigation-placeholder__preview:not(.is-loading), .wp-block-navigation.is-selected .is-medium .wp-block-navigation-placeholder__preview:not(.is-loading) {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder__controls {
|
||||
padding: 8px;
|
||||
border-radius: 2px;
|
||||
background-color: #fff;
|
||||
box-shadow: inset 0 0 0 1px #1e1e1e;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
display: none;
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
float: left;
|
||||
width: 100%;
|
||||
}
|
||||
.is-large .wp-block-navigation-placeholder__controls {
|
||||
padding: 4px 8px;
|
||||
}
|
||||
.wp-block-navigation.is-selected .wp-block-navigation-placeholder__controls {
|
||||
display: flex;
|
||||
}
|
||||
.is-small .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions, .is-medium .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions, .is-vertical .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions {
|
||||
flex-direction: column;
|
||||
}
|
||||
.is-selected.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
display: inline-flex;
|
||||
padding: 12px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__icon {
|
||||
margin-right: 12px;
|
||||
height: 36px;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
margin-right: 12px;
|
||||
padding: 0;
|
||||
align-items: center;
|
||||
justify-content: flex-start;
|
||||
line-height: 0;
|
||||
margin-left: 5px;
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator svg {
|
||||
margin-right: 4px;
|
||||
}
|
||||
.is-vertical .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
margin-bottom: 4px;
|
||||
margin-left: 0;
|
||||
}
|
||||
.is-large .wp-block-navigation-placeholder__controls .wp-block-navigation-placeholder__actions__indicator {
|
||||
display: inline-flex;
|
||||
}
|
||||
|
||||
.is-vertical .wp-block-navigation-placeholder,
|
||||
.is-vertical .wp-block-navigation-placeholder__preview,
|
||||
.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
min-height: 156px;
|
||||
}
|
||||
|
||||
.is-vertical .wp-block-navigation-placeholder__preview,
|
||||
.is-vertical .wp-block-navigation-placeholder__controls {
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
.wp-block-navigation-placeholder__actions {
|
||||
display: flex;
|
||||
font-size: 13px;
|
||||
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen-Sans, Ubuntu, Cantarell, "Helvetica Neue", sans-serif;
|
||||
}
|
||||
.wp-block-navigation-placeholder__actions .components-button.components-dropdown-menu__toggle.has-icon {
|
||||
padding: 6px 4px 6px 12px;
|
||||
display: flex;
|
||||
flex-direction: row-reverse;
|
||||
}
|
||||
.wp-block-navigation-placeholder__actions .components-dropdown,
|
||||
.wp-block-navigation-placeholder__actions > .components-button {
|
||||
margin-right: 12px;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mobile menu.
|
||||
*/
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container:not(.is-menu-open) .components-button.wp-block-navigation__responsive-container-close {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
position: fixed;
|
||||
top: 155px;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 93px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
left: 36px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 960px) {
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
left: 160px;
|
||||
}
|
||||
}
|
||||
|
||||
@media (min-width: 782px) {
|
||||
.has-fixed-toolbar .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 141px;
|
||||
}
|
||||
}
|
||||
|
||||
.is-mobile-preview .wp-block-navigation__responsive-container.is-menu-open,
|
||||
.is-tablet-preview .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 141px;
|
||||
}
|
||||
|
||||
.is-sidebar-opened .wp-block-navigation__responsive-container.is-menu-open {
|
||||
right: 280px;
|
||||
}
|
||||
|
||||
.is-fullscreen-mode .wp-block-navigation__responsive-container.is-menu-open {
|
||||
left: 0;
|
||||
top: 155px;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.is-fullscreen-mode .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 61px;
|
||||
}
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.is-fullscreen-mode .has-fixed-toolbar .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 109px;
|
||||
}
|
||||
}
|
||||
.is-fullscreen-mode .is-mobile-preview .wp-block-navigation__responsive-container.is-menu-open,
|
||||
.is-fullscreen-mode .is-tablet-preview .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 109px;
|
||||
}
|
||||
|
||||
body.editor-styles-wrapper .wp-block-navigation__responsive-container.is-menu-open {
|
||||
top: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-close {
|
||||
pointer-events: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-close .wp-block-navigation__responsive-container-close,
|
||||
.wp-block-navigation__responsive-close .block-editor-block-list__layout * {
|
||||
pointer-events: all;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__responsive-close .wp-block-pages-list__item__link {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.components-button.wp-block-navigation__responsive-container-open.wp-block-navigation__responsive-container-open,
|
||||
.components-button.wp-block-navigation__responsive-container-close.wp-block-navigation__responsive-container-close {
|
||||
padding: 0;
|
||||
height: auto;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.is-menu-open .wp-block-navigation__responsive-container-content * .block-list-appender {
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
@keyframes fadein {
|
||||
0% {
|
||||
opacity: 0;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes {
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes .components-spinner {
|
||||
position: absolute;
|
||||
top: calc(50% - 18px / 2);
|
||||
left: calc(50% - 18px / 2);
|
||||
opacity: 0;
|
||||
animation: 0.5s linear 2s normal forwards fadein;
|
||||
}
|
||||
|
||||
@keyframes fadeouthalf {
|
||||
0% {
|
||||
opacity: 1;
|
||||
}
|
||||
100% {
|
||||
opacity: 0.5;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation__unsaved-changes-overlay.is-saving {
|
||||
opacity: 1;
|
||||
animation: 0.5s linear 2s normal forwards fadeouthalf;
|
||||
}
|
||||
|
||||
.wp-block-navigation-delete-menu-button {
|
||||
width: 100%;
|
||||
justify-content: center;
|
||||
margin-bottom: 16px;
|
||||
}
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,430 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation {
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation ul {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
margin-right: 0;
|
||||
padding-right: 0;
|
||||
}
|
||||
.wp-block-navigation ul,
|
||||
.wp-block-navigation ul li {
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item .wp-block-navigation__submenu-container:empty {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item__content {
|
||||
color: inherit;
|
||||
display: block;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] .wp-block-navigation-item,
|
||||
.wp-block-navigation[style*=text-decoration] .wp-block-navigation__submenu-container {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] a {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] a:focus, .wp-block-navigation[style*=text-decoration] a:active {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation:not([style*=text-decoration]) a {
|
||||
text-decoration: none;
|
||||
}
|
||||
.wp-block-navigation:not([style*=text-decoration]) a:focus, .wp-block-navigation:not([style*=text-decoration]) a:active {
|
||||
text-decoration: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation__submenu-icon {
|
||||
align-self: center;
|
||||
height: inherit;
|
||||
line-height: 0;
|
||||
margin-right: 6px;
|
||||
padding: 0;
|
||||
background-color: inherit;
|
||||
color: currentColor;
|
||||
border: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation__submenu-icon svg {
|
||||
display: inline-block;
|
||||
stroke: currentColor;
|
||||
}
|
||||
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) {
|
||||
background-color: inherit;
|
||||
color: inherit;
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: normal;
|
||||
opacity: 0;
|
||||
transition: opacity 0.1s linear;
|
||||
visibility: hidden;
|
||||
width: 0;
|
||||
height: 0;
|
||||
right: -1px;
|
||||
top: 100%;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) > .wp-block-navigation-item > .wp-block-navigation-item__content {
|
||||
display: flex;
|
||||
flex-grow: 1;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) > .wp-block-navigation-item > .wp-block-navigation-item__content .wp-block-navigation__submenu-icon {
|
||||
margin-left: 0;
|
||||
margin-right: auto;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation-item__content {
|
||||
margin: 0;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-container {
|
||||
right: 100%;
|
||||
top: -1px;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-container::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
left: 100%;
|
||||
height: 100%;
|
||||
display: block;
|
||||
width: 0.5em;
|
||||
background: transparent;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-icon svg {
|
||||
transform: rotate(90deg);
|
||||
}
|
||||
}
|
||||
.wp-block-navigation .has-child:where(:not(.open-on-click)):hover > .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
.wp-block-navigation .has-child:where(:not(.open-on-click):not(.open-on-hover-click)):focus-within > .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
.wp-block-navigation .has-child .wp-block-navigation-submenu__toggle[aria-expanded=true] + .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
|
||||
.wp-block-navigation.has-background .has-child .wp-block-navigation__submenu-container {
|
||||
right: 0;
|
||||
top: 100%;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation.has-background .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
right: 100%;
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Margins
|
||||
*/
|
||||
.wp-block-navigation,
|
||||
.wp-block-navigation .wp-block-page-list,
|
||||
.wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container-content {
|
||||
gap: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
|
||||
.wp-block-navigation:where(.has-background),
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation .wp-block-page-list,
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation__container {
|
||||
gap: var(--wp--style--block-gap, 0.5em);
|
||||
}
|
||||
|
||||
/**
|
||||
* Paddings
|
||||
*/
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation-item__content {
|
||||
padding: 0.5em 1em;
|
||||
}
|
||||
|
||||
.wp-block-navigation :where(.wp-block-navigation__submenu-container) .wp-block-navigation-item__content {
|
||||
padding: 0.5em 1em;
|
||||
}
|
||||
|
||||
/**
|
||||
* Justifications.
|
||||
*/
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation.items-justified-space-between .wp-block-page-list > .has-child:last-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-space-between > .wp-block-navigation__container > .has-child:last-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-page-list > .has-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-navigation__container .has-child .wp-block-navigation__submenu-container {
|
||||
right: auto;
|
||||
left: 0;
|
||||
}
|
||||
.wp-block-navigation.items-justified-space-between .wp-block-page-list > .has-child:last-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-space-between > .wp-block-navigation__container > .has-child:last-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-page-list > .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-navigation__container .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
right: auto;
|
||||
left: 100%;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation:not(.has-background) .wp-block-navigation__submenu-container {
|
||||
background-color: #fff;
|
||||
color: #000;
|
||||
border: 1px solid rgba(0, 0, 0, 0.15);
|
||||
}
|
||||
|
||||
.wp-block-navigation__container {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding-right: 0;
|
||||
}
|
||||
.wp-block-navigation__container .is-responsive {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mobile menu.
|
||||
*/
|
||||
.wp-block-navigation__responsive-container {
|
||||
display: none;
|
||||
position: fixed;
|
||||
top: 0;
|
||||
right: 0;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container .wp-block-navigation__responsive-container-content {
|
||||
display: contents;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
overflow: auto;
|
||||
z-index: 100000;
|
||||
padding: 72px 24px 24px 24px;
|
||||
background-color: inherit;
|
||||
align-items: inherit;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: var(--justification-setting, inherit);
|
||||
overflow: auto;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-icon {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .has-child .submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .has-child .wp-block-navigation__submenu-container {
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
height: auto;
|
||||
width: auto;
|
||||
overflow: initial;
|
||||
min-width: 200px;
|
||||
position: static;
|
||||
border: none;
|
||||
padding-right: 32px;
|
||||
padding-left: 32px;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container {
|
||||
gap: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container .wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container .wp-block-navigation__container {
|
||||
padding-top: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation-item__content {
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation-item,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-page-list {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: var(--justification-setting, inherit);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item {
|
||||
color: inherit !important;
|
||||
background: transparent !important;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container {
|
||||
left: auto;
|
||||
right: auto;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container:not(.hidden-by-default):not(.is-menu-open) {
|
||||
display: contents;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
z-index: 2;
|
||||
background-color: inherit;
|
||||
}
|
||||
.wp-block-navigation__responsive-container:not(.hidden-by-default):not(.is-menu-open) .wp-block-navigation__responsive-container-close {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container {
|
||||
right: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation:not(.has-background) .wp-block-navigation__responsive-container.is-menu-open {
|
||||
background-color: #fff;
|
||||
color: #000;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-open,
|
||||
.wp-block-navigation__responsive-container-close {
|
||||
vertical-align: middle;
|
||||
cursor: pointer;
|
||||
color: currentColor;
|
||||
background: transparent;
|
||||
border: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container-open svg,
|
||||
.wp-block-navigation__responsive-container-close svg {
|
||||
fill: currentColor;
|
||||
pointer-events: none;
|
||||
display: block;
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-open {
|
||||
display: flex;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container-open:not(.always-shown) {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-close {
|
||||
position: absolute;
|
||||
top: 24px;
|
||||
left: 24px;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-close {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.is-menu-open .wp-block-navigation__responsive-close,
|
||||
.is-menu-open .wp-block-navigation__responsive-dialog,
|
||||
.is-menu-open .wp-block-navigation__responsive-container-content {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
html.has-modal-open {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-close,
|
||||
.wp-block-navigation__responsive-dialog,
|
||||
.wp-block-navigation__container {
|
||||
display: contents;
|
||||
}
|
||||
.is-menu-open .wp-block-navigation__responsive-close,
|
||||
.is-menu-open .wp-block-navigation__responsive-dialog,
|
||||
.is-menu-open .wp-block-navigation__container {
|
||||
align-items: inherit;
|
||||
}
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,430 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-navigation {
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation ul {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
margin-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
.wp-block-navigation ul,
|
||||
.wp-block-navigation ul li {
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
position: relative;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item .wp-block-navigation__submenu-container:empty {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation-item__content {
|
||||
color: inherit;
|
||||
display: block;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] .wp-block-navigation-item,
|
||||
.wp-block-navigation[style*=text-decoration] .wp-block-navigation__submenu-container {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] a {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation[style*=text-decoration] a:focus, .wp-block-navigation[style*=text-decoration] a:active {
|
||||
text-decoration: inherit;
|
||||
}
|
||||
.wp-block-navigation:not([style*=text-decoration]) a {
|
||||
text-decoration: none;
|
||||
}
|
||||
.wp-block-navigation:not([style*=text-decoration]) a:focus, .wp-block-navigation:not([style*=text-decoration]) a:active {
|
||||
text-decoration: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation__submenu-icon {
|
||||
align-self: center;
|
||||
height: inherit;
|
||||
line-height: 0;
|
||||
margin-left: 6px;
|
||||
padding: 0;
|
||||
background-color: inherit;
|
||||
color: currentColor;
|
||||
border: none;
|
||||
}
|
||||
.wp-block-navigation .wp-block-navigation__submenu-icon svg {
|
||||
display: inline-block;
|
||||
stroke: currentColor;
|
||||
}
|
||||
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) {
|
||||
background-color: inherit;
|
||||
color: inherit;
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: normal;
|
||||
opacity: 0;
|
||||
transition: opacity 0.1s linear;
|
||||
visibility: hidden;
|
||||
width: 0;
|
||||
height: 0;
|
||||
left: -1px;
|
||||
top: 100%;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) > .wp-block-navigation-item > .wp-block-navigation-item__content {
|
||||
display: flex;
|
||||
flex-grow: 1;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) > .wp-block-navigation-item > .wp-block-navigation-item__content .wp-block-navigation__submenu-icon {
|
||||
margin-right: 0;
|
||||
margin-left: auto;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation-item__content {
|
||||
margin: 0;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-container {
|
||||
left: 100%;
|
||||
top: -1px;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-container::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
right: 100%;
|
||||
height: 100%;
|
||||
display: block;
|
||||
width: 0.5em;
|
||||
background: transparent;
|
||||
}
|
||||
.wp-block-navigation .has-child :where(.wp-block-navigation__submenu-container) .wp-block-navigation__submenu-icon svg {
|
||||
transform: rotate(-90deg);
|
||||
}
|
||||
}
|
||||
.wp-block-navigation .has-child:where(:not(.open-on-click)):hover > .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
.wp-block-navigation .has-child:where(:not(.open-on-click):not(.open-on-hover-click)):focus-within > .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
.wp-block-navigation .has-child .wp-block-navigation-submenu__toggle[aria-expanded=true] + .wp-block-navigation__submenu-container {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
width: auto;
|
||||
height: auto;
|
||||
min-width: 200px;
|
||||
}
|
||||
|
||||
.wp-block-navigation.has-background .has-child .wp-block-navigation__submenu-container {
|
||||
left: 0;
|
||||
top: 100%;
|
||||
}
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation.has-background .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
left: 100%;
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Margins
|
||||
*/
|
||||
.wp-block-navigation,
|
||||
.wp-block-navigation .wp-block-page-list,
|
||||
.wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container-content {
|
||||
gap: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
|
||||
.wp-block-navigation:where(.has-background),
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation .wp-block-page-list,
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation__container {
|
||||
gap: var(--wp--style--block-gap, 0.5em);
|
||||
}
|
||||
|
||||
/**
|
||||
* Paddings
|
||||
*/
|
||||
.wp-block-navigation:where(.has-background) .wp-block-navigation-item__content {
|
||||
padding: 0.5em 1em;
|
||||
}
|
||||
|
||||
.wp-block-navigation :where(.wp-block-navigation__submenu-container) .wp-block-navigation-item__content {
|
||||
padding: 0.5em 1em;
|
||||
}
|
||||
|
||||
/**
|
||||
* Justifications.
|
||||
*/
|
||||
@media (min-width: 782px) {
|
||||
.wp-block-navigation.items-justified-space-between .wp-block-page-list > .has-child:last-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-space-between > .wp-block-navigation__container > .has-child:last-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-page-list > .has-child .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-navigation__container .has-child .wp-block-navigation__submenu-container {
|
||||
left: auto;
|
||||
right: 0;
|
||||
}
|
||||
.wp-block-navigation.items-justified-space-between .wp-block-page-list > .has-child:last-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-space-between > .wp-block-navigation__container > .has-child:last-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-page-list > .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation.items-justified-right .wp-block-navigation__container .has-child .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container {
|
||||
left: auto;
|
||||
right: 100%;
|
||||
}
|
||||
}
|
||||
.wp-block-navigation:not(.has-background) .wp-block-navigation__submenu-container {
|
||||
background-color: #fff;
|
||||
color: #000;
|
||||
border: 1px solid rgba(0, 0, 0, 0.15);
|
||||
}
|
||||
|
||||
.wp-block-navigation__container {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
.wp-block-navigation__container .is-responsive {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mobile menu.
|
||||
*/
|
||||
.wp-block-navigation__responsive-container {
|
||||
display: none;
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container .wp-block-navigation__responsive-container-content {
|
||||
display: contents;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
overflow: auto;
|
||||
z-index: 100000;
|
||||
padding: 72px 24px 24px 24px;
|
||||
background-color: inherit;
|
||||
align-items: inherit;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: var(--justification-setting, inherit);
|
||||
overflow: auto;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-icon {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .has-child .submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .has-child .wp-block-navigation__submenu-container {
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
height: auto;
|
||||
width: auto;
|
||||
overflow: initial;
|
||||
min-width: 200px;
|
||||
position: static;
|
||||
border: none;
|
||||
padding-left: 32px;
|
||||
padding-right: 32px;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container {
|
||||
gap: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__submenu-container .wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container .wp-block-navigation__container {
|
||||
padding-top: var(--wp--style--block-gap, 2em);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation-item__content {
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation__container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-navigation-item,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content .wp-block-page-list {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: var(--justification-setting, inherit);
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item .wp-block-navigation__submenu-container,
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item {
|
||||
color: inherit !important;
|
||||
background: transparent !important;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container {
|
||||
right: auto;
|
||||
left: auto;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container:not(.hidden-by-default):not(.is-menu-open) {
|
||||
display: contents;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
z-index: 2;
|
||||
background-color: inherit;
|
||||
}
|
||||
.wp-block-navigation__responsive-container:not(.hidden-by-default):not(.is-menu-open) .wp-block-navigation__responsive-container-close {
|
||||
display: none;
|
||||
}
|
||||
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container.wp-block-navigation__submenu-container {
|
||||
left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation:not(.has-background) .wp-block-navigation__responsive-container.is-menu-open {
|
||||
background-color: #fff;
|
||||
color: #000;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-open,
|
||||
.wp-block-navigation__responsive-container-close {
|
||||
vertical-align: middle;
|
||||
cursor: pointer;
|
||||
color: currentColor;
|
||||
background: transparent;
|
||||
border: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-navigation__responsive-container-open svg,
|
||||
.wp-block-navigation__responsive-container-close svg {
|
||||
fill: currentColor;
|
||||
pointer-events: none;
|
||||
display: block;
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-open {
|
||||
display: flex;
|
||||
}
|
||||
@media (min-width: 600px) {
|
||||
.wp-block-navigation__responsive-container-open:not(.always-shown) {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-container-close {
|
||||
position: absolute;
|
||||
top: 24px;
|
||||
right: 24px;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-close {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.is-menu-open .wp-block-navigation__responsive-close,
|
||||
.is-menu-open .wp-block-navigation__responsive-dialog,
|
||||
.is-menu-open .wp-block-navigation__responsive-container-content {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
html.has-modal-open {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.wp-block-navigation__responsive-close,
|
||||
.wp-block-navigation__responsive-dialog,
|
||||
.wp-block-navigation__container {
|
||||
display: contents;
|
||||
}
|
||||
.is-menu-open .wp-block-navigation__responsive-close,
|
||||
.is-menu-open .wp-block-navigation__responsive-dialog,
|
||||
.is-menu-open .wp-block-navigation__container {
|
||||
align-items: inherit;
|
||||
}
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1 @@
|
|||
<?php return array('dependencies' => array(), 'version' => 'f63141a5a5be0a629c2580a2c4b8e4f8');
|
|
@ -0,0 +1,619 @@
|
|||
/******/ (function(modules) { // webpackBootstrap
|
||||
/******/ // The module cache
|
||||
/******/ var installedModules = {};
|
||||
/******/
|
||||
/******/ // The require function
|
||||
/******/ function __webpack_require__(moduleId) {
|
||||
/******/
|
||||
/******/ // Check if module is in cache
|
||||
/******/ if(installedModules[moduleId]) {
|
||||
/******/ return installedModules[moduleId].exports;
|
||||
/******/ }
|
||||
/******/ // Create a new module (and put it into the cache)
|
||||
/******/ var module = installedModules[moduleId] = {
|
||||
/******/ i: moduleId,
|
||||
/******/ l: false,
|
||||
/******/ exports: {}
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // Execute the module function
|
||||
/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
|
||||
/******/
|
||||
/******/ // Flag the module as loaded
|
||||
/******/ module.l = true;
|
||||
/******/
|
||||
/******/ // Return the exports of the module
|
||||
/******/ return module.exports;
|
||||
/******/ }
|
||||
/******/
|
||||
/******/
|
||||
/******/ // expose the modules object (__webpack_modules__)
|
||||
/******/ __webpack_require__.m = modules;
|
||||
/******/
|
||||
/******/ // expose the module cache
|
||||
/******/ __webpack_require__.c = installedModules;
|
||||
/******/
|
||||
/******/ // define getter function for harmony exports
|
||||
/******/ __webpack_require__.d = function(exports, name, getter) {
|
||||
/******/ if(!__webpack_require__.o(exports, name)) {
|
||||
/******/ Object.defineProperty(exports, name, { enumerable: true, get: getter });
|
||||
/******/ }
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // define __esModule on exports
|
||||
/******/ __webpack_require__.r = function(exports) {
|
||||
/******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
|
||||
/******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
|
||||
/******/ }
|
||||
/******/ Object.defineProperty(exports, '__esModule', { value: true });
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // create a fake namespace object
|
||||
/******/ // mode & 1: value is a module id, require it
|
||||
/******/ // mode & 2: merge all properties of value into the ns
|
||||
/******/ // mode & 4: return value when already ns object
|
||||
/******/ // mode & 8|1: behave like require
|
||||
/******/ __webpack_require__.t = function(value, mode) {
|
||||
/******/ if(mode & 1) value = __webpack_require__(value);
|
||||
/******/ if(mode & 8) return value;
|
||||
/******/ if((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;
|
||||
/******/ var ns = Object.create(null);
|
||||
/******/ __webpack_require__.r(ns);
|
||||
/******/ Object.defineProperty(ns, 'default', { enumerable: true, value: value });
|
||||
/******/ if(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));
|
||||
/******/ return ns;
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // getDefaultExport function for compatibility with non-harmony modules
|
||||
/******/ __webpack_require__.n = function(module) {
|
||||
/******/ var getter = module && module.__esModule ?
|
||||
/******/ function getDefault() { return module['default']; } :
|
||||
/******/ function getModuleExports() { return module; };
|
||||
/******/ __webpack_require__.d(getter, 'a', getter);
|
||||
/******/ return getter;
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // Object.prototype.hasOwnProperty.call
|
||||
/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
|
||||
/******/
|
||||
/******/ // __webpack_public_path__
|
||||
/******/ __webpack_require__.p = "";
|
||||
/******/
|
||||
/******/
|
||||
/******/ // Load entry module and return exports
|
||||
/******/ return __webpack_require__(__webpack_require__.s = "kVj6");
|
||||
/******/ })
|
||||
/************************************************************************/
|
||||
/******/ ({
|
||||
|
||||
/***/ "kVj6":
|
||||
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
||||
|
||||
"use strict";
|
||||
// ESM COMPAT FLAG
|
||||
__webpack_require__.r(__webpack_exports__);
|
||||
|
||||
// CONCATENATED MODULE: ./node_modules/micromodal/dist/micromodal.es.js
|
||||
function _classCallCheck(instance, Constructor) {
|
||||
if (!(instance instanceof Constructor)) {
|
||||
throw new TypeError("Cannot call a class as a function");
|
||||
}
|
||||
}
|
||||
|
||||
function _defineProperties(target, props) {
|
||||
for (var i = 0; i < props.length; i++) {
|
||||
var descriptor = props[i];
|
||||
descriptor.enumerable = descriptor.enumerable || false;
|
||||
descriptor.configurable = true;
|
||||
if ("value" in descriptor) descriptor.writable = true;
|
||||
Object.defineProperty(target, descriptor.key, descriptor);
|
||||
}
|
||||
}
|
||||
|
||||
function _createClass(Constructor, protoProps, staticProps) {
|
||||
if (protoProps) _defineProperties(Constructor.prototype, protoProps);
|
||||
if (staticProps) _defineProperties(Constructor, staticProps);
|
||||
return Constructor;
|
||||
}
|
||||
|
||||
function _toConsumableArray(arr) {
|
||||
return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread();
|
||||
}
|
||||
|
||||
function _arrayWithoutHoles(arr) {
|
||||
if (Array.isArray(arr)) return _arrayLikeToArray(arr);
|
||||
}
|
||||
|
||||
function _iterableToArray(iter) {
|
||||
if (typeof Symbol !== "undefined" && Symbol.iterator in Object(iter)) return Array.from(iter);
|
||||
}
|
||||
|
||||
function _unsupportedIterableToArray(o, minLen) {
|
||||
if (!o) return;
|
||||
if (typeof o === "string") return _arrayLikeToArray(o, minLen);
|
||||
var n = Object.prototype.toString.call(o).slice(8, -1);
|
||||
if (n === "Object" && o.constructor) n = o.constructor.name;
|
||||
if (n === "Map" || n === "Set") return Array.from(n);
|
||||
if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen);
|
||||
}
|
||||
|
||||
function _arrayLikeToArray(arr, len) {
|
||||
if (len == null || len > arr.length) len = arr.length;
|
||||
|
||||
for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i];
|
||||
|
||||
return arr2;
|
||||
}
|
||||
|
||||
function _nonIterableSpread() {
|
||||
throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
|
||||
}
|
||||
|
||||
var MicroModal = function () {
|
||||
|
||||
var FOCUSABLE_ELEMENTS = ['a[href]', 'area[href]', 'input:not([disabled]):not([type="hidden"]):not([aria-hidden])', 'select:not([disabled]):not([aria-hidden])', 'textarea:not([disabled]):not([aria-hidden])', 'button:not([disabled]):not([aria-hidden])', 'iframe', 'object', 'embed', '[contenteditable]', '[tabindex]:not([tabindex^="-"])'];
|
||||
|
||||
var Modal = /*#__PURE__*/function () {
|
||||
function Modal(_ref) {
|
||||
var targetModal = _ref.targetModal,
|
||||
_ref$triggers = _ref.triggers,
|
||||
triggers = _ref$triggers === void 0 ? [] : _ref$triggers,
|
||||
_ref$onShow = _ref.onShow,
|
||||
onShow = _ref$onShow === void 0 ? function () {} : _ref$onShow,
|
||||
_ref$onClose = _ref.onClose,
|
||||
onClose = _ref$onClose === void 0 ? function () {} : _ref$onClose,
|
||||
_ref$openTrigger = _ref.openTrigger,
|
||||
openTrigger = _ref$openTrigger === void 0 ? 'data-micromodal-trigger' : _ref$openTrigger,
|
||||
_ref$closeTrigger = _ref.closeTrigger,
|
||||
closeTrigger = _ref$closeTrigger === void 0 ? 'data-micromodal-close' : _ref$closeTrigger,
|
||||
_ref$openClass = _ref.openClass,
|
||||
openClass = _ref$openClass === void 0 ? 'is-open' : _ref$openClass,
|
||||
_ref$disableScroll = _ref.disableScroll,
|
||||
disableScroll = _ref$disableScroll === void 0 ? false : _ref$disableScroll,
|
||||
_ref$disableFocus = _ref.disableFocus,
|
||||
disableFocus = _ref$disableFocus === void 0 ? false : _ref$disableFocus,
|
||||
_ref$awaitCloseAnimat = _ref.awaitCloseAnimation,
|
||||
awaitCloseAnimation = _ref$awaitCloseAnimat === void 0 ? false : _ref$awaitCloseAnimat,
|
||||
_ref$awaitOpenAnimati = _ref.awaitOpenAnimation,
|
||||
awaitOpenAnimation = _ref$awaitOpenAnimati === void 0 ? false : _ref$awaitOpenAnimati,
|
||||
_ref$debugMode = _ref.debugMode,
|
||||
debugMode = _ref$debugMode === void 0 ? false : _ref$debugMode;
|
||||
|
||||
_classCallCheck(this, Modal);
|
||||
|
||||
// Save a reference of the modal
|
||||
this.modal = document.getElementById(targetModal); // Save a reference to the passed config
|
||||
|
||||
this.config = {
|
||||
debugMode: debugMode,
|
||||
disableScroll: disableScroll,
|
||||
openTrigger: openTrigger,
|
||||
closeTrigger: closeTrigger,
|
||||
openClass: openClass,
|
||||
onShow: onShow,
|
||||
onClose: onClose,
|
||||
awaitCloseAnimation: awaitCloseAnimation,
|
||||
awaitOpenAnimation: awaitOpenAnimation,
|
||||
disableFocus: disableFocus
|
||||
}; // Register click events only if pre binding eventListeners
|
||||
|
||||
if (triggers.length > 0) this.registerTriggers.apply(this, _toConsumableArray(triggers)); // pre bind functions for event listeners
|
||||
|
||||
this.onClick = this.onClick.bind(this);
|
||||
this.onKeydown = this.onKeydown.bind(this);
|
||||
}
|
||||
/**
|
||||
* Loops through all openTriggers and binds click event
|
||||
* @param {array} triggers [Array of node elements]
|
||||
* @return {void}
|
||||
*/
|
||||
|
||||
|
||||
_createClass(Modal, [{
|
||||
key: "registerTriggers",
|
||||
value: function registerTriggers() {
|
||||
var _this = this;
|
||||
|
||||
for (var _len = arguments.length, triggers = new Array(_len), _key = 0; _key < _len; _key++) {
|
||||
triggers[_key] = arguments[_key];
|
||||
}
|
||||
|
||||
triggers.filter(Boolean).forEach(function (trigger) {
|
||||
trigger.addEventListener('click', function (event) {
|
||||
return _this.showModal(event);
|
||||
});
|
||||
});
|
||||
}
|
||||
}, {
|
||||
key: "showModal",
|
||||
value: function showModal() {
|
||||
var _this2 = this;
|
||||
|
||||
var event = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : null;
|
||||
this.activeElement = document.activeElement;
|
||||
this.modal.setAttribute('aria-hidden', 'false');
|
||||
this.modal.classList.add(this.config.openClass);
|
||||
this.scrollBehaviour('disable');
|
||||
this.addEventListeners();
|
||||
|
||||
if (this.config.awaitOpenAnimation) {
|
||||
var handler = function handler() {
|
||||
_this2.modal.removeEventListener('animationend', handler, false);
|
||||
|
||||
_this2.setFocusToFirstNode();
|
||||
};
|
||||
|
||||
this.modal.addEventListener('animationend', handler, false);
|
||||
} else {
|
||||
this.setFocusToFirstNode();
|
||||
}
|
||||
|
||||
this.config.onShow(this.modal, this.activeElement, event);
|
||||
}
|
||||
}, {
|
||||
key: "closeModal",
|
||||
value: function closeModal() {
|
||||
var event = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : null;
|
||||
var modal = this.modal;
|
||||
this.modal.setAttribute('aria-hidden', 'true');
|
||||
this.removeEventListeners();
|
||||
this.scrollBehaviour('enable');
|
||||
|
||||
if (this.activeElement && this.activeElement.focus) {
|
||||
this.activeElement.focus();
|
||||
}
|
||||
|
||||
this.config.onClose(this.modal, this.activeElement, event);
|
||||
|
||||
if (this.config.awaitCloseAnimation) {
|
||||
var openClass = this.config.openClass; // <- old school ftw
|
||||
|
||||
this.modal.addEventListener('animationend', function handler() {
|
||||
modal.classList.remove(openClass);
|
||||
modal.removeEventListener('animationend', handler, false);
|
||||
}, false);
|
||||
} else {
|
||||
modal.classList.remove(this.config.openClass);
|
||||
}
|
||||
}
|
||||
}, {
|
||||
key: "closeModalById",
|
||||
value: function closeModalById(targetModal) {
|
||||
this.modal = document.getElementById(targetModal);
|
||||
if (this.modal) this.closeModal();
|
||||
}
|
||||
}, {
|
||||
key: "scrollBehaviour",
|
||||
value: function scrollBehaviour(toggle) {
|
||||
if (!this.config.disableScroll) return;
|
||||
var body = document.querySelector('body');
|
||||
|
||||
switch (toggle) {
|
||||
case 'enable':
|
||||
Object.assign(body.style, {
|
||||
overflow: ''
|
||||
});
|
||||
break;
|
||||
|
||||
case 'disable':
|
||||
Object.assign(body.style, {
|
||||
overflow: 'hidden'
|
||||
});
|
||||
break;
|
||||
}
|
||||
}
|
||||
}, {
|
||||
key: "addEventListeners",
|
||||
value: function addEventListeners() {
|
||||
this.modal.addEventListener('touchstart', this.onClick);
|
||||
this.modal.addEventListener('click', this.onClick);
|
||||
document.addEventListener('keydown', this.onKeydown);
|
||||
}
|
||||
}, {
|
||||
key: "removeEventListeners",
|
||||
value: function removeEventListeners() {
|
||||
this.modal.removeEventListener('touchstart', this.onClick);
|
||||
this.modal.removeEventListener('click', this.onClick);
|
||||
document.removeEventListener('keydown', this.onKeydown);
|
||||
}
|
||||
}, {
|
||||
key: "onClick",
|
||||
value: function onClick(event) {
|
||||
if (event.target.hasAttribute(this.config.closeTrigger)) {
|
||||
this.closeModal(event);
|
||||
}
|
||||
}
|
||||
}, {
|
||||
key: "onKeydown",
|
||||
value: function onKeydown(event) {
|
||||
if (event.keyCode === 27) this.closeModal(event); // esc
|
||||
|
||||
if (event.keyCode === 9) this.retainFocus(event); // tab
|
||||
}
|
||||
}, {
|
||||
key: "getFocusableNodes",
|
||||
value: function getFocusableNodes() {
|
||||
var nodes = this.modal.querySelectorAll(FOCUSABLE_ELEMENTS);
|
||||
return Array.apply(void 0, _toConsumableArray(nodes));
|
||||
}
|
||||
/**
|
||||
* Tries to set focus on a node which is not a close trigger
|
||||
* if no other nodes exist then focuses on first close trigger
|
||||
*/
|
||||
|
||||
}, {
|
||||
key: "setFocusToFirstNode",
|
||||
value: function setFocusToFirstNode() {
|
||||
var _this3 = this;
|
||||
|
||||
if (this.config.disableFocus) return;
|
||||
var focusableNodes = this.getFocusableNodes(); // no focusable nodes
|
||||
|
||||
if (focusableNodes.length === 0) return; // remove nodes on whose click, the modal closes
|
||||
// could not think of a better name :(
|
||||
|
||||
var nodesWhichAreNotCloseTargets = focusableNodes.filter(function (node) {
|
||||
return !node.hasAttribute(_this3.config.closeTrigger);
|
||||
});
|
||||
if (nodesWhichAreNotCloseTargets.length > 0) nodesWhichAreNotCloseTargets[0].focus();
|
||||
if (nodesWhichAreNotCloseTargets.length === 0) focusableNodes[0].focus();
|
||||
}
|
||||
}, {
|
||||
key: "retainFocus",
|
||||
value: function retainFocus(event) {
|
||||
var focusableNodes = this.getFocusableNodes(); // no focusable nodes
|
||||
|
||||
if (focusableNodes.length === 0) return;
|
||||
/**
|
||||
* Filters nodes which are hidden to prevent
|
||||
* focus leak outside modal
|
||||
*/
|
||||
|
||||
focusableNodes = focusableNodes.filter(function (node) {
|
||||
return node.offsetParent !== null;
|
||||
}); // if disableFocus is true
|
||||
|
||||
if (!this.modal.contains(document.activeElement)) {
|
||||
focusableNodes[0].focus();
|
||||
} else {
|
||||
var focusedItemIndex = focusableNodes.indexOf(document.activeElement);
|
||||
|
||||
if (event.shiftKey && focusedItemIndex === 0) {
|
||||
focusableNodes[focusableNodes.length - 1].focus();
|
||||
event.preventDefault();
|
||||
}
|
||||
|
||||
if (!event.shiftKey && focusableNodes.length > 0 && focusedItemIndex === focusableNodes.length - 1) {
|
||||
focusableNodes[0].focus();
|
||||
event.preventDefault();
|
||||
}
|
||||
}
|
||||
}
|
||||
}]);
|
||||
|
||||
return Modal;
|
||||
}();
|
||||
/**
|
||||
* Modal prototype ends.
|
||||
* Here on code is responsible for detecting and
|
||||
* auto binding event handlers on modal triggers
|
||||
*/
|
||||
// Keep a reference to the opened modal
|
||||
|
||||
|
||||
var activeModal = null;
|
||||
/**
|
||||
* Generates an associative array of modals and it's
|
||||
* respective triggers
|
||||
* @param {array} triggers An array of all triggers
|
||||
* @param {string} triggerAttr The data-attribute which triggers the module
|
||||
* @return {array}
|
||||
*/
|
||||
|
||||
var generateTriggerMap = function generateTriggerMap(triggers, triggerAttr) {
|
||||
var triggerMap = [];
|
||||
triggers.forEach(function (trigger) {
|
||||
var targetModal = trigger.attributes[triggerAttr].value;
|
||||
if (triggerMap[targetModal] === undefined) triggerMap[targetModal] = [];
|
||||
triggerMap[targetModal].push(trigger);
|
||||
});
|
||||
return triggerMap;
|
||||
};
|
||||
/**
|
||||
* Validates whether a modal of the given id exists
|
||||
* in the DOM
|
||||
* @param {number} id The id of the modal
|
||||
* @return {boolean}
|
||||
*/
|
||||
|
||||
|
||||
var validateModalPresence = function validateModalPresence(id) {
|
||||
if (!document.getElementById(id)) {
|
||||
console.warn("MicroModal: \u2757Seems like you have missed %c'".concat(id, "'"), 'background-color: #f8f9fa;color: #50596c;font-weight: bold;', 'ID somewhere in your code. Refer example below to resolve it.');
|
||||
console.warn("%cExample:", 'background-color: #f8f9fa;color: #50596c;font-weight: bold;', "<div class=\"modal\" id=\"".concat(id, "\"></div>"));
|
||||
return false;
|
||||
}
|
||||
};
|
||||
/**
|
||||
* Validates if there are modal triggers present
|
||||
* in the DOM
|
||||
* @param {array} triggers An array of data-triggers
|
||||
* @return {boolean}
|
||||
*/
|
||||
|
||||
|
||||
var validateTriggerPresence = function validateTriggerPresence(triggers) {
|
||||
if (triggers.length <= 0) {
|
||||
console.warn("MicroModal: \u2757Please specify at least one %c'micromodal-trigger'", 'background-color: #f8f9fa;color: #50596c;font-weight: bold;', 'data attribute.');
|
||||
console.warn("%cExample:", 'background-color: #f8f9fa;color: #50596c;font-weight: bold;', "<a href=\"#\" data-micromodal-trigger=\"my-modal\"></a>");
|
||||
return false;
|
||||
}
|
||||
};
|
||||
/**
|
||||
* Checks if triggers and their corresponding modals
|
||||
* are present in the DOM
|
||||
* @param {array} triggers Array of DOM nodes which have data-triggers
|
||||
* @param {array} triggerMap Associative array of modals and their triggers
|
||||
* @return {boolean}
|
||||
*/
|
||||
|
||||
|
||||
var validateArgs = function validateArgs(triggers, triggerMap) {
|
||||
validateTriggerPresence(triggers);
|
||||
if (!triggerMap) return true;
|
||||
|
||||
for (var id in triggerMap) {
|
||||
validateModalPresence(id);
|
||||
}
|
||||
|
||||
return true;
|
||||
};
|
||||
/**
|
||||
* Binds click handlers to all modal triggers
|
||||
* @param {object} config [description]
|
||||
* @return void
|
||||
*/
|
||||
|
||||
|
||||
var init = function init(config) {
|
||||
// Create an config object with default openTrigger
|
||||
var options = Object.assign({}, {
|
||||
openTrigger: 'data-micromodal-trigger'
|
||||
}, config); // Collects all the nodes with the trigger
|
||||
|
||||
var triggers = _toConsumableArray(document.querySelectorAll("[".concat(options.openTrigger, "]"))); // Makes a mappings of modals with their trigger nodes
|
||||
|
||||
|
||||
var triggerMap = generateTriggerMap(triggers, options.openTrigger); // Checks if modals and triggers exist in dom
|
||||
|
||||
if (options.debugMode === true && validateArgs(triggers, triggerMap) === false) return; // For every target modal creates a new instance
|
||||
|
||||
for (var key in triggerMap) {
|
||||
var value = triggerMap[key];
|
||||
options.targetModal = key;
|
||||
options.triggers = _toConsumableArray(value);
|
||||
activeModal = new Modal(options); // eslint-disable-line no-new
|
||||
}
|
||||
};
|
||||
/**
|
||||
* Shows a particular modal
|
||||
* @param {string} targetModal [The id of the modal to display]
|
||||
* @param {object} config [The configuration object to pass]
|
||||
* @return {void}
|
||||
*/
|
||||
|
||||
|
||||
var show = function show(targetModal, config) {
|
||||
var options = config || {};
|
||||
options.targetModal = targetModal; // Checks if modals and triggers exist in dom
|
||||
|
||||
if (options.debugMode === true && validateModalPresence(targetModal) === false) return; // clear events in case previous modal wasn't close
|
||||
|
||||
if (activeModal) activeModal.removeEventListeners(); // stores reference to active modal
|
||||
|
||||
activeModal = new Modal(options); // eslint-disable-line no-new
|
||||
|
||||
activeModal.showModal();
|
||||
};
|
||||
/**
|
||||
* Closes the active modal
|
||||
* @param {string} targetModal [The id of the modal to close]
|
||||
* @return {void}
|
||||
*/
|
||||
|
||||
|
||||
var close = function close(targetModal) {
|
||||
targetModal ? activeModal.closeModalById(targetModal) : activeModal.closeModal();
|
||||
};
|
||||
|
||||
return {
|
||||
init: init,
|
||||
show: show,
|
||||
close: close
|
||||
};
|
||||
}();
|
||||
window.MicroModal = MicroModal;
|
||||
|
||||
/* harmony default export */ var micromodal_es = (MicroModal);
|
||||
|
||||
// CONCATENATED MODULE: ./node_modules/@wordpress/block-library/build-module/navigation/view.js
|
||||
/**
|
||||
* External dependencies
|
||||
*/
|
||||
// Responsive navigation toggle.
|
||||
|
||||
function navigationToggleModal(modal) {
|
||||
const triggerButton = document.querySelector(`button[data-micromodal-trigger="${modal.id}"]`);
|
||||
const closeButton = modal.querySelector('button[data-micromodal-close]'); // Use aria-hidden to determine the status of the modal, as this attribute is
|
||||
// managed by micromodal.
|
||||
|
||||
const isHidden = 'true' === modal.getAttribute('aria-hidden');
|
||||
triggerButton.setAttribute('aria-expanded', !isHidden);
|
||||
closeButton.setAttribute('aria-expanded', !isHidden);
|
||||
modal.classList.toggle('has-modal-open', !isHidden); // Add a class to indicate the modal is open.
|
||||
|
||||
const htmlElement = document.documentElement;
|
||||
htmlElement.classList.toggle('has-modal-open');
|
||||
} // Open on click functionality.
|
||||
|
||||
|
||||
function closeSubmenus(element) {
|
||||
element.querySelectorAll('[aria-expanded="true"]').forEach(function (toggle) {
|
||||
toggle.setAttribute('aria-expanded', 'false');
|
||||
});
|
||||
}
|
||||
|
||||
function toggleSubmenuOnClick(event) {
|
||||
const buttonToggle = event.target.closest('[aria-expanded]');
|
||||
const isSubmenuOpen = buttonToggle.getAttribute('aria-expanded');
|
||||
|
||||
if (isSubmenuOpen === 'true') {
|
||||
closeSubmenus(buttonToggle.closest('.wp-block-navigation-item'));
|
||||
} else {
|
||||
// Close all sibling submenus.
|
||||
const parentElement = buttonToggle.closest('.wp-block-navigation-item');
|
||||
const navigationParent = buttonToggle.closest('.wp-block-navigation__submenu-container, .wp-block-navigation__container, .wp-block-page-list');
|
||||
navigationParent.querySelectorAll('.wp-block-navigation-item').forEach(function (child) {
|
||||
if (child !== parentElement) {
|
||||
closeSubmenus(child);
|
||||
}
|
||||
}); // Open submenu.
|
||||
|
||||
buttonToggle.setAttribute('aria-expanded', 'true');
|
||||
}
|
||||
}
|
||||
|
||||
const submenuButtons = document.querySelectorAll('.wp-block-navigation-submenu__toggle');
|
||||
submenuButtons.forEach(function (button) {
|
||||
button.addEventListener('click', toggleSubmenuOnClick);
|
||||
}); // Close on click outside.
|
||||
|
||||
document.addEventListener('click', function (event) {
|
||||
const navigationBlocks = document.querySelectorAll('.wp-block-navigation');
|
||||
navigationBlocks.forEach(function (block) {
|
||||
if (!block.contains(event.target)) {
|
||||
closeSubmenus(block);
|
||||
}
|
||||
});
|
||||
}); // Close on focus outside.
|
||||
|
||||
document.addEventListener('keyup', function (event) {
|
||||
const submenuBlocks = document.querySelectorAll('.wp-block-navigation-item.has-child');
|
||||
submenuBlocks.forEach(function (block) {
|
||||
if (!block.contains(event.target)) {
|
||||
closeSubmenus(block);
|
||||
}
|
||||
});
|
||||
}); // Necessary for some themes such as TT1 Blocks, where
|
||||
// scripts could be loaded before the body.
|
||||
|
||||
window.onload = () => micromodal_es.init({
|
||||
onShow: navigationToggleModal,
|
||||
onClose: navigationToggleModal,
|
||||
openClass: 'is-menu-open'
|
||||
});
|
||||
|
||||
|
||||
/***/ })
|
||||
|
||||
/******/ });
|
|
@ -0,0 +1 @@
|
|||
<?php return array('dependencies' => array(), 'version' => '7b2c5174a07c417dc3db6f1d9a9c3f78');
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,44 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/pattern` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Registers the `core/pattern` block on the server.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function register_block_core_pattern() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/pattern',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_pattern',
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the `core/pattern` block on the server.
|
||||
*
|
||||
* @param array $attributes Block attributes.
|
||||
*
|
||||
* @return string Returns the output of the pattern.
|
||||
*/
|
||||
function render_block_core_pattern( $attributes ) {
|
||||
if ( empty( $attributes['slug'] ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$slug = $attributes['slug'];
|
||||
$registry = WP_Block_Patterns_Registry::get_instance();
|
||||
if ( ! $registry->is_registered( $slug ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$pattern = $registry->get_registered( $slug );
|
||||
return do_blocks( $pattern['content'] );
|
||||
}
|
||||
|
||||
add_action( 'init', 'register_block_core_pattern' );
|
|
@ -0,0 +1,17 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/pattern",
|
||||
"title": "Pattern",
|
||||
"category": "design",
|
||||
"description": "Show a block pattern.",
|
||||
"supports": {
|
||||
"html": false,
|
||||
"inserter": false
|
||||
},
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"slug": {
|
||||
"type": "string"
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,61 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/post-author` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Renders the `core/post-author` block on the server.
|
||||
*
|
||||
* @param array $attributes Block attributes.
|
||||
* @param string $content Block default content.
|
||||
* @param WP_Block $block Block instance.
|
||||
* @return string Returns the rendered author block.
|
||||
*/
|
||||
function render_block_core_post_author( $attributes, $content, $block ) {
|
||||
if ( ! isset( $block->context['postId'] ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$author_id = get_post_field( 'post_author', $block->context['postId'] );
|
||||
if ( empty( $author_id ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$avatar = ! empty( $attributes['avatarSize'] ) ? get_avatar(
|
||||
$author_id,
|
||||
$attributes['avatarSize']
|
||||
) : null;
|
||||
|
||||
$byline = ! empty( $attributes['byline'] ) ? $attributes['byline'] : false;
|
||||
$classes = array_merge(
|
||||
isset( $attributes['className'] ) ? array( $attributes['className'] ) : array(),
|
||||
isset( $attributes['itemsJustification'] ) ? array( 'items-justified-' . $attributes['itemsJustification'] ) : array(),
|
||||
isset( $attributes['textAlign'] ) ? array( 'has-text-align-' . $attributes['textAlign'] ) : array()
|
||||
);
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) );
|
||||
|
||||
return sprintf( '<div %1$s>', $wrapper_attributes ) .
|
||||
( ! empty( $attributes['showAvatar'] ) ? '<div class="wp-block-post-author__avatar">' . $avatar . '</div>' : '' ) .
|
||||
'<div class="wp-block-post-author__content">' .
|
||||
( ! empty( $byline ) ? '<p class="wp-block-post-author__byline">' . $byline . '</p>' : '' ) .
|
||||
'<p class="wp-block-post-author__name">' . get_the_author_meta( 'display_name', $author_id ) . '</p>' .
|
||||
( ! empty( $attributes['showBio'] ) ? '<p class="wp-block-post-author__bio">' . get_the_author_meta( 'user_description', $author_id ) . '</p>' : '' ) .
|
||||
'</div>' .
|
||||
'</div>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the `core/post-author` block on the server.
|
||||
*/
|
||||
function register_block_core_post_author() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/post-author',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_post_author',
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_post_author' );
|
|
@ -0,0 +1,53 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/post-author",
|
||||
"title": "Post Author",
|
||||
"category": "theme",
|
||||
"description": "Add the author of this post.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"textAlign": {
|
||||
"type": "string"
|
||||
},
|
||||
"avatarSize": {
|
||||
"type": "number",
|
||||
"default": 48
|
||||
},
|
||||
"showAvatar": {
|
||||
"type": "boolean",
|
||||
"default": true
|
||||
},
|
||||
"showBio": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"byline": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"usesContext": [ "postType", "postId", "queryId" ],
|
||||
"supports": {
|
||||
"html": false,
|
||||
"spacing": {
|
||||
"margin": true,
|
||||
"padding": true
|
||||
},
|
||||
"typography": {
|
||||
"fontSize": true,
|
||||
"lineHeight": true,
|
||||
"__experimentalFontStyle": true,
|
||||
"__experimentalFontWeight": true,
|
||||
"__experimentalLetterSpacing": true,
|
||||
"__experimentalTextTransform": true,
|
||||
"__experimentalDefaultControls": {
|
||||
"fontSize": true
|
||||
}
|
||||
},
|
||||
"color": {
|
||||
"gradients": true,
|
||||
"link": true,
|
||||
"__experimentalDuotone": ".wp-block-post-author__avatar img"
|
||||
}
|
||||
},
|
||||
"editorStyle": "wp-block-post-author-editor",
|
||||
"style": "wp-block-post-author"
|
||||
}
|
|
@ -0,0 +1,100 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-post-author {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
.wp-block-post-author__byline {
|
||||
width: 100%;
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
font-size: 0.5em;
|
||||
}
|
||||
.wp-block-post-author__avatar {
|
||||
margin-left: 1em;
|
||||
}
|
||||
.wp-block-post-author__bio {
|
||||
margin-bottom: 0.7em;
|
||||
font-size: 0.7em;
|
||||
}
|
||||
.wp-block-post-author__content {
|
||||
flex-grow: 1;
|
||||
flex-basis: 0;
|
||||
}
|
||||
.wp-block-post-author__name {
|
||||
margin: 0;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-post-author{display:flex;flex-wrap:wrap}.wp-block-post-author__byline{width:100%;margin-top:0;margin-bottom:0;font-size:.5em}.wp-block-post-author__avatar{margin-left:1em}.wp-block-post-author__bio{margin-bottom:.7em;font-size:.7em}.wp-block-post-author__content{flex-grow:1;flex-basis:0}.wp-block-post-author__name{margin:0}
|
|
@ -0,0 +1,100 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-post-author {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
.wp-block-post-author__byline {
|
||||
width: 100%;
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
font-size: 0.5em;
|
||||
}
|
||||
.wp-block-post-author__avatar {
|
||||
margin-right: 1em;
|
||||
}
|
||||
.wp-block-post-author__bio {
|
||||
margin-bottom: 0.7em;
|
||||
font-size: 0.7em;
|
||||
}
|
||||
.wp-block-post-author__content {
|
||||
flex-grow: 1;
|
||||
flex-basis: 0;
|
||||
}
|
||||
.wp-block-post-author__name {
|
||||
margin: 0;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-post-author{display:flex;flex-wrap:wrap}.wp-block-post-author__byline{width:100%;margin-top:0;margin-bottom:0;font-size:.5em}.wp-block-post-author__avatar{margin-right:1em}.wp-block-post-author__bio{margin-bottom:.7em;font-size:.7em}.wp-block-post-author__content{flex-grow:1;flex-basis:0}.wp-block-post-author__name{margin:0}
|
|
@ -0,0 +1,68 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/post-comments` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Renders the `core/post-comments` block on the server.
|
||||
*
|
||||
* @param array $attributes Block attributes.
|
||||
* @param string $content Block default content.
|
||||
* @param WP_Block $block Block instance.
|
||||
* @return string Returns the filtered post comments for the current post wrapped inside "p" tags.
|
||||
*/
|
||||
function render_block_core_post_comments( $attributes, $content, $block ) {
|
||||
global $post;
|
||||
|
||||
$post_id = $block->context['postId'];
|
||||
if ( ! isset( $post_id ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$comment_args = array(
|
||||
'post_id' => $post_id,
|
||||
'count' => true,
|
||||
);
|
||||
// Return early if there are no comments and comments are closed.
|
||||
if ( ! comments_open( $post_id ) && get_comments( $comment_args ) === 0 ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$post_before = $post;
|
||||
$post = get_post( $post_id );
|
||||
setup_postdata( $post );
|
||||
|
||||
ob_start();
|
||||
// There's a deprecation warning generated by WP Core.
|
||||
// Ideally this deprecation is removed from Core.
|
||||
// In the meantime, this removes it from the output.
|
||||
add_filter( 'deprecated_file_trigger_error', '__return_false' );
|
||||
comments_template();
|
||||
remove_filter( 'deprecated_file_trigger_error', '__return_false' );
|
||||
$post = $post_before;
|
||||
|
||||
$classes = '';
|
||||
if ( isset( $attributes['textAlign'] ) ) {
|
||||
$classes .= 'has-text-align-' . $attributes['textAlign'];
|
||||
}
|
||||
|
||||
$wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) );
|
||||
$output = ob_get_clean();
|
||||
|
||||
return sprintf( '<div %1$s>%2$s</div>', $wrapper_attributes, $output );
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the `core/post-comments` block on the server.
|
||||
*/
|
||||
function register_block_core_post_comments() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/post-comments',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_post_comments',
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_post_comments' );
|
|
@ -0,0 +1,34 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/post-comments",
|
||||
"title": "Post Comments",
|
||||
"category": "theme",
|
||||
"description": "Display a post's comments.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"textAlign": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"usesContext": [ "postId", "postType" ],
|
||||
"supports": {
|
||||
"html": false,
|
||||
"align": [ "wide", "full" ],
|
||||
"typography": {
|
||||
"fontSize": true,
|
||||
"lineHeight": true,
|
||||
"__experimentalFontStyle": true,
|
||||
"__experimentalFontWeight": true,
|
||||
"__experimentalLetterSpacing": true,
|
||||
"__experimentalTextTransform": true,
|
||||
"__experimentalDefaultControls": {
|
||||
"fontSize": true
|
||||
}
|
||||
},
|
||||
"color": {
|
||||
"gradients": true,
|
||||
"link": true
|
||||
}
|
||||
},
|
||||
"style": "wp-block-post-comments"
|
||||
}
|
|
@ -0,0 +1,155 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-post-comments > h3:first-of-type {
|
||||
margin-top: 0;
|
||||
}
|
||||
.wp-block-post-comments .commentlist {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .comment {
|
||||
min-height: 2.25em;
|
||||
padding-right: 3.25em;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .comment p {
|
||||
font-size: 0.875em;
|
||||
line-height: 1.8;
|
||||
margin: 0.36em 0 1.4em;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .children {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-post-comments .comment-author {
|
||||
line-height: 1.5;
|
||||
margin-right: -3.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-author .avatar {
|
||||
border-radius: 1.5em;
|
||||
display: block;
|
||||
float: right;
|
||||
height: 2.5em;
|
||||
margin-left: 0.75em;
|
||||
width: 2.5em;
|
||||
}
|
||||
.wp-block-post-comments .comment-author cite {
|
||||
font-style: normal;
|
||||
}
|
||||
.wp-block-post-comments .comment-meta {
|
||||
line-height: 1.5;
|
||||
margin-right: -3.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-body .commentmetadata {
|
||||
font-size: 0.75em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-comment label,
|
||||
.wp-block-post-comments .comment-form-author label,
|
||||
.wp-block-post-comments .comment-form-email label,
|
||||
.wp-block-post-comments .comment-form-url label {
|
||||
display: block;
|
||||
margin-bottom: 0.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-comment textarea {
|
||||
box-sizing: border-box;
|
||||
width: 100%;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-cookies-consent {
|
||||
display: flex;
|
||||
gap: 0.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-cookies-consent #wp-comment-cookies-consent {
|
||||
margin-top: 0.35em;
|
||||
}
|
||||
.wp-block-post-comments .reply {
|
||||
font-size: 0.75em;
|
||||
margin-bottom: 1.4em;
|
||||
}
|
||||
.wp-block-post-comments textarea,
|
||||
.wp-block-post-comments input:not([type=submit]) {
|
||||
border: 1px solid #949494;
|
||||
font-size: 1em;
|
||||
font-family: inherit;
|
||||
}
|
||||
.wp-block-post-comments textarea,
|
||||
.wp-block-post-comments input:not([type=submit]):not([type=checkbox]) {
|
||||
padding: calc(0.667em + 2px);
|
||||
}
|
||||
.wp-block-post-comments input[type=submit] {
|
||||
border: none;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-post-comments>h3:first-of-type{margin-top:0}.wp-block-post-comments .commentlist{list-style:none;margin:0;padding:0}.wp-block-post-comments .commentlist .comment{min-height:2.25em;padding-right:3.25em}.wp-block-post-comments .commentlist .comment p{font-size:.875em;line-height:1.8;margin:.36em 0 1.4em}.wp-block-post-comments .commentlist .children{list-style:none;margin:0;padding:0}.wp-block-post-comments .comment-author{line-height:1.5;margin-right:-3.25em}.wp-block-post-comments .comment-author .avatar{border-radius:1.5em;display:block;float:right;height:2.5em;margin-left:.75em;width:2.5em}.wp-block-post-comments .comment-author cite{font-style:normal}.wp-block-post-comments .comment-meta{line-height:1.5;margin-right:-3.25em}.wp-block-post-comments .comment-body .commentmetadata{font-size:.75em}.wp-block-post-comments .comment-form-author label,.wp-block-post-comments .comment-form-comment label,.wp-block-post-comments .comment-form-email label,.wp-block-post-comments .comment-form-url label{display:block;margin-bottom:.25em}.wp-block-post-comments .comment-form-comment textarea{box-sizing:border-box;width:100%}.wp-block-post-comments .comment-form-cookies-consent{display:flex;gap:.25em}.wp-block-post-comments .comment-form-cookies-consent #wp-comment-cookies-consent{margin-top:.35em}.wp-block-post-comments .reply{font-size:.75em;margin-bottom:1.4em}.wp-block-post-comments input:not([type=submit]),.wp-block-post-comments textarea{border:1px solid #949494;font-size:1em;font-family:inherit}.wp-block-post-comments input:not([type=submit]):not([type=checkbox]),.wp-block-post-comments textarea{padding:calc(.667em + 2px)}.wp-block-post-comments input[type=submit]{border:none}
|
|
@ -0,0 +1,155 @@
|
|||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Breakpoints & Media Queries
|
||||
*/
|
||||
/**
|
||||
* SCSS Variables.
|
||||
*
|
||||
* Please use variables from this sheet to ensure consistency across the UI.
|
||||
* Don't add to this sheet unless you're pretty sure the value will be reused in many places.
|
||||
* For example, don't add rules to this sheet that affect block visuals. It's purely for UI.
|
||||
*/
|
||||
/**
|
||||
* Colors
|
||||
*/
|
||||
/**
|
||||
* Fonts & basic variables.
|
||||
*/
|
||||
/**
|
||||
* Grid System.
|
||||
* https://make.wordpress.org/design/2019/10/31/proposal-a-consistent-spacing-system-for-wordpress/
|
||||
*/
|
||||
/**
|
||||
* Dimensions.
|
||||
*/
|
||||
/**
|
||||
* Shadows.
|
||||
*/
|
||||
/**
|
||||
* Editor widths.
|
||||
*/
|
||||
/**
|
||||
* Block & Editor UI.
|
||||
*/
|
||||
/**
|
||||
* Block paddings.
|
||||
*/
|
||||
/**
|
||||
* React Native specific.
|
||||
* These variables do not appear to be used anywhere else.
|
||||
*/
|
||||
/**
|
||||
* Converts a hex value into the rgb equivalent.
|
||||
*
|
||||
* @param {string} hex - the hexadecimal value to convert
|
||||
* @return {string} comma separated rgb values
|
||||
*/
|
||||
/**
|
||||
* Breakpoint mixins
|
||||
*/
|
||||
/**
|
||||
* Long content fade mixin
|
||||
*
|
||||
* Creates a fading overlay to signify that the content is longer
|
||||
* than the space allows.
|
||||
*/
|
||||
/**
|
||||
* Focus styles.
|
||||
*/
|
||||
/**
|
||||
* Applies editor left position to the selector passed as argument
|
||||
*/
|
||||
/**
|
||||
* Styles that are reused verbatim in a few places
|
||||
*/
|
||||
/**
|
||||
* Allows users to opt-out of animations via OS-level preferences.
|
||||
*/
|
||||
/**
|
||||
* Reset default styles for JavaScript UI based pages.
|
||||
* This is a WP-admin agnostic reset
|
||||
*/
|
||||
/**
|
||||
* Reset the WP Admin page styles for Gutenberg-like pages.
|
||||
*/
|
||||
.wp-block-post-comments > h3:first-of-type {
|
||||
margin-top: 0;
|
||||
}
|
||||
.wp-block-post-comments .commentlist {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .comment {
|
||||
min-height: 2.25em;
|
||||
padding-left: 3.25em;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .comment p {
|
||||
font-size: 0.875em;
|
||||
line-height: 1.8;
|
||||
margin: 0.36em 0 1.4em;
|
||||
}
|
||||
.wp-block-post-comments .commentlist .children {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.wp-block-post-comments .comment-author {
|
||||
line-height: 1.5;
|
||||
margin-left: -3.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-author .avatar {
|
||||
border-radius: 1.5em;
|
||||
display: block;
|
||||
float: left;
|
||||
height: 2.5em;
|
||||
margin-right: 0.75em;
|
||||
width: 2.5em;
|
||||
}
|
||||
.wp-block-post-comments .comment-author cite {
|
||||
font-style: normal;
|
||||
}
|
||||
.wp-block-post-comments .comment-meta {
|
||||
line-height: 1.5;
|
||||
margin-left: -3.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-body .commentmetadata {
|
||||
font-size: 0.75em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-comment label,
|
||||
.wp-block-post-comments .comment-form-author label,
|
||||
.wp-block-post-comments .comment-form-email label,
|
||||
.wp-block-post-comments .comment-form-url label {
|
||||
display: block;
|
||||
margin-bottom: 0.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-comment textarea {
|
||||
box-sizing: border-box;
|
||||
width: 100%;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-cookies-consent {
|
||||
display: flex;
|
||||
gap: 0.25em;
|
||||
}
|
||||
.wp-block-post-comments .comment-form-cookies-consent #wp-comment-cookies-consent {
|
||||
margin-top: 0.35em;
|
||||
}
|
||||
.wp-block-post-comments .reply {
|
||||
font-size: 0.75em;
|
||||
margin-bottom: 1.4em;
|
||||
}
|
||||
.wp-block-post-comments textarea,
|
||||
.wp-block-post-comments input:not([type=submit]) {
|
||||
border: 1px solid #949494;
|
||||
font-size: 1em;
|
||||
font-family: inherit;
|
||||
}
|
||||
.wp-block-post-comments textarea,
|
||||
.wp-block-post-comments input:not([type=submit]):not([type=checkbox]) {
|
||||
padding: calc(0.667em + 2px);
|
||||
}
|
||||
.wp-block-post-comments input[type=submit] {
|
||||
border: none;
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
.wp-block-post-comments>h3:first-of-type{margin-top:0}.wp-block-post-comments .commentlist{list-style:none;margin:0;padding:0}.wp-block-post-comments .commentlist .comment{min-height:2.25em;padding-left:3.25em}.wp-block-post-comments .commentlist .comment p{font-size:.875em;line-height:1.8;margin:.36em 0 1.4em}.wp-block-post-comments .commentlist .children{list-style:none;margin:0;padding:0}.wp-block-post-comments .comment-author{line-height:1.5;margin-left:-3.25em}.wp-block-post-comments .comment-author .avatar{border-radius:1.5em;display:block;float:left;height:2.5em;margin-right:.75em;width:2.5em}.wp-block-post-comments .comment-author cite{font-style:normal}.wp-block-post-comments .comment-meta{line-height:1.5;margin-left:-3.25em}.wp-block-post-comments .comment-body .commentmetadata{font-size:.75em}.wp-block-post-comments .comment-form-author label,.wp-block-post-comments .comment-form-comment label,.wp-block-post-comments .comment-form-email label,.wp-block-post-comments .comment-form-url label{display:block;margin-bottom:.25em}.wp-block-post-comments .comment-form-comment textarea{box-sizing:border-box;width:100%}.wp-block-post-comments .comment-form-cookies-consent{display:flex;gap:.25em}.wp-block-post-comments .comment-form-cookies-consent #wp-comment-cookies-consent{margin-top:.35em}.wp-block-post-comments .reply{font-size:.75em;margin-bottom:1.4em}.wp-block-post-comments input:not([type=submit]),.wp-block-post-comments textarea{border:1px solid #949494;font-size:1em;font-family:inherit}.wp-block-post-comments input:not([type=submit]):not([type=checkbox]),.wp-block-post-comments textarea{padding:calc(.667em + 2px)}.wp-block-post-comments input[type=submit]{border:none}
|
|
@ -0,0 +1,96 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/post-navigation-link` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Renders the `core/post-navigation-link` block on the server.
|
||||
*
|
||||
* @param array $attributes Block attributes.
|
||||
* @param string $content Block default content.
|
||||
*
|
||||
* @return string Returns the next or previous post link that is adjacent to the current post.
|
||||
*/
|
||||
function render_block_core_post_navigation_link( $attributes, $content ) {
|
||||
if ( ! is_singular() ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
// Get the nagigation type to show the proper link. Available options are `next|previous`.
|
||||
$navigation_type = isset( $attributes['type'] ) ? $attributes['type'] : 'next';
|
||||
// Allow only `next` and `previous` in `$navigation_type`.
|
||||
if ( ! in_array( $navigation_type, array( 'next', 'previous' ), true ) ) {
|
||||
return '';
|
||||
}
|
||||
$classes = "post-navigation-link-$navigation_type";
|
||||
if ( isset( $attributes['textAlign'] ) ) {
|
||||
$classes .= " has-text-align-{$attributes['textAlign']}";
|
||||
}
|
||||
$wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) );
|
||||
// Set default values.
|
||||
$format = '%link';
|
||||
$link = 'next' === $navigation_type ? _x( 'Next', 'label for next post link' ) : _x( 'Previous', 'label for previous post link' );
|
||||
$label = '';
|
||||
|
||||
// If a custom label is provided, make this a link.
|
||||
// `$label` is used to prepend the provided label, if we want to show the page title as well.
|
||||
if ( isset( $attributes['label'] ) && ! empty( $attributes['label'] ) ) {
|
||||
$label = "{$attributes['label']}";
|
||||
$link = $label;
|
||||
}
|
||||
|
||||
// If we want to also show the page title, make the page title a link and prepend the label.
|
||||
if ( isset( $attributes['showTitle'] ) && $attributes['showTitle'] ) {
|
||||
/*
|
||||
* If the label link option is not enabled but there is a custom label,
|
||||
* display the custom label as text before the linked title.
|
||||
*/
|
||||
if ( ! $attributes['linkLabel'] ) {
|
||||
if ( $label ) {
|
||||
$format = '<span class="post-navigation-link__label">' . $label . '</span> %link';
|
||||
}
|
||||
$link = '%title';
|
||||
} elseif ( isset( $attributes['linkLabel'] ) && $attributes['linkLabel'] ) {
|
||||
// If the label link option is enabled and there is a custom label, display it before the title.
|
||||
if ( $label ) {
|
||||
$link = '<span class="post-navigation-link__label">' . $label . '</span> <span class="post-navigation-link__title">%title</title>';
|
||||
} else {
|
||||
/*
|
||||
* If the label link option is enabled and there is no custom label,
|
||||
* add a colon between the label and the post title.
|
||||
*/
|
||||
$label = 'next' === $navigation_type ? _x( 'Next:', 'label before the title of the next post' ) : _x( 'Previous:', 'label before the title of the previous post' );
|
||||
$link = sprintf(
|
||||
'<span class="post-navigation-link__label">%1$s</span> <span class="post-navigation-link__title">%2$s</span>',
|
||||
$label,
|
||||
'%title'
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// The dynamic portion of the function name, `$navigation_type`,
|
||||
// refers to the type of adjacency, 'next' or 'previous'.
|
||||
$get_link_function = "get_{$navigation_type}_post_link";
|
||||
$content = $get_link_function( $format, $link );
|
||||
return sprintf(
|
||||
'<div %1$s>%2$s</div>',
|
||||
$wrapper_attributes,
|
||||
$content
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the `core/post-navigation-link` block on the server.
|
||||
*/
|
||||
function register_block_core_post_navigation_link() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/post-navigation-link',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_post_navigation_link',
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_post_navigation_link' );
|
|
@ -0,0 +1,43 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/post-navigation-link",
|
||||
"title": "Post Navigation Link",
|
||||
"category": "theme",
|
||||
"description": "Displays the next or previous post link that is adjacent to the current post.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"textAlign": {
|
||||
"type": "string"
|
||||
},
|
||||
"type": {
|
||||
"type": "string",
|
||||
"default": "next"
|
||||
},
|
||||
"label": {
|
||||
"type": "string"
|
||||
},
|
||||
"showTitle": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
},
|
||||
"linkLabel": {
|
||||
"type": "boolean",
|
||||
"default": false
|
||||
}
|
||||
},
|
||||
"supports": {
|
||||
"reusable": false,
|
||||
"html": false,
|
||||
"typography": {
|
||||
"fontSize": true,
|
||||
"lineHeight": true,
|
||||
"__experimentalFontStyle": true,
|
||||
"__experimentalFontWeight": true,
|
||||
"__experimentalLetterSpacing": true,
|
||||
"__experimentalTextTransform": true,
|
||||
"__experimentalDefaultControls": {
|
||||
"fontSize": true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/term-description` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Renders the `core/term-description` block on the server.
|
||||
*
|
||||
* @param array $attributes Block attributes.
|
||||
*
|
||||
* @return string Returns the description of the current taxonomy term, if available
|
||||
*/
|
||||
function render_block_core_term_description( $attributes ) {
|
||||
$term_description = '';
|
||||
|
||||
if ( is_category() || is_tag() || is_tax() ) {
|
||||
$term_description = term_description();
|
||||
}
|
||||
|
||||
if ( empty( $term_description ) ) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$extra_attributes = ( isset( $attributes['textAlign'] ) )
|
||||
? array( 'class' => 'has-text-align-' . $attributes['textAlign'] )
|
||||
: array();
|
||||
$wrapper_attributes = get_block_wrapper_attributes( $extra_attributes );
|
||||
|
||||
return '<div ' . $wrapper_attributes . '>' . $term_description . '</div>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the `core/term-description` block on the server.
|
||||
*/
|
||||
function register_block_core_term_description() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/term-description',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_term_description',
|
||||
)
|
||||
);
|
||||
}
|
||||
add_action( 'init', 'register_block_core_term_description' );
|
|
@ -0,0 +1,28 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/term-description",
|
||||
"title": "Term Description",
|
||||
"category": "theme",
|
||||
"description": "Display the description of categories, tags and custom taxonomies when viewing an archive.",
|
||||
"textdomain": "default",
|
||||
"attributes": {
|
||||
"textAlign": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"supports": {
|
||||
"align": [ "wide", "full" ],
|
||||
"html": false,
|
||||
"color": {
|
||||
"link": true
|
||||
},
|
||||
"typography": {
|
||||
"fontSize": true,
|
||||
"lineHeight": true,
|
||||
"__experimentalDefaultControls": {
|
||||
"fontSize": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"editorStyle": "wp-block-term-description-editor"
|
||||
}
|
|
@ -0,0 +1,78 @@
|
|||
<?php
|
||||
/**
|
||||
* Server-side rendering of the `core/widget-group` block.
|
||||
*
|
||||
* @package WordPress
|
||||
*/
|
||||
|
||||
/**
|
||||
* Renders the 'core/widget-group' block.
|
||||
*
|
||||
* @param array $attributes The block attributes.
|
||||
* @param string $content The block content.
|
||||
* @param WP_Block $block The block.
|
||||
*
|
||||
* @return string Rendered block.
|
||||
*/
|
||||
function render_block_core_widget_group( $attributes, $content, $block ) {
|
||||
global $wp_registered_sidebars, $_sidebar_being_rendered;
|
||||
|
||||
if ( isset( $wp_registered_sidebars[ $_sidebar_being_rendered ] ) ) {
|
||||
$before_title = $wp_registered_sidebars[ $_sidebar_being_rendered ]['before_title'];
|
||||
$after_title = $wp_registered_sidebars[ $_sidebar_being_rendered ]['after_title'];
|
||||
} else {
|
||||
$before_title = '<h2 class="widget-title">';
|
||||
$after_title = '</h2>';
|
||||
}
|
||||
|
||||
$html = '';
|
||||
|
||||
if ( ! empty( $attributes['title'] ) ) {
|
||||
$html .= $before_title . $attributes['title'] . $after_title;
|
||||
}
|
||||
|
||||
$html .= '<div class="wp-widget-group__inner-blocks">';
|
||||
foreach ( $block->inner_blocks as $inner_block ) {
|
||||
$html .= $inner_block->render();
|
||||
}
|
||||
$html .= '</div>';
|
||||
|
||||
return $html;
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the 'core/widget-group' block.
|
||||
*/
|
||||
function register_block_core_widget_group() {
|
||||
register_block_type_from_metadata(
|
||||
__DIR__ . '/widget-group',
|
||||
array(
|
||||
'render_callback' => 'render_block_core_widget_group',
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
add_action( 'init', 'register_block_core_widget_group' );
|
||||
|
||||
/**
|
||||
* Make a note of the sidebar being rendered before WordPress starts rendering
|
||||
* it. This lets us get to the current sidebar in
|
||||
* render_block_core_widget_group().
|
||||
*
|
||||
* @param int|string $index Index, name, or ID of the dynamic sidebar.
|
||||
*/
|
||||
function note_sidebar_being_rendered( $index ) {
|
||||
global $_sidebar_being_rendered;
|
||||
$_sidebar_being_rendered = $index;
|
||||
}
|
||||
add_action( 'dynamic_sidebar_before', 'note_sidebar_being_rendered' );
|
||||
|
||||
/**
|
||||
* Clear whatever we set in note_sidebar_being_rendered() after WordPress
|
||||
* finishes rendering a sidebar.
|
||||
*/
|
||||
function discard_sidebar_being_rendered() {
|
||||
global $_sidebar_being_rendered;
|
||||
unset( $_sidebar_being_rendered );
|
||||
}
|
||||
add_action( 'dynamic_sidebar_after', 'discard_sidebar_being_rendered' );
|
|
@ -0,0 +1,18 @@
|
|||
{
|
||||
"apiVersion": 2,
|
||||
"name": "core/widget-group",
|
||||
"category": "widgets",
|
||||
"attributes": {
|
||||
"title": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"supports": {
|
||||
"html": false,
|
||||
"inserter": true,
|
||||
"customClassName": true,
|
||||
"reusable": false
|
||||
},
|
||||
"editorStyle": "wp-block-widget-group-editor",
|
||||
"style": "wp-block-widget-group"
|
||||
}
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
|
@ -581,6 +581,7 @@ add_action( 'wp_footer', 'wp_maybe_inline_styles', 1 ); // Run for late-loaded s
|
|||
|
||||
add_action( 'admin_footer-post.php', 'wp_add_iframed_editor_assets_html' );
|
||||
add_action( 'admin_footer-post-new.php', 'wp_add_iframed_editor_assets_html' );
|
||||
add_action( 'admin_footer-widgets.php', 'wp_add_iframed_editor_assets_html' );
|
||||
|
||||
// Taxonomy.
|
||||
add_action( 'init', 'create_initial_taxonomies', 0 ); // Highest priority.
|
||||
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
|
@ -2287,6 +2287,8 @@ function safecss_filter_attr( $css, $deprecated = '' ) {
|
|||
'border-right-width',
|
||||
'border-bottom',
|
||||
'border-bottom-color',
|
||||
'border-bottom-left-radius',
|
||||
'border-bottom-right-radius',
|
||||
'border-bottom-style',
|
||||
'border-bottom-width',
|
||||
'border-bottom-right-radius',
|
||||
|
@ -2297,6 +2299,8 @@ function safecss_filter_attr( $css, $deprecated = '' ) {
|
|||
'border-left-width',
|
||||
'border-top',
|
||||
'border-top-color',
|
||||
'border-top-left-radius',
|
||||
'border-top-right-radius',
|
||||
'border-top-style',
|
||||
'border-top-width',
|
||||
'border-top-left-radius',
|
||||
|
|
|
@ -450,6 +450,51 @@ function create_initial_post_types() {
|
|||
)
|
||||
);
|
||||
|
||||
register_post_type(
|
||||
'wp_navigation',
|
||||
array(
|
||||
'labels' => array(
|
||||
'name' => __( 'Navigation Menus', 'gutenberg' ),
|
||||
'singular_name' => __( 'Navigation Menu', 'gutenberg' ),
|
||||
'menu_name' => _x( 'Navigation Menus', 'Admin Menu text', 'gutenberg' ),
|
||||
'add_new' => _x( 'Add New', 'Navigation Menu', 'gutenberg' ),
|
||||
'add_new_item' => __( 'Add New Navigation Menu', 'gutenberg' ),
|
||||
'new_item' => __( 'New Navigation Menu', 'gutenberg' ),
|
||||
'edit_item' => __( 'Edit Navigation Menu', 'gutenberg' ),
|
||||
'view_item' => __( 'View Navigation Menu', 'gutenberg' ),
|
||||
'all_items' => __( 'All Navigation Menus', 'gutenberg' ),
|
||||
'search_items' => __( 'Search Navigation Menus', 'gutenberg' ),
|
||||
'parent_item_colon' => __( 'Parent Navigation Menu:', 'gutenberg' ),
|
||||
'not_found' => __( 'No Navigation Menu found.', 'gutenberg' ),
|
||||
'not_found_in_trash' => __( 'No Navigation Menu found in Trash.', 'gutenberg' ),
|
||||
'archives' => __( 'Navigation Menu archives', 'gutenberg' ),
|
||||
'insert_into_item' => __( 'Insert into Navigation Menu', 'gutenberg' ),
|
||||
'uploaded_to_this_item' => __( 'Uploaded to this Navigation Menu', 'gutenberg' ),
|
||||
// Some of these are a bit weird, what are they for?
|
||||
'filter_items_list' => __( 'Filter Navigation Menu list', 'gutenberg' ),
|
||||
'items_list_navigation' => __( 'Navigation Menus list navigation', 'gutenberg' ),
|
||||
'items_list' => __( 'Navigation Menus list', 'gutenberg' ),
|
||||
),
|
||||
'description' => __( 'Navigation menus.', 'gutenberg' ),
|
||||
'public' => false,
|
||||
'_builtin' => true, /* internal use only. don't use this when registering your own post type. */
|
||||
'has_archive' => false,
|
||||
'show_ui' => false,
|
||||
'show_in_menu' => 'themes.php',
|
||||
'show_in_admin_bar' => false,
|
||||
'show_in_rest' => true,
|
||||
'rewrite' => false,
|
||||
'map_meta_cap' => true,
|
||||
'rest_base' => 'navigation',
|
||||
'rest_controller_class' => 'WP_REST_Posts_Controller',
|
||||
'supports' => array(
|
||||
'title',
|
||||
'editor',
|
||||
'revisions',
|
||||
),
|
||||
)
|
||||
);
|
||||
|
||||
register_post_status(
|
||||
'publish',
|
||||
array(
|
||||
|
|
|
@ -311,6 +311,12 @@ class WP_REST_Users_Controller extends WP_REST_Controller {
|
|||
$prepared_args['has_published_posts'] = get_post_types( array( 'show_in_rest' => true ), 'names' );
|
||||
}
|
||||
|
||||
if ( ! empty( $request['has_published_posts'] ) ) {
|
||||
$prepared_args['has_published_posts'] = ( true === $request['has_published_posts'] )
|
||||
? get_post_types( array( 'show_in_rest' => true ), 'names' )
|
||||
: (array) $request['has_published_posts'];
|
||||
}
|
||||
|
||||
if ( ! empty( $prepared_args['search'] ) ) {
|
||||
$prepared_args['search'] = '*' . $prepared_args['search'] . '*';
|
||||
}
|
||||
|
@ -1580,6 +1586,15 @@ class WP_REST_Users_Controller extends WP_REST_Controller {
|
|||
),
|
||||
);
|
||||
|
||||
$query_params['has_published_posts'] = array(
|
||||
'description' => __( 'Limit result set to users who have published posts.' ),
|
||||
'type' => array( 'boolean', 'array' ),
|
||||
'items' => array(
|
||||
'type' => 'string',
|
||||
'enum' => get_post_types( array( 'show_in_rest' => true ), 'names' ),
|
||||
),
|
||||
);
|
||||
|
||||
/**
|
||||
* Filters REST API collection parameters for the users controller.
|
||||
*
|
||||
|
|
|
@ -99,6 +99,29 @@ class WP_REST_Widget_Types_Controller extends WP_REST_Controller {
|
|||
),
|
||||
)
|
||||
);
|
||||
|
||||
register_rest_route(
|
||||
$this->namespace,
|
||||
'/' . $this->rest_base . '/(?P<id>[a-zA-Z0-9_-]+)/render',
|
||||
array(
|
||||
array(
|
||||
'methods' => WP_REST_Server::CREATABLE,
|
||||
'permission_callback' => array( $this, 'get_item_permissions_check' ),
|
||||
'callback' => array( $this, 'render' ),
|
||||
'args' => array(
|
||||
'id' => array(
|
||||
'description' => __( 'The widget type id.', 'default' ),
|
||||
'type' => 'string',
|
||||
'required' => true,
|
||||
),
|
||||
'instance' => array(
|
||||
'description' => __( 'Current instance settings of the widget.', 'default' ),
|
||||
'type' => 'object',
|
||||
),
|
||||
),
|
||||
),
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -559,6 +582,78 @@ class WP_REST_Widget_Types_Controller extends WP_REST_Controller {
|
|||
return ob_get_clean();
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders a single Legacy Widget and wraps it in a JSON-encodable array.
|
||||
*
|
||||
* @since 5.9.0
|
||||
*
|
||||
* @param WP_REST_Request $request Full details about the request.
|
||||
*
|
||||
* @return array An array with rendered Legacy Widget HTML.
|
||||
*/
|
||||
public function render( $request ) {
|
||||
return array(
|
||||
'preview' => $this->render_legacy_widget_preview_iframe(
|
||||
$request['id'],
|
||||
isset( $request['instance'] ) ? $request['instance'] : null
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders a page containing a preview of the requested Legacy Widget block.
|
||||
*
|
||||
* @since 5.9.0
|
||||
*
|
||||
* @param string $id_base The id base of the requested widget.
|
||||
* @param array $instance The widget instance attributes.
|
||||
*
|
||||
* @return string Rendered Legacy Widget block preview.
|
||||
*/
|
||||
private function render_legacy_widget_preview_iframe( $id_base, $instance ) {
|
||||
if ( ! defined( 'IFRAME_REQUEST' ) ) {
|
||||
define( 'IFRAME_REQUEST', true );
|
||||
}
|
||||
|
||||
ob_start();
|
||||
?>
|
||||
<!doctype html>
|
||||
<html <?php language_attributes(); ?>>
|
||||
<head>
|
||||
<meta charset="<?php bloginfo( 'charset' ); ?>" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<link rel="profile" href="https://gmpg.org/xfn/11" />
|
||||
<?php wp_head(); ?>
|
||||
<style>
|
||||
/* Reset theme styles */
|
||||
html, body, #page, #content {
|
||||
padding: 0 !important;
|
||||
margin: 0 !important;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body <?php body_class(); ?>>
|
||||
<div id="page" class="site">
|
||||
<div id="content" class="site-content">
|
||||
<?php
|
||||
$registry = WP_Block_Type_Registry::get_instance();
|
||||
$block = $registry->get_registered( 'core/legacy-widget' );
|
||||
echo $block->render(
|
||||
array(
|
||||
'idBase' => $id_base,
|
||||
'instance' => $instance,
|
||||
)
|
||||
);
|
||||
?>
|
||||
</div><!-- #content -->
|
||||
</div><!-- #page -->
|
||||
<?php wp_footer(); ?>
|
||||
</body>
|
||||
</html>
|
||||
<?php
|
||||
return ob_get_clean();
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves the query params for collections.
|
||||
*
|
||||
|
|
|
@ -103,8 +103,8 @@ function wp_default_packages_vendor( $scripts ) {
|
|||
);
|
||||
|
||||
$vendor_scripts_versions = array(
|
||||
'react' => '16.13.1',
|
||||
'react-dom' => '16.13.1',
|
||||
'react' => '17.0.1',
|
||||
'react-dom' => '17.0.1',
|
||||
'regenerator-runtime' => '0.13.7',
|
||||
'moment' => '2.29.1',
|
||||
'lodash' => '4.17.19',
|
||||
|
@ -1598,6 +1598,11 @@ function wp_default_styles( $styles ) {
|
|||
'wp-block-library',
|
||||
'wp-reusable-blocks',
|
||||
),
|
||||
'edit-site' => array(
|
||||
'wp-components',
|
||||
'wp-block-editor',
|
||||
'wp-edit-blocks',
|
||||
),
|
||||
);
|
||||
|
||||
foreach ( $package_styles as $package => $dependencies ) {
|
||||
|
@ -1655,6 +1660,7 @@ function wp_default_styles( $styles ) {
|
|||
'wp-components',
|
||||
'wp-customize-widgets',
|
||||
'wp-edit-post',
|
||||
'wp-edit-site',
|
||||
'wp-edit-widgets',
|
||||
'wp-editor',
|
||||
'wp-format-library',
|
||||
|
@ -2265,7 +2271,19 @@ function wp_common_block_scripts_and_styles() {
|
|||
wp_enqueue_style( 'wp-block-library' );
|
||||
|
||||
if ( current_theme_supports( 'wp-block-styles' ) ) {
|
||||
wp_enqueue_style( 'wp-block-library-theme' );
|
||||
if ( wp_should_load_separate_core_block_assets() ) {
|
||||
$suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? 'css' : 'min.css';
|
||||
$files = glob( __DIR__ . "/blocks/**/theme.$suffix" );
|
||||
foreach ( $files as $path ) {
|
||||
$block_name = basename( dirname( $path ) );
|
||||
if ( is_rtl() && file_exists( __DIR__ . "/blocks/$block_name/theme-rtl.$suffix" ) ) {
|
||||
$path = __DIR__ . "/blocks/$block_name/theme-rtl.$suffix";
|
||||
}
|
||||
wp_add_inline_style( "wp-block-{$block_name}", file_get_contents( $path ) );
|
||||
}
|
||||
} else {
|
||||
wp_enqueue_style( 'wp-block-library-theme' );
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -2773,6 +2791,8 @@ function _wp_normalize_relative_css_links( $css, $stylesheet_url ) {
|
|||
* @since 5.8.0
|
||||
*/
|
||||
function wp_add_iframed_editor_assets_html() {
|
||||
global $pagenow;
|
||||
|
||||
if ( ! wp_should_load_block_editor_scripts_and_styles() ) {
|
||||
return;
|
||||
}
|
||||
|
@ -2785,6 +2805,11 @@ function wp_add_iframed_editor_assets_html() {
|
|||
'wp-edit-blocks',
|
||||
);
|
||||
|
||||
if ( 'widgets.php' === $pagenow || 'customize.php' === $pagenow ) {
|
||||
$style_handles[] = 'wp-widgets';
|
||||
$style_handles[] = 'wp-edit-widgets';
|
||||
}
|
||||
|
||||
$block_registry = WP_Block_Type_Registry::get_instance();
|
||||
|
||||
foreach ( $block_registry->get_all_registered() as $block_type ) {
|
||||
|
@ -2806,7 +2831,8 @@ function wp_add_iframed_editor_assets_html() {
|
|||
|
||||
ob_start();
|
||||
|
||||
wp_styles()->done = array();
|
||||
// We do not need reset styles for the iframed editor.
|
||||
wp_styles()->done = array( 'wp-reset-editor-styles' );
|
||||
wp_styles()->do_items( $style_handles );
|
||||
wp_styles()->done = $done;
|
||||
|
||||
|
|
|
@ -10,8 +10,7 @@
|
|||
* This needs to run before <head> so that blocks can add scripts and styles in wp_head().
|
||||
*/
|
||||
$template_html = get_the_block_template_html();
|
||||
?>
|
||||
<!DOCTYPE html>
|
||||
?><!DOCTYPE html>
|
||||
<html <?php language_attributes(); ?>>
|
||||
<head>
|
||||
<meta charset="<?php bloginfo( 'charset' ); ?>" />
|
||||
|
|
|
@ -4075,3 +4075,14 @@ function create_initial_theme_features() {
|
|||
)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether the current theme is a block-based theme or not.
|
||||
*
|
||||
* @since 5.9.0
|
||||
*
|
||||
* @return boolean Whether the current theme is a block-based theme or not.
|
||||
*/
|
||||
function wp_is_block_template_theme() {
|
||||
return is_readable( get_theme_file_path( '/block-templates/index.html' ) );
|
||||
}
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
*
|
||||
* @global string $wp_version
|
||||
*/
|
||||
$wp_version = '5.9-alpha-52068';
|
||||
$wp_version = '5.9-alpha-52069';
|
||||
|
||||
/**
|
||||
* Holds the WordPress DB revision, increments when changes are made to the WordPress DB schema.
|
||||
|
|
|
@ -317,6 +317,7 @@ require ABSPATH . WPINC . '/block-supports/align.php';
|
|||
require ABSPATH . WPINC . '/block-supports/border.php';
|
||||
require ABSPATH . WPINC . '/block-supports/colors.php';
|
||||
require ABSPATH . WPINC . '/block-supports/custom-classname.php';
|
||||
require ABSPATH . WPINC . '/block-supports/dimensions.php';
|
||||
require ABSPATH . WPINC . '/block-supports/duotone.php';
|
||||
require ABSPATH . WPINC . '/block-supports/elements.php';
|
||||
require ABSPATH . WPINC . '/block-supports/generated-classname.php';
|
||||
|
|
Loading…
Reference in New Issue