• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Application Window Development (Stage Model)
2<!--Kit: ArkUI-->
3<!--Subsystem: Window-->
4<!--Owner: @waterwin-->
5<!--Designer: @nyankomiya-->
6<!--Tester: @qinliwen0417-->
7<!--Adviser: @ge-yafang-->
8
9## Basic Concepts
10
11- Immersive window: a window display mode where the system windows (generally the status bar and navigation bar) are hidden to allow users to fully engage with the content.
12
13  The immersive window feature is applicable only to the main window of an application in full-screen mode. It does not apply to a main window in freeform window mode or a child window (for example, a dialog box or a floating window).
14
15- Floating window: a special application window that can still be displayed in the foreground when the main window and corresponding ability are running in the background.
16
17  The floating window can be used to continue playing a video after the application is switched to the background, or offer a quick entry (for example, bubbles) to the application. Before creating a floating window, an application must apply for the required permission.
18
19
20## When to Use
21
22In the stage model, you can perform the following operations during application window development:
23
24- Setting the properties and content of the main window of an application
25
26- Setting the properties and content of the child window of an application
27
28- Experiencing the immersive window feature
29
30- Setting a floating window
31
32- Listening for interactive and non-interactive window events
33
34The following describes the development procedure specific to each application scenario.
35
36## Available APIs
37
38The table below lists the common APIs used for application window development. For details about more APIs, see [Window](../reference/apis-arkui/arkts-apis-window.md).
39
40| Instance        | API                                                      | Description                                                        |
41| -------------- | ------------------------------------------------------------ | ------------------------------------------------------------ |
42| WindowStage    | getMainWindow(callback: AsyncCallback&lt;Window&gt;): void   | Obtains the main window of this window stage.<br>This API can be used only in the stage model.|
43| WindowStage    | loadContent(path: string, callback: AsyncCallback&lt;void&gt;): void | Loads content to the main window in this window stage.<br>**path**: path of the page from which the content will be loaded. The path is configured in the **main_pages.json** file of the project.<br>This API can be used only in the stage model.|
44| WindowStage    | createSubWindow(name: string, callback: AsyncCallback&lt;Window&gt;): void | Creates a child window.<br>This API can be used only in the stage model.            |
45| WindowStage    | on(eventType: 'windowStageEvent', callback: Callback&lt;WindowStageEventType&gt;): void | Subscribes to window stage lifecycle change events.<br>This API can be used only in the stage model.|
46| Window static method| createWindow(config: Configuration, callback: AsyncCallback\<Window>): void | Creates a child window or system window.<br>**config**: parameters used for creating the window.            |
47| Window         | setUIContent(path: string, callback: AsyncCallback&lt;void&gt;): void | Loads the content of a page, with its path in the current project specified, to this window.<br>**path**: path of the page from which the content will be loaded. The path is configured in the **main_pages.json** file of the project in the stage model.                                    |
48| Window         | setWindowBrightness(brightness: number, callback: AsyncCallback&lt;void&gt;): void | Sets the brightness for this window.                                            |
49| Window         | setWindowTouchable(isTouchable: boolean, callback: AsyncCallback&lt;void&gt;): void | Sets whether this window is touchable.                                    |
50| Window         | moveWindowTo(x: number, y: number, callback: AsyncCallback&lt;void&gt;): void | Moves this window.                                          |
51| Window         | resize(width: number, height: number, callback: AsyncCallback&lt;void&gt;): void | Changes the window size.                                          |
52| Window         | setWindowLayoutFullScreen(isLayoutFullScreen: boolean): Promise&lt;void&gt; | Sets whether to enable the immersive mode for the window layout.                                |
53| Window         | setWindowSystemBarEnable(names: Array&lt;'status'\|'navigation'&gt;): Promise&lt;void&gt; | Sets whether to display the status bar and navigation bar in this window.                                |
54| Window         | setWindowSystemBarProperties(systemBarProperties: SystemBarProperties): Promise&lt;void&gt; | Sets the properties of the status bar and navigation bar in this window.<br>**systemBarProperties**: properties of the status bar and navigation bar.|
55| Window         | showWindow(callback: AsyncCallback\<void>): void             | Shows this window.                                              |
56| Window         | on(type: 'touchOutside', callback: Callback&lt;void&gt;): void | Subscribes to touch events outside this window.                          |
57| Window         | destroyWindow(callback: AsyncCallback&lt;void&gt;): void     | Destroys this window.                                              |
58
59
60## Setting the Main Window of an Application
61
62In the stage model, the main window of an application is created and maintained by a UIAbility instance. In the **onWindowStageCreate** callback of the UIAbility instance, use **WindowStage** to obtain the main window of the application and set its properties. You can also set the properties (for example, **maxWindowWidth**) in the [abilities tag of the module.json5 file](../quick-start/module-configuration-file.md#abilities).
63
64### How to Develop
65
661. Obtain the main window.
67
68   Call **getMainWindow** to obtain the main window of the application.
69
702. Set the properties of the main window.
71
72   You can set multiple properties of the main window, such as the background color, brightness, and whether the main window is touchable. The code snippet below uses the **touchable** property as an example.
73
743. Load content to the main window.
75
76   Call **loadContent** to load content to the main window.
77
78```ts
79import { UIAbility } from '@kit.AbilityKit';
80import { window } from '@kit.ArkUI';
81import { BusinessError } from '@kit.BasicServicesKit';
82
83export default class EntryAbility extends UIAbility {
84  onWindowStageCreate(windowStage: window.WindowStage) {
85    // 1. Obtain the main window of the application.
86    let windowClass: window.Window | null = null;
87    windowStage.getMainWindow((err: BusinessError, data) => {
88      let errCode: number = err.code;
89      if (errCode) {
90        console.error(`Failed to obtain the main window. Code:${err.code}, message:${err.message}`);
91        return;
92      }
93      windowClass = data;
94      console.info(`Succeeded in obtaining the main window. Result:${data}`);
95      // 2. Set the touchable property of the main window.
96      let isTouchable: boolean = true;
97      windowClass.setWindowTouchable(isTouchable, (err: BusinessError) => {
98        let errCode: number = err.code;
99        if (errCode) {
100          console.error('Failed to set the window to be touchable. Cause:' + JSON.stringify(err));
101          return;
102        }
103        console.info('Succeeded in setting the window to be touchable.');
104      })
105    })
106    // 3. Load content to the main window.
107    windowStage.loadContent("pages/page2", (err: BusinessError) => {
108      let errCode: number = err.code;
109      if (errCode) {
110        console.error('Failed to load the content. Cause:' + JSON.stringify(err));
111        return;
112      }
113      console.info('Succeeded in loading the content.');
114    });
115  }
116};
117```
118
119## Setting a Child Window of an Application
120
121You can create an application child window, such as a dialog box, and set its properties.
122
123> **NOTE**
124>
125> In the following scenarios, you are not advised to use child windows. Instead, consider using the [overlay](../reference/apis-arkui/arkui-ts/ts-universal-attributes-overlay.md) capability of components first.
126> - On mobile devices (tablets in non-freeform mode and phones), child windows cannot extend beyond the boundaries of the main window when it is in floating or split-screen mode, just like components.
127> - In split-screen or freeform window mode, components, when compared with child windows, offer better real-time adaptability to changes in the main window's position and size.
128> - On certain platforms, system configurations may restrict child windows to default system animations and rounded shadows, offering no customization options for applications and thereby limiting their versatility.
129
130### How to Develop
131
1321. Create a child window.
133
134   Call **createSubWindow** to create a child window.
135
1362. Set the properties of the child window.
137
138   After the child window is created, you can set its properties, such as the size, position, background color, and brightness.
139
140   You are advised to set the size and position of the child window before calling **showWindow**.
141
142   If the size of the child window is not set, the following will happen after **showWindow** is called:
143    + In [freeform window](./window-terminology.md#freeform-window) mode, the child window will default to the size of the current physical screen.<!--RP3--><!--RP3End-->
144    + In non-freeform window mode, the child window will default to the size of the main window.
145
1463. Load content to and show the child window.
147
148   Call **setUIContent** to load content to the child window and **showWindow** to show the child window.
149
1504. Destroy the child window.
151
152   When the child window is no longer needed, you can call **destroyWindow** to destroy it.
153
154The code snippet for creating a child window in **onWindowStageCreate** is as follows:
155
156```ts
157import { UIAbility } from '@kit.AbilityKit';
158import { window } from '@kit.ArkUI';
159import { BusinessError } from '@kit.BasicServicesKit';
160
161let windowStage_: window.WindowStage | null = null;
162let sub_windowClass: window.Window | null = null;
163
164export default class EntryAbility extends UIAbility {
165  showSubWindow() {
166    // 1. Create a child window.
167    if (windowStage_ == null) {
168      console.error('Failed to create the subwindow. Cause: windowStage_ is null');
169    }
170    else {
171      windowStage_.createSubWindow("mySubWindow", (err: BusinessError, data) => {
172        let errCode: number = err.code;
173        if (errCode) {
174          console.error('Failed to create the subwindow. Cause: ' + JSON.stringify(err));
175          return;
176        }
177        sub_windowClass = data;
178        if (!sub_windowClass) {
179          console.error('sub_windowClass is null');
180          return;
181        }
182        console.info('Succeeded in creating the subwindow. Data: ' + JSON.stringify(data));
183        // 2. Set the position, size, and other properties of the child window.
184        sub_windowClass.moveWindowTo(300, 300, (err: BusinessError) => {
185          let errCode: number = err.code;
186          if (errCode) {
187            console.error('Failed to move the window. Cause:' + JSON.stringify(err));
188            return;
189          }
190          console.info('Succeeded in moving the window.');
191        });
192        sub_windowClass.resize(500, 500, (err: BusinessError) => {
193          let errCode: number = err.code;
194          if (errCode) {
195            console.error('Failed to change the window size. Cause:' + JSON.stringify(err));
196            return;
197          }
198          console.info('Succeeded in changing the window size.');
199        });
200        // 3. Load content to the child window.
201        sub_windowClass.setUIContent("pages/page3", (err: BusinessError) => {
202          let errCode: number = err.code;
203          if (errCode) {
204            console.error('Failed to load the content. Cause:' + JSON.stringify(err));
205            return;
206          }
207          console.info('Succeeded in loading the content.');
208          if (!sub_windowClass) {
209            console.error('sub_windowClass is null');
210            return;
211          }
212          // 3. Show the child window.
213          sub_windowClass.showWindow((err: BusinessError) => {
214            let errCode: number = err.code;
215            if (errCode) {
216              console.error('Failed to show the window. Cause: ' + JSON.stringify(err));
217              return;
218            }
219            console.info('Succeeded in showing the window.');
220          });
221        });
222      })
223    }
224  }
225
226  destroySubWindow() {
227    if (!sub_windowClass) {
228      console.error('sub_windowClass is null');
229      return;
230    }
231    // 4. Destroy the child window when it is no longer needed (depending on the service logic).
232    sub_windowClass.destroyWindow((err: BusinessError) => {
233      let errCode: number = err.code;
234      if (errCode) {
235        console.error('Failed to destroy the window. Cause: ' + JSON.stringify(err));
236        return;
237      }
238      console.info('Succeeded in destroying the window.');
239    });
240  }
241
242  onWindowStageCreate(windowStage: window.WindowStage) {
243    windowStage_ = windowStage;
244    // Create a child window when it is needed, for example, when a touch event occurs in the main window. Calling onWindowStageCreate is not always necessary. The code here is for reference only.
245    this.showSubWindow();
246  }
247
248  onWindowStageDestroy() {
249    // Destroy the child window when it is no longer needed, for example, when the Close button in the child window is touched. Calling onWindowStageDestroy is not always necessary. The code here is for reference only.
250    this.destroySubWindow();
251  }
252};
253```
254
255You can also click a button on a page to create a child window. The code snippet is as follows:
256
257```ts
258// EntryAbility.ets
259import { UIAbility } from '@kit.AbilityKit';
260import { window } from '@kit.ArkUI';
261export default class EntryAbility extends UIAbility {
262  onWindowStageCreate(windowStage: window.WindowStage) {
263    windowStage.loadContent('pages/Index', (err) => {
264      if (err.code) {
265        console.error('Failed to load the content. Cause:' + JSON.stringify(err));
266        return;
267      }
268      console.info('Succeeded in loading the content.');
269    })
270
271    // Transfer the window stage to the Index page.
272    AppStorage.setOrCreate('windowStage', windowStage);
273  }
274}
275```
276
277```ts
278// Index.ets
279import { window } from '@kit.ArkUI';
280import { BusinessError } from '@kit.BasicServicesKit';
281
282let windowStage_: window.WindowStage | undefined = undefined;
283let sub_windowClass: window.Window | undefined = undefined;
284@Entry
285@Component
286struct Index {
287  @State message: string = 'Hello World';
288  private createSubWindow(){
289    // Obtain the window stage.
290    windowStage_ = AppStorage.get('windowStage');
291    // 1. Create a child window.
292    if (windowStage_ == null) {
293      console.error('Failed to create the subwindow. Cause: windowStage_ is null');
294    }
295    else {
296      windowStage_.createSubWindow("mySubWindow", (err: BusinessError, data) => {
297        let errCode: number = err.code;
298        if (errCode) {
299          console.error('Failed to create the subwindow. Cause: ' + JSON.stringify(err));
300          return;
301        }
302        sub_windowClass = data;
303        if (!sub_windowClass) {
304          console.error('sub_windowClass is null');
305          return;
306        }
307        console.info('Succeeded in creating the subwindow. Data: ' + JSON.stringify(data));
308        // 2. Set the position, size, and other properties of the child window.
309        sub_windowClass.moveWindowTo(300, 300, (err: BusinessError) => {
310          let errCode: number = err.code;
311          if (errCode) {
312            console.error('Failed to move the window. Cause:' + JSON.stringify(err));
313            return;
314          }
315          console.info('Succeeded in moving the window.');
316        });
317        sub_windowClass.resize(500, 500, (err: BusinessError) => {
318          let errCode: number = err.code;
319          if (errCode) {
320            console.error('Failed to change the window size. Cause:' + JSON.stringify(err));
321            return;
322          }
323          console.info('Succeeded in changing the window size.');
324        });
325        // 3. Load content to the child window.
326        sub_windowClass.setUIContent("pages/subWindow", (err: BusinessError) => {
327          let errCode: number = err.code;
328          if (errCode) {
329            console.error('Failed to load the content. Cause:' + JSON.stringify(err));
330            return;
331          }
332          console.info('Succeeded in loading the content.');
333          if (!sub_windowClass) {
334            console.error('sub_windowClass is null');
335            return;
336          }
337          // 3. Show the child window.
338          sub_windowClass.showWindow((err: BusinessError) => {
339            let errCode: number = err.code;
340            if (errCode) {
341              console.error('Failed to show the window. Cause: ' + JSON.stringify(err));
342              return;
343            }
344            console.info('Succeeded in showing the window.');
345          });
346        });
347      })
348    }
349  }
350  private destroySubWindow(){
351    if (!sub_windowClass) {
352      console.error('sub_windowClass is null');
353      return;
354    }
355    // 4. Destroy the child window when it is no longer needed (depending on the service logic).
356    sub_windowClass.destroyWindow((err: BusinessError) => {
357      let errCode: number = err.code;
358      if (errCode) {
359        console.error('Failed to destroy the window. Cause: ' + JSON.stringify(err));
360        return;
361      }
362      console.info('Succeeded in destroying the window.');
363    });
364  }
365  build() {
366    Row() {
367      Column() {
368        Text(this.message)
369          .fontSize(50)
370          .fontWeight(FontWeight.Bold)
371        Button(){
372          Text('CreateSubWindow')
373          .fontSize(24)
374          .fontWeight(FontWeight.Normal)
375        }.width(220).height(68)
376        .margin({left:10, top:60})
377        .onClick(() => {
378          this.createSubWindow()
379        })
380        Button(){
381          Text('destroySubWindow')
382          .fontSize(24)
383          .fontWeight(FontWeight.Normal)
384        }.width(220).height(68)
385        .margin({left:10, top:60})
386        .onClick(() => {
387          this.destroySubWindow()
388        })
389      }
390      .width('100%')
391    }
392    .height('100%')
393  }
394}
395```
396
397```ts
398// subWindow.ets
399@Entry
400@Component
401struct SubWindow {
402  @State message: string = 'Hello subWindow';
403  build() {
404    Row() {
405      Column() {
406        Text(this.message)
407          .fontSize(20)
408          .fontWeight(FontWeight.Bold)
409      }
410      .width('100%')
411    }
412    .height('100%')
413    .backgroundColor('#0D9FFB')
414  }
415}
416```
417
418## Experiencing the Immersive Window Feature
419
420To create a better video watching and gaming experience, you can use the immersive window feature to hide the status bar and navigation bar. This feature is available only for the main window of an application. Since API version 10, the immersive window has the same size as the full screen by default; its layout is controlled by the component module; the background color of its status bar and navigation bar is transparent, and the text color is black. When an application window calls **setWindowLayoutFullScreen**, with **true** passed in, an immersive window layout is used. If **false** is passed in, a non-immersive window layout is used.
421
422> **NOTE**
423>
424> Currently, immersive UI development supports window-level configuration, but not page-level configuration. If page redirection is required, you can set the immersive mode at the beginning of the page lifecycle, for example, in the **onPageShow** callback, and then restore the default settings when the page exits, for example, in the **onPageHide** callback.
425
426### How to Develop
427
4281. Obtain the main window.
429
430   Call **getMainWindow** to obtain the main window of the application.
431
4322. Implement the immersive effect. You can use either of the following methods:
433
434   - Method 1: When the main window of the application is a full-screen window, call **setWindowSystemBarEnable** to hide the status bar and navigation bar.
435
436   - Method 2: Call **setWindowLayoutFullScreen** to enable the full-screen mode for the main window layout. Call **setWindowSystemBarProperties** to set the opacity, background color, text color, and highlighted icon of the status bar and navigation bar to create a display effect consistent with that of the main window.
437
4383. Load content to the immersive window.
439
440   Call **loadContent** to load content to the immersive window.
441
442```ts
443import { UIAbility } from '@kit.AbilityKit';
444import { window } from '@kit.ArkUI';
445import { BusinessError } from '@kit.BasicServicesKit';
446
447export default class EntryAbility extends UIAbility {
448  onWindowStageCreate(windowStage: window.WindowStage) {
449    // 1. Obtain the main window of the application.
450    let windowClass: window.Window | null = null;
451    windowStage.getMainWindow((err: BusinessError, data) => {
452      let errCode: number = err.code;
453      if (errCode) {
454        console.error('Failed to obtain the main window. Cause: ' + JSON.stringify(err));
455        return;
456      }
457      windowClass = data;
458      console.info('Succeeded in obtaining the main window. Data: ' + JSON.stringify(data));
459
460      // 2. Implement the immersive effect by hiding the status bar and navigation bar.
461      let names: Array<'status' | 'navigation'> = [];
462      windowClass.setWindowSystemBarEnable(names)
463        .then(() => {
464          console.info('Succeeded in setting the system bar to be visible.');
465        })
466        .catch((err: BusinessError) => {
467          console.error('Failed to set the system bar to be visible. Cause:' + JSON.stringify(err));
468        });
469      // 2. Alternatively, implement the immersive effect by setting the properties of the status bar and navigation bar.
470      let isLayoutFullScreen = true;
471      windowClass.setWindowLayoutFullScreen(isLayoutFullScreen)
472        .then(() => {
473          console.info('Succeeded in setting the window layout to full-screen mode.');
474        })
475        .catch((err: BusinessError) => {
476          console.error('Failed to set the window layout to full-screen mode. Cause:' + JSON.stringify(err));
477        });
478      let sysBarProps: window.SystemBarProperties = {
479        statusBarColor: '#ff00ff',
480        navigationBarColor: '#00ff00',
481        // The following properties are supported since API version 8.
482        statusBarContentColor: '#ffffff',
483        navigationBarContentColor: '#ffffff'
484      };
485      windowClass.setWindowSystemBarProperties(sysBarProps)
486        .then(() => {
487          console.info('Succeeded in setting the system bar properties.');
488        })
489        .catch((err: BusinessError) => {
490          console.error('Failed to set the system bar properties. Cause: ' + JSON.stringify(err));
491        });
492    })
493    // 3. Load content to the immersive window.
494    windowStage.loadContent("pages/page2", (err: BusinessError) => {
495      let errCode: number = err.code;
496      if (errCode) {
497        console.error('Failed to load the content. Cause:' + JSON.stringify(err));
498        return;
499      }
500      console.info('Succeeded in loading the content.');
501    });
502  }
503};
504```
505
506<!--RP2-->
507## Setting a Floating Window<!--RP2End-->
508
509A floating window is created based on an existing task. It is always displayed in the foreground, even if the task used for creating the floating window is switched to the background. Generally, the floating window is above all application windows. You can create a floating window and set its properties.
510
511
512### How to Develop
513
514<!--RP1-->
515**Prerequisites**: To create a floating window (a window of the type **WindowType.TYPE_FLOAT**), you must request the ohos.permission.SYSTEM_FLOAT_WINDOW permission. For details, see [Requesting Permissions for system_basic Applications](../security/AccessToken/determine-application-mode.md#requesting-permissions-for-system_basic-applications).
516<!--RP1End-->
517
5181. Create a floating window.
519
520   Call **window.createWindow** to create a floating window.
521
5222. Set properties of the floating window.
523
524   After the floating window is created, you can set its properties, such as the size, position, background color, and brightness.
525
5263. Load content to and show the floating window.
527
528   Call **setUIContent** to load content to the floating window and **showWindow** to show the window.
529
5304. Destroy the floating window.
531
532   When the floating window is no longer needed, you can call **destroyWindow** to destroy it.
533
534```ts
535import { UIAbility } from '@kit.AbilityKit';
536import { window } from '@kit.ArkUI';
537import { BusinessError } from '@kit.BasicServicesKit';
538
539export default class EntryAbility extends UIAbility {
540  onWindowStageCreate(windowStage: window.WindowStage) {
541    // 1. Create a floating window.
542    let windowClass: window.Window | null = null;
543    let config: window.Configuration = {
544      name: "floatWindow", windowType: window.WindowType.TYPE_FLOAT, ctx: this.context
545    };
546    window.createWindow(config, (err: BusinessError, data) => {
547      let errCode: number = err.code;
548      if (errCode) {
549        console.error('Failed to create the floatWindow. Cause: ' + JSON.stringify(err));
550        return;
551      }
552      console.info('Succeeded in creating the floatWindow. Data: ' + JSON.stringify(data));
553      windowClass = data;
554      // 2. Set the position, size, and other properties of the floating window.
555      windowClass.moveWindowTo(300, 300, (err: BusinessError) => {
556        let errCode: number = err.code;
557        if (errCode) {
558          console.error('Failed to move the window. Cause:' + JSON.stringify(err));
559          return;
560        }
561        console.info('Succeeded in moving the window.');
562      });
563      windowClass.resize(500, 500, (err: BusinessError) => {
564        let errCode: number = err.code;
565        if (errCode) {
566          console.error('Failed to change the window size. Cause:' + JSON.stringify(err));
567          return;
568        }
569        console.info('Succeeded in changing the window size.');
570      });
571      // 3.1 Load content to the floating window.
572      windowClass.setUIContent("pages/page4", (err: BusinessError) => {
573        let errCode: number = err.code;
574        if (errCode) {
575          console.error('Failed to load the content. Cause:' + JSON.stringify(err));
576          return;
577        }
578        console.info('Succeeded in loading the content.');
579        // 3.2 Show the floating window.
580        (windowClass as window.Window).showWindow((err: BusinessError) => {
581          let errCode: number = err.code;
582          if (errCode) {
583            console.error('Failed to show the window. Cause: ' + JSON.stringify(err));
584            return;
585          }
586          console.info('Succeeded in showing the window.');
587        });
588      });
589      // 4. Destroy the floating window when it is no longer needed (depending on the service logic).
590      windowClass.destroyWindow((err: BusinessError) => {
591        let errCode: number = err.code;
592        if (errCode) {
593          console.error('Failed to destroy the window. Cause: ' + JSON.stringify(err));
594          return;
595        }
596        console.info('Succeeded in destroying the window.');
597      });
598    });
599  }
600};
601```
602
603## Listening for Interactive and Non-Interactive Window Events
604
605When running in the foreground, an application may switch between interactive and non-interactive states and process services depending on the state. For example, when the user opens the multitasking screen, an application becomes non-interactive and pauses the service interaction with the user, such as video playback or camera preview; when the user switched back to the foreground, the application becomes interactive again, and the paused service needs to be resumed.
606
607### How to Develop
608
609After a **WindowStage** object is created, the application can listen for the **'windowStageEvent'** event to obtain window stage lifecycle changes, for example, whether the window stage is interactive or non-interactive in the foreground. The application can process services based on the reported event status.
610
611```ts
612import { UIAbility } from '@kit.AbilityKit';
613import { window } from '@kit.ArkUI';
614
615export default class EntryAbility extends UIAbility {
616  onWindowStageCreate(windowStage: window.WindowStage) {
617    try {
618      windowStage.on('windowStageEvent', (data) => {
619        console.info('Succeeded in enabling the listener for window stage event changes. Data: ' +
620          JSON.stringify(data));
621
622        // Process services based on the event status.
623        if (data === window.WindowStageEventType.SHOWN) {
624          console.info('current window stage event is SHOWN');
625          // The application enters the foreground and is interactive by default.
626          // ...
627        } else if (data === window.WindowStageEventType.HIDDEN) {
628          console.info('current window stage event is HIDDEN');
629          // The application enters the background and is non-interactive by default.
630          // ...
631        } else if (data === window.WindowStageEventType.PAUSED) {
632          console.info('current window stage event is PAUSED');
633          // The user opens the multitasking screen when the application is running in the foreground, and the application becomes non-interactive.
634          // ...
635        } else if (data === window.WindowStageEventType.RESUMED) {
636          console.info('current window stage event is RESUMED');
637          // The user switches back from the multitasking screen to the application, and the application becomes interactive.
638          // ...
639        }
640
641        // ...
642      });
643    } catch (exception) {
644      console.error('Failed to enable the listener for window stage event changes. Cause:' +
645        JSON.stringify(exception));
646    }
647  }
648}
649```
650