Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Convert addon to use template tag #84

Merged
merged 8 commits into from
Apr 18, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/red-lizards-dress.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'ember-headless-form': patch
---

Convert addon to use template tag
16 changes: 16 additions & 0 deletions .prettierrc.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,20 @@ module.exports = {
plugins: ['prettier-plugin-ember-template-tag'],
singleQuote: true,
templateSingleQuote: false,
// this was required to make the VSCode + Prettier work correctly with <template>, see https://github.com/gitKrystan/prettier-plugin-ember-template-tag/issues/38
// we should roll this back once that issue has been fixed!
overrides: [
{
files: '*.gjs',
options: {
parser: 'ember-template-tag',
},
},
{
files: '*.gts',
options: {
parser: 'ember-template-tag',
},
},
],
};
1 change: 1 addition & 0 deletions packages/ember-headless-form/babel.config.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
{
"presets": [["@babel/preset-typescript"]],
"plugins": [
"ember-template-imports/src/babel-plugin",
"@embroider/addon-dev/template-colocation-plugin",
["@babel/plugin-proposal-decorators", { "legacy": true }],
"@babel/plugin-proposal-class-properties"
Expand Down
6 changes: 5 additions & 1 deletion packages/ember-headless-form/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@
"ember-source": ">=4.4.0"
},
"devDependencies": {
"@babel/core": "^7.17.0",
"@babel/core": "^7.21.3",
"@babel/plugin-proposal-class-properties": "^7.16.7",
"@babel/plugin-proposal-decorators": "^7.17.0",
"@babel/plugin-syntax-decorators": "^7.17.0",
Expand All @@ -51,6 +51,7 @@
"@glimmer/tracking": "^1.1.2",
"@glint/core": "^1.0.0-beta.3",
"@glint/environment-ember-loose": "^1.0.0-beta.3",
"@glint/environment-ember-template-imports": "^1.0.0-beta.3",
"@glint/template": "^1.0.0-beta.3",
"@nullvoxpopuli/eslint-configs": "^3.0.2",
"@tsconfig/ember": "^2.0.0",
Expand All @@ -62,6 +63,7 @@
"@types/ember__debug": "^4.0.0",
"@types/ember__engine": "^4.0.0",
"@types/ember__error": "^4.0.0",
"@types/ember__helper": "^4.0.1",
"@types/ember__modifier": "^4.0.3",
"@types/ember__object": "^4.0.0",
"@types/ember__polyfills": "^4.0.0",
Expand All @@ -76,6 +78,7 @@
"@typescript-eslint/parser": "^5.30.5",
"concurrently": "^7.2.1",
"ember-source": "^4.4.0",
"ember-template-imports": "^3.4.1",
"ember-template-lint": "^4.0.0",
"eslint": "^7.32.0",
"eslint-config-prettier": "^8.3.0",
Expand All @@ -85,6 +88,7 @@
"prettier": "^2.8.3",
"rollup": "^3.0.0",
"rollup-plugin-copy": "^3.4.0",
"rollup-plugin-glimmer-template-tag": "^0.3.0",
"rollup-plugin-ts": "^3.2.0",
"typescript": "^5.0.0",
"webpack": "^5.75.0"
Expand Down
6 changes: 5 additions & 1 deletion packages/ember-headless-form/rollup.config.mjs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import typescript from 'rollup-plugin-ts';
import copy from 'rollup-plugin-copy';
import { Addon } from '@embroider/addon-dev/rollup';
import { glimmerTemplateTag } from 'rollup-plugin-glimmer-template-tag';

const addon = new Addon({
srcDir: 'src',
Expand Down Expand Up @@ -31,11 +32,14 @@ export default {
// package names.
addon.dependencies(),

// compile <template> tag into plain JS
glimmerTemplateTag({ preprocessOnly: true }),

// compile TypeScript to latest JavaScript, including Babel transpilation
typescript({
transpiler: 'babel',
browserslist: false,
transpileOnly: false,
transpileOnly: true,
}),

// Ensure that standalone .hbs files are properly integrated as Javascript.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import Component from '@glimmer/component';
import { on } from '@ember/modifier';
import { action } from '@ember/object';

export interface HeadlessFormControlCheckboxComponentSignature {
Expand Down Expand Up @@ -43,4 +44,16 @@ export default class HeadlessFormControlCheckboxComponent extends Component<Head
handleInput(e: Event | InputEvent): void {
this.args.setValue((e.target as HTMLInputElement).checked);
}

<template>
<input
name={{@name}}
type="checkbox"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm surprised to see double quotes here, as we're now (sort of) in JS, and they were single quotes in the hbs... 🤷

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, didn't realise this before. Probably our prettier config is a bit inconsistent. I did wonder why we have single quotes in hbs before (which in other projects were usually double quotes)...

checked={{@value}}
id={{@fieldId}}
aria-invalid={{if @invalid "true"}}
...attributes
{{on "click" this.handleInput}}
/>
</template>
}

This file was deleted.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I love seeing these components in a single file! This is great.

Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import Component from '@glimmer/component';
import { assert } from '@ember/debug';
import { on } from '@ember/modifier';

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yay explicit imports! 🎉

import { action } from '@ember/object';

// Possible values for the input type, see https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input#input_types
Expand Down Expand Up @@ -107,4 +108,16 @@ export default class HeadlessFormControlInputComponent extends Component<Headles
assert('Expected HTMLInputElement', e.target instanceof HTMLInputElement);
this.args.setValue(e.target.value);
}
<template>
<input
name={{@name}}
type={{@type}}
value={{@value}}
id={{@fieldId}}
aria-invalid={{if @invalid "true"}}
aria-describedby={{if @invalid @errorId}}
...attributes
{{on "input" this.handleInput}}
/>
</template>
}

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
import { hash } from '@ember/helper';

import { uniqueId } from '../../utils';
import HeadlessFormControlRadioGroupLabelComponent from './radio-group/label';
import HeadlessFormControlRadioComponent from './radio-group/radio';

import type { TemplateOnlyComponent } from '@ember/component/template-only';
import type { WithBoundArgs } from '@glint/template';

export interface HeadlessFormControlRadioGroupComponentSignature {
Element: HTMLDivElement;
Args: {
// the following are private arguments curried by the component helper, so users will never have to use those

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah, I like this comment and the @internal syntax. I ran into this with a component recently and was wondering if there was good messaging like this


/*
* @internal
*/
name: string;

/*
* @internal
*/
selected: string;

/*
* @internal
*/
setValue: (value: string) => void;

/*
* @internal
*/
invalid: boolean;

/*
* @internal
*/
errorId: string;
};
Blocks: {
default: [
{
/**
* Yielded component that renders the `<input type="radio">` element.
*/
Radio: WithBoundArgs<
typeof HeadlessFormControlRadioComponent,
'name' | 'selected' | 'setValue'
>;

Label: WithBoundArgs<
typeof HeadlessFormControlRadioGroupLabelComponent,
'id'
>;
}
];
};
}

const HeadlessFormControlRadioGroupComponent: TemplateOnlyComponent<HeadlessFormControlRadioGroupComponentSignature> =
<template>
{{#let (uniqueId) as |labelId|}}
<div
role="radiogroup"
aria-labelledby={{labelId}}
aria-invalid={{if @invalid "true"}}
aria-describedby={{if @invalid @errorId}}
...attributes
>
{{yield
(hash
Radio=(component
HeadlessFormControlRadioComponent
name=@name
selected=@selected
setValue=@setValue
)
Label=(component
HeadlessFormControlRadioGroupLabelComponent id=labelId
)
)
}}
</div>
{{/let}}
</template>;

export default HeadlessFormControlRadioGroupComponent;

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import type { TemplateOnlyComponent } from '@ember/component/template-only';

export interface HeadlessFormControlRadioGroupLabelComponentSignature {
Element: HTMLDivElement;
Args: {
// the following are private arguments curried by the component helper, so users will never have to use those

/**
* @internal
*/
id: string;
};
Blocks: {
default: [];
};
}

const HeadlessFormControlRadioGroupLabelComponent: TemplateOnlyComponent<HeadlessFormControlRadioGroupLabelComponentSignature> =
<template><div id={{@id}} ...attributes>{{yield}}</div></template>;

export default HeadlessFormControlRadioGroupLabelComponent;

This file was deleted.

This file was deleted.

Loading