Skip to content

Commit eb32013

Browse files
authored
Showcase: convert PopoverPrimitive page to gts (#3179)
1 parent 83fc30a commit eb32013

File tree

10 files changed

+545
-431
lines changed

10 files changed

+545
-431
lines changed
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
/**
2+
* Copyright (c) HashiCorp, Inc.
3+
* SPDX-License-Identifier: MPL-2.0
4+
*/
5+
import Component from '@glimmer/component';
6+
import { eq } from 'ember-truth-helpers';
7+
8+
import ShwPlaceholder from 'showcase/components/shw/placeholder';
9+
10+
import { HdsPopoverPrimitive } from '@hashicorp/design-system-components/components';
11+
import type { HdsAnchoredPositionOptions } from '@hashicorp/design-system-components/modifiers/hds-anchored-position';
12+
13+
export interface CodeFragmentWithButtonTriggerSignature {
14+
Args: {
15+
isOpen?: boolean;
16+
placement?: HdsAnchoredPositionOptions['placement'];
17+
hasArrow?: boolean;
18+
arrowId?: string;
19+
strategy?: HdsAnchoredPositionOptions['strategy'];
20+
enableCollisionDetection?: HdsAnchoredPositionOptions['enableCollisionDetection'];
21+
enableClickEvents?: boolean;
22+
enableSoftEvents?: boolean;
23+
};
24+
Element: HTMLDivElement;
25+
}
26+
27+
export default class CodeFragmentWithButtonTrigger extends Component<CodeFragmentWithButtonTriggerSignature> {
28+
get anchoredPositionOptions() {
29+
const {
30+
hasArrow,
31+
enableCollisionDetection,
32+
strategy,
33+
placement = 'bottom',
34+
arrowId,
35+
} = this.args;
36+
37+
const options: HdsAnchoredPositionOptions = {
38+
enableCollisionDetection: enableCollisionDetection ?? false,
39+
placement,
40+
arrowSelector: hasArrow ? `#${arrowId}` : undefined,
41+
offsetOptions: hasArrow ? 16 : undefined,
42+
strategy,
43+
};
44+
45+
return options;
46+
}
47+
48+
<template>
49+
<HdsPopoverPrimitive
50+
@isOpen={{if (eq @isOpen undefined) true @isOpen}}
51+
@enableClickEvents={{if
52+
(eq @enableClickEvents undefined)
53+
true
54+
@enableClickEvents
55+
}}
56+
@enableSoftEvents={{@enableSoftEvents}}
57+
as |PP|
58+
>
59+
<div
60+
class="shw-utilities-popover-primitive-fake-container"
61+
{{PP.setupPrimitiveContainer}}
62+
>
63+
<button
64+
type="button"
65+
class="shw-utilities-popover-primitive-fake-toggle"
66+
{{PP.setupPrimitiveToggle}}
67+
>Toggle</button>
68+
<div
69+
class="shw-utilities-popover-primitive-fake-popover"
70+
{{PP.setupPrimitivePopover
71+
anchoredPositionOptions=this.anchoredPositionOptions
72+
}}
73+
>
74+
{{#if @hasArrow}}
75+
<div
76+
id={{@arrowId}}
77+
class="shw-utilities-popover-primitive-fake-arrow"
78+
/>
79+
{{/if}}
80+
<ShwPlaceholder @text="Content" @width="120" @height="40" />
81+
</div>
82+
</div>
83+
</HdsPopoverPrimitive>
84+
</template>
85+
}
Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
/**
2+
* Copyright (c) HashiCorp, Inc.
3+
* SPDX-License-Identifier: MPL-2.0
4+
*/
5+
import Component from '@glimmer/component';
6+
import { eq } from 'ember-truth-helpers';
7+
8+
import ShwPlaceholder from 'showcase/components/shw/placeholder';
9+
10+
import { HdsPopoverPrimitive } from '@hashicorp/design-system-components/components';
11+
import type { HdsAnchoredPositionOptions } from '@hashicorp/design-system-components/modifiers/hds-anchored-position';
12+
13+
export interface CodeFragmentWithPlaceholderTriggerSignature {
14+
Args: {
15+
placement?: HdsAnchoredPositionOptions['placement'];
16+
hasArrow?: boolean;
17+
arrowId?: string;
18+
offset?: HdsAnchoredPositionOptions['offsetOptions'];
19+
arrowPadding?: number;
20+
};
21+
Element: HTMLDivElement;
22+
}
23+
24+
export default class CodeFragmentWithPlaceholderTrigger extends Component<CodeFragmentWithPlaceholderTriggerSignature> {
25+
get anchoredPositionOptions() {
26+
const {
27+
hasArrow,
28+
offset,
29+
arrowPadding,
30+
placement = 'bottom',
31+
arrowId,
32+
} = this.args;
33+
34+
const options: HdsAnchoredPositionOptions = {
35+
enableCollisionDetection: false,
36+
placement,
37+
arrowPadding,
38+
arrowSelector: hasArrow ? `#${arrowId}` : undefined,
39+
offsetOptions: hasArrow ? 16 : undefined,
40+
};
41+
42+
// override default offsetOptions if provided
43+
if (offset) {
44+
options['offsetOptions'] = offset;
45+
}
46+
47+
return options;
48+
}
49+
50+
<template>
51+
<HdsPopoverPrimitive @isOpen={{true}} @enableClickEvents={{true}} as |PP|>
52+
<div
53+
class="shw-utilities-popover-primitive-fake-container"
54+
{{PP.setupPrimitiveContainer}}
55+
>
56+
<button
57+
type="button"
58+
aria-label="target of the popover"
59+
class="shw-utilities-popover-primitive-fake-toggle shw-utilities-popover-primitive-fake-toggle--square"
60+
{{PP.setupPrimitiveToggle}}
61+
/>
62+
<div
63+
class="shw-utilities-popover-primitive-fake-popover"
64+
{{PP.setupPrimitivePopover
65+
anchoredPositionOptions=this.anchoredPositionOptions
66+
}}
67+
>
68+
{{#if @hasArrow}}
69+
<div
70+
id={{@arrowId}}
71+
class="shw-utilities-popover-primitive-fake-arrow"
72+
/>
73+
{{/if}}
74+
<ShwPlaceholder
75+
@text={{if (eq @placement undefined) "content" @placement}}
76+
@width="90"
77+
@height="40"
78+
/>
79+
</div>
80+
</div>
81+
</HdsPopoverPrimitive>
82+
</template>
83+
}
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
/**
2+
* Copyright (c) HashiCorp, Inc.
3+
* SPDX-License-Identifier: MPL-2.0
4+
*/
5+
import type { TemplateOnlyComponent } from '@ember/component/template-only';
6+
import { pageTitle } from 'ember-page-title';
7+
8+
import ShwTextH1 from 'showcase/components/shw/text/h1';
9+
10+
import SubSectionBase from 'showcase/components/page-utilities/popover-primitive/sub-sections/base';
11+
import SubSectionInteraction from 'showcase/components/page-utilities/popover-primitive/sub-sections/interaction';
12+
import SubSectionOptions from 'showcase/components/page-utilities/popover-primitive/sub-sections/options';
13+
14+
const PopoverPrimitiveIndex: TemplateOnlyComponent = <template>
15+
{{pageTitle "PopoverPrimitive Component"}}
16+
17+
<ShwTextH1>PopoverPrimitive</ShwTextH1>
18+
19+
<section data-test-percy>
20+
<SubSectionBase />
21+
<SubSectionOptions />
22+
<SubSectionInteraction />
23+
</section>
24+
</template>;
25+
26+
export default PopoverPrimitiveIndex;
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
/**
2+
* Copyright (c) HashiCorp, Inc.
3+
* SPDX-License-Identifier: MPL-2.0
4+
*/
5+
import type { TemplateOnlyComponent } from '@ember/component/template-only';
6+
import style from 'ember-style-modifier';
7+
8+
import ShwDivider from 'showcase/components/shw/divider';
9+
import ShwGrid from 'showcase/components/shw/grid';
10+
import ShwTextH2 from 'showcase/components/shw/text/h2';
11+
12+
import CodeFragmentWithButtonTrigger from 'showcase/components/page-utilities/popover-primitive/code-fragments/with-button-trigger';
13+
14+
const SubSectionBase: TemplateOnlyComponent = <template>
15+
<ShwTextH2>Base elements</ShwTextH2>
16+
17+
<ShwGrid @columns={{4}} @gap="2rem" {{style margin-bottom="6rem"}} as |SG|>
18+
<SG.Item @label="Base">
19+
<CodeFragmentWithButtonTrigger />
20+
</SG.Item>
21+
<SG.Item @label="With arrow">
22+
<CodeFragmentWithButtonTrigger @hasArrow={{true}} @arrowId="arrow-base" />
23+
</SG.Item>
24+
</ShwGrid>
25+
26+
<ShwDivider />
27+
</template>;
28+
29+
export default SubSectionBase;
Lines changed: 114 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,114 @@
1+
/**
2+
* Copyright (c) HashiCorp, Inc.
3+
* SPDX-License-Identifier: MPL-2.0
4+
*/
5+
import type { TemplateOnlyComponent } from '@ember/component/template-only';
6+
import { eq } from 'ember-truth-helpers';
7+
import { hash, concat } from '@ember/helper';
8+
import { on } from '@ember/modifier';
9+
import style from 'ember-style-modifier';
10+
11+
import ShwDivider from 'showcase/components/shw/divider';
12+
import ShwGrid from 'showcase/components/shw/grid';
13+
import ShwTextH2 from 'showcase/components/shw/text/h2';
14+
import ShwTextH3 from 'showcase/components/shw/text/h3';
15+
16+
import { HdsPopoverPrimitive } from '@hashicorp/design-system-components/components';
17+
18+
import CodeFragmentWithButtonTrigger from 'showcase/components/page-utilities/popover-primitive/code-fragments/with-button-trigger';
19+
20+
const INTERACTION_VARIANTS = ['none', 'soft', 'click'];
21+
const IS_OPEN_VARIANTS = [false, true];
22+
23+
const SubSectionInteraction: TemplateOnlyComponent = <template>
24+
<ShwTextH2>Interaction</ShwTextH2>
25+
26+
<ShwGrid @columns={{4}} @gap="2rem" {{style align-items="center"}} as |SG|>
27+
{{#each INTERACTION_VARIANTS as |interaction|}}
28+
{{#unless (eq interaction "none")}}
29+
<SG.Item
30+
@label={{if (eq interaction "soft") 'Hover/Focus ("Soft")' "Click"}}
31+
>
32+
<HdsPopoverPrimitive
33+
@enableSoftEvents={{eq interaction "soft"}}
34+
@enableClickEvents={{eq interaction "click"}}
35+
as |PP|
36+
>
37+
<div
38+
class="shw-utilities-popover-primitive-fake-container"
39+
{{PP.setupPrimitiveContainer}}
40+
>
41+
<button
42+
type="button"
43+
class="shw-utilities-popover-primitive-fake-toggle"
44+
{{PP.setupPrimitiveToggle}}
45+
>Toggle</button>
46+
<div
47+
class="shw-utilities-popover-primitive-fake-popover"
48+
{{PP.setupPrimitivePopover
49+
anchoredPositionOptions=(hash
50+
enableCollisionDetection=true
51+
offsetOptions=16
52+
arrowSelector=(concat "#" "arrow-interaction-" interaction)
53+
)
54+
}}
55+
>
56+
<div
57+
id="arrow-interaction-{{interaction}}"
58+
class="shw-utilities-popover-primitive-fake-arrow"
59+
/>
60+
<div class="shw-component-popover-primitive-interaction-bubble">
61+
<button
62+
type="button"
63+
{{on "click" PP.hidePopover}}
64+
title="Button that closes the popover on click"
65+
>x</button>
66+
<ul>
67+
<li>
68+
Lorem ipsum dolor sit amet consectetur
69+
</li>
70+
<li>
71+
<a href="https://google.com">Link to Google</a>
72+
</li>
73+
<li>
74+
<button type="button" {{on "click" PP.hidePopover}}>Got
75+
it!</button>
76+
</li>
77+
</ul>
78+
</div>
79+
</div>
80+
</div>
81+
</HdsPopoverPrimitive>
82+
</SG.Item>
83+
{{/unless}}
84+
{{/each}}
85+
</ShwGrid>
86+
87+
<ShwDivider @level={{2}} />
88+
89+
<ShwTextH3>In combination with <code>@isOpen</code></ShwTextH3>
90+
91+
{{#each IS_OPEN_VARIANTS as |isOpen|}}
92+
<ShwGrid @columns={{3}} @gap="2rem" {{style margin-bottom="4rem"}} as |SG|>
93+
{{#each INTERACTION_VARIANTS as |interaction|}}
94+
<SG.Item @label={{concat interaction " / isOpen={{" isOpen "}}"}}>
95+
<CodeFragmentWithButtonTrigger
96+
@hasArrow={{true}}
97+
@arrowId={{concat
98+
"arrow-interaction-isopen-"
99+
isOpen
100+
"-"
101+
interaction
102+
}}
103+
@isOpen={{isOpen}}
104+
@enableClickEvents={{eq interaction "click"}}
105+
@enableSoftEvents={{eq interaction "soft"}}
106+
@enableCollisionDetection={{true}}
107+
/>
108+
</SG.Item>
109+
{{/each}}
110+
</ShwGrid>
111+
{{/each}}
112+
</template>;
113+
114+
export default SubSectionInteraction;

0 commit comments

Comments
 (0)