私もこの問題に遭遇しましたが、私の場合、ページFragmentPagerAdapterをに提供するViewPagerがありました。私が抱えていた問題onMeasure()は、ViewPagerがFragments作成される前にが呼び出されたことでした(そのため、サイズを正しく設定できませんでした)。
試行錯誤のビットの後、私はことを発見しfinishUpdate()た後FragmentPagerAdapterのメソッドが呼び出されるFragments(から初期化されているinstantiateItem()中でFragmentPagerAdapter)、また、後/ページスクロール中。私は小さなインターフェースを作りました:
public interface AdapterFinishUpdateCallbacks
{
void onFinishUpdate();
}
これを自分に渡してFragmentPagerAdapter呼び出す:
@Override
public void finishUpdate(ViewGroup container)
{
super.finishUpdate(container);
if (this.listener != null)
{
this.listener.onFinishUpdate();
}
}
これによりsetVariableHeight()、CustomViewPager実装を呼び出すことができます。
public void setVariableHeight()
{
// super.measure() calls finishUpdate() in adapter, so need this to stop infinite loop
if (!this.isSettingHeight)
{
this.isSettingHeight = true;
int maxChildHeight = 0;
int widthMeasureSpec = MeasureSpec.makeMeasureSpec(getMeasuredWidth(), MeasureSpec.EXACTLY);
for (int i = 0; i < getChildCount(); i++)
{
View child = getChildAt(i);
child.measure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(ViewGroup.LayoutParams.WRAP_CONTENT, MeasureSpec.UNSPECIFIED));
maxChildHeight = child.getMeasuredHeight() > maxChildHeight ? child.getMeasuredHeight() : maxChildHeight;
}
int height = maxChildHeight + getPaddingTop() + getPaddingBottom();
int heightMeasureSpec = MeasureSpec.makeMeasureSpec(height, MeasureSpec.EXACTLY);
super.measure(widthMeasureSpec, heightMeasureSpec);
requestLayout();
this.isSettingHeight = false;
}
}
私はそれが最良のアプローチであるかどうかはわかりませんが、それが良い/悪い/悪いと思うならコメントが大好きですが、私の実装ではかなりうまく機能しているようです:)
これが誰かに役立つことを願っています!
編集:私はrequestLayout()呼び出し後にアフターを追加するのを忘れましたsuper.measure()(そうでなければ、それはビューを再描画しません)。
また、親のパディングを最終的な高さに追加するのを忘れていました。
また、必要に応じて新しいものを作成するために、元の幅/高さのMeasureSpecsを維持することもやめました。それに応じてコードを更新しました。
私が持っていた別の問題は、それ自体がa ScrollViewで正しくサイズ調整されないことであり、犯人がのMeasureSpec.EXACTLY代わりにで子供を測定していることがわかりましたMeasureSpec.UNSPECIFIED。これを反映するように更新されました。
これらの変更はすべてコードに追加されています。必要に応じて、履歴を確認して古い(正しくない)バージョンを確認できます。