Размер кучи приложения быстро растет при сохранении нескольких растровых изображений из Textureview - PullRequest
0 голосов
/ 26 марта 2019

Я делаю приложение для Android, где пытаюсь сгенерировать видео из растровых изображений, взятых из TextureView.Здесь я могу получить растровые изображения из TextureView и сохранить их во внутренней памяти для последующего создания видео.Но проблема в том, что растровые изображения создаются и сохраняются в локальном хранилище, размер кучи приложения также быстро растет, а позже, после сохранения около 800 изображений в виде файла .png, он создает исключение OutOfMemory с целевой кучей GC Clamp от 258 МБ до 256 МБ.Итак, как мне избежать роста кучи?

Я пытался увеличить размер кучи приложения, но это бесполезно, поскольку куча растет по мере создания и сохранения новых изображений.Я попытался повторно использовать растровое изображение, а также установить нулевое значение для растрового изображения, но без изменений производительности.

// код для получения растрового изображения из текстуры *

Bitmap bitmap = textureView.getBitmap(TF_OD_API_INPUT_SIZE, TF_OD_API_INPUT_SIZE);

// Растровое изображение, отображаемое на экране

if(croppedBitmap!=null){
            croppedBitmap=null;
 }

 croppedBitmap = Bitmap.createBitmap((int) canvasWidth, (int) canvasHeight, Bitmap.Config.ARGB_8888);

приведенный выше код периодически запускается и вызывается с использованием Runnable # run ()

Когда пользователь нажимает кнопку записи под кодом, он выполняется и по мере обновления поверхности текстуры, которая сохраняется как растровое изображение локально

@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());
                    }
                }
            };

Ниже приведены журналы, которые создаются при сохранении изображений.

VideoManager: images_924.png // означает, что 925 изображений уже сохранены локально, индексирование началось с 0

Буфер:925/1800 // здесь 1800 => всего изображений, которые будут сохранены

Following the link to log file:  

https://drive.google.com/open?id=1GxFV-h2V68FSoWRs9K1AYhZChnlTFFqq

1 Ответ

0 голосов
/ 26 марта 2019

На аналогичную проблему, возникшую при попытке увеличить изображение (хотя в java), был дан ответ здесь следующим образом: если не происходит сборка мусора, JVM (хотя Android использует ART) продолжает расширять кучу, как и когдаэто необходимо, вплоть до полного размера кучи, данного ему.Короче говоря,

Java-процесс может свободно использовать всю память, которую вы ему дали.

...