Skip to content

Commit 8465680

Browse files
Add tooltip to icon button to display label
1 parent 420b267 commit 8465680

File tree

3 files changed

+27
-13
lines changed

3 files changed

+27
-13
lines changed

libs/components/src/icon-button/icon-button.component.ts

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import { NgClass } from "@angular/common";
22
import {
3+
ChangeDetectorRef,
34
Component,
45
computed,
56
effect,
@@ -17,6 +18,7 @@ import { setA11yTitleAndAriaLabel } from "../a11y/set-a11y-title-and-aria-label"
1718
import { ButtonLikeAbstraction } from "../shared/button-like.abstraction";
1819
import { FocusableElement } from "../shared/focusable-element";
1920
import { SpinnerComponent } from "../spinner";
21+
import { TooltipDirective } from "../tooltip";
2022
import { ariaDisableElement } from "../utils";
2123

2224
export type IconButtonType = "primary" | "danger" | "contrast" | "main" | "muted" | "nav-contrast";
@@ -98,7 +100,10 @@ const sizes: Record<IconButtonSize, string[]> = {
98100
*/
99101
"[attr.bitIconButton]": "icon()",
100102
},
101-
hostDirectives: [AriaDisableDirective],
103+
hostDirectives: [
104+
AriaDisableDirective,
105+
{ directive: TooltipDirective, inputs: ["tooltipPosition"] },
106+
],
102107
})
103108
export class BitIconButtonComponent implements ButtonLikeAbstraction, FocusableElement {
104109
readonly icon = model.required<string>({ alias: "bitIconButton" });
@@ -107,6 +112,10 @@ export class BitIconButtonComponent implements ButtonLikeAbstraction, FocusableE
107112

108113
readonly size = model<IconButtonSize>("default");
109114

115+
private readonly cdr = inject(ChangeDetectorRef);
116+
private elementRef = inject(ElementRef);
117+
private tooltip = inject(TooltipDirective, { host: true, optional: true });
118+
110119
/**
111120
* label input will be used to set the `aria-label` attributes on the button.
112121
* This is for accessibility purposes, as it provides a text alternative for the icon button.
@@ -184,8 +193,6 @@ export class BitIconButtonComponent implements ButtonLikeAbstraction, FocusableE
184193
return this.elementRef.nativeElement;
185194
}
186195

187-
private elementRef = inject(ElementRef);
188-
189196
constructor() {
190197
const element = this.elementRef.nativeElement;
191198

@@ -196,9 +203,11 @@ export class BitIconButtonComponent implements ButtonLikeAbstraction, FocusableE
196203
effect(() => {
197204
setA11yTitleAndAriaLabel({
198205
element: this.elementRef.nativeElement,
199-
title: originalTitle ?? this.label(),
206+
title: null,
200207
label: this.label(),
201208
});
209+
210+
this.tooltip?.setContent(originalTitle || this.label());
202211
});
203212
}
204213
}

libs/components/src/tooltip/tooltip.directive.ts

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,13 +32,14 @@ export class TooltipDirective implements OnInit {
3232
/**
3333
* The value of this input is forwarded to the tooltip.component to render
3434
*/
35-
readonly bitTooltip = input.required<string>();
35+
readonly bitTooltip = input<string>();
3636
/**
3737
* The value of this input is forwarded to the tooltip.component to set its position explicitly.
3838
* @default "above-center"
3939
*/
4040
readonly tooltipPosition = input<TooltipPositionIdentifier>("above-center");
4141

42+
private _bitTooltip = signal("");
4243
private isVisible = signal(false);
4344
private overlayRef: OverlayRef | undefined;
4445
private elementRef = inject(ElementRef);
@@ -59,7 +60,7 @@ export class TooltipDirective implements OnInit {
5960
{
6061
provide: TOOLTIP_DATA,
6162
useValue: {
62-
content: this.bitTooltip,
63+
content: this._bitTooltip,
6364
isVisible: this.isVisible,
6465
tooltipPosition: this.tooltipPosition,
6566
},
@@ -89,6 +90,10 @@ export class TooltipDirective implements OnInit {
8990
};
9091
}
9192

93+
setContent(text: string) {
94+
this._bitTooltip.set(text);
95+
}
96+
9297
ngOnInit() {
9398
this.positionStrategy.withPositions(this.computePositions(this.tooltipPosition()));
9499

libs/components/src/tooltip/tooltip.stories.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,6 @@ type Story = StoryObj<TooltipDirective>;
7272

7373
export const Default: Story = {
7474
args: {
75-
bitTooltip: "This is a tooltip",
7675
tooltipPosition: "above-center",
7776
},
7877
render: (args) => ({
@@ -81,6 +80,7 @@ export const Default: Story = {
8180
<div class="tw-p-4">
8281
<button
8382
bitIconButton="bwi-ellipsis-v"
83+
label="This is a tooltip"
8484
${formatArgsForCodeSnippet<TooltipDirective>(args)}
8585
>
8686
Button label here
@@ -102,22 +102,22 @@ export const AllPositions: Story = {
102102
<div class="tw-p-16 tw-grid tw-grid-cols-2 tw-gap-8 tw-place-items-center">
103103
<button
104104
bitIconButton="bwi-angle-up"
105-
bitTooltip="Top tooltip"
105+
label="Top tooltip"
106106
tooltipPosition="above-center"
107107
></button>
108108
<button
109109
bitIconButton="bwi-angle-right"
110-
bitTooltip="Right tooltip"
110+
label="Right tooltip"
111111
tooltipPosition="right-center"
112112
></button>
113113
<button
114114
bitIconButton="bwi-angle-left"
115-
bitTooltip="Left tooltip"
115+
label="Left tooltip"
116116
tooltipPosition="left-center"
117117
></button>
118118
<button
119119
bitIconButton="bwi-angle-down"
120-
bitTooltip="Bottom tooltip"
120+
label="Bottom tooltip"
121121
tooltipPosition="below-center"
122122
></button>
123123
</div>
@@ -131,7 +131,7 @@ export const LongContent: Story = {
131131
<div class="tw-p-16 tw-flex tw-items-center tw-justify-center">
132132
<button
133133
bitIconButton="bwi-ellipsis-v"
134-
bitTooltip="This is a very long tooltip that will wrap to multiple lines to demonstrate how the tooltip handles long content. This is not recommended for usability."
134+
label="This is a very long tooltip that will wrap to multiple lines to demonstrate how the tooltip handles long content. This is not recommended for usability."
135135
></button>
136136
</div>
137137
`,
@@ -144,7 +144,7 @@ export const OnDisabledButton: Story = {
144144
<div class="tw-p-16 tw-flex tw-items-center tw-justify-center">
145145
<button
146146
bitIconButton="bwi-ellipsis-v"
147-
bitTooltip="Tooltip on disabled button"
147+
label="Tooltip on disabled button"
148148
[disabled]="true"
149149
></button>
150150
</div>

0 commit comments

Comments
 (0)