customer-module-frontend 1.0.2

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 (87) hide show
  1. package/.cursor/rules/context.md +306 -0
  2. package/.cursor/rules/guardrails.md +35 -0
  3. package/.env +1 -0
  4. package/.github/workflows/publish-to-npm-beta.yml +56 -0
  5. package/.github/workflows/publish-to-npm.yml +58 -0
  6. package/README.md +73 -0
  7. package/eslint.config.js +23 -0
  8. package/index.html +13 -0
  9. package/package.json +43 -0
  10. package/postcss-unwrap-layers.js +31 -0
  11. package/postcss.config.js +11 -0
  12. package/public/vite.svg +1 -0
  13. package/src/App.css +40 -0
  14. package/src/App.tsx +58 -0
  15. package/src/assets/accounts.svg +3 -0
  16. package/src/assets/at_the_rate.svg +10 -0
  17. package/src/assets/buildings.svg +3 -0
  18. package/src/assets/chat.svg +3 -0
  19. package/src/assets/close.svg +3 -0
  20. package/src/assets/contacts.svg +3 -0
  21. package/src/assets/conversation.svg +10 -0
  22. package/src/assets/customers.svg +10 -0
  23. package/src/assets/details.svg +3 -0
  24. package/src/assets/domain.svg +10 -0
  25. package/src/assets/edit.svg +15 -0
  26. package/src/assets/email.svg +3 -0
  27. package/src/assets/google.svg +8 -0
  28. package/src/assets/inbox.svg +0 -0
  29. package/src/assets/message.svg +3 -0
  30. package/src/assets/no-data.svg +9 -0
  31. package/src/assets/open_in_a_new_tab.svg +10 -0
  32. package/src/assets/phone.svg +3 -0
  33. package/src/assets/react.svg +1 -0
  34. package/src/assets/search.svg +3 -0
  35. package/src/assets/search_typing.svg +4 -0
  36. package/src/assets/sm_contacts.svg +3 -0
  37. package/src/assets/sm_inbox.svg +3 -0
  38. package/src/assets/sm_slider.svg +3 -0
  39. package/src/assets/status-resolved.svg +3 -0
  40. package/src/assets/status-snoozed.svg +4 -0
  41. package/src/assets/status_open.svg +1 -0
  42. package/src/components/AccountContacts/index.tsx +107 -0
  43. package/src/components/AccountDetails/index.tsx +102 -0
  44. package/src/components/AccountsConversation/index.tsx +75 -0
  45. package/src/components/Avatar/constants.tsx +45 -0
  46. package/src/components/Avatar/index.tsx +42 -0
  47. package/src/components/BreadcrumbsSection/index.tsx +16 -0
  48. package/src/components/Card/index.tsx +31 -0
  49. package/src/components/Card/types.ts +10 -0
  50. package/src/components/ContactConversation/Converation.tsx +14 -0
  51. package/src/components/ContactConversation/index.tsx +81 -0
  52. package/src/components/ContactDetails/index.tsx +111 -0
  53. package/src/components/Contacts/EditContact.tsx +213 -0
  54. package/src/components/Contacts/constants/index.tsx +24 -0
  55. package/src/components/Contacts/index.tsx +171 -0
  56. package/src/components/ConversationBox/constants.tsx +99 -0
  57. package/src/components/ConversationBox/index.tsx +147 -0
  58. package/src/components/ConversationBox/types.ts +20 -0
  59. package/src/components/CustomersLayout/index.tsx +20 -0
  60. package/src/components/DetailsCard/index.tsx +31 -0
  61. package/src/components/DetailsCard/types.ts +10 -0
  62. package/src/components/EmptyData/NoDataFound.tsx +31 -0
  63. package/src/components/Header/index.tsx +55 -0
  64. package/src/components/Icon/index.tsx +93 -0
  65. package/src/components/Icon/types.ts +13 -0
  66. package/src/components/Listing/AccountTable.tsx +47 -0
  67. package/src/components/Listing/ContactTable.tsx +76 -0
  68. package/src/components/RightPanel/AccountPanel.tsx +123 -0
  69. package/src/components/RightPanel/ContactPanel.tsx +142 -0
  70. package/src/components/RightPanel/index.tsx +167 -0
  71. package/src/components/Search/SearchDialog.tsx +150 -0
  72. package/src/components/TabsSection/index.tsx +49 -0
  73. package/src/constants/index.tsx +645 -0
  74. package/src/hooks/useBreadcrumb.tsx +93 -0
  75. package/src/index.css +315 -0
  76. package/src/main.tsx +14 -0
  77. package/src/pages/AccountDetail.tsx +68 -0
  78. package/src/pages/Accounts.tsx +12 -0
  79. package/src/pages/ContactDetail.tsx +55 -0
  80. package/src/pages/Contacts.tsx +12 -0
  81. package/src/stores/count.tsx +17 -0
  82. package/src/types/index.ts +0 -0
  83. package/tailwind.config.js +179 -0
  84. package/tsconfig.app.json +36 -0
  85. package/tsconfig.json +7 -0
  86. package/tsconfig.node.json +26 -0
  87. package/vite.config.ts +31 -0
@@ -0,0 +1,93 @@
1
+ import { useLocation, useNavigate } from "react-router-dom";
2
+ import { accountData, contactsData } from '../constants/index';
3
+
4
+ export function useBreadcrumb() {
5
+ const location = useLocation();
6
+ const navigate = useNavigate();
7
+
8
+ const path = location.pathname; // works even in MemoryRouter
9
+
10
+ const items = [];
11
+
12
+ // Handle nested route: /accounts/:accountId/contacts/:contactId
13
+ if (path.startsWith("/accounts") && path.includes("/contacts/")) {
14
+ items.push({
15
+ label: "Accounts",
16
+ command: () => navigate("/accounts")
17
+ });
18
+
19
+ const parts = path.split("/");
20
+ const accountId = parts[2];
21
+ const contactId = parts[4]; // /accounts/:accountId/contacts/:contactId
22
+
23
+ if (accountId) {
24
+ const account = accountData.data.results.find(
25
+ (acc: { id: number; name: string }) => acc.id.toString() === accountId
26
+ );
27
+ const accountName = account?.name || 'Account';
28
+
29
+ items.push({
30
+ label: accountName,
31
+ command: () => navigate(`/accounts/${accountId}`)
32
+ });
33
+ }
34
+
35
+ if (contactId) {
36
+ const contact = contactsData.data.results.find(
37
+ (cont: { id: number; name: string }) => cont.id.toString() === contactId
38
+ );
39
+ const contactName = contact?.name || 'Contact';
40
+
41
+ items.push({
42
+ label: contactName,
43
+ command: () => navigate(`/accounts/${accountId}/contacts/${contactId}`)
44
+ });
45
+ }
46
+ }
47
+ // Handle /accounts/:accountId route
48
+ else if (path.startsWith("/accounts")) {
49
+ items.push({
50
+ label: "Accounts",
51
+ command: () => navigate("/accounts")
52
+ });
53
+
54
+ const parts = path.split("/");
55
+
56
+ if (parts[2]) {
57
+ const accountId = parts[2];
58
+ const account = accountData.data.results.find(
59
+ (acc: { id: number; name: string }) => acc.id.toString() === accountId
60
+ );
61
+ const accountName = account?.name || 'Account';
62
+
63
+ items.push({
64
+ label: accountName,
65
+ command: () => navigate(`/accounts/${accountId}`)
66
+ });
67
+ }
68
+ }
69
+ // Handle /contacts/:contactId route
70
+ else if (path.startsWith("/contacts")) {
71
+ items.push({
72
+ label: "Contacts",
73
+ command: () => navigate("/contacts")
74
+ });
75
+
76
+ const parts = path.split("/");
77
+
78
+ if (parts[2]) {
79
+ const contactId = parts[2];
80
+ const contact = contactsData.data.results.find(
81
+ (cont: { id: number; name: string }) => cont.id.toString() === contactId
82
+ );
83
+ const contactName = contact?.name || 'Contact';
84
+
85
+ items.push({
86
+ label: contactName,
87
+ command: () => navigate(`/contacts/${contactId}`)
88
+ });
89
+ }
90
+ }
91
+
92
+ return items;
93
+ }
package/src/index.css ADDED
@@ -0,0 +1,315 @@
1
+ @import url("https://fonts.googleapis.com/css2?family=Hanken+Grotesk:ital,wght@0,100..900;1,100..900&display=swap");
2
+ @import "tailwindcss" prefix(cm);
3
+ @tailwind base;
4
+ @tailwind components;
5
+ @tailwind utilities;
6
+
7
+ .p-tabview-panels {
8
+ padding: 0 !important;
9
+ }
10
+
11
+ .p-tabview-nav-link {
12
+ padding-top: 14px !important;
13
+ padding-bottom: 14px !important;
14
+ }
15
+
16
+ .p-tabview-nav {
17
+ border-bottom-width: 1px !important;
18
+ }
19
+
20
+ @theme {
21
+
22
+ /* Red color palette */
23
+ --color-red-50: #FCE4E4;
24
+ --color-red-100: #F9C9C9;
25
+ --color-red-200: #F19192;
26
+ --color-red-300: #EB5C5C;
27
+ --color-red-400: #E42525;
28
+ --color-red-500: #B81717;
29
+ --color-red-600: #911212;
30
+ --color-red-700: #6D0D0E;
31
+ --color-red-800: #480909;
32
+ --color-red-900: #230505;
33
+ --color-red-950: #120202;
34
+
35
+ /* Blue color palette */
36
+ --color-blue-50: #E6EFFD;
37
+ --color-blue-100: #D4E2FC;
38
+ --color-blue-200: #A9C5F9;
39
+ --color-blue-300: #7EA8F6;
40
+ --color-blue-400: #538BF3;
41
+ --color-blue-500: #276CF0;
42
+ --color-blue-600: #0F53D2;
43
+ --color-blue-700: #0C3E9D;
44
+ --color-blue-800: #072969;
45
+ --color-blue-900: #041534;
46
+ --color-blue-950: #020918;
47
+
48
+ /* Green color palette */
49
+ --color-green-50: #EAF9F2;
50
+ --color-green-100: #D3F4E1;
51
+ --color-green-200: #A6E9C3;
52
+ --color-green-300: #77DEA6;
53
+ --color-green-400: #4AD387;
54
+ --color-green-500: #2DBB6D;
55
+ --color-green-600: #239456;
56
+ --color-green-700: #1B6F41;
57
+ --color-green-800: #114A2B;
58
+ --color-green-900: #0A2516;
59
+ --color-green-950: #05150C;
60
+
61
+ /* Pastel Blue color palette */
62
+ --color-pastel-blue-50: #EFF5FB;
63
+ --color-pastel-blue-100: #DBE9F5;
64
+ --color-pastel-blue-200: #BBD6EC;
65
+ --color-pastel-blue-300: #97C0E2;
66
+ --color-pastel-blue-400: #77ADD9;
67
+ --color-pastel-blue-500: #5398CF;
68
+ --color-pastel-blue-600: #337CB7;
69
+ --color-pastel-blue-700: #255C87;
70
+ --color-pastel-blue-800: #1A3E5D;
71
+ --color-pastel-blue-900: #0B1E2C;
72
+ --color-pastel-blue-950: #071018;
73
+
74
+ /* Pastel Yellow color palette */
75
+ --color-pastel-yellow-50: #FBF9E8;
76
+ --color-pastel-yellow-100: #FAF5D6;
77
+ --color-pastel-yellow-200: #F4EAA9;
78
+ --color-pastel-yellow-300: #EFDF80;
79
+ --color-pastel-yellow-400: #E9D659;
80
+ --color-pastel-yellow-500: #E3CB2D;
81
+ --color-pastel-yellow-600: #C2AB1A;
82
+ --color-pastel-yellow-700: #907F13;
83
+ --color-pastel-yellow-800: #5F540E;
84
+ --color-pastel-yellow-900: #322C07;
85
+ --color-pastel-yellow-950: #241D00;
86
+
87
+ /* Slate color palette */
88
+ --color-slate-50: #F8FAFC;
89
+ --color-slate-100: #F1F5F9;
90
+ --color-slate-150: #EDF1F6;
91
+ --color-slate-200: #E2E8F0;
92
+ --color-slate-300: #CBD5E1;
93
+ --color-slate-400: #94A3B8;
94
+ --color-slate-500: #64758B;
95
+ --color-slate-600: #475569;
96
+ --color-slate-700: #334155;
97
+ --color-slate-800: #1E293B;
98
+ --color-slate-900: #0F172A;
99
+ --color-slate-950: #020617;
100
+
101
+ /* Slate colors */
102
+ --color-slate-surface-white: #ffffff;
103
+ --color-slate-surface-subtle: #f8fafc;
104
+ --color-slate-surface-subtle-100: #f1f5f9;
105
+ --color-slate-surface-subtle-150: #edf1f6;
106
+ --color-slate-surface-subtle-200: #e2e8f0;
107
+ --color-slate-surface-subtle-300: #cbd5e1;
108
+ --color-slate-surface-default: #94a3b8;
109
+ --color-slate-surface-dark-500: #64758b;
110
+ --color-slate-surface-dark-600: #475569;
111
+ --color-slate-surface-darkest: #334155;
112
+ --color-slate-surface-disabled: #e2e8f0;
113
+
114
+ --color-slate-border-default: #94a3b8;
115
+ --color-slate-border-light: #e2e8f0;
116
+ --color-slate-border-mild: #edf1f6;
117
+ --color-slate-border-dark: #64758b;
118
+
119
+ --color-slate-text-title: #1E293B;
120
+ --color-slate-text-body: #334155;
121
+ --color-slate-text-subtle: #64758b;
122
+ --color-slate-text-caption: #cbd5e1;
123
+ --color-slate-text-disabled: #94a3b8;
124
+
125
+ --color-slate-icons-active: #334155;
126
+ --color-slate-icons-subtle: #64758b;
127
+ --color-slate-icons-disabled: #94a3b8;
128
+
129
+ /* Primary colors */
130
+ --color-primary-surface-default: #276cf0;
131
+ --color-primary-surface-subtle: #e6effd;
132
+ --color-primary-surface-dark: #0c3e9d;
133
+ --color-primary-surface-mild-dark: #0f53d2;
134
+ --color-primary-surface-lighter: #7ea8f6;
135
+
136
+ --color-primary-border-subtle: #d4e2fc;
137
+ --color-primary-border-lighter: #a9c5f9;
138
+ --color-primary-border-default: #276cf0;
139
+ --color-primary-border-dark: #0c3e9d;
140
+
141
+ --color-primary-text-default: #0c3e9d;
142
+ --color-primary-text-label: #0c3e9d;
143
+
144
+ /* Error colors */
145
+ --color-error-surface-default: var(--color-red-500);
146
+ --color-error-surface-subtle: var(--color-red-50);
147
+ --color-error-surface-dark: var(--color-red-200);
148
+ --color-error-surface-disabled: var(--color-red-300);
149
+
150
+ --color-error-border-lighter: var(--color-red-200);
151
+ --color-error-border-default: var(--color-red-400);
152
+ --color-error-border-dark: var(--color-red-500);
153
+
154
+ --color-error-text-title: var(--sc-color-red-800);
155
+ --color-error-text-subtle: var(--sc-color-red-500);
156
+ --color-error-text-body: var(--sc-color-red-700);
157
+ --color-error-text-disabled: var(--sc-color-red-500);
158
+ --color-error-text-caption: var(--sc-color-red-300);
159
+
160
+
161
+ --color-success-surface-default: var(--sc-color-green-300);
162
+ --color-success-surface-subtle: var(--sc-color-green-100);
163
+ --color-success-surface-dark: var(--sc-color-green-400);
164
+
165
+ --color-success-border-lighter: var(--sc-color-green-200);
166
+ --color-success-border-default: var(--sc-color-green-400);
167
+ --color-success-border-dark: var(--sc-color-green-500);
168
+
169
+ --color-success-text-title: var(--sc-color-green-800);
170
+ --color-success-text-subtle: var(--sc-color-green-500);
171
+ --color-success-text-body: var(--sc-color-green-700);
172
+ --color-success-text-disabled: var(--sc-color-green-500);
173
+ --color-success-text-caption: var(--sc-color-green-300);
174
+
175
+
176
+ /* Blue colors */
177
+ --color-blue-surface-default: var(--sc-color-blue-100);
178
+ --color-blue-surface-subtle: var(--sc-color-blue-50);
179
+ --color-blue-surface-dark: var(--sc-color-blue-200);
180
+ --color-blue-surface-disabled: var(--sc-color-blue-300);
181
+
182
+ --color-blue-border-default: var(--sc-color-blue-400);
183
+ --color-blue-border-dark: var(--sc-color-blue-500);
184
+ --color-blue-border-light: var(--sc-color-blue-200);
185
+
186
+ --color-blue-text-title: var(--sc-color-blue-800);
187
+ --color-blue-text-body: var(--sc-color-blue-700);
188
+ --color-blue-text-subtle: var(--sc-color-blue-500);
189
+ --color-blue-text-caption: var(--sc-color-blue-300);
190
+ --color-blue-text-disabled: var(--sc-color-blue-500);
191
+
192
+ /* Pastel Yellow colors */
193
+ --color-pastel-yellow-surface-subtle: var(--sc-color-pastel-yellow-100);
194
+ --color-pastel-yellow-text-title: var(--sc-color-pastel-yellow-800);
195
+ --color-pastel-yellow-text-body: var(--sc-color-pastel-yellow-700);
196
+
197
+ /* Pastel Light Blue colors */
198
+ --color-pastel-light-blue-surface-default: var(--sc-color-pastel-blue-400);
199
+ --color-pastel-light-blue-surface-subtle: var(--sc-color-pastel-blue-100);
200
+ --color-pastel-light-blue-surface-mild: var(--sc-color-pastel-blue-50);
201
+ --color-pastel-light-blue-surface-dark: var(--sc-color-pastel-blue-700);
202
+
203
+ --color-pastel-light-blue-border-default: var(--sc-color-pastel-blue-500);
204
+ --color-pastel-light-blue-border-dark: var(--sc-color-pastel-blue-800);
205
+ --color-pastel-light-blue-border-light: var(--sc-color-pastel-blue-300);
206
+
207
+ --color-pastel-light-blue-text-title: var(--sc-color-pastel-blue-700);
208
+ --color-pastel-light-blue-text-body: var(--sc-color-pastel-blue-700);
209
+ --color-pastel-light-blue-text-subtle: var(--sc-color-pastel-blue-500);
210
+ --color-pastel-light-blue-text-caption: var(--sc-color-pastel-blue-300);
211
+ --color-pastel-light-blue-text-disabled: var(--sc-color-pastel-blue-500);
212
+
213
+ /* Additional colors */
214
+ --color-primary-blue: #007bff;
215
+ --color-primary-blue-dark: #0056b3;
216
+ --color-primary-blue-light: #66b3ff;
217
+
218
+ --color-secondary-green: #28a745;
219
+ --color-secondary-green-dark: #1e7e34;
220
+ --color-secondary-green-light: #71dd8a;
221
+
222
+ --color-accent-orange: #fd7e14;
223
+ --color-accent-purple: #6f42c1;
224
+ --color-accent-teal: #20c997;
225
+
226
+
227
+ --color-gray-1: #f8f9fa;
228
+ --color-gray-2: #e9ecef;
229
+ --color-gray-3: #dee2e6;
230
+ --color-gray-4: #ced4da;
231
+ --color-gray-5: #adb5bd;
232
+ --color-gray-6: #6c757d;
233
+ --color-gray-7: #495057;
234
+ --color-gray-8: #343a40;
235
+ --color-gray-9: #212529;
236
+
237
+ --color-success: #28a745;
238
+ --color-warning: #ffc107;
239
+ --color-error: #dc3545;
240
+ --color-info: #17a2b8;
241
+
242
+ --color-banner-bg: #d4e2fc;
243
+ --color-banner-text: #0c3e9d;
244
+ --color-banner-icon-bg: #2563eb;
245
+ --color-toggle-inactive: #94a3b8;
246
+ --color-toggle-active: #276cf0;
247
+ --color-savings-bg: #d1fae5;
248
+ --color-savings-text: #059669;
249
+ --color-card-border: #e5e7eb;
250
+ --color-card-hover-border: #d1d5db;
251
+ --color-plan-highlighted-bg: #475569;
252
+ --color-google-blue: #4285f4;
253
+ --color-google-blue-hover: #3367d6;
254
+ --color-google-blue-active: #2d5aa0;
255
+ --color-error-surface-subtle: #FCE4E4;
256
+ --color-error-surface-dark: #F19192;
257
+
258
+
259
+
260
+
261
+ --font-family-sans: "Hanken Grotesk", sans-serif;
262
+ --font-optical-sizing: auto;
263
+ --font-weight: 400;
264
+ --font-style: normal;
265
+
266
+ --font-size-label-medium: 1rem;
267
+
268
+ --font-size-body-xs: 0.75rem;
269
+ --font-size-body-sm: 0.875rem;
270
+ --font-size-body-md: 1rem;
271
+ --font-size-body-lg: 1.125rem;
272
+ --font-size-body-xl: 1.25rem;
273
+ --font-size-body-2xl: 1.5rem;
274
+ --font-size-body-3xl: 1.75rem;
275
+ --font-size-body-4xl: 2rem;
276
+ --font-size-body-5xl: 2.25rem;
277
+
278
+ /* Heading font sizes */
279
+ --font-size-heading-h4: 1.25rem; /* 20px */
280
+ --font-size-heading-h3: 1.5rem; /* 24px */
281
+ --font-size-heading-h2: 1.875rem; /* 30px */
282
+ --font-size-heading-h1: 2.25rem; /* 36px */
283
+
284
+ /* Line heights corresponding to font sizes */
285
+ --line-height-body-xs: 1.125;
286
+ --line-height-body-sm: 1.25;
287
+ --line-height-body-md: 1.5;
288
+ --line-height-body-lg: 1.75;
289
+ --line-height-body-xl: 2;
290
+ --line-height-body-2xl: 2.25;
291
+ --line-height-body-3xl: 2.5;
292
+ --line-height-body-4xl: 2.75;
293
+ --line-height-body-5xl: 3;
294
+
295
+ /* Heading line heights */
296
+ --line-height-heading-h4: 1.2; /* 24px / 20px */
297
+ --line-height-heading-h3: 1.1667; /* 28px / 24px */
298
+ --line-height-heading-h2: 1.2; /* 36px / 30px */
299
+ --line-height-heading-h1: 1.2222; /* 44px / 36px */
300
+
301
+ --font-weight-medium: 500;
302
+ --font-weight-bold: 700;
303
+ --font-weight-black: 900;
304
+ --font-weight-normal: 400;
305
+ --font-weight-light: 300;
306
+ --font-weight-thin: 100;
307
+ --font-weight-extra-light: 200;
308
+ --font-weight-extra-bold: 800;
309
+ --font-weight-extra-black: 900;
310
+ }
311
+
312
+ .p-tabview-nav {
313
+ height: 48px;
314
+ }
315
+
package/src/main.tsx ADDED
@@ -0,0 +1,14 @@
1
+ import { StrictMode } from 'react'
2
+ import { createRoot } from 'react-dom/client'
3
+ import './index.css'
4
+ import App from './App.tsx'
5
+ import { MemoryRouter } from 'react-router-dom';
6
+ import 'hiver-ui-kit-extended/dist/hiver-ui-kit-extended.css';
7
+
8
+ createRoot(document.getElementById('root')!).render(
9
+ <StrictMode>
10
+ <MemoryRouter>
11
+ <App />
12
+ </MemoryRouter>
13
+ </StrictMode>,
14
+ )
@@ -0,0 +1,68 @@
1
+ import React from 'react';
2
+ import { useState } from 'react';
3
+ import Card from '../components/Card';
4
+ import { Tabs } from 'hiver-ui-kit-extended';
5
+ import messageIcon from '../assets/message.svg';
6
+ import contactsIcon from '../assets/contacts.svg';
7
+ import AccountsConversation from '../components/AccountsConversation';
8
+ import DetailsCard from '../components/DetailsCard';
9
+ import AccountDetails from '../components/AccountDetails';
10
+ import AccountContacts from '../components/AccountContacts';
11
+ import detailsIcon from '../assets/details.svg';
12
+
13
+ const AccountDetail: React.FC = () => {
14
+ const [activeIndex, setActiveIndex] = useState(0);
15
+ const tabsItems = [
16
+ {
17
+ label: (
18
+ <>
19
+ <img src={messageIcon} alt="conversations" className="cm:inline-block cm:mr-2 cm:w-3.5 cm:h-3.5" />
20
+ Conversations
21
+ </>
22
+ ) as unknown as string,
23
+ content: '',
24
+ url: '/accounts'
25
+ },
26
+ {
27
+ label: (
28
+ <>
29
+ <img src={contactsIcon} alt="contacts" className="cm:inline-block cm:mr-2 cm:w-3.5 cm:h-3.5" />
30
+ Contacts
31
+ </>
32
+ ) as unknown as string,
33
+ content: '',
34
+ url: '/google'
35
+ },
36
+ ];
37
+ const onTabChange = (e: any) => {
38
+ console.log('onTabChange', e);
39
+ setActiveIndex(e.index);
40
+ };
41
+
42
+ return (
43
+ <div className="cm:flex cm:gap-2 cm:items-start cm:relative cm:shrink-0 cm:w-full">
44
+ <Card>
45
+ <Tabs value={activeIndex} onTabChange={onTabChange} items={tabsItems} />
46
+ {activeIndex === 0 && <AccountsConversation />}
47
+ {activeIndex === 1 && <AccountContacts/>}
48
+ </Card>
49
+ <DetailsCard
50
+ header={
51
+ <div className="cm:flex cm:gap-2 cm:items-center cm:justify-center cm:px-0 cm:rounded-[6px] cm:shrink-0">
52
+ <div className="cm:relative cm:shrink-0 cm:w-3.5 cm:h-3.5">
53
+ <img src={detailsIcon} alt="details" className="cm:w-3.5 cm:h-3.5" />
54
+ </div>
55
+ <p className="cm:font-medium cm:leading-5 cm:text-sm cm:text-slate-text-body cm:whitespace-nowrap">
56
+ Account details
57
+ </p>
58
+ </div>
59
+ }
60
+ >
61
+ <AccountDetails />
62
+ </DetailsCard>
63
+ </div>
64
+ );
65
+ };
66
+
67
+ export default AccountDetail;
68
+
@@ -0,0 +1,12 @@
1
+ import React from 'react';
2
+ import AccountTable from '../components/Listing/AccountTable';
3
+
4
+ const Accounts: React.FC = () => {
5
+
6
+ return (
7
+ <AccountTable />
8
+ );
9
+ };
10
+
11
+ export default Accounts;
12
+
@@ -0,0 +1,55 @@
1
+ import React from 'react';
2
+ import { useState } from 'react';
3
+ import Card from '../components/Card';
4
+ import { Tabs } from 'hiver-ui-kit-extended';
5
+ import messageIcon from '../assets/message.svg';
6
+ import ContactConversation from '../components/ContactConversation';
7
+ import DetailsCard from '../components/DetailsCard';
8
+ import ContactDetails from '../components/ContactDetails';
9
+ import detailsIcon from '../assets/details.svg';
10
+
11
+ const ContactDetail: React.FC = () => {
12
+ const [activeIndex, setActiveIndex] = useState(0);
13
+ const tabsItems = [
14
+ {
15
+ label: (
16
+ <>
17
+ <img src={messageIcon} alt="conversations" className="cm:inline-block cm:mr-2 cm:w-3.5 cm:h-3.5" />
18
+ Conversations
19
+ </>
20
+ ) as unknown as string,
21
+ content: '',
22
+ url: '/contacts'
23
+ },
24
+ ];
25
+ const onTabChange = (e: any) => {
26
+ console.log('onTabChange', e);
27
+ setActiveIndex(e.index);
28
+ };
29
+
30
+ return (
31
+ <div className="cm:flex cm:gap-2 cm:items-start cm:relative cm:shrink-0 cm:w-full">
32
+ <Card>
33
+ <Tabs value={activeIndex} onTabChange={onTabChange} items={tabsItems} />
34
+ {activeIndex === 0 && <ContactConversation />}
35
+ </Card>
36
+ <DetailsCard
37
+ header={
38
+ <div className="cm:flex cm:gap-2 cm:h-8 cm:items-center cm:justify-center cm:px-0 cm:py-1 cm:rounded-[6px] cm:shrink-0">
39
+ <div className="cm:relative cm:shrink-0 cm:w-3.5 cm:h-3.5">
40
+ <img src={detailsIcon} alt="details" className="cm:w-3.5 cm:h-3.5" />
41
+ </div>
42
+ <p className="cm:font-medium cm:leading-5 cm:text-sm cm:text-slate-text-body cm:whitespace-nowrap">
43
+ Contact details
44
+ </p>
45
+ </div>
46
+ }
47
+ >
48
+ <ContactDetails />
49
+ </DetailsCard>
50
+ </div>
51
+ );
52
+ };
53
+
54
+ export default ContactDetail;
55
+
@@ -0,0 +1,12 @@
1
+ import React from 'react';
2
+ import ContactTable from '../components/Listing/ContactTable';
3
+
4
+ const Contacts: React.FC = () => {
5
+
6
+ return (
7
+ <ContactTable />
8
+ );
9
+ };
10
+
11
+ export default Contacts;
12
+
@@ -0,0 +1,17 @@
1
+ import { create } from 'zustand'
2
+
3
+ interface CountState {
4
+ count: number
5
+ increment: () => void
6
+ decrement: () => void
7
+ reset: () => void
8
+ setCount: (count: number) => void
9
+ }
10
+
11
+ export const useCountStore = create<CountState>((set) => ({
12
+ count: 0,
13
+ increment: () => set((state) => ({ count: state.count + 1 })),
14
+ decrement: () => set((state) => ({ count: state.count - 1 })),
15
+ reset: () => set({ count: 0 }),
16
+ setCount: (count: number) => set({ count }),
17
+ }))
File without changes