@hashicorp/design-system-components 0.0.20 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/.husky/pre-commit CHANGED
@@ -1,14 +1,4 @@
1
1
  #!/bin/sh
2
2
  . "$(dirname "$0")/_/husky.sh"
3
3
 
4
- export NVM_DIR="$HOME/.nvm/nvm.sh"
5
- . "$(dirname $NVM_DIR)/nvm.sh"
6
-
7
- export NVM_DIR="$HOME/.nvm"
8
- a=$(nvm ls | grep 'node')
9
- b=${a#*(-> }
10
- v=${b%%[)| ]*}
11
-
12
- export PATH="$NVM_DIR/versions/node/$v/bin:$PATH"
13
-
14
- npx lint-staged
4
+ yarn lint-staged
@@ -0,0 +1,17 @@
1
+ <div class="hds-disclosure" ...attributes>
2
+ <div class="hds-disclosure__toggle">
3
+ {{yield (hash onClickToggle=this.onClickToggle) to="toggle"}}
4
+ </div>
5
+ {{#if this.isActive}}
6
+ <div
7
+ class="hds-disclosure__content"
8
+ {{focus-trap
9
+ isActive=this.isActive
10
+ shouldSelfFocus=false
11
+ focusTrapOptions=(hash clickOutsideDeactivates=this.clickOutsideDeactivates onDeactivate=this.onDeactivate)
12
+ }}
13
+ >
14
+ {{yield to="content"}}
15
+ </div>
16
+ {{/if}}
17
+ </div>
@@ -0,0 +1,41 @@
1
+ import Component from '@glimmer/component';
2
+ import { tracked } from '@glimmer/tracking';
3
+ import { action } from '@ember/object';
4
+
5
+ export default class HdsDisclosureComponent extends Component {
6
+ @tracked isActive; // notice: if in the future we need to add a "@isActive" prop to control the status from outside (eg to have the Disclosure opened on render) just add "this.args.isActive" here to initalize the variable
7
+ @tracked toggleRef;
8
+ @tracked isToggleClicked;
9
+
10
+ @action
11
+ onClickToggle(event) {
12
+ // we store a reference to the DOM node that has the "onClickToggle" event associated with it
13
+ if (!this.toggleRef) {
14
+ this.toggleRef = event.currentTarget;
15
+ }
16
+ this.isActive = !this.isActive;
17
+ }
18
+
19
+ @action
20
+ clickOutsideDeactivates(event) {
21
+ // we check if the toggle reference belongs to the tree of parent DOM nodes
22
+ // of the element that was clicked and triggered the "click outside" event handling
23
+ this.isToggleClicked = event.path.includes(this.toggleRef);
24
+ // here we need to return `true` to make sure that the focus trap will be deactivated (and allow the click event to do its thing (i.e. to pass-through to the element that was clicked).
25
+ // see: https://github.com/focus-trap/focus-trap#createoptions
26
+ return true;
27
+ }
28
+
29
+ @action
30
+ onDeactivate() {
31
+ // on deactivate we hide the content, except for the case when the button has been clicked
32
+ // the reason is that the "onClickToggle" is called in any case (there's no way to block the event)
33
+ // so when the user clicks the toggle to close the panel, we let the "onClickToggle" handle the closure
34
+ // otherwise we would have two changes of status, this and the toggle, and the panel would remain open
35
+ if (!this.isToggleClicked) {
36
+ this.isActive = false;
37
+ // we need to reset this check
38
+ this.isToggleClicked = false;
39
+ }
40
+ }
41
+ }
@@ -0,0 +1 @@
1
+ export { default } from '@hashicorp/design-system-components/components/hds/disclosure/index';
@@ -3,12 +3,11 @@
3
3
  @use "helpers/elevation";
4
4
  @use "helpers/focus-ring";
5
5
 
6
- @use "../mixins/generic-focus-state";
7
-
8
6
  @use "../components/badge";
9
7
  @use "../components/badge-count";
10
8
  @use "../components/button";
11
9
  @use "../components/card";
10
+ @use "../components/disclosure";
12
11
  @use "../components/icon-tile";
13
12
  @use "../components/link/standalone";
14
13
 
@@ -63,36 +63,36 @@ $size-props: (
63
63
 
64
64
  .hds-badge-count--color-neutral {
65
65
  &.hds-badge-count--type-filled {
66
- background-color: var(--token-color-palette-neutral-100);
67
- color: var(--token-color-palette-neutral-600);
66
+ background-color: var(--token-color-surface-strong);
67
+ color: var(--token-color-foreground-primary);
68
68
  }
69
69
 
70
70
  &.hds-badge-count--type-inverted {
71
- background-color: var(--token-color-palette-neutral-500);
72
- color: var(--token-color-palette-neutral-0);
71
+ background-color: var(--token-color-foreground-faint);
72
+ color: var(--token-color-foreground-high-contrast);
73
73
  }
74
74
 
75
75
  &.hds-badge-count--type-outlined {
76
76
  background-color: transparent;
77
- border-color: var(--token-color-palette-neutral-500);
78
- color: var(--token-color-palette-neutral-600);
77
+ border-color: var(--token-color-foreground-faint);
78
+ color: var(--token-color-foreground-primary);
79
79
  }
80
80
  }
81
81
 
82
82
  .hds-badge-count--color-neutral-dark-mode {
83
83
  &.hds-badge-count--type-filled {
84
- background-color: var(--token-color-palette-neutral-500);
85
- color: var(--token-color-palette-neutral-0);
84
+ background-color: var(--token-color-foreground-faint);
85
+ color: var(--token-color-foreground-high-contrast);
86
86
  }
87
87
 
88
88
  &.hds-badge-count--type-inverted {
89
- background-color: var(--token-color-palette-neutral-50);
90
- color: var(--token-color-palette-neutral-600);
89
+ background-color: var(--token-color-surface-faint);
90
+ color: var(--token-color-foreground-primary);
91
91
  }
92
92
 
93
93
  &.hds-badge-count--type-outlined {
94
94
  background-color: transparent;
95
95
  border-color: var(--token-color-palette-neutral-100);
96
- color: var(--token-color-palette-neutral-0);
96
+ color: var(--token-color-foreground-high-contrast);
97
97
  }
98
98
  }
@@ -91,56 +91,56 @@ $size-props: (
91
91
 
92
92
  .hds-badge--color-neutral {
93
93
  &.hds-badge--type-filled {
94
- background-color: var(--token-color-palette-neutral-100);
95
- color: var(--token-color-palette-neutral-600);
94
+ background-color: var(--token-color-surface-strong);
95
+ color: var(--token-color-foreground-primary);
96
96
  }
97
97
 
98
98
  &.hds-badge--type-inverted {
99
- background-color: var(--token-color-palette-neutral-500);
100
- color: var(--token-color-palette-neutral-0);
99
+ background-color: var(--token-color-foreground-faint);
100
+ color: var(--token-color-foreground-high-contrast);
101
101
  }
102
102
 
103
103
  &.hds-badge--type-outlined {
104
104
  background-color: transparent;
105
- border-color: var(--token-color-palette-neutral-500);
106
- color: var(--token-color-palette-neutral-600);
105
+ border-color: var(--token-color-foreground-faint);
106
+ color: var(--token-color-foreground-primary);
107
107
  }
108
108
  }
109
109
 
110
110
  .hds-badge--color-neutral-dark-mode {
111
111
  &.hds-badge--type-filled {
112
- background-color: var(--token-color-palette-neutral-500);
113
- color: var(--token-color-palette-neutral-0);
112
+ background-color: var(--token-color-foreground-faint);
113
+ color: var(--token-color-foreground-high-contrast);
114
114
  }
115
115
 
116
116
  &.hds-badge--type-inverted {
117
- background-color: var(--token-color-palette-neutral-50);
118
- color: var(--token-color-palette-neutral-600);
117
+ background-color: var(--token-color-surface-faint);
118
+ color: var(--token-color-foreground-primary);
119
119
  }
120
120
 
121
121
  &.hds-badge--type-outlined {
122
122
  background-color: transparent;
123
123
  border-color: var(--token-color-palette-neutral-100);
124
- color: var(--token-color-palette-neutral-0);
124
+ color: var(--token-color-foreground-high-contrast);
125
125
  }
126
126
  }
127
127
 
128
128
  @each $color in $hds-badge-colors-accents {
129
129
  .hds-badge--color-#{$color} {
130
130
  &.hds-badge--type-filled {
131
- background-color: var(--token-color-#{$color}-background-faint);
132
- color: var(--token-color-#{$color}-foreground-on-faint);
131
+ background-color: var(--token-color-surface-#{$color});
132
+ color: var(--token-color-foreground-#{$color}-on-surface);
133
133
  }
134
134
 
135
135
  &.hds-badge--type-inverted {
136
- background-color: var(--token-color-#{$color}-background-primary);
137
- color: var(--token-color-palette-neutral-0);
136
+ background-color: var(--token-color-foreground-#{$color});
137
+ color: var(--token-color-foreground-high-contrast);
138
138
  }
139
139
 
140
140
  &.hds-badge--type-outlined {
141
141
  background-color: transparent;
142
142
  border-color: currentColor;
143
- color: var(--token-color-#{$color}-background-primary);
143
+ color: var(--token-color-foreground-#{$color});
144
144
  }
145
145
  }
146
146
  }
@@ -24,7 +24,6 @@ $hds-button-focus-border-width: 3px;
24
24
  justify-content: center;
25
25
  outline-style: solid; // used to avoid double outline+focus-ring in Safari (see https://github.com/hashicorp/design-system-components/issues/161#issuecomment-1031548656)
26
26
  outline-color: transparent; // We need this to be transparent for a11y
27
- max-width: fit-content;
28
27
  position: relative;
29
28
  width: auto;
30
29
 
@@ -38,10 +37,10 @@ $hds-button-focus-border-width: 3px;
38
37
  &:disabled:hover,
39
38
  &[disabled]:hover,
40
39
  &.is-disabled:hover {
41
- background-color: var(--token-color-palette-neutral-50);
42
- border-color: var(--token-color-palette-alpha-200);
40
+ background-color: var(--token-color-surface-faint);
41
+ border-color: var(--token-color-border-primary);
43
42
  box-shadow: none;
44
- color: var(--token-color-palette-neutral-400);
43
+ color: var(--token-color-foreground-disabled);
45
44
  cursor: not-allowed;
46
45
 
47
46
  &::before {
@@ -140,22 +139,22 @@ $size-props: (
140
139
  // Note: the order of the pseuo-selectors need to stay the way they are; it doesn't match the Figma file but it's the correct order for browsers to render the styles correctly.
141
140
 
142
141
  .hds-button--color-primary {
143
- background-color: var(--token-color-action-background-primary);
144
- border-color: var(--token-color-action-border-on-primary);
145
- color: var(--token-color-palette-neutral-0);
142
+ background-color: var(--token-color-palette-blue-200);
143
+ border-color: var(--token-color-palette-blue-300);
144
+ color: var(--token-color-foreground-high-contrast);
146
145
 
147
146
  &:focus,
148
147
  &.is-focus {
149
- background-color: var(--token-color-action-background-primary);
150
- border-color: var(--token-color-action-border-on-primary);
151
- color: var(--token-color-palette-neutral-0);
148
+ background-color: var(--token-color-palette-blue-200);
149
+ border-color: var(--token-color-focus-action-internal);
150
+ color: var(--token-color-foreground-high-contrast);
152
151
  &::before {
153
152
  // the position absolute of an element is computed from the inside of the border of the container
154
153
  // so we have to take in account the border width of the pseudo-element container itself
155
154
  // plus for the primary button we want to have a 2px gap between the button and the focus
156
155
  $shift: $hds-button-border-width + $hds-button-focus-border-width + 2px;
157
156
  border-radius: $hds-button-border-radius + $hds-button-focus-border-width + 2px;
158
- border-color: var(--token-color-action-background-primary);
157
+ border-color: var(--token-color-focus-action-external);
159
158
  bottom: -$shift;
160
159
  left: -$shift;
161
160
  right: -$shift;
@@ -164,17 +163,17 @@ $size-props: (
164
163
  }
165
164
  &:hover,
166
165
  &.is-hover {
167
- background-color: var(--token-color-action-background-hover);
168
- border-color: var(--token-color-action-border-on-hover);
169
- color: var(--token-color-palette-neutral-0);
166
+ background-color: var(--token-color-palette-blue-300);
167
+ border-color: var(--token-color-palette-blue-400);
168
+ color: var(--token-color-foreground-high-contrast);
170
169
  cursor: pointer;
171
170
  }
172
171
  &:active,
173
172
  &.is-active {
174
- background-color: var(--token-color-action-background-active);
175
- border-color: var(--token-color-action-background-active);
173
+ background-color: var(--token-color-palette-blue-400);
174
+ border-color: var(--token-color-palette-blue-400);
176
175
  box-shadow: none;
177
- color: var(--token-color-palette-neutral-0);
176
+ color: var(--token-color-foreground-high-contrast);
178
177
  &::before {
179
178
  border-color: transparent;
180
179
  }
@@ -182,32 +181,32 @@ $size-props: (
182
181
  }
183
182
 
184
183
  .hds-button--color-secondary {
185
- background-color: var(--token-color-palette-neutral-50);
186
- border-color: var(--token-color-palette-alpha-300);
187
- color: var(--token-color-palette-neutral-600);
184
+ background-color: var(--token-color-surface-faint);
185
+ border-color: var(--token-color-border-strong);
186
+ color: var(--token-color-foreground-primary);
188
187
 
189
188
  &:focus,
190
189
  &.is-focus {
191
- background-color: var(--token-color-palette-neutral-50);
192
- border-color: var(--token-color-action-border-on-primary);
193
- color: var(--token-color-palette-neutral-600);
190
+ background-color: var(--token-color-surface-faint);
191
+ border-color: var(--token-color-focus-action-internal);
192
+ color: var(--token-color-foreground-primary);
194
193
  &::before {
195
- border-color: #5990FF;
194
+ border-color: var(--token-color-focus-action-external);
196
195
  }
197
196
  }
198
197
  &:hover,
199
198
  &.is-hover {
200
- background-color: var(--token-color-palette-neutral-0);
201
- border-color: var(--token-color-palette-alpha-300);
202
- color: var(--token-color-palette-neutral-600);
199
+ background-color: var(--token-color-surface-primary);
200
+ border-color: var(--token-color-border-strong);
201
+ color: var(--token-color-foreground-primary);
203
202
  cursor: pointer;
204
203
  }
205
204
  &:active,
206
205
  &.is-active {
207
- background-color: var(--token-color-palette-neutral-200);
208
- border-color: var(--token-color-palette-alpha-300);
206
+ background-color: var(--token-color-surface-interactive-active);
207
+ border-color: var(--token-color-border-strong);
209
208
  box-shadow: none;
210
- color: var(--token-color-palette-neutral-600);
209
+ color: var(--token-color-foreground-primary);
211
210
  &::before {
212
211
  border-color: transparent;
213
212
  }
@@ -215,33 +214,33 @@ $size-props: (
215
214
  }
216
215
 
217
216
  .hds-button--color-destructive {
218
- background-color: var(--token-color-palette-neutral-50);
219
- border-color: var(--token-color-palette-alpha-300);
220
- color: var(--token-color-critical-foreground-on-faint);
217
+ background-color: var(--token-color-background-secondary);
218
+ border-color: var(--token-color-border-strong);
219
+ color: var(--token-color-foreground-critical-on-surface);
221
220
 
222
221
  &:focus,
223
222
  &.is-focus {
224
- background-color: var(--token-color-palette-neutral-50);
225
- border-color: var(--token-color-critical-border-on-primary);
226
- color: var(--token-color-critical-foreground-on-faint);
223
+ background-color: var(--token-color-background-secondary);
224
+ border-color: var(--token-color-focus-critical-internal);
225
+ color: var(--token-color-foreground-critical-on-surface);
227
226
  &::before {
228
- border-color: #DD7578;
227
+ border-color: var(--token-color-focus-critical-external);
229
228
  }
230
229
  }
231
230
  &:hover,
232
231
  &.is-hover {
233
- background-color: var(--token-color-critical-background-hover);
234
- border-color: var(--token-color-critical-border-on-hover);
235
- color: var(--token-color-palette-neutral-0);
232
+ background-color: var(--token-color-palette-red-300);
233
+ border-color: var(--token-color-palette-red-400);
234
+ color: var(--token-color-foreground-high-contrast);
236
235
  cursor: pointer;
237
236
  }
238
237
 
239
238
  &:active,
240
239
  &.is-active {
241
- background-color: var(--token-color-critical-background-active);
242
- border-color: var(--token-color-critical-background-active);
240
+ background-color: var(--token-color-palette-red-400);
241
+ border-color: var(--token-color-palette-red-400);
243
242
  box-shadow: none;
244
- color: var(--token-color-palette-neutral-0);
243
+ color: var(--token-color-foreground-high-contrast);
245
244
  &::before {
246
245
  border-color: transparent;
247
246
  }
@@ -20,11 +20,11 @@ $hds-card-container-border-radius: 6px;
20
20
  // BACKGROUND
21
21
 
22
22
  .hds-card__container--background-neutral-primary {
23
- background-color: var(--token-color-neutral-background-primary);
23
+ background-color: var(--token-color-surface-primary);
24
24
  }
25
25
 
26
26
  .hds-card__container--background-neutral-secondary {
27
- background-color: var(--token-color-neutral-background-secondary);
27
+ background-color: var(--token-color-surface-faint);
28
28
  }
29
29
 
30
30
 
@@ -0,0 +1,10 @@
1
+ //
2
+ // DISCLOSURE COMPONENT
3
+ //
4
+ // properties within each class are sorted alphabetically
5
+ //
6
+
7
+ .hds-disclosure {
8
+ position: relative;
9
+ width: fit-content;
10
+ }
@@ -29,8 +29,8 @@
29
29
  }
30
30
 
31
31
  .hds-icon-tile__extra {
32
- background-color: var(--token-color-neutral-background-primary);
33
- border: 1px solid var(--token-color-palette-alpha-200);
32
+ background-color: var(--token-color-surface-primary);
33
+ border: 1px solid var(--token-color-border-primary);
34
34
  bottom: -6px;
35
35
  box-shadow: $hds-icon-tile-box-shadow;
36
36
  box-sizing: content-box; // the border is outside
@@ -42,7 +42,7 @@
42
42
  .hds-icon-tile__extra-icon {
43
43
  display: flex;
44
44
  margin: auto;
45
- color: var(--token-color-neutral-foreground-primary);
45
+ color: var(--token-color-foreground-strong);
46
46
  }
47
47
 
48
48
  // SIZE
@@ -112,8 +112,8 @@ $size-props: (
112
112
 
113
113
  .hds-icon-tile--logo {
114
114
  // notice: we are using colored icons so we don't need to set the "color" property here
115
- background-color: var(--token-color-neutral-background-primary);
116
- border-color: var(--token-color-neutral-border-primary);
115
+ background-color: var(--token-color-surface-primary);
116
+ border-color: var(--token-color-border-primary);
117
117
  }
118
118
 
119
119
  // ICON - COLOR
@@ -121,18 +121,17 @@ $size-props: (
121
121
  .hds-icon-tile--icon {
122
122
 
123
123
  &.hds-icon-tile--color-neutral {
124
- background-color: var(--token-color-neutral-background-secondary);
125
- border-color: var(--token-color-neutral-border-primary);
126
- color: var(--token-color-neutral-foreground-faint);
124
+ background-color: var(--token-color-surface-faint);
125
+ border-color: var(--token-color-border-primary);
126
+ color: var(--token-color-foreground-faint);
127
127
  }
128
128
 
129
129
  @each $product in $hds-icon-tile-colors-products {
130
130
  @if ($product == 'hcp') {
131
131
  // exception for HCP (we use neutral colors, we don't have specific product colors for foreground/background)
132
- // notice: at the moment we don't have a token for that, that's why we're using an hex value
133
132
  &.hds-icon-tile--color-hcp {
134
- background-color: var(--token-color-neutral-background-secondary);
135
- border-color: var(--token-color-neutral-border-primary);
133
+ background-color: var(--token-color-surface-faint);
134
+ border-color: var(--token-color-border-primary);
136
135
  color: var(--token-color-palette-#{$product}-brand);
137
136
  }
138
137
  } @else {
@@ -7,7 +7,7 @@
7
7
  //
8
8
  //
9
9
 
10
- @use '../../mixins/generic-focus-state.scss' as *;
10
+ @use "../../mixins/focus-ring" as *;
11
11
 
12
12
  $hds-link-standalone-sizes: ( 'small', 'medium', 'large' );
13
13
 
@@ -20,44 +20,10 @@ $hds-link-standalone-border-width: 1px;
20
20
  border: $hds-link-standalone-border-width solid transparent; // needs to exist AND be transparent for a11y
21
21
  display: flex;
22
22
  font-family: var(--token-typography-font-stack-text);
23
- isolation: isolate; // used to create a new stacking context (needed to have the pseudo element below text/icon but not the parent container)
24
23
  justify-content: center;
25
- outline-style: solid; // used to avoid double outline+focus-ring in Safari (see https://github.com/hashicorp/design-system-components/issues/161#issuecomment-1031548656)
26
- outline-color: transparent;
27
- position: relative;
28
24
  // notice: the text decoration is applied directly to the "text" container because of a bug in Safari (see https://github.com/hashicorp/design-system-components/issues/159)
29
25
  text-decoration-color: transparent;
30
26
  width: fit-content;
31
-
32
- // this is how much the focus is visually "shifted" from the bounding box of the
33
- // notice: you have to take in account also the inset shadow of the focus (see Figma file and also "generic-focus-state" mixin)
34
- $hds-link-standalone-focus-shift: 4px;
35
- // the position absolute of an element is computed from the inside of the border of the container
36
- // so we have to take in account the border width of the pseudo-element container itself
37
- $shift: $hds-link-standalone-focus-shift + $hds-link-standalone-border-width;
38
- // for visual/optical balance we add an extra 2px to the "shift" near the text (opposite the icon)
39
- $shift-extra: $shift + 2px;
40
-
41
- // this is used not only for the focus, but also to increase the clickable area
42
- &::before {
43
- border-radius: $hds-link-standalone-focus-border-radius;
44
- bottom: -$shift;
45
- box-sizing: border-box;
46
- content: '';
47
- left: -$shift;
48
- position: absolute;
49
- right: -$shift;
50
- top: -$shift;
51
- z-index: -1;
52
- }
53
-
54
- &.hds-link-standalone--icon-position-leading::before {
55
- right: -$shift-extra;
56
- }
57
-
58
- &.hds-link-standalone--icon-position-trailing::before {
59
- left: -$shift-extra;
60
- }
61
27
  }
62
28
 
63
29
  .hds-link-standalone__text {
@@ -75,7 +41,6 @@ $hds-link-standalone-border-width: 1px;
75
41
  }
76
42
  }
77
43
 
78
-
79
44
  // SIZE
80
45
 
81
46
  // these values later may come from the design tokens
@@ -115,46 +80,13 @@ $size-props: (
115
80
  // COLORS & STATES
116
81
  // The "primary" and "secondary" variants share a lot of styles for the interactive states
117
82
  // Note: the order of the pseuo-selectors need to stay the way they are
118
- //
119
- // For an explanation of the ":focus/:focus-visible" states see:
120
- // - https://github.com/hashicorp/design-system-components/issues/161
121
- // - https://www.tpgi.com/focus-visible-and-backwards-compatibility/
122
-
123
- .hds-link-standalone {
124
- // default focus for browsers that still rely on ":focus"
125
- &:focus,
126
- &.is-focus {
127
- &::before {
128
- @include hds-generic-focus-state();
129
- }
130
- }
131
- // undo the previous declaration for browsers that support ":focus-visible" but wouldn't normally show default focus styles
132
- &:focus:not(:focus-visible) {
133
- &::before {
134
- @include hds-remove-focus-state();
135
- }
136
- }
137
- // set focus for browsers that support ":focus-visible"
138
- &:focus-visible {
139
- &::before {
140
- @include hds-generic-focus-state();
141
- }
142
- }
143
- // remove the focus ring on "active + focused" state (by design)
144
- &:focus:active,
145
- &.is-focus.is-active {
146
- &::before {
147
- @include hds-remove-focus-state();
148
- }
149
- }
150
- }
151
83
 
152
84
  .hds-link-standalone--color-primary {
153
- color: var(--token-color-action-foreground-primary);
85
+ color: var(--token-color-foreground-action);
154
86
 
155
87
  &:hover,
156
88
  &.is-hover {
157
- color: var(--token-color-action-background-hover);
89
+ color: var(--token-color-foreground-action-hover);
158
90
 
159
91
  .hds-link-standalone__text {
160
92
  text-decoration-color: #4E81E8; // custom color by design
@@ -163,7 +95,7 @@ $size-props: (
163
95
 
164
96
  &:active,
165
97
  &.is-active {
166
- color: var(--token-color-action-background-active);
98
+ color: var(--token-color-foreground-action-active);
167
99
 
168
100
  .hds-link-standalone__text {
169
101
  text-decoration-color: #396ED6; // custom color by design
@@ -176,7 +108,7 @@ $size-props: (
176
108
  }
177
109
 
178
110
  .hds-link-standalone--color-secondary {
179
- color: var(--token-color-neutral-foreground-primary);
111
+ color: var(--token-color-foreground-primary);
180
112
 
181
113
  &:hover,
182
114
  &.is-hover {
@@ -187,14 +119,38 @@ $size-props: (
187
119
 
188
120
  &:active,
189
121
  &.is-active {
190
- color: var(--token-color-neutral-foreground-secondary);
122
+ color: var(--token-color-foreground-primary);
191
123
 
192
124
  .hds-link-standalone__text {
193
125
  text-decoration-color: #6E7075; // custom color by design
194
126
  }
195
127
 
196
128
  &::before {
197
- background-color: var(--token-color-palette-neutral-200);
129
+ background-color: var(--token-color-surface-interactive-active);
198
130
  }
199
131
  }
132
+ }
133
+
134
+ // this is how much the focus is visually "shifted" from the bounding box of the
135
+ // notice: you have to take in account also the inset shadow of the focus (see Figma file and also "focus-ring" mixin)
136
+ $hds-link-standalone-focus-shift: 4px;
137
+
138
+ .hds-link-standalone {
139
+ // the position absolute of an element is computed from the inside of the border of the container
140
+ // so we have to take in account the border width of the pseudo-element container itself
141
+ $shift: $hds-link-standalone-focus-shift + $hds-link-standalone-border-width;
142
+ // for visual/optical balance we add an extra 2px to the "shift" near the text (opposite the icon)
143
+ $shift-extra: $shift + 2px;
144
+
145
+ // notice: this is used not only for the focus, but also to increase the clickable area
146
+ @include hds-focus-ring-with-pseudo-element($top: -$shift, $right: -$shift, $bottom: -$shift, $left: -$shift, $radius: $hds-link-standalone-focus-border-radius);
147
+
148
+ // we need to override a couple of values for better visual alignment
149
+ &.hds-link-standalone--icon-position-leading::before {
150
+ right: -$shift-extra;
151
+ }
152
+
153
+ &.hds-link-standalone--icon-position-trailing::before {
154
+ left: -$shift-extra;
155
+ }
200
156
  }
@@ -0,0 +1,73 @@
1
+ // For an explanation of the ":focus/:focus-visible" states see:
2
+ // - https://github.com/hashicorp/design-system-components/issues/161
3
+ // - https://www.tpgi.com/focus-visible-and-backwards-compatibility/
4
+
5
+ @mixin hds-focus-ring-basic() {
6
+ outline-style: solid; // used to avoid double outline+focus-ring in Safari (see https://github.com/hashicorp/design-system-components/issues/161#issuecomment-1031548656)
7
+ outline-color: transparent;
8
+
9
+ // default focus for browsers that still rely on ":focus"
10
+ &:focus,
11
+ &.is-focus {
12
+ box-shadow: var(--token-focus-ring-box-shadow);
13
+ }
14
+ // undo the previous declaration for browsers that support ":focus-visible" but wouldn't normally show default focus styles
15
+ &:focus:not(:focus-visible) {
16
+ box-shadow: none;
17
+ }
18
+ // set focus for browsers that support ":focus-visible"
19
+ &:focus-visible {
20
+ box-shadow: var(--token-focus-ring-box-shadow);
21
+ }
22
+ // remove the focus ring on "active + focused" state (by design)
23
+ &:focus:active,
24
+ &.is-focus.is-active {
25
+ box-shadow: none;
26
+ }
27
+ }
28
+
29
+ @mixin hds-focus-ring-with-pseudo-element($top: 0, $right: 0, $bottom: 0, $left: 0, $radius: 5px) {
30
+ isolation: isolate; // used to create a new stacking context (needed to have the pseudo element below text/icon but not the parent container)
31
+ outline-style: solid; // used to avoid double outline+focus-ring in Safari (see https://github.com/hashicorp/design-system-components/issues/161#issuecomment-1031548656)
32
+ outline-color: transparent;
33
+ position: relative;
34
+
35
+ &::before {
36
+ border-radius: $radius;
37
+ bottom: $bottom;
38
+ box-sizing: border-box;
39
+ content: '';
40
+ left: $left;
41
+ position: absolute;
42
+ right: $right;
43
+ top: $top;
44
+ z-index: -1;
45
+ }
46
+
47
+ // default focus for browsers that still rely on ":focus"
48
+ &:focus,
49
+ &.is-focus {
50
+ &::before {
51
+ box-shadow: var(--token-focus-ring-box-shadow);
52
+ }
53
+ }
54
+ // undo the previous declaration for browsers that support ":focus-visible" but wouldn't normally show default focus styles
55
+ &:focus:not(:focus-visible) {
56
+ &::before {
57
+ box-shadow: none;
58
+ }
59
+ }
60
+ // set focus for browsers that support ":focus-visible"
61
+ &:focus-visible {
62
+ &::before {
63
+ box-shadow: var(--token-focus-ring-box-shadow);
64
+ }
65
+ }
66
+ // remove the focus ring on "active + focused" state (by design)
67
+ &:focus:active,
68
+ &.is-focus.is-active {
69
+ &::before {
70
+ box-shadow: none;
71
+ }
72
+ }
73
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hashicorp/design-system-components",
3
- "version": "0.0.20",
3
+ "version": "0.1.0",
4
4
  "description": "HashiCorp Design System Components",
5
5
  "keywords": [
6
6
  "hashicorp",
@@ -61,11 +61,14 @@
61
61
  "prepare": "husky install"
62
62
  },
63
63
  "dependencies": {
64
- "@hashicorp/design-system-tokens": "^0.4.7",
64
+ "@hashicorp/design-system-tokens": "^0.5.0",
65
65
  "@hashicorp/ember-flight-icons": "^2.0.1",
66
+ "ember-auto-import": "^2.2.3",
66
67
  "ember-cli-babel": "^7.26.6",
67
68
  "ember-cli-htmlbars": "^5.7.1",
68
69
  "ember-cli-sass": "^10.0.1",
70
+ "ember-focus-trap": "^1.0.1",
71
+ "ember-named-blocks-polyfill": "^0.2.5",
69
72
  "sass": "^1.43.4"
70
73
  },
71
74
  "devDependencies": {
@@ -79,7 +82,6 @@
79
82
  "babel-eslint": "^10.1.0",
80
83
  "broccoli-asset-rev": "^3.0.0",
81
84
  "ember-a11y-refocus": "^2.1.0",
82
- "ember-auto-import": "^2.2.3",
83
85
  "ember-cli": "~3.28.4",
84
86
  "ember-cli-clipboard": "^0.15.0",
85
87
  "ember-cli-dependency-checker": "^3.2.0",
@@ -1,7 +0,0 @@
1
- @mixin hds-generic-focus-state() {
2
- box-shadow: var(--token-focus-ring-box-shadow);
3
- }
4
-
5
- @mixin hds-remove-focus-state() {
6
- box-shadow: none;
7
- }