ohmysearch
Version:
Ohmysearch - customizable all in one search tool to boost developer productivity
159 lines (153 loc) • 4.08 kB
text/typescript
import { OMSExtension } from "../../common/types/OMSExtension";
import React from "react";
import createStore, {
StateCreator,
UseBoundStore,
StoreApi,
SetState,
GetState,
} from "zustand";
import createContext from "zustand/context";
import { sendIpcMessage } from "../utils/ipcEvent";
export const DefaultExtensions: OMSExtension[] = [
{
id: "new-notion-page",
title: "New Notion page",
subTitle: "Notion",
type: "url",
url: "https://notion.new",
iconPath: "./images/logo-notion.png",
},
{
id: "new-google-sheet",
title: "New Sheets spreadsheet",
subTitle: "Google Sheet",
type: "url",
url: "https://sheets.new",
iconPath: "./images/logo-google-sheets.png",
},
{
id: "new-google-docs",
title: "new docs document",
subTitle: "Google Docs",
type: "url",
url: "https://docs.new",
iconPath: "./images/logo-google-docs.png",
},
{
id: "new-google-slide",
title: "New Google Slide",
subTitle: "Google Slide",
type: "url",
url: "https://slides.new",
iconPath: "./images/logo-google-slides.png",
},
{
id: "mute-volume",
title: "Mute System Audio",
subTitle: "System Preferences",
type: "background-action",
iconPath: "./images/icon-mute.svg",
backgroundAction: () => {
sendIpcMessage("mute-volume");
},
},
{
id: "unmute-volume",
title: "Unmute System Audio",
subTitle: "System Preferences",
type: "background-action",
iconPath: "./images/icon-volume-up.svg",
backgroundAction: () => {
sendIpcMessage("unmute-volume");
},
},
];
type TestState = {
version: string;
updateVersion: () => void;
selectedId?: string;
setSelected: (selectedId?: string) => void;
routes: string[];
currentRoute: () => string | undefined;
pushRoute: (routeId: string) => void;
popRoute: (from?: string) => void;
clearRoute: () => void;
defaultSuggestions: OMSExtension[];
omsInputValue: string;
updateOmsInputValue: (newValue: string) => void;
suggestionPreview: React.ReactNode;
setSuggestionPreview: (suggestionPreview: React.ReactNode) => void;
showOmsInputBar: boolean;
setShowOmsInputBar: (show: boolean) => void;
};
export type GlobalState = TestState;
const createTestSlice = (
set: SetState<GlobalState>,
get: GetState<GlobalState>
) => ({
version: "0.0.0",
selectedId: undefined,
setSelected: (selectedId?: string) => {
set({ selectedId });
},
updateVersion: () => {
set({
version: get().version + "2",
});
},
defaultSuggestions: DefaultExtensions,
routes: [],
currentRoute: () => get().routes.slice(-1).pop(),
pushRoute: (routeId: string) => {
set({
routes: [...get().routes, routeId],
});
},
clearRoute: () => {
set({ routes: [], suggestionPreview: null });
},
popRoute: (from?: string) => {
const { routes } = get();
const index = routes.findIndex((r) => r === from);
if (index !== -1) {
routes.splice(index + 1, routes.length - (index + 1));
} else {
routes.pop();
}
set({
routes: [...routes],
suggestionPreview: null,
});
},
omsInputValue: "",
updateOmsInputValue: (omsInputValue: string) => {
set({
omsInputValue,
});
},
suggestionPreview: null,
setSuggestionPreview: (suggestionPreview: React.ReactNode) => {
set({ suggestionPreview });
},
showOmsInputBar: true,
setShowOmsInputBar: (showOmsInputBar: boolean) => {
set({
showOmsInputBar,
});
},
});
const zustandContext = createContext<GlobalState>();
export const ZustandProvider = zustandContext.Provider;
export const useStore = zustandContext.useStore;
let store: UseBoundStore<GlobalState, StoreApi<GlobalState>> | undefined;
export const initializeStore = () => {
return createStore<GlobalState>((set, get, api) => ({
...createTestSlice(set, get),
}));
};
export function useCreateStore() {
let tempStore = store ?? initializeStore(); // force change type to avoid undefined
store = tempStore;
return () => tempStore;
}