• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

atinc / ngx-tethys / 68ef226c-f83e-44c1-b8ed-e420a83c5d84

28 May 2025 10:31AM UTC coverage: 10.352% (-80.0%) from 90.316%
68ef226c-f83e-44c1-b8ed-e420a83c5d84

Pull #3460

circleci

pubuzhixing8
chore: xxx
Pull Request #3460: refactor(icon): migrate signal input #TINFR-1476

132 of 6823 branches covered (1.93%)

Branch coverage included in aggregate %.

10 of 14 new or added lines in 1 file covered. (71.43%)

11648 existing lines in 344 files now uncovered.

2078 of 14525 relevant lines covered (14.31%)

6.69 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.96
/src/core/overlay/abstract-overlay-ref.ts
1
import { Observable, Subject } from 'rxjs';
2
import { filter, finalize, take } from 'rxjs/operators';
3

4
import { GlobalPositionStrategy, OverlayRef, PositionStrategy } from '@angular/cdk/overlay';
5

6
import { ESCAPE } from 'ngx-tethys/util';
7
import { ThyAbstractOverlayContainer } from './abstract-overlay-container';
8
import { ThyAbstractOverlayConfig, ThyAbstractOverlayOptions, ThyAbstractOverlayPosition } from './abstract-overlay.config';
1✔
9

UNCOV
10
export abstract class ThyAbstractOverlayRef<
×
UNCOV
11
    TComponent = unknown,
×
12
    TContainer extends ThyAbstractOverlayContainer = ThyAbstractOverlayContainer,
13
    TResult = unknown
UNCOV
14
> {
×
15
    id: string;
UNCOV
16
    componentInstance: TComponent;
×
17
    backdropClosable: boolean;
18
    disableClose: boolean;
19
    containerInstance: TContainer;
20
    /**
UNCOV
21
     * 获取 OverlayRef
×
22
     */
23
    abstract getOverlayRef(): OverlayRef;
UNCOV
24

×
UNCOV
25
    /**
×
UNCOV
26
     * 关闭当前模态框,若force为true,则canClose无效,强制关闭
×
UNCOV
27
     * @param dialogResult
×
28
     * @param force
UNCOV
29
     */
×
30
    abstract close(dialogResult?: TResult, force?: boolean): void;
UNCOV
31

×
32
    /**
UNCOV
33
     * 模态框打开后的回调
×
34
     */
UNCOV
35
    abstract afterOpened(): Observable<void>;
×
36

UNCOV
37
    /**
×
UNCOV
38
     * 模态框关闭后的回调
×
39
     */
UNCOV
40
    abstract afterClosed(): Observable<TResult | undefined>;
×
41

UNCOV
42
    /**
×
UNCOV
43
     * 模态框关闭前的回调
×
UNCOV
44
     */
×
UNCOV
45
    abstract beforeClosed(): Observable<TResult | undefined>;
×
46

47
    abstract keydownEvents(): Observable<KeyboardEvent>;
48

UNCOV
49
    /**
×
UNCOV
50
     * 点击模态框遮罩层的回调
×
UNCOV
51
     */
×
52
    abstract backdropClick(): Observable<MouseEvent>;
53

54
    /**
UNCOV
55
     * 更新模态框的位置
×
UNCOV
56
     * @param position
×
57
     */
UNCOV
58
    abstract updatePosition(position?: ThyAbstractOverlayPosition): this;
×
UNCOV
59

×
60
    /**
61
     * 模态框置顶
62
     */
UNCOV
63
    public toTop?(): void;
×
64
}
65

UNCOV
66
// Counter for unique overlay ids.
×
67
const uniqueIdMap: { [key: string]: number } = {};
68

UNCOV
69
function getUniqueId(name: string) {
×
UNCOV
70
    if (uniqueIdMap[name] !== undefined) {
×
UNCOV
71
        uniqueIdMap[name] = uniqueIdMap[name] + 1;
×
UNCOV
72
    } else {
×
UNCOV
73
        uniqueIdMap[name] = 0;
×
74
    }
75
    return uniqueIdMap[name];
UNCOV
76
}
×
77

UNCOV
78
export abstract class ThyAbstractInternalOverlayRef<
×
79
    T,
UNCOV
80
    TContainer extends ThyAbstractOverlayContainer,
×
UNCOV
81
    TResult = undefined
×
82
> extends ThyAbstractOverlayRef<T, TContainer, TResult> {
83
    /** The instance of component opened into the dialog. */
84
    componentInstance: T;
85

86
    /** Whether the user is allowed to close the dialog. */
87
    backdropClosable: boolean = this.config.backdropClosable;
88

89
    /** Whether the user is not allowed to close the dialog. */
UNCOV
90
    disableClose: boolean = this.config.disableClose;
×
UNCOV
91

×
92
    /** Subject for notifying the user that the dialog has finished opening. */
UNCOV
93
    private readonly _afterOpened = new Subject<void>();
×
UNCOV
94

×
UNCOV
95
    /** Subject for notifying the user that the dialog has finished closing. */
×
96
    private readonly _afterClosed = new Subject<TResult | undefined>();
UNCOV
97

×
UNCOV
98
    /** Subject for notifying the user that the dialog has started closing. */
×
99
    private readonly _beforeClosed = new Subject<TResult | undefined>();
100

101
    /** Result to be passed to afterClosed. */
102
    private _result: TResult | undefined;
103

104
    /** Fetches the position strategy object from the overlay ref. */
UNCOV
105
    protected getPositionStrategy(): PositionStrategy {
×
106
        return this.overlayRef.getConfig().positionStrategy;
107
    }
108

109
    constructor(
110
        private options: ThyAbstractOverlayOptions,
UNCOV
111
        protected overlayRef: OverlayRef,
×
112
        containerInstance: TContainer,
113
        protected config: ThyAbstractOverlayConfig
114
    ) {
115
        super();
116
        this.containerInstance = containerInstance;
UNCOV
117
        // Pass the id along to the container.
×
118
        this.id = containerInstance.id = config.id ? config.id : `thy-${this.options.name}-${getUniqueId(this.options.name)}`;
119
        // Emit when opening animation completes
120
        containerInstance.animationOpeningDone.pipe(take(1)).subscribe(() => {
121
            this._afterOpened.next();
122
            if (this.options.disposeWhenClose) {
UNCOV
123
                this._afterOpened.complete();
×
124
            }
125
        });
126

127
        // Dispose overlay when closing animation is complete
128
        containerInstance.animationClosingDone.pipe(take(1)).subscribe(() => {
UNCOV
129
            if (this.options.disposeWhenClose) {
×
130
                this.overlayRef.dispose();
131
            }
132
        });
UNCOV
133

×
134
        // Dispose overlay when container after destroy
135
        containerInstance.containerDestroy.pipe(take(1)).subscribe(() => {
136
            if (this.options.disposeWhenClose) {
137
                // component element has not been deleted when the component destroy, so use promise wait for component element destroyed
138
                Promise.resolve().then(() => {
139
                    this.overlayRef.dispose();
UNCOV
140
                });
×
UNCOV
141
            }
×
142
        });
×
143

UNCOV
144
        overlayRef
×
UNCOV
145
            .detachments()
×
146
            .pipe(
147
                finalize(() => {
UNCOV
148
                    this.overlayRef.dispose();
×
149
                })
UNCOV
150
            )
×
UNCOV
151
            .subscribe(() => {
×
152
                this._beforeClosed.next(this._result);
153
                this._beforeClosed.complete();
UNCOV
154
                this._afterClosed.next(this._result);
×
155
                this._afterClosed.complete();
UNCOV
156
                this.componentInstance = null;
×
UNCOV
157
            });
×
158

159
        // ESC close
160
        overlayRef
161
            .keydownEvents()
162
            .pipe(filter(event => event.keyCode === ESCAPE))
163
            .subscribe(() => {
164
                if ((this.disableClose !== undefined && !this.disableClose) || this.backdropClosable) {
165
                    this.close();
166
                }
167
            });
168
    }
169

170
    /**
171
     * Close the overlay.
172
     * @param overlayResult Optional result to return to the dialog opener.
173
     */
174
    close(overlayResult?: TResult, force?: boolean): void {
175
        if (force || !this.config.canClose || !!this.config.canClose(overlayResult)) {
176
            this._result = overlayResult;
177
            // Transition the backdrop in parallel to the overlay.
178
            this._beforeClosed.next(overlayResult);
179
            if (this.options.disposeWhenClose) {
180
                this._beforeClosed.complete();
181
            }
182

183
            this.overlayRef.detachBackdrop();
184
            this.containerInstance.startExitAnimation();
185
        }
186
    }
187

188
    /**
189
     * Gets an observable that is notified when the dialog is finished opening.
190
     */
191
    afterOpened(): Observable<void> {
192
        return this._afterOpened.asObservable();
193
    }
194

195
    /**
196
     * Gets an observable that is notified when the dialog is finished closing.
197
     */
198
    afterClosed(): Observable<TResult | undefined> {
199
        return this._afterClosed.asObservable();
200
    }
201

202
    /**
203
     * Gets an observable that is notified when the dialog has started closing.
204
     */
205
    beforeClosed(): Observable<TResult | undefined> {
206
        return this._beforeClosed.asObservable();
207
    }
208

209
    /**
210
     * Gets an observable that emits when the overlay's backdrop has been clicked.
211
     */
212
    backdropClick(): Observable<MouseEvent> {
213
        return this.overlayRef.backdropClick();
214
    }
215

216
    /**
217
     * Gets an observable that emits when keydown events are targeted on the overlay.
218
     */
219
    keydownEvents(): Observable<KeyboardEvent> {
220
        return this.overlayRef.keydownEvents();
221
    }
222

223
    /** Get overlay ref */
224
    getOverlayRef() {
225
        return this.overlayRef;
226
    }
227

228
    /**
229
     * Updates the overlay's position when is GlobalPositionStrategy
230
     * @param position New overlay position.
231
     */
232
    updateGlobalPosition(position?: ThyAbstractOverlayPosition): this {
233
        const strategy = this.getPositionStrategy() as GlobalPositionStrategy;
234

235
        if ((typeof ngDevMode === 'undefined' || ngDevMode) && !(strategy instanceof GlobalPositionStrategy)) {
236
            throw new Error(`current strategy is not GlobalPositionStrategy`);
237
        }
238

239
        if (position && (position.left || position.right)) {
240
            position.left ? strategy.left(position.left) : strategy.right(position.right);
241
        } else {
242
            strategy.centerHorizontally();
243
        }
244

245
        if (position && (position.top || position.bottom)) {
246
            position.top ? strategy.top(position.top) : strategy.bottom(position.bottom);
247
        } else {
248
            strategy.centerVertically();
249
        }
250

251
        this.overlayRef.updatePosition();
252

253
        return this;
254
    }
255
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc