[android] ListViewリサイクルスイッチのシークバー位置



0 Answers

Question

私には奇妙な問題があります。 私はBaseAdapterカスタムListViewBaseAdapterます。 私のListView行レイアウトでは、 TextViewButtons 、およびSeekBarがほとんどありSeekBar 。 すべてがうまくいきます。リサイクル以外の問題はありません。

何が起こるか:目に見えるものを除いて、すべてのSeekBarは隠されています。 SeekBarは、 MediaPlayer on rowが再生されているときに表示されMediaPlayer 。 その部分もすごくうまくいっています。

しかし、ユーザーが上下にスクロールして、可視のSeekBar持つ行が表示されていない場合、それはリサイクルされ、 SeekBarもリサイクルされ、表示されず、その行が再生されていない場合でも(mp)更新されます。 また、ユーザーがスクロールして再生しているビューに戻ると、 SeekBarは表示されますが、更新されず、その位置は0です。代わりにランダムなSeekBarが更新されていますが、表示されません(すべてのSeekBarが私はそれが起こることを知る)

もちろん、私はほとんどの馬鹿げた解決策を実行し、リストビューのリサイクルを無効にすることができますが、これはユーザーエクスペリエンスが実際に悪くなり、アプリケーションがメモリ不足になる可能性があり、 LargeHeapを使用するのがLargeHeapです。 したがって、以下の方法は問題になりません。

@Override
public int getViewTypeCount() {
    return getCount();
}

@Override
public int getItemViewType(int position) {
    return position;
}

私の質問:これには明らかな解決策がありますか? 1つの列だけをリサイクルしないようにするにはどうすればよいですか? 私はそれが本当に必要になるまでコードを投稿しません、コードが大きすぎます。 代わりに、問題に関連する重要な部分を投稿します。

@Override
public View getView(final int position, View convertView, ViewGroup parent) {
    View row = convertView;
    holder = null;
    if (row == null) {
        LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        row = inflater.inflate(R.layout.item, parent, false);
        holder = new Ids(row);
        row.setTag(holder);
    } else {
        holder = (Ids) row.getTag();
    }

    rowItemClass = (ListViewRow) getItem(position);
    if (Globals.isPlaying && Globals.pos == position) {        
        holder.seekbar.setVisibility(View.VISIBLE);
    } else {
        holder.seekbar.setVisibility(View.GONE);    
    }

    holder.seekbar.setTag(position);
    final Ids finalHolder = holder;

    ...
    OnClickListener{....
    Globals.mp.start();
    finalHolder.seekbar.setProgress(0);
    finalHolder.seekbar.setMax(Globals.mp.getDuration());
    ..

    updateTimeProgressBar = new Runnable() {
        @Override
        public void run() {
            if (Globals.isPlaying) {  
                finalHolder.seekbar.setProgress(Globals.mp.getCurrentPosition());
                int currentPosition = Globals.mp.getCurrentPosition();
                handler.postDelayed(this, 100);
            }
        }
    };

    handler.postDelayed(updateTimeProgressBar, 100);
    finalHolder.seekbar.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
        @Override
        public void onStopTrackingTouch(SeekBar seekBar) {
            handler.removeCallbacks(updateTimeProgressBar);
            Globals.mp.seekTo(finalHolder.seekbar.getProgress());
            int currentPosition = Globals.mp.getCurrentPosition();
            handler.postDelayed(updateTimeProgressBar, 500);
        }

        @Override
        public void onStartTrackingTouch(SeekBar seekBar) {
            handler.removeCallbacks(updateTimeProgressBar);
        }

        @Override
        public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
        // Intentionally left empty
        }
    });
}

以上です。 なぜこうなった? 1つの行のリサイクルを無効にする方法はありますか? 1 mpだけが再生されるので、 ListViewすべてのSeekBarを更新するのは悪い考えですか? パフォーマンスにはどれくらい悪いですか?




Related