Поле FrameLayout не работает

79

Моя структура макета такая

LinearLayout
    FrameLayout
       ImageView
       ImageView
    FrameLayout
    TextView
LinearLayout

Я установил поля для двух ImageView, которые находятся внутри FrameLayout. Но поля FrameLayout отбрасываются, и он всегда устанавливает Image в верхний левый угол. Если я перейду с FrameLayout на LinearLayout, поля будут работать правильно. Как с этим справиться?

<?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:id="@+id/inner1"
    >
        <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
           android:layout_width="wrap_content"
           android:layout_height="wrap_content"
        >

            <ImageView
             android:layout_width="24px" 
             android:layout_height="24px" 
             android:id="@+id/favicon"
             android:layout_marginLeft="50px"
             android:layout_marginTop="50px"
             android:layout_marginBottom="40px"
             android:layout_marginRight="70px"      

            />      
            <ImageView
             android:layout_width="52px" 
             android:layout_height="52px" 
             android:id="@+id/applefavicon" 
             android:layout_marginLeft="100px"
             android:layout_marginTop="100px"
             android:layout_marginBottom="100px"
             android:layout_marginRight="100px"              
            />

        </FrameLayout>  
            <TextView
            android:layout_width="wrap_content" 
            android:layout_height="wrap_content" 
            android:id="@+id/title"                 
            android:layout_marginLeft="10px"        
            android:layout_marginTop="20px"
            android:textColor="#FFFFFF"  
            android:textSize = "15px"
            android:singleLine = "true"
            />

    </LinearLayout>
Винот
источник

Ответы:

221

Я была такая же проблема сам и заметил , что определение layout_поля не работает , пока вы не установите расположение гравитационный то есть ваша ImageView в android:layout_gravity="top"в файле ресурсов XML, или из кода: FrameLayout.LayoutParams.gravity = Gravity.TOP;.

Андрей
источник
21
Это работает, но я чувствую себя грязным. Я думал, что избежал времен CSS-хаков ...
Эрландо
1
FrameLayout.LayoutParams.gravity не имеет опции гравитации в 2.3
JPM
2
Вроде исправлено на 4.1 (наверное, раньше). Однако полезно знать
паблиско
исправлена ​​проблема, которая возникала у меня на старом разжигании огня. Благодаря!
DallinDyer
12
Чтобы было понятнее, почему. Вызов FrameLayout.onLayout () содержит следующее (по крайней мере, в api v2.3.4): // for each child: final LayoutParams lp = (LayoutParams) child.getLayoutParams(); final int gravity = lp.gravity; if (gravity != -1) { // handle all margin related stuff Итак, если сила тяжести равна -1, расчет маржи производиться не будет. Гравитация в FrameLayout.LayoutParams определяется следующим образом: gravity = a.getInt(com.android.internal.R.styleable.FrameLayout_Layout_layout_gravity, -1); Итак, если гравитация не задана, расчет маржи производиться не будет.
Miklos Jakab
8

Чтобы было понятнее, почему. Вызов FrameLayout.onLayout () содержит это (по крайней мере, в api v2.3.4):

    // for each child
    final LayoutParams lp = (LayoutParams) child.getLayoutParams();
    final int gravity = lp.gravity;
    if (gravity != -1) {
        // handle all margin related stuff

Таким образом, если гравитация равна -1, расчет маржи производиться не будет. Дело в том, что гравитация в FrameLayout.LayoutParams определяется следующим образом:

    gravity = a.getInt(com.android.internal.R.styleable.FrameLayout_Layout_layout_gravity, -1);

Таким образом, если гравитация не установлена, расчет маржи производиться не будет.

Миклош Якаб
источник
7

добавьте свой xml this атрибут и запустите повторно

android: layout_gravity = "вверху"

все отлично!

и вы не устанавливаете такие новые параметры макета;

FrameLayout.LayoutParams llp = new FrameLayout.LayoutParams(WallpapersActivity.ScreenWidth/2, layH);

использовать так:

FrameLayout.LayoutParams llp = (LayoutParams) myFrameLay.getLayoutParams();
llp.height = 100;
llp.width = 100;
myFrameLay.setLayoutParams(llp);
Савас Адар
источник
1
Поэтому, если у вас нет LayoutParams, при втором методе произойдет сбой.
Леон Пеллетье
вы можете проверить это с помощью if == null control.
Савас Адар
Это решит мою проблему с margin_top на Android 10.
Педро Пауло Аморим
1

Взято из документации FrameLayout ( ссылка )

Размер макета фрейма - это размер его самого большого дочернего элемента (плюс отступ), видимого или невидимого (если родительский элемент FrameLayout разрешает).

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

Вы из любопытства упомянули, что он отлично работает при использовании LinearLayoutконтейнера, почему выбор FrameLayout?

Джоуи
источник
0

Вы пробовали android: layout_gravity? Попробуйте использовать android: padding в ImageViews вместо android: layout_margin. Поля AFAIK не работают должным образом в макете кадра. Однажды мне даже пришлось написать собственный макет для этой цели. Кстати, как вы хотите, чтобы ваши ImageViews были связаны?

Дмитрий Рядненко
источник
нет веса в раскладке фрейма
njzk2
0

попробуйте setCropToPadding (true) в ImageView, это должно помочь!

дети
источник
0

вам необходимо установить верхнюю границу гравитации макета ImageView, то есть android: layout_gravity = "top" в файле ресурсов XML или из кода: FrameLayout.LayoutParams.gravity = Gravity.TOP

Комал Нихаре
источник