mirror of
https://github.com/MODSetter/SurfSense.git
synced 2026-04-28 10:26:33 +02:00
refactor: improve InlineCombobox context handling and optimize search functionality
This commit is contained in:
parent
648b00da64
commit
0edfd116af
2 changed files with 24 additions and 11 deletions
|
|
@ -28,6 +28,18 @@ import { useComposedRef, useEditorRef } from 'platejs/react';
|
|||
|
||||
import { cn } from '@/lib/utils';
|
||||
|
||||
function useRequiredComboboxContext() {
|
||||
const context = useComboboxContext();
|
||||
|
||||
if (!context) {
|
||||
throw new Error(
|
||||
'InlineCombobox compound components must be rendered within InlineCombobox'
|
||||
);
|
||||
}
|
||||
|
||||
return context;
|
||||
}
|
||||
|
||||
type FilterFn = (
|
||||
item: { value: string; group?: string; keywords?: string[]; label?: string },
|
||||
search: string
|
||||
|
|
@ -56,7 +68,7 @@ const defaultFilter: FilterFn = (
|
|||
);
|
||||
|
||||
return Array.from(uniqueTerms).some((keyword) =>
|
||||
filterWords(keyword!, search)
|
||||
filterWords(keyword as string, search)
|
||||
);
|
||||
};
|
||||
|
||||
|
|
@ -91,7 +103,7 @@ const InlineCombobox = ({
|
|||
|
||||
// Check if current user is the creator of this element (for Yjs collaboration)
|
||||
const isCreator = React.useMemo(() => {
|
||||
const elementUserId = (element as any).userId;
|
||||
const elementUserId = (element as Record<string, unknown>).userId;
|
||||
const currentUserId = editor.meta.userId;
|
||||
|
||||
// If no userId (backwards compatibility or non-Yjs), allow
|
||||
|
|
@ -170,10 +182,8 @@ const InlineCombobox = ({
|
|||
trigger,
|
||||
showTrigger,
|
||||
filter,
|
||||
inputRef,
|
||||
inputProps,
|
||||
removeInput,
|
||||
setHasEmpty,
|
||||
]
|
||||
);
|
||||
|
||||
|
|
@ -189,6 +199,8 @@ const InlineCombobox = ({
|
|||
* item.
|
||||
*/
|
||||
React.useEffect(() => {
|
||||
if (items.length === 0) return;
|
||||
|
||||
if (!store.getState().activeId) {
|
||||
store.setActiveId(store.first());
|
||||
}
|
||||
|
|
@ -225,7 +237,7 @@ const InlineComboboxInput = ({
|
|||
trigger,
|
||||
} = React.useContext(InlineComboboxContext);
|
||||
|
||||
const store = useComboboxContext()!;
|
||||
const store = useRequiredComboboxContext();
|
||||
const value = store.useState('value');
|
||||
|
||||
const ref = useComposedRef(propRef, contextRef);
|
||||
|
|
@ -341,14 +353,15 @@ const InlineComboboxItem = ({
|
|||
|
||||
const { filter, removeInput } = React.useContext(InlineComboboxContext);
|
||||
|
||||
const store = useComboboxContext()!;
|
||||
const store = useRequiredComboboxContext();
|
||||
|
||||
// Optimization: Do not subscribe to value if filter is false
|
||||
const search = filter && store.useState('value');
|
||||
// Always call hook unconditionally; only use value if filter is active
|
||||
const storeValue = store.useState('value');
|
||||
const search = filter ? storeValue : '';
|
||||
|
||||
const visible = React.useMemo(
|
||||
() =>
|
||||
!filter || filter({ group, keywords, label, value }, search as string),
|
||||
!filter || filter({ group, keywords, label, value }, search),
|
||||
[filter, group, keywords, label, value, search]
|
||||
);
|
||||
|
||||
|
|
@ -371,7 +384,7 @@ const InlineComboboxEmpty = ({
|
|||
className,
|
||||
}: React.HTMLAttributes<HTMLDivElement>) => {
|
||||
const { setHasEmpty } = React.useContext(InlineComboboxContext);
|
||||
const store = useComboboxContext()!;
|
||||
const store = useRequiredComboboxContext();
|
||||
const items = store.useState('items');
|
||||
|
||||
React.useEffect(() => {
|
||||
|
|
|
|||
|
|
@ -186,7 +186,7 @@ export function SlashInputElement({
|
|||
>
|
||||
<InlineComboboxInput />
|
||||
|
||||
<InlineComboboxContent>
|
||||
<InlineComboboxContent className="dark:bg-neutral-800 dark:border dark:border-neutral-700">
|
||||
<InlineComboboxEmpty>No results found.</InlineComboboxEmpty>
|
||||
|
||||
{slashCommandGroups.map(({ heading, items }) => (
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue