@julianoczkowski/create-trimble-app 2.0.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.
- package/README.md +191 -0
- package/bin/create-trimble-app.js +9 -0
- package/package.json +67 -0
- package/src/cli.js +134 -0
- package/src/frameworks.js +28 -0
- package/src/scaffold.js +209 -0
- package/src/utils/file.js +47 -0
- package/src/utils/git.js +140 -0
- package/src/utils/install.js +25 -0
- package/src/utils/logger.js +124 -0
- package/templates/angular/.cursor/commands/remove-dev-content.md +394 -0
- package/templates/angular/.cursor/mcp.json +13 -0
- package/templates/angular/.cursor/rules/modus-angular-20.mdc +82 -0
- package/templates/angular/.cursor/rules/modus-angular-accordion-state-management-short.mdc +45 -0
- package/templates/angular/.cursor/rules/modus-angular-accordion-state-management.mdc +322 -0
- package/templates/angular/.cursor/rules/modus-angular-best-practices.mdc +472 -0
- package/templates/angular/.cursor/rules/modus-angular-border-usage-short.mdc +48 -0
- package/templates/angular/.cursor/rules/modus-angular-border-usage.mdc +286 -0
- package/templates/angular/.cursor/rules/modus-angular-button-group-usage-short.mdc +47 -0
- package/templates/angular/.cursor/rules/modus-angular-button-group-usage.mdc +263 -0
- package/templates/angular/.cursor/rules/modus-angular-checkbox-value-inversion-short.mdc +36 -0
- package/templates/angular/.cursor/rules/modus-angular-checkbox-value-inversion.mdc +92 -0
- package/templates/angular/.cursor/rules/modus-angular-chrome-devtools-testing-short.mdc +34 -0
- package/templates/angular/.cursor/rules/modus-angular-chrome-devtools-testing.mdc +185 -0
- package/templates/angular/.cursor/rules/modus-angular-color-usage-short.mdc +56 -0
- package/templates/angular/.cursor/rules/modus-angular-color-usage.mdc +208 -0
- package/templates/angular/.cursor/rules/modus-angular-components-reference.mdc +114 -0
- package/templates/angular/.cursor/rules/modus-angular-design-system.mdc +273 -0
- package/templates/angular/.cursor/rules/modus-angular-development-workflow-short.mdc +43 -0
- package/templates/angular/.cursor/rules/modus-angular-development-workflow.mdc +145 -0
- package/templates/angular/.cursor/rules/modus-angular-essentials.mdc +272 -0
- package/templates/angular/.cursor/rules/modus-angular-forms-validation-short.mdc +56 -0
- package/templates/angular/.cursor/rules/modus-angular-forms-validation.mdc +124 -0
- package/templates/angular/.cursor/rules/modus-angular-icon-names.mdc +70 -0
- package/templates/angular/.cursor/rules/modus-angular-icons-short.mdc +40 -0
- package/templates/angular/.cursor/rules/modus-angular-icons.mdc +137 -0
- package/templates/angular/.cursor/rules/modus-angular-implementation-guides-short.mdc +36 -0
- package/templates/angular/.cursor/rules/modus-angular-implementation-guides.mdc +301 -0
- package/templates/angular/.cursor/rules/modus-angular-integration-short.mdc +60 -0
- package/templates/angular/.cursor/rules/modus-angular-integration.mdc +1096 -0
- package/templates/angular/.cursor/rules/modus-angular-master.mdc +164 -0
- package/templates/angular/.cursor/rules/modus-angular-modal-usage-short.mdc +51 -0
- package/templates/angular/.cursor/rules/modus-angular-modal-usage.mdc +115 -0
- package/templates/angular/.cursor/rules/modus-angular-navbar-usage-short.mdc +49 -0
- package/templates/angular/.cursor/rules/modus-angular-navbar-usage.mdc +146 -0
- package/templates/angular/.cursor/rules/modus-angular-no-emojis.mdc +66 -0
- package/templates/angular/.cursor/rules/modus-angular-opacity-utilities-short.mdc +43 -0
- package/templates/angular/.cursor/rules/modus-angular-opacity-utilities.mdc +160 -0
- package/templates/angular/.cursor/rules/modus-angular-select-vs-dropdown-menu-short.mdc +51 -0
- package/templates/angular/.cursor/rules/modus-angular-select-vs-dropdown-menu.mdc +83 -0
- package/templates/angular/.cursor/rules/modus-angular-semantic-html-short.mdc +36 -0
- package/templates/angular/.cursor/rules/modus-angular-semantic-html.mdc +81 -0
- package/templates/angular/.cursor/rules/modus-angular-side-navigation-usage-short.mdc +50 -0
- package/templates/angular/.cursor/rules/modus-angular-side-navigation-usage.mdc +136 -0
- package/templates/angular/.cursor/rules/modus-angular-table-usage-short.mdc +52 -0
- package/templates/angular/.cursor/rules/modus-angular-table-usage.mdc +151 -0
- package/templates/angular/.cursor/rules/modus-angular-tailwind-usage-short.mdc +44 -0
- package/templates/angular/.cursor/rules/modus-angular-tailwind-usage.mdc +242 -0
- package/templates/angular/.cursor/rules/modus-angular-themes-short.mdc +54 -0
- package/templates/angular/.cursor/rules/modus-angular-themes.mdc +222 -0
- package/templates/angular/.cursor/rules/modus-angular-utility-panel-usage-short.mdc +52 -0
- package/templates/angular/.cursor/rules/modus-angular-utility-panel-usage.mdc +130 -0
- package/templates/angular/.cursor/rules/ux/gestalt-laws-detailed.mdc +514 -0
- package/templates/angular/.cursor/rules/ux/ux-ui-foundations.mdc +235 -0
- package/templates/angular/.cursor/skills/run-lint-checks/SKILL.md +169 -0
- package/templates/angular/.editorconfig +17 -0
- package/templates/angular/.github/dependabot.yml +19 -0
- package/templates/angular/.github/workflows/a11y-check.yml +135 -0
- package/templates/angular/.github/workflows/ci.yml +44 -0
- package/templates/angular/.husky/pre-commit +32 -0
- package/templates/angular/.postcssrc.json +5 -0
- package/templates/angular/.vscode/extensions.json +4 -0
- package/templates/angular/.vscode/launch.json +20 -0
- package/templates/angular/.vscode/tasks.json +42 -0
- package/templates/angular/CLAUDE.md +148 -0
- package/templates/angular/README.md +92 -0
- package/templates/angular/amplify.yml +25 -0
- package/templates/angular/angular.json +106 -0
- package/templates/angular/data/modusIcons.ts +861 -0
- package/templates/angular/package-lock.json +11030 -0
- package/templates/angular/package.json +66 -0
- package/templates/angular/public/angular-icon.svg +12 -0
- package/templates/angular/public/favicon.ico +0 -0
- package/templates/angular/public/modus-icons.css +49 -0
- package/templates/angular/public/vite.svg +1 -0
- package/templates/angular/scripts/README.md +410 -0
- package/templates/angular/scripts/check-border-violations.js +352 -0
- package/templates/angular/scripts/check-icon-names.js +402 -0
- package/templates/angular/scripts/check-inline-styles.js +292 -0
- package/templates/angular/scripts/check-modus-colors.js +282 -0
- package/templates/angular/scripts/check-modus-icons.js +263 -0
- package/templates/angular/scripts/check-opacity-utilities.js +426 -0
- package/templates/angular/scripts/check-semantic-html.js +452 -0
- package/templates/angular/scripts/check-typescript.js +109 -0
- package/templates/angular/src/app/app.config.ts +29 -0
- package/templates/angular/src/app/app.css +0 -0
- package/templates/angular/src/app/app.html +4 -0
- package/templates/angular/src/app/app.routes.ts +351 -0
- package/templates/angular/src/app/app.spec.ts +27 -0
- package/templates/angular/src/app/app.ts +47 -0
- package/templates/angular/src/app/components/README.md +77 -0
- package/templates/angular/src/app/components/index.ts +53 -0
- package/templates/angular/src/app/components/modus-accordion.component.ts +50 -0
- package/templates/angular/src/app/components/modus-alert.component.ts +133 -0
- package/templates/angular/src/app/components/modus-autocomplete.component.ts +262 -0
- package/templates/angular/src/app/components/modus-avatar.component.ts +75 -0
- package/templates/angular/src/app/components/modus-badge.component.ts +84 -0
- package/templates/angular/src/app/components/modus-breadcrumbs.component.ts +65 -0
- package/templates/angular/src/app/components/modus-button-group.component.ts +82 -0
- package/templates/angular/src/app/components/modus-button.component.ts +292 -0
- package/templates/angular/src/app/components/modus-card.component.ts +73 -0
- package/templates/angular/src/app/components/modus-checkbox.component.ts +117 -0
- package/templates/angular/src/app/components/modus-chip.component.ts +97 -0
- package/templates/angular/src/app/components/modus-collapse.component.ts +118 -0
- package/templates/angular/src/app/components/modus-date.component.ts +165 -0
- package/templates/angular/src/app/components/modus-dropdown-menu.component.ts +108 -0
- package/templates/angular/src/app/components/modus-file-dropzone.component.ts +121 -0
- package/templates/angular/src/app/components/modus-handle.component.ts +96 -0
- package/templates/angular/src/app/components/modus-icon.component.ts +81 -0
- package/templates/angular/src/app/components/modus-input-feedback.component.ts +54 -0
- package/templates/angular/src/app/components/modus-input-label.component.ts +62 -0
- package/templates/angular/src/app/components/modus-loader.component.ts +48 -0
- package/templates/angular/src/app/components/modus-logo.component.ts +115 -0
- package/templates/angular/src/app/components/modus-menu-item.component.ts +116 -0
- package/templates/angular/src/app/components/modus-menu.component.ts +58 -0
- package/templates/angular/src/app/components/modus-modal.component.ts +70 -0
- package/templates/angular/src/app/components/modus-navbar.component.ts +303 -0
- package/templates/angular/src/app/components/modus-number-input.component.ts +174 -0
- package/templates/angular/src/app/components/modus-pagination.component.ts +74 -0
- package/templates/angular/src/app/components/modus-panel.component.ts +61 -0
- package/templates/angular/src/app/components/modus-progress.component.ts +62 -0
- package/templates/angular/src/app/components/modus-radio.component.ts +102 -0
- package/templates/angular/src/app/components/modus-rating.component.ts +80 -0
- package/templates/angular/src/app/components/modus-select.component.ts +131 -0
- package/templates/angular/src/app/components/modus-side-navigation.component.ts +90 -0
- package/templates/angular/src/app/components/modus-skeleton.component.ts +54 -0
- package/templates/angular/src/app/components/modus-slider.component.ts +132 -0
- package/templates/angular/src/app/components/modus-stepper.component.ts +65 -0
- package/templates/angular/src/app/components/modus-switch.component.ts +118 -0
- package/templates/angular/src/app/components/modus-table.component.ts +204 -0
- package/templates/angular/src/app/components/modus-tabs.component.ts +82 -0
- package/templates/angular/src/app/components/modus-text-input.component.ts +221 -0
- package/templates/angular/src/app/components/modus-textarea.component.ts +168 -0
- package/templates/angular/src/app/components/modus-theme-switcher.component.ts +45 -0
- package/templates/angular/src/app/components/modus-time-input.component.ts +172 -0
- package/templates/angular/src/app/components/modus-toast.component.ts +63 -0
- package/templates/angular/src/app/components/modus-toolbar.component.ts +43 -0
- package/templates/angular/src/app/components/modus-tooltip.component.ts +83 -0
- package/templates/angular/src/app/components/modus-typography.component.ts +79 -0
- package/templates/angular/src/app/components/modus-utility-panel.component.ts +275 -0
- package/templates/angular/src/app/components/theme-demo.component.ts +1242 -0
- package/templates/angular/src/app/data/component-demos.ts +360 -0
- package/templates/angular/src/app/data/modus-icons.ts +806 -0
- package/templates/angular/src/app/demos/accordion/accordion-demo.component.ts +212 -0
- package/templates/angular/src/app/demos/alert/alert-demo.component.ts +108 -0
- package/templates/angular/src/app/demos/autocomplete/autocomplete-demo.component.ts +174 -0
- package/templates/angular/src/app/demos/avatar/avatar-demo.component.ts +149 -0
- package/templates/angular/src/app/demos/badge/badge-demo.component.ts +148 -0
- package/templates/angular/src/app/demos/breadcrumbs/breadcrumbs-demo.component.ts +96 -0
- package/templates/angular/src/app/demos/button/button-demo.component.ts +256 -0
- package/templates/angular/src/app/demos/button-group/button-group-demo.component.ts +215 -0
- package/templates/angular/src/app/demos/card/card-demo.component.ts +180 -0
- package/templates/angular/src/app/demos/checkbox/checkbox-demo.component.ts +71 -0
- package/templates/angular/src/app/demos/chip/chip-demo.component.ts +183 -0
- package/templates/angular/src/app/demos/date/date-demo.component.ts +193 -0
- package/templates/angular/src/app/demos/dropdown/dropdown-demo.component.ts +196 -0
- package/templates/angular/src/app/demos/file-dropzone/file-dropzone-demo.component.ts +176 -0
- package/templates/angular/src/app/demos/handle/handle-demo.component.ts +265 -0
- package/templates/angular/src/app/demos/icon/icon-demo.component.ts +65 -0
- package/templates/angular/src/app/demos/input-feedback/input-feedback-demo.component.ts +189 -0
- package/templates/angular/src/app/demos/input-label/input-label-demo.component.ts +330 -0
- package/templates/angular/src/app/demos/loader/loader-demo.component.ts +143 -0
- package/templates/angular/src/app/demos/logo/logo-demo.component.ts +191 -0
- package/templates/angular/src/app/demos/menu/menu-demo.component.ts +72 -0
- package/templates/angular/src/app/demos/modal/modal-demo.component.ts +278 -0
- package/templates/angular/src/app/demos/navbar/navbar-demo.component.ts +135 -0
- package/templates/angular/src/app/demos/number-input/number-input-demo.component.ts +175 -0
- package/templates/angular/src/app/demos/pagination/pagination-demo.component.ts +134 -0
- package/templates/angular/src/app/demos/panel/panel-demo.component.ts +235 -0
- package/templates/angular/src/app/demos/progress/progress-demo.component.ts +169 -0
- package/templates/angular/src/app/demos/radio/radio-demo.component.ts +161 -0
- package/templates/angular/src/app/demos/rating/rating-demo.component.ts +97 -0
- package/templates/angular/src/app/demos/select/select-demo.component.ts +107 -0
- package/templates/angular/src/app/demos/shared/demo-example-clean.component.ts +41 -0
- package/templates/angular/src/app/demos/shared/demo-example.component.ts +42 -0
- package/templates/angular/src/app/demos/shared/demo-page.component.ts +97 -0
- package/templates/angular/src/app/demos/shared/index.ts +3 -0
- package/templates/angular/src/app/demos/side-navigation/side-navigation-demo.component.ts +524 -0
- package/templates/angular/src/app/demos/skeleton/skeleton-demo.component.ts +112 -0
- package/templates/angular/src/app/demos/slider/slider-demo.component.ts +76 -0
- package/templates/angular/src/app/demos/stepper/stepper-demo.component.ts +79 -0
- package/templates/angular/src/app/demos/switch/switch-demo.component.ts +113 -0
- package/templates/angular/src/app/demos/table/table-demo.component.ts +405 -0
- package/templates/angular/src/app/demos/tabs/tabs-demo.component.ts +318 -0
- package/templates/angular/src/app/demos/text-input/text-input-demo.component.ts +160 -0
- package/templates/angular/src/app/demos/textarea/textarea-demo.component.ts +95 -0
- package/templates/angular/src/app/demos/theme-switcher/theme-switcher-demo.component.ts +38 -0
- package/templates/angular/src/app/demos/time-input/time-input-demo.component.ts +130 -0
- package/templates/angular/src/app/demos/toast/toast-demo.component.ts +258 -0
- package/templates/angular/src/app/demos/toolbar/toolbar-demo.component.ts +54 -0
- package/templates/angular/src/app/demos/tooltip/tooltip-demo.component.ts +163 -0
- package/templates/angular/src/app/demos/utility-panel/utility-panel-demo.component.ts +197 -0
- package/templates/angular/src/app/dev/dev-config.ts +119 -0
- package/templates/angular/src/app/dev/dev-panel/dev-panel.component.ts +215 -0
- package/templates/angular/src/app/dev/dev-panel.service.ts +63 -0
- package/templates/angular/src/app/dev/index.ts +8 -0
- package/templates/angular/src/app/dev/theme-switcher-dropdown/theme-switcher-dropdown.component.ts +134 -0
- package/templates/angular/src/app/dev-pages/color-palette/color-palette.component.ts +229 -0
- package/templates/angular/src/app/dev-pages/components-gallery/components-gallery.component.ts +486 -0
- package/templates/angular/src/app/dev-pages/icons/icons.component.ts +149 -0
- package/templates/angular/src/app/pages/home/home.component.ts +251 -0
- package/templates/angular/src/app/services/README.md +57 -0
- package/templates/angular/src/app/services/theme.service.ts +163 -0
- package/templates/angular/src/environments/environment.development.ts +8 -0
- package/templates/angular/src/environments/environment.ts +8 -0
- package/templates/angular/src/index.html +14 -0
- package/templates/angular/src/main.ts +6 -0
- package/templates/angular/src/styles.css +1328 -0
- package/templates/angular/tsconfig.app.json +15 -0
- package/templates/angular/tsconfig.json +35 -0
- package/templates/angular/tsconfig.spec.json +14 -0
- package/templates/config.json +23 -0
- package/templates/react/.cursor/commands/remove-dev-content.md +311 -0
- package/templates/react/.cursor/mcp.json +13 -0
- package/templates/react/.cursor/rules/README.md +240 -0
- package/templates/react/.cursor/rules/border-usage-guidelines-short.mdc +22 -0
- package/templates/react/.cursor/rules/border-usage-guidelines.mdc +380 -0
- package/templates/react/.cursor/rules/chrome-devtools-testing-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/development-workflow-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/development-workflow-react.mdc +292 -0
- package/templates/react/.cursor/rules/implementation-guides-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/implementation-guides-react.mdc +446 -0
- package/templates/react/.cursor/rules/modus-accordion-state-management-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-accordion-state-management-react.mdc +445 -0
- package/templates/react/.cursor/rules/modus-button-group-usage-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-button-group-usage-react.mdc +117 -0
- package/templates/react/.cursor/rules/modus-checkbox-value-inversion-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-checkbox-value-inversion-react.mdc +492 -0
- package/templates/react/.cursor/rules/modus-color-usage-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-color-usage-react.mdc +420 -0
- package/templates/react/.cursor/rules/modus-components-reference.mdc +366 -0
- package/templates/react/.cursor/rules/modus-icon-names.mdc +63 -0
- package/templates/react/.cursor/rules/modus-icons-react-short.mdc +24 -0
- package/templates/react/.cursor/rules/modus-icons-react.mdc +402 -0
- package/templates/react/.cursor/rules/modus-modal-implementation-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-modal-implementation-react.mdc +831 -0
- package/templates/react/.cursor/rules/modus-navbar-side-navigation-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-navbar-side-navigation-react.mdc +247 -0
- package/templates/react/.cursor/rules/modus-no-emojis-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-opacity-utilities-react-short.mdc +70 -0
- package/templates/react/.cursor/rules/modus-opacity-utilities-react.mdc +208 -0
- package/templates/react/.cursor/rules/modus-react-best-practices-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-react-best-practices.mdc +508 -0
- package/templates/react/.cursor/rules/modus-react-essentials.mdc +209 -0
- package/templates/react/.cursor/rules/modus-react-integration-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-react-integration.mdc +509 -0
- package/templates/react/.cursor/rules/modus-react-key-warnings-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-react-key-warnings.mdc +805 -0
- package/templates/react/.cursor/rules/modus-react-master.mdc +160 -0
- package/templates/react/.cursor/rules/modus-select-vs-dropdown-menu-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-select-vs-dropdown-menu-react.mdc +442 -0
- package/templates/react/.cursor/rules/modus-semantic-html-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-semantic-html-react.mdc +427 -0
- package/templates/react/.cursor/rules/modus-tailwind-usage-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-tailwind-usage-react.mdc +642 -0
- package/templates/react/.cursor/rules/modus-themes-react-short.mdc +23 -0
- package/templates/react/.cursor/rules/modus-themes-react.mdc +506 -0
- package/templates/react/.cursor/rules/ux/gestalt-laws-detailed.mdc +456 -0
- package/templates/react/.cursor/rules/ux/ux-ui-foundations.mdc +211 -0
- package/templates/react/.cursor/skills/create-modus-form-component/SKILL.md +518 -0
- package/templates/react/.cursor/skills/create-modus-wrapper-component/SKILL.md +252 -0
- package/templates/react/.cursor/skills/fix-modus-component-event-issues/SKILL.md +345 -0
- package/templates/react/.cursor/skills/handle-modus-checkbox-value-bug/SKILL.md +202 -0
- package/templates/react/.cursor/skills/implement-modus-modal-with-refs/SKILL.md +386 -0
- package/templates/react/.cursor/skills/integrate-modus-icons/SKILL.md +300 -0
- package/templates/react/.cursor/skills/run-lint-checks/SKILL.md +235 -0
- package/templates/react/.cursor/skills/set-up-modus-event-listeners/SKILL.md +284 -0
- package/templates/react/.cursor/skills/style-modus-components-with-tailwind/SKILL.md +382 -0
- package/templates/react/.env.development +3 -0
- package/templates/react/.env.production +3 -0
- package/templates/react/.github/CODEOWNERS +28 -0
- package/templates/react/.github/ISSUE_TEMPLATE/bug_report.yml +176 -0
- package/templates/react/.github/ISSUE_TEMPLATE/config.yml +20 -0
- package/templates/react/.github/ISSUE_TEMPLATE/documentation.yml +115 -0
- package/templates/react/.github/ISSUE_TEMPLATE/feature_request.yml +171 -0
- package/templates/react/.github/ISSUE_TEMPLATE/question.yml +139 -0
- package/templates/react/.github/copilot-instructions.md +80 -0
- package/templates/react/.github/instructions/components.instructions.md +82 -0
- package/templates/react/.github/instructions/demos.instructions.md +82 -0
- package/templates/react/.github/instructions/pages.instructions.md +76 -0
- package/templates/react/.github/instructions/styles.instructions.md +77 -0
- package/templates/react/.github/instructions/typescript.instructions.md +101 -0
- package/templates/react/.github/pull_request_template.md +188 -0
- package/templates/react/.github/workflows/ci.yml +43 -0
- package/templates/react/.github/workflows/claude-code-review.yml +44 -0
- package/templates/react/.github/workflows/claude.yml +50 -0
- package/templates/react/.husky/pre-commit +28 -0
- package/templates/react/.vscode/extensions.json +8 -0
- package/templates/react/CLAUDE.md +119 -0
- package/templates/react/CODE_OF_CONDUCT.md +79 -0
- package/templates/react/CONTRIBUTING.md +65 -0
- package/templates/react/LICENSE +21 -0
- package/templates/react/README.md +728 -0
- package/templates/react/SECURITY.md +50 -0
- package/templates/react/eslint.config.js +23 -0
- package/templates/react/index.html +13 -0
- package/templates/react/package-lock.json +5209 -0
- package/templates/react/package.json +49 -0
- package/templates/react/postcss.config.js +6 -0
- package/templates/react/public/react.svg +1 -0
- package/templates/react/public/vite.svg +1 -0
- package/templates/react/readme_assets/getting_started_header.png +0 -0
- package/templates/react/readme_assets/hero.png +0 -0
- package/templates/react/readme_assets/modus_comp.png +0 -0
- package/templates/react/readme_assets/modus_figma_mcp.png +0 -0
- package/templates/react/readme_assets/teaser_comp.gif +0 -0
- package/templates/react/scripts/README.md +343 -0
- package/templates/react/scripts/check-border-violations.js +483 -0
- package/templates/react/scripts/check-icon-names.js +486 -0
- package/templates/react/scripts/check-inline-styles.js +364 -0
- package/templates/react/scripts/check-modus-colors.js +247 -0
- package/templates/react/scripts/check-modus-icons.js +256 -0
- package/templates/react/scripts/check-opacity-utilities.js +481 -0
- package/templates/react/scripts/check-semantic-html.js +476 -0
- package/templates/react/scripts/check-typescript.js +109 -0
- package/templates/react/src/App.css +42 -0
- package/templates/react/src/App.tsx +54 -0
- package/templates/react/src/assets/react.svg +1 -0
- package/templates/react/src/components/DemoExample.tsx +61 -0
- package/templates/react/src/components/DemoPage.tsx +81 -0
- package/templates/react/src/components/ModusAccordion.tsx +89 -0
- package/templates/react/src/components/ModusAlert.tsx +85 -0
- package/templates/react/src/components/ModusAutocomplete.tsx +207 -0
- package/templates/react/src/components/ModusAvatar.tsx +50 -0
- package/templates/react/src/components/ModusBadge.tsx +82 -0
- package/templates/react/src/components/ModusBreadcrumbs.tsx +75 -0
- package/templates/react/src/components/ModusButton.tsx +244 -0
- package/templates/react/src/components/ModusButtonGroup.tsx +91 -0
- package/templates/react/src/components/ModusCard.tsx +70 -0
- package/templates/react/src/components/ModusCheckbox.tsx +168 -0
- package/templates/react/src/components/ModusChip.tsx +93 -0
- package/templates/react/src/components/ModusDate.tsx +154 -0
- package/templates/react/src/components/ModusDropdownMenu.tsx +148 -0
- package/templates/react/src/components/ModusFileDropzone.tsx +140 -0
- package/templates/react/src/components/ModusHandle.tsx +101 -0
- package/templates/react/src/components/ModusIcon.tsx +49 -0
- package/templates/react/src/components/ModusInputFeedback.tsx +52 -0
- package/templates/react/src/components/ModusInputLabel.tsx +50 -0
- package/templates/react/src/components/ModusLoader.tsx +42 -0
- package/templates/react/src/components/ModusLogo.tsx +102 -0
- package/templates/react/src/components/ModusMenu.tsx +119 -0
- package/templates/react/src/components/ModusMenuItem.tsx +86 -0
- package/templates/react/src/components/ModusModal.tsx +145 -0
- package/templates/react/src/components/ModusNavbar.tsx +504 -0
- package/templates/react/src/components/ModusNumberInput.tsx +230 -0
- package/templates/react/src/components/ModusPagination.tsx +94 -0
- package/templates/react/src/components/ModusPanel.tsx +92 -0
- package/templates/react/src/components/ModusProgress.tsx +70 -0
- package/templates/react/src/components/ModusProvider.tsx +18 -0
- package/templates/react/src/components/ModusRadio.tsx +114 -0
- package/templates/react/src/components/ModusRating.tsx +108 -0
- package/templates/react/src/components/ModusSelect.tsx +171 -0
- package/templates/react/src/components/ModusSideNavigation.tsx +149 -0
- package/templates/react/src/components/ModusSkeleton.tsx +42 -0
- package/templates/react/src/components/ModusSlider.tsx +128 -0
- package/templates/react/src/components/ModusStepper.tsx +85 -0
- package/templates/react/src/components/ModusSwitch.tsx +130 -0
- package/templates/react/src/components/ModusTable.tsx +309 -0
- package/templates/react/src/components/ModusTabs.tsx +114 -0
- package/templates/react/src/components/ModusTextInput.tsx +179 -0
- package/templates/react/src/components/ModusTextarea.tsx +164 -0
- package/templates/react/src/components/ModusThemeSwitcher.tsx +58 -0
- package/templates/react/src/components/ModusTimeInput.tsx +176 -0
- package/templates/react/src/components/ModusToast.tsx +207 -0
- package/templates/react/src/components/ModusToolbar.tsx +70 -0
- package/templates/react/src/components/ModusTooltip.tsx +97 -0
- package/templates/react/src/components/ModusUtilityPanel.tsx +198 -0
- package/templates/react/src/components/ThemeSwitcherDropdown.tsx +117 -0
- package/templates/react/src/components/ThemeToggleSimple.tsx +157 -0
- package/templates/react/src/config/routes.ts +196 -0
- package/templates/react/src/contexts/ThemeContext.tsx +81 -0
- package/templates/react/src/contexts/ThemeContextData.tsx +89 -0
- package/templates/react/src/data/modusIcons.ts +865 -0
- package/templates/react/src/demos/accordion-demo/page.tsx +236 -0
- package/templates/react/src/demos/alert-demo/page.tsx +94 -0
- package/templates/react/src/demos/autocomplete-demo/page.tsx +166 -0
- package/templates/react/src/demos/avatar-demo/page.tsx +135 -0
- package/templates/react/src/demos/badge-demo/page.tsx +174 -0
- package/templates/react/src/demos/breadcrumbs-demo/page.tsx +88 -0
- package/templates/react/src/demos/button-demo/page.tsx +261 -0
- package/templates/react/src/demos/button-group-demo/page.tsx +231 -0
- package/templates/react/src/demos/card-demo/page.tsx +241 -0
- package/templates/react/src/demos/checkbox-demo/page.tsx +79 -0
- package/templates/react/src/demos/chip-demo/page.tsx +197 -0
- package/templates/react/src/demos/date-demo/page.tsx +179 -0
- package/templates/react/src/demos/dropdown-demo/page.tsx +150 -0
- package/templates/react/src/demos/file-dropzone-demo/page.tsx +186 -0
- package/templates/react/src/demos/handle-demo/page.tsx +313 -0
- package/templates/react/src/demos/icon-demo/page.tsx +72 -0
- package/templates/react/src/demos/input-feedback-demo/page.tsx +202 -0
- package/templates/react/src/demos/input-label-demo/page.tsx +392 -0
- package/templates/react/src/demos/loader-demo/page.tsx +138 -0
- package/templates/react/src/demos/logo-demo/page.tsx +292 -0
- package/templates/react/src/demos/menu-demo/page.tsx +70 -0
- package/templates/react/src/demos/modal-demo/page.tsx +332 -0
- package/templates/react/src/demos/navbar-demo/page.tsx +141 -0
- package/templates/react/src/demos/number-input-demo/page.tsx +180 -0
- package/templates/react/src/demos/pagination-demo/page.tsx +147 -0
- package/templates/react/src/demos/panel-demo/page.tsx +376 -0
- package/templates/react/src/demos/progress-demo/page.tsx +185 -0
- package/templates/react/src/demos/radio-demo/page.tsx +242 -0
- package/templates/react/src/demos/rating-demo/page.tsx +97 -0
- package/templates/react/src/demos/select-demo/page.tsx +111 -0
- package/templates/react/src/demos/side-navigation-demo/page.tsx +775 -0
- package/templates/react/src/demos/skeleton-demo/page.tsx +107 -0
- package/templates/react/src/demos/slider-demo/page.tsx +78 -0
- package/templates/react/src/demos/stepper-demo/page.tsx +86 -0
- package/templates/react/src/demos/switch-demo/page.tsx +146 -0
- package/templates/react/src/demos/table-demo/page.tsx +489 -0
- package/templates/react/src/demos/tabs-demo/page.tsx +187 -0
- package/templates/react/src/demos/text-input-demo/page.tsx +151 -0
- package/templates/react/src/demos/textarea-demo/page.tsx +73 -0
- package/templates/react/src/demos/theme-switcher-demo/page.tsx +26 -0
- package/templates/react/src/demos/time-input-demo/page.tsx +148 -0
- package/templates/react/src/demos/toast-demo/page.tsx +302 -0
- package/templates/react/src/demos/toolbar-demo/page.tsx +49 -0
- package/templates/react/src/demos/tooltip-demo/page.tsx +209 -0
- package/templates/react/src/demos/typography-test/page.tsx +28 -0
- package/templates/react/src/demos/utility-panel-demo/page.tsx +197 -0
- package/templates/react/src/dev/DevPanel.tsx +219 -0
- package/templates/react/src/dev/DevPanelContext.ts +14 -0
- package/templates/react/src/dev/DevPanelProvider.tsx +63 -0
- package/templates/react/src/dev/DevRoutes.tsx +98 -0
- package/templates/react/src/dev/config.ts +127 -0
- package/templates/react/src/dev/index.ts +8 -0
- package/templates/react/src/dev/useDevPanel.ts +17 -0
- package/templates/react/src/dev-pages/ColorPalettePage.tsx +347 -0
- package/templates/react/src/dev-pages/ComponentsGalleryPage.tsx +489 -0
- package/templates/react/src/dev-pages/IconsPage.tsx +137 -0
- package/templates/react/src/dev-pages/index.ts +3 -0
- package/templates/react/src/hooks/useTheme.ts +15 -0
- package/templates/react/src/index.css +635 -0
- package/templates/react/src/main.tsx +14 -0
- package/templates/react/src/pages/HomePage.tsx +283 -0
- package/templates/react/src/vite-env.d.ts +9 -0
- package/templates/react/tailwind.config.js +58 -0
- package/templates/react/tsconfig.app.json +27 -0
- package/templates/react/tsconfig.json +7 -0
- package/templates/react/tsconfig.node.json +25 -0
- package/templates/react/vite.config.ts +18 -0
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import { useEffect, useRef } from "react";
|
|
2
|
+
import type { ReactNode } from "react";
|
|
3
|
+
import { ModusWcChip } from "@trimble-oss/moduswebcomponents-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Props for the ModusChip component.
|
|
7
|
+
*/
|
|
8
|
+
export interface ModusChipProps {
|
|
9
|
+
/** The content to display inside the chip. */
|
|
10
|
+
children?: ReactNode;
|
|
11
|
+
/** Whether the chip is active. */
|
|
12
|
+
active?: boolean;
|
|
13
|
+
/** Whether the chip is disabled. */
|
|
14
|
+
disabled?: boolean;
|
|
15
|
+
/** Whether the chip has an error. */
|
|
16
|
+
hasError?: boolean;
|
|
17
|
+
/** The label for the chip. */
|
|
18
|
+
label?: string;
|
|
19
|
+
/** Whether to show the remove button. */
|
|
20
|
+
showRemove?: boolean;
|
|
21
|
+
/** The size of the chip. */
|
|
22
|
+
size?: 'sm' | 'md' | 'lg';
|
|
23
|
+
/** The variant of the chip. */
|
|
24
|
+
variant?: 'filled' | 'outline';
|
|
25
|
+
/** A custom CSS class to apply to the chip. */
|
|
26
|
+
customClass?: string;
|
|
27
|
+
/** The ARIA label for the chip. */
|
|
28
|
+
'aria-label'?: string;
|
|
29
|
+
/** A callback function to handle chip clicks. */
|
|
30
|
+
onChipClick?: (event: CustomEvent<MouseEvent | KeyboardEvent>) => void;
|
|
31
|
+
/** A callback function to handle chip removal. */
|
|
32
|
+
onChipRemove?: (event: CustomEvent<MouseEvent | KeyboardEvent>) => void;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Renders a Modus chip component.
|
|
37
|
+
* @param {ModusChipProps} props - The component props.
|
|
38
|
+
* @returns {JSX.Element} The rendered chip component.
|
|
39
|
+
*/
|
|
40
|
+
export default function ModusChip({
|
|
41
|
+
children,
|
|
42
|
+
active = false,
|
|
43
|
+
disabled = false,
|
|
44
|
+
hasError = false,
|
|
45
|
+
label = '',
|
|
46
|
+
showRemove = false,
|
|
47
|
+
size = 'md',
|
|
48
|
+
variant = 'filled',
|
|
49
|
+
customClass,
|
|
50
|
+
'aria-label': ariaLabel,
|
|
51
|
+
onChipClick,
|
|
52
|
+
onChipRemove,
|
|
53
|
+
}: ModusChipProps) {
|
|
54
|
+
const chipRef = useRef<HTMLModusWcChipElement>(null);
|
|
55
|
+
|
|
56
|
+
useEffect(() => {
|
|
57
|
+
const chip = chipRef.current;
|
|
58
|
+
if (!chip) return;
|
|
59
|
+
|
|
60
|
+
const handleChipClick = (event: Event) => {
|
|
61
|
+
onChipClick?.(event as CustomEvent<MouseEvent | KeyboardEvent>);
|
|
62
|
+
};
|
|
63
|
+
const handleChipRemove = (event: Event) => {
|
|
64
|
+
onChipRemove?.(event as CustomEvent<MouseEvent | KeyboardEvent>);
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
if (onChipClick) chip.addEventListener("chipClick", handleChipClick);
|
|
68
|
+
if (onChipRemove) chip.addEventListener("chipRemove", handleChipRemove);
|
|
69
|
+
|
|
70
|
+
return () => {
|
|
71
|
+
if (onChipClick) chip.removeEventListener("chipClick", handleChipClick);
|
|
72
|
+
if (onChipRemove)
|
|
73
|
+
chip.removeEventListener("chipRemove", handleChipRemove);
|
|
74
|
+
};
|
|
75
|
+
}, [onChipClick, onChipRemove]);
|
|
76
|
+
|
|
77
|
+
return (
|
|
78
|
+
<ModusWcChip
|
|
79
|
+
ref={chipRef}
|
|
80
|
+
active={active}
|
|
81
|
+
disabled={disabled}
|
|
82
|
+
hasError={hasError}
|
|
83
|
+
label={label}
|
|
84
|
+
showRemove={showRemove}
|
|
85
|
+
size={size}
|
|
86
|
+
variant={variant}
|
|
87
|
+
customClass={customClass}
|
|
88
|
+
aria-label={ariaLabel}
|
|
89
|
+
>
|
|
90
|
+
{children}
|
|
91
|
+
</ModusWcChip>
|
|
92
|
+
);
|
|
93
|
+
}
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
import { useEffect, useRef } from "react";
|
|
2
|
+
import { ModusWcDate } from "@trimble-oss/moduswebcomponents-react";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Represents feedback for an input component.
|
|
6
|
+
*/
|
|
7
|
+
export interface InputFeedbackProp {
|
|
8
|
+
/** The severity level of the feedback. */
|
|
9
|
+
level: "error" | "info" | "success" | "warning";
|
|
10
|
+
/** The message to display as feedback. */
|
|
11
|
+
message?: string;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
/** Date format options. */
|
|
15
|
+
export type DateFormat =
|
|
16
|
+
| "yyyy-mm-dd"
|
|
17
|
+
| "dd-mm-yyyy"
|
|
18
|
+
| "yyyy/mm/dd"
|
|
19
|
+
| "dd/mm/yyyy"
|
|
20
|
+
| "MMM DD, YYYY";
|
|
21
|
+
|
|
22
|
+
/** Week start day options. */
|
|
23
|
+
export type WeekStartDay = "sunday" | "monday";
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* Props for the ModusDate component.
|
|
27
|
+
*/
|
|
28
|
+
export interface ModusDateProps {
|
|
29
|
+
/** The value of the date input (Format: YYYY-MM-DD). */
|
|
30
|
+
value?: string;
|
|
31
|
+
/** Whether the date input has a border. */
|
|
32
|
+
bordered?: boolean;
|
|
33
|
+
/** Whether the date input is disabled. */
|
|
34
|
+
disabled?: boolean;
|
|
35
|
+
/** Feedback to display for the date input. */
|
|
36
|
+
feedback?: InputFeedbackProp;
|
|
37
|
+
/** Date format pattern. */
|
|
38
|
+
format?: DateFormat;
|
|
39
|
+
/** The ID of the input element. */
|
|
40
|
+
inputId?: string;
|
|
41
|
+
/** The tab index of the input element. */
|
|
42
|
+
inputTabIndex?: number;
|
|
43
|
+
/** The label for the date input. */
|
|
44
|
+
label?: string;
|
|
45
|
+
/** The maximum allowed date (Format: YYYY-MM-DD). */
|
|
46
|
+
max?: string;
|
|
47
|
+
/** The minimum allowed date (Format: YYYY-MM-DD). */
|
|
48
|
+
min?: string;
|
|
49
|
+
/** The name of the input element. */
|
|
50
|
+
name?: string;
|
|
51
|
+
/** Whether the date input is read-only. */
|
|
52
|
+
readOnly?: boolean;
|
|
53
|
+
/** Whether the date input is required. */
|
|
54
|
+
required?: boolean;
|
|
55
|
+
/** The size of the date input. */
|
|
56
|
+
size?: "sm" | "md" | "lg";
|
|
57
|
+
/** First day of the week for the calendar view. */
|
|
58
|
+
weekStartDay?: WeekStartDay;
|
|
59
|
+
/** A custom CSS class to apply to the date input. */
|
|
60
|
+
customClass?: string;
|
|
61
|
+
/** The ARIA label for the date input. */
|
|
62
|
+
"aria-label"?: string;
|
|
63
|
+
/** A callback function to handle input changes. */
|
|
64
|
+
onInputChange?: (event: CustomEvent<InputEvent>) => void;
|
|
65
|
+
/** A callback function to handle input focus. */
|
|
66
|
+
onInputFocus?: (event: CustomEvent<FocusEvent>) => void;
|
|
67
|
+
/** A callback function to handle input blur. */
|
|
68
|
+
onInputBlur?: (event: CustomEvent<FocusEvent>) => void;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* Renders a Modus date input component.
|
|
73
|
+
* @param {ModusDateProps} props - The component props.
|
|
74
|
+
* @returns {JSX.Element} The rendered date input component.
|
|
75
|
+
*/
|
|
76
|
+
export default function ModusDate({
|
|
77
|
+
value = "",
|
|
78
|
+
bordered = true,
|
|
79
|
+
disabled = false,
|
|
80
|
+
feedback,
|
|
81
|
+
format,
|
|
82
|
+
inputId,
|
|
83
|
+
inputTabIndex,
|
|
84
|
+
label,
|
|
85
|
+
max,
|
|
86
|
+
min,
|
|
87
|
+
name = "",
|
|
88
|
+
readOnly = false,
|
|
89
|
+
required = false,
|
|
90
|
+
size = "md",
|
|
91
|
+
weekStartDay,
|
|
92
|
+
customClass,
|
|
93
|
+
"aria-label": ariaLabel,
|
|
94
|
+
onInputChange,
|
|
95
|
+
onInputFocus,
|
|
96
|
+
onInputBlur,
|
|
97
|
+
}: ModusDateProps) {
|
|
98
|
+
const dateRef = useRef<HTMLModusWcDateElement>(null);
|
|
99
|
+
|
|
100
|
+
useEffect(() => {
|
|
101
|
+
const date = dateRef.current;
|
|
102
|
+
if (!date) return;
|
|
103
|
+
|
|
104
|
+
const handleInputChange = (event: Event) => {
|
|
105
|
+
onInputChange?.(event as CustomEvent<InputEvent>);
|
|
106
|
+
};
|
|
107
|
+
const handleInputFocus = (event: Event) => {
|
|
108
|
+
onInputFocus?.(event as CustomEvent<FocusEvent>);
|
|
109
|
+
};
|
|
110
|
+
const handleInputBlur = (event: Event) => {
|
|
111
|
+
onInputBlur?.(event as CustomEvent<FocusEvent>);
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
if (onInputChange) date.addEventListener("inputChange", handleInputChange);
|
|
115
|
+
if (onInputFocus) date.addEventListener("inputFocus", handleInputFocus);
|
|
116
|
+
if (onInputBlur) date.addEventListener("inputBlur", handleInputBlur);
|
|
117
|
+
|
|
118
|
+
return () => {
|
|
119
|
+
if (onInputChange)
|
|
120
|
+
date.removeEventListener("inputChange", handleInputChange);
|
|
121
|
+
if (onInputFocus)
|
|
122
|
+
date.removeEventListener("inputFocus", handleInputFocus);
|
|
123
|
+
if (onInputBlur) date.removeEventListener("inputBlur", handleInputBlur);
|
|
124
|
+
};
|
|
125
|
+
}, [onInputChange, onInputFocus, onInputBlur]);
|
|
126
|
+
|
|
127
|
+
// Note: format and weekStartDay are passed as attributes since they may not be
|
|
128
|
+
// exposed as typed props in the React bindings but are supported by the web component
|
|
129
|
+
const additionalProps: Record<string, unknown> = {};
|
|
130
|
+
if (format) additionalProps.format = format;
|
|
131
|
+
if (weekStartDay) additionalProps.weekStartDay = weekStartDay;
|
|
132
|
+
|
|
133
|
+
return (
|
|
134
|
+
<ModusWcDate
|
|
135
|
+
ref={dateRef}
|
|
136
|
+
value={value}
|
|
137
|
+
bordered={bordered}
|
|
138
|
+
disabled={disabled}
|
|
139
|
+
feedback={feedback}
|
|
140
|
+
inputId={inputId}
|
|
141
|
+
inputTabIndex={inputTabIndex}
|
|
142
|
+
label={label}
|
|
143
|
+
max={max}
|
|
144
|
+
min={min}
|
|
145
|
+
name={name}
|
|
146
|
+
readOnly={readOnly}
|
|
147
|
+
required={required}
|
|
148
|
+
size={size}
|
|
149
|
+
customClass={customClass}
|
|
150
|
+
aria-label={ariaLabel}
|
|
151
|
+
{...additionalProps}
|
|
152
|
+
/>
|
|
153
|
+
);
|
|
154
|
+
}
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
import { useEffect, useRef } from "react";
|
|
2
|
+
import type { ReactNode } from "react";
|
|
3
|
+
import { ModusWcDropdownMenu } from "@trimble-oss/moduswebcomponents-react";
|
|
4
|
+
import ModusMenuItem from "./ModusMenuItem";
|
|
5
|
+
import type { MenuItem } from "./ModusMenu";
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Props for the ModusDropdownMenu component.
|
|
9
|
+
*/
|
|
10
|
+
export interface ModusDropdownMenuProps {
|
|
11
|
+
/** The content to display inside the dropdown menu. */
|
|
12
|
+
children?: ReactNode;
|
|
13
|
+
/** The items to display in the dropdown menu. */
|
|
14
|
+
menuItems?: MenuItem[];
|
|
15
|
+
/** The color of the dropdown button. */
|
|
16
|
+
buttonColor?: 'primary' | 'secondary' | 'tertiary' | 'warning' | 'danger';
|
|
17
|
+
/** The size of the dropdown button. */
|
|
18
|
+
buttonSize?: 'xs' | 'sm' | 'md' | 'lg';
|
|
19
|
+
/** The variant of the dropdown button. */
|
|
20
|
+
buttonVariant?: 'filled' | 'outlined' | 'borderless';
|
|
21
|
+
/** A custom CSS class to apply to the dropdown menu. */
|
|
22
|
+
customClass?: string;
|
|
23
|
+
/** Whether the dropdown menu is disabled. */
|
|
24
|
+
disabled?: boolean;
|
|
25
|
+
/** Whether the dropdown menu has a border. */
|
|
26
|
+
menuBordered?: boolean;
|
|
27
|
+
/** The offset of the dropdown menu from the button. */
|
|
28
|
+
menuOffset?: number;
|
|
29
|
+
/** The placement of the dropdown menu. */
|
|
30
|
+
menuPlacement?:
|
|
31
|
+
| 'top'
|
|
32
|
+
| 'top-start'
|
|
33
|
+
| 'top-end'
|
|
34
|
+
| 'bottom'
|
|
35
|
+
| 'bottom-start'
|
|
36
|
+
| 'bottom-end'
|
|
37
|
+
| 'left'
|
|
38
|
+
| 'left-start'
|
|
39
|
+
| 'left-end'
|
|
40
|
+
| 'right'
|
|
41
|
+
| 'right-start'
|
|
42
|
+
| 'right-end';
|
|
43
|
+
/** The size of the dropdown menu. */
|
|
44
|
+
menuSize?: 'sm' | 'md' | 'lg';
|
|
45
|
+
/** Whether the dropdown menu is visible. */
|
|
46
|
+
menuVisible?: boolean;
|
|
47
|
+
/** The content to display inside the dropdown button. */
|
|
48
|
+
buttonContent?: ReactNode;
|
|
49
|
+
/** A callback function to handle menu visibility changes. */
|
|
50
|
+
onMenuVisibilityChange?: (event: CustomEvent<{ isVisible: boolean }>) => void;
|
|
51
|
+
/** A callback function to handle item selection. */
|
|
52
|
+
onItemSelect?: (event: CustomEvent<{ value: string }>) => void;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Renders a Modus dropdown menu component.
|
|
57
|
+
* @param {ModusDropdownMenuProps} props - The component props.
|
|
58
|
+
* @returns {JSX.Element} The rendered dropdown menu component.
|
|
59
|
+
*/
|
|
60
|
+
export default function ModusDropdownMenu({
|
|
61
|
+
children,
|
|
62
|
+
menuItems,
|
|
63
|
+
buttonColor = 'primary',
|
|
64
|
+
buttonSize = 'md',
|
|
65
|
+
buttonVariant = 'filled',
|
|
66
|
+
customClass,
|
|
67
|
+
disabled = false,
|
|
68
|
+
menuBordered = true,
|
|
69
|
+
menuOffset = 10,
|
|
70
|
+
menuPlacement = 'bottom-start',
|
|
71
|
+
menuSize = 'md',
|
|
72
|
+
menuVisible = false,
|
|
73
|
+
buttonContent,
|
|
74
|
+
onMenuVisibilityChange,
|
|
75
|
+
onItemSelect,
|
|
76
|
+
}: ModusDropdownMenuProps) {
|
|
77
|
+
const dropdownRef = useRef<HTMLModusWcDropdownMenuElement>(null);
|
|
78
|
+
|
|
79
|
+
useEffect(() => {
|
|
80
|
+
const dropdown = dropdownRef.current;
|
|
81
|
+
if (!dropdown) return;
|
|
82
|
+
|
|
83
|
+
const handleMenuVisibilityChange = (event: Event) => {
|
|
84
|
+
onMenuVisibilityChange?.(event as CustomEvent<{ isVisible: boolean }>);
|
|
85
|
+
};
|
|
86
|
+
const handleItemSelect = (event: Event) => {
|
|
87
|
+
onItemSelect?.(event as CustomEvent<{ value: string }>);
|
|
88
|
+
|
|
89
|
+
// Close the menu after item selection
|
|
90
|
+
const dropdown = dropdownRef.current;
|
|
91
|
+
if (dropdown) {
|
|
92
|
+
dropdown.menuVisible = false;
|
|
93
|
+
}
|
|
94
|
+
};
|
|
95
|
+
|
|
96
|
+
if (onMenuVisibilityChange)
|
|
97
|
+
dropdown.addEventListener(
|
|
98
|
+
"menuVisibilityChange",
|
|
99
|
+
handleMenuVisibilityChange
|
|
100
|
+
);
|
|
101
|
+
if (onItemSelect) dropdown.addEventListener("itemSelect", handleItemSelect);
|
|
102
|
+
|
|
103
|
+
return () => {
|
|
104
|
+
if (onMenuVisibilityChange)
|
|
105
|
+
dropdown.removeEventListener(
|
|
106
|
+
"menuVisibilityChange",
|
|
107
|
+
handleMenuVisibilityChange
|
|
108
|
+
);
|
|
109
|
+
if (onItemSelect)
|
|
110
|
+
dropdown.removeEventListener("itemSelect", handleItemSelect);
|
|
111
|
+
};
|
|
112
|
+
}, [onMenuVisibilityChange, onItemSelect]);
|
|
113
|
+
|
|
114
|
+
return (
|
|
115
|
+
<ModusWcDropdownMenu
|
|
116
|
+
ref={dropdownRef}
|
|
117
|
+
buttonColor={buttonColor}
|
|
118
|
+
buttonSize={buttonSize}
|
|
119
|
+
buttonVariant={buttonVariant}
|
|
120
|
+
customClass={customClass}
|
|
121
|
+
disabled={disabled}
|
|
122
|
+
menuBordered={menuBordered}
|
|
123
|
+
menuOffset={menuOffset}
|
|
124
|
+
menuPlacement={menuPlacement}
|
|
125
|
+
menuSize={menuSize}
|
|
126
|
+
menuVisible={menuVisible}
|
|
127
|
+
>
|
|
128
|
+
{buttonContent && <div slot="button">{buttonContent}</div>}
|
|
129
|
+
<div slot="menu">
|
|
130
|
+
{menuItems
|
|
131
|
+
? menuItems.map((item) => (
|
|
132
|
+
<ModusMenuItem
|
|
133
|
+
key={item.value}
|
|
134
|
+
label={item.label}
|
|
135
|
+
value={item.value}
|
|
136
|
+
subLabel={item.subLabel}
|
|
137
|
+
startIcon={item.startIcon}
|
|
138
|
+
selected={item.selected}
|
|
139
|
+
disabled={item.disabled}
|
|
140
|
+
bordered={item.bordered}
|
|
141
|
+
onItemSelect={onItemSelect}
|
|
142
|
+
/>
|
|
143
|
+
))
|
|
144
|
+
: children}
|
|
145
|
+
</div>
|
|
146
|
+
</ModusWcDropdownMenu>
|
|
147
|
+
);
|
|
148
|
+
}
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
import { ModusWcFileDropzone } from "@trimble-oss/moduswebcomponents-react";
|
|
2
|
+
import { forwardRef, useImperativeHandle, useRef } from "react";
|
|
3
|
+
import type { ReactNode } from "react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Props for the ModusFileDropzone component.
|
|
7
|
+
*/
|
|
8
|
+
export interface ModusFileDropzoneProps {
|
|
9
|
+
/** Accepted file types (e.g., '.jpg,.png' or 'image/*'). */
|
|
10
|
+
acceptFileTypes?: string;
|
|
11
|
+
/** Custom CSS class to apply to the dropzone element. */
|
|
12
|
+
customClass?: string;
|
|
13
|
+
/** Disables the file input and dropzone interaction. */
|
|
14
|
+
disabled?: boolean;
|
|
15
|
+
/** Custom instructions shown when files are dragged over the dropzone. */
|
|
16
|
+
fileDraggedOverInstructions?: string;
|
|
17
|
+
/** Show state icon (upload, success, error) in the dropzone. */
|
|
18
|
+
includeStateIcon?: boolean;
|
|
19
|
+
/** Custom instructions shown as the default dropzone message. */
|
|
20
|
+
instructions?: string;
|
|
21
|
+
/** Custom error message when an invalid file type is selected. */
|
|
22
|
+
invalidFileTypeMessage?: string;
|
|
23
|
+
/** Maximum number of files allowed; shows error if exceeded. */
|
|
24
|
+
maxFileCount?: number;
|
|
25
|
+
/** Maximum allowed length of filename (excluding extension); shows error if exceeded. */
|
|
26
|
+
maxFileNameLength?: number;
|
|
27
|
+
/** Maximum total file size in bytes; shows error if exceeded. */
|
|
28
|
+
maxTotalFileSizeBytes?: number;
|
|
29
|
+
/** Allow multiple file selection. */
|
|
30
|
+
multiple?: boolean;
|
|
31
|
+
/** Success message displayed when files are uploaded successfully. */
|
|
32
|
+
successMessage?: string;
|
|
33
|
+
/** Callback when files are selected (via drag-and-drop or file browser). */
|
|
34
|
+
onFileSelect?: (event: CustomEvent<FileList>) => void;
|
|
35
|
+
/** The ARIA label for the dropzone. */
|
|
36
|
+
ariaLabel?: string;
|
|
37
|
+
/** Custom content slot for progress indicators or additional instructions. */
|
|
38
|
+
children?: ReactNode;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* Handle interface for ModusFileDropzone ref methods.
|
|
43
|
+
*/
|
|
44
|
+
export interface ModusFileDropzoneHandle {
|
|
45
|
+
/** Resets the dropzone to its initial state, clearing all error and success states. */
|
|
46
|
+
reset: () => Promise<void>;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Renders a Modus file dropzone component for drag-and-drop file uploads.
|
|
51
|
+
*
|
|
52
|
+
* @example
|
|
53
|
+
* // Basic file dropzone
|
|
54
|
+
* <ModusFileDropzone
|
|
55
|
+
* acceptFileTypes=".doc, .docx, .pdf"
|
|
56
|
+
* instructions="Drag files here or browse to upload"
|
|
57
|
+
* />
|
|
58
|
+
*
|
|
59
|
+
* @example
|
|
60
|
+
* // Multiple files with validation
|
|
61
|
+
* <ModusFileDropzone
|
|
62
|
+
* acceptFileTypes="image/*"
|
|
63
|
+
* multiple
|
|
64
|
+
* maxFileCount={3}
|
|
65
|
+
* maxTotalFileSizeBytes={10485760}
|
|
66
|
+
* instructions="Upload images (max 3 files, 10MB total)"
|
|
67
|
+
* onFileSelect={(e) => console.log('Files:', e.detail)}
|
|
68
|
+
* />
|
|
69
|
+
*
|
|
70
|
+
* @example
|
|
71
|
+
* // With ref for programmatic reset
|
|
72
|
+
* const dropzoneRef = useRef<ModusFileDropzoneHandle>(null);
|
|
73
|
+
* <ModusFileDropzone ref={dropzoneRef} />
|
|
74
|
+
* // Later: dropzoneRef.current?.reset();
|
|
75
|
+
*
|
|
76
|
+
* @param {ModusFileDropzoneProps} props - The component props.
|
|
77
|
+
* @param {React.Ref<ModusFileDropzoneHandle>} ref - The ref for accessing reset method.
|
|
78
|
+
* @returns {JSX.Element} The rendered file dropzone component.
|
|
79
|
+
*/
|
|
80
|
+
const ModusFileDropzone = forwardRef<
|
|
81
|
+
ModusFileDropzoneHandle,
|
|
82
|
+
ModusFileDropzoneProps
|
|
83
|
+
>(
|
|
84
|
+
(
|
|
85
|
+
{
|
|
86
|
+
acceptFileTypes,
|
|
87
|
+
customClass,
|
|
88
|
+
disabled,
|
|
89
|
+
fileDraggedOverInstructions,
|
|
90
|
+
includeStateIcon = true,
|
|
91
|
+
instructions,
|
|
92
|
+
invalidFileTypeMessage,
|
|
93
|
+
maxFileCount,
|
|
94
|
+
maxFileNameLength,
|
|
95
|
+
maxTotalFileSizeBytes,
|
|
96
|
+
multiple,
|
|
97
|
+
successMessage,
|
|
98
|
+
onFileSelect,
|
|
99
|
+
ariaLabel,
|
|
100
|
+
children,
|
|
101
|
+
},
|
|
102
|
+
ref,
|
|
103
|
+
) => {
|
|
104
|
+
const dropzoneRef = useRef<HTMLModusWcFileDropzoneElement>(null);
|
|
105
|
+
|
|
106
|
+
useImperativeHandle(ref, () => ({
|
|
107
|
+
reset: async () => {
|
|
108
|
+
if (dropzoneRef.current) {
|
|
109
|
+
await dropzoneRef.current.reset();
|
|
110
|
+
}
|
|
111
|
+
},
|
|
112
|
+
}));
|
|
113
|
+
|
|
114
|
+
return (
|
|
115
|
+
<ModusWcFileDropzone
|
|
116
|
+
ref={dropzoneRef}
|
|
117
|
+
accept-file-types={acceptFileTypes}
|
|
118
|
+
custom-class={customClass}
|
|
119
|
+
disabled={disabled}
|
|
120
|
+
file-dragged-over-instructions={fileDraggedOverInstructions}
|
|
121
|
+
include-state-icon={includeStateIcon}
|
|
122
|
+
instructions={instructions}
|
|
123
|
+
invalid-file-type-message={invalidFileTypeMessage}
|
|
124
|
+
max-file-count={maxFileCount}
|
|
125
|
+
max-file-name-length={maxFileNameLength}
|
|
126
|
+
max-total-file-size-bytes={maxTotalFileSizeBytes}
|
|
127
|
+
multiple={multiple}
|
|
128
|
+
success-message={successMessage}
|
|
129
|
+
onFileSelect={onFileSelect}
|
|
130
|
+
aria-label={ariaLabel}
|
|
131
|
+
>
|
|
132
|
+
{children && <div slot="dropzone">{children}</div>}
|
|
133
|
+
</ModusWcFileDropzone>
|
|
134
|
+
);
|
|
135
|
+
},
|
|
136
|
+
);
|
|
137
|
+
|
|
138
|
+
ModusFileDropzone.displayName = "ModusFileDropzone";
|
|
139
|
+
|
|
140
|
+
export default ModusFileDropzone;
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
import { ModusWcHandle } from "@trimble-oss/moduswebcomponents-react";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Props for the ModusHandle component.
|
|
5
|
+
*/
|
|
6
|
+
export interface ModusHandleProps {
|
|
7
|
+
/** Custom CSS class to apply to the handle element. */
|
|
8
|
+
customClass?: string;
|
|
9
|
+
/** Initial split percentage (1-100) for the left/top panel. */
|
|
10
|
+
defaultSplit?: number;
|
|
11
|
+
/** Spacing/density of the handle container. */
|
|
12
|
+
density?: "compact" | "comfortable" | "relaxed";
|
|
13
|
+
/** CSS selector or HTMLElement reference for the left/top panel to resize. */
|
|
14
|
+
leftTarget?: string;
|
|
15
|
+
/** Orientation of the handle (horizontal resizes left/right, vertical resizes top/bottom). */
|
|
16
|
+
orientation?: "horizontal" | "vertical";
|
|
17
|
+
/** CSS selector or HTMLElement reference for the right/bottom panel to resize. */
|
|
18
|
+
rightTarget?: string;
|
|
19
|
+
/** Size of the handle bar. */
|
|
20
|
+
size?: "default" | "lg" | "xl" | "2xl";
|
|
21
|
+
/** Type of handle to display - simple bar or button with drag icon. */
|
|
22
|
+
type?: "bar" | "button";
|
|
23
|
+
/** Color of the button (only applies when type="button"). */
|
|
24
|
+
buttonColor?: "primary" | "secondary" | "tertiary" | "warning" | "danger";
|
|
25
|
+
/** Size of the button (only applies when type="button"). */
|
|
26
|
+
buttonSize?: "xs" | "sm" | "md" | "lg";
|
|
27
|
+
/** Variant of the button (only applies when type="button"). */
|
|
28
|
+
buttonVariant?: "borderless" | "filled" | "outlined";
|
|
29
|
+
/** The ARIA label for the handle. */
|
|
30
|
+
ariaLabel?: string;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Renders a Modus handle component for resizing adjacent elements.
|
|
35
|
+
*
|
|
36
|
+
* @example
|
|
37
|
+
* // Basic horizontal handle
|
|
38
|
+
* <div className="flex h-[300px]">
|
|
39
|
+
* <div id="left-panel" className="w-[200px]">Left</div>
|
|
40
|
+
* <ModusHandle
|
|
41
|
+
* orientation="horizontal"
|
|
42
|
+
* leftTarget="#left-panel"
|
|
43
|
+
* rightTarget="#right-panel"
|
|
44
|
+
* />
|
|
45
|
+
* <div id="right-panel" className="flex-1">Right</div>
|
|
46
|
+
* </div>
|
|
47
|
+
*
|
|
48
|
+
* @example
|
|
49
|
+
* // Button type handle
|
|
50
|
+
* <ModusHandle
|
|
51
|
+
* type="button"
|
|
52
|
+
* orientation="horizontal"
|
|
53
|
+
* buttonColor="primary"
|
|
54
|
+
* buttonVariant="outlined"
|
|
55
|
+
* leftTarget="#panel-a"
|
|
56
|
+
* rightTarget="#panel-b"
|
|
57
|
+
* />
|
|
58
|
+
*
|
|
59
|
+
* @example
|
|
60
|
+
* // With custom split percentage
|
|
61
|
+
* <ModusHandle
|
|
62
|
+
* orientation="horizontal"
|
|
63
|
+
* defaultSplit={30}
|
|
64
|
+
* leftTarget="#left"
|
|
65
|
+
* rightTarget="#right"
|
|
66
|
+
* />
|
|
67
|
+
*
|
|
68
|
+
* @param {ModusHandleProps} props - The component props.
|
|
69
|
+
* @returns {JSX.Element} The rendered handle component.
|
|
70
|
+
*/
|
|
71
|
+
export default function ModusHandle({
|
|
72
|
+
customClass,
|
|
73
|
+
defaultSplit = 50,
|
|
74
|
+
density = "comfortable",
|
|
75
|
+
leftTarget,
|
|
76
|
+
orientation = "horizontal",
|
|
77
|
+
rightTarget,
|
|
78
|
+
size = "default",
|
|
79
|
+
type = "bar",
|
|
80
|
+
buttonColor = "tertiary",
|
|
81
|
+
buttonSize = "md",
|
|
82
|
+
buttonVariant = "filled",
|
|
83
|
+
ariaLabel,
|
|
84
|
+
}: ModusHandleProps) {
|
|
85
|
+
return (
|
|
86
|
+
<ModusWcHandle
|
|
87
|
+
custom-class={customClass}
|
|
88
|
+
default-split={defaultSplit}
|
|
89
|
+
density={density}
|
|
90
|
+
left-target={leftTarget}
|
|
91
|
+
orientation={orientation}
|
|
92
|
+
right-target={rightTarget}
|
|
93
|
+
size={size}
|
|
94
|
+
type={type}
|
|
95
|
+
button-color={buttonColor}
|
|
96
|
+
button-size={buttonSize}
|
|
97
|
+
button-variant={buttonVariant}
|
|
98
|
+
aria-label={ariaLabel}
|
|
99
|
+
/>
|
|
100
|
+
);
|
|
101
|
+
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
|
|
2
|
+
|
|
3
|
+
import { ModusWcIcon } from "@trimble-oss/moduswebcomponents-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Props for the ModusIcon component.
|
|
7
|
+
*/
|
|
8
|
+
interface ModusIconProps {
|
|
9
|
+
/** The name of the icon to display. */
|
|
10
|
+
name: string;
|
|
11
|
+
/** The size of the icon. */
|
|
12
|
+
size?: 'xs' | 'sm' | 'md' | 'lg';
|
|
13
|
+
/** Whether the icon is decorative. */
|
|
14
|
+
decorative?: boolean;
|
|
15
|
+
/** A custom CSS class to apply to the icon. */
|
|
16
|
+
customClass?: string;
|
|
17
|
+
/** The ARIA label for the icon. */
|
|
18
|
+
ariaLabel?: string;
|
|
19
|
+
/** The color of the icon. */
|
|
20
|
+
color?: string;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Renders a Modus icon component.
|
|
25
|
+
* @param {ModusIconProps} props - The component props.
|
|
26
|
+
* @returns {JSX.Element} The rendered icon component.
|
|
27
|
+
*/
|
|
28
|
+
export default function ModusIcon({
|
|
29
|
+
name,
|
|
30
|
+
size = 'md',
|
|
31
|
+
decorative = true,
|
|
32
|
+
customClass = '',
|
|
33
|
+
ariaLabel,
|
|
34
|
+
color,
|
|
35
|
+
}: ModusIconProps) {
|
|
36
|
+
// If decorative is false and no ariaLabel is provided, generate one
|
|
37
|
+
const finalAriaLabel = !decorative && !ariaLabel ? `${name} icon` : ariaLabel;
|
|
38
|
+
|
|
39
|
+
return (
|
|
40
|
+
<ModusWcIcon
|
|
41
|
+
name={name}
|
|
42
|
+
size={size}
|
|
43
|
+
decorative={decorative}
|
|
44
|
+
custom-class={customClass}
|
|
45
|
+
aria-label={finalAriaLabel}
|
|
46
|
+
style={color ? { color } : undefined}
|
|
47
|
+
/>
|
|
48
|
+
);
|
|
49
|
+
}
|