|
@@ -176,7 +176,7 @@ import { FileUploadModal } from '../components/FileUploadModal';
|
|
|
import { PrintModal } from '../components/PrintModal';
|
|
import { PrintModal } from '../components/PrintModal';
|
|
|
import { PrinterInfoModal } from '../components/PrinterInfoModal';
|
|
import { PrinterInfoModal } from '../components/PrinterInfoModal';
|
|
|
import { FeedDirectionModal } from '../components/FeedDirectionModal';
|
|
import { FeedDirectionModal } from '../components/FeedDirectionModal';
|
|
|
-import { getAmsLabel, getGlobalTrayId, getFillBarColor, getSpoolmanFillLevel, getFallbackSpoolTag, installedNozzleDiameters, isBambuLabSpool, resolveSlotNozzleDiameter, resolveSlotExtruder, formatSlotLabel, FTS_INLET_SIDE } from '../utils/amsHelpers';
|
|
|
|
|
|
|
+import { getAmsLabel, getGlobalTrayId, getFillBarColor, getSpoolmanFillLevel, getFallbackSpoolTag, installedNozzleDiameters, isBambuLabSpool, resolveSlotNozzleDiameter, resolveSlotExtruder, formatSlotLabel, slotPresetDescribesTray, FTS_INLET_SIDE } from '../utils/amsHelpers';
|
|
|
import { MAX_CHAMBER_TEMP_C, getPrinterImage, getWifiStrength, filterCompatibleQueueItems, isPrinterCurrentlyDispatchable } from '../utils/printer';
|
|
import { MAX_CHAMBER_TEMP_C, getPrinterImage, getWifiStrength, filterCompatibleQueueItems, isPrinterCurrentlyDispatchable } from '../utils/printer';
|
|
|
import { FilamentSlotCircle } from '../components/FilamentSlotCircle';
|
|
import { FilamentSlotCircle } from '../components/FilamentSlotCircle';
|
|
|
import { Collapsible } from '../components/Collapsible';
|
|
import { Collapsible } from '../components/Collapsible';
|
|
@@ -5467,6 +5467,12 @@ function PrinterCard({
|
|
|
const cloudInfo = tray?.tray_info_idx ? filamentInfo?.[tray.tray_info_idx] : null;
|
|
const cloudInfo = tray?.tray_info_idx ? filamentInfo?.[tray.tray_info_idx] : null;
|
|
|
// Get saved slot preset mapping (for user-configured slots)
|
|
// Get saved slot preset mapping (for user-configured slots)
|
|
|
const slotPreset = slotPresets?.[globalTrayId];
|
|
const slotPreset = slotPresets?.[globalTrayId];
|
|
|
|
|
+ // Only trusted while it still describes what the printer reports in the
|
|
|
|
|
+ // slot: the row survives a spool swap, and the display chain below puts
|
|
|
|
|
+ // it ahead of the live filament id (see slotPresetDescribesTray).
|
|
|
|
|
+ const slotPresetName = slotPresetDescribesTray(slotPreset?.preset_id, tray?.tray_info_idx)
|
|
|
|
|
+ ? slotPreset?.preset_name
|
|
|
|
|
+ : undefined;
|
|
|
|
|
|
|
|
// Fill level fallback chain: Spoolman → Inventory → AMS remain
|
|
// Fill level fallback chain: Spoolman → Inventory → AMS remain
|
|
|
const trayTag = (tray?.tray_uuid || tray?.tag_uid || getFallbackSpoolTag(printer.serial_number, ams.id, slotIdx))?.toUpperCase();
|
|
const trayTag = (tray?.tray_uuid || tray?.tag_uid || getFallbackSpoolTag(printer.serial_number, ams.id, slotIdx))?.toUpperCase();
|
|
@@ -5512,7 +5518,7 @@ function PrinterCard({
|
|
|
// the hover card shows "Devil Design PLA Basic" rather than the
|
|
// the hover card shows "Devil Design PLA Basic" rather than the
|
|
|
// vendor-less form. Strip the "@<printer>..." suffix that
|
|
// vendor-less form. Strip the "@<printer>..." suffix that
|
|
|
// BambuStudio appends to user-preset names.
|
|
// BambuStudio appends to user-preset names.
|
|
|
- profile: slotPreset?.preset_name || (slotSpoolForFill ? [slotSpoolForFill.brand, slotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || slotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || inventoryAssignment?.spool?.slicer_filament_name || cloudInfo?.name || tray.tray_sub_brands || tray.tray_type,
|
|
|
|
|
|
|
+ profile: slotPresetName || (slotSpoolForFill ? [slotSpoolForFill.brand, slotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || slotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || inventoryAssignment?.spool?.slicer_filament_name || cloudInfo?.name || tray.tray_sub_brands || tray.tray_type,
|
|
|
colorName: getColorName(tray.tray_color || '', tray.tray_sub_brands),
|
|
colorName: getColorName(tray.tray_color || '', tray.tray_sub_brands),
|
|
|
colorHex: tray.tray_color || null,
|
|
colorHex: tray.tray_color || null,
|
|
|
kFactor: formatKValue(tray.k),
|
|
kFactor: formatKValue(tray.k),
|
|
@@ -5777,6 +5783,12 @@ function PrinterCard({
|
|
|
const cloudInfo = tray?.tray_info_idx ? filamentInfo?.[tray.tray_info_idx] : null;
|
|
const cloudInfo = tray?.tray_info_idx ? filamentInfo?.[tray.tray_info_idx] : null;
|
|
|
// Get saved slot preset mapping (for user-configured slots)
|
|
// Get saved slot preset mapping (for user-configured slots)
|
|
|
const slotPreset = slotPresets?.[globalTrayId];
|
|
const slotPreset = slotPresets?.[globalTrayId];
|
|
|
|
|
+ // Only trusted while it still describes what the printer reports in the
|
|
|
|
|
+ // slot: the row survives a spool swap, and the display chain below puts
|
|
|
|
|
+ // it ahead of the live filament id (see slotPresetDescribesTray).
|
|
|
|
|
+ const slotPresetName = slotPresetDescribesTray(slotPreset?.preset_id, tray?.tray_info_idx)
|
|
|
|
|
+ ? slotPreset?.preset_name
|
|
|
|
|
+ : undefined;
|
|
|
const htSlotId = tray?.id ?? 0;
|
|
const htSlotId = tray?.id ?? 0;
|
|
|
|
|
|
|
|
// Fill level fallback chain: Spoolman → Inventory → AMS remain
|
|
// Fill level fallback chain: Spoolman → Inventory → AMS remain
|
|
@@ -5813,7 +5825,7 @@ function PrinterCard({
|
|
|
// Build filament data for hover card
|
|
// Build filament data for hover card
|
|
|
const filamentData = tray?.tray_type ? {
|
|
const filamentData = tray?.tray_type ? {
|
|
|
vendor: (isBambuLabSpool(tray) ? 'Bambu Lab' : 'Generic') as 'Bambu Lab' | 'Generic',
|
|
vendor: (isBambuLabSpool(tray) ? 'Bambu Lab' : 'Generic') as 'Bambu Lab' | 'Generic',
|
|
|
- profile: slotPreset?.preset_name || (htSlotSpoolForFill ? [htSlotSpoolForFill.brand, htSlotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || htSlotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || htInventoryAssignment?.spool?.slicer_filament_name || cloudInfo?.name || tray.tray_sub_brands || tray.tray_type,
|
|
|
|
|
|
|
+ profile: slotPresetName || (htSlotSpoolForFill ? [htSlotSpoolForFill.brand, htSlotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || htSlotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || htInventoryAssignment?.spool?.slicer_filament_name || cloudInfo?.name || tray.tray_sub_brands || tray.tray_type,
|
|
|
colorName: getColorName(tray.tray_color || '', tray.tray_sub_brands),
|
|
colorName: getColorName(tray.tray_color || '', tray.tray_sub_brands),
|
|
|
colorHex: tray.tray_color || null,
|
|
colorHex: tray.tray_color || null,
|
|
|
kFactor: formatKValue(tray.k),
|
|
kFactor: formatKValue(tray.k),
|
|
@@ -6211,6 +6223,12 @@ function PrinterCard({
|
|
|
: '';
|
|
: '';
|
|
|
const extCloudInfo = extTray.tray_info_idx ? filamentInfo?.[extTray.tray_info_idx] : null;
|
|
const extCloudInfo = extTray.tray_info_idx ? filamentInfo?.[extTray.tray_info_idx] : null;
|
|
|
const extSlotPreset = slotPresets?.[255 * 4 + slotTrayId];
|
|
const extSlotPreset = slotPresets?.[255 * 4 + slotTrayId];
|
|
|
|
|
+ // Only trusted while it still describes what the printer reports in the
|
|
|
|
|
+ // slot: the row survives a spool swap, and the display chain below puts
|
|
|
|
|
+ // it ahead of the live filament id (see slotPresetDescribesTray).
|
|
|
|
|
+ const extSlotPresetName = slotPresetDescribesTray(extSlotPreset?.preset_id, extTray.tray_info_idx)
|
|
|
|
|
+ ? extSlotPreset?.preset_name
|
|
|
|
|
+ : undefined;
|
|
|
|
|
|
|
|
const extTrayTag = (extTray.tray_uuid || extTray.tag_uid || getFallbackSpoolTag(printer.serial_number, 255, slotTrayId))?.toUpperCase();
|
|
const extTrayTag = (extTray.tray_uuid || extTray.tag_uid || getFallbackSpoolTag(printer.serial_number, 255, slotTrayId))?.toUpperCase();
|
|
|
const extLinkedSpool = extTrayTag ? linkedSpools?.[extTrayTag] : undefined;
|
|
const extLinkedSpool = extTrayTag ? linkedSpools?.[extTrayTag] : undefined;
|
|
@@ -6245,7 +6263,7 @@ function PrinterCard({
|
|
|
|
|
|
|
|
const extFilamentData = {
|
|
const extFilamentData = {
|
|
|
vendor: (isBambuLabSpool(extTray) ? 'Bambu Lab' : 'Generic') as 'Bambu Lab' | 'Generic',
|
|
vendor: (isBambuLabSpool(extTray) ? 'Bambu Lab' : 'Generic') as 'Bambu Lab' | 'Generic',
|
|
|
- profile: extSlotPreset?.preset_name || (extSlotSpoolForFill ? [extSlotSpoolForFill.brand, extSlotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || extSlotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || extInventoryAssignment?.spool?.slicer_filament_name || extCloudInfo?.name || extTray.tray_sub_brands || extTray.tray_type || 'Unknown',
|
|
|
|
|
|
|
+ profile: extSlotPresetName || (extSlotSpoolForFill ? [extSlotSpoolForFill.brand, extSlotSpoolForFill.slicer_filament_name?.split('@')[0].trim() || extSlotSpoolForFill.material].filter(Boolean).join(' ').trim() : null) || extInventoryAssignment?.spool?.slicer_filament_name || extCloudInfo?.name || extTray.tray_sub_brands || extTray.tray_type || 'Unknown',
|
|
|
colorName: getColorName(extTray.tray_color || '', extTray.tray_sub_brands),
|
|
colorName: getColorName(extTray.tray_color || '', extTray.tray_sub_brands),
|
|
|
colorHex: extTray.tray_color || null,
|
|
colorHex: extTray.tray_color || null,
|
|
|
kFactor: formatKValue(extTray.k),
|
|
kFactor: formatKValue(extTray.k),
|