File size: 3,476 Bytes
8a37e0a
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
import { useStore } from '@nanostores/react';
import type { WritableAtom } from 'nanostores';
import { atom } from 'nanostores';
import { useCallback, useState } from 'react';

type UseBoolean = {
  isTrue: boolean;
  setTrue: () => void;
  setFalse: () => void;
  set: (value: boolean) => void;
  toggle: () => void;
};

/**
 * Creates a hook to manage a boolean state. The boolean is stored in a nanostores atom.
 * Returns a tuple containing the hook and the atom. Use this for global boolean state.
 * @param initialValue Initial value of the boolean
 */
export const buildUseBoolean = (initialValue: boolean): [() => UseBoolean, WritableAtom<boolean>] => {
  const $boolean = atom(initialValue);

  const setTrue = () => {
    $boolean.set(true);
  };
  const setFalse = () => {
    $boolean.set(false);
  };
  const set = (value: boolean) => {
    $boolean.set(value);
  };
  const toggle = () => {
    $boolean.set(!$boolean.get());
  };

  const useBoolean = () => {
    const isTrue = useStore($boolean);

    return {
      isTrue,
      setTrue,
      setFalse,
      set,
      toggle,
    };
  };

  return [useBoolean, $boolean] as const;
};

/**
 * Hook to manage a boolean state. Use this for a local boolean state.
 * @param initialValue Initial value of the boolean
 */
export const useBoolean = (initialValue: boolean): UseBoolean => {
  const [isTrue, set] = useState(initialValue);

  const setTrue = useCallback(() => {
    set(true);
  }, [set]);
  const setFalse = useCallback(() => {
    set(false);
  }, [set]);
  const toggle = useCallback(() => {
    set((val) => !val);
  }, [set]);

  return {
    isTrue,
    setTrue,
    setFalse,
    set,
    toggle,
  };
};

type UseDisclosure = {
  isOpen: boolean;
  open: () => void;
  close: () => void;
  set: (isOpen: boolean) => void;
  toggle: () => void;
};

/**
 * This is the same as `buildUseBoolean`, but the method names are more descriptive,
 * serving the semantics of a disclosure state.
 *
 * Creates a hook to manage a boolean state. The boolean is stored in a nanostores atom.
 * Returns a tuple containing the hook and the atom. Use this for global boolean state.
 *
 * @param defaultIsOpen Initial state of the disclosure
 */
export const buildUseDisclosure = (defaultIsOpen: boolean): [() => UseDisclosure, WritableAtom<boolean>] => {
  const $isOpen = atom(defaultIsOpen);

  const open = () => {
    $isOpen.set(true);
  };
  const close = () => {
    $isOpen.set(false);
  };
  const set = (isOpen: boolean) => {
    $isOpen.set(isOpen);
  };
  const toggle = () => {
    $isOpen.set(!$isOpen.get());
  };

  const useDisclosure = () => {
    const isOpen = useStore($isOpen);

    return {
      isOpen,
      open,
      close,
      set,
      toggle,
    };
  };

  return [useDisclosure, $isOpen] as const;
};

/**
 * This is the same as `useBoolean`, but the method names are more descriptive,
 * serving the semantics of a disclosure state.
 *
 * Hook to manage a boolean state. Use this for a local boolean state.
 * @param defaultIsOpen Initial state of the disclosure
 */
export const useDisclosure = (defaultIsOpen: boolean): UseDisclosure => {
  const [isOpen, set] = useState(defaultIsOpen);

  const open = useCallback(() => {
    set(true);
  }, [set]);
  const close = useCallback(() => {
    set(false);
  }, [set]);
  const toggle = useCallback(() => {
    set((val) => !val);
  }, [set]);

  return {
    isOpen,
    open,
    close,
    set,
    toggle,
  };
};