@ecohouse/ui 0.1.43 → 0.1.45
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +373 -199
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +24 -4
- package/dist/index.d.ts +24 -4
- package/dist/index.js +289 -121
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/components/Button/Button.stories.tsx +5 -0
- package/src/components/Button/Button.tsx +34 -5
- package/src/components/Input/Input.tsx +6 -0
- package/src/components/LanguageSwitcher/LanguageSwitcher.tsx +1 -1
- package/src/components/SegmentedToggle/SegmentedToggle.tsx +21 -1
- package/src/components/Select/Select.tsx +12 -3
- package/src/icons/Amenity/amenityPaths.ts +3 -10
- package/src/icons/Dram/DramIcon.tsx +14 -0
- package/src/icons/Dram/DramIcon.web.tsx +20 -0
- package/src/icons/Dram/dramPath.ts +2 -0
- package/src/icons/Dram/index.ts +1 -0
- package/src/icons/HouseRules/houseRulesPaths.ts +3 -3
- package/src/icons/NoPets/NoPetsIcon.tsx +23 -0
- package/src/icons/NoPets/NoPetsIcon.web.tsx +29 -0
- package/src/icons/NoPets/index.ts +1 -0
- package/src/icons/NoPets/noPetsPaths.ts +8 -0
- package/src/icons/NoReview/NoReviewIcon.tsx +20 -0
- package/src/icons/NoReview/NoReviewIcon.web.tsx +19 -0
- package/src/icons/NoReview/index.ts +1 -0
- package/src/icons/NoReview/noReviewPath.ts +3 -0
- package/src/icons/StarOutline/StarOutlineIcon.tsx +24 -0
- package/src/icons/StarOutline/StarOutlineIcon.web.tsx +30 -0
- package/src/icons/StarOutline/index.ts +1 -0
- package/src/icons/StarOutline/starOutlinePath.ts +2 -0
- package/src/icons/Sun/SunIcon.tsx +20 -0
- package/src/icons/Sun/SunIcon.web.tsx +26 -0
- package/src/icons/Sun/index.ts +1 -0
- package/src/icons/Sun/sunPath.ts +2 -0
- package/src/icons/Washer/WasherIcon.tsx +25 -0
- package/src/icons/Washer/WasherIcon.web.tsx +31 -0
- package/src/icons/Washer/index.ts +1 -0
- package/src/icons/Washer/washerPaths.ts +28 -0
- package/src/icons/index.ts +6 -0
- package/src/icons/registry.ts +18 -0
- package/src/index.ts +6 -0
package/package.json
CHANGED
|
@@ -10,6 +10,7 @@ const meta = {
|
|
|
10
10
|
title: "Button",
|
|
11
11
|
onPress: fn(),
|
|
12
12
|
disabled: false,
|
|
13
|
+
loading: false,
|
|
13
14
|
variant: "primary",
|
|
14
15
|
size: "lg",
|
|
15
16
|
showIcon: true,
|
|
@@ -105,6 +106,10 @@ export const Disabled: Story = {
|
|
|
105
106
|
args: { disabled: true },
|
|
106
107
|
};
|
|
107
108
|
|
|
109
|
+
export const Loading: Story = {
|
|
110
|
+
args: { loading: true },
|
|
111
|
+
};
|
|
112
|
+
|
|
108
113
|
const storyStyles = StyleSheet.create({
|
|
109
114
|
column: {
|
|
110
115
|
gap: 12,
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { forwardRef, useMemo, useRef, type ComponentRef, type ReactNode } from "react";
|
|
2
2
|
import {
|
|
3
|
+
ActivityIndicator,
|
|
3
4
|
Platform,
|
|
4
5
|
StyleSheet,
|
|
5
6
|
Text,
|
|
@@ -27,6 +28,8 @@ export interface ButtonProps extends Omit<
|
|
|
27
28
|
children?: ReactNode;
|
|
28
29
|
onPress: (event: GestureResponderEvent) => void;
|
|
29
30
|
disabled?: boolean;
|
|
31
|
+
/** Replaces the visible content with a centered spinner and prevents interaction. */
|
|
32
|
+
loading?: boolean;
|
|
30
33
|
variant?: ButtonVariant;
|
|
31
34
|
size?: ButtonSize;
|
|
32
35
|
showIcon?: boolean;
|
|
@@ -123,6 +126,7 @@ export const Button = forwardRef<ComponentRef<typeof TouchableOpacity>, ButtonPr
|
|
|
123
126
|
children,
|
|
124
127
|
onPress,
|
|
125
128
|
disabled = false,
|
|
129
|
+
loading = false,
|
|
126
130
|
variant = "primary",
|
|
127
131
|
size = "lg",
|
|
128
132
|
showIcon = false,
|
|
@@ -146,6 +150,7 @@ export const Button = forwardRef<ComponentRef<typeof TouchableOpacity>, ButtonPr
|
|
|
146
150
|
const hasCustomChildren = typeof children !== "undefined";
|
|
147
151
|
const customIcon = icon != null && typeof icon !== "boolean" ? icon : undefined;
|
|
148
152
|
const hasIcon = showIcon || icon === true || customIcon != null;
|
|
153
|
+
const interactionDisabled = disabled || loading;
|
|
149
154
|
const resolvedContainerClassName = className?.trim() || undefined;
|
|
150
155
|
const resolvedAccessibilityLabel =
|
|
151
156
|
accessibilityLabel ?? (typeof label === "string" ? label : undefined);
|
|
@@ -173,7 +178,7 @@ export const Button = forwardRef<ComponentRef<typeof TouchableOpacity>, ButtonPr
|
|
|
173
178
|
gap: hasIcon ? metrics.gap : 0,
|
|
174
179
|
},
|
|
175
180
|
hasIcon ? styles.contentWithIcon : styles.contentWithoutIcon,
|
|
176
|
-
disabled && styles.disabled,
|
|
181
|
+
disabled && !loading && styles.disabled,
|
|
177
182
|
style,
|
|
178
183
|
];
|
|
179
184
|
|
|
@@ -192,16 +197,20 @@ export const Button = forwardRef<ComponentRef<typeof TouchableOpacity>, ButtonPr
|
|
|
192
197
|
ref={setContainerRef}
|
|
193
198
|
style={containerStyle}
|
|
194
199
|
onPress={onPress}
|
|
195
|
-
disabled={
|
|
200
|
+
disabled={interactionDisabled}
|
|
196
201
|
activeOpacity={0.7}
|
|
197
202
|
accessibilityRole="button"
|
|
198
203
|
accessibilityLabel={resolvedAccessibilityLabel}
|
|
199
|
-
accessibilityState={{ disabled }}
|
|
204
|
+
accessibilityState={{ busy: loading, disabled: interactionDisabled }}
|
|
200
205
|
>
|
|
201
206
|
{hasCustomChildren ? (
|
|
202
|
-
|
|
207
|
+
loading ? (
|
|
208
|
+
<View style={styles.loadingContent}>{children}</View>
|
|
209
|
+
) : (
|
|
210
|
+
children
|
|
211
|
+
)
|
|
203
212
|
) : (
|
|
204
|
-
<Text ref={textRef} style={labelStyle}>
|
|
213
|
+
<Text ref={textRef} style={[labelStyle, loading && styles.loadingContent]}>
|
|
205
214
|
{label}
|
|
206
215
|
</Text>
|
|
207
216
|
)}
|
|
@@ -216,11 +225,18 @@ export const Button = forwardRef<ComponentRef<typeof TouchableOpacity>, ButtonPr
|
|
|
216
225
|
borderRadius: metrics.iconContainerSize / 2,
|
|
217
226
|
backgroundColor: iconBadgeBackgroundColor ?? preset.iconBadgeBackgroundColor,
|
|
218
227
|
},
|
|
228
|
+
loading && styles.loadingContent,
|
|
219
229
|
]}
|
|
220
230
|
>
|
|
221
231
|
{iconNode}
|
|
222
232
|
</View>
|
|
223
233
|
) : null}
|
|
234
|
+
|
|
235
|
+
{loading ? (
|
|
236
|
+
<View pointerEvents="none" style={styles.loadingIndicator}>
|
|
237
|
+
<ActivityIndicator color={preset.textColor} size="small" />
|
|
238
|
+
</View>
|
|
239
|
+
) : null}
|
|
224
240
|
</TouchableOpacity>
|
|
225
241
|
);
|
|
226
242
|
},
|
|
@@ -232,6 +248,7 @@ const styles = StyleSheet.create({
|
|
|
232
248
|
alignItems: "center",
|
|
233
249
|
alignSelf: "flex-start",
|
|
234
250
|
borderWidth: 0,
|
|
251
|
+
position: "relative",
|
|
235
252
|
},
|
|
236
253
|
disabled: {
|
|
237
254
|
opacity: 0.6,
|
|
@@ -254,4 +271,16 @@ const styles = StyleSheet.create({
|
|
|
254
271
|
justifyContent: "center",
|
|
255
272
|
flexShrink: 0,
|
|
256
273
|
},
|
|
274
|
+
loadingContent: {
|
|
275
|
+
opacity: 0,
|
|
276
|
+
},
|
|
277
|
+
loadingIndicator: {
|
|
278
|
+
alignItems: "center",
|
|
279
|
+
bottom: 0,
|
|
280
|
+
justifyContent: "center",
|
|
281
|
+
left: 0,
|
|
282
|
+
position: "absolute",
|
|
283
|
+
right: 0,
|
|
284
|
+
top: 0,
|
|
285
|
+
},
|
|
257
286
|
});
|
|
@@ -168,6 +168,8 @@ export const Input = forwardRef<ComponentRef<typeof TextInput>, InputProps>(func
|
|
|
168
168
|
showRightIcon = false,
|
|
169
169
|
onRightIconPress,
|
|
170
170
|
rightIconAccessibilityLabel,
|
|
171
|
+
autoComplete = "off",
|
|
172
|
+
importantForAutofill,
|
|
171
173
|
style,
|
|
172
174
|
fieldStyle,
|
|
173
175
|
inputStyle,
|
|
@@ -194,6 +196,8 @@ export const Input = forwardRef<ComponentRef<typeof TextInput>, InputProps>(func
|
|
|
194
196
|
const visualState = resolveVisualState({ disabled, error, focused, hasValue });
|
|
195
197
|
const chrome = chromeFor(visualState);
|
|
196
198
|
const resolvedAccessibilityLabel = accessibilityLabel ?? (showLabel ? undefined : label);
|
|
199
|
+
const resolvedImportantForAutofill =
|
|
200
|
+
importantForAutofill ?? (autoComplete === "off" ? "no" : "auto");
|
|
197
201
|
|
|
198
202
|
const hasLeftIcon = showLeftIcon || leftIcon != null;
|
|
199
203
|
const hasRightIcon = showRightIcon || rightIcon != null;
|
|
@@ -256,6 +260,8 @@ export const Input = forwardRef<ComponentRef<typeof TextInput>, InputProps>(func
|
|
|
256
260
|
ref={setInputRef}
|
|
257
261
|
{...textInputProps}
|
|
258
262
|
nativeID={inputDomId}
|
|
263
|
+
autoComplete={autoComplete}
|
|
264
|
+
importantForAutofill={resolvedImportantForAutofill}
|
|
259
265
|
value={isControlled ? value : undefined}
|
|
260
266
|
defaultValue={isControlled ? undefined : defaultValue}
|
|
261
267
|
editable={!disabled}
|
|
@@ -58,7 +58,7 @@ export const defaultLanguageOptions = [
|
|
|
58
58
|
{ value: "ru", label: "Рус" },
|
|
59
59
|
] as const satisfies readonly LanguageOption[];
|
|
60
60
|
|
|
61
|
-
const CONTROL_WIDTH =
|
|
61
|
+
const CONTROL_WIDTH = 96;
|
|
62
62
|
const CONTROL_HEIGHT = 35;
|
|
63
63
|
const ICON_SIZE = 16;
|
|
64
64
|
const ICON_BUTTON_SIZE = 32;
|
|
@@ -90,6 +90,7 @@ export const SegmentedToggle = forwardRef<ComponentRef<typeof View>, SegmentedTo
|
|
|
90
90
|
const resolvedClassName = className?.trim() || undefined;
|
|
91
91
|
const setContainerRef = useMemo(() => mergeRefs(containerRef, forwardedRef), [forwardedRef]);
|
|
92
92
|
const progress = useRef(new Animated.Value(selectedIndex)).current;
|
|
93
|
+
const hasMounted = useRef(false);
|
|
93
94
|
const [contentWidths, setContentWidths] = useState<number[]>(() =>
|
|
94
95
|
Array.from({ length: optionCount }, () => 0),
|
|
95
96
|
);
|
|
@@ -128,6 +129,12 @@ export const SegmentedToggle = forwardRef<ComponentRef<typeof View>, SegmentedTo
|
|
|
128
129
|
}, [optionCount]);
|
|
129
130
|
|
|
130
131
|
useEffect(() => {
|
|
132
|
+
if (!hasMounted.current) {
|
|
133
|
+
hasMounted.current = true;
|
|
134
|
+
progress.setValue(selectedIndex);
|
|
135
|
+
return;
|
|
136
|
+
}
|
|
137
|
+
|
|
131
138
|
const animation = Animated.timing(progress, {
|
|
132
139
|
toValue: selectedIndex,
|
|
133
140
|
duration: ANIMATION_DURATION,
|
|
@@ -202,7 +209,7 @@ export const SegmentedToggle = forwardRef<ComponentRef<typeof View>, SegmentedTo
|
|
|
202
209
|
{options.map(({ value: optionValue, label, icon: Icon, showLabel = true }, index) => {
|
|
203
210
|
const selected = optionValue === selectedValue;
|
|
204
211
|
const iconColor = selected ? colors.primary : colors.whiteAlpha20;
|
|
205
|
-
const labelColor = selected ? colors.
|
|
212
|
+
const labelColor = selected ? colors.white : colors.grey150;
|
|
206
213
|
const optionWidth = optionWidths[index] ?? 0;
|
|
207
214
|
|
|
208
215
|
return (
|
|
@@ -219,6 +226,7 @@ export const SegmentedToggle = forwardRef<ComponentRef<typeof View>, SegmentedTo
|
|
|
219
226
|
fullWidth
|
|
220
227
|
? styles.optionFullWidth
|
|
221
228
|
: [styles.optionContentWidth, optionWidth > 0 && { width: optionWidth }],
|
|
229
|
+
selected && selectedOptionWidth === 0 && styles.initialSelectedOption,
|
|
222
230
|
]}
|
|
223
231
|
>
|
|
224
232
|
<View style={styles.optionContent}>
|
|
@@ -228,6 +236,7 @@ export const SegmentedToggle = forwardRef<ComponentRef<typeof View>, SegmentedTo
|
|
|
228
236
|
numberOfLines={fullWidth ? 1 : undefined}
|
|
229
237
|
style={[
|
|
230
238
|
styles.label,
|
|
239
|
+
selected ? styles.selectedLabel : styles.inactiveLabel,
|
|
231
240
|
!fullWidth && styles.contentWidthLabel,
|
|
232
241
|
{ color: labelColor },
|
|
233
242
|
]}
|
|
@@ -292,6 +301,9 @@ const styles = StyleSheet.create({
|
|
|
292
301
|
optionContentWidth: {
|
|
293
302
|
minWidth: OPTION_MIN_WIDTH,
|
|
294
303
|
},
|
|
304
|
+
initialSelectedOption: {
|
|
305
|
+
backgroundColor: colors.grey600,
|
|
306
|
+
},
|
|
295
307
|
activeIndicator: {
|
|
296
308
|
position: "absolute",
|
|
297
309
|
top: TRACK_PADDING,
|
|
@@ -304,6 +316,14 @@ const styles = StyleSheet.create({
|
|
|
304
316
|
...segmentedToggleTypography,
|
|
305
317
|
flexShrink: 1,
|
|
306
318
|
},
|
|
319
|
+
selectedLabel: {
|
|
320
|
+
fontWeight: "600",
|
|
321
|
+
letterSpacing: 0.36,
|
|
322
|
+
},
|
|
323
|
+
inactiveLabel: {
|
|
324
|
+
fontWeight: "400",
|
|
325
|
+
letterSpacing: 0.36,
|
|
326
|
+
},
|
|
307
327
|
contentWidthLabel: {
|
|
308
328
|
flexShrink: 0,
|
|
309
329
|
},
|
|
@@ -347,15 +347,24 @@ export const Select = forwardRef<ComponentRef<typeof View>, SelectProps>(
|
|
|
347
347
|
return null;
|
|
348
348
|
}, [menuStyle]);
|
|
349
349
|
|
|
350
|
+
const resolvedOptionListMaxHeight = useMemo(() => {
|
|
351
|
+
const flat = StyleSheet.flatten(menuStyle);
|
|
352
|
+
const menuMaxHeight = flat?.maxHeight;
|
|
353
|
+
if (typeof menuMaxHeight !== "number") return MENU_MAX_LIST_HEIGHT;
|
|
354
|
+
|
|
355
|
+
const menuChromeHeight = 24 + (showSearch ? 48 : 0);
|
|
356
|
+
return Math.max(43, menuMaxHeight - menuChromeHeight);
|
|
357
|
+
}, [menuStyle, showSearch]);
|
|
358
|
+
|
|
350
359
|
const estimatedMenuHeight = useMemo(() => {
|
|
351
360
|
const searchBlock = showSearch ? 40 + 8 : 0;
|
|
352
361
|
const optionCount = Math.max(filteredOptions.length, 1);
|
|
353
362
|
const listHeight = Math.min(
|
|
354
363
|
optionCount * 43 + Math.max(0, optionCount - 1) * 8,
|
|
355
|
-
|
|
364
|
+
resolvedOptionListMaxHeight,
|
|
356
365
|
);
|
|
357
366
|
return 24 + searchBlock + listHeight;
|
|
358
|
-
}, [filteredOptions.length, showSearch]);
|
|
367
|
+
}, [filteredOptions.length, resolvedOptionListMaxHeight, showSearch]);
|
|
359
368
|
|
|
360
369
|
const setOpen = useCallback(
|
|
361
370
|
(next: boolean) => {
|
|
@@ -675,7 +684,7 @@ export const Select = forwardRef<ComponentRef<typeof View>, SelectProps>(
|
|
|
675
684
|
) : null}
|
|
676
685
|
|
|
677
686
|
<ScrollView
|
|
678
|
-
style={styles.optionList}
|
|
687
|
+
style={[styles.optionList, { maxHeight: resolvedOptionListMaxHeight }]}
|
|
679
688
|
contentContainerStyle={styles.optionListContent}
|
|
680
689
|
keyboardShouldPersistTaps="handled"
|
|
681
690
|
showsVerticalScrollIndicator={false}
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { WASHER_PATHS } from "../Washer/washerPaths";
|
|
2
|
+
|
|
1
3
|
export const amenityNames = [
|
|
2
4
|
"kitchen",
|
|
3
5
|
"wifi",
|
|
@@ -46,16 +48,7 @@ export const AMENITY_PATHS: Record<AmenityName, readonly AmenityPathDefinition[]
|
|
|
46
48
|
strokeWidth: 2,
|
|
47
49
|
},
|
|
48
50
|
],
|
|
49
|
-
washer:
|
|
50
|
-
{
|
|
51
|
-
d: "M15.833 1.66699H4.16634C3.7061 1.66699 3.33301 2.04009 3.33301 2.50033V17.5003C3.33301 17.9606 3.7061 18.3337 4.16634 18.3337H15.833C16.2932 18.3337 16.6663 17.9606 16.6663 17.5003V2.50033C16.6663 2.04009 16.2932 1.66699 15.833 1.66699ZM3.33301 5.00033C3.33301 5.46058 3.7061 5.83366 4.16634 5.83366H15.833C16.2933 5.83366 16.6663 5.46058 16.6663 5.00033V2.50033C16.6663 2.04009 16.2933 1.66699 15.833 1.66699H4.16634C3.7061 1.66699 3.33301 2.04009 3.33301 2.50033V5.00033ZM9.99967 15.0003C11.6105 15.0003 12.9163 13.6945 12.9163 12.0837C12.9163 10.4728 11.6105 9.16699 9.99967 9.16699C8.38884 9.16699 7.08301 10.4728 7.08301 12.0837C7.08301 13.6945 8.38884 15.0003 9.99967 15.0003Z",
|
|
52
|
-
strokeWidth: 1.5,
|
|
53
|
-
},
|
|
54
|
-
{
|
|
55
|
-
d: "M5.83333 4.58317C6.29357 4.58317 6.66667 4.21007 6.66667 3.74984C6.66667 3.2896 6.29357 2.9165 5.83333 2.9165C5.3731 2.9165 5 3.2896 5 3.74984C5 4.21007 5.3731 4.58317 5.83333 4.58317ZM8.33333 4.58317C8.79357 4.58317 9.16667 4.21007 9.16667 3.74984C9.16667 3.2896 8.79357 2.9165 8.33333 2.9165C7.8731 2.9165 7.5 3.2896 7.5 3.74984C7.5 4.21007 7.8731 4.58317 8.33333 4.58317Z",
|
|
56
|
-
fill: true,
|
|
57
|
-
},
|
|
58
|
-
],
|
|
51
|
+
washer: WASHER_PATHS,
|
|
59
52
|
ac: [
|
|
60
53
|
{
|
|
61
54
|
d: "M17.5003 3.33301H2.50033C2.04009 3.33301 1.66699 3.7061 1.66699 4.16634V10.833C1.66699 11.2932 2.04009 11.6663 2.50033 11.6663H17.5003C17.9606 11.6663 18.3337 11.2932 18.3337 10.833V4.16634C18.3337 3.7061 17.9606 3.33301 17.5003 3.33301ZM15 8.3335H5V11.6668H15V8.3335ZM13.333 5.83301H14.9997M10 14.1665V16.6665M6.66699 15V15.8333M13.333 15V15.8333",
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { DRAM_PATH } from "./dramPath";
|
|
5
|
+
|
|
6
|
+
export function DramIcon({ size = 12, color = colors.grey0 }: IconProps) {
|
|
7
|
+
return (
|
|
8
|
+
<Svg width={(size * 11) / 12} height={size} viewBox="0 0 11 12" fill="none">
|
|
9
|
+
<Path d={DRAM_PATH} fill={color} />
|
|
10
|
+
</Svg>
|
|
11
|
+
);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
export { DRAM_PATH } from "./dramPath";
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { colors } from "../../theme";
|
|
2
|
+
import type { IconProps } from "../types";
|
|
3
|
+
import { DRAM_PATH } from "./dramPath";
|
|
4
|
+
|
|
5
|
+
export function DramIcon({ size = 12, color = colors.grey0 }: IconProps) {
|
|
6
|
+
return (
|
|
7
|
+
<svg
|
|
8
|
+
width={(size * 11) / 12}
|
|
9
|
+
height={size}
|
|
10
|
+
viewBox="0 0 11 12"
|
|
11
|
+
fill="none"
|
|
12
|
+
xmlns="http://www.w3.org/2000/svg"
|
|
13
|
+
aria-hidden
|
|
14
|
+
>
|
|
15
|
+
<path d={DRAM_PATH} fill={color} />
|
|
16
|
+
</svg>
|
|
17
|
+
);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export { DRAM_PATH } from "./dramPath";
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
export const DRAM_PATH =
|
|
2
|
+
"M8.72034 11.584H6.78434V4.06398C6.78434 3.23198 6.58168 2.61332 6.17634 2.20798C5.77101 1.80265 5.16834 1.59998 4.36834 1.59998C3.81368 1.59998 3.35501 1.70665 2.99234 1.91998C2.64034 2.12265 2.37901 2.44265 2.20834 2.87998C2.03768 3.31732 1.95234 3.88265 1.95234 4.57598H0.0003438C0.0003438 3.63732 0.160344 2.82665 0.480344 2.14398C0.811011 1.45065 1.30168 0.922651 1.95234 0.559984C2.61368 0.186651 3.43501 -1.62125e-05 4.41634 -1.62125e-05C5.34434 -1.62125e-05 6.12834 0.17065 6.76834 0.511984C7.41901 0.842651 7.90434 1.32798 8.22434 1.96798C8.55501 2.59732 8.72034 3.34932 8.72034 4.22398V11.584ZM4.67234 4.81598H10.8323V6.03198H4.67234V4.81598ZM4.67234 7.08798H10.8323V8.31998H4.67234V7.08798Z";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { DramIcon, DRAM_PATH } from "./DramIcon";
|
|
@@ -4,10 +4,10 @@ export const QUIET_HOURS_PATH =
|
|
|
4
4
|
|
|
5
5
|
/** No-smoking — stroke paths, 20×20 viewBox. */
|
|
6
6
|
export const NO_SMOKING_PATHS = [
|
|
7
|
-
"M6.
|
|
8
|
-
"M13.
|
|
7
|
+
"M6.66797 10.834V14.1673",
|
|
8
|
+
"M13.332 4.16602V4.58268C13.332 5.02471 13.5076 5.44863 13.8202 5.76119C14.1327 6.07375 14.5567 6.24935 14.9987 6.24935C15.4407 6.24935 15.8646 6.42494 16.1772 6.7375C16.4898 7.05007 16.6654 7.47399 16.6654 7.91602V8.33268",
|
|
9
9
|
"M2.5 2.5L17.5 17.5",
|
|
10
|
-
"M14.1667 10.
|
|
10
|
+
"M14.1667 10.834H16.6667C16.8877 10.834 17.0996 10.9218 17.2559 11.0781C17.4122 11.2343 17.5 11.4463 17.5 11.6673V13.334C17.5 13.5673 17.4042 13.7782 17.25 13.929M14.1667 14.1673H3.33333C3.11232 14.1673 2.90036 14.0795 2.74408 13.9232C2.5878 13.767 2.5 13.555 2.5 13.334V11.6673C2.5 11.4463 2.5878 11.2343 2.74408 11.0781C2.90036 10.9218 3.11232 10.834 3.33333 10.834H10.8333",
|
|
11
11
|
] as const;
|
|
12
12
|
|
|
13
13
|
/** Paw / pets — stroke paths, 20×20 viewBox. */
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { NO_PETS_PATHS } from "./noPetsPaths";
|
|
5
|
+
|
|
6
|
+
export function NoPetsIcon({ size = 20, color = colors.white, strokeWidth = 1.5 }: IconProps) {
|
|
7
|
+
return (
|
|
8
|
+
<Svg width={size} height={size} viewBox="0 0 20 20" fill="none">
|
|
9
|
+
{NO_PETS_PATHS.map((path, index) => (
|
|
10
|
+
<Path
|
|
11
|
+
key={`no-pets-${index}`}
|
|
12
|
+
d={path}
|
|
13
|
+
stroke={color}
|
|
14
|
+
strokeWidth={strokeWidth}
|
|
15
|
+
strokeLinecap="round"
|
|
16
|
+
strokeLinejoin="round"
|
|
17
|
+
/>
|
|
18
|
+
))}
|
|
19
|
+
</Svg>
|
|
20
|
+
);
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export { NO_PETS_PATHS } from "./noPetsPaths";
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { colors } from "../../theme";
|
|
2
|
+
import type { IconProps } from "../types";
|
|
3
|
+
import { NO_PETS_PATHS } from "./noPetsPaths";
|
|
4
|
+
|
|
5
|
+
export function NoPetsIcon({ size = 20, color = colors.white, strokeWidth = 1.5 }: IconProps) {
|
|
6
|
+
return (
|
|
7
|
+
<svg
|
|
8
|
+
width={size}
|
|
9
|
+
height={size}
|
|
10
|
+
viewBox="0 0 20 20"
|
|
11
|
+
fill="none"
|
|
12
|
+
xmlns="http://www.w3.org/2000/svg"
|
|
13
|
+
aria-hidden
|
|
14
|
+
>
|
|
15
|
+
{NO_PETS_PATHS.map((path, index) => (
|
|
16
|
+
<path
|
|
17
|
+
key={`no-pets-${index}`}
|
|
18
|
+
d={path}
|
|
19
|
+
stroke={color}
|
|
20
|
+
strokeWidth={strokeWidth}
|
|
21
|
+
strokeLinecap="round"
|
|
22
|
+
strokeLinejoin="round"
|
|
23
|
+
/>
|
|
24
|
+
))}
|
|
25
|
+
</svg>
|
|
26
|
+
);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export { NO_PETS_PATHS } from "./noPetsPaths";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { NoPetsIcon, NO_PETS_PATHS } from "./NoPetsIcon";
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
export const NO_PETS_PATHS = [
|
|
2
|
+
"M9.30729 9.29492C8.71562 9.55326 8.32062 10.2174 7.64062 11.4558C6.85562 12.8749 5.26896 12.9933 4.87312 14.1983C4.79229 14.4191 4.75229 14.7624 4.75396 14.9999C4.75396 15.9799 5.40979 16.6666 6.25396 16.6666C7.30312 16.6666 8.75396 15.8333 10.004 15.8333C11.254 15.8333 12.7048 16.6666 13.754 16.6666C14.5265 16.6666 15.1406 16.0924 15.2398 15.2433",
|
|
3
|
+
"M16.8222 6.73435C16.7151 6.6891 16.6001 6.66586 16.4838 6.66602H16.4713C15.8588 6.67602 15.1713 7.29102 14.8105 8.22102C14.378 9.33352 14.5772 10.471 15.2588 10.7643C15.3663 10.8102 15.4813 10.8327 15.5972 10.8327C16.213 10.8327 16.9097 10.2143 17.273 9.27768C17.703 8.16518 17.4997 7.02768 16.8222 6.73435Z",
|
|
4
|
+
"M9.16562 5.82732C9.17486 5.62532 9.16369 5.42291 9.13229 5.22315C8.96312 4.14232 8.25979 3.33398 7.52229 3.33398C7.29304 3.33531 7.07077 3.41301 6.89062 3.55482",
|
|
5
|
+
"M13.7119 5.61149C13.8903 4.46482 13.3994 3.44982 12.6119 3.34315C12.5672 3.33696 12.5221 3.3339 12.4769 3.33399C11.7394 3.33399 11.0369 4.14232 10.8686 5.22315C10.6903 6.36982 11.1811 7.38482 11.9686 7.49149C12.0136 7.49732 12.0586 7.50065 12.1036 7.50065C12.8411 7.50065 13.5453 6.68899 13.7119 5.61149Z",
|
|
6
|
+
"M4.74152 10.7643C5.42152 10.471 5.61985 9.33185 5.18819 8.22102C4.82485 7.28435 4.12902 6.66602 3.51402 6.66602C3.39735 6.66602 3.28319 6.68852 3.17485 6.73435C2.49485 7.02768 2.29652 8.16685 2.72819 9.27768C3.09152 10.2143 3.78735 10.8327 4.40235 10.8327C4.51902 10.8327 4.63319 10.8102 4.74152 10.7643Z",
|
|
7
|
+
"M2.5 2.5L17.5 17.5",
|
|
8
|
+
] as const;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { NO_REVIEW_PATH } from "./noReviewPath";
|
|
5
|
+
|
|
6
|
+
export { NO_REVIEW_PATH } from "./noReviewPath";
|
|
7
|
+
|
|
8
|
+
export function NoReviewIcon({ size = 20, color = colors.grey150, strokeWidth = 2 }: IconProps) {
|
|
9
|
+
return (
|
|
10
|
+
<Svg width={size} height={size} viewBox="0 0 20 20" fill="none">
|
|
11
|
+
<Path
|
|
12
|
+
d={NO_REVIEW_PATH}
|
|
13
|
+
stroke={color}
|
|
14
|
+
strokeWidth={strokeWidth}
|
|
15
|
+
strokeLinecap="round"
|
|
16
|
+
strokeLinejoin="round"
|
|
17
|
+
/>
|
|
18
|
+
</Svg>
|
|
19
|
+
);
|
|
20
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { colors } from "../../theme";
|
|
2
|
+
import type { IconProps } from "../types";
|
|
3
|
+
import { NO_REVIEW_PATH } from "./noReviewPath";
|
|
4
|
+
|
|
5
|
+
export function NoReviewIcon({ size = 20, color = colors.grey150, strokeWidth = 2 }: IconProps) {
|
|
6
|
+
return (
|
|
7
|
+
<svg width={size} height={size} viewBox="0 0 20 20" fill="none" aria-hidden>
|
|
8
|
+
<path
|
|
9
|
+
d={NO_REVIEW_PATH}
|
|
10
|
+
stroke={color}
|
|
11
|
+
strokeWidth={strokeWidth}
|
|
12
|
+
strokeLinecap="round"
|
|
13
|
+
strokeLinejoin="round"
|
|
14
|
+
/>
|
|
15
|
+
</svg>
|
|
16
|
+
);
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
export { NO_REVIEW_PATH } from "./noReviewPath";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { NoReviewIcon, NO_REVIEW_PATH } from "./NoReviewIcon";
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
/** No-review / empty comment path — 20×20 viewBox. */
|
|
2
|
+
export const NO_REVIEW_PATH =
|
|
3
|
+
"M8.33333 10.833L9.99999 9.16633M9.99999 9.16633L11.6666 7.49967M9.99999 9.16633L8.33333 7.49967M9.99999 9.16633L11.6666 10.833M5.93631 15.584L4.66634 16.6C3.97287 17.1547 3.62596 17.4322 3.33415 17.4326C3.08036 17.4328 2.84037 17.3174 2.68205 17.1191C2.5 16.891 2.5 16.4471 2.5 15.559V5.99984C2.5 5.06642 2.5 4.59936 2.68166 4.24284C2.84144 3.92924 3.09623 3.67445 3.40983 3.51466C3.76635 3.33301 4.23341 3.33301 5.16683 3.33301H14.8335C15.7669 3.33301 16.233 3.33301 16.5895 3.51466C16.9031 3.67445 17.1587 3.92924 17.3185 4.24284C17.5 4.59901 17.5 5.0655 17.5 5.9971V12.336C17.5 13.2676 17.5 13.7334 17.3185 14.0896C17.1587 14.4032 16.9036 14.6584 16.59 14.8182C16.2338 14.9997 15.7675 14.9997 14.8359 14.9997H7.60173C7.25503 14.9997 7.08231 14.9997 6.9165 15.0337C6.7694 15.0639 6.6268 15.1136 6.49307 15.182C6.34401 15.2581 6.21041 15.365 5.94565 15.5768L5.93631 15.584Z";
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { STAR_OUTLINE_PATH } from "./starOutlinePath";
|
|
5
|
+
|
|
6
|
+
export function StarOutlineIcon({
|
|
7
|
+
size = 24,
|
|
8
|
+
color = colors.grey200,
|
|
9
|
+
strokeWidth = 1.35,
|
|
10
|
+
}: IconProps) {
|
|
11
|
+
return (
|
|
12
|
+
<Svg width={size} height={size} viewBox="0 0 24 24" fill="none">
|
|
13
|
+
<Path
|
|
14
|
+
d={STAR_OUTLINE_PATH}
|
|
15
|
+
stroke={color}
|
|
16
|
+
strokeWidth={strokeWidth}
|
|
17
|
+
strokeLinecap="round"
|
|
18
|
+
strokeLinejoin="round"
|
|
19
|
+
/>
|
|
20
|
+
</Svg>
|
|
21
|
+
);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export { STAR_OUTLINE_PATH } from "./starOutlinePath";
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { colors } from "../../theme";
|
|
2
|
+
import type { IconProps } from "../types";
|
|
3
|
+
import { STAR_OUTLINE_PATH } from "./starOutlinePath";
|
|
4
|
+
|
|
5
|
+
export function StarOutlineIcon({
|
|
6
|
+
size = 24,
|
|
7
|
+
color = colors.grey200,
|
|
8
|
+
strokeWidth = 1.35,
|
|
9
|
+
}: IconProps) {
|
|
10
|
+
return (
|
|
11
|
+
<svg
|
|
12
|
+
width={size}
|
|
13
|
+
height={size}
|
|
14
|
+
viewBox="0 0 24 24"
|
|
15
|
+
fill="none"
|
|
16
|
+
xmlns="http://www.w3.org/2000/svg"
|
|
17
|
+
aria-hidden
|
|
18
|
+
>
|
|
19
|
+
<path
|
|
20
|
+
d={STAR_OUTLINE_PATH}
|
|
21
|
+
stroke={color}
|
|
22
|
+
strokeWidth={strokeWidth}
|
|
23
|
+
strokeLinecap="round"
|
|
24
|
+
strokeLinejoin="round"
|
|
25
|
+
/>
|
|
26
|
+
</svg>
|
|
27
|
+
);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export { STAR_OUTLINE_PATH } from "./starOutlinePath";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { StarOutlineIcon, STAR_OUTLINE_PATH } from "./StarOutlineIcon";
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { SUN_PATH } from "./sunPath";
|
|
5
|
+
|
|
6
|
+
export function SunIcon({ size = 16, color = colors.primary, strokeWidth = 1.5 }: IconProps) {
|
|
7
|
+
return (
|
|
8
|
+
<Svg width={size} height={size} viewBox="0 0 16 16" fill="none">
|
|
9
|
+
<Path
|
|
10
|
+
d={SUN_PATH}
|
|
11
|
+
stroke={color}
|
|
12
|
+
strokeWidth={strokeWidth}
|
|
13
|
+
strokeLinecap="round"
|
|
14
|
+
strokeLinejoin="round"
|
|
15
|
+
/>
|
|
16
|
+
</Svg>
|
|
17
|
+
);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export { SUN_PATH } from "./sunPath";
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { colors } from "../../theme";
|
|
2
|
+
import type { IconProps } from "../types";
|
|
3
|
+
import { SUN_PATH } from "./sunPath";
|
|
4
|
+
|
|
5
|
+
export function SunIcon({ size = 16, color = colors.primary, strokeWidth = 1.5 }: IconProps) {
|
|
6
|
+
return (
|
|
7
|
+
<svg
|
|
8
|
+
width={size}
|
|
9
|
+
height={size}
|
|
10
|
+
viewBox="0 0 16 16"
|
|
11
|
+
fill="none"
|
|
12
|
+
xmlns="http://www.w3.org/2000/svg"
|
|
13
|
+
aria-hidden
|
|
14
|
+
>
|
|
15
|
+
<path
|
|
16
|
+
d={SUN_PATH}
|
|
17
|
+
stroke={color}
|
|
18
|
+
strokeWidth={strokeWidth}
|
|
19
|
+
strokeLinecap="round"
|
|
20
|
+
strokeLinejoin="round"
|
|
21
|
+
/>
|
|
22
|
+
</svg>
|
|
23
|
+
);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export { SUN_PATH } from "./sunPath";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { SunIcon, SUN_PATH } from "./SunIcon";
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
export const SUN_PATH =
|
|
2
|
+
"M8 1.33333V2.66667M8 13.3333V14.6667M1.33333 8H2.66667M13.3333 8H14.6667M3.28667 3.28667L4.22667 4.22667M11.7733 11.7733L12.7133 12.7133M12.7133 3.28667L11.7733 4.22667M4.22667 11.7733L3.28667 12.7133M10.6667 8C10.6667 9.47276 9.47276 10.6667 8 10.6667C6.52724 10.6667 5.33333 9.47276 5.33333 8C5.33333 6.52724 6.52724 5.33333 8 5.33333C9.47276 5.33333 10.6667 6.52724 10.6667 8Z";
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import Svg, { Path } from "react-native-svg";
|
|
2
|
+
import { colors } from "../../theme";
|
|
3
|
+
import type { IconProps } from "../types";
|
|
4
|
+
import { WASHER_PATHS } from "./washerPaths";
|
|
5
|
+
|
|
6
|
+
export function WasherIcon({ size = 20, color = colors.white, strokeWidth = 1.5 }: IconProps) {
|
|
7
|
+
return (
|
|
8
|
+
<Svg width={size} height={size} viewBox="0 0 20 20" fill="none">
|
|
9
|
+
{WASHER_PATHS.map((path, index) => {
|
|
10
|
+
const filled = path.fill === true;
|
|
11
|
+
return (
|
|
12
|
+
<Path
|
|
13
|
+
key={`washer-${index}`}
|
|
14
|
+
d={path.d}
|
|
15
|
+
fill={filled ? color : "none"}
|
|
16
|
+
stroke={filled ? undefined : color}
|
|
17
|
+
strokeWidth={filled ? undefined : strokeWidth}
|
|
18
|
+
/>
|
|
19
|
+
);
|
|
20
|
+
})}
|
|
21
|
+
</Svg>
|
|
22
|
+
);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export { WASHER_PATHS } from "./washerPaths";
|