2015-02-16 2 views
0

У меня есть активность, которая показывает некоторые полноэкранные изображения в кроссфейде. Всего 6 изображений. Для этого я использовал одновременно 2 анимации ImageViews и 2, один из которых уменьшает первое изображение, а второе - во втором. Я использовал это видео в качестве ссылки https://www.youtube.com/watch?v=9XbKMUtVnJAНепрерывный кроссфейд изображений и из памяти

Поскольку мне нужно, чтобы он работал непрерывно, я использовал таймер для планирования анимации каждые 4 секунды. Все работает, но использует огромное количество памяти. Для того, чтобы загрузить изображения, которые я пробовал:

  • основной не рекомендуемый способ, используемый в видео, т.е. загружать все изображения в вытяжке массиве
  • настройки изображения с помощью imageview.setImageResource
  • загрузки изображений с использованием средств Picasso

Весь этот метод интенсивно связан с памятью, вызывая исключение из памяти на более старых устройствах (например, Galaxy S2). Подход Пикассо работает неправильно.

Я уверен, что есть лучший способ сделать это, но я не знаю, какие-либо предложения?

Вот соответствующий код:

private void animateImageview(){ 
    prevImageView.animate().alpha(0); 
    nextImageView.animate().alpha(1).setListener(new AnimatorListenerAdapter() { 
     @Override 
     public void onAnimationEnd(Animator animation) { 
      mCurrentDrawable = 
        (mCurrentDrawable + 1) % imagesToShow.length; 
      int nextDrawableIndex = 
        (mCurrentDrawable + 1) % imagesToShow.length; 
      prevImageView.setImageResource(imagesToShow[mCurrentDrawable]); 

      nextImageView.setImageResource(imagesToShow[nextDrawableIndex]); 

      nextImageView.setAlpha(0f); 
      prevImageView.setAlpha(1f); 
     } 
    }); 

protected void onCreate(Bundle savedInstanceState) { 

    ... 

prevImageView.setImageResource(imagesToShow[0]); 
nextImageView.setImageResource(imagesToShow[1]); 

    new Timer().scheduleAtFixedRate(new TimerTask() { 
     @Override 
     public void run() { 
      animateImageview(); 
     } 
    }, 5000, 4000); 

} 

Edit: вариант largeHeap в манифесте, кажется, чтобы решить эту проблему, но я не уверен, что я делаю это дело прямо в любом случае.

Edit2: Сущности с решением я использовал https://gist.github.com/alexmazza/003e3449c02fe58848a9

+0

Каков размер каждого изображения? – Fahim

+0

Работает ли какое-то время, пока не закончится память? У вас может быть утечка памяти где-то. – JonasCz

+0

Изображения 1536x2048 загружены в изображение с помощью centercrop (это почти полноэкранный режим). На моем Nexus 5 он не падает, но на S2 он разбился на третьем изображении. – alex

ответ

0

Пожалуйста, удалите largeHeap опцию из манифеста. Это не проблема, это подметает проблему под ковриком.

Это проблема

Изображения 1536x2048 загружены в ImageView

Вы должны не просто пытаться загрузить изображение в максимальном разрешении, потому что, как вы сказали, в Например, S2, который имеет дисплей 800 x 480, в чем смысл?

Вообще говоря, вы должны вместо этого загружать растровое изображение в память настолько, насколько вам это необходимо (в вашем случае оно должно быть таким же большим, как ImageView). Вы можете следить за очень хорошим руководством для этого в the official docs.

Чтобы избежать исключений java.lang.OutOfMemory, перед декодированием его, если вы абсолютно доверяете источнику, чтобы предоставить вам данные предсказуемо размер изображения, что удобно помещается в пределах доступной памяти проверьте размеры растрового изображения.

[....]

Например, это не стоит загрузки 1024x768 пиксель изображения в памяти, если он будет в конечном итоге будет отображаться в 128x96 пикселей миниатюры в ImageView.

Надеюсь, это поможет.

+0

Да, это правильное решение, но есть две проблемы: я использую asynctask для загрузки растрового изображения, декодированного с использованием кода в документации. Если работает во время анимации, но первая загрузка, перед анимацией, показывает сплошной цвет. Некоторое качество изображения низкое после масштабирования на S2. – alex

+0

Можете ли вы вставить еще один код? Или даже создать сущность с соответствующим фрагментом. –

+0

Решено: проблема в том, что ImageViews имеют match_parent как ширину, поэтому, если я попытаюсь поместить изображение во время выполнения, получая размер ImageView, он не работает при первом загрузке, потому что размер еще не известен. Я решил использовать Picasso, добавляя обратный вызов для установки альфа-изображения imaview при загрузке. – alex

Смежные вопросы