当前位置: 首页 > news >正文

HarmonyOS 应用开发《掌上英语》第95篇:相机启动恢复实践(ArkTS)

相机启动恢复实践(ArkTS)

当前示例提供完整的相机应用从后台切换至前台启动恢复的流程介绍,方便开发者了解完整的接口调用顺序。

相机应用在前后台切换过程中的状态变化说明:

  • 当相机应用在退后台之后由于安全策略会被强制断流,并且此时相机状态回调会返回相机可用状态,表示当前相机设备已经被关闭,处于空闲状态。
  • 当相机应用从后台切换至前台时,相机状态回调会返回相机不可用状态,表示当前相机设备被打开,处于忙碌状态。
  • 相机应用从后台切换至前台时,需要重启相机设备的预览流、拍照流以及相机会话管理。

在参考以下示例前,建议开发者查看相机开发指导(ArkTS)的具体章节,了解相机管理、设备输入、会话管理等单个操作。

开发流程

相机应用从后台切换至前台启动恢复的调用流程建议如下:

完整示例

Context获取方式请参考:获取UIAbility的上下文信息。

相机应用从后台切换至前台启动恢复需要在页面生命周期回调函数onPageShow中调用,重新初始化相机设备。

import{camera}from'@kit.CameraKit';import{BusinessError}from'@kit.BasicServicesKit';import{common}from'@kit.AbilityKit';letcontext:common.BaseContext;letsurfaceId:string='';asyncfunctiononPageShow():Promise<void>{// 当应用从后台切换至前台页面显示时,重新初始化相机设备。awaitinitCamera(context,surfaceId);}asyncfunctioninitCamera(baseContext:common.BaseContext,surfaceId:string):Promise<void>{console.info('onForeGround recovery begin.');letcameraManager:camera.CameraManager=camera.getCameraManager(baseContext);if(!cameraManager){console.error("camera.getCameraManager error");return;}// 监听相机状态变化。cameraManager.on('cameraStatus',(err:BusinessError,cameraStatusInfo:camera.CameraStatusInfo)=>{if(err!==undefined&&err.code!==0){console.error('cameraStatus with errorCode = '+err.code);return;}console.info(`camera :${cameraStatusInfo.camera.cameraId}`);console.info(`status:${cameraStatusInfo.status}`);});// 获取相机列表。letcameraArray:Array<camera.CameraDevice>=cameraManager.getSupportedCameras();if(cameraArray.length<=0){console.error("cameraManager.getSupportedCameras error");return;}for(letindex=0;index<cameraArray.length;index++){console.info('cameraId : '+cameraArray[index].cameraId);// 获取相机ID。console.info('cameraPosition : '+cameraArray[index].cameraPosition);// 获取相机位置。console.info('cameraType : '+cameraArray[index].cameraType);// 获取相机类型。console.info('connectionType : '+cameraArray[index].connectionType);// 获取相机连接类型。}// 创建相机输入流。letcameraInput:camera.CameraInput|undefined=undefined;try{cameraInput=cameraManager.createCameraInput(cameraArray[0]);}catch(error){leterr=errorasBusinessError;console.error('Failed to createCameraInput errorCode = '+err.code);}if(cameraInput===undefined){return;}// 监听cameraInput错误信息。letcameraDevice:camera.CameraDevice=cameraArray[0];cameraInput.on('error',cameraDevice,(error:BusinessError)=>{console.error(`Camera input error code:${error.code}`);});// 打开相机。awaitcameraInput.open();// 获取支持的模式类型。letsceneModes:Array<camera.SceneMode>=cameraManager.getSupportedSceneModes(cameraArray[0]);letisSupportPhotoMode:boolean=sceneModes.indexOf(camera.SceneMode.NORMAL_PHOTO)>=0;if(!isSupportPhotoMode){console.error('photo mode not support');return;}// 获取相机设备支持的输出流能力。letcameraOutputCap:camera.CameraOutputCapability=cameraManager.getSupportedOutputCapability(cameraArray[0],camera.SceneMode.NORMAL_PHOTO);if(!cameraOutputCap){console.error("cameraManager.getSupportedOutputCapability error");return;}console.info("outputCapability: "+JSON.stringify(cameraOutputCap));letpreviewProfilesArray:Array<camera.Profile>=cameraOutputCap.previewProfiles;if(!previewProfilesArray){console.error("createOutput previewProfilesArray is null!");return;}letphotoProfilesArray:Array<camera.Profile>=cameraOutputCap.photoProfiles;if(!photoProfilesArray){console.error("createOutput photoProfilesArray is null!");return;}// 创建预览输出流,其中参数surfaceId参考上文XComponent组件,预览流为XComponent组件提供的surface。letpreviewOutput:camera.PreviewOutput|undefined=undefined;try{previewOutput=cameraManager.createPreviewOutput(previewProfilesArray[0],surfaceId);}catch(error){leterr=errorasBusinessError;console.error(`Failed to create the PreviewOutput instance. error code:${err.code}`);}if(previewOutput===undefined){return;}// 监听预览输出错误信息。previewOutput.on('error',(error:BusinessError)=>{console.error(`Preview output error code:${error.code}`);});// 创建拍照输出流。letphotoOutput:camera.PhotoOutput|undefined=undefined;try{photoOutput=cameraManager.createPhotoOutput(photoProfilesArray[0]);}catch(error){leterr=errorasBusinessError;console.error('Failed to createPhotoOutput errorCode = '+err.code);}if(photoOutput===undefined){return;}// 创建会话。letphotoSession:camera.PhotoSession|undefined=undefined;try{photoSession=cameraManager.createSession(camera.SceneMode.NORMAL_PHOTO)ascamera.PhotoSession;}catch(error){leterr=errorasBusinessError;console.error('Failed to create the session instance. errorCode = '+err.code);}if(photoSession===undefined){return;}// 监听session错误信息。photoSession.on('error',(error:BusinessError)=>{console.error(`Capture session error code:${error.code}`);});// 开始配置会话。try{photoSession.beginConfig();}catch(error){leterr=errorasBusinessError;console.error('Failed to beginConfig. errorCode = '+err.code);}// 向会话中添加相机输入流。try{photoSession.addInput(cameraInput);}catch(error){leterr=errorasBusinessError;console.error('Failed to addInput. errorCode = '+err.code);}// 向会话中添加预览输出流。try{photoSession.addOutput(previewOutput);}catch(error){leterr=errorasBusinessError;console.error('Failed to addOutput(previewOutput). errorCode = '+err.code);}// 向会话中添加拍照输出流。try{photoSession.addOutput(photoOutput);}catch(error){leterr=errorasBusinessError;console.error('Failed to addOutput(photoOutput). errorCode = '+err.code);}// 提交会话配置。awaitphotoSession.commitConfig();// 启动会话。awaitphotoSession.start().then(()=>{console.info('Promise returned to indicate the session start success.');});// 判断设备是否支持闪光灯。letflashStatus:boolean=false;try{flashStatus=photoSession.hasFlash();}catch(error){leterr=errorasBusinessError;console.error('Failed to hasFlash. errorCode = '+err.code);}console.info('Returned with the flash light support status:'+flashStatus);if(flashStatus){// 判断是否支持自动闪光灯模式。letflashModeStatus:boolean=false;try{letstatus:boolean=photoSession.isFlashModeSupported(camera.FlashMode.FLASH_MODE_AUTO);flashModeStatus=status;}catch(error){leterr=errorasBusinessError;console.error('Failed to check whether the flash mode is supported. errorCode = '+err.code);}if(flashModeStatus){// 设置自动闪光灯模式。try{photoSession.setFlashMode(camera.FlashMode.FLASH_MODE_AUTO);}catch(error){leterr=errorasBusinessError;console.error('Failed to set the flash mode. errorCode = '+err.code);}}}// 判断是否支持连续自动变焦模式。letfocusModeStatus:boolean=false;try{letstatus:boolean=photoSession.isFocusModeSupported(camera.FocusMode.FOCUS_MODE_CONTINUOUS_AUTO);focusModeStatus=status;}catch(error){leterr=errorasBusinessError;console.error('Failed to check whether the focus mode is supported. errorCode = '+err.code);}if(focusModeStatus){// 设置连续自动变焦模式。try{photoSession.setFocusMode(camera.FocusMode.FOCUS_MODE_CONTINUOUS_AUTO);}catch(error){leterr=errorasBusinessError;console.error('Failed to set the focus mode. errorCode = '+err.code);}}// 获取相机支持的可变焦距比范围。letzoomRatioRange:Array<number>=[];try{zoomRatioRange=photoSession.getZoomRatioRange();}catch(error){leterr=errorasBusinessError;console.error('Failed to get the zoom ratio range. errorCode = '+err.code);}if(zoomRatioRange.length<=0){return;}// 设置可变焦距比。try{photoSession.setZoomRatio(zoomRatioRange[0]);}catch(error){leterr=errorasBusinessError;console.error('Failed to set the zoom ratio value. errorCode = '+err.code);}letphotoCaptureSetting:camera.PhotoCaptureSetting={quality:camera.QualityLevel.QUALITY_LEVEL_HIGH,// 设置图片质量高。rotation:camera.ImageRotation.ROTATION_0// 设置图片旋转角度0。}// 使用当前拍照设置进行拍照。photoOutput.capture(photoCaptureSetting,(err:BusinessError)=>{if(err){console.error(`Failed to capture the photo${err.message}`);return;}console.info('Callback invoked to indicate the photo capture request success.');});console.info('onForeGround recovery end.');}
http://www.cnnetsun.cn/news/3880128.html

相关文章:

  • C语言二分查找算法详解:从原理到实现与避坑指南
  • Android Gradle构建产物管理:自定义APK/AAB命名与输出路径实践
  • pi-subagents分布式智能体系统:12个核心配置项详解与实战调优
  • AutoCAD快捷键从入门到精通:设计效率提升的核心修炼手册
  • Excel VBA自定义界面实战:从CommandBar到右键菜单的完整改造指南
  • Harness框架:高效集成DeepSeek构建LLM Agent的工程实践
  • Ubuntu服务器安全加固:PAM模块配置密码策略与登录失败锁定
  • 【AI Agent面试题】Agent 间怎么通信、共享上下文?
  • 2024年衡阳市民营企业转型必看:如何低成本构建一套高效的衡阳商城网站建设方案
  • UAssetGUI实战:脱离虚幻编辑器批量修改资产属性的高效方案
  • SQL注入靶场搭建全攻略:从环境配置到实战调试
  • 游戏音频集成实战:从格式选择到播放控制,以Unity主题曲集成为例
  • 技术争议中如何建立信息甄别框架与验证实践
  • 小城镇建设官方网站如何助力家乡巨变?揭秘基层规划与民生改善的幕后真相
  • Postman为何无视跨域?深入解析同源策略与CORS机制
  • Python+Django电信资费管理系统开发与部署指南
  • PyTorch深度学习从零到项目实战:环境配置、核心概念与完整训练流程
  • Termux完整命令库:移动端Linux环境配置与开发实战指南
  • 红帽系Linux使用yum安装与管理OpenJDK:从原理到生产环境实践
  • 从Prompt工程到AI Loop:构建可验收的大模型自动化工作流
  • 如何选择靠谱的网站开发团队,避坑必看网站建设合同范文详解
  • OpenCore配置工具终极指南:5步可视化配置黑苹果,告别代码恐惧!
  • vSAN集群磁盘组是否可以混用不同型号SSD分析与处理规范
  • STM32 Bootloader与APP的RAM分区与安全跳转实战指南
  • Homebench:本地大语言模型性能评估与基准测试实战指南
  • Windows 11 25H2安全中心变英文的4种修复方法
  • 揭秘四川建设人才网站:如何在行业变革中找到真正的职业归宿与成长机会
  • 深入解析CPU中断系统:从原理到实战性能排查
  • 基于微信消息触发的自动化任务平台QClaw:从原理到实战
  • SPI Flash嵌入式开发实战:从驱动设计到文件系统应用