globalfy-design-system 0.1.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 (107) hide show
  1. package/.babelrc +7 -0
  2. package/.eslintrc.cjs +20 -0
  3. package/.husky/commit-msg +4 -0
  4. package/.husky/pre-commit +4 -0
  5. package/.lintstagedrc +4 -0
  6. package/.nvmrc +1 -0
  7. package/.prettierrc +3 -0
  8. package/.storybook/main.ts +20 -0
  9. package/.storybook/preview-head.html +6 -0
  10. package/.storybook/preview.ts +17 -0
  11. package/CODEOWNERS +1 -0
  12. package/README.md +40 -0
  13. package/bitbucket-pipelines.yml +37 -0
  14. package/commitlint.config.cjs +1 -0
  15. package/components.json +16 -0
  16. package/index.html +13 -0
  17. package/jest.config.js +9 -0
  18. package/package.json +84 -0
  19. package/postcss.config.js +6 -0
  20. package/public/vite.svg +1 -0
  21. package/src/assets/fonts/satoshi/Satoshi-Black.ttf +0 -0
  22. package/src/assets/fonts/satoshi/Satoshi-Black.woff +0 -0
  23. package/src/assets/fonts/satoshi/Satoshi-Black.woff2 +0 -0
  24. package/src/assets/fonts/satoshi/Satoshi-Bold.ttf +0 -0
  25. package/src/assets/fonts/satoshi/Satoshi-Bold.woff +0 -0
  26. package/src/assets/fonts/satoshi/Satoshi-Bold.woff2 +0 -0
  27. package/src/assets/fonts/satoshi/Satoshi-Medium.ttf +0 -0
  28. package/src/assets/fonts/satoshi/Satoshi-Medium.woff +0 -0
  29. package/src/assets/fonts/satoshi/Satoshi-Medium.woff2 +0 -0
  30. package/src/assets/fonts/satoshi/Satoshi-Regular.ttf +0 -0
  31. package/src/assets/fonts/satoshi/Satoshi-Regular.woff +0 -0
  32. package/src/assets/fonts/satoshi/Satoshi-Regular.woff2 +0 -0
  33. package/src/assets/fonts/satoshi/satoshi.css +43 -0
  34. package/src/components/atoms/Avatar/Avatar.stories.tsx +26 -0
  35. package/src/components/atoms/Avatar/Avatar.test.tsx +19 -0
  36. package/src/components/atoms/Avatar/Avatar.tsx +46 -0
  37. package/src/components/atoms/Avatar/Avatar.types.ts +7 -0
  38. package/src/components/atoms/Avatar/index.ts +2 -0
  39. package/src/components/atoms/Checkbox/Checkbox.stories.tsx +19 -0
  40. package/src/components/atoms/Checkbox/Checkbox.test.tsx +12 -0
  41. package/src/components/atoms/Checkbox/Checkbox.tsx +20 -0
  42. package/src/components/atoms/Checkbox/index.ts +1 -0
  43. package/src/components/atoms/FieldMessage/FieldMessage.stories.tsx +20 -0
  44. package/src/components/atoms/FieldMessage/FieldMessage.test.tsx +14 -0
  45. package/src/components/atoms/FieldMessage/FieldMessage.tsx +6 -0
  46. package/src/components/atoms/FieldMessage/FieldMessage.type.ts +3 -0
  47. package/src/components/atoms/FieldMessage/index.ts +2 -0
  48. package/src/components/atoms/Flag/Flag.stories.tsx +34 -0
  49. package/src/components/atoms/Flag/Flag.tsx +35 -0
  50. package/src/components/atoms/Flag/Flag.types.ts +6 -0
  51. package/src/components/atoms/Flag/images/bra.svg +8 -0
  52. package/src/components/atoms/Flag/images/esp.svg +6 -0
  53. package/src/components/atoms/Flag/images/usa.svg +9 -0
  54. package/src/components/atoms/Flag/index.ts +2 -0
  55. package/src/components/atoms/Icon/Icon.stories.tsx +32 -0
  56. package/src/components/atoms/Icon/Icon.tsx +6 -0
  57. package/src/components/atoms/Icon/assets/fonts/icomoon.eot +0 -0
  58. package/src/components/atoms/Icon/assets/fonts/icomoon.svg +21 -0
  59. package/src/components/atoms/Icon/assets/fonts/icomoon.ttf +0 -0
  60. package/src/components/atoms/Icon/assets/fonts/icomoon.woff +0 -0
  61. package/src/components/atoms/Icon/assets/selection.json +285 -0
  62. package/src/components/atoms/Icon/assets/style.css +60 -0
  63. package/src/components/atoms/Icon/icon.types.ts +17 -0
  64. package/src/components/atoms/Icon/index.ts +2 -0
  65. package/src/components/atoms/Logo/Logo.stories.tsx +20 -0
  66. package/src/components/atoms/Logo/Logo.test.tsx +11 -0
  67. package/src/components/atoms/Logo/Logo.tsx +12 -0
  68. package/src/components/atoms/Logo/Logo.types.ts +3 -0
  69. package/src/components/atoms/Logo/images/globalfy_desktop.svg +9 -0
  70. package/src/components/atoms/Logo/images/globalfy_mobile.svg +3 -0
  71. package/src/components/atoms/Logo/index.ts +2 -0
  72. package/src/components/atoms/RadioGroup/RadioGroup.stories.tsx +21 -0
  73. package/src/components/atoms/RadioGroup/RadioGroup.test.tsx +47 -0
  74. package/src/components/atoms/RadioGroup/RadioGroup.tsx +26 -0
  75. package/src/components/atoms/RadioGroup/RadioGroup.types.ts +12 -0
  76. package/src/components/atoms/RadioGroup/index.ts +1 -0
  77. package/src/components/atoms/Switch/Switch.stories.tsx +18 -0
  78. package/src/components/atoms/Switch/Switch.test.tsx +12 -0
  79. package/src/components/atoms/Switch/Switch.tsx +32 -0
  80. package/src/components/atoms/Switch/Switch.types.ts +3 -0
  81. package/src/components/atoms/Switch/index.ts +2 -0
  82. package/src/components/atoms/Typography/Typography.stories.tsx +18 -0
  83. package/src/components/atoms/Typography/Typography.test.tsx +10 -0
  84. package/src/components/atoms/Typography/Typography.tsx +37 -0
  85. package/src/components/atoms/Typography/Typography.types.ts +7 -0
  86. package/src/components/atoms/Typography/index.ts +2 -0
  87. package/src/components/atoms/index.ts +9 -0
  88. package/src/components/index.ts +1 -0
  89. package/src/global.css +76 -0
  90. package/src/main.ts +1 -0
  91. package/src/shadcn/components/ui/avatar.tsx +48 -0
  92. package/src/shadcn/components/ui/button.tsx +55 -0
  93. package/src/shadcn/components/ui/checkbox.tsx +28 -0
  94. package/src/shadcn/components/ui/form.tsx +177 -0
  95. package/src/shadcn/components/ui/label.tsx +23 -0
  96. package/src/shadcn/components/ui/radio-group.tsx +44 -0
  97. package/src/shadcn/components/ui/switch.tsx +27 -0
  98. package/src/shadcn/utils.ts +6 -0
  99. package/src/utils/reactHookForm/FormWrapper.tsx +12 -0
  100. package/src/utils/tailwind/classNames.ts +4 -0
  101. package/src/vite-env.d.ts +1 -0
  102. package/tailwind.config.js +98 -0
  103. package/testSetup.ts +1 -0
  104. package/tsconfig.json +32 -0
  105. package/tsconfig.node.json +10 -0
  106. package/vite.config.ts +23 -0
  107. package/yarn.lock +10721 -0
package/.babelrc ADDED
@@ -0,0 +1,7 @@
1
+ {
2
+ "presets": [
3
+ "@babel/preset-env",
4
+ "@babel/preset-typescript",
5
+ ["@babel/preset-react", { "runtime": "automatic" }]
6
+ ]
7
+ }
package/.eslintrc.cjs ADDED
@@ -0,0 +1,20 @@
1
+ module.exports = {
2
+ root: true,
3
+ env: { browser: true, es2020: true, node: true },
4
+ extends: [
5
+ "eslint:recommended",
6
+ "plugin:@typescript-eslint/recommended",
7
+ "plugin:react-hooks/recommended",
8
+ "prettier",
9
+ "plugin:storybook/recommended"
10
+ ],
11
+ ignorePatterns: ["dist", ".eslintrc.cjs"],
12
+ parser: "@typescript-eslint/parser",
13
+ plugins: ["react-refresh", "jest-react"],
14
+ rules: {
15
+ "react-refresh/only-export-components": [
16
+ "warn",
17
+ { allowConstantExport: true }
18
+ ]
19
+ }
20
+ };
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env sh
2
+ . "$(dirname -- "$0")/_/husky.sh"
3
+
4
+ npx --no -- commitlint --edit ${1}
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env sh
2
+ . "$(dirname -- "$0")/_/husky.sh"
3
+
4
+ yarn lint-staged --concurrent false
package/.lintstagedrc ADDED
@@ -0,0 +1,4 @@
1
+ {
2
+ "*.{js,jsx,ts,tsx}": ["prettier --write", "eslint --fix", "eslint"],
3
+ "*.json": ["prettier --write"]
4
+ }
package/.nvmrc ADDED
@@ -0,0 +1 @@
1
+ 18.18.2
package/.prettierrc ADDED
@@ -0,0 +1,3 @@
1
+ {
2
+ "trailingComma": "none"
3
+ }
@@ -0,0 +1,20 @@
1
+ import type { StorybookConfig } from "@storybook/react-vite";
2
+
3
+ const config: StorybookConfig = {
4
+ stories: ["../src/**/*.mdx", "../src/**/*.stories.@(js|jsx|mjs|ts|tsx)"],
5
+ addons: [
6
+ "@storybook/addon-links",
7
+ "@storybook/addon-essentials",
8
+ "@storybook/addon-onboarding",
9
+ "@storybook/addon-interactions",
10
+ "@storybook/addon-styling"
11
+ ],
12
+ framework: {
13
+ name: "@storybook/react-vite",
14
+ options: {}
15
+ },
16
+ docs: {
17
+ autodocs: "tag"
18
+ }
19
+ };
20
+ export default config;
@@ -0,0 +1,6 @@
1
+ <link rel="preconnect" href="https://fonts.googleapis.com" />
2
+ <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
3
+ <link
4
+ href="https://fonts.googleapis.com/css2?family=Livvic:wght@300;400;500;600;700;900&display=swap"
5
+ rel="stylesheet"
6
+ />
@@ -0,0 +1,17 @@
1
+ import type { Preview } from "@storybook/react";
2
+ import "../src/global.css";
3
+ import "../src/assets/fonts/satoshi/satoshi.css";
4
+
5
+ const preview: Preview = {
6
+ parameters: {
7
+ actions: { argTypesRegex: "^on[A-Z].*" },
8
+ controls: {
9
+ matchers: {
10
+ color: /(background|color)$/i,
11
+ date: /Date$/i
12
+ }
13
+ }
14
+ }
15
+ };
16
+
17
+ export default preview;
package/CODEOWNERS ADDED
@@ -0,0 +1 @@
1
+ * jefferson.belchior@globalfy.com
package/README.md ADDED
@@ -0,0 +1,40 @@
1
+ # Globalfy Design System
2
+
3
+ Shared Components Library ready to use on React Globalfy projects
4
+
5
+ ## Working on the project
6
+
7
+ ### Scripts
8
+
9
+ - _test_ Run the unit tests
10
+ - _build_ Build the library
11
+ - _lint_ Run the project linter
12
+ - _storybook_ Run the storybook
13
+ - _build-storybook_ Build the storybook
14
+
15
+ ### Branchs
16
+
17
+ - Every work branch must be created from the `Develop` branch
18
+ - The Branch must follow the following pattern `<feature | fix>/<taskScope-taskNumber>-<taskDescription>`
19
+ - Working on a task `feature/aa-0000-drink-coffee`
20
+ - Working on a bug `fix/aa-0000-add-sugar`
21
+
22
+ ### Commits
23
+
24
+ The project is configured with commit [rules](https://github.com/conventional-changelog/commitlint/tree/master/%40commitlint/config-conventional#rules) that are checked every time a new commit is added, to be able to commit you must follow this pattern:
25
+
26
+ type(scope?): message
27
+
28
+ feat: new AgGrid component
29
+ fix: missing email validation
30
+ fix(validations): missing email validation
31
+
32
+ - _TYPE:_ Type of commit [build, chore, ci, docs, feat, fix, perf, refactor, revert, style, test]
33
+ - _SCOPE:_ Scope of the changes, it's not required
34
+ - _MESSAGE:_ The commit message
35
+
36
+ ### Tests
37
+
38
+ - Unit tests use [Jest](<[https://https://jestjs.io//](https://jestjs.io/)>) with [react-testing-library](https://testing-library.com/docs/react-testing-library/intro/)
39
+ - All components developed must have tests
40
+ - Test coverage must be 100%
@@ -0,0 +1,37 @@
1
+ image: node:18.18.2
2
+
3
+ definitions:
4
+ steps:
5
+ - step: &test
6
+ name: Test
7
+ cache:
8
+ - node
9
+ script:
10
+ - yarn install
11
+ - yarn test
12
+ - step: &build
13
+ name: Build
14
+ cache:
15
+ - node
16
+ script:
17
+ - yarn add -g typescript@5.0.2 vite@4.4.5
18
+ - yarn build
19
+ - step: &publish
20
+ name: Publish
21
+ deployment: production
22
+ script:
23
+ - npm version minor -m "[skip ci] Upgrade to %s"
24
+ - git push && git push --tags
25
+ - pipe: atlassian/npm-publish:0.2.0
26
+ variables:
27
+ NPM_TOKEN: $NPM_TOKEN
28
+
29
+ pipelines:
30
+ default:
31
+ - step: *test
32
+ - step: *build
33
+ branches:
34
+ master:
35
+ - step: *test
36
+ - step: *build
37
+ - step: *publish
@@ -0,0 +1 @@
1
+ module.exports = { extends: ["@commitlint/config-conventional"] };
@@ -0,0 +1,16 @@
1
+ {
2
+ "$schema": "https://ui.shadcn.com/schema.json",
3
+ "style": "default",
4
+ "rsc": false,
5
+ "tsx": true,
6
+ "tailwind": {
7
+ "config": "tailwind.config.js",
8
+ "css": "src/global.css",
9
+ "baseColor": "slate",
10
+ "cssVariables": true
11
+ },
12
+ "aliases": {
13
+ "components": "@/shadcn/components",
14
+ "utils": "@/shadcn/"
15
+ }
16
+ }
package/index.html ADDED
@@ -0,0 +1,13 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <link rel="icon" type="image/svg+xml" href="/vite.svg" />
6
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
+ <title>Vite + React + TS</title>
8
+ </head>
9
+ <body>
10
+ <div id="root"></div>
11
+ <script type="module" src="/src/main.tsx"></script>
12
+ </body>
13
+ </html>
package/jest.config.js ADDED
@@ -0,0 +1,9 @@
1
+ export default {
2
+ testEnvironment: "jsdom",
3
+ moduleNameMapper: {
4
+ "^.+\\.svg$": "jest-svg-transformer",
5
+ "^.+\\.(css|less|scss)$": "identity-obj-proxy",
6
+ "^@/(.*)$": "<rootDir>/src/$1"
7
+ },
8
+ setupFilesAfterEnv: ["<rootDir>/testSetup.ts"]
9
+ };
package/package.json ADDED
@@ -0,0 +1,84 @@
1
+ {
2
+ "name": "globalfy-design-system",
3
+ "version": "0.1.0",
4
+ "description": "Globalfy Design System",
5
+ "type": "module",
6
+ "scripts": {
7
+ "test": "jest --coverage",
8
+ "test:watch": "jest --watch --coverage",
9
+ "build": "tsc && vite build",
10
+ "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
11
+ "storybook": "storybook dev -p 6006",
12
+ "build-storybook": "storybook build",
13
+ "postinstall": "husky install"
14
+ },
15
+ "dependencies": {
16
+ "@hookform/resolvers": "^3.3.2",
17
+ "@radix-ui/react-checkbox": "^1.0.4",
18
+ "@radix-ui/react-avatar": "^1.0.4",
19
+ "@radix-ui/react-label": "^2.0.2",
20
+ "@radix-ui/react-radio-group": "^1.1.3",
21
+ "@radix-ui/react-slot": "^1.0.2",
22
+ "@radix-ui/react-switch": "^1.0.3",
23
+ "class-variance-authority": "^0.7.0",
24
+ "clsx": "^2.0.0",
25
+ "lucide-react": "^0.288.0",
26
+ "react": "^18.2.0",
27
+ "react-dom": "^18.2.0",
28
+ "react-hook-form": "^7.47.0",
29
+ "tailwind-merge": "^1.14.0",
30
+ "tailwindcss-animate": "^1.0.7",
31
+ "zod": "^3.22.4"
32
+ },
33
+ "devDependencies": {
34
+ "@babel/preset-env": "^7.23.3",
35
+ "@babel/preset-react": "^7.23.3",
36
+ "@babel/preset-typescript": "^7.23.3",
37
+ "@commitlint/cli": "^18.0.0",
38
+ "@commitlint/config-conventional": "^18.0.0",
39
+ "@storybook/addon-essentials": "^7.5.1",
40
+ "@storybook/addon-interactions": "^7.5.1",
41
+ "@storybook/addon-links": "^7.5.1",
42
+ "@storybook/addon-onboarding": "^1.0.8",
43
+ "@storybook/addon-styling": "^1.3.7",
44
+ "@storybook/blocks": "^7.5.1",
45
+ "@storybook/react": "^7.5.1",
46
+ "@storybook/react-vite": "^7.5.1",
47
+ "@storybook/testing-library": "^0.2.2",
48
+ "@testing-library/jest-dom": "^6.1.4",
49
+ "@testing-library/react": "^14.1.0",
50
+ "@types/jest": "^29.5.8",
51
+ "@types/node": "^20.8.7",
52
+ "@types/react": "^18.2.15",
53
+ "@types/react-dom": "^18.2.7",
54
+ "@typescript-eslint/eslint-plugin": "^6.0.0",
55
+ "@typescript-eslint/parser": "^6.0.0",
56
+ "@vitejs/plugin-react": "^4.0.3",
57
+ "autoprefixer": "^10.4.16",
58
+ "babel-jest": "^29.7.0",
59
+ "eslint": "^8.45.0",
60
+ "eslint-config-prettier": "^9.0.0",
61
+ "eslint-plugin-jest-react": "^0.1.0",
62
+ "eslint-plugin-react-hooks": "^4.6.0",
63
+ "eslint-plugin-react-refresh": "^0.4.3",
64
+ "eslint-plugin-storybook": "^0.6.15",
65
+ "husky": "^8.0.0",
66
+ "identity-obj-proxy": "^3.0.0",
67
+ "jest": "^29.7.0",
68
+ "jest-environment-jsdom": "^29.7.0",
69
+ "jest-svg-transformer": "^1.0.0",
70
+ "jsdom": "^22.1.0",
71
+ "lint-staged": "^15.0.2",
72
+ "postcss": "^8.4.31",
73
+ "prettier": "^3.0.3",
74
+ "react-test-renderer": "^18.2.0",
75
+ "storybook": "^7.5.1",
76
+ "tailwindcss": "^3.3.3",
77
+ "typescript": "^5.0.2",
78
+ "vite": "^4.4.5",
79
+ "vite-plugin-svgr": "^4.1.0"
80
+ },
81
+ "resolutions": {
82
+ "jackspeak": "2.1.1"
83
+ }
84
+ }
@@ -0,0 +1,6 @@
1
+ export default {
2
+ plugins: {
3
+ tailwindcss: {},
4
+ autoprefixer: {},
5
+ },
6
+ };
@@ -0,0 +1 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>
@@ -0,0 +1,43 @@
1
+ @font-face {
2
+ font-family: "Satoshi-Regular";
3
+ src:
4
+ url("./Satoshi-Regular.woff2") format("woff2"),
5
+ url("./Satoshi-Regular.woff") format("woff"),
6
+ url("./Satoshi-Regular.ttf") format("truetype");
7
+ font-weight: 400;
8
+ font-display: swap;
9
+ font-style: normal;
10
+ }
11
+
12
+ @font-face {
13
+ font-family: "Satoshi-Medium";
14
+ src:
15
+ url("./Satoshi-Medium.woff2") format("woff2"),
16
+ url("./Satoshi-Medium.woff") format("woff"),
17
+ url("./Satoshi-Medium.ttf") format("truetype");
18
+ font-weight: 500;
19
+ font-display: swap;
20
+ font-style: normal;
21
+ }
22
+
23
+ @font-face {
24
+ font-family: "Satoshi-Bold";
25
+ src:
26
+ url("./Satoshi-Bold.woff2") format("woff2"),
27
+ url("./Satoshi-Bold.woff") format("woff"),
28
+ url("./Satoshi-Bold.ttf") format("truetype");
29
+ font-weight: 700;
30
+ font-display: swap;
31
+ font-style: normal;
32
+ }
33
+
34
+ @font-face {
35
+ font-family: "Satoshi-Black";
36
+ src:
37
+ url("./Satoshi-Black.woff2") format("woff2"),
38
+ url("./Satoshi-Black.woff") format("woff"),
39
+ url("./Satoshi-Black.ttf") format("truetype");
40
+ font-weight: 900;
41
+ font-display: swap;
42
+ font-style: normal;
43
+ }
@@ -0,0 +1,26 @@
1
+ import { Meta, StoryObj } from "@storybook/react";
2
+
3
+ import { Avatar } from ".";
4
+
5
+ const meta = {
6
+ title: "Components/Atoms/Avatar",
7
+ component: Avatar,
8
+ tags: ["autodocs"]
9
+ } satisfies Meta<typeof Avatar>;
10
+
11
+ export default meta;
12
+
13
+ type Story = StoryObj<typeof meta>;
14
+
15
+ export const Playground: Story = {
16
+ args: {
17
+ image: "https://picsum.photos/160"
18
+ }
19
+ };
20
+
21
+ export const Sizes = () => (
22
+ <div className="flex gap-4 items-center">
23
+ <Avatar size="small" image="https://picsum.photos/160" />
24
+ <Avatar size="large" image="https://picsum.photos/160" />
25
+ </div>
26
+ );
@@ -0,0 +1,19 @@
1
+ import { render } from "@testing-library/react";
2
+
3
+ import { Avatar } from "./Avatar";
4
+
5
+ describe("Avatar Component", () => {
6
+ test("should render small size", async () => {
7
+ const { container } = render(<Avatar image="https://picsum.photos/160" />);
8
+
9
+ expect(container.firstElementChild?.classList).toContain("w-[75px]");
10
+ });
11
+
12
+ test("should render large size", async () => {
13
+ const { container } = render(
14
+ <Avatar size="large" image="https://picsum.photos/160" />
15
+ );
16
+
17
+ expect(container.firstElementChild?.classList).toContain("w-[172px]");
18
+ });
19
+ });
@@ -0,0 +1,46 @@
1
+ import {
2
+ Avatar as ShadcnAvatar,
3
+ AvatarFallback,
4
+ AvatarImage
5
+ } from "@/shadcn/components/ui/avatar";
6
+ import { AvatarProps } from "./Avatar.types";
7
+ import { Icon } from "..";
8
+ import { cva } from "class-variance-authority";
9
+ import { classNames } from "@/utils/tailwind/classNames";
10
+
11
+ export const Avatar = ({
12
+ image,
13
+ size = "small",
14
+ onLoadingStatusChange
15
+ }: AvatarProps) => {
16
+ const iconVariants = cva("text-globalfy-grey500", {
17
+ variants: {
18
+ size: {
19
+ small: "text-[32px]",
20
+ large: "text-[64px]"
21
+ }
22
+ }
23
+ });
24
+
25
+ const avatarVariants = cva("border-globalfy-grey500 bg-globalfy-grey500", {
26
+ variants: {
27
+ size: {
28
+ small: "w-[75px] h-[75px] border-[3px]",
29
+ large: "w-[172px] h-[172px] border-[5px]"
30
+ }
31
+ }
32
+ });
33
+
34
+ return (
35
+ <ShadcnAvatar className={classNames(avatarVariants({ size }))}>
36
+ <AvatarImage
37
+ onLoadingStatusChange={onLoadingStatusChange}
38
+ src={image}
39
+ alt="user avatar"
40
+ />
41
+ <AvatarFallback className="bg-globalfy-white">
42
+ <Icon name="user" className={classNames(iconVariants({ size }))} />
43
+ </AvatarFallback>
44
+ </ShadcnAvatar>
45
+ );
46
+ };
@@ -0,0 +1,7 @@
1
+ import { HTMLAttributes } from "react";
2
+
3
+ export type AvatarProps = {
4
+ image: string;
5
+ size?: "small" | "large";
6
+ onLoadingStatusChange?: (status: string) => void;
7
+ } & HTMLAttributes<HTMLImageElement>;
@@ -0,0 +1,2 @@
1
+ export * from "./Avatar";
2
+ export * from "./Avatar.types";
@@ -0,0 +1,19 @@
1
+ import { Meta, StoryObj } from "@storybook/react";
2
+ import { Checkbox } from "./Checkbox";
3
+
4
+ const meta = {
5
+ title: "Components/Atoms/Checkbox",
6
+ component: Checkbox,
7
+ tags: ["autodocs"]
8
+ } satisfies Meta<typeof Checkbox>;
9
+
10
+ export default meta;
11
+
12
+ type Story = StoryObj<typeof meta>;
13
+
14
+ export const Default: Story = {
15
+ args: {
16
+ disabled: false,
17
+ checked: true
18
+ }
19
+ };
@@ -0,0 +1,12 @@
1
+ import { render } from "@testing-library/react";
2
+
3
+ import { Checkbox } from "./Checkbox";
4
+
5
+ describe("Checkbox Component", () => {
6
+ test("should render a checkbox component", async () => {
7
+ const { getByRole } = await render(<Checkbox />);
8
+ const checkbox = getByRole("checkbox");
9
+
10
+ expect(checkbox).toBeTruthy();
11
+ });
12
+ });
@@ -0,0 +1,20 @@
1
+ import * as React from "react";
2
+ import * as CheckboxPrimitive from "@radix-ui/react-checkbox";
3
+ import { Checkbox as SCNCheckbox } from "@/shadcn/components/ui/checkbox";
4
+ import { classNames } from "@/utils/tailwind/classNames";
5
+
6
+ export const Checkbox = React.forwardRef<
7
+ React.ElementRef<typeof CheckboxPrimitive.Root>,
8
+ React.ComponentPropsWithoutRef<typeof CheckboxPrimitive.Root>
9
+ >(({ className, ...props }, ref) => {
10
+ return (
11
+ <SCNCheckbox
12
+ ref={ref}
13
+ className={classNames(
14
+ className,
15
+ "flex items-center justify-center border rounded-[2px] border-globalfy-grey600 data-[state=checked]:bg-globalfy-primaryGreen data-[state=checked]:border-globalfy-primaryGreen [&>*]:w-3 [&>*]:h-3"
16
+ )}
17
+ {...props}
18
+ />
19
+ );
20
+ });
@@ -0,0 +1 @@
1
+ export * from "./Checkbox";
@@ -0,0 +1,20 @@
1
+ import type { Meta, StoryObj } from "@storybook/react";
2
+ import { FieldMessage } from ".";
3
+ import { FormWrapper } from "@/utils/reactHookForm/FormWrapper";
4
+
5
+ type FieldMessageProps = React.ComponentProps<typeof FieldMessage>;
6
+
7
+ const meta: Meta<FieldMessageProps> = {
8
+ component: FieldMessage,
9
+ render: ({ children, ...args }) => <FormWrapper {...{ children, ...args }} />
10
+ };
11
+
12
+ export default meta;
13
+
14
+ type Story = StoryObj<FieldMessageProps>;
15
+
16
+ export const Playground: Story = {
17
+ args: {
18
+ children: "Sample message"
19
+ }
20
+ };
@@ -0,0 +1,14 @@
1
+ import { render, screen } from "@testing-library/react";
2
+ import { FormWrapper } from "@/utils/reactHookForm/FormWrapper";
3
+ import { FieldMessage } from ".";
4
+
5
+ describe("FieldMessage Component", () => {
6
+ test("should render the provided children", () => {
7
+ render(
8
+ <FormWrapper>
9
+ <FieldMessage>Test Message</FieldMessage>
10
+ </FormWrapper>
11
+ );
12
+ expect(screen.getByText("Test Message")).toBeTruthy();
13
+ });
14
+ });
@@ -0,0 +1,6 @@
1
+ import { FormMessage } from "@/shadcn/components/ui/form";
2
+ import { FieldMessageProps } from "./FieldMessage.type";
3
+
4
+ export const FieldMessage = ({ children }: FieldMessageProps) => {
5
+ return <FormMessage>{children}</FormMessage>;
6
+ };
@@ -0,0 +1,3 @@
1
+ export type FieldMessageProps = {
2
+ children: React.ReactNode;
3
+ };
@@ -0,0 +1,2 @@
1
+ export * from "./FieldMessage";
2
+ export * from "./FieldMessage.type";