about summary refs log tree commit diff
path: root/src/view/com/composer
diff options
context:
space:
mode:
authorSamuel Newman <mozzius@protonmail.com>2024-10-08 20:00:49 +0300
committerGitHub <noreply@github.com>2024-10-08 20:00:49 +0300
commitfc82d2f6d5e8a93f0e7ce4861c5205c8a4b49c30 (patch)
tree51e618db283d28ef241f0e6f2f6180004e6cb6e7 /src/view/com/composer
parentefcf8a6ae59d9767bc2289af927a2e12bc39a054 (diff)
downloadvoidsky-fc82d2f6d5e8a93f0e7ce4861c5205c8a4b49c30.tar.zst
Move Dialogs to Radix (#5648)
* Use Redix FocusTrap (#5638)

* Use Redix FocusTrap

* force resolutions on radix libs

* add focus guards

* use @radix-ui/dismissable-layer for escape handling

* fix banner menu keypress by using `Pressable`

* add menu in dialog example to storybook

---------

Co-authored-by: Samuel Newman <mozzius@protonmail.com>

* use DismissableLayer/FocusScope for composer

* fix storybook dialog

* thread Portal through Prompt and avatar/banner

* fix dialog style regression

* remove tamagui

---------

Co-authored-by: Eric Bailey <git@esb.lol>
Diffstat (limited to 'src/view/com/composer')
-rw-r--r--src/view/com/composer/Composer.tsx18
-rw-r--r--src/view/com/composer/text-input/web/EmojiPicker.web.tsx19
2 files changed, 12 insertions, 25 deletions
diff --git a/src/view/com/composer/Composer.tsx b/src/view/com/composer/Composer.tsx
index 55c2d81ab..8cc8fba0d 100644
--- a/src/view/com/composer/Composer.tsx
+++ b/src/view/com/composer/Composer.tsx
@@ -65,7 +65,6 @@ import {useDialogStateControlContext} from '#/state/dialogs'
 import {emitPostCreated} from '#/state/events'
 import {ComposerImage, pasteImage} from '#/state/gallery'
 import {useModalControls} from '#/state/modals'
-import {useModals} from '#/state/modals'
 import {useRequireAltTextEnabled} from '#/state/preferences'
 import {
   toPostLanguages,
@@ -146,7 +145,6 @@ export const ComposePost = ({
   const queryClient = useQueryClient()
   const currentDid = currentAccount!.did
   const {data: currentProfile} = useProfileQuery({did: currentDid})
-  const {isModalActive} = useModals()
   const {closeComposer} = useComposerControls()
   const pal = usePalette('default')
   const {isMobile} = useWebMediaQueries()
@@ -303,22 +301,6 @@ export const ComposePost = ({
     }
   }, [onPressCancel, closeAllDialogs, closeAllModals])
 
-  // listen to escape key on desktop web
-  const onEscape = useCallback(
-    (e: KeyboardEvent) => {
-      if (e.key === 'Escape') {
-        onPressCancel()
-      }
-    },
-    [onPressCancel],
-  )
-  useEffect(() => {
-    if (isWeb && !isModalActive) {
-      window.addEventListener('keydown', onEscape)
-      return () => window.removeEventListener('keydown', onEscape)
-    }
-  }, [onEscape, isModalActive])
-
   const onNewLink = useCallback((uri: string) => {
     dispatch({type: 'embed_add_uri', uri})
   }, [])
diff --git a/src/view/com/composer/text-input/web/EmojiPicker.web.tsx b/src/view/com/composer/text-input/web/EmojiPicker.web.tsx
index ad3bb30ec..1d5dad486 100644
--- a/src/view/com/composer/text-input/web/EmojiPicker.web.tsx
+++ b/src/view/com/composer/text-input/web/EmojiPicker.web.tsx
@@ -6,6 +6,7 @@ import {
   View,
 } from 'react-native'
 import Picker from '@emoji-mart/react'
+import {DismissableLayer} from '@radix-ui/react-dismissable-layer'
 
 import {textInputWebEmitter} from '#/view/com/composer/text-input/textInputWebEmitter'
 import {atoms as a} from '#/alf'
@@ -143,13 +144,17 @@ export function EmojiPicker({state, close, pinToTop}: IProps) {
         {/* eslint-disable-next-line react-native-a11y/has-valid-accessibility-descriptors */}
         <TouchableWithoutFeedback onPress={e => e.stopPropagation()}>
           <View style={[{position: 'absolute'}, position]}>
-            <Picker
-              data={async () => {
-                return (await import('./EmojiPickerData.json')).default
-              }}
-              onEmojiSelect={onInsert}
-              autoFocus={true}
-            />
+            <DismissableLayer
+              onFocusOutside={evt => evt.preventDefault()}
+              onDismiss={close}>
+              <Picker
+                data={async () => {
+                  return (await import('./EmojiPickerData.json')).default
+                }}
+                onEmojiSelect={onInsert}
+                autoFocus={true}
+              />
+            </DismissableLayer>
           </View>
         </TouchableWithoutFeedback>
       </View>