我正在制作android应用程序,试图从TextureView拍摄的位图图像生成视频。在这里,我能够从TextureView获取位图图像,并将其保存在内部存储中以供以后的视频生成。但是问题在于,随着位图图像的创建并将其保存在本地存储中,App的堆大小也在迅速增长,后来在将约800张图像另存为.png文件后,它给出了OutOfMemory Exception和Clamp目标GC堆,从258MB扩展到256MB。那么,如何避免堆增长?
我尝试增加应用程序堆的大小,但是随着创建和保存新图像时堆的增长,它没有用。我尝试了位图回收,也将null设置为位图,但性能没有变化。
//用于从TextureView获取位图的代码
a = [1, 2, 3, 3, 4, 4, 6, 6]
[index for index, element in enumerate(a) if index == element]
#gives you a list of indices of `a` with a value equal to the index.
//显示在屏幕上的位图
Bitmap bitmap = textureView.getBitmap(TF_OD_API_INPUT_SIZE, TF_OD_API_INPUT_SIZE);
上面的代码会使用Runnable#run()定期运行和调用
当用户按下下面的记录按钮时,将执行代码,并随着纹理表面的更新而将其保存为本地位图
if(croppedBitmap!=null){
croppedBitmap=null;
}
croppedBitmap = Bitmap.createBitmap((int) canvasWidth, (int) canvasHeight, Bitmap.Config.ARGB_8888);
以下是保存图像时生成的日志。
VideoManager:images_924.png //表示已将925张图像保存在本地,从0开始的索引编制
缓冲区:925/1800 //此处1800 =>将保存的图像总数
@Override
public void onSurfaceTextureUpdated(SurfaceTexture texture) {
if(Utils.isVideoRecordingStarted(activity)){
//if it already has bitmap recycle it to create room
if(mToVideo!=null){
mToVideo.recycle();
mToVideo=null;
}
if(newImage!=null){
newImage.recycle();
newImage=null;
}
//hold bitmap image
mToVideo = textureView.getBitmap(VideoManagerConfig.VIDEO_WIDTH,VideoManagerConfig.VIDEO_HEIGHT);
if(mToVideo!=null) {
if(activity.getResources().getConfiguration().orientation!=ORIENTATION_PORTRAIT){
mToVideo = textureView.getBitmap(VideoManagerConfig.VIDEO_HEIGHT,VideoManagerConfig.VIDEO_WIDTH);
if(mToVideo!=null){
newImage = Utils.RotateBitmap(mToVideo.copy(mToVideo.getConfig(),true),90);
Log.i(ObjectDetectionCameraImpl.TAG,"W: "+newImage.getWidth()+", H: "+newImage.getHeight());
SaveToLocalStorage(newImage);
}
}else {
SaveToLocalStorage(mToVideo.copy(mToVideo.getConfig(),true));
}
mToVideo=null;
}
}else if(isInitilizedVideo && !Utils.isVideoRecordingStarted(activity)){
//video stopped and has something to encode
imageFromTextureListener.getBuffer(getBufferMetaData());
}
}
};
答案 0 :(得分:0)
http://localhost:4200/api/postData回答了尝试缩放图像(虽然在Java中)时发生的类似问题,如下所示:除非发生垃圾收集,否则JVM(尽管Android使用ART)会在需要时不断扩展堆。一直到给定的完整堆大小。简而言之,
Java进程可以自由使用您为其分配的所有内存。