$vars Existing query vars. * @return array */ public static function register_query_vars( array $vars ): array { $vars[] = 'airygen_toc_preview'; return $vars; } /** * Render preview page when requested. * * @return void */ public static function maybe_render_preview(): void { $preview = get_query_var( 'airygen_toc_preview' ); if ( '' === $preview && empty( $_GET['airygen_toc_preview'] ) ) { // phpcs:ignore WordPress.Security.NonceVerification.Recommended -- Read-only preview route gate. return; } if ( ! current_user_can( 'manage_options' ) ) { status_header( 404 ); exit; } nocache_headers(); status_header( 200 ); header( 'Content-Type: text/html; charset=utf-8' ); show_admin_bar( false ); $settings = Settings::get(); $sample = self::load_preview_sample(); $content = ! empty( $settings['auto_injection_enabled'] ) ? Renderer::inject( $sample, $settings ) : $sample; $styles = array(); $stylesheet_uri = get_stylesheet_uri(); if ( is_string( $stylesheet_uri ) && '' !== $stylesheet_uri ) { $styles[] = $stylesheet_uri; } $template_uri = get_template_directory_uri(); if ( is_string( $template_uri ) && '' !== $template_uri ) { $parent_style = $template_uri . '/style.css'; if ( ! in_array( $parent_style, $styles, true ) ) { $styles[] = $parent_style; } } $view_path = trailingslashit( AIRYGEN_PLUGIN_DIR ) . 'resources/views/admin/toc-preview.php'; if ( ! file_exists( $view_path ) ) { exit; } $data = array( 'content' => $content, 'styles' => $styles, ); require $view_path; exit; } /** * Load the localized preview content. * * @return string */ private static function load_preview_sample(): string { $sample = '

Getting started

'; $sample .= '

This is a short preview to show the table of contents structure.

'; $sample .= '

Define the goal

Pick a single primary goal for the article.

'; $sample .= '

Primary intent

Choose one intent to focus on.

'; $sample .= '

Audience fit

Write to the reader\'s level.

'; $sample .= '

Plan the outline

Sketch headings before drafting.

'; $sample .= '

Main sections

Cover steps and examples.

'; $sample .= '

Publish and refine

'; $sample .= '

Refresh content as topics evolve.

'; $sample .= '

Monitor results

Track impressions and clicks.

'; $sample .= '

Clarity check

Ensure each section has one idea.

'; $sample .= '

Update cadence

Review core content quarterly.

'; return $sample; } /** * Inject TOC into post content. * * @param string $content Content HTML. * @return string */ public static function inject_toc( string $content ): string { if ( ! ModuleSettings::is_enabled( 'toc' ) ) { return $content; } if ( ! is_singular() ) { return $content; } $settings = Settings::get(); if ( empty( $settings['auto_injection_enabled'] ) ) { return $content; } $post = get_post(); if ( ! $post ) { return $content; } if ( 'auto' !== self::get_post_mode( $post->ID ) ) { return $content; } $post_type = get_post_type( $post ); if ( ! is_string( $post_type ) ) { return $content; } $post_types = isset( $settings['post_types'] ) && is_array( $settings['post_types'] ) ? $settings['post_types'] : array(); if ( ! in_array( $post_type, $post_types, true ) ) { return $content; } return Renderer::inject( $content, $settings ); } /** * Handle the [airygen_toc] shortcode. * * @return string */ public static function render_shortcode(): string { if ( ! ModuleSettings::is_enabled( 'toc' ) ) { return ''; } $settings = Settings::get(); if ( empty( $settings['manual_output_enabled'] ) ) { return ''; } $post = get_post(); if ( ! $post ) { return ''; } $post_mode = self::get_post_mode( $post->ID ); if ( 'disabled' === $post_mode ) { return ''; } if ( 'manual' !== $post_mode && 'auto' !== $post_mode ) { return ''; } remove_filter( 'the_content', array( __CLASS__, 'inject_toc' ), 20 ); $content = apply_filters( 'the_content', $post->post_content ); // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedHooknameFound -- Core content filter. add_filter( 'the_content', array( __CLASS__, 'inject_toc' ), 20 ); $built = Renderer::build( $content, $settings ); return $built['toc']; } /** * Resolve per-post output mode. * * @param int $post_id Post ID. * * @return string */ private static function get_post_mode( int $post_id ): string { return OutputModes::get_mode( $post_id, 'toc' ); } }