2011-11-10 13 views
7

私の行には、アダプタのgetViewに独自のクリックリスナーが設定されたボタンが含まれています。行の親のandroid:descendantFocusability = "blocksDescendants"を使用して、ボタンのクリックと実際の行項目のクリックを区別することができます。Android:ListViewのボタンの背景をonClickで変更する

ボタンをクリックすると、ボタンの背景が正しく設定されます。私の問題は、リストをスクロールして別の行にも設定するためです。私は彼らの問題をどこかでリサイクルの見解を持つと仮定します。

@Override 
public View getView(int position, View convertView, ViewGroup parent){ 

    if(convertView == null){ 

     holder = new ViewHolder(); 

     convertView = inflater.inflate(R.layout.todays_sales_favorite_row, null); 
     holder.favCatBtn = (Button)convertView.findViewById(R.id.favCatBtn);    

     convertView.setTag(holder); 

    } else { 
     holder = (ViewHolder)convertView.getTag(); 
    } 

     holder.favCatBtn.setTag(position); 
     holder.favCatBtn.setOnClickListener(this); 

    return convertView; 
} 

@Override 
public void onClick(View v) { 
    int pos = (Integer) v.getTag(); 
    Log.d(TAG, "Button row pos click: " + pos); 
    RelativeLayout rl = (RelativeLayout)v.getParent(); 
    holder.favCatBtn = (Button)rl.getChildAt(0); 
    holder.favCatBtn.setBackgroundResource(R.drawable.icon_yellow_star_large); 

} 

だから、それが必要として、私は、行の位置1ボタンの背景の変化にあるボタンをクリックした場合:

は、ここに私のコードです。しかし、次にリストをスクロールすると、他のボタンも同様に設定されています。その後、位置1に戻ってスクロールすると、ボタンの背景が元の位置に戻ってくることがあります。

私はここで何が欠けていますか?私はちょうど私がやっていないマイナーな何かがあることを知っている。

+0

if(true || convertView == null){...(これは常に膨らんでいるので)、それは正常に動作しますか?解決策ではなく、問題がもう現れないかどうかを知りたいだけです。 –

+0

他のランダムな行で背景が変わらないようにすることができます。明らかに、あなたが言ったような解決策ではありませんが、はい、スクロールアップしてボタンを元のバックグラウンドに戻すまで、問題は停止します。 – askilondz

答えて

8

はい、そうです。ビューはリサイクルされています。どの位置がクリックされたかを追跡し、メソッドでバックグラウンドリソースを更新する必要があります。例えば、私は背景トグルを追加するようにコードを拡張:

private final boolean[] mHighlightedPositions = new boolean[NUM_OF_ITEMS]; 

@Override 
public View getView(int position, View convertView, ViewGroup parent){ 

    if(convertView == null){ 
     holder = new ViewHolder(); 
     convertView = inflater.inflate(R.layout.todays_sales_favorite_row, null); 
     holder.favCatBtn = (Button)convertView.findViewById(R.id.favCatBtn); 
     holder.favCatBtn.setOnClickListener(this); 
     convertView.setTag(holder); 
    }else { 
     holder = (ViewHolder)convertView.getTag(); 
    } 

    holder.favCatBtn.setTag(position); 

    if(mHighlightedPositions[position]) { 
     holder.favCatBtn.setBackgroundResource(R.drawable.icon_yellow_star_large); 
    }else { 
     holder.favCatBtn.setBackgroundResource(0); 
    } 

    return convertView; 
} 

@Override 
public void onClick(View view) { 
    int position = (Integer)view.getTag(); 
    Log.d(TAG, "Button row pos click: " + position); 

    // Toggle background resource 
    RelativeLayout layout = (RelativeLayout)view.getParent(); 
    Button button = (Button)layout.getChildAt(0); 
    if(mHighlightedPositions[position]) { 
     button.setBackgroundResource(0); 
     mHighlightedPositions[position] = false; 
    }else { 
     button.setBackgroundResource(R.drawable.icon_yellow_star_large); 
     mHighlightedPositions[position] = true; 
    } 
} 
+0

完璧なおかげで! setBackgroundResource(0)の0を他のドロウアブルに変更するだけで、すべてが意図どおりに動作するようになりました。ありがとう、トン! – askilondz

+0

@Chase助けてくださいhttp://stackoverflow.com/questions/17482001/change-imageview-backgroundresource-in-listview-onitemselected-android – yakusha

+0

おい、あなたは私の人生を保存します – Harry

-1
holder.btnUnLock.setOnClickListener(new OnClickListener() { 

    @Override 
    public void onClick(View v) { 
// TODO Auto-generated method stub 
// Button btn = Button(v); 
    holder = (ViewHolder) v.getTag(); 
    holder.btnSetLock.setBackgroundResource(R.drawable.btn_lock_bg_right); 
holder.btnUnLock.setBackgroundResource(R.drawable.btn_unlock_bg_left); 

} 
}); 
+0

説明を追加できますか? – Robert

1

私はStateListDrawableを使用して、このため、完璧な短いときれいな解決策を見つけた:

@Override 
public View getView(final int position, View convertView, ViewGroup parent) { 
    currentPosition = position; 
    holder = null; 
    if (convertView == null) { 
     holder = new Holder(); 
     LayoutInflater vi = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
     convertView = vi.inflate(R.layout.grid_item, null); 
     holder.imageView = (ImageView) convertView.findViewById(R.id.gridItemBtn); 

     StateListDrawable states = new StateListDrawable(); 
     states.addState(new int[] {android.R.attr.state_pressed}, 
       ContextCompat.getDrawable(context, R.drawable.pressed_state)); 
     states.addState(new int[] {android.R.attr.state_focused}, 
       ContextCompat.getDrawable(context, R.drawable.focused_state)); 
     states.addState(new int[]{}, 
       ContextCompat.getDrawable(context, R.drawable.default_state)); 
     holder.imageView.setImageDrawable(states); 
    } 

    return convertView; 
} 

これはOnClickListenerと一緒に、まだ完璧に動作しますあなたの重要なことをすることができます。

関連する問題