HarmonyOS 鸿蒙Next onBackground

发布于 1周前 作者 sinazl 来自 鸿蒙OS

HarmonyOS 鸿蒙Next onBackground

3.2原来在相机按取消键进入onBackground后自动onWindowStageDestroy后onDestroy。

5.0如上图在按返回键进入onBackground后不会到onWindowStagesDestroy,而且会继续计时。

这是系统升级后改的吗,代码是3.2移植来的一摸一样的

cke_437.png


更多关于HarmonyOS 鸿蒙Next onBackground的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html

4 回复

楼主您好,请问楼主你是通过什么方式移植的?方便发一段调用相机的代码吗?

更多关于HarmonyOS 鸿蒙Next onBackground的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


export class ScannerImp extends ScannerStub implements BaseDeviceService { initialized = InitializeState.PADDING

private cameraId: number
private bundle: Bundle
private scanParam
private timer: Timer
ERROR_ENUM = scannerApi.ErrorCode
errorCodeOffset = 0x10910000
private resultNotified = false

constructor(param: Bundle) {
    super()
    this.bundle = param
    this.cameraId = param.cameraId
}

initialize(): Promise<void> {
    logger.info("initialize " + scannerApi.CameraId[this.cameraId])
    return new Promise(async (resolve, reject) => {
        resolve()
    })
}

init(config): Promise<void> {
    return Promise.resolve()
}

startScan(param: Bundle): Promise<void> {
    logger.info(`startScan ${JSON.stringify(param)}`)
    this.scanParam = param
    this.resultNotified = false
    return new Promise(async (resolve, reject) => {
        if (hasStarted) {
            logger.error(`Scanner busy`)
            reject({ code: 1, message: "Scanner busy" })
            return
        }
        hasStarted = true

        this.setTimer()
        this.subscribeScanEvent()
        if (this.cameraId == scannerApi.CameraId.FRONT) {
            try {
                if (mScanner == null) {
                    mScanner = new ScanDecoder(this.bundle)
                    await mScanner.openDevice(this.cameraId)
                }
                if (this.scanParam?.["showDefaultUI"] != false) {
                    await this.startScanView()
                }
                await mScanner.startScan(param)
                resolve()
            } catch (error) {
                this.onFinish()
                convertErrorCode(logger, reject, error, this.errorCodeOffset, this.ERROR_ENUM)
            }
        } else {
            try {
                logger.info("close ScanDecoder")
                await mScanner?.closeDevice()
                logger.info("close ScanDecoder 1")
                mScanner = null
                await this.startScanView()
                resolve()
            } catch (error) {
                logger.error("failed to close ScanDecoder")
                this.onFinish()
                convertErrorCode(logger, reject, error, this.errorCodeOffset, this.ERROR_ENUM)
            }
        }
    })
}

stopScan(): Promise<void> {
    logger.info(`stopScan`)
    this.onFinish()
    return mScanner?.stopScan()
}

on(type: 'scanSuccess' | 'scanFail', callback: any): Promise<void> {
    logger.info(`on[${type}] event`)
    if (type === 'scanSuccess') {
        successCallback = callback
    } else {
        failCallback = callback
    }
    return Promise.resolve()
}

off(type: 'scanSuccess' | 'scanFail'): Promise<void> {
    logger.info(`off[${type}] event`)
    if (type === 'scanSuccess') {
        successCallback = null
    } else {
        failCallback = null
    }
    return Promise.resolve()
}

private async subscribeScanEvent() {
    logger.debug("subscribeScanEvent")
    //订阅者信息
    emitter.once({ eventId: EventType.EVENT_STOP_SCAN, priority: emitter.EventPriority.IMMEDIATE }, () => {
        this.onFinish()
        this.stopScan()
    })
    emitter.once({ eventId: EventType.EVENT_SCAN_RESULT, priority: emitter.EventPriority.IMMEDIATE }, (data) => {
        if (this.resultNotified || data.data.cameraId != this.cameraId) {
            logger.warn("result already notified")
            return
        }
        this.onFinish()
        if (data.data.code == 0) {
            const result = BytesUtil.hexString2Bytes(data.data.result)
            logger.debug(`scanSuccess: ${result} cameraId: ${this.cameraId}`)
            if (successCallback) {
                successCallback(result)
            }
        } else {
            logger.error(`on scanFail: ${data.data.code} ${data.data.message}`)
            if (failCallback) {
                failCallback(data.data.code)
            }
        }
    })
}

private setTimer() {
    const timeout = this.scanParam?.timeout == null ? scannerApi.DEFAULT_TIMEOUT : this.scanParam.timeout
    logger.debug(`set timer ${timeout}`)
    this.timer = new Timer()
    this.timer.start(() => {
        publishResult(this.cameraId, scannerApi.ErrorCode.ERROR_TIMEOUT)
        mScanner?.stopScan()
    }, timeout)
}

private removeTimer() {
    logger.debug("remove timer")
    this.timer?.stop()
}

private onFinish() {
    logger.info("onFinish")
    emitter.off(EventType.EVENT_SCAN_RESULT)
    emitter.off(EventType.EVENT_STOP_SCAN)
    this.resultNotified = true
    this.removeTimer()
    hasStarted = false
    //避免出现问题关闭时,页面还未成功启动导致无法关闭的情况
    setTimeout(() => {
        publishClose()
    }, 30)
}

async release() {
    logger.info("release")
    this.initialized = InitializeState.PADDING
    mScanner?.closeDevice()
    mScanner = null
}

private startScanView(): Promise<void> {

    const url = this.cameraId == scannerApi.CameraId.BACK ? 'PageAbility/scanner/ScanPreviewer' : 'PageAbility/scanner/ScanPrompt'
    const timeout = this.scanParam?.["timeout"] == null ? scannerApi.DEFAULT_TIMEOUT : this.scanParam?.["timeout"]
    return new Promise(async (resolve, reject) => {
        try {
            let mContext = globalThis.serviceContext
            let want = {
                bundleName: 'oha.icbc.apiservice',
                abilityName: 'PageAbility',
                parameters: {
                    url: url,
                    cameraId: this.cameraId,
                    timeout: timeout,
                    [wantConstant.Params.ABILITY_BACK_TO_OTHER_MISSION_STACK]: true
                }
            }

            if (mContext) {
                await mContext.startAbility(want)
                resolve()
                logger.info('start callee ability succeed')
            }
        } catch (error) {
            logger.error(`start callee ability failed with ${error.code}`)
            reject(error)
        }
    })
}

}

5.0版本 onWindowStageDestro的销毁是在ondestory之前,应用切换到后台不会销毁窗口管理器,一般只在应用销毁的时候才会销毁窗口管理器,可以写在onbackground回调中来释放资源

HarmonyOS 鸿蒙Next onBackground

在HarmonyOS中,onBackground通常指的是应用进入后台时的回调处理。在鸿蒙系统的应用开发中,当应用从前台切换到后台时,系统会触发相应的生命周期回调,以便应用可以执行必要的清理或保存工作。

具体来说,onBackground并非一个直接的API调用,而是应用生命周期管理中的一个状态。在鸿蒙应用开发框架中,你需要通过实现特定的生命周期回调接口来捕获这一状态变化。例如,使用AbilityLifecycle接口中的onStoponPause等方法来近似地处理应用进入后台的逻辑。这些方法会在应用界面不可见或被系统回收资源时调用。

需要注意的是,鸿蒙系统对应用后台行为有严格的限制,以保护用户体验和系统资源。因此,开发者在设计应用时,应尽量减少后台活动,避免不必要的资源消耗。

如果你的应用需要在后台执行某些任务,可以考虑使用鸿蒙系统的后台任务调度机制,如定时任务、服务组件等,以确保任务能够在符合系统策略的前提下执行。

如果问题依旧没法解决请联系官网客服,官网地址是:https://www.itying.com/category-93-b0.html

回到顶部