DEV Community

kouwei qing
kouwei qing

Posted on

Input Box Auto-Focus, JS Bridge Implementation, Popup Full-Screen Mask, Mouse Event Adaptation, Web Cross-Domain

[Daily HarmonyOS Next Knowledge] Input Box Auto-Focus, JS Bridge Implementation, Popup Full-Screen Mask, Mouse Event Adaptation, Web Cross-Domain

1. How to Auto-Focus a TextInput or TextArea in HarmonyOS?

Use focusControl.requestFocus to set focus on components that need it. Refer to the documentation:

https://developer.huawei.com/consumer/cn/doc/harmonyos-references-V5/ts-universal-attributes-focus-V5

Example Code:

@Entry
@Component
struct TextInputExample {
  controller: TextInputController = new TextInputController()
  @State inputValue: string = ""
  ep: number = 0;
  del: boolean = false;

  // Custom keyboard component
  @Builder
  CustomKeyboardBuilder() {
    Column() {
      Button('Close Keyboard').onClick(() => {
        // Close the custom keyboard
        this.controller.stopEditing()
      })
      Button('Delete Character').onClick(() => {
        this.inputValue = this.inputValue.substring(0, this.ep-1) + this.inputValue.substring(this.ep)
        this.del = true
      })
      Grid() {
        ForEach([1, 2, 3, 4, 5, 6, 7, 8, 9, '*', 0, '#'], (item: number | string) => {
          GridItem() {
            Button(item + "")
              .width(110).onClick(() => {
              this.inputValue = this.inputValue.substring(0, this.ep) + item + this.inputValue.substring(this.ep)
              this.del = false
            })
          }
        })
      }.maxCount(3).columnsGap(10).rowsGap(10).padding(5)
    }.backgroundColor(Color.Gray)
  }

  build() {
    Column() {
      TextInput({ controller: this.controller, text: this.inputValue })
        // Bind the custom keyboard
        .customKeyboard(this.CustomKeyboardBuilder())
        .margin(10)
        .id('input1') // Set an ID for the component
        .border({ width: 1 })
        // Detect cursor changes and adjust cursor position
        .onChange(() => {
          if(this.del){
            this.controller.caretPosition(--this.ep)
          }else{
            this.controller.caretPosition(++this.ep)
          }
        })
        .onTextSelectionChange((ss) => {
          this.ep = ss;
        })
      Button("Trigger Focus")
        .width(200).height(70).fontColor(Color.White)
        .onClick(() => {
          focusControl.requestFocus('input1') // Focus the TextInput
        })
    }
  }
}
Enter fullscreen mode Exit fullscreen mode

The default input method keyboard type is text input (textinputtype 0). Refer to possible textinputtype values:

https://developer.huawei.com/consumer/cn/doc/harmonyos-references-V5/js-apis-inputmethod-V5

2. What Are the JSBridge Implementation Methods in HarmonyOS?

For app-frontend interactions, refer to:

https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/arkweb-ndk-jsbridge-V5

The figure above shows the general architecture of a universally applicable mini-program. In this architecture, the logic layer relies on the JavaScript runtime自带 by the application, which runs within an existing C++ environment. Through Native interfaces, the logic layer can directly communicate with the view layer (where ArkWeb acts as the renderer) in the C++ environment without falling back to the ArkTS environment to use the ArkTS JSBridge interface.

The left diagram shows a mini-program solution using the ArkTS JSBridge interface. As indicated by the red box, the application must first call into the ArkTS environment and then into the C++ environment. The right diagram shows a solution using the Native JSBridge interface, which eliminates the need to switch between ArkTS and C++ environments, resulting in higher execution efficiency.


The Native JSBridge solution avoids redundant ArkTS environment switches and allows callbacks to run on non-UI threads, preventing UI blockages.

3. How to Set a Full-Screen Mask for bindPopup in HarmonyOS?

Refer to the following demo:

@Entry
@Component
struct PopupExample {
  @State handlePopup: boolean = false
  @State customPopup: boolean = false

  // Popup content builder
  @Builder popupBuilder() {
    Row({ space: 2 }) {
      Image($r("app.media.startIcon")).width(24).height(24).margin({ left: -5 })
      Text('Custom Popup').fontSize(10)
    }.width(100).height(50).padding(5)
  }

  build() {
    Flex({ direction: FlexDirection.Column }) {
      // PopupOptions configuration
      Button('PopupOptions')
        .onClick(() => {
          this.handlePopup = !this.handlePopup
        })
        .bindPopup(this.handlePopup, {
          builder: this.popupBuilder,
          placement: Placement.Top,
          mask: {color: Color.Gray},
          popupColor: Color.Yellow,
          enableArrow: true,
          message: 'This is a popup with PopupOptions',
          placementOnTop: true,
          showInSubWindow: false,
          primaryButton: {
            value: 'confirm',
            action: () => {
              this.handlePopup = !this.handlePopup
              console.info('confirm Button click')
            }
          },
          // Secondary button
          secondaryButton: {
            value: 'cancel',
            action: () => {
              this.handlePopup = !this.handlePopup
              console.info('cancel Button click')
            }
          },
          onStateChange: (e) => {
            console.info(JSON.stringify(e.isVisible))
            if (!e.isVisible) {
              this.handlePopup = false
            }
          }
        })
        .position({ x: 100, y: 150 })
    }.width('100%').padding({ top: 5 })
  }
}
Enter fullscreen mode Exit fullscreen mode

4. The Right-Click Event in the HarmonyOS Web Component Works on 2-in-1 Devices but Fails on Tablets. How to Make It Compatible?

Refer to the Interaction Event Normalization interface to ensure consistent interaction experiences across different devices and minimize adaptation efforts:

5. When the HarmonyOS Web Component Loads Local Files via the file:// Protocol, HTTP Requests from Local JS Files Fail Due to Cross-Domain Restrictions. How to Solve This?

Configure customizeSchemes as described in the documentation:

You need to configure schemeMap and mimeTypeMap manually.

Top comments (0)