Ctrl K
ComunidadGuías…

src/services/chartConfig.ts

Rama main · réplica de lectura del repositorio original.

Archivo original ↗Preguntar a KiBot
/**
 * Shared Chart.js configuration utilities for consistent styling across all dashboard charts
 */

interface AxisConfig {
  grid?: {
    color: string
    drawBorder?: boolean
    borderColor?: string
  }
  border?: {
    display?: boolean
    color?: string
  }
  ticks?: {
    color: string
    maxRotation?: number
    autoSkip?: boolean
    callback?: (value: string | number) => string
  }
  beginAtZero?: boolean
  stacked?: boolean
  suggestedMax?: number
  max?: number
}

interface LegendConfig {
  display: boolean
  position?: 'top' | 'bottom' | 'left' | 'right'
  labels?: {
    color: string
    padding?: number
    font?: {
      size?: number
    }
  }
}

/**
 * Creates standardized x-axis configuration
 */
export function createXAxisConfig(isDark: boolean, options: { stacked?: boolean } = {}) {
  const gridColor = isDark ? '#323e4e' : '#cad5e2'
  const config: AxisConfig = {
    grid: {
      color: gridColor,
    },
    // Hide the axis border line (first vertical line) to match grid lines
    border: {
      display: false,
    },
    ticks: {
      color: isDark ? 'white' : 'black',
      maxRotation: 0,
      autoSkip: true,
    },
  }

  if (options.stacked !== undefined) {
    config.stacked = options.stacked
  }

  return config
}

/**
 * Creates standardized y-axis configuration
 */
export function createYAxisConfig(
  isDark: boolean,
  options: {
    stacked?: boolean
    suggestedMax?: number
    max?: number
    tickCallback?: (value: string | number) => string
  } = {},
) {
  const gridColor = isDark ? '#424e5f' : '#bfc9d6'
  const config: AxisConfig = {
    beginAtZero: true,
    grid: {
      color: gridColor,
    },
    // Hide the axis border line (bottom horizontal line) to match grid lines
    border: {
      display: false,
    },
    ticks: {
      color: isDark ? 'white' : 'black',
    },
  }

  if (options.stacked !== undefined) {
    config.stacked = options.stacked
  }

  if (options.suggestedMax !== undefined) {
    config.suggestedMax = options.suggestedMax
  }

  if (options.max !== undefined) {
    config.max = options.max
  }

  if (options.tickCallback) {
    config.ticks!.callback = options.tickCallback
  }

  return config
}

/**
 * Creates chart scales configuration (x and y axes)
 */
export function createChartScales(
  isDark: boolean,
  options: {
    xStacked?: boolean
    yStacked?: boolean
    suggestedMax?: number
    max?: number
    yTickCallback?: (value: string | number) => string
  } = {},
) {
  return {
    x: createXAxisConfig(isDark, { stacked: options.xStacked }),
    y: createYAxisConfig(isDark, {
      stacked: options.yStacked,
      suggestedMax: options.suggestedMax,
      max: options.max,
      tickCallback: options.yTickCallback,
    }),
  }
}

/**
 * Creates stacked chart scales with conditional stacking
 */
export function createStackedChartScales(isDark: boolean, stacked: boolean) {
  return createChartScales(isDark, {
    xStacked: stacked,
    yStacked: stacked,
  })
}

/**
 * Creates standardized legend configuration
 */
export function createLegendConfig(
  isDark: boolean,
  display: boolean,
  options: {
    position?: 'top' | 'bottom' | 'left' | 'right'
    fontSize?: number
    padding?: number
  } = {},
): LegendConfig {
  return {
    display,
    position: options.position ?? 'bottom',
    labels: {
      color: isDark ? 'white' : 'black',
      padding: options.padding ?? 10,
      font: {
        size: options.fontSize ?? 11,
      },
    },
  }
}