1
+ import React from 'react' ;
2
+ import { Input } from './ui/input' ;
3
+ import { Button } from './ui/button' ;
4
+ import { Label } from './ui/label' ;
5
+ import { Textarea } from './ui/textarea' ;
6
+ import { Select , SelectContent , SelectItem , SelectTrigger , SelectValue } from './ui/select' ;
7
+
8
+ interface PasswordFormProps {
9
+ entry ?: Partial < {
10
+ id : number ;
11
+ title : string ;
12
+ username : string ;
13
+ password : string ;
14
+ url ?: string ;
15
+ notes ?: string ;
16
+ category : string ;
17
+ subcategory ?: string ;
18
+ } > ;
19
+ onSave : ( entry : any ) => void ;
20
+ onCancel : ( ) => void ;
21
+ }
22
+
23
+ // Define the vault categories and their subcategories
24
+ const vaultCategories = {
25
+ "Passwords" : [
26
+ "Social Media" ,
27
+ "Email" ,
28
+ "Banking" ,
29
+ "Shopping" ,
30
+ "Work" ,
31
+ "Entertainment" ,
32
+ "Other"
33
+ ] ,
34
+ "Payment Methods" : [
35
+ "Credit Cards" ,
36
+ "Debit Cards" ,
37
+ "Bank Accounts" ,
38
+ "Digital Wallets" ,
39
+ "Cryptocurrency"
40
+ ] ,
41
+ "Secure Notes" : [
42
+ "Personal" ,
43
+ "Work" ,
44
+ "Medical" ,
45
+ "Legal" ,
46
+ "Other"
47
+ ] ,
48
+ "Personal Info" : [
49
+ "Contact Details" ,
50
+ "Addresses" ,
51
+ "Emergency Contacts" ,
52
+ "Medical Info" ,
53
+ "Other"
54
+ ] ,
55
+ "IDs & Licenses" : [
56
+ "Government ID" ,
57
+ "Passport" ,
58
+ "Driver's License" ,
59
+ "Professional License" ,
60
+ "Other"
61
+ ]
62
+ } ;
63
+
64
+ export const PasswordForm : React . FC < PasswordFormProps > = ( { entry = { } , onSave, onCancel } ) => {
65
+ const [ formData , setFormData ] = React . useState ( {
66
+ title : entry . title || '' ,
67
+ username : entry . username || '' ,
68
+ password : entry . password || '' ,
69
+ url : entry . url || '' ,
70
+ notes : entry . notes || '' ,
71
+ category : entry . category || 'Passwords' ,
72
+ subcategory : entry . subcategory || ''
73
+ } ) ;
74
+
75
+ const handleChange = ( e : React . ChangeEvent < HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement > ) => {
76
+ const { name, value } = e . target ;
77
+ setFormData ( prev => ( {
78
+ ...prev ,
79
+ [ name ] : value
80
+ } ) ) ;
81
+ } ;
82
+
83
+ const handleCategoryChange = ( value : string ) => {
84
+ setFormData ( prev => ( {
85
+ ...prev ,
86
+ category : value ,
87
+ subcategory : '' // Reset subcategory when category changes
88
+ } ) ) ;
89
+ } ;
90
+
91
+ const handleSubcategoryChange = ( value : string ) => {
92
+ setFormData ( prev => ( {
93
+ ...prev ,
94
+ subcategory : value
95
+ } ) ) ;
96
+ } ;
97
+
98
+ const handleSubmit = ( e : React . FormEvent ) => {
99
+ e . preventDefault ( ) ;
100
+ onSave ( {
101
+ ...entry ,
102
+ ...formData
103
+ } ) ;
104
+ } ;
105
+
106
+ return (
107
+ < form onSubmit = { handleSubmit } className = "space-y-4" >
108
+ < div className = "grid grid-cols-2 gap-4" >
109
+ < div className = "space-y-2" >
110
+ < Label htmlFor = "category" > Category</ Label >
111
+ < Select
112
+ name = "category"
113
+ value = { formData . category }
114
+ onValueChange = { handleCategoryChange }
115
+ >
116
+ < SelectTrigger >
117
+ < SelectValue placeholder = "Select a category" />
118
+ </ SelectTrigger >
119
+ < SelectContent >
120
+ { Object . keys ( vaultCategories ) . map ( category => (
121
+ < SelectItem key = { category } value = { category } >
122
+ { category }
123
+ </ SelectItem >
124
+ ) ) }
125
+ </ SelectContent >
126
+ </ Select >
127
+ </ div >
128
+
129
+ < div className = "space-y-2" >
130
+ < Label htmlFor = "subcategory" > Subcategory</ Label >
131
+ < Select
132
+ name = "subcategory"
133
+ value = { formData . subcategory }
134
+ onValueChange = { handleSubcategoryChange }
135
+ >
136
+ < SelectTrigger >
137
+ < SelectValue placeholder = "Select a subcategory" />
138
+ </ SelectTrigger >
139
+ < SelectContent >
140
+ { vaultCategories [ formData . category as keyof typeof vaultCategories ] ?. map ( subcategory => (
141
+ < SelectItem key = { subcategory } value = { subcategory } >
142
+ { subcategory }
143
+ </ SelectItem >
144
+ ) ) }
145
+ </ SelectContent >
146
+ </ Select >
147
+ </ div >
148
+ </ div >
149
+
150
+ < div className = "space-y-2" >
151
+ < Label htmlFor = "title" > Title</ Label >
152
+ < Input
153
+ id = "title"
154
+ name = "title"
155
+ value = { formData . title }
156
+ onChange = { handleChange }
157
+ placeholder = "Enter title"
158
+ required
159
+ />
160
+ </ div >
161
+
162
+ < div className = "space-y-2" >
163
+ < Label htmlFor = "username" > Username</ Label >
164
+ < Input
165
+ id = "username"
166
+ name = "username"
167
+ value = { formData . username }
168
+ onChange = { handleChange }
169
+ placeholder = "Enter username"
170
+ required
171
+ />
172
+ </ div >
173
+
174
+ < div className = "space-y-2" >
175
+ < Label htmlFor = "password" > Password</ Label >
176
+ < Input
177
+ id = "password"
178
+ name = "password"
179
+ type = "password"
180
+ value = { formData . password }
181
+ onChange = { handleChange }
182
+ placeholder = "Enter password"
183
+ required
184
+ />
185
+ </ div >
186
+
187
+ < div className = "space-y-2" >
188
+ < Label htmlFor = "url" > URL</ Label >
189
+ < Input
190
+ id = "url"
191
+ name = "url"
192
+ value = { formData . url }
193
+ onChange = { handleChange }
194
+ placeholder = "Enter URL (optional)"
195
+ />
196
+ </ div >
197
+
198
+ < div className = "space-y-2" >
199
+ < Label htmlFor = "notes" > Notes</ Label >
200
+ < Textarea
201
+ id = "notes"
202
+ name = "notes"
203
+ value = { formData . notes }
204
+ onChange = { handleChange }
205
+ placeholder = "Enter notes (optional)"
206
+ rows = { 3 }
207
+ />
208
+ </ div >
209
+
210
+ < div className = "flex justify-end space-x-2" >
211
+ < Button type = "button" variant = "outline" onClick = { onCancel } >
212
+ Cancel
213
+ </ Button >
214
+ < Button type = "submit" variant = "default" >
215
+ Save
216
+ </ Button >
217
+ </ div >
218
+ </ form >
219
+ ) ;
220
+ } ;
0 commit comments