From 6cfab01577b0e1a79f97d11a2d901771ee78ac2a Mon Sep 17 00:00:00 2001 From: Tony Ward <8069555+ynotdraw@users.noreply.github.com> Date: Thu, 20 Jul 2023 14:25:27 -0400 Subject: [PATCH 1/3] Expose character counter via ToucanForm --- docs/components/input-field/index.md | 14 ++ docs/components/textarea-field/index.md | 14 ++ .../src/-private/input-field.hbs | 228 +++++++++++++----- .../src/-private/textarea-field.hbs | 228 +++++++++++++----- .../toucan-form/form-input-test.gts | 92 +++++++ .../toucan-form/form-textarea-test.gts | 92 +++++++ 6 files changed, 548 insertions(+), 120 deletions(-) diff --git a/docs/components/input-field/index.md b/docs/components/input-field/index.md index 177345065..623b70e02 100644 --- a/docs/components/input-field/index.md +++ b/docs/components/input-field/index.md @@ -70,6 +70,20 @@ Provide a string to the `@hint` component argument or content to `:hint` named b ``` +## Character Counter + +Optional. + +A character counter is exposed via a `secondary` block. It can be combined with any of the other named blocks or label/hint arguments. + +```hbs + + <:secondary as |secondary|> + + + +``` + ## Error Optional. diff --git a/docs/components/textarea-field/index.md b/docs/components/textarea-field/index.md index c560c8a13..9820c3b41 100644 --- a/docs/components/textarea-field/index.md +++ b/docs/components/textarea-field/index.md @@ -66,6 +66,20 @@ Provide a string to the `@hint` component argument or content to `:hint` named b ``` +## Character Counter + +Optional. + +A character counter is exposed via a `secondary` block. It can be combined with any of the other named blocks or label/hint arguments. + +```hbs + + <:secondary as |secondary|> + + + +``` + ## Error Optional. diff --git a/packages/ember-toucan-form/src/-private/input-field.hbs b/packages/ember-toucan-form/src/-private/input-field.hbs index 37952ab5a..6ba411b79 100644 --- a/packages/ember-toucan-form/src/-private/input-field.hbs +++ b/packages/ember-toucan-form/src/-private/input-field.hbs @@ -18,66 +18,174 @@ a string is easy. }} <@form.Field @name={{@name}} as |field|> - {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} - - <:label>{{yield to='label'}} - - {{else if (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) - }} - - <:label>{{yield to='label'}} - <:hint>{{yield to='hint'}} - - {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} - - <:hint>{{yield to='hint'}} - + {{#if (has-block 'secondary')}} + {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} + + <:label>{{yield to='label'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else if + (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) + }} + + <:label>{{yield to='label'}} + <:hint>{{yield to='hint'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} + + <:hint>{{yield to='hint'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else}} + {{! Argument-only case }} + + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{/if}} {{else}} - {{! Argument-only case }} - + {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} + + <:label>{{yield to='label'}} + + {{else if + (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) + }} + + <:label>{{yield to='label'}} + <:hint>{{yield to='hint'}} + + {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} + + <:hint>{{yield to='hint'}} + + {{else}} + {{! Argument-only case }} + + {{/if}} {{/if}} \ No newline at end of file diff --git a/packages/ember-toucan-form/src/-private/textarea-field.hbs b/packages/ember-toucan-form/src/-private/textarea-field.hbs index 25544ae83..c8cefbd5a 100644 --- a/packages/ember-toucan-form/src/-private/textarea-field.hbs +++ b/packages/ember-toucan-form/src/-private/textarea-field.hbs @@ -18,66 +18,174 @@ a string is easy. }} <@form.Field @name={{@name}} as |field|> - {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} - - <:label>{{yield to='label'}} - - {{else if (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) - }} - - <:label>{{yield to='label'}} - <:hint>{{yield to='hint'}} - - {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} - - <:hint>{{yield to='hint'}} - + {{#if (has-block 'secondary')}} + {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} + + <:label>{{yield to='label'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else if + (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) + }} + + <:label>{{yield to='label'}} + <:hint>{{yield to='hint'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} + + <:hint>{{yield to='hint'}} + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{else}} + {{! Argument-only case }} + + <:secondary as |secondary|> + {{yield + (hash + CharacterCount=(component + (ensure-safe-component secondary.CharacterCount) + ) + ) + to='secondary' + }} + + + {{/if}} {{else}} - {{! Argument-only case }} - + {{#if (this.hasOnlyLabelBlock (has-block 'label') (has-block 'hint'))}} + + <:label>{{yield to='label'}} + + {{else if + (this.hasHintAndLabelBlocks (has-block 'label') (has-block 'hint')) + }} + + <:label>{{yield to='label'}} + <:hint>{{yield to='hint'}} + + {{else if (this.hasLabelArgAndHintBlock @label (has-block 'hint'))}} + + <:hint>{{yield to='hint'}} + + {{else}} + {{! Argument-only case }} + + {{/if}} {{/if}} \ No newline at end of file diff --git a/test-app/tests/integration/components/toucan-form/form-input-test.gts b/test-app/tests/integration/components/toucan-form/form-input-test.gts index 45b0104f8..c2a26d723 100644 --- a/test-app/tests/integration/components/toucan-form/form-input-test.gts +++ b/test-app/tests/integration/components/toucan-form/form-input-test.gts @@ -46,6 +46,26 @@ module('Integration | Component | ToucanForm | Input', function (hooks) { assert.dom('[data-hint]').exists(); }); + test('it renders `@label` and `@hint` component arguments with the character counter', async function (assert) { + const data: TestData = { + text: 'text', + }; + + await render(); + + assert.dom('[data-label]').exists(); + assert.dom('[data-hint]').exists(); + assert.dom('[data-character-count]').exists(); + }); + test('it renders a `:label` named block with a `@hint` argument', async function (assert) { const data: TestData = { text: 'text', @@ -66,6 +86,31 @@ module('Integration | Component | ToucanForm | Input', function (hooks) { assert.dom('[data-hint]').hasText('Hint'); }); + test('it renders a `:label` named block with a `@hint` argument with the character counter', async function (assert) { + const data: TestData = { + text: 'text', + }; + + await render(); + + assert.dom('[data-label-block]').exists(); + + // NOTE: `data-hint` comes from `@hint`. + assert.dom('[data-hint]').exists(); + assert.dom('[data-hint]').hasText('Hint'); + + assert.dom('[data-character-count]').exists(); + }); + test('it renders a `:hint` named block with a `@label` argument', async function (assert) { const data: TestData = { text: 'text', @@ -86,6 +131,31 @@ module('Integration | Component | ToucanForm | Input', function (hooks) { assert.dom('[data-hint-block]').exists(); }); + test('it renders a `:hint` named block with a `@label` argument with the character counter', async function (assert) { + const data: TestData = { + text: 'text', + }; + + await render(); + + // NOTE: `data-label` comes from `@label`. + assert.dom('[data-label]').exists(); + assert.dom('[data-label]').hasText('Label'); + + assert.dom('[data-hint-block]').exists(); + + assert.dom('[data-character-count]').exists(); + }); + test('it renders both a `:label` and `:hint` named block', async function (assert) { const data: TestData = { text: 'text', @@ -103,4 +173,26 @@ module('Integration | Component | ToucanForm | Input', function (hooks) { assert.dom('[data-label-block]').exists(); assert.dom('[data-hint-block]').exists(); }); + + test('it renders `:label`, `:secondary` with character counter, and `:hint` blocks', async function (assert) { + const data: TestData = { + text: 'text', + }; + + await render(); + + assert.dom('[data-label-block]').exists(); + assert.dom('[data-hint-block]').exists(); + assert.dom('[data-character-count]').exists(); + }); }); diff --git a/test-app/tests/integration/components/toucan-form/form-textarea-test.gts b/test-app/tests/integration/components/toucan-form/form-textarea-test.gts index cbb88a568..1b87ecb04 100644 --- a/test-app/tests/integration/components/toucan-form/form-textarea-test.gts +++ b/test-app/tests/integration/components/toucan-form/form-textarea-test.gts @@ -46,6 +46,26 @@ module('Integration | Component | ToucanForm | Textarea', function (hooks) { assert.dom('[data-hint]').exists(); }); + test('it renders `@label` and `@hint` component arguments with the character counter', async function (assert) { + const data: TestData = { + text: 'multi-line text', + }; + + await render(); + + assert.dom('[data-label]').exists(); + assert.dom('[data-hint]').exists(); + assert.dom('[data-character-count]').exists(); + }); + test('it renders a `:label` named block with a `@hint` argument', async function (assert) { const data: TestData = { text: 'multi-line text', @@ -66,6 +86,31 @@ module('Integration | Component | ToucanForm | Textarea', function (hooks) { assert.dom('[data-hint]').hasText('Hint'); }); + test('it renders a `:label` named block with a `@hint` argument with the character counter', async function (assert) { + const data: TestData = { + text: 'multi-line text', + }; + + await render(); + + assert.dom('[data-label-block]').exists(); + + // NOTE: `data-hint` comes from `@hint`. + assert.dom('[data-hint]').exists(); + assert.dom('[data-hint]').hasText('Hint'); + + assert.dom('[data-character-count]').exists(); + }); + test('it renders a `:hint` named block with a `@label` argument', async function (assert) { const data: TestData = { text: 'multi-line text', @@ -86,6 +131,31 @@ module('Integration | Component | ToucanForm | Textarea', function (hooks) { assert.dom('[data-hint-block]').exists(); }); + test('it renders a `:hint` named block with a `@label` argument with the character counter', async function (assert) { + const data: TestData = { + text: 'multi-line text', + }; + + await render(); + + // NOTE: `data-label` comes from `@label`. + assert.dom('[data-label]').exists(); + assert.dom('[data-label]').hasText('Label'); + + assert.dom('[data-hint-block]').exists(); + + assert.dom('[data-character-count]').exists(); + }); + test('it renders both a `:label` and `:hint` named block', async function (assert) { const data: TestData = { text: 'multi-line text', @@ -103,4 +173,26 @@ module('Integration | Component | ToucanForm | Textarea', function (hooks) { assert.dom('[data-label-block]').exists(); assert.dom('[data-hint-block]').exists(); }); + + test('it renders `:label`, `:secondary` with character counter, and `:hint` blocks', async function (assert) { + const data: TestData = { + text: 'multi-line text', + }; + + await render(); + + assert.dom('[data-label-block]').exists(); + assert.dom('[data-hint-block]').exists(); + assert.dom('[data-character-count]').exists(); + }); }); From 3cb8650b0d9757f8bd913bda276776679e99000f Mon Sep 17 00:00:00 2001 From: Tony Ward <8069555+ynotdraw@users.noreply.github.com> Date: Thu, 20 Jul 2023 14:25:59 -0400 Subject: [PATCH 2/3] Revert back to docfy0.6.0 --- docs-app/package.json | 4 ++-- pnpm-lock.yaml | 32 ++++++++++++++------------------ 2 files changed, 16 insertions(+), 20 deletions(-) diff --git a/docs-app/package.json b/docs-app/package.json index 80b95a16d..73bb9ddf2 100644 --- a/docs-app/package.json +++ b/docs-app/package.json @@ -30,8 +30,8 @@ "@babel/eslint-parser": "^7.19.1", "@crowdstrike/ember-toucan-styles": "^2.0.1", "@crowdstrike/tailwind-toucan-base": "^3.5.0", - "@docfy/core": "^0.7.0", - "@docfy/ember": "^0.7.0", + "@docfy/core": "^0.6.0", + "@docfy/ember": "^0.6.0", "@ember/optional-features": "^2.0.0", "@ember/string": "^3.0.1", "@ember/test-helpers": "^3.1.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index ea72b3b25..617789918 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -30,7 +30,7 @@ importers: dependencies: '@crowdstrike/ember-oss-docs': specifier: ^1.1.6 - version: 1.1.6(@babel/core@7.20.12)(@crowdstrike/tailwind-toucan-base@3.5.0)(@docfy/core@0.7.0)(@docfy/ember@0.7.0)(@glimmer/component@1.1.2)(@glint/environment-ember-loose@1.0.2)(@glint/template@1.0.2)(@tailwindcss/typography@0.5.9)(ember-browser-services@4.0.4)(ember-source@5.1.0)(highlight.js@11.7.0)(highlightjs-glimmer@2.0.1) + version: 1.1.6(@babel/core@7.20.12)(@crowdstrike/tailwind-toucan-base@3.5.0)(@docfy/core@0.6.0)(@docfy/ember@0.6.0)(@glimmer/component@1.1.2)(@glint/environment-ember-loose@1.0.2)(@glint/template@1.0.2)(@tailwindcss/typography@0.5.9)(ember-browser-services@4.0.4)(ember-source@5.1.0)(highlight.js@11.7.0)(highlightjs-glimmer@2.0.1) '@crowdstrike/ember-toucan-core': specifier: workspace:* version: file:packages/ember-toucan-core(@babel/core@7.20.12)(@crowdstrike/ember-toucan-styles@2.0.1)(@ember/test-helpers@3.1.0)(@glimmer/tracking@1.1.2)(autoprefixer@10.4.13)(ember-source@5.1.0)(fractal-page-object@0.4.0)(postcss@8.4.21)(tailwindcss@3.2.4) @@ -81,11 +81,11 @@ importers: specifier: ^3.5.0 version: 3.5.0(autoprefixer@10.4.13)(postcss@8.4.21) '@docfy/core': - specifier: ^0.7.0 - version: 0.7.0 + specifier: ^0.6.0 + version: 0.6.0 '@docfy/ember': - specifier: ^0.7.0 - version: 0.7.0 + specifier: ^0.6.0 + version: 0.6.0 '@ember/optional-features': specifier: ^2.0.0 version: 2.0.0 @@ -3632,7 +3632,7 @@ packages: dev: true optional: true - /@crowdstrike/ember-oss-docs@1.1.6(@babel/core@7.20.12)(@crowdstrike/tailwind-toucan-base@3.5.0)(@docfy/core@0.7.0)(@docfy/ember@0.7.0)(@glimmer/component@1.1.2)(@glint/environment-ember-loose@1.0.2)(@glint/template@1.0.2)(@tailwindcss/typography@0.5.9)(ember-browser-services@4.0.4)(ember-source@5.1.0)(highlight.js@11.7.0)(highlightjs-glimmer@2.0.1): + /@crowdstrike/ember-oss-docs@1.1.6(@babel/core@7.20.12)(@crowdstrike/tailwind-toucan-base@3.5.0)(@docfy/core@0.6.0)(@docfy/ember@0.6.0)(@glimmer/component@1.1.2)(@glint/environment-ember-loose@1.0.2)(@glint/template@1.0.2)(@tailwindcss/typography@0.5.9)(ember-browser-services@4.0.4)(ember-source@5.1.0)(highlight.js@11.7.0)(highlightjs-glimmer@2.0.1): resolution: {integrity: sha512-hq6FxeQFjdlCsGniG3EvcUSxZWGfAKAcVg/2rcUxgdiauTkgvJAaCa68oggpTe+m5B4jaijoeNr3eAV5yj8o4w==} peerDependencies: '@crowdstrike/tailwind-toucan-base': ^3.3.1 @@ -3648,8 +3648,8 @@ packages: dependencies: '@babel/runtime': 7.21.5 '@crowdstrike/tailwind-toucan-base': 3.5.0(autoprefixer@10.4.13)(postcss@8.4.21) - '@docfy/core': 0.7.0 - '@docfy/ember': 0.7.0 + '@docfy/core': 0.6.0 + '@docfy/ember': 0.6.0 '@embroider/addon-shim': 1.8.4 '@glimmer/component': 1.1.2(@babel/core@7.20.12) '@glint/environment-ember-loose': 1.0.2(@glimmer/component@1.1.2)(@glint/template@1.0.2)(@types/ember__array@4.0.3)(@types/ember__component@4.0.12)(@types/ember__controller@4.0.4)(@types/ember__object@4.0.5)(@types/ember__routing@4.0.12)(ember-cli-htmlbars@6.2.0)(ember-modifier@4.1.0) @@ -3722,8 +3722,8 @@ packages: - postcss - ts-node - /@docfy/core@0.7.0: - resolution: {integrity: sha512-7FRhToPy+jsVlq/8ESmfjcF6Y+AoAjht6fTBLUSxNGzXt3FsPLK6XkfZitfubyZLs/BNhO9l2NYNnKsmLTMciw==} + /@docfy/core@0.6.0: + resolution: {integrity: sha512-2L5UiE720h6tmkTxvB43Q+nZybKV/8UC6jYVBqiyP9YriVjWxxVpTkR80Egg4rrMnGfYKedOI4ZgxekgdoHDMQ==} engines: {node: '>= 12.*'} dependencies: debug: 4.3.4 @@ -3745,15 +3745,15 @@ packages: trough: 1.0.5 unified: 9.2.2 unist-util-visit: 2.0.3 - yaml: 2.3.1 + yaml: 1.10.2 transitivePeerDependencies: - supports-color - /@docfy/ember@0.7.0: - resolution: {integrity: sha512-tnDsaKmGxjhRuWtpgH0AY9DTdL4M4fxPPVCGGnb4oQIpDYodfzhER7YjRiFZ2KLUMJ8rsNiuBMUxPeFwV9W7HA==} + /@docfy/ember@0.6.0: + resolution: {integrity: sha512-TcZoNwZpQGs7EuvSvuxLp6gt11Fq/9qIHUESYR5j9qZOwLFvuvRXaui27n+Rq03LZQW/eGtBUQM06nSn9FsuXg==} engines: {node: '>= 12'} dependencies: - '@docfy/core': 0.7.0 + '@docfy/core': 0.6.0 broccoli-bridge: 1.0.0 broccoli-file-creator: 2.1.1 broccoli-funnel: 3.0.8 @@ -18965,10 +18965,6 @@ packages: resolution: {integrity: sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==} engines: {node: '>= 6'} - /yaml@2.3.1: - resolution: {integrity: sha512-2eHWfjaoXgTBC2jNM1LRef62VQa0umtvRiDSk6HSzW7RvS5YtkabJrwYLLEKWBc8a5U2PTSCs+dJjUTJdlHsWQ==} - engines: {node: '>= 14'} - /yargs-parser@18.1.3: resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==} engines: {node: '>=6'} From ff50f274aad06257f05dd8ddbb39e76377edf755 Mon Sep 17 00:00:00 2001 From: Tony Ward <8069555+ynotdraw@users.noreply.github.com> Date: Thu, 20 Jul 2023 14:29:19 -0400 Subject: [PATCH 3/3] Add a changeset --- .changeset/eight-shoes-flash.md | 25 +++++++++++++++++++ .../toucan-form/form-input-test.gts | 4 +-- .../toucan-form/form-textarea-test.gts | 4 +-- 3 files changed, 29 insertions(+), 4 deletions(-) create mode 100644 .changeset/eight-shoes-flash.md diff --git a/.changeset/eight-shoes-flash.md b/.changeset/eight-shoes-flash.md new file mode 100644 index 000000000..3bf93d6f7 --- /dev/null +++ b/.changeset/eight-shoes-flash.md @@ -0,0 +1,25 @@ +--- +'@crowdstrike/ember-toucan-form': patch +--- + +Expose the `:secondary` block and Character Counter component from ` + + <:label>Label + <:hint>Hint + <:secondary as |secondary|> + + + + + + <:label>Label + <:hint>Hint + <:secondary as |secondary|> + + + + +``` diff --git a/test-app/tests/integration/components/toucan-form/form-input-test.gts b/test-app/tests/integration/components/toucan-form/form-input-test.gts index c2a26d723..5794f4411 100644 --- a/test-app/tests/integration/components/toucan-form/form-input-test.gts +++ b/test-app/tests/integration/components/toucan-form/form-input-test.gts @@ -163,7 +163,7 @@ module('Integration | Component | ToucanForm | Input', function (hooks) { await render(