イラストのコード:
mLinearLayoutManager = new LinearLayoutManager(this);
mLinearLayoutManager.setReverseLayout(true);
mLinearLayoutManager.setStackFromEnd(true);
mMessageRecyclerView.setLayoutManager(mLinearLayoutManager);
リサイクルビューのbottomに新しいアイテム(私の場合はメッセージ)を追加し、ビューの「重力」を上部に維持するにはどうすればよいですか?
したがって、現在機能しているのは次のとおりです。
動作しないもの:
setStackFromEnd = trueおよびsetReverseLayout = true
setStackFromEnd
は最後の要素を表示するようにビューを設定しますが、レイアウトの方向は変わりませんが、setReverseLayout
はアダプタによって追加された要素の順序を変更します。
これらの2行を削除するか、false
を設定してみてください
layoutManager.setReverseLayout(true);
layoutManager.setStackFromEnd(true);
これを使用して、キーボードが表示されたらRecyclerView
とEditText
を上に移動してみてください
<activity name="YourActivity"
Android:windowSoftInputMode="stateHidden|adjustResize">
//stateHidden--->keyboard is hidden when you first open the activity and adjustResize---> this will adjust the layout resize option.
...
</activity>
AndroidManifest.xml
。
RecyclerViewを上部にフックするには
<Android.support.v7.widget.RecyclerView
Android:id="@+id/messageRecyclerViewRep"
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:layout_alignParentLeft="true"
Android:layout_alignParentStart="true"
Android:layout_below="@+id/linearLayout3"
Android:layout_marginLeft="36dp"
Android:scrollbars="vertical" />
RecyclerViewを一番下に配置し、キーボードがポップアップするときに押し上げます。
<LinearLayout
Android:id="@+id/recyclerContainer"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:layout_below="@+id/linearLayout3"
Android:layout_above="@+id/linearLayout"
Android:gravity="bottom">
<Android.support.v7.widget.RecyclerView
Android:id="@+id/messageRecyclerViewRep"
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:layout_marginLeft="36dp"
Android:scrollbars="vertical" />
</LinearLayout>
キーボードがポップアップしたとき、つまりリサイクラービューのレイアウトが変更されたときにrecyclerViewを下にスクロールするには
recyclerView.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
if (bottom < oldBottom) {
recyclerView.postDelayed(new Runnable() {
@Override
public void run() {
recyclerView.smoothScrollToPosition(mAdapter.getItemCount());
}
}, 100);
}
}
});
setReverseLayout(true) これは、アイテムの走査とレイアウトの順序を逆にします。最初のアイテムは、ビューやコンテンツではなく終了します。
setStackFromEnd(true) これは、ビューの下からリサイクラリストのコンテンツを埋めます。
setStackFromEnd(true)
ではなくsetReverseLayout(true)
する必要があります
XML Recyclerviewでは、高さはmatch_parent
以下に作業コードを示しました。
activity xml
<?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:orientation="vertical">
<Button
Android:id="@+id/btnAdd"
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:text="Add" />
<Android.support.v7.widget.RecyclerView
Android:id="@+id/rcList"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:clipToPadding="true" />
</LinearLayout>
list item xml layout
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:layout_marginLeft="20dp"
Android:layout_marginRight="20dp"
Android:gravity="center_vertical">
<TextView
Android:id="@+id/textView"
Android:layout_width="wrap_content" Android:textSize="23sp"
Android:layout_height="wrap_content" Android:textColor="#4a4883"
Android:text="Test Text" />
</FrameLayout>
アダプタクラス
public class CustomAdapter extends RecyclerView.Adapter<CustomAdapter.ViewHolder> {
private static final String TAG = "CustomAdapter";
private ArrayList<String> mDataSet;
private int size = 0;
public static class ViewHolder extends RecyclerView.ViewHolder {
private final TextView textView;
public ViewHolder(View v) {
super(v);
v.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.d(TAG, "Element " + getAdapterPosition() + " clicked.");
}
});
textView = (TextView) v.findViewById(R.id.textView);
}
public TextView getTextView() {
return textView;
}
}
public CustomAdapter(ArrayList<String> dataSet) {
mDataSet = dataSet;
if (mDataSet != null && !mDataSet.isEmpty()) {
size = mDataSet.size();
}
}
public void refreshData(String add) {
if (!TextUtils.isEmpty(add)) {
mDataSet.add(add);
size = mDataSet.size();
notifyDataSetChanged();
}
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) {
// Create a new view.
View v = LayoutInflater.from(viewGroup.getContext())
.inflate(R.layout.list_item, viewGroup, false);
return new ViewHolder(v);
}
@Override
public void onBindViewHolder(ViewHolder viewHolder, final int position) {
Log.d(TAG, "Element " + position + " set.");
viewHolder.getTextView().setText(mDataSet.get(position));
}
@Override
public int getItemCount() {
return size;
}
}
アクティビティクラス
public class MainActivity extends AppCompatActivity {
private RecyclerView mRecyclerView;
protected CustomAdapter mAdapter;
protected LinearLayoutManager mLayoutManager;
protected ArrayList<String> listString = new ArrayList<>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mRecyclerView = (RecyclerView) findViewById(R.id.rcList);
mLayoutManager = new LinearLayoutManager(this);
mLayoutManager.setOrientation(LinearLayoutManager.VERTICAL);
/**
*setStackFromEnd true will fill the content(list item) from the bottom of the view
*/
mLayoutManager.setStackFromEnd(true);
mLayoutManager.setReverseLayout(true);
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setItemAnimator(new DefaultItemAnimator());
findViewById(R.id.btnAdd).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int temp = mAdapter.getItemCount() + 1;
mAdapter.refreshData("Test text " + temp);
mRecyclerView.smoothScrollToPosition(mAdapter.getItemCount());
}
});
mAdapter = new CustomAdapter(listString);
mRecyclerView.setAdapter(mAdapter);
}
}
これを実現する最も簡単な方法は、Firebaseデータベースに入力された方法と逆の順序で要素をRecyclerviewにロードすることです。
@Override
public void onBindViewHolder(ViewHolder viewHolder, final int position) {
Log.d(TAG, "Element " + position + " set.");
viewHolder.getTextView().setText(mDataSet.get(getItemCount() - 1 -position));
}
これは、上からアイテムをロードしているため、最後に挿入されたアイテムが下に表示されるということです。 XMLやその他のコードを変更する必要はありません。
キーボードがポップアップしたときにRecylerviewのサイズが変更されないという同じ問題があったため、この方法に頼りました。
ではごきげんよう!!
これを実装しました。FirebaseRecyclerViewを使用した実装です。これを設定する必要がありますsetStackFromEnd=true
およびsetReverseLayout=true
リサイクラービューホルダー
public class TestingFirebaseHolder extends RecyclerView.ViewHolder {
private TextView mTextView;
private TextView mTextView2;
public TestingFirebaseHolder(View itemView) {
super(itemView);
mTextView = itemView.findViewById(R.id.textViewTesting);
mTextView2 = itemView.findViewById(R.id.textViewTesting2);
}
public void setTextView(String text,String text2)
{
mTextView.setText(text);
mTextView2.setText(text2);
}
}
テストクラス
public class TestingUser {
public String UserName;
public String mUid;
public TestingUser() {
}
public TestingUser(String userName, String uid) {
UserName = userName;
mUid = uid;
}
}
アクティビティコード
private EditText mEditText;
private RecyclerView mRecyclerView;
private FirebaseRecyclerAdapter<TestingUser,TestingFirebaseHolder> mAdapter;
private FirebaseUser mUser;
private DatabaseReference mReference;
mEditText = findViewById(R.id.testingEditText);
mRecyclerView = findViewById(R.id.hello_rec);
mUser = FirebaseAuth.getInstance().getCurrentUser();
mReference = FirebaseDatabase.getInstance().getReference();
LinearLayoutManager ll = new LinearLayoutManager(this);
ll.setReverseLayout(true); // set this
ll.setStackFromEnd(true); // set this
mRecyclerView.setLayoutManager(ll);
Query query = mReference.child("Testing").child(mUser.getUid()).orderByValue();
mAdapter = new FirebaseRecyclerAdapter<TestingUser, TestingFirebaseHolder>(
TestingUser.class,R.layout.testing_recycler_layout,TestingFirebaseHolder.class,query
) {
@Override
protected void populateViewHolder(TestingFirebaseHolder viewHolder, TestingUser model, int position) {
viewHolder.setTextView(model.mUid,model.UserName);
}
};
mRecyclerView.setAdapter(mAdapter);
public void buttonClick(View view) {
if(!mEditText.getText().toString().isEmpty())
{
TestingUser user = new TestingUser("Salman",mEditText.getText().toString());
mReference.child("Testing").child(mUser.getUid()).Push().setValue(user);
mEditText.setText("");
}
}
結果はリンク
これを試してください、それは私のために動作します。
mLinearLayoutManager = new LinearLayoutManager(this);
mLinearLayoutManager.stackFromEnd(true)
mLinearLayoutManager.isSmoothScrollbarEnabled(true)
mMessageRecyclerView.setLayoutManager(mLinearLayoutManager);