@ngbase/adk 0.1.17 → 0.1.19
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/fesm2022/ngbase-adk-a11y.mjs +42 -42
- package/fesm2022/ngbase-adk-a11y.mjs.map +1 -1
- package/fesm2022/ngbase-adk-accordion.mjs +20 -26
- package/fesm2022/ngbase-adk-accordion.mjs.map +1 -1
- package/fesm2022/ngbase-adk-autocomplete.mjs +11 -11
- package/fesm2022/ngbase-adk-autocomplete.mjs.map +1 -1
- package/fesm2022/ngbase-adk-avatar.mjs +13 -13
- package/fesm2022/ngbase-adk-avatar.mjs.map +1 -1
- package/fesm2022/ngbase-adk-bidi.mjs +3 -3
- package/fesm2022/ngbase-adk-bidi.mjs.map +1 -1
- package/fesm2022/ngbase-adk-breadcrumb.mjs +14 -14
- package/fesm2022/ngbase-adk-breadcrumb.mjs.map +1 -1
- package/fesm2022/ngbase-adk-cache.mjs +3 -3
- package/fesm2022/ngbase-adk-cache.mjs.map +1 -1
- package/fesm2022/ngbase-adk-carousel.mjs +18 -18
- package/fesm2022/ngbase-adk-carousel.mjs.map +1 -1
- package/fesm2022/ngbase-adk-checkbox.mjs +15 -21
- package/fesm2022/ngbase-adk-checkbox.mjs.map +1 -1
- package/fesm2022/ngbase-adk-chip.mjs +12 -12
- package/fesm2022/ngbase-adk-chip.mjs.map +1 -1
- package/fesm2022/ngbase-adk-clipboard.mjs +7 -5
- package/fesm2022/ngbase-adk-clipboard.mjs.map +1 -1
- package/fesm2022/ngbase-adk-collections.mjs.map +1 -1
- package/fesm2022/ngbase-adk-color-picker.mjs +44 -53
- package/fesm2022/ngbase-adk-color-picker.mjs.map +1 -1
- package/fesm2022/ngbase-adk-cookies.mjs +3 -3
- package/fesm2022/ngbase-adk-cookies.mjs.map +1 -1
- package/fesm2022/ngbase-adk-datepicker.mjs +70 -89
- package/fesm2022/ngbase-adk-datepicker.mjs.map +1 -1
- package/fesm2022/ngbase-adk-dialog.mjs +17 -39
- package/fesm2022/ngbase-adk-dialog.mjs.map +1 -1
- package/fesm2022/ngbase-adk-drag.mjs +20 -20
- package/fesm2022/ngbase-adk-drag.mjs.map +1 -1
- package/fesm2022/ngbase-adk-form-field.mjs +65 -118
- package/fesm2022/ngbase-adk-form-field.mjs.map +1 -1
- package/fesm2022/ngbase-adk-hover-card.mjs +5 -5
- package/fesm2022/ngbase-adk-hover-card.mjs.map +1 -1
- package/fesm2022/ngbase-adk-icon.mjs +9 -11
- package/fesm2022/ngbase-adk-icon.mjs.map +1 -1
- package/fesm2022/ngbase-adk-inline-edit.mjs +27 -35
- package/fesm2022/ngbase-adk-inline-edit.mjs.map +1 -1
- package/fesm2022/ngbase-adk-jwt.mjs +6 -6
- package/fesm2022/ngbase-adk-jwt.mjs.map +1 -1
- package/fesm2022/ngbase-adk-keys.mjs +6 -6
- package/fesm2022/ngbase-adk-keys.mjs.map +1 -1
- package/fesm2022/ngbase-adk-layout.mjs.map +1 -1
- package/fesm2022/ngbase-adk-list.mjs +10 -10
- package/fesm2022/ngbase-adk-list.mjs.map +1 -1
- package/fesm2022/ngbase-adk-mask.mjs +8 -8
- package/fesm2022/ngbase-adk-mask.mjs.map +1 -1
- package/fesm2022/ngbase-adk-menu.mjs +69 -79
- package/fesm2022/ngbase-adk-menu.mjs.map +1 -1
- package/fesm2022/ngbase-adk-network.mjs +3 -3
- package/fesm2022/ngbase-adk-network.mjs.map +1 -1
- package/fesm2022/ngbase-adk-otp.mjs +24 -45
- package/fesm2022/ngbase-adk-otp.mjs.map +1 -1
- package/fesm2022/ngbase-adk-pagination.mjs +9 -9
- package/fesm2022/ngbase-adk-pagination.mjs.map +1 -1
- package/fesm2022/ngbase-adk-popover.mjs +120 -89
- package/fesm2022/ngbase-adk-popover.mjs.map +1 -1
- package/fesm2022/ngbase-adk-portal.mjs +139 -47
- package/fesm2022/ngbase-adk-portal.mjs.map +1 -1
- package/fesm2022/ngbase-adk-progress.mjs +7 -7
- package/fesm2022/ngbase-adk-progress.mjs.map +1 -1
- package/fesm2022/ngbase-adk-radio.mjs +20 -27
- package/fesm2022/ngbase-adk-radio.mjs.map +1 -1
- package/fesm2022/ngbase-adk-resizable.mjs +138 -48
- package/fesm2022/ngbase-adk-resizable.mjs.map +1 -1
- package/fesm2022/ngbase-adk-scroll-area.mjs +28 -20
- package/fesm2022/ngbase-adk-scroll-area.mjs.map +1 -1
- package/fesm2022/ngbase-adk-select.mjs +58 -80
- package/fesm2022/ngbase-adk-select.mjs.map +1 -1
- package/fesm2022/ngbase-adk-selectable.mjs +19 -30
- package/fesm2022/ngbase-adk-selectable.mjs.map +1 -1
- package/fesm2022/ngbase-adk-sheet.mjs +6 -20
- package/fesm2022/ngbase-adk-sheet.mjs.map +1 -1
- package/fesm2022/ngbase-adk-sidenav.mjs +65 -48
- package/fesm2022/ngbase-adk-sidenav.mjs.map +1 -1
- package/fesm2022/ngbase-adk-slider.mjs +40 -53
- package/fesm2022/ngbase-adk-slider.mjs.map +1 -1
- package/fesm2022/ngbase-adk-sonner.mjs +12 -19
- package/fesm2022/ngbase-adk-sonner.mjs.map +1 -1
- package/fesm2022/ngbase-adk-stepper.mjs +17 -25
- package/fesm2022/ngbase-adk-stepper.mjs.map +1 -1
- package/fesm2022/ngbase-adk-switch.mjs +25 -32
- package/fesm2022/ngbase-adk-switch.mjs.map +1 -1
- package/fesm2022/ngbase-adk-table.mjs +581 -83
- package/fesm2022/ngbase-adk-table.mjs.map +1 -1
- package/fesm2022/ngbase-adk-tabs.mjs +37 -35
- package/fesm2022/ngbase-adk-tabs.mjs.map +1 -1
- package/fesm2022/ngbase-adk-test.mjs.map +1 -1
- package/fesm2022/ngbase-adk-toggle-group.mjs +20 -34
- package/fesm2022/ngbase-adk-toggle-group.mjs.map +1 -1
- package/fesm2022/ngbase-adk-toggle.mjs +14 -19
- package/fesm2022/ngbase-adk-toggle.mjs.map +1 -1
- package/fesm2022/ngbase-adk-tooltip.mjs +12 -19
- package/fesm2022/ngbase-adk-tooltip.mjs.map +1 -1
- package/fesm2022/ngbase-adk-tour.mjs +47 -52
- package/fesm2022/ngbase-adk-tour.mjs.map +1 -1
- package/fesm2022/ngbase-adk-translate.mjs +8 -10
- package/fesm2022/ngbase-adk-translate.mjs.map +1 -1
- package/fesm2022/ngbase-adk-tree.mjs +20 -20
- package/fesm2022/ngbase-adk-tree.mjs.map +1 -1
- package/fesm2022/ngbase-adk-utils.mjs +30 -43
- package/fesm2022/ngbase-adk-utils.mjs.map +1 -1
- package/fesm2022/ngbase-adk-virtualizer.mjs +9 -9
- package/fesm2022/ngbase-adk-virtualizer.mjs.map +1 -1
- package/package.json +101 -101
- package/schematics/components/files/accordion/accordion.ts.template +10 -5
- package/schematics/components/files/audio/AudioPlayer.ts.template +245 -0
- package/schematics/components/files/audio/AudioRecorder.ts.template +377 -0
- package/schematics/components/files/audio/AudioVisualizer.ts.template +175 -0
- package/schematics/components/files/audio/index.ts.template +3 -0
- package/schematics/components/files/badge/badge-llm.md.template +2 -2
- package/schematics/components/files/badge/badge.ts.template +29 -9
- package/schematics/components/files/card/card.ts.template +1 -1
- package/schematics/components/files/charts/area-chart.component.ts.template +278 -0
- package/schematics/components/files/charts/bar-chart.component.ts.template +262 -0
- package/schematics/components/files/charts/chart-tooltip.component.ts.template +168 -0
- package/schematics/components/files/charts/index.ts.template +4 -0
- package/schematics/components/files/charts/line-chart.component.ts.template +238 -0
- package/schematics/components/files/charts/pie-chart.component.ts.template +283 -0
- package/schematics/components/files/checkbox/checkbox.ts.template +4 -7
- package/schematics/components/files/color-picker/color-picker.ts.template +2 -2
- package/schematics/components/files/dialog/dialog.ts.template +11 -14
- package/schematics/components/files/drawer/drawer.ts.template +25 -28
- package/schematics/components/files/form-field/form-field.ts.template +59 -23
- package/schematics/components/files/inline-edit/inline-edit.ts.template +3 -1
- package/schematics/components/files/pagination/pagination.ts.template +6 -6
- package/schematics/components/files/picasa/picasa-base.component.ts.template +9 -30
- package/schematics/components/files/popover/popover.ts.template +9 -4
- package/schematics/components/files/select/list-selection.ts.template +0 -2
- package/schematics/components/files/select/option.ts.template +1 -1
- package/schematics/components/files/selectable/selectable.ts.template +2 -2
- package/schematics/components/files/sheet/sheet.ts.template +20 -14
- package/schematics/components/files/sidenav/sidenav.ts.template +69 -6
- package/schematics/components/files/sonner/sonner.ts.template +1 -2
- package/schematics/components/files/stepper/stepper-llm.md.template +7 -0
- package/schematics/components/files/stepper/stepper.ts.template +2 -4
- package/schematics/components/files/switch/switch.ts.template +2 -2
- package/schematics/components/files/table/table-llm.md.template +14 -2
- package/schematics/components/files/table/table.ts.template +42 -3
- package/schematics/components/files/theme/theme.service.ts.template +3 -3
- package/schematics/components/files/toggle/toggle.ts.template +1 -1
- package/schematics/components/files/toggle-group/toggle-group.ts.template +1 -1
- package/schematics/components/files/tooltip/tooltip.ts.template +2 -3
- package/{accordion/index.d.ts → types/ngbase-adk-accordion.d.ts} +1 -3
- package/{autocomplete/index.d.ts → types/ngbase-adk-autocomplete.d.ts} +2 -7
- package/{checkbox/index.d.ts → types/ngbase-adk-checkbox.d.ts} +8 -14
- package/types/ngbase-adk-clipboard.d.ts +12 -0
- package/{color-picker/index.d.ts → types/ngbase-adk-color-picker.d.ts} +14 -26
- package/{datepicker/index.d.ts → types/ngbase-adk-datepicker.d.ts} +9 -18
- package/{dialog/index.d.ts → types/ngbase-adk-dialog.d.ts} +3 -8
- package/types/ngbase-adk-form-field.d.ts +88 -0
- package/{inline-edit/index.d.ts → types/ngbase-adk-inline-edit.d.ts} +8 -16
- package/{menu/index.d.ts → types/ngbase-adk-menu.d.ts} +6 -5
- package/{otp/index.d.ts → types/ngbase-adk-otp.d.ts} +8 -16
- package/{popover/index.d.ts → types/ngbase-adk-popover.d.ts} +14 -2
- package/{portal/index.d.ts → types/ngbase-adk-portal.d.ts} +30 -8
- package/{radio/index.d.ts → types/ngbase-adk-radio.d.ts} +9 -12
- package/{resizable/index.d.ts → types/ngbase-adk-resizable.d.ts} +4 -4
- package/{scroll-area/index.d.ts → types/ngbase-adk-scroll-area.d.ts} +2 -1
- package/{select/index.d.ts → types/ngbase-adk-select.d.ts} +8 -22
- package/{selectable/index.d.ts → types/ngbase-adk-selectable.d.ts} +6 -10
- package/{sheet/index.d.ts → types/ngbase-adk-sheet.d.ts} +4 -3
- package/{sidenav/index.d.ts → types/ngbase-adk-sidenav.d.ts} +7 -8
- package/{slider/index.d.ts → types/ngbase-adk-slider.d.ts} +8 -17
- package/{sonner/index.d.ts → types/ngbase-adk-sonner.d.ts} +1 -3
- package/{stepper/index.d.ts → types/ngbase-adk-stepper.d.ts} +1 -4
- package/{switch/index.d.ts → types/ngbase-adk-switch.d.ts} +7 -14
- package/{table/index.d.ts → types/ngbase-adk-table.d.ts} +126 -3
- package/{test/index.d.ts → types/ngbase-adk-test.d.ts} +1 -1
- package/{toggle-group/index.d.ts → types/ngbase-adk-toggle-group.d.ts} +5 -10
- package/types/ngbase-adk-toggle.d.ts +14 -0
- package/{tooltip/index.d.ts → types/ngbase-adk-tooltip.d.ts} +9 -11
- package/{tour/index.d.ts → types/ngbase-adk-tour.d.ts} +3 -6
- package/{utils/index.d.ts → types/ngbase-adk-utils.d.ts} +15 -11
- package/clipboard/index.d.ts +0 -11
- package/form-field/index.d.ts +0 -97
- package/toggle/index.d.ts +0 -16
- /package/{a11y/index.d.ts → types/ngbase-adk-a11y.d.ts} +0 -0
- /package/{avatar/index.d.ts → types/ngbase-adk-avatar.d.ts} +0 -0
- /package/{bidi/index.d.ts → types/ngbase-adk-bidi.d.ts} +0 -0
- /package/{breadcrumb/index.d.ts → types/ngbase-adk-breadcrumb.d.ts} +0 -0
- /package/{cache/index.d.ts → types/ngbase-adk-cache.d.ts} +0 -0
- /package/{carousel/index.d.ts → types/ngbase-adk-carousel.d.ts} +0 -0
- /package/{chip/index.d.ts → types/ngbase-adk-chip.d.ts} +0 -0
- /package/{collections/index.d.ts → types/ngbase-adk-collections.d.ts} +0 -0
- /package/{cookies/index.d.ts → types/ngbase-adk-cookies.d.ts} +0 -0
- /package/{drag/index.d.ts → types/ngbase-adk-drag.d.ts} +0 -0
- /package/{hover-card/index.d.ts → types/ngbase-adk-hover-card.d.ts} +0 -0
- /package/{icon/index.d.ts → types/ngbase-adk-icon.d.ts} +0 -0
- /package/{jwt/index.d.ts → types/ngbase-adk-jwt.d.ts} +0 -0
- /package/{keys/index.d.ts → types/ngbase-adk-keys.d.ts} +0 -0
- /package/{layout/index.d.ts → types/ngbase-adk-layout.d.ts} +0 -0
- /package/{list/index.d.ts → types/ngbase-adk-list.d.ts} +0 -0
- /package/{mask/index.d.ts → types/ngbase-adk-mask.d.ts} +0 -0
- /package/{network/index.d.ts → types/ngbase-adk-network.d.ts} +0 -0
- /package/{pagination/index.d.ts → types/ngbase-adk-pagination.d.ts} +0 -0
- /package/{progress/index.d.ts → types/ngbase-adk-progress.d.ts} +0 -0
- /package/{tabs/index.d.ts → types/ngbase-adk-tabs.d.ts} +0 -0
- /package/{translate/index.d.ts → types/ngbase-adk-translate.d.ts} +0 -0
- /package/{tree/index.d.ts → types/ngbase-adk-tree.d.ts} +0 -0
- /package/{virtualizer/index.d.ts → types/ngbase-adk-virtualizer.d.ts} +0 -0
- /package/{index.d.ts → types/ngbase-adk.d.ts} +0 -0
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ngbase-adk-jwt.mjs","sources":["../../../projects/adk/jwt/jwt.service.ts","../../../projects/adk/jwt/token-refresh.ts","../../../projects/adk/jwt/token-guard.ts","../../../projects/adk/jwt/ngbase-adk-jwt.ts"],"sourcesContent":["import { HttpEvent, HttpHandler, HttpInterceptor, HttpRequest } from '@angular/common/http';\nimport {\n computed,\n inject,\n Injectable,\n InjectionToken,\n makeEnvironmentProviders,\n signal,\n} from '@angular/core';\nimport { Observable } from 'rxjs';\n\n// injectiontoken for getting the token\nconst JWT_OPTIONS = new InjectionToken<JwtOptions>('JWT_OPTIONS');\n\ninterface JwtOptions {\n tokenGetter: () => string | null | undefined;\n tokenSetter?: (token: string | null) => void;\n refreshTokenGetter?: () => string | null | undefined;\n refreshTokenSetter?: (token: string | null) => void;\n}\n\nexport function provideJwt(options: () => JwtOptions) {\n return makeEnvironmentProviders([\n { provide: JWT_OPTIONS, useFactory: options },\n { provide: JwtInterceptor, useClass: JwtInterceptor },\n ]);\n}\n\nclass TokenHandler<T = any> {\n readonly _token = signal<string | null>(null);\n readonly token = this._token.asReadonly();\n\n readonly decoded = computed<T | null>(() => {\n const tokenValue = this._token();\n if (!tokenValue) return null;\n\n try {\n const payload = tokenValue.split('.')[1];\n return JSON.parse(this.base64UrlDecode(payload));\n } catch (e) {\n console.error('Error decoding token', e);\n return null;\n }\n });\n\n readonly exp = computed<number | null>(() => {\n const decodedToken = this.decoded() as T extends { exp: number } ? T : null;\n return decodedToken?.exp || null;\n });\n\n readonly expirationDate = computed<Date | null>(() => {\n const exp = this.exp();\n if (!exp) return null;\n\n const date = new Date(0);\n date.setUTCSeconds(exp);\n return date;\n });\n\n readonly isExpired = () => {\n const expiry = this.expirationDate();\n const ise = expiry ? expiry <= new Date() : true;\n return ise;\n };\n\n constructor(\n private storageKey: string,\n private tokenGetter?: () => string | null | undefined,\n private tokenSetter?: (token: string | null) => void,\n ) {\n const initialToken = this.tokenGetter?.() ?? localStorage.getItem(this.storageKey);\n this._token.set(initialToken);\n }\n\n setToken(token: string | null): void {\n if (this.tokenSetter) {\n this.tokenSetter(token);\n } else {\n if (token) {\n localStorage.setItem(this.storageKey, token);\n } else {\n localStorage.removeItem(this.storageKey);\n }\n }\n this._token.set(token);\n }\n\n private base64UrlDecode(input: string): string {\n input = input.replace(/-/g, '+').replace(/_/g, '/');\n while (input.length % 4) {\n input += '=';\n }\n return atob(input);\n }\n}\n\n@Injectable({ providedIn: 'root' })\nexport class JwtService<T> {\n private options = inject(JWT_OPTIONS, { optional: true });\n\n private accessTokenKey = 'access_token';\n private refreshTokenKey = 'refresh_token';\n\n private _accessToken = new TokenHandler<T>(\n this.accessTokenKey,\n this.options?.tokenGetter,\n this.options?.tokenSetter,\n );\n private _refreshToken = new TokenHandler<T>(\n this.refreshTokenKey,\n this.options?.refreshTokenGetter,\n this.options?.refreshTokenSetter,\n );\n\n getAccessToken = this._accessToken.token;\n\n getRefreshToken = this._refreshToken.token;\n\n setTokens(accessToken: string, refreshToken: string): void {\n this._accessToken.setToken(accessToken);\n this._refreshToken.setToken(refreshToken);\n }\n\n clearTokens(): void {\n this._accessToken.setToken(null);\n this._refreshToken.setToken(null);\n }\n\n isAccessTokenExpired = this._accessToken.isExpired;\n\n isRefreshTokenExpired = this._refreshToken.isExpired;\n\n isAccessTokenNearExpiry(minutesBeforeExpiry: number = 5): boolean {\n const token = this.getAccessToken();\n if (!token) return true;\n\n const expiry = this.getTokenExpirationDate();\n if (!expiry) return true;\n\n console.log('minutesBeforeExpiry ', minutesBeforeExpiry);\n const bufferTime = new Date(Date.now() + 0.5 * 60 * 1000);\n return expiry <= bufferTime;\n }\n\n decodeToken = this._accessToken.decoded;\n\n getTokenExpirationDate = this._accessToken.expirationDate;\n}\n\n// jwt interceptor\n@Injectable({ providedIn: 'root' })\nexport class JwtInterceptor implements HttpInterceptor {\n constructor(private jwtService: JwtService<any>) {}\n\n intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {\n const token = this.jwtService.getAccessToken();\n if (token) {\n req = req.clone({\n setHeaders: { Authorization: `Bearer ${token}` },\n });\n }\n return next.handle(req);\n }\n}\n\nexport const injectJwt = <T>() => inject<JwtService<T>>(JwtService);\n","import { BehaviorSubject, Observable, throwError, of } from 'rxjs';\nimport { catchError, tap, switchMap } from 'rxjs/operators';\nimport { injectJwt } from './jwt.service';\n\nexport class TokenRefreshService<T> {\n private jwt = injectJwt();\n private refreshSubject = new BehaviorSubject<T | null>(null);\n private isRefreshing = false;\n\n /**\n * Returns an observable that emits when refresh completes\n */\n getRefreshStatus$ = this.refreshSubject.asObservable();\n\n constructor(private refreshApi: () => Observable<T>) {}\n\n /**\n * Attempts to refresh the access token using the refresh token\n * @returns Observable with new token pair\n */\n refreshToken(): Observable<T | null> {\n const refreshToken = this.jwt.getRefreshToken();\n if (!refreshToken) {\n return throwError(() => new Error('No refresh token available'));\n }\n\n if (this.isRefreshing) {\n // If already refreshing, wait for the refresh to complete\n return this.refreshSubject.asObservable();\n }\n\n this.isRefreshing = true;\n this.refreshSubject.next(null);\n\n return this.refreshApi().pipe(\n tap(res => {\n this.isRefreshing = false;\n this.refreshSubject.next(res);\n }),\n catchError(error => {\n this.isRefreshing = false;\n this.refreshSubject.next(null);\n\n // Clear tokens on refresh failure\n this.jwt.clearTokens();\n\n return throwError(() => error);\n }),\n );\n }\n\n /**\n * Checks if a refresh operation is currently in progress\n */\n isTokenRefreshing(): boolean {\n return this.isRefreshing;\n }\n\n /**\n * Proactively refresh token if it's expired or near expiry\n * @param minutesBeforeExpiry How many minutes before expiry to refresh (default: 5)\n * @returns Observable that emits true if refresh was needed and successful, false if not needed\n */\n refreshIfNeeded(minutesBeforeExpiry: number = 5): Observable<boolean> {\n if (this.jwt.isRefreshTokenExpired()) {\n // Refresh token is expired, clear tokens and reject\n this.jwt.clearTokens();\n return throwError(() => new Error('Refresh token expired'));\n }\n\n if (this.jwt.isAccessTokenExpired() || this.jwt.isAccessTokenNearExpiry(minutesBeforeExpiry)) {\n // Need to refresh\n return this.refreshToken().pipe(\n switchMap(() => of(true)), // Return true to indicate refresh was performed\n catchError(error => throwError(() => error)),\n );\n }\n\n // No refresh needed\n return of(false);\n }\n}\n","import { Observable, of } from 'rxjs';\nimport { map, catchError, switchMap, filter, take } from 'rxjs/operators';\nimport { TokenRefreshService } from './token-refresh';\nimport { injectJwt } from './jwt.service';\n\n/**\n * Centralized authentication service for guards and interceptors\n * Handles token validation and refresh logic consistently\n */\nexport class TokenGuardHelper {\n private readonly tokenRefreshService: TokenRefreshService<any>;\n private readonly jwt = injectJwt();\n\n constructor(\n private refreshApi: () => Observable<any>,\n private logout: () => void,\n ) {\n this.tokenRefreshService = new TokenRefreshService(this.refreshApi);\n }\n\n /**\n * Checks if user is authenticated, handles token refresh if needed\n * Returns Observable<boolean> - true if authenticated, false if should redirect to login\n */\n checkAuthentication = (): Observable<boolean> => {\n // Check if we have basic tokens\n const accessToken = this.jwt.getAccessToken();\n const refreshToken = this.jwt.getRefreshToken();\n\n if (!accessToken || !refreshToken) {\n console.log('AuthGuard: No tokens available, redirecting to login');\n return of(false);\n }\n\n // Check if refresh token is expired\n if (this.jwt.isRefreshTokenExpired()) {\n console.warn('AuthGuard: Refresh token is expired, clearing tokens');\n this.logout();\n return of(false);\n }\n\n // If access token is valid, allow access\n if (!this.jwt.isAccessTokenExpired() && !this.jwt.isAccessTokenNearExpiry(5)) {\n console.log('AuthGuard: Access token is valid, allowing access');\n return of(true);\n }\n\n // Access token is expired or near expiry, need to refresh\n console.log('AuthGuard: Access token expired or near expiry, attempting refresh');\n\n // Check if already refreshing\n if (this.tokenRefreshService.isTokenRefreshing()) {\n console.log('AuthGuard: Token refresh already in progress, waiting...');\n return this.tokenRefreshService.getRefreshStatus$.pipe(\n filter(refreshed => refreshed === true),\n take(1),\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken && !this.jwt.isAccessTokenExpired()) {\n console.log('AuthGuard: Token refresh completed successfully');\n return true;\n } else {\n console.warn('AuthGuard: No valid token after refresh completion');\n return false;\n }\n }),\n catchError(error => {\n console.error('AuthGuard: Failed to wait for token refresh:', error);\n return of(false);\n }),\n );\n }\n\n // Start token refresh\n return this.tokenRefreshService.refreshToken().pipe(\n map(() => {\n if (!this.jwt.isAccessTokenExpired()) {\n console.log('AuthGuard: Token refresh successful');\n return true;\n } else {\n console.warn('AuthGuard: Invalid refresh response or token still expired');\n return false;\n }\n }),\n catchError(refreshError => {\n console.warn('AuthGuard: Token refresh failed:', refreshError);\n this.logout();\n return of(false);\n }),\n );\n };\n\n /**\n * Enhanced authentication check with automatic retry\n * Attempts refresh once, then falls back to login redirect\n */\n ensureAuthenticated = (): Observable<boolean> => {\n return this.checkAuthentication().pipe(\n switchMap(isAuthenticated => {\n if (isAuthenticated) {\n return of(true);\n }\n\n // If not authenticated after refresh attempt, redirect to login\n console.log('AuthGuard: Authentication failed, redirecting to login');\n this.logout();\n return of(false);\n }),\n );\n };\n\n /**\n * Quick synchronous check for authentication status\n * Use this only when you don't need token refresh\n */\n isQuickAuthenticated = (): boolean => {\n const accessToken = this.jwt.getAccessToken();\n const refreshToken = this.jwt.getRefreshToken();\n\n if (!accessToken || !refreshToken) return false;\n if (this.jwt.isRefreshTokenExpired()) return false;\n if (this.jwt.isAccessTokenExpired()) return false;\n\n return true;\n };\n\n /**\n * Validates and refreshes token for HTTP requests\n * Returns Observable<string> with valid access token or throws error\n * Used by interceptors\n */\n getValidAccessToken = (): Observable<string> => {\n // Check if we have tokens\n const accessToken = this.jwt.getAccessToken();\n\n if (!accessToken) {\n console.warn('Interceptor: No access token available');\n this.logout();\n throw new Error('No access token available');\n }\n\n // Check if refresh token is expired\n if (this.jwt.isRefreshTokenExpired()) {\n console.warn('Interceptor: Refresh token is expired, redirecting to login');\n this.logout();\n throw new Error('Refresh token expired');\n }\n\n // If access token is valid, return it\n if (!this.jwt.isAccessTokenExpired() && !this.jwt.isAccessTokenNearExpiry(5)) {\n return of(accessToken);\n }\n\n // Access token needs refresh\n console.log('Interceptor: Access token expired or near expiry, refreshing proactively');\n\n // Check if already refreshing\n if (this.tokenRefreshService.isTokenRefreshing()) {\n return this.tokenRefreshService.getRefreshStatus$.pipe(\n filter(refreshed => refreshed === true),\n take(1),\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken) {\n return newToken;\n } else {\n this.logout();\n throw new Error('Failed to get new access token');\n }\n }),\n catchError(error => {\n console.error('Interceptor: Failed to wait for token refresh:', error);\n this.logout();\n throw error;\n }),\n );\n }\n\n // Start token refresh\n return this.tokenRefreshService.refreshToken().pipe(\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken) {\n return newToken;\n } else {\n this.logout();\n throw new Error('Invalid refresh response');\n }\n }),\n catchError(refreshError => {\n console.warn('Interceptor: Token refresh failed:', refreshError);\n this.logout();\n throw refreshError;\n }),\n );\n };\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"ngbase-adk-jwt.mjs","sources":["../../../projects/adk/jwt/jwt.service.ts","../../../projects/adk/jwt/token-refresh.ts","../../../projects/adk/jwt/token-guard.ts","../../../projects/adk/jwt/ngbase-adk-jwt.ts"],"sourcesContent":["import { HttpEvent, HttpHandler, HttpInterceptor, HttpRequest } from '@angular/common/http';\nimport {\n computed,\n inject,\n Injectable,\n InjectionToken,\n makeEnvironmentProviders,\n signal,\n} from '@angular/core';\nimport { Observable } from 'rxjs';\n\n// injectiontoken for getting the token\nconst JWT_OPTIONS = new InjectionToken<JwtOptions>('JWT_OPTIONS');\n\ninterface JwtOptions {\n tokenGetter: () => string | null | undefined;\n tokenSetter?: (token: string | null) => void;\n refreshTokenGetter?: () => string | null | undefined;\n refreshTokenSetter?: (token: string | null) => void;\n}\n\nexport function provideJwt(options: () => JwtOptions) {\n return makeEnvironmentProviders([\n { provide: JWT_OPTIONS, useFactory: options },\n { provide: JwtInterceptor, useClass: JwtInterceptor },\n ]);\n}\n\nclass TokenHandler<T = any> {\n readonly _token = signal<string | null>(null);\n readonly token = this._token.asReadonly();\n\n readonly decoded = computed<T | null>(() => {\n const tokenValue = this._token();\n if (!tokenValue) return null;\n\n try {\n const payload = tokenValue.split('.')[1];\n return JSON.parse(this.base64UrlDecode(payload));\n } catch (e) {\n console.error('Error decoding token', e);\n return null;\n }\n });\n\n readonly exp = computed<number | null>(() => {\n const decodedToken = this.decoded() as T extends { exp: number } ? T : null;\n return decodedToken?.exp || null;\n });\n\n readonly expirationDate = computed<Date | null>(() => {\n const exp = this.exp();\n if (!exp) return null;\n\n const date = new Date(0);\n date.setUTCSeconds(exp);\n return date;\n });\n\n readonly isExpired = () => {\n const expiry = this.expirationDate();\n const ise = expiry ? expiry <= new Date() : true;\n return ise;\n };\n\n constructor(\n private storageKey: string,\n private tokenGetter?: () => string | null | undefined,\n private tokenSetter?: (token: string | null) => void,\n ) {\n const initialToken = this.tokenGetter?.() ?? localStorage.getItem(this.storageKey);\n this._token.set(initialToken);\n }\n\n setToken(token: string | null): void {\n if (this.tokenSetter) {\n this.tokenSetter(token);\n } else {\n if (token) {\n localStorage.setItem(this.storageKey, token);\n } else {\n localStorage.removeItem(this.storageKey);\n }\n }\n this._token.set(token);\n }\n\n private base64UrlDecode(input: string): string {\n input = input.replace(/-/g, '+').replace(/_/g, '/');\n while (input.length % 4) {\n input += '=';\n }\n return atob(input);\n }\n}\n\n@Injectable({ providedIn: 'root' })\nexport class JwtService<T> {\n private options = inject(JWT_OPTIONS, { optional: true });\n\n private accessTokenKey = 'access_token';\n private refreshTokenKey = 'refresh_token';\n\n private _accessToken = new TokenHandler<T>(\n this.accessTokenKey,\n this.options?.tokenGetter,\n this.options?.tokenSetter,\n );\n private _refreshToken = new TokenHandler<T>(\n this.refreshTokenKey,\n this.options?.refreshTokenGetter,\n this.options?.refreshTokenSetter,\n );\n\n getAccessToken = this._accessToken.token;\n\n getRefreshToken = this._refreshToken.token;\n\n setTokens(accessToken: string, refreshToken: string): void {\n this._accessToken.setToken(accessToken);\n this._refreshToken.setToken(refreshToken);\n }\n\n clearTokens(): void {\n this._accessToken.setToken(null);\n this._refreshToken.setToken(null);\n }\n\n isAccessTokenExpired = this._accessToken.isExpired;\n\n isRefreshTokenExpired = this._refreshToken.isExpired;\n\n isAccessTokenNearExpiry(minutesBeforeExpiry: number = 5): boolean {\n const token = this.getAccessToken();\n if (!token) return true;\n\n const expiry = this.getTokenExpirationDate();\n if (!expiry) return true;\n\n console.log('minutesBeforeExpiry ', minutesBeforeExpiry);\n const bufferTime = new Date(Date.now() + 0.5 * 60 * 1000);\n return expiry <= bufferTime;\n }\n\n decodeToken = this._accessToken.decoded;\n\n getTokenExpirationDate = this._accessToken.expirationDate;\n}\n\n// jwt interceptor\n@Injectable({ providedIn: 'root' })\nexport class JwtInterceptor implements HttpInterceptor {\n constructor(private jwtService: JwtService<any>) {}\n\n intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {\n const token = this.jwtService.getAccessToken();\n if (token) {\n req = req.clone({\n setHeaders: { Authorization: `Bearer ${token}` },\n });\n }\n return next.handle(req);\n }\n}\n\nexport const injectJwt = <T>() => inject<JwtService<T>>(JwtService);\n","import { BehaviorSubject, Observable, throwError, of } from 'rxjs';\nimport { catchError, tap, switchMap } from 'rxjs/operators';\nimport { injectJwt } from './jwt.service';\n\nexport class TokenRefreshService<T> {\n private jwt = injectJwt();\n private refreshSubject = new BehaviorSubject<T | null>(null);\n private isRefreshing = false;\n\n /**\n * Returns an observable that emits when refresh completes\n */\n getRefreshStatus$ = this.refreshSubject.asObservable();\n\n constructor(private refreshApi: () => Observable<T>) {}\n\n /**\n * Attempts to refresh the access token using the refresh token\n * @returns Observable with new token pair\n */\n refreshToken(): Observable<T | null> {\n const refreshToken = this.jwt.getRefreshToken();\n if (!refreshToken) {\n return throwError(() => new Error('No refresh token available'));\n }\n\n if (this.isRefreshing) {\n // If already refreshing, wait for the refresh to complete\n return this.refreshSubject.asObservable();\n }\n\n this.isRefreshing = true;\n this.refreshSubject.next(null);\n\n return this.refreshApi().pipe(\n tap(res => {\n this.isRefreshing = false;\n this.refreshSubject.next(res);\n }),\n catchError(error => {\n this.isRefreshing = false;\n this.refreshSubject.next(null);\n\n // Clear tokens on refresh failure\n this.jwt.clearTokens();\n\n return throwError(() => error);\n }),\n );\n }\n\n /**\n * Checks if a refresh operation is currently in progress\n */\n isTokenRefreshing(): boolean {\n return this.isRefreshing;\n }\n\n /**\n * Proactively refresh token if it's expired or near expiry\n * @param minutesBeforeExpiry How many minutes before expiry to refresh (default: 5)\n * @returns Observable that emits true if refresh was needed and successful, false if not needed\n */\n refreshIfNeeded(minutesBeforeExpiry: number = 5): Observable<boolean> {\n if (this.jwt.isRefreshTokenExpired()) {\n // Refresh token is expired, clear tokens and reject\n this.jwt.clearTokens();\n return throwError(() => new Error('Refresh token expired'));\n }\n\n if (this.jwt.isAccessTokenExpired() || this.jwt.isAccessTokenNearExpiry(minutesBeforeExpiry)) {\n // Need to refresh\n return this.refreshToken().pipe(\n switchMap(() => of(true)), // Return true to indicate refresh was performed\n catchError(error => throwError(() => error)),\n );\n }\n\n // No refresh needed\n return of(false);\n }\n}\n","import { Observable, of } from 'rxjs';\nimport { map, catchError, switchMap, filter, take } from 'rxjs/operators';\nimport { TokenRefreshService } from './token-refresh';\nimport { injectJwt } from './jwt.service';\n\n/**\n * Centralized authentication service for guards and interceptors\n * Handles token validation and refresh logic consistently\n */\nexport class TokenGuardHelper {\n private readonly tokenRefreshService: TokenRefreshService<any>;\n private readonly jwt = injectJwt();\n\n constructor(\n private refreshApi: () => Observable<any>,\n private logout: () => void,\n ) {\n this.tokenRefreshService = new TokenRefreshService(this.refreshApi);\n }\n\n /**\n * Checks if user is authenticated, handles token refresh if needed\n * Returns Observable<boolean> - true if authenticated, false if should redirect to login\n */\n checkAuthentication = (): Observable<boolean> => {\n // Check if we have basic tokens\n const accessToken = this.jwt.getAccessToken();\n const refreshToken = this.jwt.getRefreshToken();\n\n if (!accessToken || !refreshToken) {\n console.log('AuthGuard: No tokens available, redirecting to login');\n return of(false);\n }\n\n // Check if refresh token is expired\n if (this.jwt.isRefreshTokenExpired()) {\n console.warn('AuthGuard: Refresh token is expired, clearing tokens');\n this.logout();\n return of(false);\n }\n\n // If access token is valid, allow access\n if (!this.jwt.isAccessTokenExpired() && !this.jwt.isAccessTokenNearExpiry(5)) {\n console.log('AuthGuard: Access token is valid, allowing access');\n return of(true);\n }\n\n // Access token is expired or near expiry, need to refresh\n console.log('AuthGuard: Access token expired or near expiry, attempting refresh');\n\n // Check if already refreshing\n if (this.tokenRefreshService.isTokenRefreshing()) {\n console.log('AuthGuard: Token refresh already in progress, waiting...');\n return this.tokenRefreshService.getRefreshStatus$.pipe(\n filter(refreshed => refreshed === true),\n take(1),\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken && !this.jwt.isAccessTokenExpired()) {\n console.log('AuthGuard: Token refresh completed successfully');\n return true;\n } else {\n console.warn('AuthGuard: No valid token after refresh completion');\n return false;\n }\n }),\n catchError(error => {\n console.error('AuthGuard: Failed to wait for token refresh:', error);\n return of(false);\n }),\n );\n }\n\n // Start token refresh\n return this.tokenRefreshService.refreshToken().pipe(\n map(() => {\n if (!this.jwt.isAccessTokenExpired()) {\n console.log('AuthGuard: Token refresh successful');\n return true;\n } else {\n console.warn('AuthGuard: Invalid refresh response or token still expired');\n return false;\n }\n }),\n catchError(refreshError => {\n console.warn('AuthGuard: Token refresh failed:', refreshError);\n this.logout();\n return of(false);\n }),\n );\n };\n\n /**\n * Enhanced authentication check with automatic retry\n * Attempts refresh once, then falls back to login redirect\n */\n ensureAuthenticated = (): Observable<boolean> => {\n return this.checkAuthentication().pipe(\n switchMap(isAuthenticated => {\n if (isAuthenticated) {\n return of(true);\n }\n\n // If not authenticated after refresh attempt, redirect to login\n console.log('AuthGuard: Authentication failed, redirecting to login');\n this.logout();\n return of(false);\n }),\n );\n };\n\n /**\n * Quick synchronous check for authentication status\n * Use this only when you don't need token refresh\n */\n isQuickAuthenticated = (): boolean => {\n const accessToken = this.jwt.getAccessToken();\n const refreshToken = this.jwt.getRefreshToken();\n\n if (!accessToken || !refreshToken) return false;\n if (this.jwt.isRefreshTokenExpired()) return false;\n if (this.jwt.isAccessTokenExpired()) return false;\n\n return true;\n };\n\n /**\n * Validates and refreshes token for HTTP requests\n * Returns Observable<string> with valid access token or throws error\n * Used by interceptors\n */\n getValidAccessToken = (): Observable<string> => {\n // Check if we have tokens\n const accessToken = this.jwt.getAccessToken();\n\n if (!accessToken) {\n console.warn('Interceptor: No access token available');\n this.logout();\n throw new Error('No access token available');\n }\n\n // Check if refresh token is expired\n if (this.jwt.isRefreshTokenExpired()) {\n console.warn('Interceptor: Refresh token is expired, redirecting to login');\n this.logout();\n throw new Error('Refresh token expired');\n }\n\n // If access token is valid, return it\n if (!this.jwt.isAccessTokenExpired() && !this.jwt.isAccessTokenNearExpiry(5)) {\n return of(accessToken);\n }\n\n // Access token needs refresh\n console.log('Interceptor: Access token expired or near expiry, refreshing proactively');\n\n // Check if already refreshing\n if (this.tokenRefreshService.isTokenRefreshing()) {\n return this.tokenRefreshService.getRefreshStatus$.pipe(\n filter(refreshed => refreshed === true),\n take(1),\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken) {\n return newToken;\n } else {\n this.logout();\n throw new Error('Failed to get new access token');\n }\n }),\n catchError(error => {\n console.error('Interceptor: Failed to wait for token refresh:', error);\n this.logout();\n throw error;\n }),\n );\n }\n\n // Start token refresh\n return this.tokenRefreshService.refreshToken().pipe(\n map(() => {\n const newToken = this.jwt.getAccessToken();\n if (newToken) {\n return newToken;\n } else {\n this.logout();\n throw new Error('Invalid refresh response');\n }\n }),\n catchError(refreshError => {\n console.warn('Interceptor: Token refresh failed:', refreshError);\n this.logout();\n throw refreshError;\n }),\n );\n };\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
@@ -44,10 +44,10 @@ class Keys {
|
|
|
44
44
|
isKey(key) {
|
|
45
45
|
return this.keys.has(key);
|
|
46
46
|
}
|
|
47
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
48
|
-
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "
|
|
47
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Keys, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
48
|
+
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Keys, providedIn: 'root' }); }
|
|
49
49
|
}
|
|
50
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
50
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Keys, decorators: [{
|
|
51
51
|
type: Injectable,
|
|
52
52
|
args: [{ providedIn: 'root' }]
|
|
53
53
|
}] });
|
|
@@ -181,10 +181,10 @@ class Shortcuts {
|
|
|
181
181
|
this.keydown.on();
|
|
182
182
|
}
|
|
183
183
|
}
|
|
184
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
185
|
-
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "
|
|
184
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Shortcuts, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
185
|
+
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Shortcuts, providedIn: 'root' }); }
|
|
186
186
|
}
|
|
187
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
187
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Shortcuts, decorators: [{
|
|
188
188
|
type: Injectable,
|
|
189
189
|
args: [{
|
|
190
190
|
providedIn: 'root',
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ngbase-adk-keys.mjs","sources":["../../../projects/adk/keys/keys.service.ts","../../../projects/adk/keys/shortcuts.service.ts","../../../projects/adk/keys/public-api.ts","../../../projects/adk/keys/ngbase-adk-keys.ts"],"sourcesContent":["import { Injectable, inject, DOCUMENT } from '@angular/core';\nimport { fromEvent, merge, distinctUntilKeyChanged, filter, finalize, map, share, tap } from 'rxjs';\n\n@Injectable({ providedIn: 'root' })\nexport class Keys {\n private document = inject(DOCUMENT);\n private keyup$ = fromEvent<KeyboardEvent>(this.document, 'keyup');\n private keydown$ = fromEvent<KeyboardEvent>(this.document, 'keydown');\n private keypress$ = merge(this.keyup$, this.keydown$).pipe(\n tap(ev => {\n if (ev.type === 'keyup') {\n this.keys.delete(ev.key);\n } else {\n this.keys.add(ev.key);\n }\n this.lastEvent = ev;\n }),\n finalize(() => {\n // we have to clear the keys when there is no subscriber\n // because keyup is not considered on last unsubscribe\n this.keys.clear();\n }),\n share(),\n );\n\n lastEvent?: KeyboardEvent;\n\n private keys = new Set<string>();\n\n event(keyCombination: string) {\n keyCombination = [\n ['ctrl', 'Control'],\n ['esc', 'Escape'],\n ].reduce((a, [b, B]) => a.replace(b, B), keyCombination);\n const keys = keyCombination.split('+');\n let isFirstTrueValue = false;\n\n return this.keypress$.pipe(\n map<KeyboardEvent, [boolean, KeyboardEvent]>(ev => {\n // make sure key combination and number of keys should be same\n const isLengthSame = this.keys.size === keys.length;\n // check all the keys are matching\n const isAllKeysSame = [...this.keys].every(k => keys.includes(k));\n const active = isLengthSame && isAllKeysSame;\n\n isFirstTrueValue = isFirstTrueValue || active;\n return [active, ev];\n }),\n filter(() => isFirstTrueValue), //skipValues until positive value comes\n distinctUntilKeyChanged(0), // avoid duplicate values emitting\n );\n }\n\n isKey(key: string) {\n return this.keys.has(key);\n }\n}\n","import { DestroyRef, inject, Injectable, Injector, runInInjectionContext } from '@angular/core';\nimport { documentListener, isClient, uniqueId } from '@ngbase/adk/utils';\n\nconst IGNORED_TAGS = ['INPUT', 'TEXTAREA', 'SELECT'];\nconst SHORTCUT_MAP: Record<string, string> = {\n '⇧': 'shift',\n '⌥': 'alt',\n '⌃': 'ctrl',\n '⌘': 'meta',\n '⏎': 'enter',\n esc: 'escape',\n};\n\n// prettier-ignore\nconst SPECIAL_KEYS = new Set([\n 'ArrowLeft', 'ArrowRight', 'ArrowUp', 'ArrowDown',\n 'Enter', 'Escape', 'Tab', 'Backspace', 'Delete',\n 'Home', 'End', 'PageUp', 'PageDown',\n 'F1', 'F2', 'F3', 'F4', 'F5', 'F6', 'F7', 'F8', 'F9', 'F10', 'F11', 'F12'\n]);\n\ninterface Shortcut {\n callback: (ev: KeyboardEvent) => void;\n prevent: boolean;\n stop: boolean;\n global: boolean;\n id: string;\n}\n\n@Injectable({\n providedIn: 'root',\n})\nexport class Shortcuts {\n private readonly shortcuts = new Map<string, Shortcut[]>();\n private isActive = false;\n private isClient = isClient();\n\n on(keyCombination: string, data: Shortcut): void {\n const parsedKey = this.getParsedKey(keyCombination);\n for (const key of parsedKey) {\n const shortcuts = this.shortcuts.get(key) || [];\n shortcuts.push(data);\n this.shortcuts.set(key, shortcuts);\n }\n this.turnOn();\n }\n\n off(keyCombination: string, id: string): void {\n const parsedKey = this.getParsedKey(keyCombination);\n for (const key of parsedKey) {\n const shortcuts = this.shortcuts.get(key);\n if (shortcuts) {\n const index = shortcuts.findIndex(s => s.id === id);\n if (index > -1) {\n shortcuts.splice(index, 1);\n }\n if (shortcuts.length === 0) {\n this.shortcuts.delete(key);\n }\n }\n }\n this.turnOff();\n }\n\n /**\n * We need to parse the key combination\n * e.g. ⇧⌘P -> shift+meta+p, ⌥⌘P -> meta+alt+p, ctrl+p -> ctrl+p\n * e.g. esc|prevent|stop|global -> escape\n */\n private getParsedKey(combination: string): string[] {\n const baseSplit = combination.split('|');\n return baseSplit.map(split => {\n const keys = split.split('+');\n const parsedKeys = keys.map(key => {\n // Check if the key is a special character in our map\n if (SHORTCUT_MAP[key]) {\n return SHORTCUT_MAP[key];\n }\n\n // If it's a special key, return it as is (case-sensitive)\n if (SPECIAL_KEYS.has(key)) {\n return key;\n }\n // If not found in the map or special keys, return the lowercase key\n return key.toLowerCase();\n });\n return parsedKeys.join('+');\n });\n }\n\n private handleKeyEvent = (event: KeyboardEvent): void => {\n const key = this.getKeyCombo(event);\n const data = this.shortcuts.get(key);\n if (!data) {\n return;\n }\n let i = data.length;\n while (i--) {\n const item = data[i];\n if (item.global && this.shouldIgnoreEvent(event)) {\n return;\n }\n\n if (item.callback) {\n if (item.prevent) {\n event.preventDefault();\n }\n if (item.stop) {\n event.stopPropagation();\n }\n item.callback(event);\n if (item.stop) {\n break;\n }\n }\n }\n };\n private keydown = documentListener('keydown', this.handleKeyEvent, { lazy: true });\n\n private shouldIgnoreEvent(event: KeyboardEvent): boolean {\n const target = event.target as HTMLElement;\n\n return (\n IGNORED_TAGS.includes(target.tagName) ||\n target.isContentEditable ||\n target.getAttribute('role') === 'textbox'\n );\n }\n\n private getKeyCombo(event: KeyboardEvent): string {\n const modifiers = [];\n\n if (event.ctrlKey) modifiers.push('ctrl');\n if (event.altKey) modifiers.push('alt');\n if (event.shiftKey) modifiers.push('shift');\n if (event.metaKey) modifiers.push('meta');\n\n const key = event.key?.toLowerCase();\n return [...modifiers, ...(key ? [key] : [])].join('+');\n }\n\n private turnOff() {\n if (this.isClient && this.shortcuts.size === 0 && this.isActive) {\n this.isActive = false;\n this.keydown.off();\n }\n }\n\n private turnOn() {\n if (this.isClient && this.shortcuts.size > 0 && !this.isActive) {\n this.isActive = true;\n this.keydown.on();\n }\n }\n}\n\nexport function keyMap(\n key: string,\n callback: (ev: KeyboardEvent) => void,\n data?: {\n injector?: Injector;\n cleanup?: (off: () => void) => void;\n stop?: boolean;\n global?: boolean;\n prevent?: boolean;\n },\n) {\n const { injector, cleanup, stop = false, global = false, prevent = true } = data || {};\n return runInInjectionContext(injector || inject(Injector), () => {\n const shortcuts = inject(Shortcuts);\n const onDestroy = inject(DestroyRef);\n const id = uniqueId();\n\n shortcuts.on(key, { callback, prevent, stop, global, id });\n\n const off = () => {\n shortcuts.off(key, id);\n };\n\n onDestroy?.onDestroy(off);\n cleanup?.(off);\n return off;\n });\n}\n","/*\n * Public API Surface of keys\n */\n\nexport { Keys } from './keys.service';\nexport { keyMap, Shortcuts } from './shortcuts.service';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":";;;;;MAIa,IAAI,CAAA;AADjB,IAAA,WAAA,GAAA;AAEU,QAAA,IAAA,CAAA,QAAQ,GAAG,MAAM,CAAC,QAAQ,CAAC;QAC3B,IAAM,CAAA,MAAA,GAAG,SAAS,CAAgB,IAAI,CAAC,QAAQ,EAAE,OAAO,CAAC;QACzD,IAAQ,CAAA,QAAA,GAAG,SAAS,CAAgB,IAAI,CAAC,QAAQ,EAAE,SAAS,CAAC;AAC7D,QAAA,IAAA,CAAA,SAAS,GAAG,KAAK,CAAC,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC,IAAI,CACxD,GAAG,CAAC,EAAE,IAAG;AACP,YAAA,IAAI,EAAE,CAAC,IAAI,KAAK,OAAO,EAAE;gBACvB,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,GAAG,CAAC;;iBACnB;gBACL,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,CAAC;;AAEvB,YAAA,IAAI,CAAC,SAAS,GAAG,EAAE;AACrB,SAAC,CAAC,EACF,QAAQ,CAAC,MAAK;;;AAGZ,YAAA,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE;AACnB,SAAC,CAAC,EACF,KAAK,EAAE,CACR;AAIO,QAAA,IAAA,CAAA,IAAI,GAAG,IAAI,GAAG,EAAU;AA6BjC;AA3BC,IAAA,KAAK,CAAC,cAAsB,EAAA;AAC1B,QAAA,cAAc,GAAG;YACf,CAAC,MAAM,EAAE,SAAS,CAAC;YACnB,CAAC,KAAK,EAAE,QAAQ,CAAC;SAClB,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,cAAc,CAAC;QACxD,MAAM,IAAI,GAAG,cAAc,CAAC,KAAK,CAAC,GAAG,CAAC;QACtC,IAAI,gBAAgB,GAAG,KAAK;QAE5B,OAAO,IAAI,CAAC,SAAS,CAAC,IAAI,CACxB,GAAG,CAA0C,EAAE,IAAG;;YAEhD,MAAM,YAAY,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,KAAK,IAAI,CAAC,MAAM;;YAEnD,MAAM,aAAa,GAAG,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,KAAK,CAAC,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;AACjE,YAAA,MAAM,MAAM,GAAG,YAAY,IAAI,aAAa;AAE5C,YAAA,gBAAgB,GAAG,gBAAgB,IAAI,MAAM;AAC7C,YAAA,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC;SACpB,CAAC,EACF,MAAM,CAAC,MAAM,gBAAgB,CAAC;AAC9B,QAAA,uBAAuB,CAAC,CAAC,CAAC,CAC3B;;AAGH,IAAA,KAAK,CAAC,GAAW,EAAA;QACf,OAAO,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC;;8GAlDhB,IAAI,EAAA,IAAA,EAAA,EAAA,EAAA,MAAA,EAAA,EAAA,CAAA,eAAA,CAAA,UAAA,EAAA,CAAA,CAAA;AAAJ,IAAA,SAAA,IAAA,CAAA,KAAA,GAAA,EAAA,CAAA,qBAAA,CAAA,EAAA,UAAA,EAAA,QAAA,EAAA,OAAA,EAAA,QAAA,EAAA,QAAA,EAAA,EAAA,EAAA,IAAA,EAAA,IAAI,cADS,MAAM,EAAA,CAAA,CAAA;;2FACnB,IAAI,EAAA,UAAA,EAAA,CAAA;kBADhB,UAAU;mBAAC,EAAE,UAAU,EAAE,MAAM,EAAE;;;ACAlC,MAAM,YAAY,GAAG,CAAC,OAAO,EAAE,UAAU,EAAE,QAAQ,CAAC;AACpD,MAAM,YAAY,GAA2B;AAC3C,IAAA,GAAG,EAAE,OAAO;AACZ,IAAA,GAAG,EAAE,KAAK;AACV,IAAA,GAAG,EAAE,MAAM;AACX,IAAA,GAAG,EAAE,MAAM;AACX,IAAA,GAAG,EAAE,OAAO;AACZ,IAAA,GAAG,EAAE,QAAQ;CACd;AAED;AACA,MAAM,YAAY,GAAG,IAAI,GAAG,CAAC;AAC3B,IAAA,WAAW,EAAE,YAAY,EAAE,SAAS,EAAE,WAAW;AACjD,IAAA,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE,WAAW,EAAE,QAAQ;AAC/C,IAAA,MAAM,EAAE,KAAK,EAAE,QAAQ,EAAE,UAAU;IACnC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE;AACrE,CAAA,CAAC;MAaW,SAAS,CAAA;AAHtB,IAAA,WAAA,GAAA;AAImB,QAAA,IAAA,CAAA,SAAS,GAAG,IAAI,GAAG,EAAsB;QAClD,IAAQ,CAAA,QAAA,GAAG,KAAK;QAChB,IAAQ,CAAA,QAAA,GAAG,QAAQ,EAAE;AAuDrB,QAAA,IAAA,CAAA,cAAc,GAAG,CAAC,KAAoB,KAAU;YACtD,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC;YACnC,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC;YACpC,IAAI,CAAC,IAAI,EAAE;gBACT;;AAEF,YAAA,IAAI,CAAC,GAAG,IAAI,CAAC,MAAM;YACnB,OAAO,CAAC,EAAE,EAAE;AACV,gBAAA,MAAM,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC;gBACpB,IAAI,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,iBAAiB,CAAC,KAAK,CAAC,EAAE;oBAChD;;AAGF,gBAAA,IAAI,IAAI,CAAC,QAAQ,EAAE;AACjB,oBAAA,IAAI,IAAI,CAAC,OAAO,EAAE;wBAChB,KAAK,CAAC,cAAc,EAAE;;AAExB,oBAAA,IAAI,IAAI,CAAC,IAAI,EAAE;wBACb,KAAK,CAAC,eAAe,EAAE;;AAEzB,oBAAA,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC;AACpB,oBAAA,IAAI,IAAI,CAAC,IAAI,EAAE;wBACb;;;;AAIR,SAAC;AACO,QAAA,IAAA,CAAA,OAAO,GAAG,gBAAgB,CAAC,SAAS,EAAE,IAAI,CAAC,cAAc,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;AAqCnF;IArHC,EAAE,CAAC,cAAsB,EAAE,IAAc,EAAA;QACvC,MAAM,SAAS,GAAG,IAAI,CAAC,YAAY,CAAC,cAAc,CAAC;AACnD,QAAA,KAAK,MAAM,GAAG,IAAI,SAAS,EAAE;AAC3B,YAAA,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,EAAE;AAC/C,YAAA,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC;YACpB,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,EAAE,SAAS,CAAC;;QAEpC,IAAI,CAAC,MAAM,EAAE;;IAGf,GAAG,CAAC,cAAsB,EAAE,EAAU,EAAA;QACpC,MAAM,SAAS,GAAG,IAAI,CAAC,YAAY,CAAC,cAAc,CAAC;AACnD,QAAA,KAAK,MAAM,GAAG,IAAI,SAAS,EAAE;YAC3B,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC;YACzC,IAAI,SAAS,EAAE;AACb,gBAAA,MAAM,KAAK,GAAG,SAAS,CAAC,SAAS,CAAC,CAAC,IAAI,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC;AACnD,gBAAA,IAAI,KAAK,GAAG,CAAC,CAAC,EAAE;AACd,oBAAA,SAAS,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC,CAAC;;AAE5B,gBAAA,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE;AAC1B,oBAAA,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,GAAG,CAAC;;;;QAIhC,IAAI,CAAC,OAAO,EAAE;;AAGhB;;;;AAIG;AACK,IAAA,YAAY,CAAC,WAAmB,EAAA;QACtC,MAAM,SAAS,GAAG,WAAW,CAAC,KAAK,CAAC,GAAG,CAAC;AACxC,QAAA,OAAO,SAAS,CAAC,GAAG,CAAC,KAAK,IAAG;YAC3B,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC;YAC7B,MAAM,UAAU,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,IAAG;;AAEhC,gBAAA,IAAI,YAAY,CAAC,GAAG,CAAC,EAAE;AACrB,oBAAA,OAAO,YAAY,CAAC,GAAG,CAAC;;;AAI1B,gBAAA,IAAI,YAAY,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE;AACzB,oBAAA,OAAO,GAAG;;;AAGZ,gBAAA,OAAO,GAAG,CAAC,WAAW,EAAE;AAC1B,aAAC,CAAC;AACF,YAAA,OAAO,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC;AAC7B,SAAC,CAAC;;AAgCI,IAAA,iBAAiB,CAAC,KAAoB,EAAA;AAC5C,QAAA,MAAM,MAAM,GAAG,KAAK,CAAC,MAAqB;QAE1C,QACE,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC;AACrC,YAAA,MAAM,CAAC,iBAAiB;YACxB,MAAM,CAAC,YAAY,CAAC,MAAM,CAAC,KAAK,SAAS;;AAIrC,IAAA,WAAW,CAAC,KAAoB,EAAA;QACtC,MAAM,SAAS,GAAG,EAAE;QAEpB,IAAI,KAAK,CAAC,OAAO;AAAE,YAAA,SAAS,CAAC,IAAI,CAAC,MAAM,CAAC;QACzC,IAAI,KAAK,CAAC,MAAM;AAAE,YAAA,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC;QACvC,IAAI,KAAK,CAAC,QAAQ;AAAE,YAAA,SAAS,CAAC,IAAI,CAAC,OAAO,CAAC;QAC3C,IAAI,KAAK,CAAC,OAAO;AAAE,YAAA,SAAS,CAAC,IAAI,CAAC,MAAM,CAAC;QAEzC,MAAM,GAAG,GAAG,KAAK,CAAC,GAAG,EAAE,WAAW,EAAE;QACpC,OAAO,CAAC,GAAG,SAAS,EAAE,IAAI,GAAG,GAAG,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC;;IAGhD,OAAO,GAAA;AACb,QAAA,IAAI,IAAI,CAAC,QAAQ,IAAI,IAAI,CAAC,SAAS,CAAC,IAAI,KAAK,CAAC,IAAI,IAAI,CAAC,QAAQ,EAAE;AAC/D,YAAA,IAAI,CAAC,QAAQ,GAAG,KAAK;AACrB,YAAA,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE;;;IAId,MAAM,GAAA;AACZ,QAAA,IAAI,IAAI,CAAC,QAAQ,IAAI,IAAI,CAAC,SAAS,CAAC,IAAI,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE;AAC9D,YAAA,IAAI,CAAC,QAAQ,GAAG,IAAI;AACpB,YAAA,IAAI,CAAC,OAAO,CAAC,EAAE,EAAE;;;8GAvHV,SAAS,EAAA,IAAA,EAAA,EAAA,EAAA,MAAA,EAAA,EAAA,CAAA,eAAA,CAAA,UAAA,EAAA,CAAA,CAAA;AAAT,IAAA,SAAA,IAAA,CAAA,KAAA,GAAA,EAAA,CAAA,qBAAA,CAAA,EAAA,UAAA,EAAA,QAAA,EAAA,OAAA,EAAA,QAAA,EAAA,QAAA,EAAA,EAAA,EAAA,IAAA,EAAA,SAAS,cAFR,MAAM,EAAA,CAAA,CAAA;;2FAEP,SAAS,EAAA,UAAA,EAAA,CAAA;kBAHrB,UAAU;AAAC,YAAA,IAAA,EAAA,CAAA;AACV,oBAAA,UAAU,EAAE,MAAM;AACnB,iBAAA;;SA6He,MAAM,CACpB,GAAW,EACX,QAAqC,EACrC,IAMC,EAAA;IAED,MAAM,EAAE,QAAQ,EAAE,OAAO,EAAE,IAAI,GAAG,KAAK,EAAE,MAAM,GAAG,KAAK,EAAE,OAAO,GAAG,IAAI,EAAE,GAAG,IAAI,IAAI,EAAE;IACtF,OAAO,qBAAqB,CAAC,QAAQ,IAAI,MAAM,CAAC,QAAQ,CAAC,EAAE,MAAK;AAC9D,QAAA,MAAM,SAAS,GAAG,MAAM,CAAC,SAAS,CAAC;AACnC,QAAA,MAAM,SAAS,GAAG,MAAM,CAAC,UAAU,CAAC;AACpC,QAAA,MAAM,EAAE,GAAG,QAAQ,EAAE;AAErB,QAAA,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,EAAE,QAAQ,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;QAE1D,MAAM,GAAG,GAAG,MAAK;AACf,YAAA,SAAS,CAAC,GAAG,CAAC,GAAG,EAAE,EAAE,CAAC;AACxB,SAAC;AAED,QAAA,SAAS,EAAE,SAAS,CAAC,GAAG,CAAC;AACzB,QAAA,OAAO,GAAG,GAAG,CAAC;AACd,QAAA,OAAO,GAAG;AACZ,KAAC,CAAC;AACJ;;ACvLA;;AAEG;;ACFH;;AAEG;;;;"}
|
|
1
|
+
{"version":3,"file":"ngbase-adk-keys.mjs","sources":["../../../projects/adk/keys/keys.service.ts","../../../projects/adk/keys/shortcuts.service.ts","../../../projects/adk/keys/public-api.ts","../../../projects/adk/keys/ngbase-adk-keys.ts"],"sourcesContent":["import { Injectable, inject, DOCUMENT } from '@angular/core';\nimport { fromEvent, merge, distinctUntilKeyChanged, filter, finalize, map, share, tap } from 'rxjs';\n\n@Injectable({ providedIn: 'root' })\nexport class Keys {\n private document = inject(DOCUMENT);\n private keyup$ = fromEvent<KeyboardEvent>(this.document, 'keyup');\n private keydown$ = fromEvent<KeyboardEvent>(this.document, 'keydown');\n private keypress$ = merge(this.keyup$, this.keydown$).pipe(\n tap(ev => {\n if (ev.type === 'keyup') {\n this.keys.delete(ev.key);\n } else {\n this.keys.add(ev.key);\n }\n this.lastEvent = ev;\n }),\n finalize(() => {\n // we have to clear the keys when there is no subscriber\n // because keyup is not considered on last unsubscribe\n this.keys.clear();\n }),\n share(),\n );\n\n lastEvent?: KeyboardEvent;\n\n private keys = new Set<string>();\n\n event(keyCombination: string) {\n keyCombination = [\n ['ctrl', 'Control'],\n ['esc', 'Escape'],\n ].reduce((a, [b, B]) => a.replace(b, B), keyCombination);\n const keys = keyCombination.split('+');\n let isFirstTrueValue = false;\n\n return this.keypress$.pipe(\n map<KeyboardEvent, [boolean, KeyboardEvent]>(ev => {\n // make sure key combination and number of keys should be same\n const isLengthSame = this.keys.size === keys.length;\n // check all the keys are matching\n const isAllKeysSame = [...this.keys].every(k => keys.includes(k));\n const active = isLengthSame && isAllKeysSame;\n\n isFirstTrueValue = isFirstTrueValue || active;\n return [active, ev];\n }),\n filter(() => isFirstTrueValue), //skipValues until positive value comes\n distinctUntilKeyChanged(0), // avoid duplicate values emitting\n );\n }\n\n isKey(key: string) {\n return this.keys.has(key);\n }\n}\n","import { DestroyRef, inject, Injectable, Injector, runInInjectionContext } from '@angular/core';\nimport { documentListener, isClient, uniqueId } from '@ngbase/adk/utils';\n\nconst IGNORED_TAGS = ['INPUT', 'TEXTAREA', 'SELECT'];\nconst SHORTCUT_MAP: Record<string, string> = {\n '⇧': 'shift',\n '⌥': 'alt',\n '⌃': 'ctrl',\n '⌘': 'meta',\n '⏎': 'enter',\n esc: 'escape',\n};\n\n// prettier-ignore\nconst SPECIAL_KEYS = new Set([\n 'ArrowLeft', 'ArrowRight', 'ArrowUp', 'ArrowDown',\n 'Enter', 'Escape', 'Tab', 'Backspace', 'Delete',\n 'Home', 'End', 'PageUp', 'PageDown',\n 'F1', 'F2', 'F3', 'F4', 'F5', 'F6', 'F7', 'F8', 'F9', 'F10', 'F11', 'F12'\n]);\n\ninterface Shortcut {\n callback: (ev: KeyboardEvent) => void;\n prevent: boolean;\n stop: boolean;\n global: boolean;\n id: string;\n}\n\n@Injectable({\n providedIn: 'root',\n})\nexport class Shortcuts {\n private readonly shortcuts = new Map<string, Shortcut[]>();\n private isActive = false;\n private isClient = isClient();\n\n on(keyCombination: string, data: Shortcut): void {\n const parsedKey = this.getParsedKey(keyCombination);\n for (const key of parsedKey) {\n const shortcuts = this.shortcuts.get(key) || [];\n shortcuts.push(data);\n this.shortcuts.set(key, shortcuts);\n }\n this.turnOn();\n }\n\n off(keyCombination: string, id: string): void {\n const parsedKey = this.getParsedKey(keyCombination);\n for (const key of parsedKey) {\n const shortcuts = this.shortcuts.get(key);\n if (shortcuts) {\n const index = shortcuts.findIndex(s => s.id === id);\n if (index > -1) {\n shortcuts.splice(index, 1);\n }\n if (shortcuts.length === 0) {\n this.shortcuts.delete(key);\n }\n }\n }\n this.turnOff();\n }\n\n /**\n * We need to parse the key combination\n * e.g. ⇧⌘P -> shift+meta+p, ⌥⌘P -> meta+alt+p, ctrl+p -> ctrl+p\n * e.g. esc|prevent|stop|global -> escape\n */\n private getParsedKey(combination: string): string[] {\n const baseSplit = combination.split('|');\n return baseSplit.map(split => {\n const keys = split.split('+');\n const parsedKeys = keys.map(key => {\n // Check if the key is a special character in our map\n if (SHORTCUT_MAP[key]) {\n return SHORTCUT_MAP[key];\n }\n\n // If it's a special key, return it as is (case-sensitive)\n if (SPECIAL_KEYS.has(key)) {\n return key;\n }\n // If not found in the map or special keys, return the lowercase key\n return key.toLowerCase();\n });\n return parsedKeys.join('+');\n });\n }\n\n private handleKeyEvent = (event: KeyboardEvent): void => {\n const key = this.getKeyCombo(event);\n const data = this.shortcuts.get(key);\n if (!data) {\n return;\n }\n let i = data.length;\n while (i--) {\n const item = data[i];\n if (item.global && this.shouldIgnoreEvent(event)) {\n return;\n }\n\n if (item.callback) {\n if (item.prevent) {\n event.preventDefault();\n }\n if (item.stop) {\n event.stopPropagation();\n }\n item.callback(event);\n if (item.stop) {\n break;\n }\n }\n }\n };\n private keydown = documentListener('keydown', this.handleKeyEvent, { lazy: true });\n\n private shouldIgnoreEvent(event: KeyboardEvent): boolean {\n const target = event.target as HTMLElement;\n\n return (\n IGNORED_TAGS.includes(target.tagName) ||\n target.isContentEditable ||\n target.getAttribute('role') === 'textbox'\n );\n }\n\n private getKeyCombo(event: KeyboardEvent): string {\n const modifiers = [];\n\n if (event.ctrlKey) modifiers.push('ctrl');\n if (event.altKey) modifiers.push('alt');\n if (event.shiftKey) modifiers.push('shift');\n if (event.metaKey) modifiers.push('meta');\n\n const key = event.key?.toLowerCase();\n return [...modifiers, ...(key ? [key] : [])].join('+');\n }\n\n private turnOff() {\n if (this.isClient && this.shortcuts.size === 0 && this.isActive) {\n this.isActive = false;\n this.keydown.off();\n }\n }\n\n private turnOn() {\n if (this.isClient && this.shortcuts.size > 0 && !this.isActive) {\n this.isActive = true;\n this.keydown.on();\n }\n }\n}\n\nexport function keyMap(\n key: string,\n callback: (ev: KeyboardEvent) => void,\n data?: {\n injector?: Injector;\n cleanup?: (off: () => void) => void;\n stop?: boolean;\n global?: boolean;\n prevent?: boolean;\n },\n) {\n const { injector, cleanup, stop = false, global = false, prevent = true } = data || {};\n return runInInjectionContext(injector || inject(Injector), () => {\n const shortcuts = inject(Shortcuts);\n const onDestroy = inject(DestroyRef);\n const id = uniqueId();\n\n shortcuts.on(key, { callback, prevent, stop, global, id });\n\n const off = () => {\n shortcuts.off(key, id);\n };\n\n onDestroy?.onDestroy(off);\n cleanup?.(off);\n return off;\n });\n}\n","/*\n * Public API Surface of keys\n */\n\nexport { Keys } from './keys.service';\nexport { keyMap, Shortcuts } from './shortcuts.service';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ngbase-adk-layout.mjs","sources":["../../../projects/adk/layout/layout.ts","../../../projects/adk/layout/ngbase-adk-layout.ts"],"sourcesContent":["import { DestroyRef, inject, signal, WritableSignal } from '@angular/core';\nimport { isClient } from '@ngbase/adk/utils';\n\nconst mediaQueryListeners = new Map<\n string,\n { mql: MediaQueryList; listeners: Set<(event: MediaQueryListEvent) => void> }\n>();\n\nexport function breakpointObserver() {\n const client = isClient();\n const activeListeners = new Map<any, () => void>();\n\n function observe<T extends string>(queries: Record<T, string>) {\n const breakpointStates = signal({} as Record<T, boolean>);\n\n if (client) {\n const cleanup = setupMediaQueries(queries, breakpointStates);\n activeListeners.set(queries, cleanup);\n }\n\n return {\n state: breakpointStates.asReadonly(),\n unobserve: () => {\n activeListeners.get(queries)?.();\n activeListeners.delete(queries);\n },\n };\n }\n\n function setupMediaQueries(\n queries: Record<string, string>,\n breakpointStates: WritableSignal<Record<string, boolean>>,\n ) {\n const states = {} as Record<string, boolean>;\n const cleanupFns: Array<() => void> = [];\n\n Object.entries(queries).forEach(([name, query]) => {\n let queryData = mediaQueryListeners.get(query);\n\n if (!queryData) {\n const mql = _matchMedia(query);\n if (!mql) return;\n queryData = { mql, listeners: new Set() };\n mediaQueryListeners.set(query, queryData);\n\n mql.addEventListener('change', event => {\n queryData!.listeners.forEach(listener => listener(event));\n });\n }\n\n states[name] = queryData.mql.matches;\n\n const listener = (event: MediaQueryListEvent) => {\n breakpointStates.update(states => ({\n ...states,\n [name]: event.matches,\n }));\n };\n\n queryData.listeners.add(listener);\n cleanupFns.push(() => {\n queryData!.listeners.delete(listener);\n if (queryData!.listeners.size === 0) {\n queryData!.mql.removeEventListener('change', listener);\n mediaQueryListeners.delete(query);\n }\n });\n });\n\n breakpointStates.set(states);\n\n return () => cleanupFns.forEach(fn => fn());\n }\n\n // cleanup all listeners when the component is destroyed\n inject(DestroyRef).onDestroy(() => {\n activeListeners.forEach(cleanup => cleanup());\n });\n\n function matches(queryName: string): boolean {\n if (!client) return false;\n return _matchMedia(queryName)?.matches ?? false;\n }\n\n function _matchMedia(queryName: string) {\n return typeof window.matchMedia !== 'undefined' ? window.matchMedia(queryName) : null;\n }\n\n return { observe, matches };\n}\n\n// This is a mock for testing purposes\nexport function setupTestBreakpoint(fn: Function) {\n const createMockMediaQuery = () => ({\n matches: false,\n addEventListener: fn(),\n removeEventListener: fn(),\n });\n\n const _mediaQueryList = createMockMediaQuery();\n const _matchMedia = fn(() => _mediaQueryList);\n window.matchMedia = _matchMedia;\n\n return {\n reset: () => {\n Object.assign(_mediaQueryList, createMockMediaQuery());\n Object.assign(\n _matchMedia,\n fn(() => _mediaQueryList),\n );\n window.matchMedia = _matchMedia;\n },\n get mediaQueryList() {\n return _mediaQueryList;\n },\n get matchMedia() {\n return _matchMedia;\n },\n };\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":";;;AAGA,MAAM,mBAAmB,GAAG,IAAI,GAAG,EAGhC;SAEa,kBAAkB,GAAA;AAChC,IAAA,MAAM,MAAM,GAAG,QAAQ,EAAE;AACzB,IAAA,MAAM,eAAe,GAAG,IAAI,GAAG,EAAmB;IAElD,SAAS,OAAO,CAAmB,OAA0B,EAAA;AAC3D,QAAA,MAAM,gBAAgB,GAAG,MAAM,CAAC,EAAwB,4DAAC;QAEzD,IAAI,MAAM,EAAE;YACV,MAAM,OAAO,GAAG,iBAAiB,CAAC,OAAO,EAAE,gBAAgB,CAAC;AAC5D,YAAA,eAAe,CAAC,GAAG,CAAC,OAAO,EAAE,OAAO,CAAC
|
|
1
|
+
{"version":3,"file":"ngbase-adk-layout.mjs","sources":["../../../projects/adk/layout/layout.ts","../../../projects/adk/layout/ngbase-adk-layout.ts"],"sourcesContent":["import { DestroyRef, inject, signal, WritableSignal } from '@angular/core';\nimport { isClient } from '@ngbase/adk/utils';\n\nconst mediaQueryListeners = new Map<\n string,\n { mql: MediaQueryList; listeners: Set<(event: MediaQueryListEvent) => void> }\n>();\n\nexport function breakpointObserver() {\n const client = isClient();\n const activeListeners = new Map<any, () => void>();\n\n function observe<T extends string>(queries: Record<T, string>) {\n const breakpointStates = signal({} as Record<T, boolean>);\n\n if (client) {\n const cleanup = setupMediaQueries(queries, breakpointStates);\n activeListeners.set(queries, cleanup);\n }\n\n return {\n state: breakpointStates.asReadonly(),\n unobserve: () => {\n activeListeners.get(queries)?.();\n activeListeners.delete(queries);\n },\n };\n }\n\n function setupMediaQueries(\n queries: Record<string, string>,\n breakpointStates: WritableSignal<Record<string, boolean>>,\n ) {\n const states = {} as Record<string, boolean>;\n const cleanupFns: Array<() => void> = [];\n\n Object.entries(queries).forEach(([name, query]) => {\n let queryData = mediaQueryListeners.get(query);\n\n if (!queryData) {\n const mql = _matchMedia(query);\n if (!mql) return;\n queryData = { mql, listeners: new Set() };\n mediaQueryListeners.set(query, queryData);\n\n mql.addEventListener('change', event => {\n queryData!.listeners.forEach(listener => listener(event));\n });\n }\n\n states[name] = queryData.mql.matches;\n\n const listener = (event: MediaQueryListEvent) => {\n breakpointStates.update(states => ({\n ...states,\n [name]: event.matches,\n }));\n };\n\n queryData.listeners.add(listener);\n cleanupFns.push(() => {\n queryData!.listeners.delete(listener);\n if (queryData!.listeners.size === 0) {\n queryData!.mql.removeEventListener('change', listener);\n mediaQueryListeners.delete(query);\n }\n });\n });\n\n breakpointStates.set(states);\n\n return () => cleanupFns.forEach(fn => fn());\n }\n\n // cleanup all listeners when the component is destroyed\n inject(DestroyRef).onDestroy(() => {\n activeListeners.forEach(cleanup => cleanup());\n });\n\n function matches(queryName: string): boolean {\n if (!client) return false;\n return _matchMedia(queryName)?.matches ?? false;\n }\n\n function _matchMedia(queryName: string) {\n return typeof window.matchMedia !== 'undefined' ? window.matchMedia(queryName) : null;\n }\n\n return { observe, matches };\n}\n\n// This is a mock for testing purposes\nexport function setupTestBreakpoint(fn: Function) {\n const createMockMediaQuery = () => ({\n matches: false,\n addEventListener: fn(),\n removeEventListener: fn(),\n });\n\n const _mediaQueryList = createMockMediaQuery();\n const _matchMedia = fn(() => _mediaQueryList);\n window.matchMedia = _matchMedia;\n\n return {\n reset: () => {\n Object.assign(_mediaQueryList, createMockMediaQuery());\n Object.assign(\n _matchMedia,\n fn(() => _mediaQueryList),\n );\n window.matchMedia = _matchMedia;\n },\n get mediaQueryList() {\n return _mediaQueryList;\n },\n get matchMedia() {\n return _matchMedia;\n },\n };\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
@@ -11,7 +11,7 @@ class NgbList {
|
|
|
11
11
|
this.el = inject(ElementRef);
|
|
12
12
|
// Inputs
|
|
13
13
|
this.ayId = input(...(ngDevMode ? [undefined, { debugName: "ayId" }] : []));
|
|
14
|
-
this.disabled = input(false, ...(ngDevMode ?
|
|
14
|
+
this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : {}), transform: booleanAttribute });
|
|
15
15
|
this.allyItem._ayId = linkedSignal(this.ayId);
|
|
16
16
|
}
|
|
17
17
|
setAyId(id) {
|
|
@@ -27,10 +27,10 @@ class NgbList {
|
|
|
27
27
|
unselect() {
|
|
28
28
|
this.el.nativeElement.classList.remove('bg-muted');
|
|
29
29
|
}
|
|
30
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
31
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "
|
|
30
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: NgbList, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
31
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "21.1.0", type: NgbList, isStandalone: true, selector: "[ngbList]", inputs: { ayId: { classPropertyName: "ayId", publicName: "ayId", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null } }, host: { attributes: { "role": "list" } }, hostDirectives: [{ directive: i1.AccessibleItem, inputs: ["role", "role", "disabled", "disabled"] }], ngImport: i0 }); }
|
|
32
32
|
}
|
|
33
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
33
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: NgbList, decorators: [{
|
|
34
34
|
type: Directive,
|
|
35
35
|
args: [{
|
|
36
36
|
selector: '[ngbList]',
|
|
@@ -39,7 +39,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.2.0", ngImpor
|
|
|
39
39
|
role: 'list',
|
|
40
40
|
},
|
|
41
41
|
}]
|
|
42
|
-
}], ctorParameters: () => [] });
|
|
42
|
+
}], ctorParameters: () => [], propDecorators: { ayId: [{ type: i0.Input, args: [{ isSignal: true, alias: "ayId", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }] } });
|
|
43
43
|
function provideList(list) {
|
|
44
44
|
return {
|
|
45
45
|
provide: NgbList,
|
|
@@ -49,7 +49,7 @@ function provideList(list) {
|
|
|
49
49
|
|
|
50
50
|
class NgbListActionGroup {
|
|
51
51
|
constructor() {
|
|
52
|
-
this.options = contentChildren(NgbList, ...(ngDevMode ?
|
|
52
|
+
this.options = contentChildren(NgbList, { ...(ngDevMode ? { debugName: "options" } : {}), descendants: true });
|
|
53
53
|
this.activeIndex = signal(undefined, ...(ngDevMode ? [{ debugName: "activeIndex" }] : []));
|
|
54
54
|
this.optionsMap = new WeakMap();
|
|
55
55
|
this.handleKeyDown = (event) => {
|
|
@@ -87,15 +87,15 @@ class NgbListActionGroup {
|
|
|
87
87
|
lastIndex?.unselect();
|
|
88
88
|
option?.focus();
|
|
89
89
|
}
|
|
90
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
91
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.2.0", version: "
|
|
90
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: NgbListActionGroup, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
91
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.2.0", version: "21.1.0", type: NgbListActionGroup, isStandalone: true, selector: "[ngbActionGroup]", queries: [{ propertyName: "options", predicate: NgbList, descendants: true, isSignal: true }], ngImport: i0 }); }
|
|
92
92
|
}
|
|
93
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
93
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: NgbListActionGroup, decorators: [{
|
|
94
94
|
type: Directive,
|
|
95
95
|
args: [{
|
|
96
96
|
selector: '[ngbActionGroup]',
|
|
97
97
|
}]
|
|
98
|
-
}], ctorParameters: () => [] });
|
|
98
|
+
}], ctorParameters: () => [], propDecorators: { options: [{ type: i0.ContentChildren, args: [i0.forwardRef(() => NgbList), { ...{ descendants: true }, isSignal: true }] }] } });
|
|
99
99
|
|
|
100
100
|
/*
|
|
101
101
|
* Public API Surface of list
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ngbase-adk-list.mjs","sources":["../../../projects/adk/list/list.ts","../../../projects/adk/list/list.directive.ts","../../../projects/adk/list/public-api.ts","../../../projects/adk/list/ngbase-adk-list.ts"],"sourcesContent":["import {\n booleanAttribute,\n Directive,\n ElementRef,\n inject,\n input,\n linkedSignal,\n WritableSignal,\n} from '@angular/core';\nimport { AccessibleItem } from '@ngbase/adk/a11y';\n\n@Directive({\n selector: '[ngbList]',\n hostDirectives: [{ directive: AccessibleItem, inputs: ['role', 'disabled'] }],\n host: {\n role: 'list',\n },\n})\nexport class NgbList {\n // Dependencies\n private readonly allyItem = inject(AccessibleItem);\n readonly el = inject<ElementRef<HTMLElement>>(ElementRef);\n\n // Inputs\n readonly ayId = input<string>();\n readonly disabled = input(false, { transform: booleanAttribute });\n\n constructor() {\n this.allyItem._ayId = linkedSignal(this.ayId) as WritableSignal<string>;\n }\n\n setAyId(id: string) {\n this.allyItem._ayId.set(id);\n }\n\n select() {\n this.el.nativeElement.click();\n }\n\n focus() {\n this.el.nativeElement.scrollIntoView({ block: 'nearest' });\n this.el.nativeElement.classList.add('bg-muted');\n }\n\n unselect() {\n this.el.nativeElement.classList.remove('bg-muted');\n }\n}\n\nexport function provideList(list: typeof NgbList) {\n return {\n provide: NgbList,\n useExisting: list,\n };\n}\n","import {\n Directive,\n afterNextRender,\n contentChildren,\n effect,\n signal,\n untracked,\n} from '@angular/core';\nimport { documentListener } from '@ngbase/adk/utils';\nimport { NgbList } from './list';\n\n@Directive({\n selector: '[ngbActionGroup]',\n})\nexport class NgbListActionGroup {\n readonly options = contentChildren(NgbList, { descendants: true });\n\n private readonly activeIndex = signal<NgbList | undefined>(undefined);\n private readonly optionsMap = new WeakMap<NgbList, number>();\n\n constructor() {\n documentListener('keydown', this.handleKeyDown);\n afterNextRender(() => this.afterAction());\n\n effect(() => {\n const options = this.options();\n options.forEach((x, i) => this.optionsMap.set(x, i));\n untracked(() => {\n const lastIndex = this.activeIndex();\n this.activeIndex.set(options[0]);\n this.afterAction(lastIndex);\n });\n });\n }\n\n private handleKeyDown = (event: KeyboardEvent) => {\n const options = this.options();\n const lastIndex = this.activeIndex();\n const i = this.optionsMap.get(this.activeIndex() || options[0])!;\n if (event.key === 'ArrowDown') {\n this.activeIndex.set(options[Math.min(i + 1, options.length - 1)]);\n } else if (event.key === 'ArrowUp') {\n this.activeIndex.set(options[Math.max(i - 1, 0)]);\n } else if (event.key === 'Enter') {\n lastIndex?.select();\n }\n if (lastIndex !== this.activeIndex()) {\n event.preventDefault();\n this.afterAction(lastIndex);\n }\n };\n\n private afterAction(lastIndex?: NgbList) {\n const option = this.activeIndex();\n lastIndex?.unselect();\n option?.focus();\n }\n}\n","/*\n * Public API Surface of list\n */\n\nexport * from './list';\nexport * from './list.directive';\n// export * from './list-selection.component';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":";;;;;;MAkBa,OAAO,CAAA;AASlB,IAAA,WAAA,GAAA;;AAPiB,QAAA,IAAA,CAAA,QAAQ,GAAG,MAAM,CAAC,cAAc,CAAC;AACzC,QAAA,IAAA,CAAA,EAAE,GAAG,MAAM,CAA0B,UAAU,CAAC;;QAGhD,
|
|
1
|
+
{"version":3,"file":"ngbase-adk-list.mjs","sources":["../../../projects/adk/list/list.ts","../../../projects/adk/list/list.directive.ts","../../../projects/adk/list/public-api.ts","../../../projects/adk/list/ngbase-adk-list.ts"],"sourcesContent":["import {\n booleanAttribute,\n Directive,\n ElementRef,\n inject,\n input,\n linkedSignal,\n WritableSignal,\n} from '@angular/core';\nimport { AccessibleItem } from '@ngbase/adk/a11y';\n\n@Directive({\n selector: '[ngbList]',\n hostDirectives: [{ directive: AccessibleItem, inputs: ['role', 'disabled'] }],\n host: {\n role: 'list',\n },\n})\nexport class NgbList {\n // Dependencies\n private readonly allyItem = inject(AccessibleItem);\n readonly el = inject<ElementRef<HTMLElement>>(ElementRef);\n\n // Inputs\n readonly ayId = input<string>();\n readonly disabled = input(false, { transform: booleanAttribute });\n\n constructor() {\n this.allyItem._ayId = linkedSignal(this.ayId) as WritableSignal<string>;\n }\n\n setAyId(id: string) {\n this.allyItem._ayId.set(id);\n }\n\n select() {\n this.el.nativeElement.click();\n }\n\n focus() {\n this.el.nativeElement.scrollIntoView({ block: 'nearest' });\n this.el.nativeElement.classList.add('bg-muted');\n }\n\n unselect() {\n this.el.nativeElement.classList.remove('bg-muted');\n }\n}\n\nexport function provideList(list: typeof NgbList) {\n return {\n provide: NgbList,\n useExisting: list,\n };\n}\n","import {\n Directive,\n afterNextRender,\n contentChildren,\n effect,\n signal,\n untracked,\n} from '@angular/core';\nimport { documentListener } from '@ngbase/adk/utils';\nimport { NgbList } from './list';\n\n@Directive({\n selector: '[ngbActionGroup]',\n})\nexport class NgbListActionGroup {\n readonly options = contentChildren(NgbList, { descendants: true });\n\n private readonly activeIndex = signal<NgbList | undefined>(undefined);\n private readonly optionsMap = new WeakMap<NgbList, number>();\n\n constructor() {\n documentListener('keydown', this.handleKeyDown);\n afterNextRender(() => this.afterAction());\n\n effect(() => {\n const options = this.options();\n options.forEach((x, i) => this.optionsMap.set(x, i));\n untracked(() => {\n const lastIndex = this.activeIndex();\n this.activeIndex.set(options[0]);\n this.afterAction(lastIndex);\n });\n });\n }\n\n private handleKeyDown = (event: KeyboardEvent) => {\n const options = this.options();\n const lastIndex = this.activeIndex();\n const i = this.optionsMap.get(this.activeIndex() || options[0])!;\n if (event.key === 'ArrowDown') {\n this.activeIndex.set(options[Math.min(i + 1, options.length - 1)]);\n } else if (event.key === 'ArrowUp') {\n this.activeIndex.set(options[Math.max(i - 1, 0)]);\n } else if (event.key === 'Enter') {\n lastIndex?.select();\n }\n if (lastIndex !== this.activeIndex()) {\n event.preventDefault();\n this.afterAction(lastIndex);\n }\n };\n\n private afterAction(lastIndex?: NgbList) {\n const option = this.activeIndex();\n lastIndex?.unselect();\n option?.focus();\n }\n}\n","/*\n * Public API Surface of list\n */\n\nexport * from './list';\nexport * from './list.directive';\n// export * from './list-selection.component';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
@@ -16,7 +16,7 @@ class Mask {
|
|
|
16
16
|
// Inputs
|
|
17
17
|
this.ngbMask = input('', ...(ngDevMode ? [{ debugName: "ngbMask" }] : []));
|
|
18
18
|
this.showMaskType = input(false, ...(ngDevMode ? [{ debugName: "showMaskType" }] : []));
|
|
19
|
-
this.localValue = linkedSignal(() => this.inputC.value() ?? '');
|
|
19
|
+
this.localValue = linkedSignal(() => this.inputC.value() ?? '', ...(ngDevMode ? [{ debugName: "localValue" }] : []));
|
|
20
20
|
afterRenderEffect(() => {
|
|
21
21
|
const mask = this.ngbMask();
|
|
22
22
|
const value = this.localValue();
|
|
@@ -148,10 +148,10 @@ class Mask {
|
|
|
148
148
|
}
|
|
149
149
|
return unmaskedValue;
|
|
150
150
|
}
|
|
151
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
152
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "
|
|
151
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Mask, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
152
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "21.1.0", type: Mask, isStandalone: true, selector: "[ngbMask]", inputs: { ngbMask: { classPropertyName: "ngbMask", publicName: "ngbMask", isSignal: true, isRequired: false, transformFunction: null }, showMaskType: { classPropertyName: "showMaskType", publicName: "showMaskType", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "keydown": "onKeyDown($event)", "paste": "onPaste($event)" } }, ngImport: i0 }); }
|
|
153
153
|
}
|
|
154
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
154
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: Mask, decorators: [{
|
|
155
155
|
type: Directive,
|
|
156
156
|
args: [{
|
|
157
157
|
selector: '[ngbMask]',
|
|
@@ -160,7 +160,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.2.0", ngImpor
|
|
|
160
160
|
'(paste)': 'onPaste($event)',
|
|
161
161
|
},
|
|
162
162
|
}]
|
|
163
|
-
}], ctorParameters: () => [] });
|
|
163
|
+
}], ctorParameters: () => [], propDecorators: { ngbMask: [{ type: i0.Input, args: [{ isSignal: true, alias: "ngbMask", required: false }] }], showMaskType: [{ type: i0.Input, args: [{ isSignal: true, alias: "showMaskType", required: false }] }] } });
|
|
164
164
|
function maskTransform(value, mask, showMaskType = false) {
|
|
165
165
|
let result = '';
|
|
166
166
|
let valueIndex = 0;
|
|
@@ -218,10 +218,10 @@ class MaskPipe {
|
|
|
218
218
|
transform(value, mask) {
|
|
219
219
|
return maskTransform(value, mask);
|
|
220
220
|
}
|
|
221
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "
|
|
222
|
-
static { this.ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "
|
|
221
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: MaskPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe }); }
|
|
222
|
+
static { this.ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.0", ngImport: i0, type: MaskPipe, isStandalone: true, name: "mask" }); }
|
|
223
223
|
}
|
|
224
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "
|
|
224
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.0", ngImport: i0, type: MaskPipe, decorators: [{
|
|
225
225
|
type: Pipe,
|
|
226
226
|
args: [{
|
|
227
227
|
name: 'mask',
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ngbase-adk-mask.mjs","sources":["../../../projects/adk/mask/mask.ts","../../../projects/adk/mask/mask-pipe.ts","../../../projects/adk/mask/ngbase-adk-mask.ts"],"sourcesContent":["import {\n afterRenderEffect,\n Directive,\n ElementRef,\n inject,\n input,\n linkedSignal,\n} from '@angular/core';\nimport { NgControl } from '@angular/forms';\nimport { InputBase } from '@ngbase/adk/form-field';\n\n@Directive({\n selector: '[ngbMask]',\n host: {\n '(keydown)': 'onKeyDown($event)',\n '(paste)': 'onPaste($event)',\n },\n})\nexport class Mask {\n // Dependencies\n private readonly el = inject<ElementRef<HTMLInputElement>>(ElementRef);\n readonly control = inject(NgControl, { optional: true });\n private readonly inputC = inject(InputBase);\n\n // Inputs\n readonly ngbMask = input<string>('');\n readonly showMaskType = input(false);\n\n readonly localValue = linkedSignal(() => (this.inputC.value() as string) ?? '');\n // private lastValue = '';\n\n constructor() {\n // this.control?.valueChanges?.subscribe(value => {\n // if (value !== this.lastValue) this.handleValue(value);\n // });\n\n afterRenderEffect(() => {\n const mask = this.ngbMask();\n const value = this.localValue();\n this.el.nativeElement.value = this.updateView(value, mask);\n });\n }\n\n onKeyDown(event: KeyboardEvent): void {\n // console.log('onKeyDown', event);\n const input = event.target as HTMLInputElement;\n const keyCode = event.key;\n\n // Allow navigation keys\n if (\n [\n 'ArrowLeft',\n 'ArrowRight',\n 'Home',\n 'End',\n 'Tab',\n 'Backspace',\n 'Delete',\n 'Shift',\n 'Meta',\n 'Control',\n 'Alt',\n 'Escape',\n 'CapsLock',\n ].includes(keyCode)\n ) {\n return;\n }\n\n // allow selecting all text\n if (keyCode === 'a' && (event.metaKey || event.ctrlKey)) {\n return;\n }\n\n event.preventDefault();\n const cursorPos = input.selectionStart || 0;\n const key = event.key;\n\n // Get the current value and mask\n const currentValue = input.value;\n const mask = this.ngbMask();\n\n // Check if the key matches the mask at current position\n if (this.isValidChar(key, this.getCurrentMaskChar(mask, cursorPos))) {\n // Insert the character at cursor position\n const newValue =\n currentValue.substring(0, cursorPos) + key + currentValue.substring(cursorPos);\n\n this.handleValue(newValue, cursorPos);\n }\n }\n\n getCurrentMaskChar(mask: string, cursorPos: number): string {\n // we only have to check cursor position and have to skip non-mask characters\n for (let i = cursorPos; i < mask.length; i++) {\n if (mask[i] !== '#' && mask[i] !== 'a' && mask[i] !== '*') {\n continue;\n }\n return mask[i];\n }\n return '';\n }\n\n onPaste(event: ClipboardEvent): void {\n event.preventDefault();\n const input = event.target as HTMLInputElement;\n const cursorPos = input.selectionStart || 0;\n const pastedText = event.clipboardData?.getData('text') || '';\n\n const currentValue = input.value;\n const beforeCursor = currentValue.substring(0, cursorPos);\n const afterCursor = currentValue.substring(cursorPos);\n\n const newValue = beforeCursor + pastedText + afterCursor;\n this.handleValue(newValue, cursorPos);\n }\n\n private isValidChar(char: string, maskChar: string): boolean {\n switch (maskChar) {\n case '#':\n return /\\d/.test(char);\n case 'a':\n return /[a-zA-Z]/.test(char);\n case '*':\n return /[a-zA-Z0-9]/.test(char);\n default:\n return char === maskChar;\n }\n }\n\n handleValue(value: string, cursorPos?: number) {\n // Apply mask and update view\n const maskedValue = this.updateView(value);\n // Update actualValue\n const actualValue = this.unmask(maskedValue);\n\n this.updateLocalValue(actualValue, actualValue !== value);\n\n // Set cursor position after update\n // if (cursorPos !== undefined) {\n // setTimeout(() => {\n // const newPos = this.calculateCursorPosition(maskedValue, cursorPos);\n // this.el.nativeElement.setSelectionRange(newPos, newPos);\n // });\n // }\n }\n\n private calculateCursorPosition(maskedValue: string, oldPos: number): number {\n const mask = this.ngbMask();\n let newPos = oldPos;\n\n // Move cursor past any fixed mask characters\n while (newPos < mask.length && !'#a*'.includes(mask[newPos])) {\n newPos++;\n }\n\n return Math.min(newPos, maskedValue.length);\n }\n\n private updateLocalValue(value: string, emit = true) {\n this.inputC.setValue(value);\n // this.lastValue = value;\n this.localValue.set(value);\n if (emit) this.control?.control?.setValue(value);\n }\n\n writeValue(value: string): void {\n this.handleValue(value);\n }\n\n private updateView(value: string, mask = this.ngbMask()): string {\n return maskTransform(value, mask);\n }\n\n private unmask(value: string): string {\n const mask = this.ngbMask();\n let unmaskedValue = '';\n let valueIndex = 0;\n\n for (let maskIndex = 0; maskIndex < mask.length && valueIndex < value.length; maskIndex++) {\n const maskChar = mask[maskIndex];\n const valueChar = value[valueIndex];\n\n if ('#a*'.includes(maskChar)) {\n unmaskedValue += valueChar;\n valueIndex++;\n } else if (maskChar === valueChar) {\n valueIndex++;\n }\n }\n\n return unmaskedValue;\n }\n}\n\nexport function maskTransform(value: string, mask: string, showMaskType = false): string {\n let result = '';\n let valueIndex = 0;\n\n for (let maskIndex = 0; maskIndex < mask.length && valueIndex < value.length; maskIndex++) {\n const maskChar = mask[maskIndex];\n const valueChar = value[valueIndex];\n\n switch (maskChar) {\n case '#':\n if (/\\d/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n case 'a':\n if (/[a-zA-Z]/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n case '*':\n if (/[a-zA-Z0-9]/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n default:\n result += maskChar;\n if (maskChar === valueChar && valueIndex === maskIndex) {\n valueIndex++;\n }\n }\n }\n\n return result;\n}\n","import { Pipe, PipeTransform } from '@angular/core';\nimport { maskTransform } from './mask';\n\n@Pipe({\n name: 'mask',\n})\nexport class MaskPipe implements PipeTransform {\n transform(value: string, mask: string): string {\n return maskTransform(value, mask);\n }\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"ngbase-adk-mask.mjs","sources":["../../../projects/adk/mask/mask.ts","../../../projects/adk/mask/mask-pipe.ts","../../../projects/adk/mask/ngbase-adk-mask.ts"],"sourcesContent":["import {\n afterRenderEffect,\n Directive,\n ElementRef,\n inject,\n input,\n linkedSignal,\n} from '@angular/core';\nimport { NgControl } from '@angular/forms';\nimport { InputBase } from '@ngbase/adk/form-field';\n\n@Directive({\n selector: '[ngbMask]',\n host: {\n '(keydown)': 'onKeyDown($event)',\n '(paste)': 'onPaste($event)',\n },\n})\nexport class Mask {\n // Dependencies\n private readonly el = inject<ElementRef<HTMLInputElement>>(ElementRef);\n readonly control = inject(NgControl, { optional: true });\n private readonly inputC = inject(InputBase);\n\n // Inputs\n readonly ngbMask = input<string>('');\n readonly showMaskType = input(false);\n\n readonly localValue = linkedSignal(() => (this.inputC.value() as string) ?? '');\n // private lastValue = '';\n\n constructor() {\n // this.control?.valueChanges?.subscribe(value => {\n // if (value !== this.lastValue) this.handleValue(value);\n // });\n\n afterRenderEffect(() => {\n const mask = this.ngbMask();\n const value = this.localValue();\n this.el.nativeElement.value = this.updateView(value, mask);\n });\n }\n\n onKeyDown(event: KeyboardEvent): void {\n // console.log('onKeyDown', event);\n const input = event.target as HTMLInputElement;\n const keyCode = event.key;\n\n // Allow navigation keys\n if (\n [\n 'ArrowLeft',\n 'ArrowRight',\n 'Home',\n 'End',\n 'Tab',\n 'Backspace',\n 'Delete',\n 'Shift',\n 'Meta',\n 'Control',\n 'Alt',\n 'Escape',\n 'CapsLock',\n ].includes(keyCode)\n ) {\n return;\n }\n\n // allow selecting all text\n if (keyCode === 'a' && (event.metaKey || event.ctrlKey)) {\n return;\n }\n\n event.preventDefault();\n const cursorPos = input.selectionStart || 0;\n const key = event.key;\n\n // Get the current value and mask\n const currentValue = input.value;\n const mask = this.ngbMask();\n\n // Check if the key matches the mask at current position\n if (this.isValidChar(key, this.getCurrentMaskChar(mask, cursorPos))) {\n // Insert the character at cursor position\n const newValue =\n currentValue.substring(0, cursorPos) + key + currentValue.substring(cursorPos);\n\n this.handleValue(newValue, cursorPos);\n }\n }\n\n getCurrentMaskChar(mask: string, cursorPos: number): string {\n // we only have to check cursor position and have to skip non-mask characters\n for (let i = cursorPos; i < mask.length; i++) {\n if (mask[i] !== '#' && mask[i] !== 'a' && mask[i] !== '*') {\n continue;\n }\n return mask[i];\n }\n return '';\n }\n\n onPaste(event: ClipboardEvent): void {\n event.preventDefault();\n const input = event.target as HTMLInputElement;\n const cursorPos = input.selectionStart || 0;\n const pastedText = event.clipboardData?.getData('text') || '';\n\n const currentValue = input.value;\n const beforeCursor = currentValue.substring(0, cursorPos);\n const afterCursor = currentValue.substring(cursorPos);\n\n const newValue = beforeCursor + pastedText + afterCursor;\n this.handleValue(newValue, cursorPos);\n }\n\n private isValidChar(char: string, maskChar: string): boolean {\n switch (maskChar) {\n case '#':\n return /\\d/.test(char);\n case 'a':\n return /[a-zA-Z]/.test(char);\n case '*':\n return /[a-zA-Z0-9]/.test(char);\n default:\n return char === maskChar;\n }\n }\n\n handleValue(value: string, cursorPos?: number) {\n // Apply mask and update view\n const maskedValue = this.updateView(value);\n // Update actualValue\n const actualValue = this.unmask(maskedValue);\n\n this.updateLocalValue(actualValue, actualValue !== value);\n\n // Set cursor position after update\n // if (cursorPos !== undefined) {\n // setTimeout(() => {\n // const newPos = this.calculateCursorPosition(maskedValue, cursorPos);\n // this.el.nativeElement.setSelectionRange(newPos, newPos);\n // });\n // }\n }\n\n private calculateCursorPosition(maskedValue: string, oldPos: number): number {\n const mask = this.ngbMask();\n let newPos = oldPos;\n\n // Move cursor past any fixed mask characters\n while (newPos < mask.length && !'#a*'.includes(mask[newPos])) {\n newPos++;\n }\n\n return Math.min(newPos, maskedValue.length);\n }\n\n private updateLocalValue(value: string, emit = true) {\n this.inputC.setValue(value);\n // this.lastValue = value;\n this.localValue.set(value);\n if (emit) this.control?.control?.setValue(value);\n }\n\n writeValue(value: string): void {\n this.handleValue(value);\n }\n\n private updateView(value: string, mask = this.ngbMask()): string {\n return maskTransform(value, mask);\n }\n\n private unmask(value: string): string {\n const mask = this.ngbMask();\n let unmaskedValue = '';\n let valueIndex = 0;\n\n for (let maskIndex = 0; maskIndex < mask.length && valueIndex < value.length; maskIndex++) {\n const maskChar = mask[maskIndex];\n const valueChar = value[valueIndex];\n\n if ('#a*'.includes(maskChar)) {\n unmaskedValue += valueChar;\n valueIndex++;\n } else if (maskChar === valueChar) {\n valueIndex++;\n }\n }\n\n return unmaskedValue;\n }\n}\n\nexport function maskTransform(value: string, mask: string, showMaskType = false): string {\n let result = '';\n let valueIndex = 0;\n\n for (let maskIndex = 0; maskIndex < mask.length && valueIndex < value.length; maskIndex++) {\n const maskChar = mask[maskIndex];\n const valueChar = value[valueIndex];\n\n switch (maskChar) {\n case '#':\n if (/\\d/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n case 'a':\n if (/[a-zA-Z]/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n case '*':\n if (/[a-zA-Z0-9]/.test(valueChar)) {\n result += valueChar;\n valueIndex++;\n } else if (showMaskType) {\n result += '_';\n } else {\n return result;\n }\n break;\n default:\n result += maskChar;\n if (maskChar === valueChar && valueIndex === maskIndex) {\n valueIndex++;\n }\n }\n }\n\n return result;\n}\n","import { Pipe, PipeTransform } from '@angular/core';\nimport { maskTransform } from './mask';\n\n@Pipe({\n name: 'mask',\n})\nexport class MaskPipe implements PipeTransform {\n transform(value: string, mask: string): string {\n return maskTransform(value, mask);\n }\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
|