ビューにはminHeight
があります ですが、何らかの理由でmaxHeight
がありません:
私が達成しようとしているのは、いくつかのアイテム(ビュー)がScrollView
を満たすことです。 1..3アイテムがある場合、それらを直接表示したい。 ScrollView
の意味は、1、2、または3アイテムの高さです。
4つ以上のアイテムがある場合、ScrollView
の展開を停止し(したがってmaxHeight
)、スクロールの提供を開始します。
ただし、残念ながらmaxHeight
を設定する方法はありません。したがって、1..3アイテムがある場合はScrollView
の高さをプログラムでWRAP_CONTENT
に設定し、4つ以上のアイテムがある場合は高さを3*sizeOf(View)
に設定する必要があります。
すでにmaxHeight
が存在する場合、minHeight
が提供されない理由を誰でも説明できますか?
(ところで:ImageView
などの一部のビューにはmaxHeight
が実装されています。)
これらのソリューションはどれも、wrap_contentに設定されたScrollViewであるが、特定のポイントの後に拡張を停止してスクロールを開始するmaxHeightを持っている必要なものには機能しませんでした。 ScrollViewのonMeasureメソッドを単にオーバーライドしました。
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
heightMeasureSpec = MeasureSpec.makeMeasureSpec(300, MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
これはすべての状況で機能するとは限りませんが、レイアウトに必要な結果が得られることは確かです。また、madhuによるコメントにも対応しています。
スクロールビューの下にレイアウトが存在する場合、このトリックは機能しません– madhu Mar 5 at 4:36
MaxHeightでScrollView
またはListView
を作成するには、maxHeightの高さを指定して、その周りにTransparent LinearLayoutを作成するだけです。次に、ScrollViewのHeightをwrap_content
に設定します。これにより、親のLinearLayoutと同じ高さになるまで拡大するように見えるScrollViewが作成されます。
これは私にそれをxmlでカスタマイズ可能にするのに役立ちました:
MaxHeightScrollView.Java:
public class MaxHeightScrollView extends ScrollView {
private int maxHeight;
private final int defaultHeight = 200;
public MaxHeightScrollView(Context context) {
super(context);
}
public MaxHeightScrollView(Context context, AttributeSet attrs) {
super(context, attrs);
if (!isInEditMode()) {
init(context, attrs);
}
}
public MaxHeightScrollView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
if (!isInEditMode()) {
init(context, attrs);
}
}
@TargetApi(Build.VERSION_CODES.Lollipop)
public MaxHeightScrollView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
if (!isInEditMode()) {
init(context, attrs);
}
}
private void init(Context context, AttributeSet attrs) {
if (attrs != null) {
TypedArray styledAttrs = context.obtainStyledAttributes(attrs, R.styleable.MaxHeightScrollView);
//200 is a defualt value
maxHeight = styledAttrs.getDimensionPixelSize(R.styleable.MaxHeightScrollView_maxHeight, defaultHeight);
styledAttrs.recycle();
}
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
heightMeasureSpec = MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
}
attr.xml
<declare-styleable name="MaxHeightScrollView">
<attr name="maxHeight" format="dimension" />
</declare-styleable>
レイアウト例
<blah.blah.MaxHeightScrollView Android:layout_weight="1"
app:maxHeight="90dp"
Android:layout_width="fill_parent"
Android:layout_height="wrap_content">
<EditText Android:id="@+id/commentField"
Android:hint="Say Something"
Android:background="#FFFFFF"
Android:paddingLeft="8dp"
Android:paddingRight="8dp"
Android:gravity="center_vertical"
Android:maxLines="500"
Android:minHeight="36dp"
Android:layout_width="fill_parent"
Android:layout_height="wrap_content" />
</blah.blah.MaxHeightScrollView>
(私はこれが質問に直接答えないことを知っていますが、maxHeight機能を探している他の人には役立つかもしれません)
ConstraintLayoutは、
app:layout_constraintHeight_max="300dp"
app:layout_constrainedHeight="true"
または
app:layout_constraintWidth_max="300dp"
app:layout_constrainedWidth="true"
サンプルの使用法 ここ 。
できればウィズルの答えにコメントしていましたが、Android Nのマルチウィンドウモードのコンテキストでこの問題を解決するには、コードを変更する必要があることに注意するのが便利だと思いましたこれに少し:
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
if(MeasureSpec.getSize(heightMeasureSpec) > maxHeight) {
heightMeasureSpec = MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST);
}
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
これにより、レイアウトのサイズを最大の高さよりも小さくすることができますが、最大の高さよりも大きくなることもできません。これを使用して、RelativeLayout
をオーバーライドするレイアウトクラスを使用しました。これにより、ScrollView
の子としてMaxHeightRelativeLayout
を含むカスタムダイアログを作成し、画面の全高を拡張せず、また、Android Nのマルチウィンドウで最小のWidowサイズに収まるように縮小します。
MaxHeightを設定する方法はありません。ただし、高さは設定できます。
そのためには、scrollViewの各アイテムの高さを発見する必要があります。その後、scrollViewの高さをnumberOfItens * heightOfItemに設定するだけです。
アイテムの高さを発見するには、次のようにします。
View item = adapter.getView(0, null, scrollView);
item.measure(0, 0);
int heightOfItem = item.getMeasuredHeight();
高さを設定するには、次のようにします。
// if the scrollView already has a layoutParams:
scrollView.getLayoutParams().height = heightOfItem * numberOfItens;
// or
// if the layoutParams is null, then create a new one.
scrollView.setLayoutParams(new LayoutParams(LayoutParams.FILL_PARENT, heightOfItem * numberOfItens));
マイMaxHeightScrollView
カスタムビュー
public class MaxHeightScrollView extends ScrollView {
private int maxHeight;
public MaxHeightScrollView(Context context) {
this(context, null);
}
public MaxHeightScrollView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public MaxHeightScrollView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init(context, attrs);
}
private void init(Context context, AttributeSet attrs) {
TypedArray styledAttrs =
context.obtainStyledAttributes(attrs, R.styleable.MaxHeightScrollView);
try {
maxHeight = styledAttrs.getDimensionPixelSize(R.styleable.MaxHeightScrollView_mhs_maxHeight, 0);
} finally {
styledAttrs.recycle();
}
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
if (maxHeight > 0) {
heightMeasureSpec = MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST);
}
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
}
style.xml
<declare-styleable name="MaxHeightScrollView">
<attr name="mhs_maxHeight" format="dimension" />
</declare-styleable>
使用
<....MaxHeightScrollView
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
app:mhs_maxHeight="100dp"
>
...
</....MaxHeightScrollView>
layout_weight value を使用してみましたか? 0より大きい値に設定すると、使用可能な残りのスペースにそのビューが拡大されます。
ストレッチが必要なビューが複数ある場合、値はそれらの間の重みになります。
したがって、2つのビューが両方ともlayout_weight値1に設定されている場合、それらは両方とも空間を埋めるためにストレッチしますが、両方とも同じ量のスペースにストレッチします。それらの1つを値2に設定すると、他のビューの2倍に伸びます。
Layout_height = "max_height"でScrollView
をplainLinearLayout
で包むと、これは完璧な仕事をします。実際、このコードは過去5年間に問題なく生産されています。
<LinearLayout
Android:id="@+id/subsParent"
Android:layout_width="match_parent"
Android:layout_height="150dp"
Android:gravity="bottom|center_horizontal"
Android:orientation="vertical">
<ScrollView
Android:id="@+id/subsScroll"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_marginBottom="10dp"
Android:layout_marginEnd="15dp"
Android:layout_marginStart="15dp">
<TextView
Android:id="@+id/subsTv"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text="@string/longText"
Android:visibility="visible" />
</ScrollView>
</LinearLayout>
誰かがLayoutParamsに正確な値を使用することを検討している場合.
setLayoutParams(new LayoutParams(Y, X );
デバイスディスプレイの密度を考慮することを忘れないでください。そうしないと、異なるデバイスで非常に奇妙な動作をする可能性があります。例えば:
Display display = getWindowManager().getDefaultDisplay();
DisplayMetrics d = new DisplayMetrics();
display.getMetrics(d);
setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, (int)(50*d.density) ));
ご存知のとおり、Androidを実行しているデバイスは、さまざまな画面サイズを持つことができます。さらに知っているように、ビューは動的に調整し、適切なスペースになる必要があります。
最大の高さを設定した場合、十分なスペースを確保しないように、またはスペースを少なくするようにビューを強制することができます。私は時々、実際には最大の高さを設定するように思われることを知っています。しかし、解像度が劇的に変化し、変化する場合、最大の高さを持つビューは適切に見えません。
必要なレイアウトを正確に実行する適切な方法はないと思います。レイアウトマネージャーと関連するメカニズムを使用して、レイアウトを検討することをお勧めします。あなたが何を達成しようとしているのかわかりませんが、リストには3つのアイテムしか表示されず、ユーザーはスクロールする必要があるというのは少し奇妙に聞こえます。
ところで。 minHeightは保証されていません(おそらく存在しないはずです)。アイテムを強制的に表示し、他の関連アイテムを小さくすると、いくつかの利点があります。
最初にアイテムの高さをピクセル単位で取得します
View rowItem = adapter.getView(0, null, scrollView);
rowItem.measure(0, 0);
int heightOfItem = rowItem.getMeasuredHeight();
その後、単に
Display display = getWindowManager().getDefaultDisplay();
DisplayMetrics displayMetrics = new DisplayMetrics();
display.getMetrics(displayMetrics);
scrollView.getLayoutParams().height = (int)((heightOfItem * 3)*displayMetrics .density);
scrollView.setHeight(200px)
、2つのアイテムscrollView.setheight(400px)
の3つ以上のscrollView.setHeight(600px)
だけで、1つのアイテムの実行時に高さを設定できると思います
オーバーフロー以外のスクロールビューまたはリストビューを作成したい場合は、RelativeLayoutでトップビューとボトムビューを上下に配置してください:
<ScrollView
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:layout_above="@+id/topview"
Android:layout_below="@+id/bottomview" >
私はここに答えがあります:
https://stackoverflow.com/a/29178364/1148784
ScrollViewを拡張する新しいクラスを作成し、onMeasure
メソッドをオーバーライドするだけです。
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
if (maxHeight > 0){
int hSize = MeasureSpec.getSize(heightMeasureSpec);
int hMode = MeasureSpec.getMode(heightMeasureSpec);
switch (hMode){
case MeasureSpec.AT_MOST:
heightMeasureSpec = MeasureSpec.makeMeasureSpec(Math.min(hSize, maxHeight), MeasureSpec.AT_MOST);
break;
case MeasureSpec.UNSPECIFIED:
heightMeasureSpec = MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST);
break;
case MeasureSpec.EXACTLY:
heightMeasureSpec = MeasureSpec.makeMeasureSpec(Math.min(hSize, maxHeight), MeasureSpec.EXACTLY);
break;
}
}
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}