Skip to content

Commit ee85628

Browse files
committed
Setting Component Refactor
1 parent 3917371 commit ee85628

File tree

11 files changed

+1301
-1328
lines changed

11 files changed

+1301
-1328
lines changed

webview-ui/src/components/settings/ApiOptions.tsx

Lines changed: 705 additions & 717 deletions
Large diffs are not rendered by default.

webview-ui/src/components/settings/ExperimentalFeature.tsx

Lines changed: 0 additions & 31 deletions
This file was deleted.

webview-ui/src/components/settings/ModelPicker.tsx

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -141,7 +141,14 @@ export const ModelPicker = ({
141141
useEffect(() => setValue(selectedModelId), [selectedModelId])
142142

143143
return (
144-
<>
144+
<div
145+
style={{
146+
marginBottom: 15,
147+
marginTop: 10,
148+
paddingLeft: 10,
149+
borderLeft: "2px solid",
150+
borderColor: "var(--vscode-button-background)",
151+
}}>
145152
<div className="font-semibold">Model</div>
146153
<Popover open={open} onOpenChange={setOpen}>
147154
<PopoverTrigger asChild>
@@ -219,6 +226,6 @@ export const ModelPicker = ({
219226
</div>
220227
</div>
221228
)}
222-
</>
229+
</div>
223230
)
224231
}
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
import { VSCodeCheckbox } from "@vscode/webview-ui-toolkit/react"
2+
3+
interface SettingCheckboxProps {
4+
name: string
5+
description: React.ReactNode
6+
checked?: boolean
7+
onChange: (value: boolean) => void
8+
experimental?: boolean
9+
children?: React.ReactNode
10+
}
11+
12+
const SettingCheckbox = ({
13+
name,
14+
description,
15+
checked: enabled,
16+
onChange,
17+
experimental,
18+
children,
19+
}: SettingCheckboxProps) => {
20+
return (
21+
<div
22+
style={{
23+
marginTop: 10,
24+
marginBottom: 15,
25+
paddingLeft: 10,
26+
borderLeft: "2px solid",
27+
borderColor: experimental ? "var(--vscode-errorForeground)" : "var(--vscode-button-background)",
28+
}}>
29+
<div style={{ display: "flex", alignItems: "center", gap: "5px" }}>
30+
{experimental && <span style={{ color: "var(--vscode-errorForeground)" }}>⚠️</span>}
31+
<VSCodeCheckbox checked={enabled} onChange={(e: any) => onChange(e.target.checked)}>
32+
<span style={{ fontWeight: "700" }}>{name}</span>
33+
</VSCodeCheckbox>
34+
</div>
35+
<p style={{ fontSize: "12px", marginTop: "5px", color: "var(--vscode-descriptionForeground)" }}>
36+
{description}
37+
</p>
38+
{enabled && children}
39+
</div>
40+
)
41+
}
42+
43+
export default SettingCheckbox
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
import { Dropdown } from "vscrui"
2+
import type { DropdownOption } from "vscrui"
3+
4+
interface SettingComboProps {
5+
id?: string
6+
name: string
7+
description?: string
8+
value?: string
9+
onChange: (value: string) => void
10+
options: DropdownOption[]
11+
children?: React.ReactNode
12+
inline?: boolean
13+
}
14+
15+
const SettingCombo = ({ id, name, description, value, onChange, options, children, inline }: SettingComboProps) => {
16+
const defaultValue = options.length > 0 ? options[0].value : undefined
17+
return (
18+
<div
19+
style={{
20+
marginBottom: 15,
21+
marginTop: 10,
22+
paddingLeft: 10,
23+
borderLeft: "2px solid",
24+
borderColor: "var(--vscode-button-background)",
25+
}}>
26+
<div style={{ display: inline ? "flex" : "block", alignItems: "end" }}>
27+
<label style={{ fontWeight: "700", display: "block", marginBottom: 5, paddingRight: 10 }}>{name}</label>
28+
<div className="dropdown-container">
29+
<Dropdown
30+
id={id}
31+
value={value ?? defaultValue}
32+
onChange={(value: unknown) => {
33+
onChange((value as DropdownOption).value)
34+
}}
35+
style={{ width: "100%" }}
36+
options={options}
37+
/>
38+
</div>
39+
</div>
40+
{description && (
41+
<p
42+
style={{
43+
fontSize: "12px",
44+
marginTop: "5px",
45+
color: "var(--vscode-descriptionForeground)",
46+
}}>
47+
{description}
48+
</p>
49+
)}
50+
{children}
51+
</div>
52+
)
53+
}
54+
55+
export default SettingCombo
Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
import { memo } from "react"
2+
3+
interface SettingSliderProps {
4+
name: string
5+
description?: string
6+
value: number
7+
onChange: (value: number) => void
8+
min: number
9+
max: number
10+
step: number
11+
unit?: string
12+
style?: React.CSSProperties
13+
}
14+
15+
const SettingSlider = ({
16+
name,
17+
description,
18+
value,
19+
onChange,
20+
min,
21+
max,
22+
step,
23+
unit = "",
24+
style,
25+
}: SettingSliderProps) => {
26+
const sliderStyle = {
27+
flexGrow: 1,
28+
accentColor: "var(--vscode-button-background)",
29+
height: "2px",
30+
}
31+
32+
const labelStyle = {
33+
minWidth: "45px",
34+
lineHeight: "20px",
35+
paddingBottom: "2px",
36+
paddingLeft: "5px",
37+
}
38+
39+
return (
40+
<div
41+
style={{
42+
display: "flex",
43+
flexDirection: "column",
44+
gap: "5px",
45+
marginTop: 10,
46+
marginBottom: 15,
47+
paddingLeft: 10,
48+
borderLeft: "2px solid",
49+
borderColor: "var(--vscode-button-background)",
50+
...style,
51+
}}>
52+
<span style={{ fontWeight: "700" }}>{name}</span>
53+
<div style={{ display: "flex", alignItems: "center", gap: "5px" }}>
54+
<input
55+
type="range"
56+
min={min}
57+
max={max}
58+
step={step}
59+
value={value}
60+
onChange={(e) => onChange(parseFloat(e.target.value))}
61+
style={sliderStyle}
62+
aria-label={name.toLowerCase()}
63+
/>
64+
<span style={labelStyle}>
65+
{value}
66+
{unit}
67+
</span>
68+
</div>
69+
{description && (
70+
<p
71+
style={{
72+
fontSize: "12px",
73+
marginTop: "5px",
74+
color: "var(--vscode-descriptionForeground)",
75+
}}>
76+
{description}
77+
</p>
78+
)}
79+
</div>
80+
)
81+
}
82+
83+
export default memo(SettingSlider)
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
import { VSCodeTextField } from "@vscode/webview-ui-toolkit/react"
2+
3+
interface SettingTextFieldProps {
4+
name: string
5+
description: React.ReactNode
6+
value?: string
7+
placeholder?: string
8+
type?: "text" | "password" | "url" // Limited to types actually used in ApiOptions.tsx
9+
onBlur: (value: string) => void
10+
children?: React.ReactNode
11+
}
12+
13+
const SettingTextField = ({
14+
name,
15+
description,
16+
value,
17+
placeholder,
18+
type = "text",
19+
onBlur,
20+
children,
21+
}: SettingTextFieldProps) => {
22+
return (
23+
<div
24+
style={{
25+
marginTop: 10,
26+
marginBottom: 15,
27+
paddingLeft: 10,
28+
borderLeft: "2px solid",
29+
borderColor: "var(--vscode-button-background)",
30+
}}>
31+
<VSCodeTextField
32+
value={value || ""}
33+
style={{ width: "100%" }}
34+
type={type}
35+
onBlur={(e: any) => onBlur(e.target.value)}
36+
placeholder={placeholder}>
37+
<span style={{ fontWeight: "700" }}>{name}</span>
38+
</VSCodeTextField>
39+
<p style={{ fontSize: "12px", marginTop: "5px", color: "var(--vscode-descriptionForeground)" }}>
40+
{description}
41+
</p>
42+
{children}
43+
</div>
44+
)
45+
}
46+
47+
export default SettingTextField

0 commit comments

Comments
 (0)