# All files / autocomplete AutoComplete.tsx

0% Statements 0/66
0% Branches 0/1
0% Functions 0/1
0% Lines 0/66

Press n or j to go to the next uncovered block, b, p or k for the previous block.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67

     "use client";
    import { useMemo, type ReactElement } from "react";
    import { Option } from "../form/Option.js";
    import { TextField } from "../form/TextField.js";
    import { ListboxProvider } from "../form/useListboxProvider.js";
    import { Menu } from "../menu/Menu.js";
    import { KeyboardMovementProvider } from "../movement/useKeyboardMovementProvider.js";
    import { type AutoCompleteImplementation } from "./useAutoComplete.js";

    export interface AutoCompleteProps<Value extends string = string>
      extends Pick<
        AutoCompleteImplementation<Value, HTMLDivElement>,
        | "movementContext"
        | "comboboxRef"
        | "comboboxProps"
        | "getMenuProps"
        | "suggestions"
      > {
      //
    }

    export function AutoComplete<Value extends string = string>(
      props: AutoCompleteProps<Value>
    ): ReactElement {
      const {
        movementContext,
        comboboxRef,
        comboboxProps,
        getMenuProps,
        suggestions,
      } = props;
      const listboxContext = useMemo(
        () => ({
          inputRef: comboboxRef,
          currentValue: null,
          selectedIconAfter: false,
          disableSelectedIcon: true,
        }),
        [comboboxRef]
      );
      return (
        <KeyboardMovementProvider value={movementContext}>
          <TextField label="Dessert" {...comboboxProps} />
          <Menu {...getMenuProps()} aria-label="Options" width="equal">
            <ListboxProvider value={listboxContext}>
              {suggestions.map((suggestion) => {
                let value: string;
                let label: string;
                if (typeof suggestion === "string") {
                  label = suggestion;
                  value = suggestion;
                } else {
                  ({ label, value } = suggestion);
                }

                return (
                  <Option key={value} value={label}>
                    {label}
                  </Option>
                );
              })}
            </ListboxProvider>
          </Menu>
        </KeyboardMovementProvider>
      );
    }