@weni/unnnic-system 3.2.8 → 3.2.9-alpha.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 (172) hide show
  1. package/dist/components/Accordion/Accordion.vue.d.ts +1 -1
  2. package/dist/components/Alert/Alert.vue.d.ts +18 -119
  3. package/dist/components/Alert/Alert.vue.d.ts.map +1 -1
  4. package/dist/components/Alert/Version1dot1.vue.d.ts +2 -38
  5. package/dist/components/Alert/Version1dot1.vue.d.ts.map +1 -1
  6. package/dist/components/AudioRecorder/AudioHandler.vue.d.ts +2 -2
  7. package/dist/components/AudioRecorder/AudioPlayer.vue.d.ts +1 -1
  8. package/dist/components/AudioRecorder/AudioRecorder.vue.d.ts +5 -5
  9. package/dist/components/AvatarIcon/AvatarIcon.vue.d.ts +2 -2
  10. package/dist/components/Banner/Banner.vue.d.ts +1 -1
  11. package/dist/components/Banner/InfoBanner.vue.d.ts +1 -1
  12. package/dist/components/Breadcrumb/Breadcrumb.vue.d.ts +1 -1
  13. package/dist/components/Button/Button.vue.d.ts +2 -2
  14. package/dist/components/Button/Button.vue.d.ts.map +1 -1
  15. package/dist/components/Button/ButtonIcon.vue.d.ts +1 -1
  16. package/dist/components/Button/types.d.ts +1 -1
  17. package/dist/components/Button/types.d.ts.map +1 -1
  18. package/dist/components/Card/AccountCard.vue.d.ts +3 -3
  19. package/dist/components/Card/BlankCard.vue.d.ts +1 -1
  20. package/dist/components/Card/Card.vue.d.ts +21 -21
  21. package/dist/components/Card/CardCompany.vue.d.ts +8 -8
  22. package/dist/components/Card/CardData.vue.d.ts +1 -1
  23. package/dist/components/Card/CardStatusesContainer.vue.d.ts +4 -4
  24. package/dist/components/Card/ContentCard.vue.d.ts +2 -2
  25. package/dist/components/Card/DashCard.vue.d.ts +4 -4
  26. package/dist/components/Card/DefaultCard.vue.d.ts +1 -1
  27. package/dist/components/Card/MarketplaceCard.vue.d.ts +2 -2
  28. package/dist/components/Card/SimpleCard.vue.d.ts +3 -3
  29. package/dist/components/Card/StatusCard.vue.d.ts +2 -2
  30. package/dist/components/Card/TitleCard.vue.d.ts +2 -2
  31. package/dist/components/CardImage/CardImage.vue.d.ts +8 -8
  32. package/dist/components/CardInformation/CardInformation.vue.d.ts +4 -4
  33. package/dist/components/CardProject/CardProject.vue.d.ts +3 -3
  34. package/dist/components/Carousel/Carousel.vue.d.ts +11 -11
  35. package/dist/components/Carousel/TagCarousel.vue.d.ts +9 -9
  36. package/dist/components/ChartBar/ChartBar.vue.d.ts +8 -8
  37. package/dist/components/ChartLine/ChartLine.vue.d.ts +1 -1
  38. package/dist/components/ChatText/ChatText.vue.d.ts +2 -2
  39. package/dist/components/ChatsContact/ChatsContact.vue.d.ts +15 -15
  40. package/dist/components/ChatsDashboardTagLive/ChatsDashboardTagLive.vue.d.ts +1 -1
  41. package/dist/components/ChatsHeader/ChatsHeader.vue.d.ts +1 -1
  42. package/dist/components/ChatsHeader/ChatsHeader.vue.d.ts.map +1 -1
  43. package/dist/components/ChatsMessage/ChatsMessage.vue.d.ts +5 -5
  44. package/dist/components/ChatsMessage/ChatsMessageStatusBackdrop.vue.d.ts +2 -2
  45. package/dist/components/ChatsNavbar/ChatsNavbar.vue.d.ts +1 -1
  46. package/dist/components/ChatsUserAvatar/ChatsUserAvatar.vue.d.ts +2 -2
  47. package/dist/components/Checkbox/Checkbox.vue.d.ts +3 -3
  48. package/dist/components/Comment/Comment.vue.d.ts +1 -1
  49. package/dist/components/DataArea/DataArea.vue.d.ts +2 -2
  50. package/dist/components/DataTable/index.vue.d.ts +1 -1
  51. package/dist/components/DataTable/index.vue.d.ts.map +1 -1
  52. package/dist/components/DateFilter/DateFilter.vue.d.ts +182 -27
  53. package/dist/components/DatePicker/DatePicker.vue.d.ts +8 -8
  54. package/dist/components/Drawer/Drawer.vue.d.ts +7 -7
  55. package/dist/components/Dropdown/Dropdown.vue.d.ts +1 -1
  56. package/dist/components/Dropdown/LanguageSelect.vue.d.ts +3 -3
  57. package/dist/components/Flag.vue.d.ts +2 -2
  58. package/dist/components/FormElement/FormElement.vue.d.ts +38 -32
  59. package/dist/components/FormElement/FormElement.vue.d.ts.map +1 -1
  60. package/dist/components/Icon.vue.d.ts +1 -1
  61. package/dist/components/IconLoading/IconLoading.vue.d.ts +1 -1
  62. package/dist/components/ImportCard/ImportCard.vue.d.ts +7 -7
  63. package/dist/components/Input/BaseInput.vue.d.ts +10 -1
  64. package/dist/components/Input/BaseInput.vue.d.ts.map +1 -1
  65. package/dist/components/Input/Input.vue.d.ts +182 -27
  66. package/dist/components/Input/Input.vue.d.ts.map +1 -1
  67. package/dist/components/Input/TextInput.vue.d.ts +31 -13
  68. package/dist/components/Input/TextInput.vue.d.ts.map +1 -1
  69. package/dist/components/InputDatePicker/InputDatePicker.vue.d.ts +192 -37
  70. package/dist/components/InputNext/InputNext.vue.d.ts +3 -3
  71. package/dist/components/Label/Label.vue.d.ts +9 -15
  72. package/dist/components/Label/Label.vue.d.ts.map +1 -1
  73. package/dist/components/Modal/Modal.vue.d.ts +2 -2
  74. package/dist/components/ModalDialog/ModalDialog.vue.d.ts +9 -9
  75. package/dist/components/ModalDialog/ModalDialog.vue.d.ts.map +1 -1
  76. package/dist/components/ModalNext/ModalNext.vue.d.ts +190 -35
  77. package/dist/components/ModalUpload/ModalUpload.vue.d.ts +14 -14
  78. package/dist/components/MoodRating/MoodRating.vue.d.ts +1 -1
  79. package/dist/components/MultiSelect/MultiSelect.vue.d.ts +7 -7
  80. package/dist/components/Pagination/Pagination.vue.d.ts +6 -6
  81. package/dist/components/ProgressBar/ProgressBar.vue.d.ts +1 -1
  82. package/dist/components/Radio/Radio.vue.d.ts +2 -2
  83. package/dist/components/SelectSmart/SelectSmart.vue.d.ts +45 -27
  84. package/dist/components/SelectSmart/SelectSmartMultipleHeader.vue.d.ts +8 -8
  85. package/dist/components/SelectSmart/SelectSmartOption.vue.d.ts +4 -4
  86. package/dist/components/SelectTime/index.vue.d.ts +31 -13
  87. package/dist/components/SkeletonLoading/skeletonTheme.vue.d.ts +1 -1
  88. package/dist/components/Slider/Slider.vue.d.ts +2 -2
  89. package/dist/components/StarRating/StarRating.vue.d.ts +1 -1
  90. package/dist/components/Switch/Switch.vue.d.ts +2 -2
  91. package/dist/components/Tab/Tab.vue.d.ts +2 -2
  92. package/dist/components/TableNext/TableBodyCell.vue.d.ts +2 -2
  93. package/dist/components/TableNext/TablePagination.vue.d.ts +6 -6
  94. package/dist/components/TabsExpanded/TabsExpanded.vue.d.ts +1 -1
  95. package/dist/components/Tag/BrandTag.vue.d.ts +2 -2
  96. package/dist/components/Tag/DefaultTag.vue.d.ts +2 -2
  97. package/dist/components/Tag/IndicatorTag.vue.d.ts +2 -2
  98. package/dist/components/Tag/Tag.vue.d.ts +8 -8
  99. package/dist/components/TemplatePreview/TemplatePreview.vue.d.ts +9 -0
  100. package/dist/components/TemplatePreview/TemplatePreview.vue.d.ts.map +1 -0
  101. package/dist/components/TemplatePreview/TemplatePreviewModal.vue.d.ts +15 -0
  102. package/dist/components/TemplatePreview/TemplatePreviewModal.vue.d.ts.map +1 -0
  103. package/dist/components/TextArea/TextArea.vue.d.ts +38 -32
  104. package/dist/components/TextArea/TextArea.vue.d.ts.map +1 -1
  105. package/dist/components/Toast/Toast.vue.d.ts +16 -0
  106. package/dist/components/Toast/Toast.vue.d.ts.map +1 -0
  107. package/dist/components/Toast/ToastManager.d.ts +14 -0
  108. package/dist/components/Toast/ToastManager.d.ts.map +1 -0
  109. package/dist/components/Toast/types.d.ts +35 -0
  110. package/dist/components/Toast/types.d.ts.map +1 -0
  111. package/dist/components/ToolTip/ToolTip.vue.d.ts +1 -1
  112. package/dist/components/Tour/Tour.vue.d.ts +6 -6
  113. package/dist/components/Tour/TourPopover.vue.d.ts +6 -6
  114. package/dist/components/UploadArea/UploadArea.vue.d.ts +7 -7
  115. package/dist/components/index.d.ts +2116 -1064
  116. package/dist/components/index.d.ts.map +1 -1
  117. package/dist/{es-b3e51efa.js → es-2735a8fb.js} +1 -1
  118. package/dist/{index-b9e3c5e9.js → index-e012fa52.js} +8396 -8093
  119. package/dist/{pt-br-20887b32.js → pt-br-f38a8b9c.js} +1 -1
  120. package/dist/style.css +1 -1
  121. package/dist/unnnic.js +126 -120
  122. package/dist/unnnic.umd.cjs +42 -41
  123. package/dist/utils/call.d.ts +2 -1
  124. package/dist/utils/call.d.ts.map +1 -1
  125. package/package.json +2 -2
  126. package/src/assets/img/previews/doc-preview.png +0 -0
  127. package/src/assets/img/previews/image-preview.png +0 -0
  128. package/src/assets/img/previews/video-preview.png +0 -0
  129. package/src/assets/scss/scheme-colors.scss +131 -4
  130. package/src/assets/tokens/colors.json +2 -2
  131. package/src/components/Alert/Alert.vue +26 -135
  132. package/src/components/Alert/Version1dot1.vue +0 -36
  133. package/src/components/Button/Button.vue +60 -108
  134. package/src/components/Button/types.ts +0 -1
  135. package/src/components/FormElement/FormElement.vue +51 -91
  136. package/src/components/Input/BaseInput.vue +10 -12
  137. package/src/components/Input/Input.scss +17 -20
  138. package/src/components/Input/Input.vue +96 -28
  139. package/src/components/Input/TextInput.vue +28 -41
  140. package/src/components/Input/__test__/TextInput.spec.js +5 -5
  141. package/src/components/Input/__test__/__snapshots__/Input.spec.js.snap +12 -3
  142. package/src/components/Input/__test__/__snapshots__/TextInput.spec.js.snap +1 -1
  143. package/src/components/Label/Label.vue +52 -21
  144. package/src/components/Label/__tests__/Label.spec.js +1 -1
  145. package/src/components/Label/__tests__/__snapshots__/Label.spec.js.snap +1 -1
  146. package/src/components/ModalDialog/ModalDialog.vue +1 -0
  147. package/src/components/ModalDialog/__tests__/__snapshots__/ModalDialog.spec.js.snap +1 -1
  148. package/src/components/TableNext/__test__/__snapshots__/TableNext.spec.js.snap +2 -2
  149. package/src/components/TableNext/__test__/__snapshots__/TablePagination.spec.js.snap +2 -2
  150. package/src/components/TemplatePreview/TemplatePreview.vue +252 -0
  151. package/src/components/TemplatePreview/TemplatePreviewModal.vue +51 -0
  152. package/src/components/TemplatePreview/types.d.ts +16 -0
  153. package/src/components/TextArea/TextArea.vue +13 -9
  154. package/src/components/TextArea/__test__/__snapshots__/TextArea.spec.js.snap +7 -2
  155. package/src/components/Toast/Toast.vue +236 -0
  156. package/src/components/Toast/ToastManager.ts +110 -0
  157. package/src/components/Toast/types.ts +57 -0
  158. package/src/components/index.ts +18 -4
  159. package/src/stories/Alert.stories.js +6 -67
  160. package/src/stories/Button.stories.js +2 -17
  161. package/src/stories/Input.stories.js +16 -3
  162. package/src/stories/Label.stories.js +7 -0
  163. package/src/stories/TemplatePreview.stories.js +94 -0
  164. package/src/stories/TemplatePreviewModal.stories.js +110 -0
  165. package/src/stories/Toast.mdx +123 -0
  166. package/src/stories/Toast.stories.js +126 -0
  167. package/src/types/scheme-colors.d.ts +120 -14
  168. package/src/utils/call.js +46 -18
  169. package/src/components/Alert/AlertBanner.vue +0 -182
  170. package/src/components/Alert/AlertCaller.vue +0 -49
  171. package/src/components/Alert/__tests__/AlertBanner.spec.js +0 -89
  172. package/src/components/Alert/__tests__/AlertCaller.spec.js +0 -98
@@ -0,0 +1,252 @@
1
+ <template>
2
+ <section class="unnnic-template-preview">
3
+ <section
4
+ :class="[
5
+ 'unnnic-template-preview__content',
6
+ { 'unnnic-template-preview__content--has-media': hasHeaderMedia },
7
+ ]"
8
+ >
9
+ <header
10
+ v-if="hasHeader"
11
+ :class="`unnnic-template-preview__header__${
12
+ template?.header.type === 'TEXT' ? 'text' : 'media'
13
+ }`"
14
+ >
15
+ <img
16
+ class="unnnic-template-preview__header__media__preview"
17
+ v-if="
18
+ template?.header.type === 'MEDIA' &&
19
+ template?.header.mediaType === 'IMAGE'
20
+ "
21
+ :src="template.header.src || imagePreview"
22
+ />
23
+ <template
24
+ v-else-if="
25
+ template?.header.type === 'MEDIA' &&
26
+ template?.header.mediaType === 'VIDEO'
27
+ "
28
+ >
29
+ <video
30
+ v-if="template.header.src"
31
+ class="unnnic-template-preview__header__media__preview"
32
+ :src="template.header.src"
33
+ controls
34
+ />
35
+ <img
36
+ v-else
37
+ class="unnnic-template-preview__header__media__preview"
38
+ :src="videoPreview"
39
+ />
40
+ </template>
41
+ <template
42
+ v-else-if="
43
+ template?.header.type === 'MEDIA' &&
44
+ template?.header.mediaType === 'DOCUMENT'
45
+ "
46
+ >
47
+ <img
48
+ class="unnnic-template-preview__header__media__preview"
49
+ :src="documentPreview"
50
+ />
51
+ </template>
52
+ <h1
53
+ class="unnnic-template-preview__header__text__preview"
54
+ v-else-if="template?.header.type === 'TEXT'"
55
+ >
56
+ {{ template.header.text }}
57
+ </h1>
58
+ </header>
59
+ <section
60
+ v-if="hasBody"
61
+ :class="[
62
+ 'unnnic-template-preview__body',
63
+ { 'unnnic-template-preview__body--has-media': hasHeaderMedia },
64
+ ]"
65
+ >
66
+ <section v-html="parsedBody"></section>
67
+ </section>
68
+ <footer
69
+ v-if="hasFooter"
70
+ :class="[
71
+ 'unnnic-template-preview__footer',
72
+ { 'unnnic-template-preview__footer--has-media': hasHeaderMedia },
73
+ ]"
74
+ >
75
+ {{ template?.footer }}
76
+ </footer>
77
+ </section>
78
+ <footer
79
+ v-if="hasButtons"
80
+ class="unnnic-template-preview__buttons"
81
+ >
82
+ <section
83
+ v-for="(button, index) in template?.buttons"
84
+ :key="`button-${index}`"
85
+ class="unnnic-template-preview__buttons__button"
86
+ >
87
+ <UnnnicIcon
88
+ class="unnnic-template-preview__buttons__button__icon"
89
+ :icon="getButtonIcon(button.type)"
90
+ scheme="aux-blue-500"
91
+ size="ant"
92
+ />
93
+ <p class="unnnic-template-preview__buttons__button__text">
94
+ {{ button.text }}
95
+ </p>
96
+ </section>
97
+ </footer>
98
+ </section>
99
+ </template>
100
+
101
+ <script lang="ts" setup>
102
+ import { computed } from 'vue';
103
+
104
+ import type { Template } from './types';
105
+
106
+ import imagePreview from '../../assets/img/previews/image-preview.png';
107
+ import documentPreview from '../../assets/img/previews/doc-preview.png';
108
+ import videoPreview from '../../assets/img/previews/video-preview.png';
109
+
110
+ import UnnnicIcon from '../Icon.vue';
111
+
112
+ interface Props {
113
+ template?: Template | null;
114
+ }
115
+
116
+ const props = withDefaults(defineProps<Props>(), {
117
+ template: null,
118
+ });
119
+
120
+ const hasHeader = computed(
121
+ () => props.template?.header && props.template.header.type,
122
+ );
123
+ const hasHeaderMedia = computed(
124
+ () => !!props.template?.header && props.template.header.type === 'MEDIA',
125
+ );
126
+ const hasBody = computed(
127
+ () => !!props.template?.body && props.template.body.length > 0,
128
+ );
129
+ const hasFooter = computed(
130
+ () => !!props.template?.footer && props.template.footer.length > 0,
131
+ );
132
+ const hasButtons = computed(
133
+ () => !!props.template?.buttons && props.template.buttons.length > 0,
134
+ );
135
+ const parsedBody = computed(() => {
136
+ if (!hasBody.value) return '';
137
+
138
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
139
+ const result = props
140
+ .template!.body!.replaceAll('\n', '<br/>')
141
+ .replaceAll(/(?:\*)([^*<\n]+)(?:\*)/g, '<strong>$1</strong>')
142
+ .replaceAll(/(?:_)([^_<\n]+)(?:_)/g, '<i>$1</i>')
143
+ .replaceAll(/(?:~)([^~<\n]+)(?:~)/g, '<s>$1</s>')
144
+ .replaceAll(/(?:```)([^```<\n]+)(?:```)/g, '<tt>$1</tt>')
145
+ .replaceAll(/{{.*?}}/g, (match) => `<strong>${match}</strong>`);
146
+
147
+ return result;
148
+ });
149
+
150
+ const getButtonIcon = (buttonType) => {
151
+ const buttonMapper = {
152
+ PHONE_NUMBER: 'phone',
153
+ URL: 'open_in_new',
154
+ COPY_CODE: 'content_copy',
155
+ FLOW: '',
156
+ QUICK_REPLY: 'reply',
157
+ };
158
+
159
+ return buttonMapper[buttonType] || '';
160
+ };
161
+ </script>
162
+
163
+ <style lang="scss" scoped>
164
+ @use '@/assets/scss/unnnic' as *;
165
+
166
+ .unnnic-template-preview {
167
+ display: flex;
168
+ flex-direction: column;
169
+ box-shadow: $unnnic-shadow-level-near;
170
+ background-color: $unnnic-color-background-white;
171
+ width: 368px;
172
+ border-radius: $unnnic-border-radius-md;
173
+
174
+ &__content {
175
+ display: flex;
176
+ flex-direction: column;
177
+ gap: $unnnic-space-3;
178
+ padding: $unnnic-space-4 $unnnic-space-3;
179
+
180
+ &--has-media {
181
+ padding: $unnnic-space-1;
182
+ }
183
+ }
184
+
185
+ &__header {
186
+ &__text {
187
+ &__preview {
188
+ font-family: $unnnic-font-family-secondary;
189
+ font-weight: $unnnic-font-weight-bold;
190
+ font-size: $unnnic-font-size-body-gt;
191
+ line-height: $unnnic-font-size-body-gt + $unnnic-line-height-medium;
192
+ color: $unnnic-color-neutral-dark;
193
+
194
+ margin: $unnnic-space-0;
195
+ }
196
+ }
197
+
198
+ &__media {
199
+ &__preview {
200
+ width: 100%;
201
+ object-fit: cover;
202
+ }
203
+ }
204
+ }
205
+
206
+ &__body {
207
+ font-family: $unnnic-font-family-secondary;
208
+ font-weight: $unnnic-font-weight-regular;
209
+ font-size: $unnnic-font-size-body-gt;
210
+ line-height: $unnnic-font-size-body-gt + $unnnic-line-height-medium;
211
+ color: $unnnic-color-neutral-cloudy;
212
+
213
+ &--has-media {
214
+ padding: $unnnic-space-0 $unnnic-space-2;
215
+ }
216
+ }
217
+
218
+ &__footer {
219
+ font-family: $unnnic-font-family-secondary;
220
+ font-weight: $unnnic-font-weight-regular;
221
+ font-size: $unnnic-font-size-body-md;
222
+ line-height: $unnnic-font-size-body-md + $unnnic-line-height-medium;
223
+ color: $unnnic-color-neutral-clean;
224
+
225
+ &--has-media {
226
+ padding: $unnnic-space-0 $unnnic-space-3 $unnnic-space-2;
227
+ }
228
+ }
229
+
230
+ &__buttons {
231
+ font-family: $unnnic-font-family-secondary;
232
+ font-weight: $unnnic-font-weight-bold;
233
+ font-size: $unnnic-font-size-body-gt;
234
+ line-height: $unnnic-font-size-body-gt + $unnnic-line-height-medium;
235
+
236
+ &__button {
237
+ margin: 0;
238
+ display: flex;
239
+ align-items: center;
240
+ justify-content: center;
241
+ gap: $unnnic-space-2;
242
+ padding: $unnnic-space-3;
243
+ border-top: 1px solid $unnnic-color-neutral-light;
244
+
245
+ &__text {
246
+ color: $unnnic-color-aux-blue-500;
247
+ margin: $unnnic-space-0;
248
+ }
249
+ }
250
+ }
251
+ }
252
+ </style>
@@ -0,0 +1,51 @@
1
+ <template>
2
+ <UnnnicModalDialog
3
+ :modelValue="modelValue"
4
+ @update:modelValue="$event === false && $emit('close')"
5
+ :title="defaultTranslations.title[props.locale]"
6
+ :showCloseIcon="true"
7
+ class="unnnic-template-preview-modal"
8
+ >
9
+ <UnnnicTemplatePreview :template="template" />
10
+ </UnnnicModalDialog>
11
+ </template>
12
+
13
+ <script lang="ts" setup>
14
+ import UnnnicTemplatePreview from './TemplatePreview.vue';
15
+ import UnnnicModalDialog from '../ModalDialog/ModalDialog.vue';
16
+
17
+ import type { Template } from './types';
18
+
19
+ const defaultTranslations = {
20
+ title: {
21
+ 'pt-br': 'Visualizar modelo',
22
+ en: 'Template preview',
23
+ es: 'Vista previa de plantilla',
24
+ },
25
+ };
26
+
27
+ interface Props {
28
+ locale?: string;
29
+ template: Template;
30
+ modelValue: boolean;
31
+ }
32
+
33
+ const props = withDefaults(defineProps<Props>(), {
34
+ locale: 'en',
35
+ });
36
+
37
+ defineEmits<{
38
+ close: void;
39
+ }>();
40
+ </script>
41
+
42
+ <style lang="scss" scoped>
43
+ @use '@/assets/scss/unnnic' as *;
44
+
45
+ :deep(.unnnic-modal-dialog__container__content) {
46
+ display: flex;
47
+ align-items: center;
48
+ justify-content: center;
49
+ background-color: $unnnic-color-neutral-lightest;
50
+ }
51
+ </style>
@@ -0,0 +1,16 @@
1
+ export interface Template {
2
+ header: {
3
+ type: 'TEXT' | 'MEDIA';
4
+ mediaType?: 'IMAGE' | 'VIDEO' | 'DOCUMENT';
5
+ text?: string | null;
6
+ src?: string | null;
7
+ };
8
+ body?: string;
9
+ footer?: string;
10
+ buttons?: Array<{
11
+ type: 'QUICK_REPLY' | 'PHONE_NUMBER';
12
+ text: string;
13
+ countryCode?: string;
14
+ phoneNumber?: string;
15
+ }>;
16
+ }
@@ -18,13 +18,14 @@
18
18
  :disabled="disabled"
19
19
  :value="modelValue"
20
20
  @input="$emit('update:modelValue', fullySanitize($event.target.value))"
21
- ></textarea>
21
+ />
22
22
 
23
23
  <template
24
24
  v-if="maxLength"
25
25
  #rightMessage
26
- >{{ modelValue.length }}/{{ maxLength }}</template
27
26
  >
27
+ {{ modelValue.length }}/{{ maxLength }}
28
+ </template>
28
29
  </UnnnicFormElement>
29
30
  </template>
30
31
 
@@ -96,6 +97,12 @@ export default {
96
97
  @use '@/assets/scss/unnnic' as *;
97
98
  @use '@/components/Input/Input' as *;
98
99
 
100
+ * {
101
+ margin: 0;
102
+ padding: 0;
103
+ box-sizing: border-box;
104
+ }
105
+
99
106
  .unnnic-text-area {
100
107
  &__textarea {
101
108
  @include input-base;
@@ -103,24 +110,21 @@ export default {
103
110
  display: block;
104
111
  width: 100%;
105
112
  resize: vertical;
106
- box-sizing: border-box;
107
113
 
108
114
  scrollbar-width: thin;
109
115
 
116
+ padding: $unnnic-space-3 $unnnic-space-4;
117
+
110
118
  &--size-md {
111
119
  @include input-md-font;
112
120
 
113
- min-height: 6.25 * $unnnic-font-size;
114
- padding: ($unnnic-spacing-ant - $unnnic-border-width-thinner)
115
- ($unnnic-spacing-sm - $unnnic-border-width-thinner);
121
+ min-height: 100px;
116
122
  }
117
123
 
118
124
  &--size-sm {
119
125
  @include input-sm-font;
120
126
 
121
- min-height: 5 * $unnnic-font-size;
122
- padding: ($unnnic-spacing-xs)
123
- ($unnnic-spacing-sm - $unnnic-border-width-thinner);
127
+ min-height: $unnnic-space-20;
124
128
  }
125
129
 
126
130
  &.unnnic-text-area__textarea--type-error {
@@ -3,7 +3,12 @@
3
3
  exports[`TextArea.vue > matches the snapshot 1`] = `
4
4
  "<section data-v-9f8d6c86="" data-v-735b3c51="" class="unnnic-form-element">
5
5
  <p data-v-9f8d6c86="" class="unnnic-form-element__label">Description</p><textarea data-v-735b3c51="" class="unnnic-text-area__textarea unnnic-text-area__textarea--size-md unnnic-text-area__textarea--type-normal" placeholder="Enter text" maxlength="200" value=""></textarea>
6
- <!--v-if-->
7
- <p data-v-9f8d6c86="" class="unnnic-form-element__message"> <span data-v-9f8d6c86="" class="unnnic-form-element__right-message">0/200</span></p>
6
+ <section data-v-9f8d6c86="" class="unnnic-form-element__hints-container">
7
+ <section data-v-9f8d6c86="" class="unnnic-form-element__message-container">
8
+ <!--v-if-->
9
+ <!--v-if-->
10
+ </section>
11
+ <p data-v-9f8d6c86="">0/200</p>
12
+ </section>
8
13
  </section>"
9
14
  `;
@@ -0,0 +1,236 @@
1
+ <template>
2
+ <Transition
3
+ name="toast-slide"
4
+ appear
5
+ @after-leave="$emit('destroy')"
6
+ >
7
+ <aside
8
+ v-if="isVisible"
9
+ :class="['unnnic-toast', `unnnic-toast--${type}`]"
10
+ :role="type === 'error' ? 'alert' : 'status'"
11
+ :aria-live="type === 'error' ? 'assertive' : 'polite'"
12
+ data-testid="unnnic-toast"
13
+ >
14
+ <section class="unnnic-toast__content">
15
+ <header class="unnnic-toast__header">
16
+ <UnnnicIcon
17
+ :icon="typeConfig.icon"
18
+ :scheme="typeConfig.scheme"
19
+ size="ant"
20
+ data-testid="toast-type-icon"
21
+ />
22
+
23
+ <h3 class="unnnic-toast__title">
24
+ {{ title }}
25
+ </h3>
26
+
27
+ <UnnnicIcon
28
+ icon="close"
29
+ scheme="neutral-dark"
30
+ size="ant"
31
+ clickable
32
+ class="unnnic-toast__close"
33
+ data-testid="toast-close-button"
34
+ @click="handleClose"
35
+ @keydown.enter="handleClose"
36
+ @keydown.space.prevent="handleClose"
37
+ />
38
+ </header>
39
+
40
+ <p
41
+ v-if="description"
42
+ class="unnnic-toast__text"
43
+ >
44
+ {{ description }}
45
+ </p>
46
+ </section>
47
+
48
+ <UnnnicButton
49
+ v-if="button"
50
+ type="tertiary"
51
+ :text="button.text"
52
+ class="unnnic-toast__action-button"
53
+ data-testid="toast-action-button"
54
+ @click="handleAction"
55
+ @keydown.enter="handleAction"
56
+ @keydown.space.prevent="handleAction"
57
+ />
58
+ </aside>
59
+ </Transition>
60
+ </template>
61
+
62
+ <script setup lang="ts">
63
+ import { ref, computed, onMounted, onUnmounted } from 'vue';
64
+
65
+ import UnnnicIcon from '@/components/Icon.vue';
66
+ import UnnnicButton from '@/components/Button/Button.vue';
67
+
68
+ import type { ToastProps, ToastEmits } from './types';
69
+ import type { SchemeColor } from '@/types/scheme-colors';
70
+
71
+ defineOptions({
72
+ name: 'UnnnicToast',
73
+ });
74
+
75
+ const props = withDefaults(defineProps<ToastProps>(), {
76
+ title: '',
77
+ description: '',
78
+ button: undefined,
79
+ timeout: 5000,
80
+ type: 'informational',
81
+ });
82
+
83
+ const emit = defineEmits<ToastEmits>();
84
+
85
+ const isVisible = ref(false);
86
+ let timeoutId: number | null = null;
87
+
88
+ const typeConfig = computed(() => {
89
+ const configMap = {
90
+ informational: { icon: 'info', scheme: 'blue-500' },
91
+ attention: { icon: 'error', scheme: 'yellow-500' },
92
+ success: { icon: 'check_circle', scheme: 'green-500' },
93
+ error: { icon: 'cancel', scheme: 'red-500' },
94
+ };
95
+
96
+ return configMap[props.type || 'informational'] as {
97
+ icon: string;
98
+ scheme: SchemeColor;
99
+ };
100
+ });
101
+
102
+ const handleClose = () => {
103
+ isVisible.value = false;
104
+ emit('close');
105
+ };
106
+
107
+ const handleAction = () => {
108
+ if (props.button?.action) {
109
+ props.button.action();
110
+ }
111
+ };
112
+
113
+ const startTimeout = () => {
114
+ if (props.timeout > 0) {
115
+ timeoutId = window.setTimeout(() => {
116
+ handleClose();
117
+ }, props.timeout);
118
+ }
119
+ };
120
+
121
+ const clearTimeout = () => {
122
+ if (timeoutId) {
123
+ window.clearTimeout(timeoutId);
124
+ timeoutId = null;
125
+ }
126
+ };
127
+
128
+ onMounted(() => {
129
+ isVisible.value = true;
130
+ startTimeout();
131
+ });
132
+
133
+ onUnmounted(() => {
134
+ clearTimeout();
135
+ });
136
+ </script>
137
+
138
+ <style lang="scss" scoped>
139
+ @use '@/assets/scss/unnnic' as *;
140
+
141
+ .unnnic-toast {
142
+ position: fixed;
143
+ bottom: $unnnic-space-4;
144
+ right: $unnnic-space-4;
145
+ z-index: 9999;
146
+
147
+ display: flex;
148
+ align-items: flex-end;
149
+ flex-direction: column;
150
+ gap: $unnnic-space-5;
151
+
152
+ min-width: 250px;
153
+ max-width: 450px;
154
+ padding: $unnnic-space-4;
155
+
156
+ border-radius: $unnnic-radius-2;
157
+ box-shadow: $unnnic-shadow-2;
158
+ border: 1px solid $unnnic-color-border-base;
159
+
160
+ &--informational {
161
+ border-color: $unnnic-color-border-info;
162
+ background-color: $unnnic-color-bg-info;
163
+ }
164
+
165
+ &--attention {
166
+ border-color: $unnnic-color-border-warning;
167
+ background-color: $unnnic-color-bg-warning;
168
+ }
169
+
170
+ &--success {
171
+ border-color: $unnnic-color-border-success;
172
+ background-color: $unnnic-color-bg-success;
173
+ }
174
+
175
+ &--error {
176
+ border-color: $unnnic-color-border-critical;
177
+ background-color: $unnnic-color-bg-critical;
178
+ }
179
+
180
+ &__content,
181
+ &__header {
182
+ width: 100%;
183
+
184
+ display: flex;
185
+ gap: $unnnic-space-2;
186
+ }
187
+
188
+ &__content {
189
+ flex-direction: column;
190
+ gap: $unnnic-space-2;
191
+ }
192
+
193
+ &__header {
194
+ align-items: center;
195
+ }
196
+
197
+ &__title {
198
+ flex: 1;
199
+
200
+ margin: 0;
201
+
202
+ font: $unnnic-font-action;
203
+ color: $unnnic-color-fg-emphasized;
204
+ }
205
+
206
+ &__text {
207
+ margin: 0;
208
+ margin-left: $unnnic-space-7;
209
+
210
+ font: $unnnic-font-caption-2;
211
+ color: $unnnic-color-fg-emphasized;
212
+ }
213
+ }
214
+
215
+ // Animations
216
+ .toast-slide-enter-active,
217
+ .toast-slide-leave-active {
218
+ transition: all 0.3s ease;
219
+ }
220
+
221
+ .toast-slide-enter-from {
222
+ transform: translateY(100%);
223
+ opacity: 0;
224
+ }
225
+
226
+ .toast-slide-leave-to {
227
+ transform: translateY(100%);
228
+ opacity: 0;
229
+ }
230
+
231
+ .toast-slide-enter-to,
232
+ .toast-slide-leave-from {
233
+ transform: translateY(0);
234
+ opacity: 1;
235
+ }
236
+ </style>