From 830c343a3f9c7e374ce2cea6aa9f629e9d43d064 Mon Sep 17 00:00:00 2001 From: Murhaf Sousli Date: Mon, 18 Mar 2024 08:10:47 +0300 Subject: [PATCH] Update --- .nx/cache/nx_files.nxt | Bin 0 -> 22340 bytes CHANGELOG.md | 12 +- angular.json | 4 +- .../src/app/app.component.html | 9 +- .../src/app/app.component.scss | 12 +- .../ngx-scrollbar-demo/src/app/app.routes.ts | 8 +- .../example-infinite-scroll.component.scss | 4 +- .../example-mat-select.component.scss | 5 +- .../example-mat-select.component.ts | 4 +- ...ample-nested-virtual-scroll.component.scss | 10 +- .../example-ngx-datatable.component.scss | 2 +- .../src/app/example2/example2.component.html | 4 +- .../src/app/example2/example2.component.scss | 5 +- .../src/app/example2/example2.component.ts | 8 +- .../src/app/example3/example3.component.scss | 1 + .../css-variables-form.component.ts | 4 +- .../src/app/lab/lab.component.html | 18 ++- .../src/app/lab/lab.component.ts | 15 +- .../reached-notifier.component.scss | 19 +++ .../reached-notifier.component.ts | 50 +++++-- .../prime-ng-table/prime-ng.component.html | 2 +- .../prime-ng-table/prime-ng.component.scss | 4 +- .../app/shared/header/header.component.html | 30 ++-- .../app/shared/header/header.component.scss | 5 +- projects/ngx-scrollbar-demo/src/styles.scss | 13 +- projects/ngx-scrollbar/.eslintrc.json | 2 + projects/ngx-scrollbar/package.json | 2 +- .../reached-event/src/ng-scroll-dropped.ts | 60 ++++++++ .../reached-event/src/ng-scroll-reached.ts | 60 ++++++++ .../src/ng-scrollbar-reached.module.ts | 13 -- .../reached-event/src/public_api.ts | 4 +- ...bar-reached.ts => reached-dropped-base.ts} | 127 +++++++--------- .../ngx-scrollbar/src/lib/ng-scrollbar.scss | 3 - .../src/lib/scrollbar/shared.scss | 1 - .../src/lib/styles/reached-events.scss | 90 +++++++++--- .../src/lib/tests/dropped-events.spec.ts | 137 ++++++++++++++++++ .../src/lib/tests/reached-events.spec.ts | 4 +- .../src/lib/tests/visibility.spec.ts | 2 - projects/ngx-scrollbar/src/lib/thumb/thumb.ts | 4 +- projects/ngx-scrollbar/src/lib/track/track.ts | 4 +- .../src/lib/viewport/viewport-adapter.ts | 8 +- .../utils/src/mat-select-viewport.ts | 4 +- 42 files changed, 571 insertions(+), 202 deletions(-) create mode 100644 .nx/cache/nx_files.nxt create mode 100644 projects/ngx-scrollbar/reached-event/src/ng-scroll-dropped.ts create mode 100644 projects/ngx-scrollbar/reached-event/src/ng-scroll-reached.ts delete mode 100644 projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.module.ts rename projects/ngx-scrollbar/reached-event/src/{ng-scrollbar-reached.ts => reached-dropped-base.ts} (50%) create mode 100644 projects/ngx-scrollbar/src/lib/tests/dropped-events.spec.ts diff --git a/.nx/cache/nx_files.nxt b/.nx/cache/nx_files.nxt new file mode 100644 index 0000000000000000000000000000000000000000..c16b7df1c3512a6f0da29c0272e3c8a9aeb60bd2 GIT binary patch literal 22340 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 CBUD`g literal 0 HcmV?d00001 diff --git a/CHANGELOG.md b/CHANGELOG.md index 245784be..0f9d95d7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,15 @@ # Changelog +## 14.0.0-beta.7 + +- regret: Use `offsetWidth` and `offsetHeight` again instead of `getBoundingClientRect` due to incorrect value when scrollbar is used in an overlay such as `matSelect`. +- fix: `(reachedEnd)` does not work without subscribing to `(reachedBottom)`. + +### Breaking changes: + +- Remove `NgScrollbarReachModule`. +- Rename the directive `MatSelectViewport` to `NgScrollbarMatSelectViewport`. + ## 14.0.0-beta.6 - feat: Add scrollbar buttons using `buttons` options, closes [#465](https://github.com/MurhafSousli/ngx-scrollbar/issues/465). @@ -8,7 +18,7 @@ - refactor: Use `swithcMap` instead of `expand` for track long ongoing pointer down event. - refactor: Only use `getRtlScrollAxisType` once on initialization in `SmoothScrollManager`. - refactor: `matSelectViewport` use instant scroll function to scroll to the selected item in the list. -- refactor: Use `getBoundingClientRect` in all directives instead of `clientWidth` and `clientHeight` for high precision calculation. +- refactor: Use `getBoundingClientRect` in all directives instead of `offsetWidth` and `offsetHeight` for high precision calculation. ### Breaking Changes diff --git a/angular.json b/angular.json index 0bac3f41..f7cec184 100644 --- a/angular.json +++ b/angular.json @@ -58,8 +58,8 @@ }, { "type": "anyComponentStyle", - "maximumWarning": "12kb", - "maximumError": "12kb" + "maximumWarning": "13kb", + "maximumError": "13kb" } ], "outputHashing": "all" diff --git a/projects/ngx-scrollbar-demo/src/app/app.component.html b/projects/ngx-scrollbar-demo/src/app/app.component.html index eae5c94a..84ebe6b4 100644 --- a/projects/ngx-scrollbar-demo/src/app/app.component.html +++ b/projects/ngx-scrollbar-demo/src/app/app.component.html @@ -21,15 +21,10 @@ Material Integration - Integration + Other Integrations - - - - - diff --git a/projects/ngx-scrollbar-demo/src/app/app.component.scss b/projects/ngx-scrollbar-demo/src/app/app.component.scss index 208f5ba2..caafba7e 100644 --- a/projects/ngx-scrollbar-demo/src/app/app.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/app.component.scss @@ -5,12 +5,22 @@ ng-scrollbar { --scrollbar-track-color: rgb(0 0 0 / 30%); --scrollbar-border-radius: 0; + --scrollbar-button-color: var(--scrollbar-thumb-color); + --scrollbar-button-hover-color: var(--scrollbar-button-color); + --scrollbar-button-active-color: var(--scrollbar-button-hover-color); + + // Scrollbar button arrow fill + --scrollbar-button-fill: white; + --scrollbar-button-hover-fill: var(--scrollbar-button-fill); + --scrollbar-button-active-fill: var(--scrollbar-button-hover-fill); + + color: white; height: calc(100% - 60px); ::ng-deep { .app-scrollbar-track { - box-shadow: inset 0 0 0 1px rgb(0 0 0 / 10%); + //box-shadow: inset 0 0 0 1px rgb(0 0 0 / 10%); } .app-scrollbar-thumb { diff --git a/projects/ngx-scrollbar-demo/src/app/app.routes.ts b/projects/ngx-scrollbar-demo/src/app/app.routes.ts index 7417a231..a6283bb4 100644 --- a/projects/ngx-scrollbar-demo/src/app/app.routes.ts +++ b/projects/ngx-scrollbar-demo/src/app/app.routes.ts @@ -11,11 +11,7 @@ export const routes: Routes = [ loadComponent: () => import('./material-page/material-page.component').then(c => c.MaterialPageComponent), }, { - path: 'integration', + path: 'other-integrations', loadComponent: () => import('./integration-page/integration-page.component').then(c => c.IntegrationPageComponent), - }, - // { - // path: 'lab', - // loadComponent: () => import('./lab/lab.component').then(c => c.LabComponent), - // } + } ]; diff --git a/projects/ngx-scrollbar-demo/src/app/example-infinite-scroll/example-infinite-scroll.component.scss b/projects/ngx-scrollbar-demo/src/app/example-infinite-scroll/example-infinite-scroll.component.scss index 1488af97..88b3eb4e 100644 --- a/projects/ngx-scrollbar-demo/src/app/example-infinite-scroll/example-infinite-scroll.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example-infinite-scroll/example-infinite-scroll.component.scss @@ -15,7 +15,9 @@ ng-scrollbar { --scrollbar-track-color: rgb(0 0 0 / 5%); --scrollbar-thumb-color: var(--color-primary); - --scrollbar-thickness: 12; + --scrollbar-thickness: 10; + --scrollbar-offset: 6; + --scrollbar-border-radius: 7px; border-radius: 3px; border: 2px solid rgb(0 0 0 / 5%); diff --git a/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.scss b/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.scss index 41abddc0..91474943 100644 --- a/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.scss @@ -1,10 +1,13 @@ ng-scrollbar { - --scrollbar-thumb-color: var(--color-primary); + --scrollbar-thumb-color: var(--color-track-orange-passion); --scrollbar-thickness: 8; --scrollbar-track-color: rgb(0 0 0 / 20%); + --scrollbar-offset: 6; + --scrollbar-border-radius: 7px; } .mat-mdc-select { + --mat-select-enabled-arrow-color: rgb(255 255 255 / 54%); margin-bottom: 30px !important; color: white; } diff --git a/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.ts b/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.ts index a1c4f390..e4b11faa 100644 --- a/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.ts +++ b/projects/ngx-scrollbar-demo/src/app/example-mat-select/example-mat-select.component.ts @@ -5,7 +5,7 @@ import { MatCardModule } from '@angular/material/card'; import { MatSelectModule } from '@angular/material/select'; import { Chance } from 'chance'; import { NgScrollbar } from 'ngx-scrollbar'; -import { MatSelectViewport } from 'ngx-scrollbar/utils'; +import { NgScrollbarMatSelectViewport } from 'ngx-scrollbar/utils'; @Component({ selector: 'app-example-mat-select', @@ -16,7 +16,7 @@ import { MatSelectViewport } from 'ngx-scrollbar/utils'; NgForOf, NgScrollbar, MatCardModule, - MatSelectViewport + NgScrollbarMatSelectViewport ], templateUrl: './example-mat-select.component.html', styleUrl: './example-mat-select.component.scss', diff --git a/projects/ngx-scrollbar-demo/src/app/example-nested-virtual-scroll/example-nested-virtual-scroll.component.scss b/projects/ngx-scrollbar-demo/src/app/example-nested-virtual-scroll/example-nested-virtual-scroll.component.scss index 8025b012..b7c781a3 100644 --- a/projects/ngx-scrollbar-demo/src/app/example-nested-virtual-scroll/example-nested-virtual-scroll.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example-nested-virtual-scroll/example-nested-virtual-scroll.component.scss @@ -12,14 +12,17 @@ .outer-ng-scrollbar { color: black; border: 2px solid rgb(0 0 0 / 5%); - --scrollbar-track-color: var(--color-track-orange-passion); + //--scrollbar-track-color: var(--color-track-orange-passion); + --scrollbar-track-color: rgb(255 255 255 / 15%); --scrollbar-thumb-color: var(--color-orange-passion); - --scrollbar-thickness: 12; + --scrollbar-offset: 3; + --scrollbar-thickness: 10; --scrollbar-border-radius: 10px; } .cdk-virtual-scroll-orientation-vertical ::ng-deep > .ng-scroll-content { - background: #643761; + //background: #643761; + background: var(--primary-color); } .cards { @@ -73,6 +76,7 @@ --scrollbar-track-color: #d3d3d3; --scrollbar-offset: 7; --scrollbar-thickness: 6; + --scrollbar-border-radius: 7px; --scrollbar-thumb-color: var(--color-accent); } } diff --git a/projects/ngx-scrollbar-demo/src/app/example-ngx-datatable/example-ngx-datatable.component.scss b/projects/ngx-scrollbar-demo/src/app/example-ngx-datatable/example-ngx-datatable.component.scss index 40e9f2f5..f284c00c 100644 --- a/projects/ngx-scrollbar-demo/src/app/example-ngx-datatable/example-ngx-datatable.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example-ngx-datatable/example-ngx-datatable.component.scss @@ -1,7 +1,7 @@ ng-scrollbar { --scrollbar-thickness: 6; --scrollbar-hover-thickness: 10; - --scrollbar-offset: 0; + --scrollbar-offset: 1; --scrollbar-border-radius: 0; --scrollbar-thumb-color: var(--color-primary); --scrollbar-track-color: rgb(0 0 0 / 20%); diff --git a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.html b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.html index 972396f8..e4d6097d 100644 --- a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.html +++ b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.html @@ -7,7 +7,7 @@ externalViewport appearance="compact" (afterInit)="onScrollbarUpdate(scrollbarRef)" - (afterUpdate)="onScrollbarUpdate(scrollbarRef)"> + (afterUpdate)="onScrollbarUpdate(scrollbarRef, 200)">
  • @@ -22,6 +22,6 @@
- + diff --git a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.scss b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.scss index a81449af..73c443bc 100644 --- a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.scss @@ -4,6 +4,7 @@ ng-scrollbar { --scrollbar-track-color: rgb(0 0 0 / 10%); --scrollbar-thumb-color: rgb(0 0 0 / 20%); --scrollbar-thumb-hover-color: rgb(0 0 0 / 30%); + --scrollbar-border-radius: 7px; width: 100%; border: 1px solid rgb(0 0 0 / 25%); height: 200px; @@ -58,8 +59,8 @@ ng-scrollbar { } header { - font-size: 1.1em; - padding: .2em; + font-size: 16px; + padding: 8px; letter-spacing: 1px; background-image: linear-gradient(to bottom, #3d434a, #242931); color: white; diff --git a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.ts b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.ts index cc5204fc..ac979cc8 100644 --- a/projects/ngx-scrollbar-demo/src/app/example2/example2.component.ts +++ b/projects/ngx-scrollbar-demo/src/app/example2/example2.component.ts @@ -3,7 +3,7 @@ import { CommonModule } from '@angular/common'; import { MatCardModule } from '@angular/material/card'; import { MatButtonModule } from '@angular/material/button'; import { NgScrollbarExt, NgScrollbarModule } from 'ngx-scrollbar'; -import { NgScrollbarReachedModule } from 'ngx-scrollbar/reached-event'; +import { NgScrollReached } from 'ngx-scrollbar/reached-event'; @Component({ selector: 'app-example2', @@ -14,7 +14,7 @@ import { NgScrollbarReachedModule } from 'ngx-scrollbar/reached-event'; '[class.example-component]': 'true' }, standalone: true, - imports: [CommonModule, NgScrollbarModule, NgScrollbarReachedModule, MatCardModule, MatButtonModule] + imports: [CommonModule, NgScrollbarModule, NgScrollReached, MatCardModule, MatButtonModule] }) export class Example2Component { @@ -102,7 +102,7 @@ export class Example2Component { ]; } - onScrollbarUpdate(scrollbarRef: NgScrollbarExt): void { - scrollbarRef.scrollTo({ bottom: 0, duration: 200 }); + onScrollbarUpdate(scrollbarRef: NgScrollbarExt, duration: number = 0): void { + scrollbarRef.scrollTo({ bottom: 0, duration }); } } diff --git a/projects/ngx-scrollbar-demo/src/app/example3/example3.component.scss b/projects/ngx-scrollbar-demo/src/app/example3/example3.component.scss index eb200384..a969a860 100644 --- a/projects/ngx-scrollbar-demo/src/app/example3/example3.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/example3/example3.component.scss @@ -7,6 +7,7 @@ --scrollbar-thickness: 12; --scrollbar-track-color: rgb(0 0 0 / 50%); --scrollbar-border-radius: 6px; + --scrollbar-offset: 4; } .mat-mdc-card-content { diff --git a/projects/ngx-scrollbar-demo/src/app/lab/css-variables-form/css-variables-form.component.ts b/projects/ngx-scrollbar-demo/src/app/lab/css-variables-form/css-variables-form.component.ts index 27aeccfa..878f808c 100644 --- a/projects/ngx-scrollbar-demo/src/app/lab/css-variables-form/css-variables-form.component.ts +++ b/projects/ngx-scrollbar-demo/src/app/lab/css-variables-form/css-variables-form.component.ts @@ -19,9 +19,9 @@ export class CssVariablesFormComponent implements OnInit { this.form = new FormGroup({ thickness: new FormControl('12'), hoverThickness: new FormControl('15'), - trackColor: new FormControl('#975857'), + trackColor: new FormControl('#77b4e8'), thumbColor: new FormControl('var(--color-scrollbar-example-x)'), - thumbHoverColor: new FormControl('#ff6060'), //var(--color-scrollbar-example-x)'), + thumbHoverColor: new FormControl('var(--color-scrollbar-example-x)'), trackOffset: new FormControl('0'), borderRadius: new FormControl('0px'), overscrollBehavior: new FormControl('initial'), diff --git a/projects/ngx-scrollbar-demo/src/app/lab/lab.component.html b/projects/ngx-scrollbar-demo/src/app/lab/lab.component.html index 88cdad25..3ecaff19 100644 --- a/projects/ngx-scrollbar-demo/src/app/lab/lab.component.html +++ b/projects/ngx-scrollbar-demo/src/app/lab/lab.component.html @@ -97,6 +97,15 @@ +
+
Disable dropped events
+ + True + False + +
+
Sensor throttle time
@@ -153,7 +162,12 @@ (reachedStart)="onReached('start')" (reachedEnd)="onReached('end')" (reachedBottom)="onReached('bottom')" - [disableReached]="disableReached"> + [disableReached]="disableReached" + (droppedTop)="onDropped('top')" + (droppedStart)="onDropped('start')" + (droppedEnd)="onDropped('end')" + (droppedBottom)="onDropped('bottom')" + [disableDropped]="disableDropped">
@@ -171,7 +185,7 @@
- +
diff --git a/projects/ngx-scrollbar-demo/src/app/lab/lab.component.ts b/projects/ngx-scrollbar-demo/src/app/lab/lab.component.ts index 2366b871..072af393 100644 --- a/projects/ngx-scrollbar-demo/src/app/lab/lab.component.ts +++ b/projects/ngx-scrollbar-demo/src/app/lab/lab.component.ts @@ -12,7 +12,7 @@ import { ScrollbarOrientation, ScrollbarVisibility } from 'ngx-scrollbar'; -import { NgScrollbarReached } from 'ngx-scrollbar/reached-event'; +import { NgScrollDropped, NgScrollReached } from 'ngx-scrollbar/reached-event'; import { NzResizableModule, NzResizeDirection, NzResizeEvent } from 'ng-zorro-antd/resizable'; import { NzIconModule } from 'ng-zorro-antd/icon'; @@ -31,7 +31,8 @@ import { SmoothScrollFormComponent, SmoothScrollOptionsForm } from './smooth-scr FormsModule, ReactiveFormsModule, NgScrollbar, - NgScrollbarReached, + NgScrollReached, + NgScrollDropped, MatCardModule, MatButtonToggleModule, MatExpansionModule, @@ -57,6 +58,7 @@ export class LabComponent { interactionDisabled: boolean = false; disableSensor: boolean = false; disableReached: boolean = false; + disableDropped: boolean = false; sensorThrottleTime: number = 0; trackScrollDuration: number = 50; @@ -87,6 +89,8 @@ export class LabComponent { reached: WritableSignal = signal({}); + dropped: WritableSignal = signal({}); + scrollReached: WritableSignal = signal(false); get content(): string { @@ -122,6 +126,13 @@ export class LabComponent { }, 600); } + onDropped(eventName: string): void { + this.dropped.set({ [eventName]: true }); + setTimeout(() => { + this.dropped.set({ [eventName]: false }) + }, 600); + } + onScrollTo(event: SmoothScrollOptionsForm): void { // Prepare scrollTo options from event const options: Partial = { diff --git a/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.scss b/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.scss index 13051c10..4077e0fb 100644 --- a/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.scss @@ -10,6 +10,13 @@ } } +.notifier-wrapper { + display: flex; + gap: 1em; + align-items: center; + margin-bottom: 0.5em; +} + .reached-event-title { margin-bottom: 5px; } @@ -27,7 +34,19 @@ } &.changed { + transition: unset !important; + } +} + +.reached { + .mat-mdc-chip.changed { background-color: var(--color-highlight) !important; transition: unset !important; } } + +.dropped { + .mat-mdc-chip.changed { + background-color: #85ff3f !important; + } +} diff --git a/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.ts b/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.ts index 003afb60..638f18cd 100644 --- a/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.ts +++ b/projects/ngx-scrollbar-demo/src/app/lab/reached-notifier/reached-notifier.component.ts @@ -4,20 +4,41 @@ import { MatChipsModule } from '@angular/material/chips'; @Component({ selector: 'app-reached-notifier', template: ` - - - Top - - - Bottom - - - Start - - - End - - +
+
Reached
+ + + Top + + + Bottom + + + Start + + + End + + +
+ +
+
Dropped
+ + + Top + + + Bottom + + + Start + + + End + + +
`, styleUrls: ['./reached-notifier.component.scss'], changeDetection: ChangeDetectionStrategy.OnPush, @@ -26,6 +47,7 @@ import { MatChipsModule } from '@angular/material/chips'; }) export class ReachedNotifierComponent { @Input() reached: ReachedEvent; + @Input() dropped: ReachedEvent; } export interface ReachedEvent { diff --git a/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.html b/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.html index 81c44326..a71660f5 100644 --- a/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.html +++ b/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.html @@ -26,7 +26,7 @@ asyncDetection="auto"> diff --git a/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.scss b/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.scss index 1c4f29c5..e5f4335a 100644 --- a/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/prime-ng-table/prime-ng.component.scss @@ -25,7 +25,9 @@ ng-scrollbar { --scrollbar-track-color: rgb(0 0 0 / 5%); --scrollbar-thumb-color: var(--color-primary); - --scrollbar-thickness: 12; + --scrollbar-thickness: 10; + --scrollbar-offset: 6; + --scrollbar-border-radius: 7px; border-radius: 3px; border: 2px solid rgb(0 0 0 / 5%); diff --git a/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.html b/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.html index 3f280397..4daf52d0 100644 --- a/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.html +++ b/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.html @@ -5,7 +5,7 @@ d="M0,288L48,266.7C96,245,192,203,288,202.7C384,203,480,245,576,250.7C672,256,768,224,864,224C960,224,1056,256,1152,261.3C1248,267,1344,245,1392,234.7L1440,224L1440,0L1392,0C1344,0,1248,0,1152,0C1056,0,960,0,864,0C768,0,672,0,576,0C480,0,384,0,288,0C192,0,96,0,48,0L0,0Z"> -
+

ngx-scrollbar

@@ -27,13 +27,14 @@

Custom overlay-scrollbars with native scrolling mechanism

- - - npm - + + + codecov + Custom overlay-scrollbars with native scrolling mechanism + + + npm +
-
library_books
-
Go To Documentation
+
+ library_books +
+
Go To Documentation
diff --git a/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.scss b/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.scss index 59a2b3ba..94fcef9b 100644 --- a/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.scss +++ b/projects/ngx-scrollbar-demo/src/app/shared/header/header.component.scss @@ -42,15 +42,14 @@ app-logo { margin: 2em 0; display: flex; flex-wrap: wrap; - justify-content: center; - align-items: center; + place-content: center; + gap: 4px; a, iframe { margin-top: 7px; } a { - margin-left: 7px; display: flex; } } diff --git a/projects/ngx-scrollbar-demo/src/styles.scss b/projects/ngx-scrollbar-demo/src/styles.scss index 7cfc6a37..acb2726c 100644 --- a/projects/ngx-scrollbar-demo/src/styles.scss +++ b/projects/ngx-scrollbar-demo/src/styles.scss @@ -49,8 +49,8 @@ $purple-passion-palette: ( ) ); -$app-primary: mat.define-palette($purple-passion-palette, 500); -//$app-primary: mat.define-palette(mat.$light-green-palette, 500); +//$app-primary: mat.define-palette($purple-passion-palette, 500); +$app-primary: mat.define-palette(mat.$blue-palette, 500); $app-accent: mat.define-palette(mat.$orange-palette, 500); $app-warn: mat.define-palette(mat.$red-palette); $app-success: mat.define-palette(mat.$light-green-palette); @@ -90,7 +90,10 @@ body { --color-orange-passion: #{mat.get-color-from-palette(mat.define-palette($app-accent, 500))}; - --color-track-orange-passion: #975857; + --color-track-orange-passion: #963634; + + --mat-option-selected-state-label-text-color: var(--color-track-orange-passion); + --mat-option-selected-state-label-text-color: var(--color-track-orange-passion); --color-app-background: #{mat.get-color-from-palette(mat.define-palette($app-primary, 400))}; --color-app-logo: var(--color-app-background); @@ -205,6 +208,6 @@ a { .mat-mdc-select-panel { padding: 0 !important; - --mat-minimal-pseudo-checkbox-selected-checkmark-color: var(--color-primary); - background-image: linear-gradient( to bottom, var(--color-example3), #EFB436); + --mat-minimal-pseudo-checkbox-selected-checkmark-color: var(--color-track-orange-passion); + background-image: linear-gradient( to bottom, var(--color-example3), var(--color-accent)); } diff --git a/projects/ngx-scrollbar/.eslintrc.json b/projects/ngx-scrollbar/.eslintrc.json index d4266efc..dde2dd6a 100644 --- a/projects/ngx-scrollbar/.eslintrc.json +++ b/projects/ngx-scrollbar/.eslintrc.json @@ -34,6 +34,8 @@ "@angular-eslint/component-class-suffix": 0, "@angular-eslint/directive-class-suffix": 0, "@angular-eslint/no-input-rename": 0, + "@angular-eslint/no-output-rename": 0, + "@angular-eslint/no-output-native": 0, "@angular-eslint/no-host-metadata-property": 0 } }, diff --git a/projects/ngx-scrollbar/package.json b/projects/ngx-scrollbar/package.json index 1fbe265d..5a893323 100644 --- a/projects/ngx-scrollbar/package.json +++ b/projects/ngx-scrollbar/package.json @@ -1,6 +1,6 @@ { "name": "ngx-scrollbar", - "version": "14.0.0-beta.6", + "version": "14.0.0-beta.7", "license": "MIT", "homepage": "https://ngx-scrollbar.netlify.com/", "author": { diff --git a/projects/ngx-scrollbar/reached-event/src/ng-scroll-dropped.ts b/projects/ngx-scrollbar/reached-event/src/ng-scroll-dropped.ts new file mode 100644 index 00000000..29e03e5a --- /dev/null +++ b/projects/ngx-scrollbar/reached-event/src/ng-scroll-dropped.ts @@ -0,0 +1,60 @@ +import { + Directive, + Input, + Output, + numberAttribute, + booleanAttribute, + input, + EventEmitter, + InputSignalWithTransform +} from '@angular/core'; +import { ReachedDroppedBase } from './reached-dropped-base'; + +@Directive({ + selector: 'ng-scrollbar[droppedTop], ng-scrollbar[droppedBottom], ng-scrollbar[droppedStart], ng-scrollbar[droppedEnd]', + standalone: true, +}) +export class NgScrollDropped extends ReachedDroppedBase { + + /** Dropped offset value in px */ + @Input({ alias: 'droppedOffset', transform: numberAttribute }) set offsetSetter(value: number) { + this.setCssVariable('--dropped-offset', value); + } + + @Input({ alias: 'droppedTopOffset', transform: numberAttribute }) set offsetTopSetter(value: number) { + this.setCssVariable('--dropped-offset-top', value); + } + + @Input({ alias: 'droppedBottomOffset', transform: numberAttribute }) set offsetBottomSetter(value: number) { + this.setCssVariable('--dropped-offset-bottom', value); + } + + @Input({ alias: 'droppedStartOffset', transform: numberAttribute }) set offsetStartSetter(value: number) { + this.setCssVariable('--dropped-offset-start', value); + } + + @Input({ alias: 'droppedEndOffset', transform: numberAttribute }) set offsetEndSetter(value: number) { + this.setCssVariable('--dropped-offset-end', value); + } + + disabled: InputSignalWithTransform = input(false, { + alias: 'disableDropped', + transform: booleanAttribute + }); + + @Output('droppedTop') top: EventEmitter = new EventEmitter(); + + @Output('droppedBottom') bottom: EventEmitter = new EventEmitter(); + + @Output('droppedStart') start: EventEmitter = new EventEmitter(); + + @Output('droppedEnd') end: EventEmitter = new EventEmitter(); + + protected triggerElementsWrapperClass: string = 'ng-scroll-dropped-wrapper'; + + protected triggerElementClass: string = 'scroll-dropped-trigger-element'; + + protected isTriggered(entry: IntersectionObserverEntry): boolean { + return !entry.isIntersecting; + } +} diff --git a/projects/ngx-scrollbar/reached-event/src/ng-scroll-reached.ts b/projects/ngx-scrollbar/reached-event/src/ng-scroll-reached.ts new file mode 100644 index 00000000..f839c904 --- /dev/null +++ b/projects/ngx-scrollbar/reached-event/src/ng-scroll-reached.ts @@ -0,0 +1,60 @@ +import { + Directive, + Input, + Output, + numberAttribute, + booleanAttribute, + input, + EventEmitter, + InputSignalWithTransform +} from '@angular/core'; +import { ReachedDroppedBase } from './reached-dropped-base'; + +@Directive({ + selector: 'ng-scrollbar[reachedTop], ng-scrollbar[reachedBottom], ng-scrollbar[reachedStart], ng-scrollbar[reachedEnd]', + standalone: true, +}) +export class NgScrollReached extends ReachedDroppedBase { + + /** Reached offset value in px */ + @Input({ alias: 'reachedOffset', transform: numberAttribute }) set offsetSetter(value: number) { + this.setCssVariable('--reached-offset', value); + } + + @Input({ alias: 'reachedTopOffset', transform: numberAttribute }) set offsetTopSetter(value: number) { + this.setCssVariable('--reached-offset-top', value); + } + + @Input({ alias: 'reachedBottomOffset', transform: numberAttribute }) set offsetBottomSetter(value: number) { + this.setCssVariable('--reached-offset-bottom', value); + } + + @Input({ alias: 'reachedStartOffset', transform: numberAttribute }) set offsetStartSetter(value: number) { + this.setCssVariable('--reached-offset-start', value); + } + + @Input({ alias: 'reachedEndOffset', transform: numberAttribute }) set offsetEndSetter(value: number) { + this.setCssVariable('--reached-offset-end', value); + } + + disabled: InputSignalWithTransform = input(false, { + alias: 'disableReached', + transform: booleanAttribute + }); + + @Output('reachedTop') top: EventEmitter = new EventEmitter(); + + @Output('reachedBottom') bottom: EventEmitter = new EventEmitter(); + + @Output('reachedStart') start: EventEmitter = new EventEmitter(); + + @Output('reachedEnd') end: EventEmitter = new EventEmitter(); + + protected triggerElementsWrapperClass: string = 'ng-scroll-reached-wrapper'; + + protected triggerElementClass: string = 'scroll-reached-trigger-element'; + + protected isTriggered(entry: IntersectionObserverEntry): boolean { + return entry.isIntersecting; + } +} diff --git a/projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.module.ts b/projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.module.ts deleted file mode 100644 index 7ffbad69..00000000 --- a/projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.module.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { NgModule } from '@angular/core'; -import { NgScrollbarReached } from './ng-scrollbar-reached'; - -@NgModule({ - imports: [ - NgScrollbarReached - ], - exports: [ - NgScrollbarReached - ] -}) -export class NgScrollbarReachedModule { -} diff --git a/projects/ngx-scrollbar/reached-event/src/public_api.ts b/projects/ngx-scrollbar/reached-event/src/public_api.ts index 42093f63..5e685305 100644 --- a/projects/ngx-scrollbar/reached-event/src/public_api.ts +++ b/projects/ngx-scrollbar/reached-event/src/public_api.ts @@ -1,2 +1,2 @@ -export * from './ng-scrollbar-reached.module'; -export * from './ng-scrollbar-reached'; +export * from './ng-scroll-reached'; +export * from './ng-scroll-dropped'; diff --git a/projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.ts b/projects/ngx-scrollbar/reached-event/src/reached-dropped-base.ts similarity index 50% rename from projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.ts rename to projects/ngx-scrollbar/reached-event/src/reached-dropped-base.ts index 34df308b..615c5beb 100644 --- a/projects/ngx-scrollbar/reached-event/src/ng-scrollbar-reached.ts +++ b/projects/ngx-scrollbar/reached-event/src/reached-dropped-base.ts @@ -1,101 +1,84 @@ -import { isPlatformBrowser } from '@angular/common'; import { Directive, - Input, - Output, + inject, + effect, + runInInjectionContext, OnInit, OnDestroy, NgZone, - Renderer2, - WritableSignal, Injector, - inject, - signal, - effect, - numberAttribute, - booleanAttribute, - runInInjectionContext, + Renderer2, EventEmitter, - PLATFORM_ID + PLATFORM_ID, + InputSignalWithTransform } from '@angular/core'; +import { isPlatformBrowser } from '@angular/common'; import { _NgScrollbar, NG_SCROLLBAR } from 'ngx-scrollbar'; -type ReachedEventAction = { +type EventAction = { emit: () => void; } -@Directive({ - selector: 'ng-scrollbar[reachedTop], ng-scrollbar[reachedBottom], ng-scrollbar[reachedStart], ng-scrollbar[reachedEnd]', - standalone: true, -}) -export class NgScrollbarReached implements OnInit, OnDestroy { - - private readonly isBrowser: boolean = isPlatformBrowser(inject(PLATFORM_ID)); +@Directive() +export abstract class ReachedDroppedBase implements OnInit, OnDestroy { - private readonly zone: NgZone = inject(NgZone); + protected readonly isBrowser: boolean = isPlatformBrowser(inject(PLATFORM_ID)); - private readonly renderer: Renderer2 = inject(Renderer2); + protected readonly zone: NgZone = inject(NgZone); - private readonly injector: Injector = inject(Injector); + protected readonly renderer: Renderer2 = inject(Renderer2); - private readonly scrollbar: _NgScrollbar = inject(NG_SCROLLBAR); + protected readonly injector: Injector = inject(Injector); - private readonly disabled: WritableSignal = signal(false); + protected readonly scrollbar: _NgScrollbar = inject(NG_SCROLLBAR); /** An array that contains all trigger elements **/ - private triggerElements: HTMLElement[] = []; + protected triggerElements: HTMLElement[] = []; /** The intersection observer reference */ - private intersectionObserver: IntersectionObserver; + protected intersectionObserver: IntersectionObserver; /** An array that contains the chosen outputs */ - private subscribedEvents: string[] = []; + protected subscribedEvents: string[] = []; - /** The scrollbars element that contains the trigger elements */ - private triggerElementsWrapper: HTMLElement; + /** The wrapper element that contains the trigger elements */ + protected triggerElementsWrapper: HTMLElement; - /** Reached offset value in px */ - @Input({ alias: 'reachedOffset', transform: numberAttribute }) set offsetSetter(value: number) { - this.setCssVariable('--reached-offset', value); - } + /** The wrapper element class name */ + protected abstract triggerElementsWrapperClass: string; - @Input({ alias: 'reachedTopOffset', transform: numberAttribute }) set offsetTopSetter(value: number) { - this.setCssVariable('--reached-offset-top', value); - } + /** The trigger element class name */ + protected abstract triggerElementClass: string; - @Input({ alias: 'reachedBottomOffset', transform: numberAttribute }) set offsetBottomSetter(value: number) { - this.setCssVariable('--reached-offset-bottom', value); - } + abstract disabled: InputSignalWithTransform; - @Input({ alias: 'reachedStartOffset', transform: numberAttribute }) set offsetStartSetter(value: number) { - this.setCssVariable('--reached-offset-start', value); - } + abstract top: EventEmitter; - @Input({ alias: 'reachedEndOffset', transform: numberAttribute }) set offsetEndSetter(value: number) { - this.setCssVariable('--reached-offset-end', value); - } + abstract bottom: EventEmitter; - @Input({ alias: 'disableReached', transform: booleanAttribute }) - set disableReachedSetter(value: boolean) { - this.disabled.set(value); - } + abstract start: EventEmitter; + + abstract end: EventEmitter; - @Output() reachedTop: EventEmitter = new EventEmitter(); - @Output() reachedBottom: EventEmitter = new EventEmitter(); - @Output() reachedStart: EventEmitter = new EventEmitter(); - @Output() reachedEnd: EventEmitter = new EventEmitter(); + protected abstract isTriggered(entry: IntersectionObserverEntry): boolean; /** A mapper function to ease forwarding the intersected element to its proper output */ - readonly reachedEventActions: Record = { - top: { emit: (): void => this.scrollbar.isVerticallyScrollable() ? this.reachedTop.emit() : null }, - bottom: { emit: (): void => this.scrollbar.isVerticallyScrollable() ? this.reachedBottom.emit() : null }, - start: { emit: (): void => this.scrollbar.isHorizontallyScrollable() ? this.reachedStart.emit() : null }, - end: { emit: (): void => this.scrollbar.isHorizontallyScrollable() ? this.reachedEnd.emit() : null } + readonly eventActions: Record = { + top: { emit: (): void => this.scrollbar.isVerticallyScrollable() ? this.top.emit() : null }, + bottom: { emit: (): void => this.scrollbar.isVerticallyScrollable() ? this.bottom.emit() : null }, + start: { emit: (): void => this.scrollbar.isHorizontallyScrollable() ? this.start.emit() : null }, + end: { emit: (): void => this.scrollbar.isHorizontallyScrollable() ? this.end.emit() : null } }; - private onReached(trigger: string): void { + private onAction(trigger: string): void { if (trigger) { - this.reachedEventActions[trigger]?.emit(); + this.eventActions[trigger]?.emit(); + } + } + + protected setCssVariable(property: string, value: number): void { + if (value) { + this.scrollbar.nativeElement.style.setProperty(property, `${ value }px`); } } @@ -103,13 +86,13 @@ export class NgScrollbarReached implements OnInit, OnDestroy { this.zone.runOutsideAngular(() => { // Create the scrollbars element inside the viewport this.triggerElementsWrapper = this.renderer.createElement('div'); - this.renderer.addClass(this.triggerElementsWrapper, 'ng-scroll-reached-wrapper'); + this.renderer.addClass(this.triggerElementsWrapper, this.triggerElementsWrapperClass); this.renderer.appendChild(this.scrollbar.viewport.contentWrapperElement, this.triggerElementsWrapper); // Create a trigger element for each subscribed event this.subscribedEvents.forEach((event: string) => { const triggerElement: HTMLElement = this.renderer.createElement('div'); - this.renderer.addClass(triggerElement, 'scroll-reached-trigger-element'); + this.renderer.addClass(triggerElement, this.triggerElementClass); this.renderer.setAttribute(triggerElement, 'trigger', event); this.renderer.appendChild(this.triggerElementsWrapper, triggerElement); this.triggerElements.push(triggerElement); @@ -122,10 +105,10 @@ export class NgScrollbarReached implements OnInit, OnDestroy { this.intersectionObserver = new IntersectionObserver((entries: IntersectionObserverEntry[]) => { if (intersectionObserverInit) { entries.forEach((entry: IntersectionObserverEntry) => { - if (entry.isIntersecting) { + if (this.isTriggered(entry)) { // Forward the detected trigger element only after the observer is initialized // Only observe the trigger elements when scrollable - this.zone.run(() => this.onReached(entry.target.getAttribute('trigger'))); + this.zone.run(() => this.onAction(entry.target.getAttribute('trigger'))); } }); } else { @@ -146,23 +129,17 @@ export class NgScrollbarReached implements OnInit, OnDestroy { this.triggerElements = []; } - private setCssVariable(property: string, value: number): void { - if (value) { - this.scrollbar.nativeElement.style.setProperty(property, `${ value }px`); - } - } - ngOnInit(): void { - if (this.reachedTop.observed) { + if (this.top.observed) { this.subscribedEvents.push('top'); } - if (this.reachedBottom.observed) { + if (this.bottom.observed) { this.subscribedEvents.push('bottom'); } - if (this.reachedStart.observed) { + if (this.start.observed) { this.subscribedEvents.push('start'); } - if (this.reachedBottom.observed) { + if (this.end.observed) { this.subscribedEvents.push('end'); } diff --git a/projects/ngx-scrollbar/src/lib/ng-scrollbar.scss b/projects/ngx-scrollbar/src/lib/ng-scrollbar.scss index 8d5afe8f..e9767d61 100644 --- a/projects/ngx-scrollbar/src/lib/ng-scrollbar.scss +++ b/projects/ngx-scrollbar/src/lib/ng-scrollbar.scss @@ -32,9 +32,6 @@ // Scrollbar track color --scrollbar-track-color: transparent; - // Scrollbar track transition - --scrollbar-track-transition: none; - // Scrollbar thumb color --scrollbar-thumb-color: rgb(0 0 0 / 20%); diff --git a/projects/ngx-scrollbar/src/lib/scrollbar/shared.scss b/projects/ngx-scrollbar/src/lib/scrollbar/shared.scss index 5554da54..a471f555 100644 --- a/projects/ngx-scrollbar/src/lib/scrollbar/shared.scss +++ b/projects/ngx-scrollbar/src/lib/scrollbar/shared.scss @@ -45,7 +45,6 @@ width: 100%; height: 100%; background-color: var(--scrollbar-track-color); - transition: var(--scrollbar-track-transition); border-radius: var(--scrollbar-border-radius); cursor: default; z-index: 1; diff --git a/projects/ngx-scrollbar/src/lib/styles/reached-events.scss b/projects/ngx-scrollbar/src/lib/styles/reached-events.scss index 6f449c19..bf35a7ab 100644 --- a/projects/ngx-scrollbar/src/lib/styles/reached-events.scss +++ b/projects/ngx-scrollbar/src/lib/styles/reached-events.scss @@ -7,44 +7,60 @@ --reached-offset-start: var(--reached-offset); --reached-offset-end: var(--reached-offset); + --dropped-offset: 1px; + --dropped-offset-top: var(--dropped-offset); + --dropped-offset-bottom: var(--dropped-offset); + --dropped-offset-start: var(--dropped-offset); + --dropped-offset-end: var(--dropped-offset); + + @include selector.LTR { - ::ng-deep .scroll-reached-trigger-element { - &[trigger="start"] { - left: 0; - right: unset; - } + ::ng-deep { + .scroll-reached-trigger-element, + .scroll-dropped-trigger-element { + &[trigger="start"] { + left: 0; + right: unset; + } - &[trigger="end"] { - right: 0; - left: unset; + &[trigger="end"] { + right: 0; + left: unset; + } } } } @include selector.RTL { - ::ng-deep .scroll-reached-trigger-element { - &[trigger="start"] { - right: 0; - left: unset; - } + ::ng-deep { + .scroll-reached-trigger-element, + .scroll-dropped-trigger-element { + &[trigger="start"] { + right: 0; + left: unset; + } - &[trigger="end"] { - left: 0; - right: unset; + &[trigger="end"] { + left: 0; + right: unset; + } } } } ::ng-deep { .ng-scroll-reached-wrapper, - .scroll-reached-trigger-element { + .ng-scroll-dropped-wrapper, + .scroll-reached-trigger-element, + .scroll-dropped-trigger-element { position: absolute; user-select: none; pointer-events: none; z-index: -9999; } - .ng-scroll-reached-wrapper { + .ng-scroll-reached-wrapper, + .ng-scroll-dropped-wrapper { visibility: hidden; top: 0; left: 0; @@ -56,7 +72,8 @@ // Should only hide the END trigger when content isn't horizontally scrollable &[isHorizontallyScrollable="false"] { - .scroll-reached-trigger-element { + .scroll-reached-trigger-element , + .scroll-dropped-trigger-element { &[trigger="end"] { display: none; } @@ -65,7 +82,8 @@ // Should only hide the BOTTOM trigger when content isn't vertically scrollable &[isVerticallyScrollable="false"] { - .scroll-reached-trigger-element { + .scroll-reached-trigger-element , + .scroll-dropped-trigger-element { &[trigger="bottom"] { display: none; } @@ -104,4 +122,36 @@ } } } + + .scroll-dropped-trigger-element { + background: blue; + + &[trigger="top"], &[trigger="bottom"] { + left: 0; + right: 0; + } + + &[trigger="start"], &[trigger="end"] { + top: 0; + bottom: 0; + } + + &[trigger="top"] { + top: 0; + height: var(--dropped-offset-top); + } + + &[trigger="bottom"] { + bottom: 0; + height: var(--dropped-offset-bottom); + } + + &[trigger="start"] { + width: var(--dropped-offset-start); + } + + &[trigger="end"] { + width: var(--dropped-offset-end); + } + } } diff --git a/projects/ngx-scrollbar/src/lib/tests/dropped-events.spec.ts b/projects/ngx-scrollbar/src/lib/tests/dropped-events.spec.ts new file mode 100644 index 00000000..f94d1606 --- /dev/null +++ b/projects/ngx-scrollbar/src/lib/tests/dropped-events.spec.ts @@ -0,0 +1,137 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; +import { Component, ViewChild } from '@angular/core'; +import { BidiModule } from '@angular/cdk/bidi'; +import { NgScrollbar, NgScrollbarModule } from 'ngx-scrollbar'; +import { NgScrollDropped } from 'ngx-scrollbar/reached-event'; + +@Component({ + template: ` + +
+
+ `, + standalone: true, + imports: [BidiModule, NgScrollbarModule, NgScrollDropped] +}) +class TestComponent { + offset: number; + topOffset: number; + bottomOffset: number; + startOffset: number; + endOffset: number; + isRtl: boolean = false; + disabled: boolean = false; + + @ViewChild(NgScrollbar, { static: true }) scrollbar: NgScrollbar; + + onScrollDropped(value: string): void { + console.log(value); + } +} + +describe('Dropped Events Directives', () => { + let fixture: ComponentFixture; + let component: TestComponent; + let onScrollDroppedSpy: jasmine.Spy; + + beforeEach(() => { + fixture = TestBed.createComponent(TestComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + onScrollDroppedSpy = spyOn(component, 'onScrollDropped'); + }); + + it('[DroppedOffset]: should emit (droppedTop) (droppedBottom) (droppedStart) (droppedEnd)', async () => { + component.offset = 10; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ top: 0, duration: 0 }); + await component.scrollbar.scrollTo({ top: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('top'); + await component.scrollbar.scrollTo({ bottom: 0, duration: 0 }); + await component.scrollbar.scrollTo({ bottom: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('bottom'); + await component.scrollbar.scrollTo({ end: 0, duration: 0 }); + await component.scrollbar.scrollTo({ end: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('end'); + await component.scrollbar.scrollTo({ start: 0, duration: 0 }); + await component.scrollbar.scrollTo({ start: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('start'); + }); + + it('[DroppedTopEvent]: should emit (droppedTop)', async () => { + component.topOffset = 10; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ top: 0, duration: 0 }); + await component.scrollbar.scrollTo({ top: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('top'); + }); + + it('[DroppedBottomEvent]: should emit (droppedBottom)', async () => { + component.bottomOffset = 10; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ bottom: 0, duration: 0 }); + await component.scrollbar.scrollTo({ bottom: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('bottom'); + }); + + it('[DroppedStartEvent]: should emit (droppedStart)', async () => { + component.startOffset = 10; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ start: 0, duration: 0 }); + await component.scrollbar.scrollTo({ start: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('start'); + }); + + it('[DroppedEndEvent]: should emit (droppedEnd)', async () => { + component.endOffset = 10; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ end: 0, duration: 0 }); + await component.scrollbar.scrollTo({ end: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('end'); + }); + + it('[DroppedStartEvent]: should emit (droppedStart) in RTL mode', async () => { + component.startOffset = 10; + component.isRtl = true; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ start: 0, duration: 0 }); + await component.scrollbar.scrollTo({ start: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('start'); + }); + + it('[DroppedEndEvent]: should emit (droppedEnd) in RTL mode', async () => { + component.endOffset = 10; + component.isRtl = true; + fixture.detectChanges(); + + await component.scrollbar.scrollTo({ end: 0, duration: 0 }); + await component.scrollbar.scrollTo({ end: 11, duration: 50 }); + expect(onScrollDroppedSpy).toHaveBeenCalledWith('end'); + }); + + + it('[reachDisabled]: should not emit when scroll is dropped destination', async () => { + component.disabled = true; + fixture.detectChanges(); + await component.scrollbar.scrollTo({ bottom: 0, duration: 0 }); + await component.scrollbar.scrollTo({ bottom: 11, duration: 50 }); + expect(onScrollDroppedSpy).not.toHaveBeenCalledWith('bottom'); + }); +}); diff --git a/projects/ngx-scrollbar/src/lib/tests/reached-events.spec.ts b/projects/ngx-scrollbar/src/lib/tests/reached-events.spec.ts index 22b54ebd..121ecea1 100644 --- a/projects/ngx-scrollbar/src/lib/tests/reached-events.spec.ts +++ b/projects/ngx-scrollbar/src/lib/tests/reached-events.spec.ts @@ -2,7 +2,7 @@ import { ComponentFixture, TestBed } from '@angular/core/testing'; import { Component, ViewChild } from '@angular/core'; import { BidiModule } from '@angular/cdk/bidi'; import { NgScrollbar, NgScrollbarModule } from 'ngx-scrollbar'; -import { NgScrollbarReachedModule } from 'ngx-scrollbar/reached-event'; +import { NgScrollReached } from 'ngx-scrollbar/reached-event'; @Component({ template: ` @@ -22,7 +22,7 @@ import { NgScrollbarReachedModule } from 'ngx-scrollbar/reached-event'; `, standalone: true, - imports: [BidiModule, NgScrollbarModule, NgScrollbarReachedModule] + imports: [BidiModule, NgScrollbarModule, NgScrollReached] }) class TestComponent { offset: number; diff --git a/projects/ngx-scrollbar/src/lib/tests/visibility.spec.ts b/projects/ngx-scrollbar/src/lib/tests/visibility.spec.ts index 2608e780..51fba101 100644 --- a/projects/ngx-scrollbar/src/lib/tests/visibility.spec.ts +++ b/projects/ngx-scrollbar/src/lib/tests/visibility.spec.ts @@ -75,7 +75,6 @@ describe('Visibility styles', () => { it('[Visibility] should be able to override styles related to scrollbar track using CSS variables', async () => { setDimensions(component, { cmpWidth: 100, cmpHeight: 100, contentWidth: 100, contentHeight: 200 }); // Override track color and transition using CSS variables - component.nativeElement.style.setProperty('--scrollbar-track-transition', 'height 0.66s linear, width 0.33s linear'); component.nativeElement.style.setProperty('--scrollbar-track-color', 'red'); component.ngOnInit(); component.ngAfterViewInit(); @@ -84,7 +83,6 @@ describe('Visibility styles', () => { const trackDebugElement: DebugElement = fixture.debugElement.query(By.directive(TrackYDirective)); const trackStyles: CSSStyleDeclaration = getComputedStyle(trackDebugElement.nativeElement); - expect(trackStyles.transition).toBe('height 0.66s linear 0s, width 0.33s linear 0s'); expect(trackStyles.backgroundColor).toBe('rgb(255, 0, 0)'); }); diff --git a/projects/ngx-scrollbar/src/lib/thumb/thumb.ts b/projects/ngx-scrollbar/src/lib/thumb/thumb.ts index 582a3896..6da4d569 100644 --- a/projects/ngx-scrollbar/src/lib/thumb/thumb.ts +++ b/projects/ngx-scrollbar/src/lib/thumb/thumb.ts @@ -13,7 +13,7 @@ export class ThumbXDirective extends ThumbAdapter { } get size(): number { - return this.clientRect.width; + return this.nativeElement.offsetWidth; } protected get dragStartOffset(): number { @@ -33,7 +33,7 @@ export class ThumbYDirective extends ThumbAdapter { } get size(): number { - return this.clientRect.height; + return this.nativeElement.offsetHeight; } protected get dragStartOffset(): number { diff --git a/projects/ngx-scrollbar/src/lib/track/track.ts b/projects/ngx-scrollbar/src/lib/track/track.ts index c6877f78..3b35aef8 100644 --- a/projects/ngx-scrollbar/src/lib/track/track.ts +++ b/projects/ngx-scrollbar/src/lib/track/track.ts @@ -17,7 +17,7 @@ export class TrackXDirective extends TrackAdapter { } get size(): number { - return this.clientRect.width; + return this.nativeElement.offsetWidth; } protected get viewportScrollSize(): number { @@ -104,7 +104,7 @@ export class TrackYDirective extends TrackAdapter { } get size(): number { - return this.clientRect.height; + return this.nativeElement.offsetHeight; } protected get viewportScrollSize(): number { diff --git a/projects/ngx-scrollbar/src/lib/viewport/viewport-adapter.ts b/projects/ngx-scrollbar/src/lib/viewport/viewport-adapter.ts index 8b6e4806..b9f8feae 100644 --- a/projects/ngx-scrollbar/src/lib/viewport/viewport-adapter.ts +++ b/projects/ngx-scrollbar/src/lib/viewport/viewport-adapter.ts @@ -20,12 +20,12 @@ export class ViewportAdapter { /** Viewport clientHeight */ get offsetHeight(): number { - return this.nativeElement.getBoundingClientRect().height; + return this.nativeElement.offsetHeight; } /** Viewport clientWidth */ get offsetWidth(): number { - return this.nativeElement.getBoundingClientRect().width; + return this.nativeElement.offsetWidth; } /** Viewport scrollTop */ @@ -40,12 +40,12 @@ export class ViewportAdapter { /** Content height, falls back to scroll height */ get contentHeight(): number { - return this.contentWrapperElement.getBoundingClientRect().height; + return this.contentWrapperElement.offsetHeight; } /** Content width, falls back to scroll height */ get contentWidth(): number { - return this.contentWrapperElement.getBoundingClientRect().width; + return this.contentWrapperElement.offsetWidth; } /** The horizontal remaining scrollable distance */ diff --git a/projects/ngx-scrollbar/utils/src/mat-select-viewport.ts b/projects/ngx-scrollbar/utils/src/mat-select-viewport.ts index 4644a690..9d954d8e 100644 --- a/projects/ngx-scrollbar/utils/src/mat-select-viewport.ts +++ b/projects/ngx-scrollbar/utils/src/mat-select-viewport.ts @@ -4,9 +4,9 @@ import { _NgScrollbar, NG_SCROLLBAR } from 'ngx-scrollbar'; @Directive({ standalone: true, - selector: 'ng-scrollbar[matSelectViewport], ng-scrollbar[mat-select-viewport]' + selector: 'ng-scrollbar[matSelectViewport]' }) -export class MatSelectViewport { +export class NgScrollbarMatSelectViewport { private readonly scrollbar: _NgScrollbar = inject(NG_SCROLLBAR);