2016-06-16 7 views
0

私はthorbenprimkeアンドロイド変えるためには、実行時のレルムにRecyclerview

でRealmRecyclerViewを使用してレルムDBからrecyclerview内のデータをロードしています starredAt

を言うフィールドに基づいて項目のリストを注文する必要があります

フィールドは、ユーザーの操作に応じて値を変更します。つまり、ユーザーが「スター」ボタンを押すと、項目は上に移動する必要があります。

このため、オブジェクトのstarredAtフィールドを更新するだけです。

アイテムはすでにstarredAtでソートされているため、レルムは更新されたリストをロードしますが、1つ以上のアイテムをrecyclerviewにランダムに追加します。

CheatSheet.java

public class CheatSheet extends RealmObject { 

@PrimaryKey 
private String id; 

private RealmList<Item> items; 

private String title; 

public String getId() { 
    return id; 
} 

public void setId(String id) { 
    this.id = id; 
} 

public String getTitle() { 
    return title; 
} 

public void setTitle(String title) { 
    this.title = title; 
} 

public RealmList<Item> getItems() { 
    return items; 
} 

public void setItems(RealmList<Item> items) { 
    this.items = items; 
} 
} 

Item.java

public class Item extends RealmObject { 

@PrimaryKey 
private String id; 

private String description; 

private Date starredAt; 

public Item() { 
} 

public String getId() { 
    return id; 
} 

public void setId(String id) { 
    this.id = id; 
} 

public String getDescription() { 
    return description; 
} 

public void setDescription(String description) { 
    this.description = description; 
} 

public Date getStarredAt() { 
    return starredAt; 
} 

public void setStarredAt(Date starredAt) { 
    this.starredAt = starredAt; 
} 
} 

CheatSheetActivity.java

public class MainActivity extends AppCompatActivity { 

RealmRecyclerView revItems; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 
    setData(); 
} 

private void setData() { 
    rvItems = (RealmRecyclerView) findViewById(R.id.rev_items); 
    RealmResults<Item> items = Realm.getDefaultInstance().where(CheatSheet.class) 
         .equalTo("id", "some-id").findFirst().getItems() 
         .where() 
         .findAllSorted("starredAt", Sort.DESCENDING); 

    ItemRealmListAdapter itemRealmListAdapter = 
        new ItemRealmListAdapter(this, items, 
              true, true); 
    rvItems.setAdapter(itemRealmListAdapter); 
} 

ItemRealmListAdapter.java

public class ItemRealmListAdapter extends RealmBasedRecyclerViewAdapter<Item, 
    ItemRealmListAdapter.ItemViewHolder> { 

RealmResults<Item> mItems; 

public ItemRealmListAdapter(Context context, RealmResults<Item> realmResults, 
          boolean automaticUpdate, boolean animateResults) { 
    super(context, realmResults, automaticUpdate, animateResults); 
    this.mItems = realmResults; 
} 

@Override 
public ItemViewHolder onCreateRealmViewHolder(ViewGroup viewGroup, int i) { 
    return new ItemViewHolder(LayoutInflater.from(viewGroup.getContext()) 
      .inflate(R.layout.item_layout_cs_text, viewGroup, false)); 
} 

public Item getItem(int position) { 
    return mItems.get(position); 
} 

@Override 
public void onBindRealmViewHolder(ItemViewHolder itemViewHolder, int position) { 
    itemViewHolder.txtBody.setText(getItem(position).getDescription()); 
    if (getItem(position).getStarredAt() != null) { 
     itemViewHolder.imvStar.setImageResource(R.drawable.ic_star_yellow); 
    } 
    itemViewHolder.imvStar.setOnClickListener(v -> handleStarClick(v,position)); 
} 

private void handleStarClick(View v, int position) { 
    if (getItem(position).getStarredAt() != null) { 
     ((ImageView) v).setImageResource(R.drawable.ic_star); 
     CheatSheetStorage.unStarItem("some-id", getItem(position)); 
    } else { 
     ((ImageView) v).setImageResource(R.drawable.ic_star_yellow); 
     CheatSheetStorage.starItem("some-id", getItem(position)); 
    } 

} 

public static class ItemViewHolder extends RealmViewHolder { 

    @Bind(R.id.txt_cheat_sheet) 
    TextView txtBody; 

    @Bind(R.id.img_star) 
    ImageView imvStar; 


    public ItemViewHolder(View itemView) { 
     super(itemView); 
     ButterKnife.bind(this, itemView); 
    } 
} 
} 

CheatSheetStorage.java

public class CheatSheetStorage { 
public static void unStarItem(String cheatSheetId, Item item) { 
    Realm realm = Realm.getDefaultInstance(); 
    realm.beginTransaction(); 
    CheatSheet cheatSheet = getCheatSheetById(cheatSheetId); 
    Item itemDB = cheatSheet.getItems().where().equalTo("id", item.getId()).findFirst(); 
    itemDB.setStarredAt(null); 
    realm.commitTransaction(); 
} 

public static void starItem(String cheatSheetId, Item item) { 
    Realm realm = Realm.getDefaultInstance(); 
    realm.beginTransaction(); 
    CheatSheet cheatSheet = getCheatSheetById(cheatSheetId); 
    Item itemDB = cheatSheet.getItems().where().equalTo("id", item.getId()).findFirst(); 
    itemDB.setStarredAt(new Date()); 
    realm.commitTransaction(); 
} 
} 

明確なアイデアについては、以下のスクリーンショットをご参照ください:ロハン-Peshkar @

Screenshot before starring

Screenshot after starring the sixth item

+0

何かのようなサウンドがリサイクル/リバウンドされていませんか?しかし、いくつかのコードを表示してください。 –

答えて

1

を - あなたはアダプタにanimateExtraColumnName価値を提供する必要があります。アニメーションの場合、アダプターは項目を追跡し、その項目のIDは変更されないため、リストは更新されません。追加の列(starredAt列の場合は、Integerとして格納されている必要があります)を使用すると、差分アルゴリズムで変更が検出され、順序が更新されます。参考のため

https://github.com/thorbenprimke/realm-recyclerview/blob/2835a543dce20993d8f98a4f773fa0e67132ce52/library/src/main/java/io/realm/RealmBasedRecyclerViewAdapter.java#L177

あなたはまた、例えばフォルダ内MainActivityをチェックアウトすることができます。この例では、行のテキストを「ABC」から「Updated ABC」に変更し、主キーと引用フィールドの両方を使用して基本的に比較目的の複合キーを作成するため、リストに変更が認識されます。

+0

あまりにも遅く返答して申し訳ありませんが、実際にはフィールドstarrdAtは日付型です。日付自体に基づいてソートする必要があります。このフィールドは、ユーザー操作で更新されます。 そして、実際の結果を送信している間に、並べ替え順にそれらを照会しています。 –

+0

いいえ。あなたのケース@RohanPeshkarのようなサウンド、 'animateExtraColumnName'としてのDateのサポートを追加する必要があります。 当分の間、行のアニメーションをオフにすると、リストの更新に関して期待どおりに動作するはずです。素晴らしいRecyclerViewアニメーションはありません。 –

+0

日付のサポートが追加されました。 libを '0.9.21'(https://github.com/thorbenprimke/realm-recyclerview/commit/295895fa49a8499aa4b5fe2c0658573411ada781)にアップグレードしてください。試してみてください。この例は 'Date'を使うように更新されています。 –

関連する問題