How to retrieve the dimensions of a view?

前端 未结 16 1667
小蘑菇
小蘑菇 2020-11-22 01:09

I have a view made up of TableLayout, TableRow and TextView. I want it to look like a grid. I need to get the height and width of this grid. The methods

相关标签:
16条回答
  • 2020-11-22 01:30

    ViewTreeObserver and onWindowFocusChanged() are not so necessary at all.

    If you inflate the TextView as layout and/or put some content in it and set LayoutParams then you can use getMeasuredHeight() and getMeasuredWidth().

    BUT you have to be careful with LinearLayouts (maybe also other ViewGroups). The issue there is, that you can get the width and height after onWindowFocusChanged() but if you try to add some views in it, then you can't get that information until everything have been drawn. I was trying to add multiple TextViews to LinearLayouts to mimic a FlowLayout (wrapping style) and so couldn't use Listeners. Once the process is started, it should continue synchronously. So in such case, you might want to keep the width in a variable to use it later, as during adding views to layout, you might need it.

    0 讨论(0)
  • 2020-11-22 01:37

    You are trying to get width and height of an elements, that weren't drawn yet.

    If you use debug and stop at some point, you'll see, that your device screen is still empty, that's because your elements weren't drawn yet, so you can't get width and height of something, that doesn't yet exist.

    And, I might be wrong, but setWidth() is not always respected, Layout lays out it's children and decides how to measure them (calling child.measure()), so If you set setWidth(), you are not guaranteed to get this width after element will be drawn.

    What you need, is to use getMeasuredWidth() (the most recent measure of your View) somewhere after the view was actually drawn.

    Look into Activity lifecycle for finding the best moment.

    http://developer.android.com/reference/android/app/Activity.html#ActivityLifecycle

    I believe a good practice is to use OnGlobalLayoutListener like this:

    yourView.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                if (!mMeasured) {
                    // Here your view is already layed out and measured for the first time
                    mMeasured = true; // Some optional flag to mark, that we already got the sizes
                }
            }
        });
    

    You can place this code directly in onCreate(), and it will be invoked when views will be laid out.

    0 讨论(0)
  • 2020-11-22 01:39

    You can use a broadcast that is called in OnResume ()

    For example:

    int vh = 0;   
    int vw = 0;
    
    public void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
          setContentView(R.layout.maindemo);  //<- includes the grid called "board"
    
          registerReceiver(new BroadcastReceiver() {
                @Override
                public void onReceive(Context context, Intent intent) {
                    TableLayout tl = (TableLayout) findViewById(R.id.board);  
                    tl = (TableLayout) findViewById(R.id.board);
                    vh = tl.getHeight();       
                    vw = tl.getWidth();               
                }
          }, new IntentFilter("Test"));
    }
    
    protected void onResume() {
            super.onResume();
    
            Intent it = new Intent("Test");
            sendBroadcast(it);
    
    }
    

    You can not get the height of a view in OnCreate (), onStart (), or even in onResume () for the reason that kcoppock responded

    0 讨论(0)
  • 2020-11-22 01:39

    CORRECTION: I found out that the above solution is terrible. Especially when your phone is slow. And here, I found another solution: calculate out the px value of the element, including the margins and paddings: dp to px: https://stackoverflow.com/a/6327095/1982712

    or dimens.xml to px: https://stackoverflow.com/a/16276351/1982712

    sp to px: https://stackoverflow.com/a/9219417/1982712 (reverse the solution)

    or dimens to px: https://stackoverflow.com/a/16276351/1982712

    and that's it.

    0 讨论(0)
提交回复
热议问题