DEV Community

Cover image for HarmonyNEXT: Immersive Effect Implementation
harmony
harmony

Posted on

HarmonyNEXT: Immersive Effect Implementation

This article tags: HarmonyOS/ArkUI
API supported in this article> = 18

the main purpose of realizing immersive effect is to improve the user experience, make the effect of the status bar consistent with the theme of the page, and increase the visual experience. Just Imagine, if there is no immersion, it will appear very abrupt visually. As shown in the following figure, you can see that the page is red, while the status bar is white, which is very incompatible.

Image description

It is precisely because of immersion that the developed applications look so fresh visually. It can be said that many applications on the market have been adapted to immersion. We can open an application at will, such as WeChat, such as Alipay, such as various shopping software, and the transparent status bar at the top can be seen everywhere.

Image description

What we need to know is that immersive effect mainly refers to extending the application content to the edge of the screen by hiding or transparently making the status bar and navigation bar, that is, extending to the status bar area at the top and the navigation bar area at the bottom. The main purpose, as mentioned above, is to improve the user experience.

In the development of Hongmeng, it can be said that it is very simple to realize an immersion type. At present, there are two ways to realize it, one is independent setting within the page, that is, avoiding safe areas, and the other is global configuration.

Safe Area Avoidance

Safe area avoidance is mainly to achieve immersive effect by setting expandSafeArea attribute to components in the page. We must know that the so-called safe area refers to the display area of the page, that is, the area outside the status bar and navigation bar area.

expandSafeArea

Click on the expandSafeArea attribute, we can enter the source code, we can see that expandSafeArea currently receives two parameters, the first parameter types, its type is Array , identified by a question mark, you can know that it is not necessary to pass parameters, its function is mainly to configure the type of extended security area, when no metadata configuration item is added, the page thing does not avoid digging holes, CUTOUT type does not take effect; The second parameter edges, its type is Array , It is also an optional parameter. Its main function is to configure the direction of expanding the security area.

 expandSafeArea(types?: Array<SafeAreaType>, edges?: Array<SafeAreaEdge>): T;
Enter fullscreen mode Exit fullscreen mode

SafeAreaType

the enumeration types of extended security zones. Currently, there are three types.

Name description
SYSTEM the system default non-security area, including the status bar, navigation bar.
CUTOUT non-safe areas of equipment, such as bangs or dug-out screen areas.
KEYBOARD soft keyboard area.

SafeAreaEdge

there are currently four directions for expanding the security zone.

Name description
TOP upper area.
BOTTOM lower area.
START Front area.
END the tail area.

Main realization

the implementation is very simple, the code is as follows:

 Column() {

    }.width("100%")
    .height("100%")
    .backgroundColor(Color.Red)
    .expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP, SafeAreaEdge.BOTTOM])
Enter fullscreen mode Exit fullscreen mode

if we look at the actual operation effect, we can see that both the navigation bar and the status bar have been immersive.

Image description

If you want to modify the icon color of the status bar, you can combine windows to achieve.

In an independent page, in addition to the above security area avoidance, we can also directly obtain getLastWindow and set it. The effect is exactly the same as the security area setting.

aboutToAppear(): void {
    window.getLastWindow(getContext(), (_, win) => {
      win.setWindowLayoutFullScreen(true).then(() => {
        console.info('Succeeded in setting the window layout to full-screen mode.');
      }).catch((err: BusinessError) => {
        console.error('Failed to set the window layout to full-screen mode. Cause:' + JSON.stringify(err));
      });
    })
  }
Enter fullscreen mode Exit fullscreen mode

Global Settings

in actual development, if our entire project is immersive, then we can use global configuration, which will be applied to all pages. Its implementation is mainly set by the setWindowLayoutFullScreen method in window.

We can configure the following code in the EntryAbility of the main entrance:

onWindowStageCreate(windowStage: window.WindowStage): void {

    let windowClass: window.Window = windowStage.getMainWindowSync()
    windowClass.setWindowLayoutFullScreen(true).then(() => {
      console.info('Succeeded in setting the window layout to full-screen mode.');
    }).catch((err: BusinessError) => {
      console.error('Failed to set the window layout to full-screen mode. Cause:' + JSON.stringify(err));
    });
}
Enter fullscreen mode Exit fullscreen mode

in addition to the above methods, you can also obtain the window asynchronously through Promise. The code is as follows:

  let window=await windowStage.getMainWindow()
Enter fullscreen mode Exit fullscreen mode

when we set up the above code, if we run the project, we will find that our content page will expand into non-secure areas.

Image description

In order to solve the above problem, the content in the safe area needs to avoid the navigation bar and status bar. In this case, we need to take the overall UI view, under the status bar, we can first get the height of the status bar, and then set it:

Column() {
        Text("我是标题")
          .width("100%")
          .height(40)
          .textAlign(TextAlign.Center)
          .fontColor(Color.White)
      }.width("100%")
      .padding({ top: this.navHeight })
      .backgroundColor(Color.Red)
Enter fullscreen mode Exit fullscreen mode

as you can see, our title has been displayed normally.

Image description

The code for obtaining the height of the status bar and navigation bar is as follows. If you need to obtain the window, you can obtain it by using window.getLastWindow.

let type = window.AvoidAreaType.TYPE_NAVIGATION_INDICATOR;
let avoidArea = windowClass.getWindowAvoidArea(type);
let bottomRectHeight = avoidArea.bottomRect.height; 

let type = window.AvoidAreaType.TYPE_SYSTEM; 
let avoidArea = win.getWindowAvoidArea(type);
let topRectHeight = avoidArea.topRect.height; 
Enter fullscreen mode Exit fullscreen mode

Another thing to note is that Immersive can change the color of the properties in the status bar, as shown below.

let windowClass: window.Window = windowStage.getMainWindowSync()
    let SystemBarProperties: window.SystemBarProperties = {
      statusBarColor: '#FFC0CB',
      statusBarContentColor: "#ffffff",
    };

    try {
      windowClass.setWindowSystemBarProperties(SystemBarProperties).then(() => {
        console.info('Succeeded in setting the system bar properties.');
      }).catch((err: BusinessError) => {
        console.error(`Failed to set the system bar properties. Cause code: ${err.code}, message: ${err.message}`);
      });
    } catch (exception) {
      console.error(`Failed to set the system bar properties. Cause code: ${exception.code}, message: ${exception.message}`);
    }
Enter fullscreen mode Exit fullscreen mode

Precautions

if you want to set immersion for a single page, you recommend use expandSafeArea to avoid safe areas here, because expandSafeArea attribute is set for components and will not affect other pages, but only has effect on the current page. When using expandSafeArea attribute, if the root component is a scroll component, it will not take effect, which should be noted. If the whole project needs to be immersed, you can use global configuration, and in the content area, you need to control the position of the components to avoid the status bar or navigation bar overlaying the content area.

Top comments (0)