Android:ListViewから子ビューにアクセスします
-
05-07-2019 - |
質問
ListView
を使用して表示されたリスト内の1つの要素のピクセル位置を見つける必要があります。 TextViewのの1つを取得してから getTop()
を使用する必要があるようですが、 ListViewの子ビューを取得する方法がわかりません
。
更新: ListView
の場合、 ViewGroup
の子はリスト内のアイテムと1対1で対応しません。代わりに、 ViewGroup
の子は、現在表示されているビューのみに対応しています。したがって、 getChildAt()
は、 ViewGroup
の内部にあるインデックスで動作し、 ListView のリスト内の位置とは必ずしも関係ありませんcode>を使用します。
解決
参照: Android ListView:のデータインデックスを取得表示アイテム 上記のFeetの回答の一部と組み合わせると、次のようなものが得られます。
int wantedPosition = 10; // Whatever position you're looking for
int firstPosition = listView.getFirstVisiblePosition() - listView.getHeaderViewsCount(); // This is the same as child #0
int wantedChild = wantedPosition - firstPosition;
// Say, first visible position is 8, you want position 10, wantedChild will now be 2
// So that means your view is child #2 in the ViewGroup:
if (wantedChild < 0 || wantedChild >= listView.getChildCount()) {
Log.w(TAG, "Unable to get view for desired position, because it's not being displayed on screen.");
return;
}
// Could also check if wantedPosition is between listView.getFirstVisiblePosition() and listView.getLastVisiblePosition() instead.
View wantedView = listView.getChildAt(wantedChild);
利点は、ListViewの子を反復処理しないことです。これにより、パフォーマンスが低下する可能性があります。
他のヒント
このコードは使いやすいです:
View rowView = listView.getChildAt(viewIndex);//The item number in the List View
if(rowView != null)
{
// Your code here
}
ListViewクラスのドキュメントをすばやく検索すると、ViewGroupから継承されたgetChildCount()およびgetChildAt()メソッドが見つかりました。これらを使用してそれらを反復処理できますか?よくわかりませんが、試してみる価値はあります。
見つかったこちら
listview.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, final View view, int position, long id) {
View v;
int count = parent.getChildCount();
v = parent.getChildAt(position);
parent.requestChildFocus(v, view);
v.setBackground(res.getDrawable(R.drawable.transparent_button));
for (int i = 0; i < count; i++) {
if (i != position) {
v = parent.getChildAt(i);
v.setBackground(res.getDrawable(R.drawable.not_clicked));
}
}
}
});
基本的に、2つの Drawables を作成します-1つは透明で、もう1つは目的の色です。クリックした位置(定義どおり int position
)でフォーカスを要求し、その行の色を変更します。次に、親の ListView
をウォークスルーし、それに応じて他のすべての行を変更します。これは、ユーザーが listview
を複数回クリックしたときに考慮されます。これは、 ListView
の各行のカスタムレイアウトを使用して行われます。 (非常にシンプルで、 TextView
で新しいレイアウトファイルを作成するだけです-フォーカス可能またはクリック可能に設定しないでください!)。
カスタムアダプタは不要- ArrayAdapter
int position = 0;
listview.setItemChecked(position, true);
View wantedView = adapter.getView(position, null, listview);
これは、ListView内の要素の位置を知っていることを前提としています:
View element = listView.getListAdapter().getView(position, null, null);
その後、getLeft()およびgetTop()を呼び出して、画面上の位置の要素を決定できるはずです。