问题
I have a listview
with seekbar
, each seekbar
represents 100% of a value of product. By moving the seekbar
the % value can be changed, I want to show the change in value along the seekbar while the user is dragging the seekbar
. I do not wish to add another text box where the value is updated.
I am more looking at options to show a small view on top of the seekbar pointer, which appears onStartTracking
and disappears onStopTracking
event.
Is there a way to achieve this?
回答1:
Here is a one simple way,
- Add a
textView
in your XML - Change it's position with the movement of the
seekBar
- That will position it using
setX()
- If you want you can give
setY()
for its Y position as well - If you want to hide write some logic and make
textView
Visibility GONE when you need.
example:
seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
@Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
int val = (progress * (seekBar.getWidth() - 2 * seekBar.getThumbOffset())) / seekBar.getMax();
textView.setText("" + progress);
textView.setX(seekBar.getX() + val + seekBar.getThumbOffset() / 2);
//textView.setY(100); just added a value set this properly using screen with height aspect ratio , if you do not set it by default it will be there below seek bar
}
or you can use Paint with your custom SeekBar
class without any TextView
Create a class
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.widget.SeekBar;
public class MySeekBar extends SeekBar {
public MySeekBar (Context context) {
super(context);
}
public MySeekBar (Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public MySeekBar (Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
protected void onDraw(Canvas c) {
super.onDraw(c);
int thumb_x = (int) (( (double)this.getProgress()/this.getMax() ) * (double)this.getWidth());
float middle = (float) (this.getHeight());
Paint paint = new Paint();
paint.setColor(Color.BLACK);
paint.setTextSize(20);
c.drawText(""+this.getProgress(), thumb_x, middle, paint);
}
}
Set/create your SeekBar
in your XML
<yourPackageName.MySeekBar
android:id="@+id/my_seek_bar"
android:layout_width="300dp"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:layout_marginTop="26dp"
android:max="10"/>
Now from your Activity
seekBar = (MySeekBar) findViewById(R.id.my_seek_bar);
seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
@Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {
}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
}
});
回答2:
add a text view in your xml file, you can use a linrarlayout like this:
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<SeekBar
android:id="@+id/seekBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:max="1000" />
<TextView
android:id="@+id/textView4"
android:layout_width="80dp"
android:layout_height="wrap_content"
android:layout_weight="1" />
</LinearLayout>
and in java file, change text view text in onProgressChanged method of seekbar:
SeekBar sk = (SeekBar) findViewById(R.id.seekBar);
sk.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
@Override
public void onProgressChanged(SeekBar seekBar, int i, boolean b) {
TextView t=(TextView)findViewById(R.id.textView4);
t.setText(String.valueOf(i));
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {
}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
}
});
回答3:
Check this library out. You can use the 'range seekbar with single thumb to true'.
回答4:
The accepted answer is probably good enough for most situations. However, if you want precision so that the text is exactly in the middle of your seek bar thumb, you have to a little more calculations. This is because the width of the text is different. Say, you want to show numbers from 0 to 150. Width of 188 will be different from 111. Because of this, the text you are showing will always tilt to some side.
The way to solve it is to measure the width of the text, remove that from the width of the seekbar thumb, divide it by 2, and add that to the result that was given in the accepted answer. Now you would not care about how large the number range. Here is the code:
override fun onProgressChanged(seekBar: SeekBar, progress: Int, fromUser: Boolean) {
val value = progress * (seekBar.width - 2 * seekBar.thumbOffset) / seekBar.max
label.text = progress.toString()
label.measure(0, 0)
val textWidth = label.measuredWidth
val firstRemainder = seekThumbWidth - textWidth
val result = firstRemainder / 2
label.x = (seekBar.x + value + result)
}
来源:https://stackoverflow.com/questions/41774963/android-seekbar-show-progress-value-along-the-seekbar