interface MeasureTextWidthParams {
    text: string;
    fontSize: number;
    fontFamily: string;
    fontWeight: string;
    fontStyle: string;
    letterSpacing: string;
}

interface CalculateOptimalFontSizeParams {
    element: HTMLElement;
    text: string;
    defaultSize: number;
    availableWidth: number;
    minSize?: number;
}

/**
 * 测量文本的实际渲染宽度
 * @param params 测量参数
 * @returns 文本宽度（像素）
 */
export function measureTextWidth({
    text,
    fontSize,
    fontFamily,
    fontWeight,
    fontStyle,
    letterSpacing,
}: MeasureTextWidthParams): number {
    if (!text || text.trim() === '') {
        return 0;
    }

    const tempEl = document.createElement('span');
    tempEl.style.visibility = 'hidden';
    tempEl.style.position = 'absolute';
    tempEl.style.top = '-9999px';
    tempEl.style.left = '-9999px';
    tempEl.style.whiteSpace = 'nowrap';
    tempEl.style.fontSize = `${fontSize}px`;
    tempEl.style.fontFamily = fontFamily;
    tempEl.style.fontWeight = fontWeight;
    tempEl.style.fontStyle = fontStyle;
    tempEl.style.letterSpacing = letterSpacing;
    tempEl.textContent = text;
    document.body.appendChild(tempEl);

    const textWidth = tempEl.offsetWidth;
    document.body.removeChild(tempEl);

    return textWidth;
}

/**
 * 计算文本的最优字体大小，使其适配指定宽度
 * @param params 计算参数
 * @returns 最优字体大小（像素）
 */
export function calculateOptimalFontSize({
    element,
    text,
    defaultSize,
    availableWidth,
    minSize = 12,
}: CalculateOptimalFontSizeParams): number {
    if (!text || text.trim() === '' || availableWidth <= 0) {
        return defaultSize;
    }

    const style = window.getComputedStyle(element);
    const textWidth = measureTextWidth({
        text,
        fontSize: defaultSize,
        fontFamily: style.fontFamily,
        fontWeight: style.fontWeight,
        fontStyle: style.fontStyle,
        letterSpacing: style.letterSpacing,
    });

    if (textWidth + 5 <= availableWidth) {
        return defaultSize;
    }

    const ratio = availableWidth / textWidth;
    const newSize = Math.max(minSize, Math.floor(defaultSize * ratio * 0.95));

    return newSize;
}
