Пользовательский вид Android getForeground() возвращает значение null, даже если он задан в xml

#java #android #android-layout

Вопрос:

У меня проблема с тем, что мое встроенное пользовательское представление не соблюдается setClickable(false) .

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

Рисование переднего плана задано в xml, я не знаю, почему getForeground() оно не возвращается.

(Чтобы получить тот же эффект, я хотел использовать селекторы в state_active качестве определяющей переменной, но я читал, что она где-то используется Android, поэтому я воздержался от ее использования. Мое собственное введение state_enable_ripple не произвело того эффекта, которого я хотел.)

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

 <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:clickable="false"
    android:focusable="false"
    android:foreground="@drawable/ripple_colors">

    <ProgressBar/>

    <Button />

</FrameLayout>
 
     @Override
    public void setClickable(boolean clickable) {
        super.setClickable(clickable);
        Timber.d("foreground %s", getForeground());
        Timber.d("foreground tint %s", getForegroundTintList());
        if (getForeground() != null) {
            Timber.d("i co");
            getForeground().mutate().setVisible(clickable, false);
        }
    }
 

Комментарии:

1. Я нигде не вижу никаких обычаев View . Я вижу <FrameLayout> , что у него есть описанные атрибуты, но так как это обычный класс платформы, данный код не может работать с ним, так как это внутренний View код. Кроме того, если этот код предполагает , что передний план будет установлен android:foreground="..." к тому времени, когда это setClickable() потребуется android:clickable="false" , вам действительно не следует этого предполагать.

2. Отображение фрейма встроено в другое место в качестве пользовательского представления. XML-код представляет файл макета пользовательского представления. Почему я не должен предполагать, что передний план установлен? При создании экземпляра представления я раздуваю вложенные представления и обрабатываю их ножом для масла. Я также называю это «ваааай в жизнь вида».

3. Эти атрибуты не входят в ваши пользовательские <View> настройки . Они этим <FrameLayout> занимаются . Вы не можете выйти на передний план, FrameLayout обращаясь getForeground() к своему обычаю View . Вам придется позвонить getForeground() по этому FrameLayout поводу . Если эти атрибуты должны быть в вашем обычае <View> , вам нужно переместить их туда. Кроме того, если ваш обычай View является FrameLayout подклассом, то вам, вероятно, это вообще не нужно <FrameLayout> , а скорее <merge> теги, хотя атрибуты все равно нужно будет переместить.

4.Что касается другого вопроса, почему вы думаете, что android:foreground это обязательно будет установлено раньше android:clickable ? Или вы хотите setClickable() сказать, что сами куда-то звоните отдельно? Я не совсем уверен, какова там цель.

5. Да, хорошо, вы понимаете, что я имел в виду, что касается порядка атрибутов. После super вызова конструктора оба этих атрибута будут установлены к тому времени, так что после этого вы сможете внести коррективы в свой конструктор; вы просто не должны предполагать ничего иного. Также да, инфляция-это правильный термин там. В любом случае, рад, что ты с этим разобрался. Я на самом деле мало что сделал, кроме как указал на (распространенную) путаницу между обычаем View и его внутренней компоновкой, так что, вероятно, не стоит давать полный ответ. 🙂 Пожалуйста, не стесняйтесь отвечать сами, если хотите. Хотя спасибо тебе. Я ценю ваше предложение. Ваше здоровье!