Androidレイアウトの各機種への適応を簡単に紹介(GridViewを含む)
2022-02-24 16:52:56
最近の個人的なプロジェクトは終わりに近づいているのですが、別の問題が発生しました。解像度の異なる携帯電話では、以下のインターフェイスを例にとると、レイアウトが思った通りにならないことがよくあるのです。
今のところ、インターフェースのレイアウトに問題はなく
ただ、レイアウトファイルを書くときに、全部スマホの高さに合わせて書きました。
背の高い携帯に出会うと、こんな風に表示されるんです。
ご想像の通り、スマホが短いとどうしても表示が不完全になってしまうので、ユーザーのスマホの高さに応じて各コントロールの高さを動的に調整する必要があるのです。
1. xml ファイルを解析する。
The layout is generally a LinearLayout with a Banner at the top, then two consecutive TextViews + GridView, a Fragment interface, and a ViewPager+Fragment+RadioButton at the bottom to implement the bottom menu bar, which also occupies a certain height. For the implementation of the menu bar please see.
Android: ViewPager+Fragment+RadioButton implementation of the bottom menu bar sliding switch
Note: For the interface to adapt on different models, be sure to use the padding and margin attributes sparingly in the layout file, which can complicate the situation.
The initial xml file was filled with a lot of padding and margin, but later on, after modification, I only kept two margins, i.e. 5dp spacing above and below each of the two TextViews (personal faculty and data visualization).
Then the situation becomes clear: the
Screen height = Height of status bar above + Height of Banner + 5dp + 20dp of TextView + 5dp
+ GridView + 5dp + 20dp of TextView + 5dp + GridView + 50dp of a set of RadioButton.
2. Get the screen height.
WindowManager manager = this.getWindowManager();
DisplayMetrics outMetrics = new DisplayMetrics();
manager.getDefaultDisplay().getMetrics(outMetrics);
int width = outMetrics.widthPixels;
int height = outMetrics.heightPixels;
width = px2dip(this, width); //360dp
height = px2dip(this, height); //720dp
Where the pixel px to dp method px2dip.
public static int px2dip(Context context, float pxValue) {
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (pxValue / scale + 0.5f);
}
The final calculation is 720dp high and 360dp wide for the screen.
3. Get the height of the status bar above.
public int getStatusBarHeight() {
Resources resources = this.getResources();
int resourceId = resources.getIdentifier("status_bar_height","dimen","android");
int height = resources.getDimensionPixelSize(resourceId);
return px2dip(this, height); //24dp
}
The height of the top status bar is 24dp.
So you end up with the following height in addition to the status bar and the RadioButton below.
int pagerHeight = height - status_bar_height - 50;
We then write it to a SharedPreferences file at
sharedPreferences = getSharedPreferences("user_info", Context.MODE_PRIVATE);
editor = sharedPreferences.edit();
editor.putInt("pager", pagerHeight);
editor.commit();
The final pager is where we put a Banner + two GridViews + two TextViews.
4. Dynamically generated height
In the QueryFragment's onCreateView method, we need to come to dynamically set the height, where I have set the height ratio of the topmost rotating image to the two GriViews below at 6:7:7, i.e.
private void setHeight() {
SharedPreferences sharedPreferences = getContext().getSharedPreferences("user_info", Context.MODE_PRIVATE);
float pagerHeight = sharedPreferences.getInt("pager", StudentMainActivity.pagerHeight);
pagerHeight -= 60;
LinearLayout.LayoutParams linearParams = (LinearLayout.LayoutParams) banner.getLayoutParams();
linearParams.height = dip2px(getContext(), pagerHeight / 20 * 6);
banner.setLayoutParams(linearParams);
linearParams = (LinearLayout.LayoutParams) eduGridView.getLayoutParams();
linearParams.height = dip2px(getContext(), pagerHeight / 20 * 7);
eduGridView.setLayoutParams(linearParams);
linearParams = (LinearLayout.LayoutParams) visionGridView.getLayoutParams();
linearParams.height = dip2px(getContext(), pagerHeight / 20 * 7);
visionGridView.setLayoutParams(linearParams);
}
The subtracted 60dp is the height of the two TextViews and the four margins, but of course you can dynamically set the height of the two TextViews, but I'm limiting it to 20dp high.
5. GridView's Adapter file modification
The use of the GridView requires the Adapter file, in which we set each item, in this case, the item is an ImageView above and a TextView below.
<?xml version="1.0" encoding="utf-8"? >
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center_horizontal"
android:orientation="vertical">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="vertical"
android:padding="0dp">
<ImageView
android:id="@+id/iv_grid"
android:layout_width="60dp"
android:layout_height="79.375dp"/>
<TextView
android:id="@+id/tv_grid"
android:layout_width="wrap_content"
android:layout_height="20dp"
android:layout_marginTop="3dp"
android:gravity="center"
android:text=""/>
</LinearLayout>
</LinearLayout>
So then in the adapter file we also have to dynamically set the height of each item, because each GridView has two rows, so the height of a GridView is
height = (ImageView + 3dp's margin + TextView height) * 2
Here the height of the TextView is also like the previous one, I have written it to death at 20dp, while the height of the GridView has been calculated earlier as follows.
float gridViewHeight = pagerHeight / 20 * 7;
So the final height of the ImageView is
(gridViewHeight - 46) / 2
So we end up setting it up like this.
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View view = LayoutInflater.from(context).inflate(R.layout.item_grid, null);
SharedPreferences sharedPreferences = context.getSharedPreferences("user_info", Context.MODE_PRIVATE);
pagerHeight -= 60;
float gridViewHeight = pagerHeight / 20 * 7;
ImageView iv = view.findViewById(R.id.iv_grid);
TextView tv = view.findViewById(R.id.tv_grid);
LinearLayout.LayoutParams linearParams = (LinearLayout.LayoutParams) iv.getLayoutParams();
linearParams.height = dip2px(context, (gridViewHeight - 46) / 2);
iv.setLayoutParams(linearParams);
iv.setImageResource(images[position]);
tv.setText(names[position]);
return view;
}
The core code is.
LinearLayout.LayoutParams linearParams = (LinearLayout.LayoutParams) iv.getLayoutParams();
linearParams.height = dip2px(context, (gridViewHeight - 46) / 2);
iv.setLayoutParams(linearParams);
Note here: LinearLayout.LayoutParams needs to be converted to pixels when setting the height, so it needs to use dip2px:.
public static int dip2px(Context context, float dpValue) {
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (dpValue * scale + 0.5f);
}
Screen height = Height of status bar above + Height of Banner + 5dp + 20dp of TextView + 5dp
+ GridView + 5dp + 20dp of TextView + 5dp + GridView + 50dp of a set of RadioButton.
関連
-
ADBサーバーがACKしない ソリューション
-
[android.os.NetworkOnMainThreadException を解決してください。
-
RecyclerView がアダプタが接続されていませんと表示され、レイアウトソリューションをスキップする
-
ERROR: x86 エミュレーションには現在ハードウェアアクセラレーションが必要です。
-
android studioについて Error:Execution failed for task ':app:preDebugAndroidTestBuild'. 解決方法
-
アンドロイドのdrawableフォルダ配下の各種xmlスタイルファイルの使用方法について詳しく解説しています
-
Androidの内部育成に磨きをかける2年間
-
江さんが熟練者から始めさせます。Android Studioは、ランディングページのパスワードスイッチの表示(小さな目)を作成する
-
Android TextViewの自動改行問題
-
原因:android.content.res.Resources$NotFoundException。文字列リソースID #0x0
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Androidでの録音とMP3へのローカルトランスコード
-
ADBサーバーがACKしなかった
-
AndroidStudioは、新しいプロジェクト:エミュレータを作成した後、エラーを報告します。ERROR: x86 emulation currently requires hardware acceleration!
-
ArrayAdapter のソリューションでは、リソース ID が TextView である必要があります。
-
AndroidでSPAN_EXCLUSIVE_EXCLUSIVEスパンが長さ0にできない場合、EditTextでコンテンツを削除する
-
Androidアプリの放送受信機登録(registerReceiver)処理の分析
-
Android Studioのヒント - これを読めば、すべてのヒントが役に立つ
-
MPAndroidChartのPieChartで、セクターが表示されず、中央のテキストのみが表示される。
-
アンドロイドについて:DescendantFocusability いくつかの使用感
-
SQLiteReadOnlyDatabaseException: 読み取り専用のデータベースを書き込もうとした (コード 1032)