wip
This commit is contained in:
@@ -70,6 +70,18 @@ function parseVoltageSortKey(voltageLabel: string): number {
|
||||
function compactNumericForLocale(value: string, locale: 'en' | 'de'): string {
|
||||
const v = normalizeValue(value);
|
||||
if (!v) return '';
|
||||
|
||||
// Compact common bending-radius style: "15xD (Single core); 12xD (Multi core)" -> "15/12xD".
|
||||
// Keep semantics, reduce width. Never truncate with ellipses.
|
||||
if (/\d+xD/i.test(v)) {
|
||||
const nums = Array.from(v.matchAll(/(\d+)xD/gi)).map(m => m[1]).filter(Boolean);
|
||||
const unique: string[] = [];
|
||||
for (const n of nums) {
|
||||
if (!unique.includes(n)) unique.push(n);
|
||||
}
|
||||
if (unique.length) return `${unique.join('/') }xD`;
|
||||
}
|
||||
|
||||
const hasDigit = /\d/.test(v);
|
||||
if (!hasDigit) return v;
|
||||
const trimmed = v.replace(/\s+/g, ' ').trim();
|
||||
@@ -242,6 +254,12 @@ function denseAbbrevLabel(args: { key: string; locale: 'en' | 'de'; unit?: strin
|
||||
return args.locale === 'de' ? 'Leiter' : 'Cond.';
|
||||
case 'shape':
|
||||
return args.locale === 'de' ? 'Form' : 'Shape';
|
||||
// Electrical
|
||||
case 'cap':
|
||||
// Capacitance. Use a clear label; lowercase "cap" looks like an internal key.
|
||||
return `Cap${suffix}`;
|
||||
case 'X':
|
||||
return `X${suffix}`;
|
||||
case 'test_volt':
|
||||
return `U_test${suffix}`;
|
||||
case 'rated_volt':
|
||||
@@ -265,13 +283,14 @@ function denseAbbrevLabel(args: { key: string; locale: 'en' | 'de'; unit?: strin
|
||||
}
|
||||
}
|
||||
|
||||
function summarizeOptions(options: string[] | undefined, maxItems: number = 3): string {
|
||||
function summarizeOptions(options: string[] | undefined): string {
|
||||
const vals = (options || []).map(normalizeValue).filter(Boolean);
|
||||
if (vals.length === 0) return '';
|
||||
const uniq = Array.from(new Set(vals));
|
||||
if (uniq.length === 1) return uniq[0];
|
||||
if (uniq.length <= maxItems) return uniq.join(' / ');
|
||||
return `${uniq.slice(0, maxItems).join(' / ')} / ...`;
|
||||
// Never use ellipsis truncation in datasheets. Prefer full value list.
|
||||
// (Long values should be handled by layout; if needed we can later add wrapping rules.)
|
||||
return uniq.join(' / ');
|
||||
}
|
||||
|
||||
function parseNumericOption(value: string): number | null {
|
||||
@@ -294,10 +313,17 @@ function summarizeNumericRange(options: string[] | undefined): { ok: boolean; te
|
||||
return { ok: true, text: `${fmt(min)}–${fmt(max)}` };
|
||||
}
|
||||
|
||||
function summarizeSmartOptions(label: string, options: string[] | undefined): string {
|
||||
function summarizeSmartOptions(_label: string, options: string[] | undefined): string {
|
||||
const range = summarizeNumericRange(options);
|
||||
if (range.ok) return range.text;
|
||||
return summarizeOptions(options, 3);
|
||||
return summarizeOptions(options);
|
||||
}
|
||||
|
||||
function normalizeDesignation(value: string): string {
|
||||
return String(value || '')
|
||||
.toUpperCase()
|
||||
.replace(/-\d+$/g, '')
|
||||
.replace(/[^A-Z0-9]+/g, '');
|
||||
}
|
||||
|
||||
function buildExcelModel(args: { product: ProductData; locale: 'en' | 'de' }): BuildExcelModelResult {
|
||||
@@ -361,6 +387,14 @@ function buildExcelModel(args: { product: ProductData; locale: 'en' | 'de' }): B
|
||||
'cpr class': { header: 'CPR class', unit: '', key: 'cpr' },
|
||||
'flame retardant': { header: 'Flame retardant', unit: '', key: 'flame' },
|
||||
'self-extinguishing of single cable': { header: 'Flame retardant', unit: '', key: 'flame' },
|
||||
|
||||
// High-value electrical/screen columns
|
||||
'capacitance (approx.)': { header: 'Capacitance', unit: 'uF/km', key: 'cap' },
|
||||
'capacitance': { header: 'Capacitance', unit: 'uF/km', key: 'cap' },
|
||||
'reactance': { header: 'Reactance', unit: 'Ohm/km', key: 'X' },
|
||||
'diameter over screen': { header: 'Diameter over screen', unit: 'mm', key: 'D_screen' },
|
||||
'metallic screen mm2': { header: 'Metallic screen', unit: 'mm2', key: 'S_screen' },
|
||||
'metallic screen': { header: 'Metallic screen', unit: 'mm2', key: 'S_screen' },
|
||||
};
|
||||
|
||||
const excelKeys = Object.keys(sample).filter(k => k && k !== 'Part Number' && k !== 'Units');
|
||||
@@ -464,6 +498,10 @@ function buildExcelModel(args: { product: ProductData; locale: 'en' | 'de' }): B
|
||||
const denseTableKeyOrder = [
|
||||
'Cond',
|
||||
'shape',
|
||||
// Electrical properties (when present)
|
||||
'cap',
|
||||
'X',
|
||||
// Dimensions and ratings
|
||||
'DI',
|
||||
'RI',
|
||||
'Wi',
|
||||
@@ -473,6 +511,9 @@ function buildExcelModel(args: { product: ProductData; locale: 'en' | 'de' }): B
|
||||
'Wm',
|
||||
'Rbv',
|
||||
'Ø',
|
||||
// Screen data (when present)
|
||||
'D_screen',
|
||||
'S_screen',
|
||||
'Fzv',
|
||||
'G',
|
||||
] as const;
|
||||
@@ -510,16 +551,33 @@ function buildExcelModel(args: { product: ProductData; locale: 'en' | 'de' }): B
|
||||
if (!mappedByKey.has(c.mapping.key)) mappedByKey.set(c.mapping.key, c);
|
||||
}
|
||||
|
||||
// If conductor material is missing in Excel, derive it from designation.
|
||||
// NA... => Al, N... => Cu (common for this dataset).
|
||||
if (!mappedByKey.has('Cond')) {
|
||||
mappedByKey.set('Cond', {
|
||||
excelKey: '',
|
||||
mapping: { header: 'Cond.', unit: '', key: 'Cond' },
|
||||
});
|
||||
}
|
||||
|
||||
const orderedTableColumns = denseTableKeyOrder
|
||||
.filter(k => mappedByKey.has(k))
|
||||
.map(k => mappedByKey.get(k)!)
|
||||
.map(({ excelKey, mapping }) => {
|
||||
const unit = normalizeUnit(units[excelKey] || mapping.unit || '');
|
||||
const unit = normalizeUnit((excelKey ? units[excelKey] : '') || mapping.unit || '');
|
||||
return {
|
||||
key: mapping.key,
|
||||
label: denseAbbrevLabel({ key: mapping.key, locale: args.locale, unit }) || formatExcelHeaderLabel(excelKey, unit),
|
||||
get: (rowIndex: number) => {
|
||||
const srcRowIndex = indices[rowIndex];
|
||||
|
||||
if (mapping.key === 'Cond' && !excelKey) {
|
||||
const pn = normalizeDesignation(args.product.name || args.product.slug || args.product.sku || '');
|
||||
if (/^NA/.test(pn)) return 'Al';
|
||||
if (/^N/.test(pn)) return 'Cu';
|
||||
return '';
|
||||
}
|
||||
|
||||
const raw = excelKey ? normalizeValue(String(compatibleRows[srcRowIndex]?.[excelKey] ?? '')) : '';
|
||||
return compactCellForDenseTable(raw, unit, args.locale);
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user