1
1
import { useRouter } from "next/router"
2
+ import { useTranslation } from "react-i18next"
2
3
3
4
import { BaseLink } from "@/components/Link"
4
5
5
6
import { cn } from "@/lib/utils/cn"
6
- import { isMobile } from "@/lib/utils/isMobile"
7
7
8
8
import {
9
9
Command ,
@@ -12,6 +12,7 @@ import {
12
12
CommandInput ,
13
13
CommandList ,
14
14
} from "../ui/command"
15
+ import { Dialog , DialogContent , DialogTrigger } from "../ui/dialog"
15
16
import { Popover , PopoverContent , PopoverTrigger } from "../ui/popover"
16
17
17
18
import MenuItem from "./MenuItem"
@@ -25,15 +26,17 @@ type LanguagePickerProps = {
25
26
children : React . ReactNode
26
27
className ?: string
27
28
handleClose ?: ( ) => void
29
+ dialog ?: boolean
28
30
}
29
31
30
32
const LanguagePicker = ( {
31
33
children,
32
34
handleClose,
33
35
className,
36
+ dialog,
34
37
} : LanguagePickerProps ) => {
35
38
const { asPath, push } = useRouter ( )
36
- const { t , disclosure, languages } = useLanguagePicker ( handleClose )
39
+ const { disclosure, languages } = useLanguagePicker ( handleClose )
37
40
const { isOpen, setValue, onClose, onOpen } = disclosure
38
41
39
42
/**
@@ -63,6 +66,33 @@ const LanguagePicker = ({
63
66
eventName : "/contributing/translation-program" ,
64
67
} )
65
68
69
+ if ( dialog ) {
70
+ return (
71
+ < Dialog open = { isOpen } onOpenChange = { setValue } >
72
+ < DialogTrigger asChild > { children } </ DialogTrigger >
73
+ < DialogContent className = "inset-4 flex h-auto w-auto transform-none flex-col bg-background-highlight p-0 [&>button]:hidden" >
74
+ { /* Mobile Close bar */ }
75
+ < MobileCloseBar handleClick = { handleMobileCloseBarClick } />
76
+
77
+ < LanguagePickerMenu
78
+ languages = { languages }
79
+ onSelect = { handleMenuItemSelect }
80
+ onClose = { ( ) =>
81
+ onClose ( {
82
+ eventAction : "Translation program link (no results)" ,
83
+ eventName : "/contributing/translation-program" ,
84
+ } )
85
+ }
86
+ />
87
+
88
+ < LanguagePickerFooter
89
+ onTranslationProgramClick = { handleBaseLinkClose }
90
+ />
91
+ </ DialogContent >
92
+ </ Dialog >
93
+ )
94
+ }
95
+
66
96
return (
67
97
< Popover open = { isOpen } onOpenChange = { setValue } >
68
98
< PopoverTrigger asChild > { children } </ PopoverTrigger >
@@ -73,83 +103,94 @@ const LanguagePicker = ({
73
103
className
74
104
) }
75
105
>
76
- { /* Mobile Close bar */ }
77
- { /* avoid rendering mobile only feature on desktop */ }
78
- { isMobile ( ) && (
79
- < MobileCloseBar handleClick = { handleMobileCloseBarClick } />
80
- ) }
81
-
82
- < Command
83
- className = "gap-2 p-4"
84
- filter = { ( value : string , search : string ) => {
85
- const item = languages . find ( ( name ) => name . localeOption === value )
106
+ < LanguagePickerMenu
107
+ languages = { languages }
108
+ onSelect = { handleMenuItemSelect }
109
+ onClose = { ( ) =>
110
+ onClose ( {
111
+ eventAction : "Translation program link (no results)" ,
112
+ eventName : "/contributing/translation-program" ,
113
+ } )
114
+ }
115
+ />
116
+
117
+ < LanguagePickerFooter onTranslationProgramClick = { handleBaseLinkClose } />
118
+ </ PopoverContent >
119
+ </ Popover >
120
+ )
121
+ }
86
122
87
- if ( ! item ) return 0
123
+ const LanguagePickerMenu = ( { languages, onClose, onSelect } ) => {
124
+ const { t } = useTranslation ( "common" )
88
125
89
- const { localeOption, sourceName, targetName, englishName } = item
126
+ return (
127
+ < Command
128
+ className = "gap-2 p-4"
129
+ filter = { ( value : string , search : string ) => {
130
+ const item = languages . find ( ( name ) => name . localeOption === value )
131
+
132
+ if ( ! item ) return 0
133
+
134
+ const { localeOption, sourceName, targetName, englishName } = item
135
+
136
+ if (
137
+ ( localeOption + sourceName + targetName + englishName )
138
+ . toLowerCase ( )
139
+ . includes ( search . toLowerCase ( ) )
140
+ ) {
141
+ return 1
142
+ }
143
+
144
+ return 0
145
+ } }
146
+ >
147
+ < div className = "text-xs text-body-medium" >
148
+ { t ( "page-languages-filter-label" ) } { " " }
149
+ < span className = "lowercase" >
150
+ ({ languages . length } { t ( "common:languages" ) } )
151
+ </ span >
152
+ </ div >
153
+
154
+ < CommandInput
155
+ placeholder = { t ( "page-languages-filter-placeholder" ) }
156
+ className = "h-9"
157
+ kbdShortcut = "\"
158
+ />
159
+
160
+ < CommandList className = "max-h-[75vh]" >
161
+ < CommandEmpty className = "py-0 text-left text-base" >
162
+ < NoResultsCallout onClose = { onClose } />
163
+ </ CommandEmpty >
164
+ < CommandGroup className = "p-0" >
165
+ { languages . map ( ( displayInfo ) => (
166
+ < MenuItem
167
+ key = { "item-" + displayInfo . localeOption }
168
+ displayInfo = { displayInfo }
169
+ onSelect = { onSelect }
170
+ />
171
+ ) ) }
172
+ </ CommandGroup >
173
+ </ CommandList >
174
+ </ Command >
175
+ )
176
+ }
90
177
91
- if (
92
- ( localeOption + sourceName + targetName + englishName )
93
- . toLowerCase ( )
94
- . includes ( search . toLowerCase ( ) )
95
- ) {
96
- return 1
97
- }
178
+ const LanguagePickerFooter = ( { onTranslationProgramClick } ) => {
179
+ const { t } = useTranslation ( "common" )
98
180
99
- return 0
100
- } }
181
+ return (
182
+ < div className = "sticky bottom-0 flex justify-center border-t-2 border-primary bg-primary-low-contrast p-3" >
183
+ < p className = "text-center text-xs text-body" >
184
+ { t ( "page-languages-recruit-community" ) } { " " }
185
+ { /* TODO migrate once #13411 is merged */ }
186
+ < BaseLink
187
+ href = "/contributing/translation-program"
188
+ onClick = { onTranslationProgramClick }
101
189
>
102
- < div className = "text-xs text-body-medium" >
103
- { t ( "page-languages-filter-label" ) } { " " }
104
- < span className = "lowercase" >
105
- ({ languages . length } { t ( "common:languages" ) } )
106
- </ span >
107
- </ div >
108
-
109
- < CommandInput
110
- placeholder = { t ( "page-languages-filter-placeholder" ) }
111
- className = "h-9"
112
- kbdShortcut = "\"
113
- />
114
-
115
- < CommandList className = "max-h-[75vh]" >
116
- < CommandEmpty className = "py-0 text-left text-base" >
117
- < NoResultsCallout
118
- onClose = { ( ) =>
119
- onClose ( {
120
- eventAction : "Translation program link (no results)" ,
121
- eventName : "/contributing/translation-program" ,
122
- } )
123
- }
124
- />
125
- </ CommandEmpty >
126
- < CommandGroup className = "p-0" >
127
- { languages . map ( ( displayInfo ) => (
128
- < MenuItem
129
- key = { "item-" + displayInfo . localeOption }
130
- displayInfo = { displayInfo }
131
- onSelect = { handleMenuItemSelect }
132
- />
133
- ) ) }
134
- </ CommandGroup >
135
- </ CommandList >
136
- </ Command >
137
-
138
- { /* Footer callout */ }
139
- < div className = "sticky bottom-0 flex justify-center border-t-2 border-primary bg-primary-low-contrast p-3" >
140
- < p className = "text-center text-xs text-body" >
141
- { t ( "page-languages-recruit-community" ) } { " " }
142
- { /* TODO migrate once #13411 is merged */ }
143
- < BaseLink
144
- href = "/contributing/translation-program"
145
- onClick = { handleBaseLinkClose }
146
- >
147
- { t ( "common:learn-more" ) }
148
- </ BaseLink >
149
- </ p >
150
- </ div >
151
- </ PopoverContent >
152
- </ Popover >
190
+ { t ( "common:learn-more" ) }
191
+ </ BaseLink >
192
+ </ p >
193
+ </ div >
153
194
)
154
195
}
155
196
0 commit comments