<?php

if (!defined('ABSPATH')) {
    exit;
}

class SEO_Fury_Breadcrumbs {
    // All shortcode tags we handle (own + aliases for other plugins).
    private static $breadcrumb_shortcodes = array(
        'seo_fury_breadcrumbs',
        'rank_math_breadcrumb',
        'wpseo_breadcrumb',
        'seopress_breadcrumbs',
        'bcn_display',
        'aioseo_breadcrumbs',
    );

    public function __construct() {
        add_shortcode('seo_fury_breadcrumbs', array($this, 'render_shortcode'));

        // Register aliases for other SEO plugins' breadcrumb shortcodes.
        // This way, if a theme or content contains [rank_math_breadcrumb] etc.,
        // our breadcrumbs render instead of showing a broken shortcode.
        $aliases = array(
            'rank_math_breadcrumb',   // Rank Math
            'wpseo_breadcrumb',       // Yoast SEO
            'seopress_breadcrumbs',   // SEOPress
            'bcn_display',            // Breadcrumb NavXT
            'aioseo_breadcrumbs',     // All in One SEO
        );
        foreach ($aliases as $alias) {
            if (!shortcode_exists($alias)) {
                add_shortcode($alias, array($this, 'render_shortcode'));
            }
        }

        $auto_insert = get_option('seo_fury_breadcrumbs_auto_insert', 0);
        if ($auto_insert && !is_admin()) {
            add_action('wp_body_open', array($this, 'auto_output_breadcrumbs'), 5);
        }

        // Inject BreadcrumbList into the unified schema @graph when the
        // breadcrumb shortcode is present in the post content and schema
        // markup is enabled for the current post type.
        add_filter('seo_fury_schema_nodes', array($this, 'inject_breadcrumb_schema_node'), 20, 2);
    }

    public function auto_output_breadcrumbs() {
        $html = $this->get_breadcrumbs_html();
        if (!empty($html)) {
            $brand = function_exists('seo_fury_get_brand_name') ? seo_fury_get_brand_name() : 'SEO Fury';
            echo "\n<!-- " . esc_html($brand) . " -->\n";
            echo wp_kses_post( $html ); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
            echo "<!-- /" . esc_html($brand) . " -->\n";
        }
    }

    public function register_settings() {
        $sanitize_checkbox = array('sanitize_callback' => 'absint');
        $sanitize_text     = array('sanitize_callback' => 'sanitize_text_field');
        $sanitize_url      = array('sanitize_callback' => 'esc_url_raw');

        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_enabled', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_schema', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_auto_insert', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_show_home', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_home_label', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_home_url', $sanitize_url);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_prefix', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_separator', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_separator_custom', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_archive_format', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_search_format', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_404_label', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_hide_post_title', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_show_categories', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_hide_taxonomy', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_blog_link', $sanitize_checkbox);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_blog_label', $sanitize_text);
        register_setting('seo_fury_breadcrumbs_group', 'seo_fury_breadcrumbs_blog_url', $sanitize_url);

        add_settings_section(
            'seo_fury_breadcrumbs_section',
            '',
            null,
            'seo_fury_breadcrumbs_group'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_enabled',
            __('Enable Breadcrumbs', 'seo-fury'),
            array($this, 'breadcrumbs_enabled_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_schema',
            __('Structured Data', 'seo-fury'),
            array($this, 'breadcrumbs_schema_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_auto_insert',
            __('Auto Insert', 'seo-fury'),
            array($this, 'breadcrumbs_auto_insert_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_show_home',
            __('Show Home Link', 'seo-fury'),
            array($this, 'breadcrumbs_show_home_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_home_label',
            __('Home Label', 'seo-fury'),
            array($this, 'breadcrumbs_home_label_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_home_url',
            __('Home URL', 'seo-fury'),
            array($this, 'breadcrumbs_home_url_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_prefix',
            __('Breadcrumb Prefix', 'seo-fury'),
            array($this, 'breadcrumbs_prefix_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_separator',
            __('Separator', 'seo-fury'),
            array($this, 'breadcrumbs_separator_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_archive_format',
            __('Archive Format', 'seo-fury'),
            array($this, 'breadcrumbs_archive_format_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_search_format',
            __('Search Format', 'seo-fury'),
            array($this, 'breadcrumbs_search_format_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_404_label',
            __('404 Label', 'seo-fury'),
            array($this, 'breadcrumbs_404_label_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_hide_post_title',
            __('Hide Post Title', 'seo-fury'),
            array($this, 'breadcrumbs_hide_post_title_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_show_categories',
            __('Show Categories', 'seo-fury'),
            array($this, 'breadcrumbs_show_categories_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_hide_taxonomy',
            __('Hide Taxonomy Name', 'seo-fury'),
            array($this, 'breadcrumbs_hide_taxonomy_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_blog_link',
            __('Blog Link for Posts', 'seo-fury'),
            array($this, 'breadcrumbs_blog_link_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_blog_label',
            __('Blog Label', 'seo-fury'),
            array($this, 'breadcrumbs_blog_label_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );

        add_settings_field(
            'seo_fury_breadcrumbs_blog_url',
            __('Blog URL', 'seo-fury'),
            array($this, 'breadcrumbs_blog_url_callback'),
            'seo_fury_breadcrumbs_group',
            'seo_fury_breadcrumbs_section'
        );
    }

    public function render_settings_page() {
        ?>
        <form method="post" action="options.php">
            <?php
            settings_fields('seo_fury_breadcrumbs_group');
            do_settings_sections('seo_fury_breadcrumbs_group');
            submit_button();
            ?>
        </form>
        <div class="seo-card">
            <h3><?php esc_html_e('How to display breadcrumbs', 'seo-fury'); ?></h3>
            <p><?php esc_html_e('Use this PHP snippet in your theme template:', 'seo-fury'); ?></p>
            <div class="seo-fury-code-row">
                <pre class="seo-fury-code-inline"><code id="seo-fury-php-snippet">&lt;?php if (function_exists('seo_fury_breadcrumbs')) { seo_fury_breadcrumbs(); } ?&gt;</code></pre>
                <button type="button" class="seo-fury-copy-btn" data-target="seo-fury-php-snippet" title="<?php esc_attr_e('Copy to clipboard', 'seo-fury'); ?>">
                    <span class="dashicons dashicons-clipboard"></span>
                </button>
            </div>
            <p><?php esc_html_e('Or use shortcode:', 'seo-fury'); ?></p>
            <div class="seo-fury-code-row">
                <pre class="seo-fury-code-inline"><code id="seo-fury-shortcode">[seo_fury_breadcrumbs]</code></pre>
                <button type="button" class="seo-fury-copy-btn" data-target="seo-fury-shortcode" title="<?php esc_attr_e('Copy to clipboard', 'seo-fury'); ?>">
                    <span class="dashicons dashicons-clipboard"></span>
                </button>
            </div>
        </div>
        <script>
        jQuery(document).ready(function($) {
            var sfPhpSnippet = <?php echo wp_json_encode("<?php if (function_exists('seo_fury_breadcrumbs')) { seo_fury_breadcrumbs(); } ?>"); ?>;
            $('.seo-fury-copy-btn').on('click', function() {
                var target = $(this).data('target');
                var el = document.getElementById(target);
                if (!el) return;
                var text = el.textContent;
                if (target === 'seo-fury-php-snippet') {
                    text = sfPhpSnippet;
                }
                if (navigator.clipboard) {
                    navigator.clipboard.writeText(text);
                } else {
                    var ta = document.createElement('textarea');
                    ta.value = text;
                    ta.style.position = 'fixed';
                    ta.style.left = '-9999px';
                    document.body.appendChild(ta);
                    ta.select();
                    document.execCommand('copy');
                    document.body.removeChild(ta);
                }
                var btn = $(this);
                btn.find('.dashicons').removeClass('dashicons-clipboard').addClass('dashicons-yes');
                setTimeout(function() {
                    btn.find('.dashicons').removeClass('dashicons-yes').addClass('dashicons-clipboard');
                }, 1500);
            });
        });
        </script>
        <?php
    }

    public function breadcrumbs_section_callback() {
        echo '<p>' . esc_html__('Enable and configure breadcrumbs for your site.', 'seo-fury') . '</p>';
    }

    public function breadcrumbs_enabled_callback() {
        $enabled = get_option('seo_fury_breadcrumbs_enabled', 1);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_enabled" value="1" <?php checked($enabled, 1); ?>>
            <?php esc_html_e('Show breadcrumbs output', 'seo-fury'); ?>
        </label>
        <?php
    }

    public function breadcrumbs_schema_callback() {
        $enabled      = get_option('seo_fury_breadcrumbs_enabled', 1);
        $schema_value = get_option('seo_fury_breadcrumbs_schema', null);
        // Default: inherit state of the main "Enable Breadcrumbs" toggle.
        if ($schema_value === null || $schema_value === false || $schema_value === '') {
            $schema_value = $enabled ? 1 : 0;
        }
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_schema" value="1" <?php checked($schema_value, 1); ?>>
            <?php esc_html_e('Add breadcrumb micromarkup (BreadcrumbList JSON-LD)', 'seo-fury'); ?>
        </label>
        <p class="description"><?php esc_html_e('When a breadcrumb shortcode is present in the post content, automatically add a BreadcrumbList structured data node to the schema graph on that page.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_auto_insert_callback() {
        $auto_insert = get_option('seo_fury_breadcrumbs_auto_insert', 0);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_auto_insert" value="1" <?php checked($auto_insert, 1); ?>>
            <?php esc_html_e('Automatically display breadcrumbs at the top of every page (no theme editing required)', 'seo-fury'); ?>
        </label>
        <p class="description"><?php esc_html_e('Enable this if your theme does not support breadcrumbs or if you want breadcrumbs to appear on all pages including 404 pages. Uses the wp_body_open hook.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_show_home_callback() {
        $show_home = get_option('seo_fury_breadcrumbs_show_home', 1);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_show_home" value="1" <?php checked($show_home, 1); ?>>
            <?php esc_html_e('Show link to the homepage', 'seo-fury'); ?>
        </label>
        <?php
    }

    public function breadcrumbs_home_label_callback() {
        $label = get_option('seo_fury_breadcrumbs_home_label', __('Home', 'seo-fury'));
        ?>
        <input type="text" name="seo_fury_breadcrumbs_home_label" value="<?php echo esc_attr($label); ?>" class="regular-text" />
        <p class="description"><?php esc_html_e('The label used for the homepage link (the first item) in breadcrumb trails.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_home_url_callback() {
        $home_url = get_option('seo_fury_breadcrumbs_home_url', '');
        ?>
        <input type="text" name="seo_fury_breadcrumbs_home_url" value="<?php echo esc_attr($home_url); ?>" class="regular-text" placeholder="<?php echo esc_attr(home_url('/')); ?>" />
        <p class="description"><?php esc_html_e('The homepage link (the first item) in breadcrumb trails. Leave empty to use the default homepage URL.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_prefix_callback() {
        $prefix = get_option('seo_fury_breadcrumbs_prefix', '');
        ?>
        <input type="text" name="seo_fury_breadcrumbs_prefix" value="<?php echo esc_attr($prefix); ?>" class="regular-text" />
        <p class="description"><?php esc_html_e('An element displayed before the breadcrumb trail.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_separator_callback() {
        $separator = get_option('seo_fury_breadcrumbs_separator', '›');
        $custom_separator = get_option('seo_fury_breadcrumbs_separator_custom', '');
        $predefined = array('›', '-', '–', '—', '»', '|', '•');
        ?>
        <select name="seo_fury_breadcrumbs_separator" id="breadcrumbs_separator">
            <?php foreach ($predefined as $sep): ?>
                <option value="<?php echo esc_attr($sep); ?>" <?php selected($separator, $sep); ?>><?php echo esc_html($sep); ?></option>
            <?php endforeach; ?>
            <option value="custom" <?php selected($separator, 'custom'); ?>><?php esc_html_e('Custom', 'seo-fury'); ?></option>
        </select>
        <input type="text" name="seo_fury_breadcrumbs_separator_custom" id="breadcrumbs_separator_custom" value="<?php echo esc_attr($custom_separator); ?>" style="width: 150px; margin-left: 10px; <?php echo ($separator === 'custom') ? '' : 'display:none;'; ?>" placeholder="<?php echo esc_attr__('Enter custom separator', 'seo-fury'); ?>" />
        <script>
        jQuery(document).ready(function($) {
            $('#breadcrumbs_separator').on('change', function() {
                if ($(this).val() === 'custom') {
                    $('#breadcrumbs_separator_custom').show();
                } else {
                    $('#breadcrumbs_separator_custom').hide();
                }
            });
        });
        </script>
        <?php
    }

    public function breadcrumbs_archive_format_callback() {
        $format = get_option('seo_fury_breadcrumbs_archive_format', '');
        $placeholder = self::get_localized_archive_format();
        ?>
        <input type="text" name="seo_fury_breadcrumbs_archive_format" value="<?php echo esc_attr($format); ?>" class="regular-text" placeholder="<?php echo esc_attr($placeholder); ?>" />
        <p class="description"><?php
        /* translators: 1: %s placeholder variable, 2: example archive format string */
        printf( esc_html__('Format the label used for archive pages. Use %1$s as a placeholder for the archive name (e.g. %2$s will display "Archives for News" on the News category page). Leave blank to show just the archive name.', 'seo-fury'), '<code>%s</code>', '<code>"Archives for %s"</code>' ); ?></p>
        <?php
    }

    public function breadcrumbs_search_format_callback() {
        $format = get_option('seo_fury_breadcrumbs_search_format', '');
        $placeholder = self::get_localized_search_format();
        ?>
        <input type="text" name="seo_fury_breadcrumbs_search_format" value="<?php echo esc_attr($format); ?>" class="regular-text" placeholder="<?php echo esc_attr($placeholder); ?>" />
        <p class="description"><?php
        /* translators: %s: placeholder variable for search query */
        esc_html_e('Format the label used for search results pages. Use %s as a placeholder for the search query.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_404_label_callback() {
        $label = get_option('seo_fury_breadcrumbs_404_label', '');
        $placeholder = self::get_localized_404_label();
        ?>
        <input type="text" name="seo_fury_breadcrumbs_404_label" value="<?php echo esc_attr($label); ?>" class="regular-text" placeholder="<?php echo esc_attr($placeholder); ?>" />
        <p class="description"><?php esc_html_e('The label used for the 404 error page in breadcrumb trails.', 'seo-fury'); ?></p>
        <?php
    }

    /**
     * Locale-aware default for search results format.
     */
    private static function get_localized_search_format() {
        $locale = determine_locale();
        $defaults = array(
            'ru_RU' => "\xd0\xa0\xd0\xb5\xd0\xb7\xd1\x83\xd0\xbb\xd1\x8c\xd1\x82\xd0\xb0\xd1\x82\xd1\x8b \xd0\xbf\xd0\xbe\xd0\xb8\xd1\x81\xd0\xba\xd0\xb0: \"%s\"",
            'uk'    => "\xd0\xa0\xd0\xb5\xd0\xb7\xd1\x83\xd0\xbb\xd1\x8c\xd1\x82\xd0\xb0\xd1\x82\xd0\xb8 \xd0\xbf\xd0\xbe\xd1\x88\xd1\x83\xd0\xba\xd1\x83: \"%s\"",
            'de_DE' => 'Suchergebnisse f' . "\xc3\xbc" . 'r: "%s"',
            'fr_FR' => 'R' . "\xc3\xa9" . 'sultats de recherche pour: "%s"',
            'es_ES' => 'Resultados de b' . "\xc3\xba" . 'squeda para: "%s"',
            'it_IT' => 'Risultati della ricerca per: "%s"',
            'pt_BR' => 'Resultados da pesquisa para: "%s"',
            'nl_NL' => 'Zoekresultaten voor: "%s"',
            'pl_PL' => 'Wyniki wyszukiwania dla: "%s"',
            'ja'    => '"%s" ' . "\xe3\x81\xae\xe6\xa4\x9c\xe7\xb4\xa2\xe7\xb5\x90\xe6\x9e\x9c",
            'zh_CN' => '"%s" ' . "\xe7\x9a\x84\xe6\x90\x9c\xe7\xb4\xa2\xe7\xbb\x93\xe6\x9e\x9c",
        );
        /* translators: %s: search query */
        return isset($defaults[$locale]) ? $defaults[$locale] : __('Search results for "%s"', 'seo-fury');
    }

    /**
     * Locale-aware default for 404 page label.
     */
    private static function get_localized_404_label() {
        $locale = determine_locale();
        $defaults = array(
            'ru_RU' => "\xd0\xa1\xd1\x82\xd1\x80\xd0\xb0\xd0\xbd\xd0\xb8\xd1\x86\xd0\xb0 \xd0\xbd\xd0\xb5 \xd0\xbd\xd0\xb0\xd0\xb9\xd0\xb4\xd0\xb5\xd0\xbd\xd0\xb0",
            'uk'    => "\xd0\xa1\xd1\x82\xd0\xbe\xd1\x80\xd1\x96\xd0\xbd\xd0\xba\xd1\x83 \xd0\xbd\xd0\xb5 \xd0\xb7\xd0\xbd\xd0\xb0\xd0\xb9\xd0\xb4\xd0\xb5\xd0\xbd\xd0\xbe",
            'de_DE' => 'Seite nicht gefunden',
            'fr_FR' => 'Page non trouv' . "\xc3\xa9" . 'e',
            'es_ES' => 'P' . "\xc3\xa1" . 'gina no encontrada',
            'it_IT' => 'Pagina non trovata',
            'pt_BR' => 'P' . "\xc3\xa1" . 'gina n' . "\xc3\xa3" . 'o encontrada',
            'nl_NL' => 'Pagina niet gevonden',
            'pl_PL' => 'Strona nie znaleziona',
            'ja'    => "\xe3\x83\x9a\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\x8c\xe8\xa6\x8b\xe3\x81\xa4\xe3\x81\x8b\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x9b\xe3\x82\x93",
            'zh_CN' => "\xe9\xa1\xb5\xe9\x9d\xa2\xe6\x9c\xaa\xe6\x89\xbe\xe5\x88\xb0",
        );
        return isset($defaults[$locale]) ? $defaults[$locale] : __('Page not found', 'seo-fury');
    }

    /**
     * Locale-aware default for archive format.
     */
    private static function get_localized_archive_format() {
        $locale = determine_locale();
        $defaults = array(
            'ru_RU' => "\xd0\x90\xd1\x80\xd1\x85\xd0\xb8\xd0\xb2\xd1\x8b: %s",
            'uk'    => "\xd0\x90\xd1\x80\xd1\x85\xd1\x96\xd0\xb2\xd0\xb8: %s",
            'de_DE' => 'Archiv: %s',
            'fr_FR' => 'Archives: %s',
            'es_ES' => 'Archivos: %s',
            'it_IT' => 'Archivi: %s',
            'pt_BR' => 'Arquivos: %s',
            'nl_NL' => 'Archief: %s',
            'pl_PL' => 'Archiwum: %s',
            'ja'    => "\xe3\x82\xa2\xe3\x83\xbc\xe3\x82\xab\xe3\x82\xa4\xe3\x83\x96: %s",
            'zh_CN' => "\xe5\xbd\x92\xe6\xa1\xa3: %s",
        );
        /* translators: %s: archive name */
        return isset($defaults[$locale]) ? $defaults[$locale] : __('Archives for %s', 'seo-fury');
    }

    public function breadcrumbs_hide_post_title_callback() {
        $hide_post_title = get_option('seo_fury_breadcrumbs_hide_post_title', 0);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_hide_post_title" value="1" <?php checked($hide_post_title, 1); ?>>
            <?php esc_html_e('Hide the post title in the breadcrumb trail', 'seo-fury'); ?>
        </label>
        <?php
    }

    public function breadcrumbs_show_categories_callback() {
        $show_categories = get_option('seo_fury_breadcrumbs_show_categories', 1);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_show_categories" value="1" <?php checked($show_categories, 1); ?>>
            <?php esc_html_e('If a category is a child, display all parent categories', 'seo-fury'); ?>
        </label>
        <?php
    }

    public function breadcrumbs_hide_taxonomy_callback() {
        $hide_taxonomy = get_option('seo_fury_breadcrumbs_hide_taxonomy', 0);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_hide_taxonomy" value="1" <?php checked($hide_taxonomy, 1); ?>>
            <?php esc_html_e('Hide the taxonomy name in the breadcrumb trail', 'seo-fury'); ?>
        </label>
        <?php
    }

    public function breadcrumbs_blog_link_callback() {
        $blog_link = get_option('seo_fury_breadcrumbs_blog_link', 0);
        ?>
        <label>
            <input type="checkbox" name="seo_fury_breadcrumbs_blog_link" value="1" <?php checked($blog_link, 1); ?>>
            <?php esc_html_e('For single posts, show a single Blog link instead of the post categories', 'seo-fury'); ?>
        </label>
        <p class="description"><?php esc_html_e('When enabled, the breadcrumb trail for blog posts will be "Home › Blog › Post title" instead of using the post category. This overrides the "Show Categories" option for posts.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_blog_label_callback() {
        $label = get_option('seo_fury_breadcrumbs_blog_label', '');
        ?>
        <input type="text" name="seo_fury_breadcrumbs_blog_label" value="<?php echo esc_attr($label); ?>" class="regular-text" placeholder="<?php echo esc_attr__('Blog', 'seo-fury'); ?>" />
        <p class="description"><?php esc_html_e('The label used for the Blog link. Leave blank to use the actual title of the linked blog page (its H1); falls back to "Blog" if the page cannot be determined.', 'seo-fury'); ?></p>
        <?php
    }

    public function breadcrumbs_blog_url_callback() {
        $blog_url = get_option('seo_fury_breadcrumbs_blog_url', '');
        $placeholder = self::get_default_blog_url();
        if (empty($placeholder)) {
            $placeholder = home_url('/blog/');
        }
        ?>
        <input type="text" name="seo_fury_breadcrumbs_blog_url" value="<?php echo esc_attr($blog_url); ?>" class="regular-text" placeholder="<?php echo esc_attr($placeholder); ?>" />
        <p class="description"><?php esc_html_e('The URL the Blog link points to. Leave blank to use the WordPress posts page automatically.', 'seo-fury'); ?></p>
        <?php
    }

    /**
     * Resolve the default Blog URL from the WordPress "Posts page" setting.
     * Returns an empty string when no posts page is configured.
     */
    private static function get_default_blog_url() {
        $page_for_posts = (int) get_option('page_for_posts');
        if ($page_for_posts > 0) {
            $url = get_permalink($page_for_posts);
            if ($url) {
                return $url;
            }
        }
        return '';
    }

    public function render_shortcode() {
        return $this->get_breadcrumbs_html();
    }

    /**
     * Build and return the breadcrumb items array.
     *
     * Each item: array( 'label' => string, 'url' => string ).
     * url is empty for the current (non-linked) item.
     */
    public function get_breadcrumb_items() {
        $show_home = get_option('seo_fury_breadcrumbs_show_home', 1);
        $home_label = get_option('seo_fury_breadcrumbs_home_label', __('Home', 'seo-fury'));
        $home_url = get_option('seo_fury_breadcrumbs_home_url', '');
        $archive_format = get_option('seo_fury_breadcrumbs_archive_format', '');
        if (empty($archive_format)) {
            $archive_format = self::get_localized_archive_format();
        }
        $search_format = get_option('seo_fury_breadcrumbs_search_format', '');
        if (empty($search_format)) {
            $search_format = self::get_localized_search_format();
        }
        $label_404 = get_option('seo_fury_breadcrumbs_404_label', '');
        if (empty($label_404)) {
            $label_404 = self::get_localized_404_label();
        }
        $hide_post_title = get_option('seo_fury_breadcrumbs_hide_post_title', 0);
        $show_categories = get_option('seo_fury_breadcrumbs_show_categories', 1);
        $hide_taxonomy = get_option('seo_fury_breadcrumbs_hide_taxonomy', 0);

        $home_link = !empty($home_url) ? $home_url : home_url('/');

        $items = array();

        if ($show_home) {
            $items[] = array('label' => $home_label, 'url' => $home_link);
        }

        if (is_singular()) {
            global $post;
            if (is_page()) {
                $ancestors = array_reverse(get_post_ancestors($post));
                foreach ($ancestors as $ancestor_id) {
                    $items[] = array(
                        'label' => get_the_title($ancestor_id),
                        'url' => get_permalink($ancestor_id)
                    );
                }
            } elseif (is_single()) {
                $blog_link = get_option('seo_fury_breadcrumbs_blog_link', 0);
                if ($blog_link && get_post_type($post) === 'post') {
                    // Resolve the target blog page (and its ID) so we can fall
                    // back to its actual title when no custom label is set.
                    $blog_url     = get_option('seo_fury_breadcrumbs_blog_url', '');
                    $blog_page_id = 0;
                    if (empty($blog_url)) {
                        $blog_page_id = (int) get_option('page_for_posts');
                        if ($blog_page_id > 0) {
                            $blog_url = get_permalink($blog_page_id);
                        }
                    } else {
                        $blog_page_id = (int) url_to_postid($blog_url);
                    }

                    $blog_label = get_option('seo_fury_breadcrumbs_blog_label', '');
                    if ($blog_label === '') {
                        if ($blog_page_id > 0) {
                            $blog_label = get_the_title($blog_page_id);
                        }
                        if ($blog_label === '') {
                            $blog_label = __('Blog', 'seo-fury');
                        }
                    }

                    if (!empty($blog_url)) {
                        $items[] = array('label' => $blog_label, 'url' => $blog_url);
                    }
                } elseif ($show_categories) {
                    $categories = get_the_category($post->ID);
                    if (!empty($categories)) {
                        $primary = $categories[0];
                        $cat_ancestors = array_reverse(get_ancestors($primary->term_id, 'category'));
                        foreach ($cat_ancestors as $cat_id) {
                            $items[] = array(
                                'label' => get_cat_name($cat_id),
                                'url' => get_category_link($cat_id)
                            );
                        }
                        $items[] = array(
                            'label' => $primary->name,
                            'url' => get_category_link($primary->term_id)
                        );
                    }
                }
            }

            if (!$hide_post_title) {
                $items[] = array('label' => get_the_title($post), 'url' => '');
            }
        } elseif (is_archive()) {
            if (is_category()) {
                $current_cat = get_queried_object();
                if ($current_cat && $show_categories && $current_cat->parent) {
                    $cat_ancestors = array_reverse(get_ancestors($current_cat->term_id, 'category'));
                    foreach ($cat_ancestors as $cat_id) {
                        $items[] = array(
                            'label' => get_cat_name($cat_id),
                            'url' => get_category_link($cat_id)
                        );
                    }
                }
                $archive_name = $current_cat ? $current_cat->name : '';
                if (!$hide_taxonomy) {
                    $taxonomy_obj = get_taxonomy('category');
                    $taxonomy_label = $taxonomy_obj ? $taxonomy_obj->labels->singular_name : '';
                    if ($taxonomy_label) {
                        $archive_name = $taxonomy_label . ': ' . $archive_name;
                    }
                }
                if ($archive_format && strpos($archive_format, '%s') !== false) {
                    $label = sprintf($archive_format, $archive_name);
                } else {
                    $label = $archive_name;
                }
                $items[] = array('label' => $label, 'url' => '');
            } elseif (is_tag() || is_tax()) {
                $term = get_queried_object();
                $archive_name = $term ? $term->name : '';
                if (!$hide_taxonomy) {
                    $taxonomy_obj = get_taxonomy($term->taxonomy);
                    $taxonomy_label = $taxonomy_obj ? $taxonomy_obj->labels->singular_name : '';
                    if ($taxonomy_label) {
                        $archive_name = $taxonomy_label . ': ' . $archive_name;
                    }
                }
                if ($archive_format && strpos($archive_format, '%s') !== false) {
                    $label = sprintf($archive_format, $archive_name);
                } else {
                    $label = $archive_name;
                }
                $items[] = array('label' => $label, 'url' => '');
            } else {
                $archive_title = get_the_archive_title();
                $archive_title = wp_strip_all_tags($archive_title);
                if ($hide_taxonomy) {
                    $archive_title = preg_replace('/^[^:]+:\s*/', '', $archive_title);
                }
                if ($archive_format && strpos($archive_format, '%s') !== false) {
                    $archive_title = sprintf($archive_format, $archive_title);
                }
                $items[] = array('label' => $archive_title, 'url' => '');
            }
        } elseif (is_home()) {
            // Blog posts index (the designated "Posts page"). WordPress sets
            // is_home() here — not is_singular()/is_archive() — so add the
            // posts page itself as the current, non-linked trail item. Skip
            // when the blog is the front page (Home already covers it).
            if (!is_front_page()) {
                $page_for_posts = (int) get_option('page_for_posts');
                $home_label_text = $page_for_posts ? get_the_title($page_for_posts) : '';
                if ($home_label_text === '') {
                    $home_label_text = __('Blog', 'seo-fury');
                }
                $items[] = array('label' => $home_label_text, 'url' => '');
            }
        } elseif (is_search()) {
            $search_query = get_search_query();
            $search_label = sprintf($search_format, $search_query);
            $items[] = array('label' => $search_label, 'url' => '');
        } elseif (is_404()) {
            $items[] = array('label' => $label_404, 'url' => '');
        }

        return $items;
    }

    public function get_breadcrumbs_html() {
        $enabled = get_option('seo_fury_breadcrumbs_enabled', 1);
        if (!$enabled) {
            return '';
        }

        $separator = get_option('seo_fury_breadcrumbs_separator', '›');
        if ($separator === 'custom') {
            $separator = get_option('seo_fury_breadcrumbs_separator_custom', '›');
        }
        $prefix = get_option('seo_fury_breadcrumbs_prefix', '');

        $items = $this->get_breadcrumb_items();

        $parts = array();
        foreach ($items as $item) {
            if (!empty($item['url'])) {
                $parts[] = '<a href="' . esc_url($item['url']) . '">' . esc_html($item['label']) . '</a>';
            } else {
                $parts[] = '<span>' . esc_html($item['label']) . '</span>';
            }
        }

        $output = '';
        if (!empty($prefix)) {
            $output .= '<span class="breadcrumb-prefix">' . esc_html($prefix) . ' </span>';
        }

        $output .= implode(' <span class="separator">' . esc_html($separator) . '</span> ', $parts);

        return '<nav class="seo-fury-breadcrumbs">' . $output . '</nav>';
    }

    /**
     * Inject a BreadcrumbList node into the unified schema @graph when:
     *  1. The breadcrumbs module is enabled.
     *  2. The post content contains one of our breadcrumb shortcodes.
     *  3. Schema/micromarkup is enabled for this post type (either a
     *     post-specific schema is configured or a default schema type is set).
     *
     * @param array    $nodes Existing schema nodes.
     * @param \WP_Post $post  Current post object.
     * @return array
     */
    public function inject_breadcrumb_schema_node( $nodes, $post ) {
        if ( ! get_option( 'seo_fury_breadcrumbs_enabled', 1 ) ) {
            return $nodes;
        }

        // Resolve default: on when breadcrumbs are enabled, off otherwise.
        $schema_opt = get_option( 'seo_fury_breadcrumbs_schema', null );
        if ( $schema_opt === null || $schema_opt === false || $schema_opt === '' ) {
            $schema_opt = get_option( 'seo_fury_breadcrumbs_enabled', 1 ) ? 1 : 0;
        }
        if ( ! $schema_opt ) {
            return $nodes;
        }

        if ( ! is_singular() ) {
            return $nodes;
        }

        // Check if any breadcrumb shortcode is present in the post content.
        $has_shortcode = false;
        foreach ( self::$breadcrumb_shortcodes as $tag ) {
            if ( has_shortcode( $post->post_content, $tag ) ) {
                $has_shortcode = true;
                break;
            }
        }

        if ( ! $has_shortcode ) {
            return $nodes;
        }

        // Build BreadcrumbList from the same items used for the visible trail.
        $items = $this->get_breadcrumb_items();
        if ( empty( $items ) ) {
            return $nodes;
        }

        $list_elements = array();
        $position      = 1;
        foreach ( $items as $item ) {
            $list_item = array(
                '@type'    => 'ListItem',
                'position' => $position++,
                'name'     => $item['label'],
            );
            if ( ! empty( $item['url'] ) ) {
                $list_item['item'] = $item['url'];
            }
            $list_elements[] = $list_item;
        }

        $nodes[] = array(
            '@type'           => 'BreadcrumbList',
            'itemListElement' => $list_elements,
        );

        return $nodes;
    }
}

function seo_fury_breadcrumbs() {
    if (!class_exists('SEO_Fury_Core')) {
        return;
    }
    $core = SEO_Fury_Core::get_instance();
    $breadcrumbs = method_exists($core, 'get_breadcrumbs') ? $core->get_breadcrumbs() : null;
    if ($breadcrumbs) {
        echo wp_kses_post( $breadcrumbs->get_breadcrumbs_html() ); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
    }
}
