2011-09-22 10 views
5

ViewGroupを拡張するカスタムレイアウトを作成しました。すべて正常に動作しており、私は期待どおりにレイアウトを取得しています。ViewGroup finish inflateイベント

レイアウト内の要素を動的に変更したいと考えています。しかし、これは私がonCreateで呼び出すときには機能しません。その時間まで、レイアウト全体が実際に(描画され)画面上に展開されず、実際のサイズにはなりません。

レイアウトの膨張がいつ行われたかを知るために使用できるイベントはありますか?私はonFinishInflateを試しましたが、Viewgroupは複数のビューを持ち、これは複数回呼び出されるため動作しません。

私はカスタムレイアウトクラスでインターフェイスを作成しようと考えていますが、いつ発射するのかはわかりません。

答えて

20

を必要。

View myView=findViewById(R.id.myView); 
    myView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() { 
      @Override 
      public void onGlobalLayout() { 
       //At this point the layout is complete and the 
       //dimensions of myView and any child views are known. 
      } 
     }); 
+0

私はこれをtextviewizeで調整するためにこれを使用してきましたが、ViewGroupでもこれを使うことはできませんでした。助けてくれてありがとう! – PravinCG

2

通常、ViewまたはViewGroupに拡張されたカスタムレイアウトを作成するときは、protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)protected void onLayout(boolean changed, int left, int top, int right, int bottom)を上書きする必要があります。これらは、ビューに関連するサイズと位置情報を取得するために、インフレーションの処理中に呼び出されます。また、その後、ViewGroupを延長する場合は、内に含まれるすべての子ビューでmeasure(int widthMeasureSpec, int heightMeasureSpec)layout(int l, int t, int r, int b)を呼び出す必要があります。 (measure()はonMeasure()で呼び出され、layout()はonLayout()で呼び出されます)。

とにかく、onMeasure()には、このようなことが一般的です。 onLayout()

@Override 
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) 
{ 
    // Gather this view's specs that were passed to it 
    int widthMode = MeasureSpec.getMode(widthMeasureSpec); 
    int widthSize = MeasureSpec.getSize(widthMeasureSpec); 
    int heightMode = MeasureSpec.getMode(heightMeasureSpec); 
    int heightSize = MeasureSpec.getSize(heightMeasureSpec); 

    int chosenWidth = DEFAULT_WIDTH; 
    int chosenHeight = DEFAULT_HEIGHT; 
    if(widthMode == MeasureSpec.AT_MOST || widthMode == MeasureSpec.EXACTLY) 
     chosenWidth = widthSize; 
    if(heightMode == MeasureSpec.AT_MOST || heightMode == MeasureSpec.EXACTLY) 
     chosenHeight = heightSize; 

    setMeasuredDimension(chosenWidth, chosenHeight); 

    *** NOW YOU KNOW THE DIMENSIONS OF THE LAYOUT *** 
} 

あなたがそうのような物理的なサイズ得ることができるので、あなたは、ビューの実際のピクセル座標を取得する:私が正しくあなたの要件を理解していれば、OnGlobalLayoutListenerはあなたに何を与える可能性があり

@Override 
protected void onLayout(boolean changed, int left, int top, int right, int bottom) 
{ 
    // Android coordinate system starts from the top-left 
    int width = right - left; 
    int height = bottom - top; 
} 
+0

お返事ありがとうございます。値が動的になるので、私はあなたのクエリを指定したものをすべて実行しました。アクティビティからそのデータを渡すにはどうしたらいいのですか? – PravinCG

+1

ビュー内でビューを動的に変更していると思いました。そのような場合は、これらの2つの方法を使用して座標を(表示する前から)見つけることができます。別のオプションは、 'Activity'の一部である' onWindowFocusChanged() 'を使用しているかもしれません。 '活動の現在のウィンドウがフォーカスを得るか失ったときに呼び出されるドキュメントによると。これは、このアクティビティがユーザーに表示されるかどうかを示す最も優れた指標です。デフォルトの実装では、キーのトラッキング状態がクリアされるため、常に呼び出す必要があります。 '私はそれを使って、ウィンドウがいつ見えているのかを判断しました。 – DeeV

+0

+1、ありがとうございます。上記の方法は信頼できる方法ではありませんが、場合によっては動作する可能性があります。 – PravinCG

関連する問題