So legen Sie den Rand von ImageView mithilfe von Code fest, nicht mithilfe von XML

177

Ich möchte ImageViewmeinem Layout eine unbekannte Anzahl von Ansichten mit Rand hinzufügen . In XML kann ich Folgendes verwenden layout_margin:

<ImageView android:layout_margin="5dip" android:src="@drawable/image" />

Es gibt ImageView.setPadding(), aber nein ImageView.setMargin(). Ich denke, es ist in etwa so ImageView.setLayoutParams(LayoutParams), aber ich bin mir nicht sicher, was ich dazu beitragen soll .

Weiß jemand?

Bruce Lee
quelle

Antworten:

381

android.view.ViewGroup.MarginLayoutParamshat eine Methode setMargins(left, top, right, bottom). Direkte Unterklassen sind: FrameLayout.LayoutParams, LinearLayout.LayoutParamsund RelativeLayout.LayoutParams.

Verwenden Sie zB LinearLayout:

LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.WRAP_CONTENT);
lp.setMargins(left, top, right, bottom);
imageView.setLayoutParams(lp);

MarginLayoutParams

Dadurch werden die Ränder in Pixel festgelegt. Um es zu skalieren, verwenden Sie

context.getResources().getDisplayMetrics().density

DisplayMetrics

Schlüssel
quelle
18
Beachten Sie, dass dies die Randgröße in PIXELS festlegt und nicht mit der dpi-Einheit in der XML-Datei dieser Frage übereinstimmt.
Aromero
Wie können wir einen dpi-Wert anstelle eines Pixels verwenden?
Pascal Piché
10
Sie können die Pixel - Wert mit context.getResources skalieren () getDisplayMetrics () Dichte.. Developer.android.com/reference/android/util/...
Key
1
Beachten Sie, dass es Probleme mit FrameLayout.LayoutParamsund möglicherweise mit anderen geben kann: stackoverflow.com/questions/5401952/…
Dmitry Zaytsev
für den Fall, dass wir nur den unteren Rand der Bildansicht festlegen wollten, was ist android:layout_centerHorizontal = "true"und android:layout_alignParentBottom = "true"auf welche Weise könnte ich dies erreichen?
SSRP
51
    image = (ImageView) findViewById(R.id.imageID);
    MarginLayoutParams marginParams = new MarginLayoutParams(image.getLayoutParams());
    marginParams.setMargins(left_margin, top_margin, right_margin, bottom_margin);
    RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(marginParams);
    image.setLayoutParams(layoutParams);
Kevin Wadera
quelle
5
Was ist der Deal mit den letzten 2 Zeilen? Klonen Sie die Randparameter in eine andere Parametervariable? Ich kann bestätigen, dass es erforderlich ist :)
Adam Rabung
1
für den Fall, dass wir nur den unteren Rand der Bildansicht festlegen wollten, was ist android:layout_centerHorizontal = "true"und android:layout_alignParentBottom = "true"auf welche Weise könnte ich dies erreichen?
SSRP
layoutparams.addRule (RelativeLayout.CENTER_HORIZONTAL);
cwhsu
Das Erstellen weiterer Layoutparameter ist erforderlich. Danke :)
Muzaffer
42

Alle obigen Beispiele ersetzen tatsächlich alle Parameter, die bereits für die Ansicht vorhanden sind, was möglicherweise nicht erwünscht ist. Der folgende Code erweitert lediglich die vorhandenen Parameter, ohne sie zu ersetzen:

ImageView myImage = (ImageView) findViewById(R.id.image_view);
MarginLayoutParams marginParams = (MarginLayoutParams) image.getLayoutParams();
marginParams.setMargins(left, top, right, bottom);
Kelevandos
quelle
1
Dies ist die erste Lösung in dieser Liste, die für mich funktioniert hat. Die anderen haben die anderen Parameter, die ich im XML festgelegt hatte, vermasselt, einschließlich der RelativeLayout-Parameter für die Positionierung.
Chris Dutrow
22

Kevins Code erstellt ein redundantes MarginLayoutParamsObjekt. Einfachere Version:

ImageView image = (ImageView) findViewById(R.id.main_image);
RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(image.getLayoutParams());
lp.setMargins(50, 100, 0, 0);
image.setLayoutParams(lp);
Adam Stelmaszczyk
quelle
1
Seltsamerweise erhalte ich dann "Methode setmargins () kann nicht aufgelöst werden", weshalb ich nach dieser Frage gegoogelt habe und hier gelandet bin.
user2875404
11

Wenn Sie den Bildansichtsrand ändern möchten, aber alle anderen Ränder intakt lassen möchten.

  1. Holen Sie sich in diesem Fall MarginLayoutParameters Ihrer Bildansicht: myImageView

     MarginLayoutParams marginParams = (MarginLayoutParams) myImageView.getLayoutParams();
  2. Ändern Sie nun einfach den Rand, den Sie ändern möchten, und lassen Sie die anderen unverändert:

     marginParams.setMargins(marginParams.leftMargin, 
                             marginParams.topMargin, 
                             150, //notice only changing right margin
                             marginParams.bottomMargin); 
CommonSenseCode
quelle
8

Sie können diese Methode verwenden, wenn Sie Ränder in dp angeben möchten:

private void addMarginsInDp(View view, int leftInDp, int topInDp, int rightInDp, int bottomInDp) {
    DisplayMetrics dm = view.getResources().getDisplayMetrics();
    LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
    lp.setMargins(convertDpToPx(leftInDp, dm), convertDpToPx(topInDp, dm), convertDpToPx(rightInDp, dm), convertDpToPx(bottomInDp, dm));
    view.setLayoutParams(lp);
}

private int convertDpToPx(int dp, DisplayMetrics displayMetrics) {
    float pixels = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp, displayMetrics);
    return Math.round(pixels);
}
Divonas
quelle
8

Ich benutze einfach das und funktioniert super:

ImageView imageView = (ImageView) findViewById(R.id.image_id);
RelativeLayout.LayoutParams layoutParams = (RelativeLayout.LayoutParams) imageView.getLayoutParams();
layoutParams.setMargins(left, top, right, bottom);
imageView.setLayoutParams(layoutParams);

Die Einheit von setMargins () ist Pixel, nicht dp. Wenn Sie den Rand in dp festlegen möchten , erstellen Sie Ihre Dimensionen direkt in Ihrer Datei values ​​/ dimension.xml wie folgt :

<resources>
    <dimen name="right">16dp</dimen>
    <dimen name="left">16dp</dimen>    
</resources>

und Zugriff wie:

getResources().getDimension(R.dimen.right);
Elnoor
quelle
5

Wenn Sie Kotlin verwenden, kann dies durch Erstellen einer Erweiterungsfunktion vereinfacht werden

fun View.setMarginExtensionFunction(left: Int, top: Int, right: Int, bottom: Int) {
  val params = layoutParams as ViewGroup.MarginLayoutParams
  params.setMargins(left, top, right, bottom)
  layoutParams = params
}

Jetzt brauchen Sie nur noch eine Ansicht, und diese Erweiterungsfunktion kann überall verwendet werden.

val imageView = findViewById(R.id.imageView)
imageView.setMarginExtensionFunction(0, 0, 0, 0)
Enyciaa
quelle
1
Dies funktioniert für leftund rightRänder, aber wenn Sie relative Ränder ( startund end) haben, funktioniert es nicht. Ich habe eine Liste mit einer 'verbesserten' Version Ihres Codes geschrieben: gist.github.com/Grohden/f40c53bf86c5395638f7a44bf90e732d (die setMarginsRelativeFunktion) - könnten Sie das in Ihre Antwort aufnehmen?
Gabriel De Oliveira Rohden
4

Erstellen Sie ein Layout dynamisch und legen Sie den Parameter so fest, dass setmargin () in einer imageView nicht direkt funktioniert

ImageView im;
im = (ImageView) findViewById(R.id.your_image_in_XML_by_id);
 RelativeLayout.LayoutParams layout = new RelativeLayout.LayoutParams(im.getLayoutParams());
                        layout.setMargins(counter*27, 0, 0, 0);//left,right,top,bottom
                        im.setLayoutParams(layout);
                        im.setImageResource(R.drawable.yourimage)
Muhammad Adil
quelle
4

Bei mir hat das geklappt:

int imgCarMarginRightPx = (int)TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, definedValueInDp, res.getDisplayMetrics());

MarginLayoutParams lp = (MarginLayoutParams) imgCar.getLayoutParams();
lp.setMargins(0,0,imgCarMarginRightPx,0);
imgCar.setLayoutParams(lp);
Wahib Ul Haq
quelle
2

Beispielcode ist hier, es ist sehr einfach

LayoutParams params1 = (LayoutParams)twoLetter.getLayoutParams();//twoletter-imageview
                params1.height = 70;
                params1.setMargins(0, 210, 0, 0);//top margin -210 here
                twoLetter.setLayoutParams(params1);//setting layout params
                twoLetter.setImageResource(R.drawable.oo);
Sydroid
quelle
0

Die Verwendung einer ähnlichen Methode kann Ihnen in bestimmten Situationen Kopfschmerzen ersparen. Wenn Sie zwei Durchgänge programmatisches Basteln mit Rändern haben, ist es sicherer zu überprüfen, ob bereits einige layoutParams festgelegt sind. Wenn es bereits einige Ränder gibt, sollte man diese erhöhen und nicht ersetzen:

public void addMargins(View v, int left, int top, int right, int bottom) {
    LinearLayout.LayoutParams params = (LinearLayout.LayoutParams) v.getLayoutParams();
    if (params == null)
        params = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
                                               ViewGroup.LayoutParams.WRAP_CONTENT);
    int oldLeft = params.leftMargin;
    int oldTop = params.topMargin;
    int oldRight = params.rightMargin;
    int oldBottom = params.bottomMargin;
    params.setMargins(oldLeft + left, oldTop + top, oldRight + right, oldBottom + bottom);
    v.setLayoutParams(params);
}
GA1
quelle
0

Hier ist ein Beispiel zum Hinzufügen eines 8px-Randes links, oben, rechts, unten.


ImageView imageView = new ImageView(getApplicationContext());

ViewGroup.MarginLayoutParams marginLayoutParams = new ViewGroup.MarginLayoutParams(
    ViewGroup.MarginLayoutParams.MATCH_PARENT,
    ViewGroup.MarginLayoutParams.WRAP_CONTENT
);

marginLayoutParams.setMargins(8, 8, 8, 8);

imageView.setLayoutParams(marginLayoutParams);
Md. Zubaer Ahammed
quelle
0

Antwort aus dem Jahr 2020:

dependencies {
    implementation "androidx.core:core-ktx:1.2.0"
}

und kalibrieren Sie es einfach in Ihrem Code

view.updateLayoutParams<ViewGroup.MarginLayoutParams> {
   setMargins(5)
}
i30mb1
quelle