Najeebullah Shah
Najeebullah Shah

Reputation: 3709

Android: get width of Layout programatically having fill_parent in its xml

I have the a LinearLayout with width set in xml as fill_parent , now i need its width at runtime programatically. So i did this:

    LinearLayout layoutGet=(LinearLayout) findViewById(R.id.GameField1);
    LayoutParams layParamsGet= layoutGet.getLayoutParams();
    int width=layParamsGet.width;

But width value on debugging was found to be -1, anybody with idea why can't i get the exact width at runtime for LinearLayout with fill_parent set in layout xml.

Upvotes: 11

Views: 32795

Answers (5)

Tony
Tony

Reputation: 2451

I got a simple approach working.

myLayout = (RelativeLayout) findViewById(R.id.my_layout);
myLayout.post(new Runnable() 
    {

        @Override
        public void run()
        {
            Log.i("TEST", "Layout width : "+ myLayout.getWidth());

        }
    });

Jens Vossnack's approach mentioned below works fine. However, I found that the onGlobalLayout() method of GlobalLayoutListener is called repeatedly, which may not be appropriate in certain cases.

Upvotes: 41

Jens Vossnack
Jens Vossnack

Reputation: 247

You can try to listen to the globalLayout event, and get the width in there. You probably get the -1 because you are trying to get the width before the views are layed-out.

vto.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
    @Override
    public void onGlobalLayout() {
       //Do it here
       LinearLayout layoutGet=(LinearLayout) findViewById(R.id.GameField1);
       LayoutParams layParamsGet= layoutGet.getLayoutParams();
       int width=layParamsGet.width;
       removeOnGlobalLayoutListener(layoutGet, this); // Assuming layoutGet is the View which you got the ViewTreeObserver from
    }
});

@SuppressLint("NewApi")
public static void removeOnGlobalLayoutListener(View v, ViewTreeObserver.OnGlobalLayoutListener listener){
    if (Build.VERSION.SDK_INT < 16) v.getViewTreeObserver().removeGlobalOnLayoutListener(listener); 
    else v.getViewTreeObserver().removeOnGlobalLayoutListener(listener);
}

(vto is the view you want to get the width of)

Upvotes: 5

Sergio Carvalho
Sergio Carvalho

Reputation: 251

First of all, you should use match_parent instead of fill_parent (deprecated).

When you do int width=layParamsGet.width;, you take the right result which is -1 corresponding at fill_parent. If you wan't to get the real width, you need to wait onMesure() call and use

LinearLayout layoutGet=(LinearLayout) findViewById(R.id.GameField1);
int width = layoutGet. getMeasuredHeight();

Upvotes: 0

dymmeh
dymmeh

Reputation: 22306

If you look at the value for FILL_PARENT (you should be using MATCH_PARENT since FILL_PARENT is now deprecated) you will notice the value for it is -1. LayoutParams are simply attributes for how your view should look. Once the view is inflated and looks the way the params specify, the view does not go back and change those Params to reflect the actual values of the view (width/height/etc).

If you wanted to get the actual width of your view you would have to call getWidth() on your view once the layout has been inflated and displayed. Calling getWidth() before your layout has been displayed will result in 0.

LinearLayout layoutGet=(LinearLayout) findViewById(R.id.GameField1);
int width = layoutGet.getWidth();

Upvotes: 2

Onur A.
Onur A.

Reputation: 3017

layoutGet.getWidth() should work out

Upvotes: -1

Related Questions