• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Calculating and Adjusting Safe Area Insets
2
3In earlier versions, the screen of most devices is rectangular, and the application UI can be completely displayed. With the popularization of irregular screens such as bezel-less screen and notch screen, rounded corners, cameras, or system navigation bars may appear on the edge of the screen. As a result, some parts of the screen are obscured.
4
5A safe area is a region on the screen that is not obscured by device hardware or system UI elements. It is demarcated from non-safe areas, such as the status bar, notch area, and navigation bar. By default, the application layout is restricted to the safe area. However, the system provides the immersive layout capability, allowing the application to extend the UI to the non-safe area through configuration.
6
7In an immersive experience, web page elements in a **Web** component may be obscured by the status bar, notch area, and navigation bar. In this case, you need to perform avoidance adaptation to ensure that key content, such as text, forms, and interactive components, on the web page avoids non-safe areas. This ensures that users can read and operate without obstruction.
8
9The **Web** component provides the W3C CSS capability for calculating and adjusting safe area insets. By utilizing this capability to avoid obstructions, you can display web pages properly on devices with irregular screens in immersive mode.
10
11## Enabling the Immersive Mode for the Web Component
12
13**Web** components are displayed in the safe area by default. After the immersive mode is enabled, the web page is extended to the status bar and navigation bar to maximize the visible area of the screen, enhance visual continuity, and improve user experience. You can enable the immersive mode of **Web** components in the following ways:
14
15- Use [setWindowLayoutFullScreen](../reference/apis-arkui/arkts-apis-window-Window.md#setwindowlayoutfullscreen9) to set the application window to full screen. When the window is displayed in full screen, the **Web** component can be displayed in non-safe areas.
16
17  ```ts
18  // EntryAbility.ets
19  import { UIAbility } from '@kit.AbilityKit';
20  import { window } from '@kit.ArkUI';
21
22  export default class EntryAbility extends UIAbility {
23    // ...
24    onWindowStageCreate(windowStage: window.WindowStage): void {
25      windowStage.getMainWindow().then(window => {
26        // Set the window to full screen.
27        window.setWindowLayoutFullScreen(true);
28      });
29    }
30  }
31  ```
32
33  ```ts
34  // xxx.ets
35  import { webview } from '@kit.ArkWeb';
36
37  @Entry
38  @Component
39  struct WebComponent {
40    controller: webview.WebviewController = new webview.WebviewController();
41
42    build() {
43      Column() {
44        Web({ src: 'www.example.com', controller: this.controller })
45          .width('100%').height('100%')
46      }
47    }
48  }
49  ```
50
51- Use [expandSafeArea](../reference/apis-arkui/arkui-ts/ts-universal-attributes-expand-safe-area.md) to expand the safe area for **Web** components. You can customize the expansion type and direction. In the following example, the **Web** component can be expanded to the status bar and navigation bar to achieve an immersive effect.
52
53  ```ts
54  // xxx.ets
55  import { webview } from '@kit.ArkWeb';
56
57  @Entry
58  @Component
59  struct WebComponent {
60    controller: webview.WebviewController = new webview.WebviewController();
61
62    build() {
63      Column() {
64        Web({ src: 'www.example.com', controller: this.controller })
65          .width('100%').height('100%')
66          // Expand the component to the default non-safe areas (status bar and navigation bar) and set that only the upper and lower areas are expanded.
67          .expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP, SafeAreaEdge.BOTTOM])
68      }
69    }
70  }
71  ```
72
73## Setting the Web Page Layout in a Viewport
74
75Use **viewport-fit**, which is an attribute of the **\<meta name="viewport">** tag, to set the layout of a web page in a viewport as follows:
76
77```html
78<meta name='viewport' content='viewport-fit=cover'>
79```
80
81As shown in Table 1, the default value of **viewport-fit** is **auto**, which has the same effect as **contain**, indicating that all web page content is displayed within the safe area. **cover** indicates that the web page content completely covers the visible window and may overlap with the non-safe area.
82
83**Table 1** Values of viewport-fit
84
85| Value| Description| Scenario|
86| - | - | - |
87| auto | Default value, which has the same effect as **contain**.| Common web pages that do not require special adaptation.|
88| contain | Restricts web page content within the safe area, and does not overlap with the non-safe area.| Web pages that need to be completely displayed.|
89| cover | Covers the viewport completely and may overlap the non-safe area.| Web pages that need to render the maximum viewport and require avoidance adaptation.|
90
91> **NOTE**
92>
93> Currently, the **Web** component does not support the feature of restricting the web page content to the safe area when the immersive mode is enabled. Therefore, the value **contain** of **viewport-fit** has the same effect as **cover**, that is, the web page content completely fills the **Web** component area.
94
95## Avoidance Adaptation of Web Page Elements
96
97**safe-area-inset-*** is a group of CSS environment variables, which define the distance between the safe area and the edge of the viewport, that is, the distance needs to be avoided in the top, right, bottom, and left directions when the web page content needs to be completely displayed, as shown in the following figure. Unlike other CSS attributes, the attribute name of an environment variable is case sensitive.
98
99**Figure 1** safe-area-inset-*
100
101![web-safe-area-inset](figures/arkweb_safe_area_inset.png)
102
103When **viewport-fit=cover** is set, the ArkWeb kernel continuously monitors the locations and sizes of **Web** components and system non-safe areas. It calculates the specific distances that need to be avoided in the four directions based on the overlapping parts and sets these distances to the environment variables **safe-area-inset-***. On a rectangular display (such as the screen of a regular PC/2-in-1 device), these values are zero. On a non-rectangular display (such as a circular watch face or a mobile device screen), an inner rectangular area defined by **safe-area-inset-*** is a safe area. Web page content is completely displayed in the safe area, to avoid being cropped by the non-rectangular display area.
104
105The avoidance adaptation of web page elements depends on the CSS function **env()**, which is used to obtain the environment variables provided by the browser or system. You can use the **env()** function to obtain the value of **safe-area-inset-***. Through CSS **env(safe-area-inset-*)**, you can define the distance to be avoided on a web page to implement cross-device avoidance, without the need to pay attention to the location and size of the non-safe areas. The syntax is as follows:
106
107```
108/* Avoidance values in the top, right, bottom, and left directions. */
109env(safe-area-inset-top);
110env(safe-area-inset-right);
111env(safe-area-inset-bottom);
112env(safe-area-inset-left);
113
114/* Set the avoidance value based on fallback. The second parameter indicates the fallback value when the environment variable does not exist. */
115/* For details about the length unit, see https://developer.mozilla.org/en-US/docs/Web/CSS/length. */.
116env(safe-area-inset-top, 20px);
117env(safe-area-inset-right, 1em);
118env(safe-area-inset-bottom, 0.5vh);
119env(safe-area-inset-left, 1.4rem);
120
121/* env() can be calculated based on some mathematical calculation functions `calc()`,`min()`,`max()`. */
122calc(env(safe-area-inset-top) + 10px)
123min(env(safe-area-inset-left), 50px)
124max(env(safe-area-inset-bottom), 30px)
125```
126
127> **NOTE**
128>
129> When **env(safe-area-inset-*)** is used for avoidance, set **viewport-fit** to **cover**. When **viewport-fit** is set to **contain**, the value of **env(safe-area-inset-*)** is 0.
130
131## Best Practices
132
133When the immersive mode is enabled for the **Web** component, the rendered content may overlap with the non-safe area, affecting user browsing and interaction, as shown in Figure 2. Non-safe areas include the top status bar, notch area and bottom navigation bar. In the immersive mode, the title bar of the **index.html** web page is obscured by the notch area, and the bottom tab area overlaps the navigation bar.
134
135**Figure 2** Web page elements obscured by non-safe areas when the immersive mode is enabled
136
137![web-safe-area-immersion](figures/arkweb_safe_area_immersion.png)
138
139```html
140<!-- index.html -->
141<!DOCTYPE html>
142<html lang="en">
143<head>
144    <meta charset="UTF-8">
145    <meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover">
146    <style>
147        body {
148            margin: 0;
149            background: #f6f6f6;
150        }
151        .edge {
152            position: fixed;
153            display: flex;
154            width: 100%;
155            background: #fefefe;
156        }
157        .title-bar {
158            align-items: center;
159            justify-content: center;
160            top: 0;
161            height: 40px;
162        }
163        .content {
164            margin: 8px;
165            padding-top: 40px;
166        }
167        .tabs {
168            justify-content: space-around;
169            bottom: 0;
170            height: 40px;
171        }
172        .tab {
173            padding: 10px;
174        }
175        .tab.active {
176            color: Blue;
177        }
178    </style>
179</head>
180<body>
181    <div>
182        <div class="edge title-bar">Example page</div>
183        <div class="content">
184            <p>Contents of page</p>
185        </div>
186    </div>
187    <div class="edge tabs">
188        <div class="tab active">Tab1</div>
189        <div class="tab">Tab2</div>
190        <div class="tab">Tab3</div>
191    </div>
192</body>
193</html>
194```
195
196You can use **env(safe-area-inset-*)** to define the CSS style, ensuring that texts, images, and interaction components avoid non-safe areas. In the following example, **env(safe-area-inset-*)** is used to update the CSS style of **index.html** so that the main content of the web page avoids the non-safe area, as shown in Figure 3.
197
198```
199.title-bar {
200    align-items: center;
201    justify-content: center;
202    top: 0;
203    height: 40px;
204    padding-top: env(safe-area-inset-top); /* Set padding-top to avoid the upper non-safe area. */
205}
206.content {
207    margin: 8px;
208    padding-top: calc(env(safe-area-inset-top) + 40px); / * Set the title bar to increase the padding-top height. */
209}
210.tabs {
211    justify-content: space-around;
212    bottom: 0;
213    height: calc(env(safe-area-inset-bottom) + 40px); /* Increase the height of the tab area to avoid the lower non-safe area. */
214}
215```
216
217**Figure 3** Avoiding non-safe areas when the immersive mode is enabled
218
219![web-safe-area](figures/arkweb_safe_area_avoid.png)
220