Skip to content

Commit 3460850

Browse files
committed
ntp: new show/hide buttons
1 parent 129d82f commit 3460850

35 files changed

+880
-505
lines changed

special-pages/pages/new-tab/app/activity/activity.utils.js

Lines changed: 0 additions & 30 deletions
This file was deleted.

special-pages/pages/new-tab/app/activity/components/Activity.module.css

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,7 @@
229229
display: flex;
230230
align-items: center;
231231
width: 100%;
232+
height: 16px;
232233
+ .historyItem {
233234
margin-top: 5px;
234235
}
@@ -238,7 +239,6 @@
238239
font-weight: var(--small-label-font-weight);
239240
line-height: var(--small-label-line-height);
240241
color: var(--ntp-text-normal);
241-
height: 16px;
242242
text-decoration: none;
243243
min-width: 0;
244244
white-space: nowrap;

special-pages/pages/new-tab/app/activity/mocks/activity.mocks.js

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -160,15 +160,3 @@ export const activityMocks = {
160160
],
161161
},
162162
};
163-
164-
/**
165-
* @param {ActivityData} data
166-
* @return {import('../batched-activity.service.js').Incoming}
167-
*/
168-
export function intoServiceData(data) {
169-
return {
170-
activity: data.activity,
171-
urls: data.activity.map((x) => x.url),
172-
totalTrackers: data.activity.reduce((acc, item) => acc + item.trackingStatus.totalCount, 0),
173-
};
174-
}

special-pages/pages/new-tab/app/components/Icons.js

Lines changed: 3 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,28 +1,14 @@
11
import { h } from 'preact';
22
import styles from './Icons.module.css';
33

4-
export function ChevronButton() {
5-
return (
6-
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" class={styles.chevronButton}>
7-
<rect fill="black" fill-opacity="0.06" width="24" height="24" rx="12" class={styles.chevronCircle} />
8-
<path
9-
fill="black"
10-
fill-opacity="0.6"
11-
class={styles.chevronArrow}
12-
d="M6.90039 10.191C6.91514 9.99804 7.00489 9.81855 7.15039 9.69098C7.2879 9.56799 7.46591 9.5 7.65039 9.5C7.83487 9.5 8.01289 9.56799 8.15039 9.69098L12.1504 13.691L16.1504 9.69098C16.2903 9.62414 16.4476 9.60233 16.6004 9.62856C16.7533 9.65479 16.8943 9.72776 17.0039 9.83743C17.1136 9.9471 17.1866 10.0881 17.2128 10.2409C17.239 10.3938 17.2172 10.551 17.1504 10.691L12.6504 15.191C12.5098 15.3314 12.3191 15.4103 12.1204 15.4103C11.9216 15.4103 11.731 15.3314 11.5904 15.191L7.15039 10.691C7.00489 10.5634 6.91514 10.3839 6.90039 10.191Z"
13-
/>
14-
</svg>
15-
);
16-
}
17-
184
export function Chevron() {
195
return (
20-
<svg fill="none" width="16" height="16" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
6+
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
217
<path
22-
fill="currentColor"
238
fill-rule="evenodd"
24-
d="M3.293 7.793a1 1 0 0 0 0 1.414l8 8a1 1 0 0 0 1.414 0l8-8a1 1 0 0 0-1.414-1.414L12 15.086 4.707 7.793a1 1 0 0 0-1.414 0Z"
259
clip-rule="evenodd"
10+
d="M12.0694 9.48822C11.7999 9.80271 11.3264 9.83913 11.0119 9.56956L7.99999 6.98793L4.98808 9.56956C4.67359 9.83913 4.20011 9.80271 3.93054 9.48822C3.66098 9.17372 3.6974 8.70025 4.01189 8.43068L7.51189 5.43068C7.79276 5.18994 8.20721 5.18994 8.48808 5.43068L11.9881 8.43068C12.3026 8.70025 12.339 9.17372 12.0694 9.48822Z"
11+
fill="currentColor"
2612
/>
2713
</svg>
2814
);
Lines changed: 91 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,4 @@
11
.button {
2-
opacity: 0;
3-
transition: opacity 0.3s;
42
cursor: pointer;
53
background: none;
64
border: none;
@@ -9,108 +7,123 @@
97
justify-content: center;
108
align-items: center;
119
color: var(--ntp-text-normal);
12-
height: var(--ntp-gap);
13-
width: 100%;
14-
border-radius: var(--border-radius-sm);
15-
16-
&.round {
17-
height: 2rem;
18-
width: 2rem;
19-
border-radius: 50%;
20-
padding-inline: 0;
21-
background-color: transparent;
22-
color: var(--ntp-text-muted);
23-
2410

25-
.iconBlock {
26-
backdrop-filter: unset;
27-
background-color: transparent;
28-
box-shadow: none;
29-
transition: all 0.3s ease-in;
11+
> * {
12+
pointer-events: none;
13+
}
3014

31-
[data-theme=dark] & {
32-
box-shadow: none;
33-
background-color: transparent;
34-
}
35-
}
15+
svg {
16+
transition: transform .3s;
17+
}
3618

37-
&:hover {
38-
.iconBlock {
39-
background-color: var(--color-black-at-6);
19+
&[aria-pressed=false] svg {
20+
transform: rotate(-180deg);
21+
}
4022

41-
[data-theme=dark] & {
42-
background-color: var(--color-white-at-12);
43-
}
44-
}
45-
}
23+
&:focus-visible {
24+
box-shadow: var(--focus-ring-thin);
25+
}
26+
}
27+
28+
.iconBlock {
29+
backdrop-filter: blur(48px);
30+
background-color: var(--ntp-surface-background-color);
31+
border-radius: 50%;
32+
height: 1.5rem;
33+
width: 1.5rem;
34+
display: flex;
35+
align-items: center;
36+
justify-content: center;
37+
box-shadow: 0px 2px 4px 0px var(--color-black-at-12), 0px 0px 3px 0px var(--color-black-at-18);
38+
color: var(--ntp-text-muted);
4639

47-
&:focus-visible {
48-
box-shadow: var(--focus-ring);
49-
}
40+
[data-theme="dark"] & {
41+
box-shadow: 0px 2px 4px 0px var(--color-white-at-6), 0px 0px 3px 0px var(--color-white-at-9);
5042
}
43+
}
5144

52-
&.withText {
53-
border: 1px solid var(--color-black-at-9);
45+
.round {
46+
height: 2rem;
47+
width: 2rem;
48+
border-radius: 50%;
49+
padding-inline: 0;
50+
background-color: transparent;
51+
color: var(--ntp-text-muted);
5452

55-
svg {
56-
margin-right: var(--sp-2);
57-
}
53+
.iconBlock {
54+
backdrop-filter: unset;
55+
background-color: transparent;
56+
box-shadow: none;
57+
transition: all 0.3s ease-in;
5858

59-
&:hover {
60-
background-color: var(--color-black-at-9);
59+
[data-theme=dark] & {
60+
box-shadow: none;
61+
background-color: transparent;
6162
}
63+
}
6264

63-
&:active {
64-
background-color: var(--color-black-at-12);
65+
&:hover {
66+
.iconBlock {
67+
background-color: var(--color-black-at-6);
68+
69+
[data-theme=dark] & {
70+
background-color: var(--color-white-at-12);
71+
}
6572
}
6673
}
6774

68-
>* {
69-
pointer-events: none;
75+
&:focus-visible {
76+
box-shadow: var(--focus-ring);
7077
}
78+
}
79+
80+
.pill {
81+
height: calc(26 * var(--px-in-rem));
82+
border-radius: 9999px;
83+
padding-left: 8px;
84+
padding-right: 11px;
85+
font-size: var(--callout-font-size);
86+
font-weight: var(--callout-font-weight);
87+
line-height: var(--callout-line-height);
88+
border: 1px solid var(--ntp-surface-border-color);
89+
backdrop-filter: blur(48px);
90+
background-color: var(--ntp-surface-background-color);
91+
color: var(--ntp-text-muted);
92+
}
93+
94+
.hover {
95+
transition: background-color .2s;
7196

7297
svg {
73-
transition: transform .3s;
74-
}
75-
76-
.iconBlock {
77-
backdrop-filter: blur(48px);
78-
background-color: var(--ntp-surface-background-color);
79-
border-radius: 50%;
80-
height: 1.5rem;
81-
width: 1.5rem;
82-
display: flex;
83-
align-items: center;
84-
justify-content: center;
85-
box-shadow: 0px 2px 4px 0px var(--color-black-at-12), 0px 0px 3px 0px var(--color-black-at-18);
86-
color: var(--ntp-text-muted);
87-
88-
89-
[data-theme="dark"] & {
90-
box-shadow: 0px 2px 4px 0px var(--color-white-at-6), 0px 0px 3px 0px var(--color-white-at-9);
91-
}
98+
margin-right: calc(6 * var(--px-in-rem));
9299
}
93100

94-
&[aria-pressed=true] svg {
95-
transform: rotate(-180deg);
101+
&:hover {
102+
background-color: var(--color-black-at-6);
96103
}
97104

98-
&:focus-visible {
99-
opacity: 1;
100-
box-shadow: var(--focus-ring-thin);
105+
&:active {
106+
background-color: var(--color-black-at-12);
101107
}
102108

103109
[data-theme=dark] & {
104-
&.withText {
105-
border-color: var(--color-white-at-9);
110+
border-color: var(--color-white-at-9);
106111

107-
&:hover {
108-
background-color: var(--color-white-at-9);
109-
}
112+
&:hover {
113+
border-color: var(--color-white-at-18);
114+
background-color: var(--color-white-at-6);
115+
}
110116

111-
&:active {
112-
background-color: var(--color-white-at-12);
113-
}
117+
&:active {
118+
background-color: var(--color-white-at-12);
114119
}
115120
}
121+
}
122+
123+
.bar {
124+
padding-top: 11px;
125+
padding-bottom: 11px;
126+
display: flex;
127+
justify-content: center;
128+
font-size: 12px;
116129
}
Lines changed: 41 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,62 @@
11
import styles from './ShowHide.module.css';
22
import cn from 'classnames';
33
import { Chevron } from './Icons.js';
4-
import { Fragment, h } from 'preact';
4+
import { h } from 'preact';
55

66
/**
77
* Function to handle showing or hiding content based on certain conditions.
88
*
99
* @param {Object} props - Input parameters for controlling the behavior of the ShowHide functionality.
10+
* @param {string} props.label
11+
* @param {() => void} props.onClick
12+
* @param {import("preact").ComponentProps<'button'>} [props.buttonAttrs]
13+
*/
14+
export function ShowHideButtonCircle({ label, onClick, buttonAttrs = {} }) {
15+
return (
16+
<button {...buttonAttrs} class={cn(styles.button, styles.round)} aria-label={label} data-toggle="true" onClick={onClick}>
17+
<div class={styles.iconBlock}>
18+
<Chevron />
19+
</div>
20+
</button>
21+
);
22+
}
23+
24+
/**
25+
* Use this version for a small pill version with text and option aria-label
26+
* @param {object} props
1027
* @param {string} props.text
28+
* @param {string|undefined} props.label
1129
* @param {() => void} props.onClick
12-
* @param {'none'|'round'} [props.shape] - when "none", is a full width btn w/ icon inside (used for below Favorites and NextSteps), Round is the PrivacyStats heading button
13-
* @param {boolean} [props.showText] - btn w/ icon and text (used to expand PrivacyStats list), should be used with shape="none"
1430
* @param {import("preact").ComponentProps<'button'>} [props.buttonAttrs]
1531
*/
16-
export function ShowHideButton({ text, onClick, buttonAttrs = {}, shape = 'none', showText = false }) {
32+
export function ShowHideButtonPill({ label, onClick, text, buttonAttrs = {} }) {
33+
// if a different label was given, make the main text aria-hidden=true
34+
const btnText = label ? <span aria-hidden="true">{text}</span> : text;
35+
1736
return (
1837
<button
1938
{...buttonAttrs}
20-
class={cn(styles.button, shape === 'round' && styles.round, !!showText && styles.withText)}
21-
aria-label={text}
39+
aria-label={label}
40+
class={cn(styles.button, styles.hover, styles.pill)}
2241
data-toggle="true"
2342
onClick={onClick}
2443
>
25-
{showText ? (
26-
<Fragment>
27-
<Chevron />
28-
{text}
29-
</Fragment>
30-
) : (
31-
<div class={styles.iconBlock}>
32-
<Chevron />
33-
</div>
34-
)}
44+
<Chevron />
45+
{btnText}
3546
</button>
3647
);
3748
}
49+
50+
/**
51+
* A container you can place a <ShowHideButtonPill /> into.
52+
* Consumers can use the `data-show-hide` to show/hide the bar
53+
* @param {object} props
54+
* @param {import("preact").ComponentChild} props.children
55+
*/
56+
export function ShowHideBar({ children }) {
57+
return (
58+
<div class={styles.bar} data-show-hide>
59+
{children}
60+
</div>
61+
);
62+
}

special-pages/pages/new-tab/app/customizer/components/CustomizerMenu.js

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -179,17 +179,6 @@ function useDropdown() {
179179
return { dropdownRef, buttonRef, isOpen, setIsOpen };
180180
}
181181

182-
export class VisibilityRowState {
183-
checked;
184-
/**
185-
* @param {object} params
186-
* @param {boolean} params.checked - whether this item should appear 'checked'
187-
*/
188-
constructor({ checked }) {
189-
this.checked = checked;
190-
}
191-
}
192-
193182
export class VisibilityRowData {
194183
/**
195184
* @param {object} params

0 commit comments

Comments
 (0)