前言
补充上一次的alpha06并不是最新版,官方文档记载到alpha10,但是却还有beta01版本,官网还列出了从01->10的所有bug,除此之外alpha06在部分手机上还出现了不能预览前置摄像头的问题(我手机),所以最新版必须盘它。
对beta有兴趣,想更深了解,可以看看4月1号的这个标题链接
刨根问底原则,camerax到此搁置,至最终发行版出来再看了。
改动内容及好处
-
依赖
依赖的量增加了,不仅增加了功能方面的代码,连布局都给你安排了,官网是提倡使用comera-view里的PreviewView,而不是之前的TextureView,说是这种控件可以使图像显示更为流畅(吃瓜),香就行,并且这个PreviewView控件是个FrameLayout,并不如TextureView是个View,所以你懂的,品,你细品。
ext { camerax_version = '1.0.0-beta01' .... } api "androidx.camera:camera-core:$camerax_version" api "androidx.camera:camera-camera2:$camerax_version" api "androidx.camera:camera-lifecycle:$camerax_version" api "androidx.camera:camera-view:1.0.0-alpha08" api "androidx.camera:camera-extensions:1.0.0-alpha08"
application
open class BaseApplication : Application() , CameraXConfig.Provider { override fun getCameraXConfig(): CameraXConfig { return Camera2Config.defaultConfig() } }
-
图像分析
这里多了一个image.close。这个是表示你这个图像已经分析挖完毕,可以丢弃了,之前alpha06的时候这个是放在内部自己使用的,analyze自带一个类似循环的获取图像数据的设计,你也别想控制它,我们只能在不断的循环拿数据中,截取我们需要的一部分资源。
这里用image的close来提示analyze这个帧已经ok了,可以扔了,来执行下一个帧吧,然后就可以不断的循环下去,如果没有close,就说明你一直在处理,则不会再获取camera的数据,所以,不加close,就只能获取初始化的第一帧的数据了,好处不言而喻。
class CameraPicAnalyzer(pixel: PixelCameraInter) : ImageAnalysis.Analyzer { // 图像的平面(像素矩阵)缓冲 private fun ByteBuffer.toByteArray(): ByteArray { rewind() // Rewind the buffer to zero val data = ByteArray(remaining()) get(data) // Copy the buffer into a byte array return data // Return the byte array } private var lastAnalyzedTimestamp: Long = 0 private val bytes = pixel override fun analyze(image: ImageProxy) { val currentTimestamp = System.currentTimeMillis() //计算平均频率不超过每秒一次 if (currentTimestamp - lastAnalyzedTimestamp >= TimeUnit.SECONDS.toMillis(1)) { val bitmap = BitmapUtils.imageToBitmap(image) bytes.data(bitmap!!) lastAnalyzedTimestamp = currentTimestamp } image.close() } }
-
初始化的改动
具体的实现大体逻辑还是和之前一样
为了简化代码,其中的Config部分全部砍掉,config看着本来就是累赘,全合并到功能类上,这里不对照。
从alpha07开始多了CameraSelector等操作方式,一改之前的臃肿编写方式,
imageProxy的格式还是和之前一致是YUV_420_888
val processCameraProvider = ProcessCameraProvider.getInstance(owner as Context) val preview = Preview.Builder() .setTargetAspectRatio(AspectRatio.RATIO_4_3) .build() preview.setSurfaceProvider(viewFinder.previewSurfaceProvider) // 图片文件捕获下载的UseCase imageCapture = ImageCapture.Builder() .setCaptureMode(ImageCapture.CAPTURE_MODE_MAXIMIZE_QUALITY) .build() // 图片设计的UserCase val analyzerUseCase = ImageAnalysis.Builder() .setBackpressureStrategy(ImageAnalysis.STRATEGY_KEEP_ONLY_LATEST) .setTargetResolution(Size(1280, 720)) .build() analyzerUseCase.setAnalyzer(executors,analyze) // 相机选择器 val selector=CameraSelector.Builder() .requireLensFacing(CameraSelector.LENS_FACING_BACK) .build() // 绑定 processCameraProvider.get().bindToLifecycle(owner, selector, preview, imageCapture, analyzerUseCase)
-
文件下载的改动
这里使用了一个ImageCapture.OutputFileOptions,之前直接是file,并且之前如果要给图片添加附带信息,只能通过给ImageCapture中添加MetaData,而现在是将所有的信息传递进了Option中,并且内容比之前更丰富了。
fun getPictureFile(callback : ImageCapture.OnImageSavedCallback) { val file = File(BaseApplication.INSTANCE.applicationContext.filesDir.absolutePath + File.separator + "file_camera") if(!file.exists()){ file.mkdirs() } val resource = File(file.absolutePath,"${TimeUtils.curTimeString}.jpg") if(imageCapture!=null && executors != null){ val option = ImageCapture.OutputFileOptions .Builder(resource) .build() imageCapture!!.takePicture(option,executors,callback) } }
🔗 前言
🔗 Android Temporary
🔗 NO.1 Retrofit
🔗 NO.2 CameraX
🔗 NO.3 GreenDao(&加密问题)
🔗 NO.4 Tinker