class ViewComponentContrib::StyleVariants::StyleSet

def base(&block)

def base(&block)
  @base_block = block
end

def base(&block)

def base(&block)
  @base_block = block
end

def build_variants(&block)

def build_variants(&block)
  VariantBuilder.new(true).build(&block)
end

def build_variants(&block)

def build_variants(&block)
  VariantBuilder.new(true).build(&block)
end

def cast_value(val)

def cast_value(val)
  case val
  when true then :yes
  when false then :no
  else
    val
  end
end

def cast_value(val)

def cast_value(val)
  case val
  when true then :yes
  when false then :no
  else
    val
  end
end

def compile(**variants)

def compile(**variants)
  acc = Array(@base_block&.call || [])
  config = @defaults.merge(variants.compact)
  config.each do |variant, value|
    value = cast_value(value)
    variant = @variants.dig(variant, value) || next
    styles = variant.is_a?(::Proc) ? variant.call(**config) : variant
    acc.concat(Array(styles))
  end
  @compounds.each do |compound, value|
    next unless compound.all? { |k, v| config[k] == v }
    styles = value.is_a?(::Proc) ? value.call(**config) : value
    acc.concat(Array(styles))
  end
  acc.concat(Array(config[:class]))
  acc.concat(Array(config[:class_name]))
  acc
end

def compile(**variants)

def compile(**variants)
  acc = Array(@base_block&.call || [])
  config = @defaults.merge(variants.compact)
  config.each do |variant, value|
    value = cast_value(value)
    variant = @variants.dig(variant, value) || next
    styles = variant.is_a?(::Proc) ? variant.call(**config) : variant
    acc.concat(Array(styles))
  end
  @compounds.each do |compound, value|
    next unless compound.all? { |k, v| config[k] == v }
    styles = value.is_a?(::Proc) ? value.call(**config) : value
    acc.concat(Array(styles))
  end
  acc.concat(Array(config[:class]))
  acc.concat(Array(config[:class_name]))
  acc
end

def compound(**variants, &block)

def compound(**variants, &block)
  @compounds[variants] = block
end

def compound(**variants, &block)

def compound(**variants, &block)
  @compounds[variants] = block
end

def defaults(&block)

def defaults(&block)
  @defaults = block.call.freeze
end

def defaults(&block)

def defaults(&block)
  @defaults = block.call.freeze
end

def dup

def dup
  copy = super
  copy.instance_variable_set(:@defaults, @defaults.dup)
  copy.instance_variable_set(:@variants, @variants.dup)
  copy.instance_variable_set(:@compounds, @compounds.dup)
  copy
end

def dup

def dup
  copy = super
  copy.instance_variable_set(:@defaults, @defaults.dup)
  copy.instance_variable_set(:@variants, @variants.dup)
  copy.instance_variable_set(:@compounds, @compounds.dup)
  copy
end

def find_parent_variants

def find_parent_variants
  parent_component = @init_block.binding.receiver.superclass
  return unless parent_component.respond_to?(:style_config)
  parent_config = parent_component.style_config
  default_parent_style = parent_component.default_style_name
  parent_style_set = parent_config.instance_variable_get(:@styles)[default_parent_style.to_sym]
  parent_style_set.instance_variable_get(:@variants).deep_dup
end

def find_parent_variants

def find_parent_variants
  parent_component = @init_block.binding.receiver.superclass
  return unless parent_component.respond_to?(:style_config)
  parent_config = parent_component.style_config
  default_parent_style = parent_component.default_style_name
  parent_style_set = parent_config.instance_variable_get(:@styles)[default_parent_style.to_sym]
  parent_style_set.instance_variable_get(:@variants).deep_dup
end

def handle_variants(variants, strategy)

def handle_variants(variants, strategy)
  return variants if strategy == :override
  parent_variants = find_parent_variants
  return variants unless parent_variants
  return parent_variants.deep_merge(variants) if strategy == :merge
  parent_variants.merge(variants) if strategy == :extend
end

def handle_variants(variants, strategy)

def handle_variants(variants, strategy)
  return variants if strategy == :override
  parent_variants = find_parent_variants
  return variants unless parent_variants
  return parent_variants.deep_merge(variants) if strategy == :merge
  parent_variants.merge(variants) if strategy == :extend
end

def initialize(&init_block)

def initialize(&init_block)
  @base_block = nil
  @defaults = {}
  @variants = {}
  @compounds = {}
  return unless init_block
  @init_block = init_block
  instance_eval(&init_block)
end

def initialize(&init_block)

def initialize(&init_block)
  @base_block = nil
  @defaults = {}
  @variants = {}
  @compounds = {}
  return unless init_block
  @init_block = init_block
  instance_eval(&init_block)
end

def variants(strategy: :override, &block)

def variants(strategy: :override, &block)
  variants = build_variants(&block)
  @variants = handle_variants(variants, strategy)
end

def variants(strategy: :override, &block)

def variants(strategy: :override, &block)
  variants = build_variants(&block)
  @variants = handle_variants(variants, strategy)
end