Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improving extensibility #3

Closed
timc1 opened this issue Sep 7, 2021 · 0 comments · Fixed by #4
Closed

Improving extensibility #3

timc1 opened this issue Sep 7, 2021 · 0 comments · Fixed by #4

Comments

@timc1
Copy link
Owner

timc1 commented Sep 7, 2021

KBar currently takes a static data structure and handles all of the parsing internally. The current component structure is as follows:

KBar
  KeyboardShortcuts
  KBarAnimator
    KBarSearch
  • KBar handles the primary cmd+k/esc listeners, and coordinates when to show, animate, and hide the content
  • KeyboardShortcuts attaches keydown listeners and matches the keystroke patterns with our actions object
  • KBarAnimator leverages ResizeObserver and the Web Animations API to coordinate the smooth transitions when the content updates
  • KBarSearch handles the search and rendering of results

Problem

Since all state management and rendering logic is within KBar itself, it is currently impossible for users to customize their command menu to fit their brand.

Although we can theoretically expose props which enable users to pass certain configurations, this would lead us to quite a restrictive API.

Let's take a look at an approach:

Solution

Provide a way to hook into the internal state; e.g. visualState, currentActionId, actions, and
a method to trigger internal state updates.

The component heirarchy would look something like this:

// app.tsx
<KBarProvider actions={actions}>
  <Breadcrumbs /> // custom user component
  <KBarAnimator>
    <KBarSearch />
    <KBarResults 
      // 
      onRender={(result) => (
        <div>
          // ...
        </div>
      )}
    />
  </KBarAnimator>
</KBarProvider>
// <MyApp />

User defined components within the KBarProvider can hook into the internal state through a useKBar hook.

// breadcrumbs.tsx
function Breadcrumbs() {
  const { actions, breadcrumbs } = useKBar((state) => ({
    breadcrumbs: getBreadcrumbs(state)
  }));

  return (
    <ul>
      {breadcrumbs.map(breadcrumb => (
        <li key={breadcrumb.id}>
          <Button onClick={() => actions.setCurrentRootActionId(breadcrumb.id)}>{breadcrumb.name}</Button>
        </li>
      ))}
    </ul>
  )
}
@timc1 timc1 changed the title Cleanup 🧹 Improving extensibility Sep 8, 2021
@timc1 timc1 linked a pull request Sep 10, 2021 that will close this issue
@timc1 timc1 closed this as completed Sep 10, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant