continue ordertest

This commit is contained in:
faiztyanirh 2026-04-26 13:24:28 +07:00
parent d4becb0a12
commit 3f81d45a55
2 changed files with 71 additions and 141 deletions

View File

@ -148,7 +148,7 @@ export const orderTestFormFields = [
type: "tests2", type: "tests2",
optionsEndpoint: `${API.BASE_URL}${API.TEST}`, optionsEndpoint: `${API.BASE_URL}${API.TEST}`,
otherEndpoint: `${API.BASE_URL}${API.DISCIPLINE}`, otherEndpoint: `${API.BASE_URL}${API.DISCIPLINE}`,
valueKey: 'TestSiteCode', valueKey: 'TestSiteID',
labelKey: (item) => `${item.TestSiteCode} - ${item.TestSiteName}`, labelKey: (item) => `${item.TestSiteCode} - ${item.TestSiteName}`,
validateOn: ['input'] validateOn: ['input']
}, },

View File

@ -46,7 +46,28 @@
); );
let discipline = $state([]); let discipline = $state([]);
let selectedDiscipline = $state(null); let selectedDiscipline = $state(null);
$inspect(discipline) let searchText = $state('');
let searchedTests = $derived.by(() => {
if (!searchText.trim()) return filteredTests;
const query = searchText.toLowerCase().trim();
const result = {};
for (const [disciplineId, { disciplineName, tests }] of Object.entries(filteredTests)) {
const matched = tests.filter(test =>
test.rawItem.TestSiteName.toLowerCase().includes(query) ||
test.rawItem.TestSiteCode.toLowerCase().includes(query)
);
if (matched.length > 0) {
result[disciplineId] = { disciplineName, tests: matched };
}
}
return result;
});
function getFilteredOptions(key) { function getFilteredOptions(key) {
const query = searchQuery[key] || ''; const query = searchQuery[key] || '';
if (!query) return formState.selectOptions?.[key] ?? []; if (!query) return formState.selectOptions?.[key] ?? [];
@ -127,11 +148,34 @@
if (col.type === 'tests2' && col.otherEndpoint) { if (col.type === 'tests2' && col.otherEndpoint) {
fetchDiscipline(col.otherEndpoint); fetchDiscipline(col.otherEndpoint);
} }
if (col.type === "tests2" && col.optionsEndpoint) {
formState.fetchOptions(col, formState.form);
}
} }
} }
} }
}); });
}); });
let testsByDiscipline = $derived.by(() => {
return (formState.selectOptions?.Tests ?? []).reduce((acc, test) => {
const id = test.rawItem.DisciplineID;
if (!acc[id]) {
acc[id] = { disciplineName: test.rawItem.DisciplineName, tests: [] };
}
acc[id].tests.push(test);
return acc;
}, {});
});
let filteredTests = $derived.by(() => {
if (!selectedDiscipline) return testsByDiscipline;
return Object.fromEntries(
Object.entries(testsByDiscipline).filter(([disciplineId]) => disciplineId === selectedDiscipline)
);
});
$inspect(searchedTests)
</script> </script>
{#snippet Fieldset({ {#snippet Fieldset({
@ -355,19 +399,7 @@
</Table.Body> </Table.Body>
</Table.Root> </Table.Root>
{:else if type === "tests2"} {:else if type === "tests2"}
{@const allTests = formState.selectOptions?.[key] ?? []}
{@const _ = console.log('allTests', allTests)}
{@const disciplineList = [
...new Map(
allTests
.filter(t => t.DisciplineID !== null)
.map(t => [t.DisciplineID, { id: t.DisciplineID, name: t.DisciplineName }])
).values()
]}
{@const filteredOptions = getFilteredOptions(key)} {@const filteredOptions = getFilteredOptions(key)}
{@const filteredTests = selectedDiscipline
? allTests.filter(t => t.DisciplineID === selectedDiscipline)
: allTests}
<div class="flex flex-1 h-full min-h-0 w-full gap-2"> <div class="flex flex-1 h-full min-h-0 w-full gap-2">
<div class="flex flex-1 flex-col gap-2 overflow-hidden min-h-0 h-full w-full"> <div class="flex flex-1 flex-col gap-2 overflow-hidden min-h-0 h-full w-full">
<div class="shrink-0 h-18 p-1 flex gap-2 border-b-2 flex flex-col"> <div class="shrink-0 h-18 p-1 flex gap-2 border-b-2 flex flex-col">
@ -376,17 +408,9 @@
<Select.Root <Select.Root
type="single" type="single"
onValueChange={(val) => selectedDiscipline = val || null} onValueChange={(val) => selectedDiscipline = val || null}
onOpenChange={(open) => {
if (open && otherEndpoint) {
formState.fetchOptions?.(
{ key, otherEndpoint, valueKey, labelKey },
formState.form
);
}
}}
> >
<Select.Trigger class="w-full truncate"> <Select.Trigger class="w-full truncate">
{disciplineList.find(d => d.id === selectedDiscipline)?.name || 'All Disciplines'} {discipline.find(d => d.id === selectedDiscipline)?.name || 'All Disciplines'}
</Select.Trigger> </Select.Trigger>
<Select.Content> <Select.Content>
<Select.Item value="">- All -</Select.Item> <Select.Item value="">- All -</Select.Item>
@ -397,130 +421,36 @@
</Select.Root> </Select.Root>
<Input <Input
type="text" type="text"
placeholder="Search test..."
bind:value={searchText}
/> />
</div> </div>
</div> </div>
<div class="flex-1 min-h-0 overflow-y-auto [scrollbar-width:thin] [&::-webkit-scrollbar]:w-1" > <div class="flex-1 min-h-0 overflow-y-auto [scrollbar-width:thin] [&::-webkit-scrollbar]:w-1" >
<Collapsible.Root> {#each Object.entries(searchedTests) as [disciplineId, { disciplineName, tests }]}
<Collapsible.Trigger <Collapsible.Root>
class="flex w-full items-center justify-between px-3 py-2 rounded-md bg-muted/50 hover:bg-muted transition-colors text-left" <Collapsible.Trigger
> class="flex w-full items-center justify-between px-3 py-2 rounded-md bg-muted/50 hover:bg-muted transition-colors text-left"
<div class="flex items-center gap-2"> >
<ChevronDownIcon /> <div class="flex items-center gap-2">
<span class="text-sm font-medium">Hematologi</span> <ChevronDownIcon />
<span class="text-xs text-muted-foreground">5 tests</span> <span class="text-sm font-medium">{disciplineName}</span>
</div> <span class="text-xs text-muted-foreground">{tests.length} tests</span>
</Collapsible.Trigger>
<Collapsible.Content>
<div class="py-1 px-1">
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">HB</span>
<Label class="text-sm cursor-pointer">Hemoglobin</Label>
</div> </div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors"> </Collapsible.Trigger>
<Checkbox /> <Collapsible.Content>
<span class="text-xs font-semibold text-primary w-14 shrink-0">HCT</span> <div class="py-1 px-1">
<Label class="text-sm cursor-pointer">Hematokrit</Label> {#each tests as test}
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">{test.rawItem.TestSiteCode}</span>
<Label class="text-sm cursor-pointer">{test.rawItem.TestSiteName}</Label>
</div>
{/each}
</div> </div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors"> </Collapsible.Content>
<Checkbox /> </Collapsible.Root>
<span class="text-xs font-semibold text-primary w-14 shrink-0">HCT</span> {/each}
<Label class="text-sm cursor-pointer">Hematocrit</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">HCT</span>
<Label class="text-sm cursor-pointer">Hematocret</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">HCT</span>
<Label class="text-sm cursor-pointer">Hematocrut</Label>
</div>
</div>
</Collapsible.Content>
</Collapsible.Root>
<Collapsible.Root>
<Collapsible.Trigger
class="flex w-full items-center justify-between px-3 py-2 rounded-md bg-muted/50 hover:bg-muted transition-colors text-left"
>
<div class="flex items-center gap-2">
<ChevronDownIcon />
<span class="text-sm font-medium">Kimia Klenik</span>
<span class="text-xs text-muted-foreground">17 tests</span>
</div>
</Collapsible.Trigger>
<Collapsible.Content>
<div class="py-1 px-1">
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">CREA</span>
<Label class="text-sm cursor-pointer">Creatinine</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">GLU</span>
<Label class="text-sm cursor-pointer">Glukosa</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">GLUP</span>
<Label class="text-sm cursor-pointer">Glukosa Puasa</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">GPU</span>
<Label class="text-sm cursor-pointer">Yahud</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">ASOE</span>
<Label class="text-sm cursor-pointer">Israhell</Label>
</div>
</div>
</Collapsible.Content>
</Collapsible.Root>
<Collapsible.Root>
<Collapsible.Trigger
class="flex w-full items-center justify-between px-3 py-2 rounded-md bg-muted/50 hover:bg-muted transition-colors text-left"
>
<div class="flex items-center gap-2">
<ChevronDownIcon />
<span class="text-sm font-medium">Immunologi</span>
<span class="text-xs text-muted-foreground">10 tests</span>
</div>
</Collapsible.Trigger>
<Collapsible.Content>
<div class="py-1 px-1">
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">HIV</span>
<Label class="text-sm cursor-pointer">HIV</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">TESTO</span>
<Label class="text-sm cursor-pointer">Testosteron</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">ESTR</span>
<Label class="text-sm cursor-pointer">Estrogen</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">GPU</span>
<Label class="text-sm cursor-pointer">Yahud</Label>
</div>
<div class="flex items-center gap-3 px-3 py-2 rounded-md transition-colors">
<Checkbox />
<span class="text-xs font-semibold text-primary w-14 shrink-0">ASOE</span>
<Label class="text-sm cursor-pointer">Israhell</Label>
</div>
</div>
</Collapsible.Content>
</Collapsible.Root>
</div> </div>
<div class="shrink-0 p-2 border-t border-b flex items-center justify-between"> <div class="shrink-0 p-2 border-t border-b flex items-center justify-between">
<span class="text-sm">0 selected</span> <span class="text-sm">0 selected</span>