@flightlesslabs/dodo-ui 0.3.0 → 0.4.0

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.
Files changed (46) hide show
  1. package/dist/index.d.ts +9 -0
  2. package/dist/index.js +8 -0
  3. package/dist/stories/components/Form/Button/Button.svelte +4 -1
  4. package/dist/stories/components/Form/Button/Button.svelte.d.ts +4 -2
  5. package/dist/stories/components/Form/FormControl/FormControl.stories.svelte +27 -0
  6. package/dist/stories/components/Form/FormControl/FormControl.stories.svelte.d.ts +19 -0
  7. package/dist/stories/components/Form/FormControl/FormControl.svelte +34 -0
  8. package/dist/stories/components/Form/FormControl/FormControl.svelte.d.ts +20 -0
  9. package/dist/stories/components/Form/Label/Label.stories.svelte +21 -0
  10. package/dist/stories/components/Form/Label/Label.stories.svelte.d.ts +19 -0
  11. package/dist/stories/components/Form/Label/Label.svelte +19 -0
  12. package/dist/stories/components/Form/Label/Label.svelte.d.ts +18 -0
  13. package/dist/stories/components/Form/Message/Message.stories.svelte +46 -0
  14. package/dist/stories/components/Form/Message/Message.stories.svelte.d.ts +19 -0
  15. package/dist/stories/components/Form/Message/Message.svelte +39 -0
  16. package/dist/stories/components/Form/Message/Message.svelte.d.ts +17 -0
  17. package/dist/stories/components/Form/PasswordInput/PasswordInput.stories.svelte +17 -1
  18. package/dist/stories/components/Form/PasswordInput/PasswordInput.svelte +11 -34
  19. package/dist/stories/components/Form/PasswordInput/PasswordInput.svelte.d.ts +8 -4
  20. package/dist/stories/components/Form/TextInput/TextInput.stories.svelte +2 -0
  21. package/dist/stories/components/Form/TextInput/TextInput.svelte +3 -1
  22. package/dist/stories/components/Form/TextInput/TextInput.svelte.d.ts +6 -2
  23. package/dist/stories/developer tools/Intro.mdx +7 -0
  24. package/dist/stories/developer tools/components/UtilityButton/Size/Size.stories.svelte +27 -0
  25. package/dist/stories/developer tools/components/UtilityButton/Size/Size.stories.svelte.d.ts +26 -0
  26. package/dist/stories/developer tools/components/UtilityButton/UtilityButton.stories.svelte +29 -0
  27. package/dist/stories/developer tools/components/UtilityButton/UtilityButton.stories.svelte.d.ts +21 -0
  28. package/dist/stories/developer tools/components/UtilityButton/UtilityButton.svelte +79 -0
  29. package/dist/stories/developer tools/components/UtilityButton/UtilityButton.svelte.d.ts +26 -0
  30. package/package.json +30 -30
  31. package/src/lib/index.ts +13 -0
  32. package/src/lib/stories/components/Form/Button/Button.svelte +8 -2
  33. package/src/lib/stories/components/Form/FormControl/FormControl.stories.svelte +29 -0
  34. package/src/lib/stories/components/Form/FormControl/FormControl.svelte +67 -0
  35. package/src/lib/stories/components/Form/Label/Label.stories.svelte +23 -0
  36. package/src/lib/stories/components/Form/Label/Label.svelte +45 -0
  37. package/src/lib/stories/components/Form/Message/Message.stories.svelte +48 -0
  38. package/src/lib/stories/components/Form/Message/Message.svelte +71 -0
  39. package/src/lib/stories/components/Form/PasswordInput/PasswordInput.stories.svelte +17 -1
  40. package/src/lib/stories/components/Form/PasswordInput/PasswordInput.svelte +22 -45
  41. package/src/lib/stories/components/Form/TextInput/TextInput.stories.svelte +2 -0
  42. package/src/lib/stories/components/Form/TextInput/TextInput.svelte +9 -1
  43. package/src/lib/stories/developer tools/Intro.mdx +7 -0
  44. package/src/lib/stories/developer tools/components/UtilityButton/Size/Size.stories.svelte +27 -0
  45. package/src/lib/stories/developer tools/components/UtilityButton/UtilityButton.stories.svelte +33 -0
  46. package/src/lib/stories/developer tools/components/UtilityButton/UtilityButton.svelte +128 -0
@@ -2,6 +2,7 @@
2
2
  import { defineMeta } from '@storybook/addon-svelte-csf';
3
3
  import PasswordInput from './PasswordInput.svelte';
4
4
  import type { StoryBookArgTypes } from '$lib/storybook-types.js';
5
+ import Icon from '@iconify/svelte';
5
6
 
6
7
  export const storyPasswordInputArgTypes: StoryBookArgTypes = {
7
8
  roundness: {
@@ -38,4 +39,19 @@
38
39
  <Story name="No toggle" args={{ passwordToggle: false }} />
39
40
 
40
41
  <!-- Show Password by default -->
41
- <Story name="Show Password" args={{ defaultPasswordToggleState: true }} />
42
+ <Story name="Show Password" args={{ passwordToggleState: true }} />
43
+
44
+ <Story name="Read only" args={{ readonly: true }} />
45
+
46
+ <!-- Show Password by default -->
47
+ <Story name="Custom toggle icon">
48
+ <PasswordInput value="Hello world!">
49
+ {#snippet customPasswordToggleIcon(toggle)}
50
+ {#if toggle}
51
+ <Icon icon="mingcute:eye-close-line" width="24" height="24" />
52
+ {:else}
53
+ <Icon icon="mingcute:eye-2-line" width="24" height="24" />
54
+ {/if}
55
+ {/snippet}
56
+ </PasswordInput>
57
+ </Story>
@@ -16,16 +16,19 @@
16
16
  } from 'svelte/elements';
17
17
  import type { TextInputFocusEvent, TextInputRoundness } from '../TextInput/TextInput.svelte';
18
18
  import Icon from '@iconify/svelte';
19
+ import UtilityButton from '$lib/stories/developer tools/components/UtilityButton/UtilityButton.svelte';
19
20
 
20
21
  interface PasswordInputProps {
21
22
  /** How large should the button be? */
22
23
  size?: ComponentSize;
24
+ /** Input ref */
25
+ ref?: HTMLInputElement;
23
26
  /** Toggle Password */
24
27
  passwordToggle?: boolean;
25
28
  /** Default Password Toggle State */
26
- defaultPasswordToggleState?: boolean;
29
+ passwordToggleState?: boolean;
27
30
  /** Toggle Password Icon */
28
- passwordToggleIcon?: Snippet;
31
+ customPasswordToggleIcon?: (toggle: boolean) => Snippet;
29
32
  /** How round should the border radius be? */
30
33
  roundness?: TextInputRoundness;
31
34
  /** Add a border around the button. Default True */
@@ -34,8 +37,10 @@
34
37
  value?: string;
35
38
  /** How round should the border radius be? */
36
39
  placeholder?: string;
37
- /** Button disabled state */
40
+ /** disabled state */
38
41
  disabled?: boolean;
42
+ /** Read only ? */
43
+ readonly?: boolean;
39
44
  /** is there any associated Error ? */
40
45
  error?: boolean;
41
46
  /** Name */
@@ -83,17 +88,22 @@
83
88
  oncut,
84
89
  before,
85
90
  after,
86
- passwordToggleIcon,
91
+ customPasswordToggleIcon,
87
92
  error = false,
88
93
  passwordToggle = true,
89
- defaultPasswordToggleState = false,
94
+ passwordToggleState = $bindable<boolean>(),
90
95
  value = $bindable<string>(),
91
96
  placeholder,
92
97
  ontoggle,
98
+ ref = $bindable<HTMLInputElement>(),
99
+ readonly = false,
93
100
  }: PasswordInputProps = $props();
94
101
 
95
102
  let focused: boolean = $state(false);
96
- let toggle: boolean = $state(defaultPasswordToggleState);
103
+ let toggle: boolean = $state(passwordToggleState);
104
+
105
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
106
+ let customPasswordToggleIconTyped = customPasswordToggleIcon as any;
97
107
 
98
108
  function onfocusMod(e: TextInputFocusEvent) {
99
109
  focused = true;
@@ -152,18 +162,20 @@
152
162
  {oncut}
153
163
  {placeholder}
154
164
  bind:value
165
+ bind:this={ref}
166
+ {readonly}
155
167
  />
156
168
 
157
169
  {#if passwordToggle && !disabled}
158
- <button class="passwordToggle" title="Toggle password" onclick={ontoggleMod} class:toggle>
159
- {#if passwordToggleIcon}
160
- {@render passwordToggleIcon()}
170
+ <UtilityButton {size} title="Toggle password" class="passwordToggle" onclick={ontoggleMod}>
171
+ {#if customPasswordToggleIcon}
172
+ {@render customPasswordToggleIconTyped(toggle)}
161
173
  {:else if toggle}
162
174
  <Icon icon="mdi:eye-off" width="24" height="24" />
163
175
  {:else}
164
176
  <Icon icon="mdi:eye" width="24" height="24" />
165
177
  {/if}
166
- </button>
178
+ </UtilityButton>
167
179
  {/if}
168
180
 
169
181
  {#if after}
@@ -181,8 +193,6 @@
181
193
 
182
194
  --dodo-ui-PasswordInput-disabled-color: var(--dodo-color-default-400);
183
195
  --dodo-ui-PasswordInput-disabled-bg: var(--dodo-color-default-200);
184
-
185
- --dodo-ui-PasswordInput-ToggleButton-hover: var(--dodo-color-primary-700);
186
196
  }
187
197
 
188
198
  :global(.dodo-theme--dark) {
@@ -192,8 +202,6 @@
192
202
 
193
203
  --dodo-ui-PasswordInput-disabled-bg: var(--dodo-color-default-100);
194
204
  --dodo-ui-PasswordInput-disabled-color: var(--dodo-color-default-500);
195
-
196
- --dodo-ui-PasswordInput-ToggleButton-hover: var(--dodo-color-primary-600);
197
205
  }
198
206
 
199
207
  .dodo-ui-PasswordInput {
@@ -270,10 +278,6 @@
270
278
  margin-left: -4px;
271
279
  }
272
280
  }
273
-
274
- .passwordToggle {
275
- width: var(--dodo-ui-element-height-normal);
276
- }
277
281
  }
278
282
 
279
283
  &--small {
@@ -294,10 +298,6 @@
294
298
  margin-left: -2px;
295
299
  }
296
300
  }
297
-
298
- .passwordToggle {
299
- width: var(--dodo-ui-element-height-small);
300
- }
301
301
  }
302
302
 
303
303
  &--large {
@@ -318,10 +318,6 @@
318
318
  margin-left: -4px;
319
319
  }
320
320
  }
321
-
322
- .passwordToggle {
323
- width: var(--dodo-ui-element-height-large);
324
- }
325
321
  }
326
322
  }
327
323
 
@@ -338,24 +334,5 @@
338
334
  border-radius: var(--dodo-ui-element-roundness-3x);
339
335
  }
340
336
  }
341
-
342
- .passwordToggle {
343
- background-color: transparent;
344
- outline: 0;
345
- border: 0;
346
- display: inline-flex;
347
- justify-content: center;
348
- align-items: center;
349
- height: 100%;
350
- cursor: pointer;
351
- padding: 0;
352
- margin-right: 4px;
353
- color: var(--dodo-color-default-700);
354
- transition: all 150ms;
355
-
356
- &:hover {
357
- color: var(--dodo-ui-PasswordInput-ToggleButton-hover);
358
- }
359
- }
360
337
  }
361
338
  </style>
@@ -37,3 +37,5 @@
37
37
  <Story name="Error" args={{ error: true }} />
38
38
 
39
39
  <Story name="Disabled" args={{ disabled: true }} />
40
+
41
+ <Story name="Read only" args={{ readonly: true }} />
@@ -24,6 +24,8 @@
24
24
  interface TextInputProps {
25
25
  /** Input type? */
26
26
  type?: TextInputType;
27
+ /** Input ref */
28
+ ref?: HTMLInputElement;
27
29
  /** How large should the button be? */
28
30
  size?: ComponentSize;
29
31
  /** How round should the border radius be? */
@@ -34,8 +36,10 @@
34
36
  value?: string;
35
37
  /** How round should the border radius be? */
36
38
  placeholder?: string;
37
- /** Button disabled state */
39
+ /** disabled state */
38
40
  disabled?: boolean;
41
+ /** Read only ? */
42
+ readonly?: boolean;
39
43
  /** is there any associated Error ? */
40
44
  error?: boolean;
41
45
  /** Name */
@@ -85,6 +89,8 @@
85
89
  error = false,
86
90
  value = $bindable<string>(),
87
91
  placeholder,
92
+ ref = $bindable<HTMLInputElement>(),
93
+ readonly = false,
88
94
  }: TextInputProps = $props();
89
95
 
90
96
  let focused: boolean = $state(false);
@@ -131,7 +137,9 @@
131
137
  {oncopy}
132
138
  {oncut}
133
139
  {placeholder}
140
+ {readonly}
134
141
  bind:value
142
+ bind:this={ref}
135
143
  />
136
144
  {#if after}
137
145
  <span class="content--after">
@@ -0,0 +1,7 @@
1
+ # Developer Tools
2
+
3
+ A set of components and tools used internally in dodo-ui.
4
+
5
+ ## Explore More
6
+
7
+ - [Utility Button](?path=/docs/developer-tools-components-utilitybutton--docs)
@@ -0,0 +1,27 @@
1
+ <script module>
2
+ import { defineMeta } from '@storybook/addon-svelte-csf';
3
+ import { fn } from '@storybook/test';
4
+ import UtilityButton from '../UtilityButton.svelte';
5
+ import { storyUtilityButtonArgTypes } from '../UtilityButton.stories.svelte';
6
+ import Icon from '@iconify/svelte';
7
+
8
+ // More on how to set up stories at: https://storybook.js.org/docs/writing-stories
9
+ const { Story } = defineMeta({
10
+ component: UtilityButton,
11
+ tags: ['autodocs'],
12
+ argTypes: storyUtilityButtonArgTypes,
13
+ args: {
14
+ onclick: fn(),
15
+ },
16
+ });
17
+ </script>
18
+
19
+ <Story name="Normal" args={{ disabled: false }}>
20
+ <UtilityButton><Icon icon="mdi:eye" width="24" height="24" /></UtilityButton>
21
+ </Story>
22
+ <Story name="Small" args={{ size: 'small' }}>
23
+ <UtilityButton size="small"><Icon icon="mdi:eye" width="22" height="22" /></UtilityButton>
24
+ </Story>
25
+ <Story name="Large" args={{ size: 'large' }}>
26
+ <UtilityButton size="large"><Icon icon="mdi:eye" width="28" height="28" /></UtilityButton>
27
+ </Story>
@@ -0,0 +1,33 @@
1
+ <script module lang="ts">
2
+ import { defineMeta } from '@storybook/addon-svelte-csf';
3
+ import UtilityButton from './UtilityButton.svelte';
4
+ import type { StoryBookArgTypes } from '$lib/storybook-types.js';
5
+ import Icon from '@iconify/svelte';
6
+ import { fn } from '@storybook/test';
7
+
8
+ export const storyUtilityButtonArgTypes: StoryBookArgTypes = {
9
+ size: {
10
+ control: { type: 'select' },
11
+ options: ['normal', 'small', 'large'],
12
+ },
13
+ };
14
+
15
+ // More on how to set up stories at: https://storybook.js.org/docs/writing-stories
16
+ const { Story } = defineMeta({
17
+ component: UtilityButton,
18
+ tags: ['autodocs'],
19
+ argTypes: storyUtilityButtonArgTypes,
20
+ args: {
21
+ onclick: fn(),
22
+ },
23
+ });
24
+ </script>
25
+
26
+ <!-- Button with default style -->
27
+ <Story name="Default">
28
+ <UtilityButton><Icon icon="mdi:eye" width="24" height="24" /></UtilityButton>
29
+ </Story>
30
+
31
+ <Story name="Disabled" args={{ disabled: true }}>
32
+ <UtilityButton disabled><Icon icon="mdi:eye" width="24" height="24" /></UtilityButton>
33
+ </Story>
@@ -0,0 +1,128 @@
1
+ <script lang="ts">
2
+ import type { ComponentSize } from '$lib/types.js';
3
+ import type { Snippet } from 'svelte';
4
+ import type { MouseEventHandler } from 'svelte/elements';
5
+
6
+ interface UtilityButtonProps {
7
+ /** Button contents goes here*/
8
+ children?: Snippet;
9
+ /** Button ref */
10
+ ref?: HTMLButtonElement;
11
+ /** How large should the button be? */
12
+ size?: ComponentSize;
13
+ /** Button disabled state */
14
+ disabled?: boolean;
15
+ /** Name */
16
+ name?: string;
17
+ /** Id */
18
+ id?: string;
19
+ /** Title (for tooltip) */
20
+ title?: string;
21
+ /** Custom css class*/
22
+ class?: string;
23
+ /** The onclick event handler */
24
+ onclick?: MouseEventHandler<HTMLButtonElement>;
25
+ }
26
+
27
+ let {
28
+ children,
29
+ size = 'normal',
30
+ name,
31
+ id,
32
+ title,
33
+ class: className = '',
34
+ disabled = false,
35
+ onclick,
36
+ ref = $bindable<HTMLButtonElement>(),
37
+ }: UtilityButtonProps = $props();
38
+ </script>
39
+
40
+ <button
41
+ class={['dodo-ui-UtilityButton', `size--${size}`, className].join(' ')}
42
+ {name}
43
+ {id}
44
+ {title}
45
+ {disabled}
46
+ {onclick}
47
+ bind:this={ref}
48
+ >
49
+ {#if children}
50
+ {@render children()}
51
+ {/if}
52
+ </button>
53
+
54
+ <style lang="scss">
55
+ :global(:root) {
56
+ --dodo-ui-UtilityButton-hover: var(--dodo-color-primary-600);
57
+ --dodo-ui-UtilityButton-active: var(--dodo-color-primary-600);
58
+
59
+ --dodo-ui-UtilityButton-disabled-color: var(--dodo-color-default-400);
60
+ }
61
+
62
+ :global(.dodo-theme--dark) {
63
+ --dodo-ui-UtilityButton-hover: var(--dodo-color-primary-600);
64
+ --dodo-ui-UtilityButton-active: var(--dodo-color-primary-600);
65
+
66
+ --dodo-ui-UtilityButton-disabled-color: var(--dodo-color-default-500);
67
+ }
68
+
69
+ .dodo-ui-UtilityButton {
70
+ cursor: pointer;
71
+ outline: none;
72
+ transition: all 150ms;
73
+ text-decoration: none;
74
+ margin: 0;
75
+ display: inline-flex;
76
+ justify-content: center;
77
+ align-items: center;
78
+ font-family: inherit;
79
+ background-color: transparent;
80
+ border: 0;
81
+ outline: 0;
82
+ padding: 0;
83
+ color: var(--dodo-color-default-700);
84
+ border-radius: 50%;
85
+ font-family: inherit;
86
+
87
+ &:hover {
88
+ color: var(--dodo-ui-UtilityButton-hover);
89
+ }
90
+
91
+ &:active {
92
+ color: var(--dodo-ui-UtilityButton-active);
93
+ }
94
+
95
+ &.size {
96
+ &--normal {
97
+ height: var(--dodo-ui-element-height-normal);
98
+ width: var(--dodo-ui-element-height-normal);
99
+ font-size: 1rem;
100
+ }
101
+
102
+ &--small {
103
+ height: var(--dodo-ui-element-height-small);
104
+ width: var(--dodo-ui-element-height-small);
105
+ font-size: 0.9rem;
106
+ }
107
+
108
+ &--large {
109
+ height: var(--dodo-ui-element-height-large);
110
+ width: var(--dodo-ui-element-height-large);
111
+ font-size: 1.1rem;
112
+ }
113
+ }
114
+
115
+ &[disabled] {
116
+ cursor: initial;
117
+ color: var(--dodo-ui-UtilityButton-disabled-color);
118
+
119
+ &:hover {
120
+ color: var(--dodo-ui-UtilityButton-disabled-color);
121
+ }
122
+
123
+ &:active {
124
+ color: var(--dodo-ui-UtilityButton-disabled-color);
125
+ }
126
+ }
127
+ }
128
+ </style>