@@ -17,6 +17,7 @@ defmodule LivebookWeb.FormComponents do
17
17
attr :help , :string , default: nil
18
18
attr :type , :string , default: "text"
19
19
attr :class , :string , default: nil
20
+ attr :outer_prefix , :string , default: nil
20
21
21
22
attr :rest , :global , include: ~w( autocomplete readonly disabled step min max)
22
23
@@ -25,30 +26,80 @@ defmodule LivebookWeb.FormComponents do
25
26
26
27
~H"""
27
28
< . field_wrapper id = { @ id } name = { @ name } label = { @ label } errors = { @ errors } help = { @ help } >
28
- < input
29
- type = { @ type }
30
- name = { @ name }
31
- id = { @ id || @ name }
32
- value = { Phoenix.HTML.Form . normalize_value ( "text" , @ value ) }
33
- class = { [ input_classes ( @ errors ) , @ class ] }
34
- { @ rest }
35
- />
29
+ <%= if @ outer_prefix do %>
30
+ < div class = { outer_prefixed_input_wrapper_classes ( @ errors ) } >
31
+ < span class = "inline-flex items-center rounded-l-lg bg-gray-100 px-3 text-sm text-gray-400 opacity-70 border-r border-gray-200 " >
32
+ { @ outer_prefix }
33
+ </ span >
34
+
35
+ < input
36
+ type = { @ type }
37
+ name = { @ name }
38
+ id = { @ id || @ name }
39
+ value = { Phoenix.HTML.Form . normalize_value ( "text" , @ value ) }
40
+ class = { [
41
+ outer_prefixed_input_classes ( @ errors ) ,
42
+ @ class
43
+ ] }
44
+ { @ rest }
45
+ />
46
+ </ div >
47
+ <% else %>
48
+ < input
49
+ type = { @ type }
50
+ name = { @ name }
51
+ id = { @ id || @ name }
52
+ value = { Phoenix.HTML.Form . normalize_value ( "text" , @ value ) }
53
+ class = { [ input_classes ( @ errors ) , @ class ] }
54
+ { @ rest }
55
+ />
56
+ <% end %>
36
57
</ . field_wrapper >
37
58
"""
38
59
end
39
60
40
- defp input_classes ( errors ) do
61
+ defp outer_prefixed_input_wrapper_classes ( errors ) do
41
62
[
42
- "w-full px-3 py-2 text-sm font-normal border rounded-lg placeholder-gray-400 disabled:opacity-70 disabled:cursor-not-allowed focus: border-blue-600 focus-visible:outline-none " ,
63
+ "relative flex items-stretch rounded-lg border focus-within: border-blue-600" ,
43
64
if errors == [ ] do
44
- "bg-gray-50 border-gray-200 text-gray-600 "
65
+ "border-gray-200"
45
66
else
46
- "bg-red-50 border-red-600 text-red-600"
47
- end ,
67
+ "border-red-600"
68
+ end
69
+ ]
70
+ end
71
+
72
+ defp input_classes ( errors ) do
73
+ [
74
+ base_input_classes ( ) ,
75
+ "border rounded-lg focus:border-blue-600" ,
76
+ error_color_classes ( errors ) ,
77
+ if ( errors != [ ] , do: "border-red-600" ) ,
48
78
"invalid:bg-red-50 invalid:border-red-600 invalid:text-red-600"
49
79
]
50
80
end
51
81
82
+ defp outer_prefixed_input_classes ( errors ) do
83
+ [
84
+ base_input_classes ( ) ,
85
+ "border-0 rounded-none rounded-r-lg focus:ring-0 focus:outline-none" ,
86
+ error_color_classes ( errors ) ,
87
+ "invalid:text-red-600"
88
+ ]
89
+ end
90
+
91
+ defp base_input_classes do
92
+ "w-full px-3 py-2 text-sm font-normal placeholder-gray-400 disabled:opacity-70 disabled:cursor-not-allowed focus-visible:outline-none"
93
+ end
94
+
95
+ defp error_color_classes ( errors ) do
96
+ if errors == [ ] do
97
+ "bg-gray-50 text-gray-600"
98
+ else
99
+ "bg-red-50 text-red-600"
100
+ end
101
+ end
102
+
52
103
@ doc """
53
104
Renders a textarea input with label and error messages.
54
105
"""
0 commit comments