Implemented highlightning / selecting values on touch for line and barchart.

This commit is contained in:
Philipp Jahoda 2014-05-03 01:23:00 +02:00
parent 08c94fc0f9
commit 09bd5e1f7b
9 changed files with 146 additions and 29 deletions

View file

@ -30,7 +30,7 @@
android:layout_marginBottom="35dp"
android:layout_toLeftOf="@+id/tvXMax"
android:layout_marginRight="5dp"
android:max="1000"
android:max="500"
android:paddingBottom="12dp" />
<TextView

View file

@ -30,7 +30,7 @@
android:layout_marginBottom="35dp"
android:layout_toLeftOf="@+id/tvXMax"
android:layout_marginRight="5dp"
android:max="1000"
android:max="500"
android:paddingBottom="12dp" />
<TextView

View file

@ -49,6 +49,8 @@ public class LineChartActivity extends Activity implements OnSeekBarChangeListen
mChart.setTouchEnabled(true);
mChart.setHighlightEnabled(true);
// mChart.highlightValues(new int[] {2, 6});
mChart.setDragEnabled(true);
mChart.setTouchEnabled(true);
mSeekBarX.setProgress(45);
mSeekBarY.setProgress(100);

View file

@ -149,6 +149,9 @@ public class PieChartActivity extends Activity implements OnSeekBarChangeListene
for(int i = 0; i < values.length; i++) a.append("val: " + values[i] + ", ind: " + indices[i] + "\n");
Log.i("PieChart", "Selected: " + a.toString());
// immediately unselect
// mChart.highlightValues(null);
}
@Override

View file

@ -37,6 +37,16 @@ public class BarChart extends BarLineChartBase {
public BarChart(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
@Override
protected void init() {
super.init();
mHighlightPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mHighlightPaint.setStyle(Paint.Style.STROKE);
mHighlightPaint.setStrokeWidth(2f);
mHighlightPaint.setColor(Color.rgb(255, 187, 115));
}
/** array that holds all the colors for the top 3D effect */
private int[] mTopColors;
@ -111,7 +121,20 @@ public class BarChart extends BarLineChartBase {
for(int i = 0; i < mIndicesToHightlight.length; i++) {
int index = mIndicesToHightlight[i];
// check outofbounds
if (index < mYVals.size()) {
float[] pts = new float[] {
index + 0.5f, mYChartMax, index + 0.5f, mYChartMin,
0, mYVals.get(index), mDeltaX, mYVals.get(index)
};
transformPointArray(pts);
// draw the highlight lines
mDrawCanvas.drawLines(pts, mHighlightPaint);
}
}
}
}
@ -329,6 +352,17 @@ public class BarChart extends BarLineChartBase {
public int[] getSideColors() {
return mSideColors;
}
@Override
public void setPaint(Paint p, int which) {
super.setPaint(p, which);
switch(which) {
case PAINT_HIGHLIGHT_BAR:
mHighlightPaint = p;
break;
}
}
@Override
protected void drawAdditional() {

View file

@ -52,6 +52,9 @@ public abstract class BarLineChartBase extends Chart {
/** if true, the grid will be drawn, otherwise not, default true */
protected boolean mDrawGrid = true;
/** if true, dragging / scaling is enabled for the chart */
protected boolean mDragEnabled = true;
/**
* if true, the y-legend values will be rounded - the legend entry count
* will only be approximated
@ -75,6 +78,9 @@ public abstract class BarLineChartBase extends Chart {
/** paint for the y-legend values */
protected Paint mYLegendPaint;
/** paint used for highlighting values */
protected Paint mHighlightPaint;
public BarLineChartBase(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
@ -120,6 +126,11 @@ public abstract class BarLineChartBase extends Chart {
// mGridBackgroundPaint.setColor(Color.WHITE);
mGridBackgroundPaint.setColor(Color.rgb(240, 240, 240)); // light
// grey
mHighlightPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mHighlightPaint.setStyle(Paint.Style.STROKE);
mHighlightPaint.setStrokeWidth(2f);
mHighlightPaint.setColor(Color.rgb(255, 187, 115));
}
@Override
@ -269,6 +280,7 @@ public abstract class BarLineChartBase extends Chart {
// calc delta
mDeltaY = (mYMax + spaceTop) - mYChartMin;
mYChartMax = mYChartMin + mDeltaY;
Log.i(LOG_TAG, "DeltaX: " + mDeltaX + ", DeltaY: " + mDeltaY);
}
@ -358,6 +370,7 @@ public abstract class BarLineChartBase extends Chart {
// set the new delta adequate to the last y-legend value
mDeltaY = val - step - mYChartMin;
mYChartMax = yLegend.get(yLegend.size() - 1);
} else {
@ -684,19 +697,67 @@ public abstract class BarLineChartBase extends Chart {
mGridWidth = width;
}
/**
* set this to true to enable dragging / scaling for the chart
* @param enabled
*/
public void setDragEnabled(boolean enabled) {
this.mDragEnabled = enabled;
}
/**
* returns true if dragging / scaling is enabled for the chart, false if not
* @return
*/
public boolean isDragEnabled() {
return mDragEnabled;
}
/**
* returns the index of the value at the given touch point
*
* @param x
* @param y
* @return
*/
public int getIndexByTouchPoint(float x, float y) {
return -1;
// create an array of the touch-point
float[] pts = new float[2];
pts[0] = x;
pts[1] = y;
Matrix tmp = new Matrix();
// invert all matrixes to convert back to the original value
mMatrixOffset.invert(tmp);
tmp.mapPoints(pts);
mMatrixTouch.invert(tmp);
tmp.mapPoints(pts);
mMatrixValueToPx.invert(tmp);
tmp.mapPoints(pts);
double touchPointIndex = pts[0];
double base = Math.floor(touchPointIndex);
int index = (int) base;
if(this instanceof LineChart) {
// check if we are more than half of a x-value or not
if (touchPointIndex - base > 0.5) {
index = (int) base + 1;
}
}
return index;
}
/**
* returns the value displayed at the touched position of the chart
*
* @param x
* @param y
* @return

View file

@ -32,11 +32,11 @@ public class BarLineChartTouchListener extends SimpleOnGestureListener implement
private int mode = NONE;
private float oldDist = 1f;
private Chart mChart;
private BarLineChartBase mChart;
private GestureDetector mGestureDetector;
public BarLineChartTouchListener(Chart ctx, Matrix start) {
public BarLineChartTouchListener(BarLineChartBase ctx, Matrix start) {
this.mChart = ctx;
this.matrix = start;
@ -49,6 +49,8 @@ public class BarLineChartTouchListener extends SimpleOnGestureListener implement
if(mode == NONE) {
mGestureDetector.onTouchEvent(event);
}
if(!mChart.isDragEnabled()) return true;
// Handle touch events here...
switch (event.getAction() & MotionEvent.ACTION_MASK) {
@ -245,11 +247,15 @@ public class BarLineChartTouchListener extends SimpleOnGestureListener implement
@Override
public boolean onSingleTapConfirmed(MotionEvent e) {
int highlightindex = mChart.getIndexByTouchPoint(e.getX(), e.getY());
mChart.highlightValues(new int[] {1});
mChart.highlightValues(new int[] {highlightindex});
return super.onSingleTapConfirmed(e);
}
@Override
public void onLongPress(MotionEvent arg0) {

View file

@ -226,15 +226,12 @@ public abstract class Chart extends View {
protected void calcMinMax() {
mYMin = mYVals.get(0);
mYMax = mYVals.get(0);
for (int i = 0; i < mYVals.size(); i++) {
if (mYVals.get(i) < mYMin)
mYMin = mYVals.get(i);
}
mYMax = mYVals.get(0);
for (int i = 0; i < mYVals.size(); i++) {
if (mYVals.get(i) > mYMax)
mYMax = mYVals.get(i);
}
@ -931,6 +928,9 @@ public abstract class Chart extends View {
/** paint for highlightning the values of a linechart */
public static final int PAINT_HIGHLIGHT_LINE = 15;
/** paint for highlightning the values of a linechart */
public static final int PAINT_HIGHLIGHT_BAR = 16;
/**
* set a new paint object for the specified parameter in the chart e.g.

View file

@ -17,8 +17,8 @@ public class LineChart extends BarLineChartBase {
/** the width of the drawn data lines */
protected float mLineWidth = 1f;
/** the width of the highlighning rectangle */
protected float mHighlightWidth = 0.6f;
/** the width of the highlighning line */
protected float mHighlightWidth = 3f;
/** if true, the data will also be drawn filled */
protected boolean mDrawFilled = false;
@ -38,9 +38,6 @@ public class LineChart extends BarLineChartBase {
/** paint for the inner circle of the value indicators */
protected Paint mCirclePaintInner;
/** paint used for highlighting values */
protected Paint mHighlightPaint;
public LineChart(Context context) {
super(context);
}
@ -80,7 +77,8 @@ public class LineChart extends BarLineChartBase {
mCirclePaintInner.setColor(Color.WHITE);
mHighlightPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mHighlightPaint.setStyle(Paint.Style.FILL);
mHighlightPaint.setStyle(Paint.Style.STROKE);
mHighlightPaint.setStrokeWidth(2f);
mHighlightPaint.setColor(Color.rgb(255, 187, 115));
}
@ -108,10 +106,25 @@ public class LineChart extends BarLineChartBase {
for (int i = 0; i < mIndicesToHightlight.length; i++) {
RectF highlight = new RectF(mIndicesToHightlight[i] - mHighlightWidth / 2,
mYChartMax, mIndicesToHightlight[i] + mHighlightWidth / 2, mYChartMin);
transformRect(highlight);
mDrawCanvas.drawRect(highlight, mHighlightPaint);
// RectF highlight = new RectF(mIndicesToHightlight[i] - mHighlightWidth / 2,
// mYChartMax, mIndicesToHightlight[i] + mHighlightWidth / 2, mYChartMin);
// transformRect(highlight);
// mDrawCanvas.drawRect(highlight, mHighlightPaint);
int index = mIndicesToHightlight[i];
// check outofbounds
if (index < mYVals.size()) {
float[] pts = new float[] {
index, mYChartMax, index, mYChartMin,
0, mYVals.get(index), mDeltaX, mYVals.get(index)
};
transformPointArray(pts);
// draw the highlight lines
mDrawCanvas.drawLines(pts, mHighlightPaint);
}
}
}
}
@ -291,22 +304,20 @@ public class LineChart extends BarLineChartBase {
}
/**
* set the width of the highlightning rectangle 1.0f == 100% width of the
* cell, 0f = 0%, default 0.6f
* set the width of the highlightning lines, default 3f
*
* @param width
*/
public void setHighlightRectWidth(float width) {
public void setHighlightLineWidth(float width) {
mHighlightWidth = width;
}
/**
* returns the width of the highlightning rectanlge, 1f == 100%, 0f = 0% of
* the highlighted cell
* returns the width of the highlightning line, default 3f
*
* @return
*/
public float getHighlightRectWidth() {
public float getHighlightLineWidth() {
return mHighlightWidth;
}