mirror of
https://github.com/rgrgogu/new_starr.git
synced 2026-09-27 00:12:54 +08:00
@@ -15,14 +15,22 @@ const FIELD_DISPLAY_MAP = {
|
||||
const BOOLEAN_FIELDS = Object.keys(FIELD_DISPLAY_MAP);
|
||||
|
||||
// ─── Generic formatter ────────────────────────────────────────────────────────
|
||||
// Audit fields (createdBy/updatedBy/deletedBy) come back from the field-values
|
||||
// API as { value: user_id, label: full_name } — filtering has to select on the
|
||||
// id, but the sheet should still display the name. Every other field type
|
||||
// still hands this plain primitives, which pass through unchanged.
|
||||
const itemValue = (item) => (item && typeof item === "object" && "value" in item) ? item.value : item;
|
||||
const itemLabel = (item) => (item && typeof item === "object" && "label" in item) ? item.label : item;
|
||||
|
||||
const formatFilterItem = (item, field, type, fmtDate) => {
|
||||
const label = itemLabel(item);
|
||||
if (FIELD_DISPLAY_MAP[field]) {
|
||||
return FIELD_DISPLAY_MAP[field][String(item)] ?? item;
|
||||
return FIELD_DISPLAY_MAP[field][String(label)] ?? label;
|
||||
}
|
||||
if (type === "date" && item) {
|
||||
return fmtDate(item);
|
||||
if (type === "date" && label) {
|
||||
return fmtDate(label);
|
||||
}
|
||||
return item;
|
||||
return label;
|
||||
};
|
||||
|
||||
// ─── Reusable empty state ─────────────────────────────────────────────────────
|
||||
@@ -37,17 +45,20 @@ const FilterList = ({ items, field, type, selected, onToggle, inputType = "check
|
||||
const { fmtDate } = useDateFormat();
|
||||
if (items.length === 0) return <EmptyState />;
|
||||
|
||||
return items.map((item) => (
|
||||
<label key={item} className="flex items-center gap-2 text-sm cursor-pointer">
|
||||
<input
|
||||
type={inputType}
|
||||
name={inputType === "radio" ? field : undefined}
|
||||
checked={selected.includes(String(item))}
|
||||
onChange={() => onToggle(item)}
|
||||
/>
|
||||
{formatFilterItem(item, field, type, fmtDate)}
|
||||
</label>
|
||||
));
|
||||
return items.map((item) => {
|
||||
const value = itemValue(item);
|
||||
return (
|
||||
<label key={value} className="flex items-center gap-2 text-sm cursor-pointer">
|
||||
<input
|
||||
type={inputType}
|
||||
name={inputType === "radio" ? field : undefined}
|
||||
checked={selected.includes(String(value))}
|
||||
onChange={() => onToggle(value)}
|
||||
/>
|
||||
{formatFilterItem(item, field, type, fmtDate)}
|
||||
</label>
|
||||
);
|
||||
});
|
||||
};
|
||||
|
||||
export function FilterSheet({ open, onOpenChange, column, attr, data = [], loading }) {
|
||||
|
||||
Reference in New Issue
Block a user