beautify slider element.

This commit is contained in:
cyBerta
2019-03-25 13:21:38 +01:00
parent 869fb5c16b
commit d41323e69e
5 changed files with 126 additions and 40 deletions
+1 -2
View File
@@ -60,8 +60,7 @@
<org.thoughtcrime.securesms.components.rangeslider.TimeRangeSlider
android:layout_marginTop="10dp"
android:id="@+id/timeRangeSlider"
android:layout_marginBottom="10dp"
android:paddingStart="32dp"
@@ -17,15 +17,16 @@ import java.util.ArrayList;
public class RangeSliderView extends View {
private static final String TAG = RangeSliderView.class.getName();
private int trackTintColor;
private int trackHighlightTintColor;
private float trackHeight;
private float thumbRadius;
private float thumbOutlineSize;
private float displayTextFontSize;
private float displayTextBasicOffsetY;
private int sliderPaddingLeft;
private int sliderPaddingRight;
protected int trackTintColor;
protected int trackHighlightTintColor;
protected float trackHeight;
protected float thumbRadius;
protected float thumbOutlineSize;
protected float displayTextFontSize;
protected float displayTextBasicOffsetY;
protected int sliderPaddingLeft;
protected int sliderPaddingRight;
private ThumbLayer minValueThumb;
private TextLayer minValueDisplayLabel;
@@ -39,7 +40,7 @@ public class RangeSliderView extends View {
protected int minValue;
protected int maxValue;
protected int steps;
protected float delta;
private float beginTrackOffsetX;
@@ -123,9 +124,10 @@ public class RangeSliderView extends View {
for (int index = 1; index <= 100; index++) {
values.add(index);
}
delta = 0;
}
public void setOnValueChangedListener(OnValueChangedListener onValueChangedListener) {
void setOnValueChangedListener(OnValueChangedListener onValueChangedListener) {
this.onValueChangedListener = onValueChangedListener;
invalidate();
}
@@ -149,39 +151,49 @@ public class RangeSliderView extends View {
float offsetY = getHeight() / 2;
float minValueOffsetX = getPositionFromIndex(minValue);
float maxValueOffsetX = getPositionFromIndex(maxValue);
float displayLabelOffsetY = offsetY - thumbRadius - displayTextBasicOffsetY;
float displayLabelOffsetAbove = offsetY - thumbRadius - displayTextBasicOffsetY;
float displayLabelOffsetBelow = offsetY + thumbRadius + thumbOutlineSize + displayTextFontSize;
Log.d(TAG, "onDraw minValueOffsetX: " + minValueOffsetX + ", maxValueOffsetX: " + maxValueOffsetX);
track.draw(canvas, getWidth(), minValueOffsetX, maxValueOffsetX, offsetY - trackHeight / 2);
track.draw(canvas, getWidth(), minValueOffsetX, maxValueOffsetX, offsetY - trackHeight / 2, getDeltaInPixel());
minValueThumb.draw(canvas, minValueOffsetX, offsetY);
maxValueThumb.draw(canvas, maxValueOffsetX, offsetY);
if (onValueChangedListener != null) {
minValueDisplayLabel.draw(
canvas,
onValueChangedListener.parseMinValueDisplayText(minValue),
minValueOffsetX,
displayLabelOffsetY
displayLabelOffsetBelow
);
} else {
minValueDisplayLabel.draw(canvas, String.valueOf(minValue), minValueOffsetX, displayLabelOffsetY);
}
maxValueThumb.draw(canvas, maxValueOffsetX, offsetY);
if (onValueChangedListener != null) {
maxValueDisplayLabel.draw(
canvas,
onValueChangedListener.parseMaxValueDisplayText(maxValue),
maxValueOffsetX,
displayLabelOffsetY
displayLabelOffsetAbove
);
} else {
maxValueDisplayLabel.draw(canvas, String.valueOf(maxValue), maxValueOffsetX, displayLabelOffsetY);
minValueDisplayLabel.draw(canvas, String.valueOf(minValue), minValueOffsetX, displayLabelOffsetBelow);
maxValueDisplayLabel.draw(canvas, String.valueOf(maxValue), maxValueOffsetX, displayLabelOffsetAbove);
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_CANCEL || event.getAction() == MotionEvent.ACTION_UP) {
if (event.getAction() == MotionEvent.ACTION_CANCEL) {
minValueThumb.isHighlight = false;
maxValueThumb.isHighlight = false;
invalidate();
return true;
}
if (event.getAction() == MotionEvent.ACTION_UP && (minValueThumb.isHighlight || maxValueThumb.isHighlight)) {
if (onValueChangedListener != null) {
onValueChangedListener.onValueChanged(minValue, maxValue);
}
minValueThumb.isHighlight = false;
maxValueThumb.isHighlight = false;
invalidate();
@@ -244,9 +256,6 @@ public class RangeSliderView extends View {
}
if (minValueThumb.isHighlight || maxValueThumb.isHighlight) {
if (onValueChangedListener != null) {
onValueChangedListener.onValueChanged(minValue, maxValue);
}
invalidate();
}
break;
@@ -256,13 +265,24 @@ public class RangeSliderView extends View {
}
protected int getIndexFromPosition(int offsetX) {
int count = values.size();
return ((offsetX - sliderPaddingLeft) * count / getSliderWidth());
return ((offsetX - sliderPaddingLeft) * getCount() / getSliderWidth());
}
protected float getPositionFromIndex(int value) {
int count = values.size();
Log.d(TAG, "value: " + value +", position: " + (getSliderWidth() / count) * value + sliderPaddingLeft);
return (getSliderWidth() / count) * value + sliderPaddingLeft;
Log.d(TAG, "value: " + value +", position: " + (getSliderWidth() / getCount()) * value + sliderPaddingLeft);
return (getSliderWidth() / getCount()) * value + sliderPaddingLeft;
}
public float getDeltaInPixel() {
// '* 2' is just an offset factor to increase the visibility
return (getSliderWidth() / getCount()) * delta + (2 * thumbRadius + thumbOutlineSize);
}
public float getDeltaInValues() {
return delta;
}
public int getCount() {
return values.size();
}
public int getSliderWidth() {
@@ -2,6 +2,7 @@ package org.thoughtcrime.securesms.components.rangeslider;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.util.AttributeSet;
import org.thoughtcrime.securesms.R;
@@ -15,12 +16,14 @@ import java.util.Locale;
*/
public class TimeRangeSlider extends RangeSliderView implements RangeSliderView.OnValueChangedListener {
// timeframe in seconds
private static final int DEFAULT_TIMEFRAME_2D = 60 * 60 * 24 * 2;
private static final int DEFAULT_STEPS = 60 * 10;
int timeFrame;
private static final int DEFAULT_TIMEFRAME_2D = 60 * 60 * 24 * 2; // 2d
private static final float DEFAULT_DELTA = 1000*60*30; // 30 min
int timeFrame; // timeframe in seconds
Locale locale;
OnTimestampChangedListener listener;
private TextLayer minRangeDisplayLabel;
private TextLayer maxRangeDisplayLabel;
public TimeRangeSlider(Context context) {
@@ -42,6 +45,41 @@ public class TimeRangeSlider extends RangeSliderView implements RangeSliderView.
locale = DynamicLanguage.getSelectedLocale(context);
super.setOnValueChangedListener(this);
minRangeDisplayLabel = new TextLayer(displayTextFontSize, trackHighlightTintColor);
maxRangeDisplayLabel = new TextLayer(displayTextFontSize, trackHighlightTintColor);
delta = DEFAULT_DELTA / (timeFrame * 1000) * getCount();
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
float offsetY = getHeight() / 2;
float minValueOffsetX = getPositionFromIndex(minValue);
float maxValueOffsetX = getPositionFromIndex(maxValue);
float displayLabelOffsetBelow = offsetY + thumbRadius + thumbOutlineSize + displayTextFontSize;
if (minValue == maxValue) {
if (minValueOffsetX - getDeltaInPixel() >= sliderPaddingLeft
) {
minRangeDisplayLabel.draw(
canvas,
getDeltaInTime(getContext()),
minValueOffsetX - getDeltaInPixel(),
displayLabelOffsetBelow
);
}
if (maxValueOffsetX + getDeltaInPixel() <= (getWidth() - sliderPaddingRight)) {
maxRangeDisplayLabel.draw(
canvas,
getDeltaInTime(getContext()),
maxValueOffsetX + getDeltaInPixel(),
displayLabelOffsetBelow
);
}
}
}
public interface OnTimestampChangedListener {
@@ -62,6 +100,9 @@ public class TimeRangeSlider extends RangeSliderView implements RangeSliderView.
@Override
public String parseMinValueDisplayText(int minValue) {
if (minValue == maxValue) {
return "";
}
return getStringForValue(minValue);
}
@@ -76,7 +117,11 @@ public class TimeRangeSlider extends RangeSliderView implements RangeSliderView.
}
private long getTimestampForValue(int value) {
return System.currentTimeMillis() - ((timeFrame / 100) * (100 - value) * 1000);
return System.currentTimeMillis() - ((timeFrame / getCount()) * (getCount() - value) * 1000);
}
public String getDeltaInTime(Context context) {
return DateUtils.getFormattedTimespan(context, (int) (timeFrame * 1000 / getCount() * getDeltaInValues()));
}
@@ -32,9 +32,26 @@ class TrackLayer {
this.paddingRight = paddingRight;
}
void draw(Canvas canvas, int width, float offsetLeft, float offsetRight, float offsetY) {
void draw(Canvas canvas, int width, float offsetLeft, float offsetRight, float offsetY, float delta) {
draw(canvas, backgoundPaint, paddingLeft, width - paddingRight, offsetY);
draw(canvas, centerPaint, offsetLeft, offsetRight, offsetY);
if (offsetLeft == offsetRight) {
float maxEndX = width - paddingRight;
float minStartX = paddingLeft;
float offsetDeltaLeft = offsetLeft - delta;
float offsetDeltaRight = offsetRight + delta;
if (offsetLeft - delta < minStartX) {
offsetDeltaLeft = minStartX;
} else if (offsetRight + delta > maxEndX) {
offsetDeltaRight = maxEndX;
}
draw(canvas, centerPaint, offsetDeltaLeft, offsetDeltaRight, offsetY);
}
else {
draw(canvas, centerPaint, offsetLeft, offsetRight, offsetY);
}
}
void draw(Canvas canvas, Paint paint, float startX, float endX, float offsetY) {
@@ -175,4 +175,9 @@ public class DateUtils extends android.text.format.DateUtils {
TimeUnit.MILLISECONDS.toMinutes(millis),
TimeUnit.MILLISECONDS.toSeconds(millis-(TimeUnit.MILLISECONDS.toMinutes(millis)*60000)));
}
public static String getFormattedTimespan(Context c, int timestamp) {
int mins = timestamp / (1000 * 60);
return c.getResources().getQuantityString(R.plurals.n_minutes, mins, mins);
}
}