xterm
[VSoRC/.git] / node_modules / xterm / src / browser / ScreenDprMonitor.ts
1 /**
2  * Copyright (c) 2017 The xterm.js authors. All rights reserved.
3  * @license MIT
4  */
5
6 import { Disposable } from 'common/Lifecycle';
7
8 export type ScreenDprListener = (newDevicePixelRatio?: number, oldDevicePixelRatio?: number) => void;
9
10 /**
11  * The screen device pixel ratio monitor allows listening for when the
12  * window.devicePixelRatio value changes. This is done not with polling but with
13  * the use of window.matchMedia to watch media queries. When the event fires,
14  * the listener will be reattached using a different media query to ensure that
15  * any further changes will register.
16  *
17  * The listener should fire on both window zoom changes and switching to a
18  * monitor with a different DPI.
19  */
20 export class ScreenDprMonitor extends Disposable {
21   private _currentDevicePixelRatio: number = window.devicePixelRatio;
22   private _outerListener: ((this: MediaQueryList, ev: MediaQueryListEvent) => any) | undefined;
23   private _listener: ScreenDprListener | undefined;
24   private _resolutionMediaMatchList: MediaQueryList | undefined;
25
26   public setListener(listener: ScreenDprListener): void {
27     if (this._listener) {
28       this.clearListener();
29     }
30     this._listener = listener;
31     this._outerListener = () => {
32       if (!this._listener) {
33         return;
34       }
35       this._listener(window.devicePixelRatio, this._currentDevicePixelRatio);
36       this._updateDpr();
37     };
38     this._updateDpr();
39   }
40
41   public dispose(): void {
42     super.dispose();
43     this.clearListener();
44   }
45
46   private _updateDpr(): void {
47     if (!this._resolutionMediaMatchList || !this._outerListener) {
48       return;
49     }
50
51     // Clear listeners for old DPR
52     this._resolutionMediaMatchList.removeListener(this._outerListener);
53
54     // Add listeners for new DPR
55     this._currentDevicePixelRatio = window.devicePixelRatio;
56     this._resolutionMediaMatchList = window.matchMedia(`screen and (resolution: ${window.devicePixelRatio}dppx)`);
57     this._resolutionMediaMatchList.addListener(this._outerListener);
58   }
59
60   public clearListener(): void {
61     if (!this._resolutionMediaMatchList || !this._listener || !this._outerListener) {
62       return;
63     }
64     this._resolutionMediaMatchList.removeListener(this._outerListener);
65     this._resolutionMediaMatchList = undefined;
66     this._listener = undefined;
67     this._outerListener = undefined;
68   }
69 }