{{- /*
  Code block wrapper hook for highlight output.
  - Applies wrapper UI features based on codeblock config.
  - Supports classic/modern modes, copy button, expand button, and line-number states.
  @param {Object} .Attributes - Code block attributes
  @param {Object} .Options - Code fence options
  @param {String} .Inner - Raw code content
  @param {Object} .Page - Current page context
  @param {String} .Type - Language/type for current block
*/ -}}

{{- $config := .Attributes | merge (dict "Page" .Page "Key" "codeblock" | partial "function/param.html") -}}

{{- /* Deprecated camelCase attribute support: Hugo lowercases Markdown attributes */ -}}
{{- if isset .Attributes "wrapperclass" | and (not (isset .Attributes "wrapper_class")) -}}
  {{- warnidf "v1-deprecated-codeblock-attr" "The attribute `wrapperClass` is deprecated since v1.0.0, use `wrapper_class` instead. See %s" .Position -}}
{{- end -}}
{{- if isset .Attributes "maxshownlines" | and (not (isset .Attributes "max_shown_lines")) -}}
  {{- warnidf "v1-deprecated-codeblock-attr" "The attribute `maxShownLines` is deprecated since v1.0.0, use `max_shown_lines` instead. See %s" .Position -}}
{{- end -}}
{{- if isset .Attributes "linenostoggler" | and (not (isset .Attributes "line_nos_toggler")) -}}
  {{- warnidf "v1-deprecated-codeblock-attr" "The attribute `lineNosToggler` is deprecated since v1.0.0, use `line_nos_toggler` instead. See %s" .Position -}}
{{- end -}}
{{- if isset .Attributes "linewraptoggler" | and (not (isset .Attributes "line_wrap_toggler")) -}}
  {{- warnidf "v1-deprecated-codeblock-attr" "The attribute `lineWrapToggler` is deprecated since v1.0.0, use `line_wrap_toggler` instead. See %s" .Position -}}
{{- end -}}

{{- $result := transform.HighlightCodeBlock . -}}
{{- $wrapper := $result.Wrapped -}}

{{- /* If wrapper is enabled, add code wrapper and more features */ -}}
{{- if $config.wrapper -}}
  {{- $mode := $config.mode | default "classic" -}}
  {{- $lines := cond .Inner (len (split .Inner "\n")) 0 -}}
  {{- $maxShownLines := $config.max_shown_lines | default .Attributes.maxshownlines -}}
  {{- $lineNoStart := cond (ne .Options.linenostart nil) .Options.linenostart 1 -}}
  {{- $lineNosDigit := strings.RuneCount (sub (add $lines $lineNoStart) 1) -}}
  {{- $class := "highlight" -}}
  {{- with $config.class -}}{{ $class = add $class " " . }}{{- end -}}
  {{- $targetClass := add "code-block " $class -}}
  {{- with ($config.wrapper_class | default .Attributes.wrapperclass) -}}{{ $targetClass = add $targetClass " " . }}{{- end -}}

  {{- /* Add code wrapper around the table or pre */ -}}
  {{- $REin := cond (strings.Contains $wrapper `<table class="lntable">`)
    `(<table class="lntable">[\s\S]*?<\/table>)`
    `(<pre tabindex="0" class="chroma">[\s\S]*?<\/pre>)` -}}
  {{- $REout := printf `<div class="code-wrapper">$1</div>` -}}
  {{- $wrapper = replaceRE $REin $REout $wrapper -}}

  {{- /* Hide line numbers if linenos=false */ -}}
  {{- if (not (strings.Contains $wrapper `class="lnt"`)) | and (not (strings.Contains $wrapper `class="ln"`)) -}}
    {{- $targetClass = add $targetClass " line-nos-hidden" -}}
  {{- end -}}

  {{- /* Add code expand button */ -}}
  {{- if (gt $lines $maxShownLines) | and (gt $lines 0) | and (gt $maxShownLines 0) -}}
    {{- $wrapper = dict "Wrapper" $wrapper | partial "function/code-expand-btn.html" -}}
  {{- end -}}

  {{- /* Render for different modes */ -}}
  {{- if eq $mode "classic" -}}
    {{- $wrapper = dict "Wrapper" $wrapper "Config" $config "Type" .Type | partial "function/code-header.html" -}}
  {{- else -}}
    {{- $wrapper = dict "Wrapper" $wrapper "Config" $config | partial "function/code-copy-btn.html" -}}
  {{- end -}}

  {{- /*
    Add data attributes and class
    Directly set CSS variables to ensure compatibility with non-Chromium-based browsers
    See https://caniuse.com/css3-attr for attr() support status
  */ -}}
  {{- if $config.editable -}}
    {{- $wrapper =
      replace $wrapper
      (printf `class="%s"` $class)
      (printf `class="%s" data-editable="%v"` $class $config.editable)
    -}}
  {{- end -}}
  {{- if $config.copyable -}}
    {{- $wrapper =
      replace $wrapper
      (printf `class="%s"` $class)
      (printf `class="%s" data-copyable="%v"` $class $config.copyable)
    -}}
  {{- end -}}
  {{- if ne $config.shadow "never" -}}
    {{- $wrapper =
      replace $wrapper
      (printf `class="%s"` $class)
      (printf `class="%s" data-shadow="%s"` $class $config.shadow)
    -}}
  {{- end -}}
  {{- if $config.group -}}
    {{- $tabTitle := $config.name | default (strings.FirstUpper .Type) | default "Code" -}}
    {{- $groupKey := printf "code-tab-group-first:%s" $config.group -}}
    {{- $isFirst := not (.Page.Store.Get $groupKey) -}}
    {{- if $isFirst -}}
      {{- .Page.Store.Set $groupKey true -}}
    {{- else -}}
      {{- $targetClass = add $targetClass " hidden" -}}
    {{- end -}}
    {{- $wrapper =
      replace $wrapper
      (printf `class="%s"` $class)
      (printf `class="%s" data-tab-title="%s"` $class $tabTitle)
    -}}
  {{- end -}}
  {{- if ne .Options.linenostart nil -}}
    {{- $wrapper =
      replace $wrapper
      `class="code-wrapper"`
      (printf `class="code-wrapper" data-line-start="%v"` .Options.linenostart)
    -}}
  {{- end -}}
  {{- $wrapperStyle := printf "--fi-max-shown-lines:%v;--fi-line-digit:%v;--fi-line-start:%v;" $maxShownLines $lineNosDigit $lineNoStart -}}
  {{- $wrapper =
    replace $wrapper
    `class="code-wrapper"`
    (printf `class="code-wrapper" style="%s"` $wrapperStyle)
  -}}
  {{- $wrapper =
    replace $wrapper
    `class="code-wrapper"`
    (printf
      `class="code-wrapper" data-max="%v" data-line-digit="%d"`
      $maxShownLines
      $lineNosDigit
    )
  -}}
  {{- $wrapper =
    replace $wrapper
    (printf `class="%s"` $class)
    (printf `class="%s" data-mode="%s"` $targetClass $mode)
  -}}
{{- end -}}

{{- $wrapper | safeHTML -}}
