vueless 0.0.706 → 0.0.708

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/bin/constants.js CHANGED
@@ -10,7 +10,6 @@ export default {
10
10
  gray: "cool",
11
11
  darkMode: "auto",
12
12
  ring: 2,
13
- ringOffset: 2,
14
13
  ringOffsetColorLight: "#ffffff", // white
15
14
  ringOffsetColorDark: "#111827", // gray-900
16
15
  rounding: 8,
package/constants.js CHANGED
@@ -18,7 +18,6 @@ export const COLOR_MODE_KEY = "vl-color-mode";
18
18
  export const DEFAULT_BRAND_COLOR = GRAYSCALE_COLOR;
19
19
  export const DEFAULT_GRAY_COLOR = COOL_COLOR;
20
20
  export const DEFAULT_RING = 2; /* pixels */
21
- export const DEFAULT_RING_OFFSET = 2; /* pixels */
22
21
  export const DEFAULT_RING_OFFSET_COLOR_LIGHT = "#ffffff"; // white
23
22
  export const DEFAULT_RING_OFFSET_COLOR_DARK = "#111827"; // gray-900
24
23
  export const DEFAULT_ROUNDING = 8; /* pixels */
@@ -173,7 +172,6 @@ export const TAILWIND_MERGE_EXTENSION = {
173
172
  },
174
173
  classGroups: {
175
174
  "ring-w": [{ ring: ["dynamic"] }],
176
- "ring-offset-w": [{ "ring-offset": ["dynamic"] }],
177
175
  "ring-offset-color": [{ "ring-offset": ["color-dynamic"] }],
178
176
  "font-size": [{ text: ["2xs"] }],
179
177
  rounded: [{ rounded: ["dynamic", "dynamic-sm", "dynamic-lg", "inherit"] }],
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vueless",
3
- "version": "0.0.706",
3
+ "version": "0.0.708",
4
4
  "license": "MIT",
5
5
  "description": "Vue Styleless UI Component Library, powered by Tailwind CSS.",
6
6
  "keywords": [
@@ -13,7 +13,6 @@ import {
13
13
  TAILWIND_COLORS,
14
14
  DEFAULT_ROUNDING,
15
15
  DEFAULT_RING,
16
- DEFAULT_RING_OFFSET,
17
16
  DEFAULT_RING_OFFSET_COLOR_LIGHT,
18
17
  DEFAULT_BRAND_COLOR,
19
18
  DEFAULT_GRAY_COLOR,
@@ -95,9 +94,6 @@ export const vuelessTailwindConfig = {
95
94
  ringWidth: {
96
95
  dynamic: "var(--vl-ring)",
97
96
  },
98
- ringOffsetWidth: {
99
- dynamic: "var(--vl-ring-offset)",
100
- },
101
97
  ringOffsetColor: {
102
98
  dynamic: twColorWithOpacity("--vl-ring-offset-color"),
103
99
  },
@@ -106,7 +102,6 @@ export const vuelessTailwindConfig = {
106
102
  themeReplacements: {
107
103
  /* eslint-disable prettier/prettier */
108
104
  "var(--vl-ring)": globalSettings.ring || DEFAULT_RING,
109
- "var(--vl-ring-offset)": globalSettings.ringOffset || DEFAULT_RING_OFFSET,
110
105
  "var(--vl-ring-offset-color)": globalSettings.ringOffsetColorLight || DEFAULT_RING_OFFSET_COLOR_LIGHT,
111
106
  "var(--vl-rounding-sm)": globalSettings.roundingSm || (globalSettings.ring || DEFAULT_ROUNDING) / 2,
112
107
  "var(--vl-rounding)": globalSettings.ring || DEFAULT_ROUNDING,
package/types.ts CHANGED
@@ -100,11 +100,6 @@ export interface ThemeConfig {
100
100
  */
101
101
  ring?: number;
102
102
 
103
- /**
104
- * Default components ring offset width.
105
- */
106
- ringOffset?: number;
107
-
108
103
  /**
109
104
  * Default components ring color for light theme.
110
105
  */
@@ -345,7 +340,6 @@ export interface TailwindColorShades {
345
340
 
346
341
  export interface VuelessCssVariables {
347
342
  "--vl-ring": string;
348
- "--vl-ring-offset": string;
349
343
  "--vl-ring-offset-color": string;
350
344
  "--vl-rounding-sm": string;
351
345
  "--vl-rounding": string;
@@ -3,7 +3,7 @@ export default /*tw*/ {
3
3
  base: `
4
4
  flex items-center justify-center font-medium !leading-snug whitespace-nowrap
5
5
  border border-transparent outline-none transition cursor-pointer
6
- focus-visible:ring-dynamic focus-visible:ring-offset-dynamic
6
+ focus-visible:ring-dynamic focus-visible:ring-offset-2
7
7
  focus-visible:ring-{color}-600 dark:focus-visible:ring-{color}-400
8
8
  disabled:cursor-not-allowed disabled:ring-0 disabled:ring-offset-0
9
9
  `,
@@ -7,7 +7,7 @@ export default /*tw*/ {
7
7
  active:border-{color}-600 active:bg-{color}-200
8
8
  focus:ring-0 focus:ring-offset-0
9
9
  checked:text-{color}-600
10
- focus-visible:ring-{color}-600 focus-visible:ring-dynamic focus-visible:ring-offset-dynamic
10
+ focus-visible:ring-{color}-600 focus-visible:ring-dynamic focus-visible:ring-offset-2
11
11
  disabled:border-gray-300 disabled:bg-gray-100 disabled:cursor-not-allowed
12
12
  `,
13
13
  variants: {
@@ -4,7 +4,7 @@ export default /*tw*/ {
4
4
  datepickerInputActive: {
5
5
  base: "{UInput} {>datepickerInput}",
6
6
  wrapper: {
7
- base: "ring-dynamic ring-offset-dynamic ring-brand-700/15 border-brand-500 hover:border-brand-500",
7
+ base: "ring-dynamic ring-offset-2 ring-brand-700/15 border-brand-500 hover:border-brand-500",
8
8
  variants: {
9
9
  error: {
10
10
  true: "ring-red-700/15 border-red-500 hover:border-red-500",
@@ -43,11 +43,7 @@ const DefaultTemplate: StoryFn<UInputArgs> = (args: UInputArgs) => ({
43
43
  components: { UInput, UIcon },
44
44
  setup() {
45
45
  const slots = getSlotNames(UInput.__name);
46
- const errorMessage = computed(() =>
47
- args.modelValue === "" && args.error !== ""
48
- ? "This field is required. Please enter a value."
49
- : "",
50
- );
46
+ const errorMessage = computed(() => (args.modelValue === "" ? args.error : ""));
51
47
 
52
48
  return { args, slots, errorMessage };
53
49
  },
@@ -127,13 +123,13 @@ export const Default = DefaultTemplate.bind({});
127
123
  Default.args = {};
128
124
 
129
125
  export const Placeholder = DefaultTemplate.bind({});
130
- Placeholder.args = { modelValue: "", placeholder: "Type something here...", error: "" };
126
+ Placeholder.args = { modelValue: "", placeholder: "Type something here..." };
131
127
 
132
128
  export const Description = DefaultTemplate.bind({});
133
129
  Description.args = { description: "Provide additional details if necessary." };
134
130
 
135
131
  export const Error = DefaultTemplate.bind({});
136
- Error.args = { modelValue: "" };
132
+ Error.args = { error: "This field is required. Please enter a value." };
137
133
 
138
134
  export const Readonly = DefaultTemplate.bind({});
139
135
  Readonly.args = {
@@ -40,9 +40,7 @@ const DefaultTemplate: StoryFn<UInputRatingArgs> = (args: UInputRatingArgs) => (
40
40
  components: { UInputRating, UBadge },
41
41
  setup() {
42
42
  const slots = getSlotNames(UInputRating.__name);
43
- const errorMessage = computed(() =>
44
- !args.modelValue && args.error !== "" ? "Your review helps us improve our services." : "",
45
- );
43
+ const errorMessage = computed(() => (!args.modelValue ? args.error : ""));
46
44
 
47
45
  return { args, slots, errorMessage };
48
46
  },
@@ -87,7 +85,11 @@ export const Description = DefaultTemplate.bind({});
87
85
  Description.args = { description: "Your review helps us improve our services." };
88
86
 
89
87
  export const Error = DefaultTemplate.bind({});
90
- Error.args = { selectable: true, modelValue: NaN };
88
+ Error.args = {
89
+ selectable: true,
90
+ modelValue: 0,
91
+ error: "Please select a rating before submitting your review.",
92
+ };
91
93
 
92
94
  export const Disabled = DefaultTemplate.bind({});
93
95
  Disabled.args = { disabled: true };
@@ -43,11 +43,7 @@ const DefaultTemplate: StoryFn<UInputSearchArgs> = (args: UInputSearchArgs) => (
43
43
  components: { UInputSearch, UButton, UIcon },
44
44
  setup() {
45
45
  const slots = getSlotNames(UInputSearch.__name);
46
- const errorMessage = computed(() =>
47
- args.modelValue === "" && args.error !== ""
48
- ? "This field is required. Please enter a value."
49
- : "",
50
- );
46
+ const errorMessage = computed(() => (args.modelValue === "" ? args.error : ""));
51
47
 
52
48
  return { args, slots, errorMessage };
53
49
  },
@@ -102,13 +98,13 @@ export const Label = DefaultTemplate.bind({});
102
98
  Label.args = { label: "Search for product or brand" };
103
99
 
104
100
  export const Placeholder = DefaultTemplate.bind({});
105
- Placeholder.args = { modelValue: "", placeholder: "Type to search...", error: "" };
101
+ Placeholder.args = { modelValue: "", placeholder: "Type to search..." };
106
102
 
107
103
  export const Description = DefaultTemplate.bind({});
108
104
  Description.args = { description: "Search for additional details." };
109
105
 
110
106
  export const Error = DefaultTemplate.bind({});
111
- Error.args = { modelValue: "" };
107
+ Error.args = { error: "This field is required. Please enter a value." };
112
108
 
113
109
  export const Disabled = DefaultTemplate.bind({});
114
110
  Disabled.args = { disabled: true };
@@ -7,7 +7,7 @@ export default /*tw*/ {
7
7
  active:border-{color}-600 active:bg-{color}-200
8
8
  focus:ring-0 focus:ring-offset-0
9
9
  checked:text-{color}-600
10
- focus-visible:ring-{color}-600 focus-visible:ring-dynamic focus-visible:ring-offset-dynamic
10
+ focus-visible:ring-{color}-600 focus-visible:ring-dynamic focus-visible:ring-offset-2
11
11
  disabled:border-gray-300 disabled:bg-gray-100 disabled:cursor-not-allowed
12
12
  disabled:checked:bg-gray-400 disabled:checked:border-transparent
13
13
  `,
@@ -3,7 +3,7 @@ export default /*tw*/ {
3
3
  wrapper: {
4
4
  base: `
5
5
  flex items-center p-0.5 relative rounded-full cursor-pointer transition
6
- focus-visible:ring-dynamic focus-visible:ring-offset-dynamic ring-{color}-600 outline-0
6
+ focus-visible:ring-dynamic focus-visible:ring-offset-2 ring-{color}-600 outline-0
7
7
  `,
8
8
  variants: {
9
9
  size: {
@@ -99,7 +99,7 @@ function getNewRowCount() {
99
99
  function onEnter() {
100
100
  const newRowCount = getNewRowCount();
101
101
 
102
- if (newRowCount > currentRows.value) {
102
+ if (newRowCount > currentRows.value && !props.readonly) {
103
103
  currentRows.value = newRowCount;
104
104
  }
105
105
  }
@@ -107,7 +107,7 @@ function onEnter() {
107
107
  function onBackspace() {
108
108
  const newRowCount = getNewRowCount() - 1;
109
109
 
110
- if (newRowCount < currentRows.value) {
110
+ if (newRowCount < currentRows.value && !props.readonly) {
111
111
  currentRows.value = newRowCount;
112
112
  }
113
113
  }
@@ -1,3 +1,4 @@
1
+ import { ref, computed } from "vue";
1
2
  import {
2
3
  getArgTypes,
3
4
  getSlotNames,
@@ -8,6 +9,9 @@ import {
8
9
  import UTextarea from "../../ui.form-textarea/UTextarea.vue";
9
10
  import UIcon from "../../ui.image-icon/UIcon.vue";
10
11
  import UCol from "../../ui.container-col/UCol.vue";
12
+ import URow from "../../ui.container-row/URow.vue";
13
+ import UAvatar from "../../ui.image-avatar/UAvatar.vue";
14
+ import tooltip from "../../directives/tooltip/vTooltip.ts";
11
15
 
12
16
  import type { Meta, StoryFn } from "@storybook/vue3";
13
17
  import type { Props } from "../types.ts";
@@ -22,7 +26,9 @@ export default {
22
26
  title: "Form Inputs & Controls / Textarea",
23
27
  component: UTextarea,
24
28
  args: {
25
- label: "Label",
29
+ label: "Your message",
30
+ modelValue:
31
+ "Hi there! I'd like to learn more about your services. When you have a moment, could you share some details?",
26
32
  },
27
33
  argTypes: {
28
34
  ...getArgTypes(UTextarea.__name),
@@ -38,11 +44,17 @@ const DefaultTemplate: StoryFn<UTextareaArgs> = (args: UTextareaArgs) => ({
38
44
  components: { UTextarea, UIcon },
39
45
  setup() {
40
46
  const slots = getSlotNames(UTextarea.__name);
47
+ const errorMessage = computed(() => (args.modelValue === "" ? args.error : ""));
41
48
 
42
- return { args, slots };
49
+ return { args, slots, errorMessage };
43
50
  },
44
51
  template: `
45
- <UTextarea v-bind="args" v-model="args.modelValue">
52
+ <UTextarea
53
+ v-bind="args"
54
+ v-model="args.modelValue"
55
+ :error="errorMessage"
56
+ class="max-w-96"
57
+ >
46
58
  ${args.slotTemplate || getSlotsFragment("")}
47
59
  </UTextarea>
48
60
  `,
@@ -51,18 +63,28 @@ const DefaultTemplate: StoryFn<UTextareaArgs> = (args: UTextareaArgs) => ({
51
63
  const EnumVariantTemplate: StoryFn<UTextareaArgs> = (args: UTextareaArgs, { argTypes }) => ({
52
64
  components: { UTextarea, UCol },
53
65
  setup() {
66
+ let filteredOptions = argTypes?.[args.enum]?.options;
67
+
68
+ if (args.enum === "labelAlign") {
69
+ filteredOptions = argTypes?.[args.enum]?.options?.filter(
70
+ (item) => item !== "right" && item !== "topWithDesc",
71
+ );
72
+ }
73
+
54
74
  return {
55
75
  args,
56
- options: argTypes?.[args.enum]?.options,
76
+ filteredOptions,
57
77
  };
58
78
  },
59
79
  template: `
60
80
  <UCol>
61
- <div class="w-1/3" v-for="(option, index) in options" :key="index">
81
+ <div class="w-1/3" v-for="(option, index) in filteredOptions" :key="index">
62
82
  <UTextarea
63
83
  v-bind="args"
64
84
  :[args.enum]="option"
65
- :label="option"
85
+ :description="option"
86
+ rows="3"
87
+ class="max-w-96"
66
88
  />
67
89
  </div>
68
90
  </UCol>
@@ -72,53 +94,75 @@ const EnumVariantTemplate: StoryFn<UTextareaArgs> = (args: UTextareaArgs, { argT
72
94
  export const Default = DefaultTemplate.bind({});
73
95
  Default.args = {};
74
96
 
75
- export const LabelPlacement = EnumVariantTemplate.bind({});
76
- LabelPlacement.args = { enum: "labelAlign" };
77
-
78
97
  export const Placeholder = DefaultTemplate.bind({});
79
- Placeholder.args = { placeholder: "some placeholder text" };
98
+ Placeholder.args = { modelValue: "", placeholder: "Enter text here..." };
99
+
100
+ export const Description = DefaultTemplate.bind({});
101
+ Description.args = { description: "Provide additional details in this field." };
102
+
103
+ export const Error = DefaultTemplate.bind({});
104
+ Error.args = { modelValue: "", error: "This field is required. Please enter a value." };
80
105
 
81
106
  export const Disabled = DefaultTemplate.bind({});
82
107
  Disabled.args = { disabled: true };
83
108
 
84
- export const Error = DefaultTemplate.bind({});
85
- Error.args = { error: "some error text" };
109
+ export const LabelPlacement = EnumVariantTemplate.bind({});
110
+ LabelPlacement.args = { enum: "labelAlign" };
86
111
 
87
- export const Description = DefaultTemplate.bind({});
88
- Description.args = { description: "some description text" };
112
+ export const Sizes = EnumVariantTemplate.bind({});
113
+ Sizes.args = { enum: "size" };
89
114
 
90
- export const Rows1 = DefaultTemplate.bind({});
91
- Rows1.args = { rows: "1" };
115
+ export const Resizable = DefaultTemplate.bind({});
116
+ Resizable.args = { resizable: true };
117
+
118
+ export const RowsNumber = DefaultTemplate.bind({});
119
+ RowsNumber.args = { rows: "6" };
120
+ RowsNumber.parameters = {
121
+ docs: {
122
+ description: {
123
+ story: "You can set the number of visible rows via the `rows` prop.",
124
+ },
125
+ },
126
+ };
92
127
 
93
128
  export const Readonly = DefaultTemplate.bind({});
94
- Readonly.args = { readonly: true, modelValue: "some value for read" };
129
+ Readonly.args = { readonly: true, modelValue: "Meeting scheduled for Monday at 10 AM." };
95
130
 
96
131
  export const NoAutocomplete = DefaultTemplate.bind({});
97
- NoAutocomplete.args = { noAutocomplete: true };
98
-
99
- export const Sizes = EnumVariantTemplate.bind({});
100
- Sizes.args = { enum: "size" };
101
-
102
- export const SlotLeft = DefaultTemplate.bind({});
103
- SlotLeft.args = {
104
- slotTemplate: `
105
- <template #left>
106
- <UIcon
107
- name="star"
108
- color="black"
109
- />
110
- </template>
111
- `,
132
+ NoAutocomplete.args = {
133
+ noAutocomplete: true,
134
+ modelValue: "",
135
+ placeholder: "Try typing something here...",
136
+ };
137
+ NoAutocomplete.parameters = {
138
+ docs: {
139
+ description: {
140
+ story: "Disable browser's autocomplete.",
141
+ },
142
+ },
112
143
  };
113
144
 
114
- export const SlotRight = DefaultTemplate.bind({});
115
- SlotRight.args = {
116
- slotTemplate: `
117
- <template #right>
118
- <UIcon
119
- name="star"
120
- color="black"
121
- />
122
- </template>
145
+ export const Slots: StoryFn<UTextareaArgs> = (args) => ({
146
+ components: { UTextarea, URow, UIcon, UAvatar },
147
+ directives: { tooltip },
148
+ setup() {
149
+ const switchModel = ref(false);
150
+
151
+ return { args, switchModel };
152
+ },
153
+ template: `
154
+ <URow no-mobile>
155
+ <UTextarea v-bind="args">
156
+ <template #left>
157
+ <UAvatar />
158
+ </template>
159
+ </UTextarea>
160
+
161
+ <UTextarea v-bind="args">
162
+ <template #right>
163
+ <UIcon name="send" color="green" v-tooltip="'Send message'" />
164
+ </template>
165
+ </UTextarea>
166
+ </URow>
123
167
  `,
124
- };
168
+ });
@@ -28,7 +28,7 @@ export interface Props {
28
28
  /**
29
29
  * Label placement.
30
30
  */
31
- labelAlign?: "top" | "topInside" | "topWithDesc" | "left" | "right";
31
+ labelAlign?: "topInside" | "top" | "topWithDesc" | "left" | "right";
32
32
 
33
33
  /**
34
34
  * Set description for component.
@@ -16,7 +16,7 @@ export default /*tw*/ {
16
16
  true: "rounded-full",
17
17
  },
18
18
  tabindex: {
19
- true: "cursor-pointer focus-visible:ring-dynamic focus-visible:ring-offset-dynamic focus-visible:ring-{color}-600",
19
+ true: "cursor-pointer focus-visible:ring-dynamic focus-visible:ring-offset-2 focus-visible:ring-{color}-600",
20
20
  },
21
21
  color: {
22
22
  grayscale: "focus-visible:ring-gray-900",
package/utils/theme.ts CHANGED
@@ -11,7 +11,6 @@ import {
11
11
  GRAYSCALE_COLOR,
12
12
  TAILWIND_COLORS,
13
13
  DEFAULT_RING,
14
- DEFAULT_RING_OFFSET,
15
14
  DEFAULT_ROUNDING,
16
15
  DEFAULT_BRAND_COLOR,
17
16
  DEFAULT_GRAY_COLOR,
@@ -42,7 +41,6 @@ declare interface RootCSSVariableOptions {
42
41
  brand: string;
43
42
  gray: string;
44
43
  ring: number;
45
- ringOffset: number;
46
44
  ringOffsetColorDark: string;
47
45
  ringOffsetColorLight: string;
48
46
  roundingSm: number;
@@ -158,7 +156,6 @@ export function setTheme(config: Config = {}) {
158
156
  config.gray ?? getSelectedGrayColor() ?? vuelessConfig.gray ?? DEFAULT_GRAY_COLOR;
159
157
 
160
158
  const ring = config.ring ?? vuelessConfig.ring ?? DEFAULT_RING;
161
- const ringOffset = config.ringOffset ?? vuelessConfig.ringOffset ?? DEFAULT_RING_OFFSET;
162
159
 
163
160
  const ringOffsetColorDark =
164
161
  config.ringOffsetColorDark ??
@@ -202,7 +199,6 @@ export function setTheme(config: Config = {}) {
202
199
  brand,
203
200
  gray,
204
201
  ring,
205
- ringOffset,
206
202
  ringOffsetColorDark,
207
203
  ringOffsetColorLight,
208
204
  roundingSm,
@@ -245,7 +241,6 @@ function setRootCSSVariables(options: RootCSSVariableOptions) {
245
241
  brand,
246
242
  gray,
247
243
  ring,
248
- ringOffset,
249
244
  ringOffsetColorDark,
250
245
  ringOffsetColorLight,
251
246
  roundingSm,
@@ -263,7 +258,6 @@ function setRootCSSVariables(options: RootCSSVariableOptions) {
263
258
  "--vl-rounding": `${Number(rounding) / PX_IN_REM}rem`,
264
259
  "--vl-rounding-lg": `${Number(roundingLg) / PX_IN_REM}rem`,
265
260
  "--vl-ring": `${Math.max(0, ring)}px`,
266
- "--vl-ring-offset": `${Math.max(0, ringOffset)}px`,
267
261
  "--vl-ring-offset-color": convertHexInRgb(defaultRingOffsetColor),
268
262
  "--vl-color-gray-default": convertHexInRgb(colors[gray]?.[defaultBrandShade]),
269
263
  "--vl-color-brand-default": convertHexInRgb(colors[brand]?.[defaultGrayShade]),