Skip to content
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
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { Dictionary } from './../../../utilities/types/types';
import { TelemetryProviderConfig, UserTelemetryProvider, UserTraits } from '../../telemetry';
import { Dictionary } from './../../../utilities/types/types';
import { loadGA } from './load-snippet';

export class GoogleAnalyticsTelemetry<InitConfig extends TelemetryProviderConfig>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { createDirectiveFactory, SpectatorDirective } from '@ngneat/spectator/jest';
import { SelectOptionRendererDirective } from './select-option-renderer.directive';

describe('Select Option Renderer directive', () => {
let spectator: SpectatorDirective<SelectOptionRendererDirective>;

const createDirective = createDirectiveFactory<SelectOptionRendererDirective>({
directive: SelectOptionRendererDirective
});

beforeEach(() => {
spectator = createDirective(`
<div class="content" *htSelectOptionRenderer>content</div>
`);
});

test('should render content', () => {
const content = spectator.directive.getTemplateRef();
expect(content).toExist();
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { Directive, TemplateRef } from '@angular/core';

@Directive({
selector: '[htSelectOptionRenderer]'
})
export class SelectOptionRendererDirective {
public constructor(private readonly templateRef: TemplateRef<unknown>) {}

public getTemplateRef(): TemplateRef<unknown> {
return this.templateRef;
}
}
8 changes: 6 additions & 2 deletions projects/components/src/select/select-option.component.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
import { ChangeDetectionStrategy, Component, Input, OnChanges } from '@angular/core';
import { ChangeDetectionStrategy, Component, ContentChild, Input, OnChanges } from '@angular/core';
import { IconType } from '@hypertrace/assets-library';
import { Observable, Subject } from 'rxjs';
import { IconBorder } from '../icon/icon-border';
import { SelectOptionRendererDirective } from './directive/select-option-renderer.directive';
import { SelectOption } from './select-option';

@Component({
selector: 'ht-select-option',
changeDetection: ChangeDetectionStrategy.OnPush,
template: '' // No template, just gathering data
template: ``
})
export class SelectOptionComponent<V> implements OnChanges, SelectOption<V> {
@Input()
Expand Down Expand Up @@ -40,6 +41,9 @@ export class SelectOptionComponent<V> implements OnChanges, SelectOption<V> {
@Input()
public disabled?: boolean;

@ContentChild(SelectOptionRendererDirective)
public selectOptionRenderer?: SelectOptionRendererDirective;

private readonly optionChangeSubject$: Subject<V> = new Subject<V>();
public readonly optionChange$: Observable<V> = this.optionChangeSubject$.asObservable();

Expand Down
2 changes: 1 addition & 1 deletion projects/components/src/select/select-option.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
export interface SelectOption<V> {
value: V;
label: string;
label?: string;
selectedLabel?: string;
icon?: string;
iconColor?: string;
Expand Down
20 changes: 20 additions & 0 deletions projects/components/src/select/select.component.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,26 @@ describe('Select Component', () => {
expect(spectator.element).toHaveText(selectionOptions[2].label);
}));

test('should display initial selection for new select renderer', fakeAsync(() => {
spectator = hostFactory(
`
<ht-select [selected]="selected">
<ht-select-option *ngFor="let option of options; let i = index" [label]="option.label" [value]="option.value">
<div *htSelectOptionRenderer>new-label</div>
</ht-select-option>
</ht-select>`,
{
hostProps: {
options: selectionOptions,
selected: selectionOptions[1].value
}
}
);
spectator.tick();

expect(spectator.element).toHaveText('new-label');
}));

test('should display provided options when clicked', fakeAsync(() => {
spectator = hostFactory(
`
Expand Down
81 changes: 51 additions & 30 deletions projects/components/src/select/select.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,20 +55,28 @@ import { SelectSize } from './select-size';
class="trigger-content menu-with-border"
[ngClass]="[this.justifyClass]"
>
<ht-icon
*ngIf="this.getPrefixIcon(selected)"
class="trigger-prefix-icon"
[icon]="this.getPrefixIcon(selected)"
[size]="this.iconSize"
[color]="selected?.iconColor"
[borderType]="selected?.iconBorderType"
[borderColor]="selected?.iconBorderColor"
[borderRadius]="selected?.iconBorderRadius"
>
</ht-icon>
<ht-label class="trigger-label" [label]="selected?.selectedLabel || selected?.label || this.placeholder">
</ht-label>
<ng-container
[ngTemplateOutlet]="selected?.selectOptionRenderer?.getTemplateRef() ?? defaultMenuWithBorderTriggerTemplate"
></ng-container>
<ht-icon class="trigger-icon" icon="${IconType.ChevronDown}" size="${IconSize.ExtraSmall}"> </ht-icon>
<ng-template #defaultMenuWithBorderTriggerTemplate
><ht-icon
*ngIf="this.getPrefixIcon(selected)"
class="trigger-prefix-icon"
[icon]="this.getPrefixIcon(selected)"
[size]="this.iconSize"
[color]="selected?.iconColor"
[borderType]="selected?.iconBorderType"
[borderColor]="selected?.iconBorderColor"
[borderRadius]="selected?.iconBorderRadius"
>
</ht-icon>
<ht-label
class="trigger-label"
[label]="selected?.selectedLabel || selected?.label || this.placeholder"
>
</ht-label>
</ng-template>
</div>
<div
*ngSwitchCase="'${SelectTriggerDisplayMode.Icon}'"
Expand All @@ -89,8 +97,16 @@ import { SelectSize } from './select-size';
class="trigger-content menu-with-background"
[ngClass]="[this.justifyClass]"
>
<ht-label class="trigger-label" [label]="selected?.selectedLabel || selected?.label || this.placeholder">
</ht-label>
<ng-container
[ngTemplateOutlet]="selected?.selectOptionRenderer?.getTemplateRef() ?? defaultMenuWithBackgroundTriggerTemplate"
></ng-container>
<ng-template #defaultMenuWithBackgroundTriggerTemplate
><<ht-label
class="trigger-label"
[label]="selected?.selectedLabel || selected?.label || this.placeholder"
>
</ht-label
></ng-template>
<ht-icon class="trigger-icon" icon="${IconType.ChevronDown}" size="${IconSize.Small}"> </ht-icon>
</div>
</div>
Expand All @@ -111,28 +127,16 @@ import { SelectSize } from './select-size';
*ngTemplateOutlet="itemsTemplate; context: { items: items, showSelectionStatus: true }"
></ng-container>
</div>

<ng-template #itemsTemplate let-items="items" let-showSelectionStatus="showSelectionStatus">
<div
*ngFor="let item of items"
(click)="this.onSelectionChange(item)"
class="select-option"
[ngClass]="this.getStyleClassesForSelectItem | htMemoize: this.size:item"
>
<div class="select-option-info">
<ht-icon
*ngIf="item.icon"
class="icon"
[icon]="item.icon"
size="${IconSize.Small}"
[color]="item.iconColor"
[borderType]="item?.iconBorderType"
[borderColor]="item?.iconBorderColor"
[borderRadius]="item?.iconBorderRadius"
>
</ht-icon>
<span class="label">{{ item.label }}</span>
</div>
<ng-container
*ngTemplateOutlet="item.selectOptionRenderer?.getTemplateRef() ?? defaultSelectOptionTemplate; context: {$implicit: item}"
></ng-container>
<ht-icon
class="status-icon"
*ngIf="showSelectionStatus && this.highlightSelected && this.isSelectedItem(item)"
Expand All @@ -141,6 +145,23 @@ import { SelectSize } from './select-size';
></ht-icon>
</div>
</ng-template>

<ng-template #defaultSelectOptionTemplate let-item
><div class="select-option-info">
<ht-icon
*ngIf="item.icon"
class="icon"
[icon]="item.icon"
size="${IconSize.Small}"
[color]="item.iconColor"
[borderType]="item?.iconBorderType"
[borderColor]="item?.iconBorderColor"
[borderRadius]="item?.iconBorderRadius"
>
</ht-icon>
<span class="label">{{ item.label }}</span>
</div>
</ng-template>
</ht-popover-content>
</ht-popover>
</div>
Expand Down
17 changes: 15 additions & 2 deletions projects/components/src/select/select.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import { LabelModule } from '../label/label.module';
import { LetAsyncModule } from '../let-async/let-async.module';
import { PopoverModule } from '../popover/popover.module';
import { TooltipModule } from '../tooltip/tooltip.module';
import { SelectOptionRendererDirective } from './directive/select-option-renderer.directive';
import { SelectControlOptionComponent } from './select-control-option.component';
import { SelectGroupComponent } from './select-group.component';
import { SelectOptionComponent } from './select-option.component';
Expand All @@ -25,7 +26,19 @@ import { SelectComponent } from './select.component';
DividerModule,
MemoizeModule
],
declarations: [SelectComponent, SelectOptionComponent, SelectGroupComponent, SelectControlOptionComponent],
exports: [SelectComponent, SelectOptionComponent, SelectGroupComponent, SelectControlOptionComponent]
declarations: [
SelectComponent,
SelectOptionComponent,
SelectGroupComponent,
SelectControlOptionComponent,
SelectOptionRendererDirective
],
exports: [
SelectComponent,
SelectOptionComponent,
SelectGroupComponent,
SelectControlOptionComponent,
SelectOptionRendererDirective
]
})
export class SelectModule {}