В этой , этой и этой ветке я попытался найти ответ о том, как установить поля для одного представления. Однако мне было интересно, если нет более легкого пути. Я объясню, почему я не хотел бы использовать этот подход:
У меня есть пользовательская кнопка, которая расширяет кнопку. Если задан фон, отличный от фона по умолчанию (вызывая либо setBackgroundResource(int id)
или setBackgroundDrawable(Drawable d)
), я хочу, чтобы поля были равны 0. Если я вызываю это:
public void setBackgroundToDefault() {
backgroundIsDefault = true;
super.setBackgroundResource(android.R.drawable.btn_default);
// Set margins somehow
}
Я хочу, чтобы поля были сброшены в -3dp (я уже читал здесь, как конвертировать из пикселей в dp, поэтому, когда я знаю, как установить поля в px, я могу сам управлять конвертацией). Но так как это вызывается в CustomButton
классе, родитель может варьироваться от LinearLayout до TableLayout, и я бы предпочел, чтобы он не брал своего родителя и не проверял экземпляр этого родителя. Я полагаю, это также будет совершенно неэффективно.
Кроме того, при вызове (используя LayoutParams) parentLayout.addView(myCustomButton, newParams)
я не знаю, добавляет ли это его в правильную позицию (однако не пробовал), скажем, среднюю кнопку ряда из пяти.
Вопрос: Есть ли более простой способ установить поле для одной кнопки программно, кроме использования LayoutParams?
РЕДАКТИРОВАТЬ: я знаю способ LayoutParams, но я хотел бы решение, которое избегает обработки каждого типа контейнера:
ViewGroup.LayoutParams p = this.getLayoutParams();
if (p instanceof LinearLayout.LayoutParams) {
LinearLayout.LayoutParams lp = (LinearLayout.LayoutParams)p;
if (_default) lp.setMargins(mc.oml, mc.omt, mc.omr, mc.omb);
else lp.setMargins(mc.ml, mc.mt, mc.mr, mc.mb);
this.setLayoutParams(lp);
}
else if (p instanceof RelativeLayout.LayoutParams) {
RelativeLayout.LayoutParams lp = (RelativeLayout.LayoutParams)p;
if (_default) lp.setMargins(mc.oml, mc.omt, mc.omr, mc.omb);
else lp.setMargins(mc.ml, mc.mt, mc.mr, mc.mb);
this.setLayoutParams(lp);
}
else if (p instanceof TableRow.LayoutParams) {
TableRow.LayoutParams lp = (TableRow.LayoutParams)p;
if (_default) lp.setMargins(mc.oml, mc.omt, mc.omr, mc.omb);
else lp.setMargins(mc.ml, mc.mt, mc.mr, mc.mb);
this.setLayoutParams(lp);
}
}
Потому что this.getLayoutParams();
возвращает ViewGroup.LayoutParams
, которые не имеют атрибуты topMargin
, bottomMargin
, leftMargin
, rightMargin
. Экземпляр mc, который вы видите - это просто MarginContainer
поле со смещением (-3dp) и (oml, omr, omt, omb) и исходные поля (ml, mr, mt, mb).
LayoutParams - НЕ РАБОТАЕТ! ! !
Нужно использовать тип: MarginLayoutParams
Пример кода для MarginLayoutParams:
http://www.codota.com/android/classes/android.view.ViewGroup.MarginLayoutParams
источник
Button
просмотра:ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) button.getLayoutParams()
возвращаетсяnull
Лучший способ когда-либо:
Как вызвать метод:
Надеюсь, что это поможет вам.
источник
затем
Или
источник
Вот ответ «все в одном» с последними обновлениями:
Шаг 1, чтобы обновить поля
Основная идея состоит в том, чтобы вывести маржу и затем обновить ее. Обновление будет применено автоматически, и вам не нужно устанавливать его обратно. Чтобы получить параметры макета, просто вызовите этот метод:
LayoutParams
Происходит от расположения вашего зрения. Если вид из линейного макета, вам нужно импортироватьLinearLayout.LayoutParams
. Если вы используете относительное расположение, импортLinearLayout.LayoutParams
и т. Д.Теперь, если вы устанавливаете маржу, используя
Layout_marginLeft
,Right
и т.д., вам нужно обновить маржу таким образомЕсли вы устанавливаете маржу, используя новую
layout_marginStart
, вам необходимо обновить маржу таким образомШаг 2, чтобы обновить поля в дп
Все два способа обновления полей выше обновляются в пикселях. Вам нужно сделать перевод dp в пиксели.
Теперь поместите вычисленное значение в вышеприведенные функции обновления полей, и вы должны быть полностью настроены.
источник
layout_margin - это ограничение, которое дочерний элемент представления сообщает своему родителю. Однако родительская роль состоит в том, чтобы выбрать, разрешить ли маржу или нет. В основном, установив android: layout_margin = "10dp", дочерний элемент умоляет родительскую группу представления выделить пространство, которое на 10dp больше, чем его фактический размер. (padding = "10dp", с другой стороны, означает, что дочернее представление уменьшит собственный контент на 10dp .)
Следовательно, не все ViewGroups уважают маржу . Самый печально известный пример - просмотр списка, где поля элементов игнорируются. Прежде чем вызывать
setMargin()
LayoutParam, вы всегда должны убедиться, что текущее представление находится в ViewGroup, которая поддерживает маржу (например, LinearLayouot или RelativeLayout), и привести результатgetLayoutParams()
к конкретным желаемым LayoutParams. (ViewGroup.LayoutParams
даже не имеетsetMargins()
метода!)Функция ниже должна сделать свое дело. Однако убедитесь, что вы заменили RelativeLayout на тип родительского представления.
источник
Этот метод позволит вам установить маржу в DP
ОБНОВИТЬ
Вы можете изменить параметр, который соответствует вашим потребностям.
источник
В Котлине это будет выглядеть так:
источник
Когда вы находитесь в пользовательском представлении, вы можете использовать
getDimensionPixelSize(R.dimen.dimen_value)
, в моем случае, я добавил поле в LayoutParams, созданный наinit
метода.В котлине
в Java:
источник
Вы можете использовать этот метод и поставить статический размер как 20, он преобразует в соответствии с вашим устройством
источник
Используйте этот метод, чтобы установить маржу в дп
вызвать метод:
источник
Для быстрой настройки в одну строку используйте
но будьте осторожны за любое неправильное использование LayoutParams, так как это не будет иметь
if
чека экземпляра statmentисточник
Создана функция расширения Kotlin для тех из вас, кому это может пригодиться.
Убедитесь, что в пикселях указано не dp. Удачного кодирования :)
источник
В моем примере я добавляю ImageView к LinearLayout программно. Я установил верхнее и нижнее поля для ImagerView. Затем добавьте ImageView к LinearLayout.
источник
Как сегодня, вероятно, лучше всего использовать Париж , библиотеку, предоставленную AirBnB.
Стили могут быть применены следующим образом:
он также поддерживает пользовательское представление (если вы расширяете представление), используя аннотации:
источник
Вы должны позвонить
вот так:
your_view.setPadding(0,16,0,0)
То, что вы пытаетесь использовать, это только получатель.
Студия Android показывает, что на
padding...()
самом деле означает в Java:пример заполнения На рисунке показаны только вызовы
getPadding...()
Если вы хотите добавить поле для вашего TextView, вам нужно использовать LayoutParams:
источник
Мне пришлось использовать
FrameLayout
свой метод для linearLayout, поскольку он наследуется от него, и установить поля там, чтобы действие отображалось только на части экрана вместе с другим фоном, чем исходные параметры макета вsetContentView
.Никто из остальных не работал на то же действие и не изменял поля, основываясь на открытии упражнения из другого меню! setLayoutParams никогда не работал для меня - устройство зависало каждый раз. Даже если это жестко закодированные числа - это только пример кода только для демонстрации.
источник
Вы можете использовать,
ViewGroup.MarginLayoutParams
чтобы установить ширину, высоту и поляГде метод
setMargins();
принимает значения для left, top, right, bottom соответственно. По часовой стрелке!, Начиная слева.источник