Android: клонирование рисунка, чтобы сделать StateListDrawable с фильтрами

Я пытаюсь сделать общую функцию фреймворка, которая позволяет выделить любой Drawable при нажатии / сфокусировке / выборе / etc.

Моя функция принимает Drawable и возвращает StateListDrawable, где состояние по умолчанию – это сам Drawable, а состояние для android.R.attr.state_pressed – это то же самое, что и в случае с фильтром, используемым с помощью setColorFilter .

Моя проблема в том, что я не могу клонировать выталкиваемый и сделать отдельный экземпляр этого с применением фильтра. Вот чего я пытаюсь достичь:

 StateListDrawable makeHighlightable(Drawable drawable) { StateListDrawable res = new StateListDrawable(); Drawable clone = drawable.clone(); // how do I do this?? clone.setColorFilter(0xFFFF0000, PorterDuff.Mode.MULTIPLY); res.addState(new int[] {android.R.attr.state_pressed}, clone); res.addState(new int[] { }, drawable); return res; } 

Если я не клонирую, фильтр, очевидно, применяется к обоим состояниям. Я пробовал играть с mutate() но это не помогает.

Есть идеи?

Обновить:

Принятый ответ действительно клонирует. Это мне не помогло, потому что моя общая функция не срабатывает по другой проблеме. Кажется, что когда вы добавляете drawable в StateList, он теряет все свои фильтры.

Попробуйте следующее:

 Drawable clone = drawable.getConstantState().newDrawable(); 

Если вы примените фильтр / etc к drawable, созданный с помощью getConstantState().newDrawable() все экземпляры этого drawable также будут изменены, так как drawables используют constantState в качестве кеша!

Поэтому, если вы покрасьте круг с цветовым фильтром и newDrawable, вы измените цвет всех кругов.

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

 // To make a drawable use a separate constant state drawable.mutate() 

Для хорошего объяснения см .:

http://www.curious-creature.org/2009/05/02/drawable-mutations/

http://developer.android.com/reference/android/graphics/drawable/Drawable.html#mutate ()

Это мое решение, основанное на этом вопросе SO .

Идея заключается в том, что ImageView получает цветной фильтр, когда пользователь прикасается к нему, а цветной фильтр удаляется, когда пользователь перестает касаться его. В памяти всего 1 растровая / растровая карта, поэтому не нужно ее тратить. Он работает так, как должен.

 class PressedEffectStateListDrawable extends StateListDrawable { private int selectionColor; public PressedEffectStateListDrawable(Drawable drawable, int selectionColor) { super(); this.selectionColor = selectionColor; addState(new int[] { android.R.attr.state_pressed }, drawable); addState(new int[] {}, drawable); } @Override protected boolean onStateChange(int[] states) { boolean isStatePressedInArray = false; for (int state : states) { if (state == android.R.attr.state_pressed) { isStatePressedInArray = true; } } if (isStatePressedInArray) { super.setColorFilter(selectionColor, PorterDuff.Mode.MULTIPLY); } else { super.clearColorFilter(); } return super.onStateChange(states); } @Override public boolean isStateful() { return true; } } 

Применение:

 Drawable drawable = new FastBitmapDrawable(bm); imageView.setImageDrawable(new PressedEffectStateListDrawable(drawable, 0xFF33b5e5)); 

Это то, что работает для меня.

 Drawable clone = drawable.getConstantState().newDrawable().mutate(); 

Я ответил на соответствующий вопрос здесь

В принципе, похоже, что StateListDrawables действительно теряют свои фильтры. Я создал новый BitmapDrawale из измененной копии Bitmap, которую я первоначально хотел использовать.

Interesting Posts

Где я могу найти окончательный Selenium WebDriver для Матрицы совместимости Firefox?

Отбор проб в R из вектора различной длины

Ошибка java.lang.StackOverFlow. Подозревали слишком много просмотров?

Лучшая практика для управления файлами Windows PATH / environment?

Почему я могу добавить именованные свойства в массив, как если бы это был объект?

как вычислять среднее / медианное значение для каждой группы в кадре данных в r

перерыв петли, если Esc был нажат

Обновление Windows 8.1 с 32-разрядной версией до версии Windows 64 с 64-разрядной версией

Что быстрее: несколько одиночных INSERT или один многострочный INSERT?

Компиляция программы на C ++ с помощью gcc

Mac OS X .bashrc не работает

Хосты файлы и разблокированные субдомены

Объем компьютера падает при подключении USB-устройства

C ++ где инициализировать статический const

Обновления в реальном времени из базы данных с использованием JSF / Java EE

Давайте будем гением компьютера.