【问题标题】:Android seekbar with custom thumb having dynamic text inside it带有自定义拇指的 Android 搜索栏,其中包含动态文本
【发布时间】:2016-10-02 14:21:32
【问题描述】:

我想创建 android 自定义 SeekBar,其中包含 thumb 和文本 以显示当前的搜索位置。

这是我的代码:

SeekBar sb;

@Override
public void onCreate(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);
    setContentView(R.layout.custom_seek_bar_activity);

    sb = (SeekBar)findViewById(R.id.slider);
    sb.setMax(100);
    sb.setProgress(10);
    BitmapDrawable bd = writeOnDrawable(R.drawable.star2, Double.toString(50));

    sb.setThumb(bd);

    sb.setOnSeekBarChangeListener(new OnSeekBarChangeListener(){
        @Override
        public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser)
        {
            int pos = sb.getProgress();
            double star = pos/(20.0);
            TextView tv = (TextView)findViewById(R.id.percent);
            tv.setText(Double.toString(star)+"%");
            BitmapDrawable bd = writeOnDrawable(R.drawable.star2, Double.toString(star));
            bd.setBounds(new Rect(0,0, 
                bd.getIntrinsicWidth(), 
                bd.getIntrinsicHeight()
            ));
            seekBar.setThumb(bd);
        }

        @Override
        public void onStartTrackingTouch(SeekBar arg0) {
            // TODO Auto-generated method stub

        }

        @Override
        public void onStopTrackingTouch(SeekBar arg0) {
            // TODO Auto-generated method stub

        }
    });

}   

public BitmapDrawable writeOnDrawable(int drawableId, String text){

    Bitmap bm = BitmapFactory.decodeResource(getResources(), drawableId).copy(Bitmap.Config.ARGB_8888, true);

    Paint paint = new Paint(); 
    paint.setStyle(Style.FILL);  
    paint.setColor(Color.BLACK); 
    paint.setTextSize(10); 

    Canvas canvas = new Canvas(bm);
    canvas.drawText(text, 0, bm.getHeight()/2, paint);

    return new BitmapDrawable(bm);
}

但是当我移动拇指时,它会转到搜索栏的开头。 有没有人有解决方案来移动带有搜索栏位置的自定义拇指?

【问题讨论】:

    标签: android seekbar


    【解决方案1】:

    我使用 SeekBar 在我的应用程序中显示计时器倒计时。在计时器拇指内,我使用以下代码显示当前的 SeekBar 进度号:

        SeekBar timerBar = (SeekBar) findViewById(R.id.seekBarTimer);
        if (timerBar != null) {
            timerBar.setMax((int) (Settings.countdownSeconds + 1));
            timerBar.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
    
                @Override
                public void onStopTrackingTouch(SeekBar arg0) {
                }
    
                @Override
                public void onStartTrackingTouch(SeekBar arg0) {
                }
    
                @Override
                public void onProgressChanged(SeekBar timerBar, int arg1, boolean arg2) {
                    Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.seek_thumb);
                    Bitmap bmp = bitmap.copy(Bitmap.Config.ARGB_8888, true);
                    Canvas c = new Canvas(bmp);
                    String text = Integer.toString(timerBar.getProgress());
                    Paint p = new Paint();
                    p.setTypeface(Typeface.DEFAULT_BOLD);
                    p.setTextSize(14);
                    p.setColor(0xFFFFFFFF);
                    int width = (int) p.measureText(text);
                    int yPos = (int) ((c.getHeight() / 2) - ((p.descent() + p.ascent()) / 2));
                    c.drawText(text, (bmp.getWidth()-width)/2, yPos, p);
                    timerBar.setThumb(new BitmapDrawable(getResources(), bmp));
                }
            });
            timerBar.setProgress(0);
        }
    

    R.drawable.seek_thumb drawable 是我的拇指可绘制对象。

    【讨论】:

      【解决方案2】:

      我现在得到了解决方案,在setBound() 方法中,我将左上角传递为0,这就是它在开始时显示搜索栏的原因。进行以下更改后,我得到了它的工作原理。

      onProgressChanged()事件中调用setThumbPos()方法

      public void setThumbPosition(SeekBar seekBar){
          int max = seekBar.getMax();
      
          int available = seekBar.getWidth() - seekBar.getPaddingLeft() - seekBar.getPaddingRight();
          float scale = max > 0 ? (float) seekBar.getProgress() / (float) max : 0;
      
          //scale = 1;
          int pos = sb.getProgress();
          double star = pos/(20.0);
      
          BitmapDrawable bd = writeOnDrawable(R.drawable.star2, Double.toString(star));
      
          int thumbWidth = bd.getIntrinsicWidth();
          int thumbHeight = bd.getIntrinsicHeight();
          //available -= thumbWidth;
      
          int thumbPos = (int) (scale * available);
          if(thumbPos <= 0+thumbWidth){
              thumbPos += (thumbWidth/2);
          }else if(thumbPos >= seekBar.getWidth()-thumbWidth){
              thumbPos -= (thumbWidth/2);
          }
      
          bd.setBounds(new Rect(thumbPos,0, 
                  thumbPos+bd.getIntrinsicWidth(), 
              bd.getIntrinsicHeight()
          ));
      
          seekBar.setThumb(bd);
      
          TextView tv = (TextView)findViewById(R.id.percent);
          tv.setText(Double.toString(star)+"%");
      }
      

      【讨论】:

        【解决方案3】:

        我最终使用了这个简单的解决方案。它可能没有 像适当的自定义 SeekBar 那样具有高性能,但它确实很容易插入现有布局,并在 SeekBar 拇指顶部使用任何标签或其他视图。

        protected void positionThumbLabel(SeekBar seekBar, TextView label)
        {
          Rect tr = seekBar.getThumb().getBounds();
          label.setWidth(tr.width());
          label.setX(tr.left + seekBar.getPaddingLeft());
        }
        

        通过一些小改动,您可以相对于拇指中心定位叠加层:

        protected void positionThumbOverlayCenter(SeekBar seekBar, View overlay)
        {
          Rect tr = seekBar.getThumb().getBounds();
          overlay.setX(tr.centerX() - (overlay.getWidth() * 0.5f) + seekBar.getPaddingLeft());
        }
        

        【讨论】:

          【解决方案4】:

          【讨论】:

          • 链接已失效。你能提供一个替代方案吗?
          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2015-09-12
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多