2016-08-10 4 views
0

私はアプリを作っており、ユーザーフィードを表示するためのリサイクルビューを持っています。私は記事を好きにするためにトグルボタンを使用しています。ユーザーがアプリを開くと、そのアプリを使用しているユーザーがステータスを既に好きで、他のソーシャルアプリのようにスクロールして、そのユーザーが投稿を好きになるような場合は、likeボタンが有効になります。Androidリサイクラービューのトグルボタンのリサイクルの問題

のスクロール時にトグルボタンがチェックされていると、他のポストに属するトグルボタンもチェックされてしまうという問題があります。

アダプタクラス

public class topNewsAdapter extends RecyclerView.Adapter<topNewsRowHolder> { 

     private ArrayList<topData> topDataList; 
     private Context context; 
     private Activity activity; 
     private RecyclerView recyclerView; 
     private View v; 
     protected String liked = "success"; 
     protected String expired = "Expired"; 




     public topNewsAdapter(ArrayList<topData> listItemList , Activity activity , RecyclerView view) { 

      this.topDataList = listItemList; 
      this.activity = activity; 
      this.recyclerView = view; 

     } 



     @Override 
     public topNewsRowHolder onCreateViewHolder(final ViewGroup parent, int viewType) { 
      v = LayoutInflater.from(parent.getContext()).inflate(R.layout.top_news_row, parent, false); 
      context = parent.getContext(); 
      return new topNewsRowHolder(v , activity); //passed activity 



     } 

     @Override 
     public void onBindViewHolder(final topNewsRowHolder holder, final int position) { 


      topData item = topDataList.get(position); 

      if(!(item == null)) { 

       holder.userName.setText(item.getUserName().toString()); 
       holder.timer.setText(item.getCreatedTime().toString()); 
       holder.status.setText(item.getStatus().toString()); 
       holder.fameCount.setText(item.getLikeCount().toString()); 
       holder.dislike_Count.setText(item.getDislike_Count().toString()); 
       holder.statusID.setText(item.getStatusID().toString()); 



       if(item.getLiked().equals(1)){ 
        holder.fameButton.setChecked(true); 
       }else if(item.getLiked().equals(0)){ 
        holder.fameButton.setChecked(false); 
       } 



       if(item.getDisliked().equals(1)){ 
        holder.disLikeButton.setChecked(true); 

       }else if(item.getDisliked().equals(0)){ 
        holder.disLikeButton.setChecked(false); 
       } 





       holder.fameButton.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() { 
        @Override 
        public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { 
         if(isChecked){ 

          lRequester(holder.statusID.getText().toString() , "1" , holder.fameCount); 
          dRequester(holder.statusID.getText().toString() , "0" , holder.dislike_Count); 

          holder.fameButton.setChecked(true); 


         }else if(!isChecked){ 
          lRequester(holder.statusID.getText().toString() , "0" , holder.fameCount); 


         } 
        } 
       }); 


       holder.disLikeButton.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() { 
        @Override 
        public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { 
         if(isChecked){ 
          dRequester(holder.statusID.getText().toString(), "1" ,holder.dislike_Count); 
          lRequester(holder.statusID.getText().toString() , "0" , holder.fameCount); 

          holder.fameButton.setChecked(false); 

         }else if(!isChecked){ 
          dRequester(holder.statusID.getText().toString() , "0" , holder.dislike_Count); 
         } 
        } 
       }); 







     } 



     } 













     @Override 
     public int getItemCount() { 
      return topDataList.size(); 
     } 


     @Override 
     public long getItemId(int position) { 
      return position; 
     } 




     public void lRequester(String id , String type, final TextView textview){ 
      Call<responseFD> request = handler.handlerClass.fame(data("u") , data("t") , id , type); 
      request.enqueue(new Callback<responseFD>() { 
       @Override 
       public void onResponse(Call<responseFD> call, Response<responseFD> response) { 
        if(!response.body().getResponse().isEmpty() && (response.body().getResponse() != null)) { 

         if (response.body().getResponse().equals(expired)) { 
          vlData.getInstance().terminateRunnable(); 
          reset(); 

         }else if (response.body().getResponse().equals(liked)) { 
          textview.setText(response.body().getLike_count().toString()); 

         } 


        } 

       } 

       @Override 
       public void onFailure(Call<responseFD> call, Throwable t) { 
        Toast.makeText(v.getContext(), "Something Gone Wrong", Toast.LENGTH_SHORT).show(); 

       } 
      }); 


     } 


     public void dRequester(String id , String type , final TextView textView){ 
      Call<responseFD> request = handler.handlerClass.disfame(data("u") , data("t") , id , type); 
      request.enqueue(new Callback<responseFD>() { 
       @Override 
       public void onResponse(Call<responseFD> call, Response<responseFD> response) { 
        if(!response.body().getResponse().isEmpty() && response.body().getResponse() != null) { 
         if (response.body().getResponse().equals(expired)) { 
          vlData.getInstance().terminateRunnable(); 
          reset(); 

         }else if (response.body().getResponse().equals(liked)) { 
          textView.setText(response.body().getDislike_Count().toString()); 

         } 
        } 


       } 

       @Override 
       public void onFailure(Call<responseFD> call, Throwable t) { 
        Log.d("data", "onFailure: " + t.getMessage()); 
       } 
      }); 







     } 


     public void reset(){ 

      Intent i = new Intent(activity , login.class); 
      activity.startActivity(i); 
      activity.finish(); 
     } 



    } 

Rowholderクラス

public class topNewsRowHolder extends RecyclerView.ViewHolder { 

    protected TextView userName; 
    protected TextView timer; 
    protected TextView status; 
    protected ImageView profilePicHolder; 
    protected TextView fameCount; 
    protected TextView dislike_Count; 
    protected ToggleButton fameButton; 
    protected ToggleButton disLikeButton; 
    protected View v; 
    protected TextView statusID; 
    protected Activity activity; 
    protected RelativeLayout holderlayout; 




    public topNewsRowHolder(View view , Activity activity){ 
     super(view); 
     v = view; 
     this.activity = activity; 

     this.userName = (TextView)view.findViewById(R.id.usernameHolder); 
     this.timer = (TextView)view.findViewById(R.id.timeHolder); 
     this.status = (TextView)view.findViewById(R.id.status_user); 
     this.profilePicHolder = (ImageView)view.findViewById(R.id.profile_pic_holder); 
     this.fameCount = (TextView)view.findViewById(R.id.like_count); 
     this.dislike_Count = (TextView)view.findViewById(R.id.dislike_count); 
     this.fameButton = (ToggleButton)view.findViewById(R.id.fameButton); 
     this.disLikeButton = (ToggleButton)view.findViewById(R.id.dislikeButton); 
     this.statusID = (TextView)view.findViewById(R.id.statusID); 
     this.holderlayout = (RelativeLayout) view.findViewById(R.id.text); 







    } 


    } 

私はこれが原因で、リサイクルである知っています。この問題を解決するには?ありがとう:)

+0

変更されたリスナーをチェックするには、setLikedとsetItemDislikedを設定し、notifyitemChanged(getAdapterPosition())を呼び出す必要があります。それはそれを解決すべきです。それが役に立ったら教えてください。 –

+0

'SparseBooleanArray' [SparseBooleanArray](https://developer.android.com/reference/android/util/SparseBooleanArray.html) –

+0

どのような例@vrundpurohit? –

答えて

0

これを試してください:RecyclerViewは、チェックしているアイテムを追跡するために外部変数が必要ですが、SparseBooleanArrayは面倒です。

holder.fameButton.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() { 
    @Override 
    public void onCheckedChanged(CompoundButton buttonView, boolean IsChecked) { 
     isChecked ? item.setIsLiked(1) : item.setIsLiked(0); 
     if(isChecked){ 
      lRequester(holder.statusID.getText().toString() , "1" , holder.fameCount); 
      dRequester(holder.statusID.getText().toString() , "0" , holder.dislike_Count); 
     } else if(!isChecked){ 
      lRequester(holder.statusID.getText().toString() , "0" , holder.fameCount); 
     } 
     } 
    }); 
+0

私はこれらの値をブール配列ではなくjsonから取得しています。ユーザーが既に投稿を好きだった場合は、トグルボタンを有効にします。 if(item.getLiked()。equals(1)){ holder.fameButton.setChecked(true); } なら{holder.disLikeButton.setChecked(真)(item.getDisliked()に等しい(1))。 } –

+0

トグルボタンのチェック時に好き嫌いをするオプションはありませんか? –

+0

はいそうです。これらの値のソースは三項で使用されますか? isChecked? item.setIsLiked(1):item.setIsLiked(0); ? –

0

コンテンツフィード内のmanagind likesのブローカパターンを作成します。

このシングルトンが壊れた場合、各ContentフィードアイテムのIDが追跡され、ハッシュマップ内の状態(ソーシャルまたは好きなもの)にマッピングされます。また、Contentフィードアイテムに反応するような反応があるたびに、このブローカを使用してアクタリアンをトリガします。このブローカは、変更をローカルに伝播して追跡します。あなたは、変更についてUIを作成するために、Broadcasterまたはpub-subパターンを実装する必要があります。

ウェブサーバーから取得しているjsonを格納するためのデータベースを備えたコンテンツプロバイダを使用することをおすすめします。

さらなる説明が必要な場合はお知らせください。


SocialBroker.java

public class SocialBroker extends ISocialBroker { 
    //region <!-- Private properties --> 
    private static SocialBroker _instance; 
    private HashMap<UUID, SocialStatus> _map = new HashMap<>(); 
    //endregion 

    //region <!-- Singleton initializer --> 
    public static SocialBroker newInstance() { 
     if (_instance == null) { 
      _instance = new SocialBroker(); 
     } 
     return _instance; 
    } 

    private SocialBroker() {}; 
    //endregion 
    // The interface method implemented here 
} 

ISocialBroker.java

public interface ISocialBroker { 
    public synchronized SocialStatus save(String expiresAt, UUID id, boolean hasLiked, int numberOfLikes, int numberOfComments); 
    public SocialStatus lookup(UUID id); 
    public synchronized SocialStatus like(UUID id); 
    public synchronized SocialStatus unlike(UUID id); 

    public HashMap<UUID, SocialStatus> getMap(); 
    public void loadState(HashMap<UUID, SocialStatus> restoredSocialState); 
} 

OnReactionObserver.java

public interface OnReactionObserver { 
    void onLikeReaction(); 
} 

OnReactionPublisher.java

public interface OnReactionPublisher { 
    void attachObserver(OnReactionObserver... observer); 
    void notifyListeners(); 
} 

アダプターのビューに結果をバインドすると、ブローカーを使用してエントリーを保管し、同様のボタン・ビューでブローカーを再度呼び出してlike/unlike/dislike/undislikeを実行します。

SocialStatusは、情報を追跡し、シリアライズ、保存、オンラインサービスとの同期が可能な単なるモデルです。

これは正しい方向に向いていますか?

+0

どのような例ですか? –

+0

@JijoJohnは上記の私の答えを更新しました。 – anthonymonori