<?php
if ( ! defined( 'ABSPATH' ) ) {
    exit;
}

add_shortcode( 'idsc_toc', 'idsc_toc_shortcode' );

// Add IDs to content headings so TOC links work
add_filter( 'the_content', 'idsc_toc_add_heading_ids', 5 );

function idsc_toc_shortcode( $atts ) {
    IDSC_Assets::flag_css();
    IDSC_Assets::flag_js();

    $atts = shortcode_atts( array(
        'levels'      => 'h2,h3',
        'title'       => 'On This Page',
        'style'       => 'numbered',
        'collapsible' => 'no',
    ), $atts, 'idsc_toc' );

    // Store attrs for the_content filter to use
    $GLOBALS['idsc_toc_atts'] = $atts;

    // Return placeholder — replaced in the_content filter after headings are parsed
    return '<!--idsc_toc_placeholder-->';
}

function idsc_toc_add_heading_ids( $content ) {
    if ( ! isset( $GLOBALS['idsc_toc_atts'] ) ) {
        return $content;
    }
    if ( strpos( $content, '<!--idsc_toc_placeholder-->' ) === false ) {
        return $content;
    }

    $atts   = $GLOBALS['idsc_toc_atts'];
    $levels = array_map( 'trim', explode( ',', $atts['levels'] ) );
    $regex  = '/<(h[1-6])([^>]*)>(.*?)<\/h[1-6]>/is';
    $items  = array();
    $used   = array();

    // Add IDs to headings and collect TOC entries
    $content = preg_replace_callback( $regex, function( $match ) use ( $levels, &$items, &$used ) {
        $tag   = strtolower( $match[1] );
        $attrs = $match[2];
        $text  = wp_strip_all_tags( $match[3] );

        if ( ! in_array( $tag, $levels, true ) ) {
            return $match[0];
        }

        // Generate a slug
        $slug = sanitize_title( $text );
        if ( empty( $slug ) ) {
            $slug = 'section';
        }
        if ( isset( $used[ $slug ] ) ) {
            $used[ $slug ]++;
            $slug .= '-' . $used[ $slug ];
        } else {
            $used[ $slug ] = 1;
        }

        // Check if heading already has an id
        if ( preg_match( '/\bid=["\']([^"\']+)["\']/i', $attrs ) ) {
            preg_match( '/\bid=["\']([^"\']+)["\']/i', $attrs, $id_match );
            $slug = $id_match[1];
        } else {
            $attrs .= ' id="' . esc_attr( $slug ) . '"';
        }

        $level   = intval( substr( $tag, 1 ) );
        $items[] = array( 'slug' => $slug, 'text' => $text, 'level' => $level );

        return '<' . $tag . $attrs . '>' . $match[3] . '</' . $tag . '>';
    }, $content );

    // Build TOC HTML
    $list_tag = $atts['style'] === 'numbered' ? 'ol' : 'ul';
    $toc_html = '';

    if ( ! empty( $items ) ) {
        $class = 'idsc-toc';
        if ( $atts['collapsible'] === 'yes' ) {
            $toc_html .= '<details class="' . esc_attr( $class ) . '" open>';
            $toc_html .= '<summary class="idsc-toc__title">' . esc_html( $atts['title'] ) . '</summary>';
        } else {
            $toc_html .= '<nav class="' . esc_attr( $class ) . '">';
            if ( ! empty( $atts['title'] ) ) {
                $toc_html .= '<div class="idsc-toc__title">' . esc_html( $atts['title'] ) . '</div>';
            }
        }

        $toc_html .= '<' . $list_tag . ' class="idsc-toc__list">';
        foreach ( $items as $item ) {
            $indent = $item['level'] - $items[0]['level'];
            $pad    = $indent > 0 ? ' style="margin-left:' . ( $indent * 20 ) . 'px"' : '';
            $toc_html .= '<li class="idsc-toc__item"' . $pad . '><a href="#' . esc_attr( $item['slug'] ) . '" data-idsc-smooth>' . esc_html( $item['text'] ) . '</a></li>';
        }
        $toc_html .= '</' . $list_tag . '>';

        if ( $atts['collapsible'] === 'yes' ) {
            $toc_html .= '</details>';
        } else {
            $toc_html .= '</nav>';
        }
    }

    $content = str_replace( '<!--idsc_toc_placeholder-->', $toc_html, $content );

    unset( $GLOBALS['idsc_toc_atts'] );

    return $content;
}
