我使用MPAndroidChart我想說明這裏面CombinedChart
自定義繪製像下圖:MPAndroidChart:裏面的酒吧,並添加自定義圖像
如果欄值> =目標價值,說,50,然後我想在欄內添加一個星形圖像。
任何人都可以幫我定製BarChart嗎?
我使用MPAndroidChart我想說明這裏面CombinedChart
自定義繪製像下圖:MPAndroidChart:裏面的酒吧,並添加自定義圖像
如果欄值> =目標價值,說,50,然後我想在欄內添加一個星形圖像。
任何人都可以幫我定製BarChart嗎?
要獲得我們酒吧內的星形圖像,我們需要創建一個自定義渲染器。因爲我們的條形圖使用BarChartRenderer
我們將繼承這個第一和添加參數爲我們的形象:
public class ImageBarChartRenderer extends BarChartRenderer {
private final Bitmap barImage;
public ImageBarChartRenderer(BarDataProvider chart, ChartAnimator animator, ViewPortHandler viewPortHandler, Bitmap barImage) {
super(chart, animator, viewPortHandler);
this.barImage = barImage;
}
如果我們檢查源BarChartRenderer
我們可以看到,它調用調用的方法drawData
,然後遍歷每個數據集和請致電drawDataSet
。 drawDataSet
是動作發生的地方:它正在繪製陰影和酒吧。這是一個合適的地方加入邏輯繪製圖像等額外的,所以讓我們添加一個調用一個方法有引起我們的圖片:
@Override
protected void drawDataSet(Canvas c, IBarDataSet dataSet, int index) {
super.drawDataSet(c, dataSet, index);
drawBarImages(c, dataSet, index);
}
我們現在需要的是將通過DataSet迭代並繪製星的方法圖片。一個適當的方法將作爲模板drawValues
所以讓我們複製並更改它,以便繪製圖像而不是文本。理解這一點的關鍵是看BarBuffer是如何工作的。 BarBuffer保存給定條目的條形屏幕(像素)座標,格式爲j
,j + 1
,j + 2
,j + 3
。
爲了澄清,j
是左x座標,j + 1
是最高y座標等等,通過右邊x座標j + 3
。我們將提取這些變量,使其更易於理解:
protected void drawBarImages(Canvas c, IBarDataSet dataSet, int index) {
BarBuffer buffer = mBarBuffers[index];
float left; //avoid allocation inside loop
float right;
float top;
float bottom;
for (int j = 0; j < buffer.buffer.length * mAnimator.getPhaseX(); j += 4) {
left = buffer.buffer[j];
right = buffer.buffer[j + 2];
top = buffer.buffer[j + 1];
bottom = buffer.buffer[j + 3];
float x = (left + right)/2f;
if (!mViewPortHandler.isInBoundsRight(x))
break;
if (!mViewPortHandler.isInBoundsY(top)
|| !mViewPortHandler.isInBoundsLeft(x))
continue;
BarEntry entry = dataSet.getEntryForIndex(j/4);
float val = entry.getY();
if (val > 50) {
drawStar(c, barImage, x, top);
}
}
}
下面是如何消費的渲染:
Bitmap starBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.star);
mChart.setRenderer(new ImageBarChartRenderer(mChart, mChart.getAnimator(), mChart.getViewPortHandler(), starBitmap));
渲染器的最後一步是添加邏輯來縮放位圖和正確定位。下面是自定義渲染的最終證明的概念:
package com.xxmassdeveloper.mpchartexample;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import com.github.mikephil.charting.animation.ChartAnimator;
import com.github.mikephil.charting.buffer.BarBuffer;
import com.github.mikephil.charting.data.BarEntry;
import com.github.mikephil.charting.interfaces.dataprovider.BarDataProvider;
import com.github.mikephil.charting.interfaces.datasets.IBarDataSet;
import com.github.mikephil.charting.renderer.BarChartRenderer;
import com.github.mikephil.charting.utils.ViewPortHandler;
/**
* Created by David on 29/12/2016.
*/
public class ImageBarChartRenderer extends BarChartRenderer {
private final Bitmap barImage;
public ImageBarChartRenderer(BarDataProvider chart, ChartAnimator animator, ViewPortHandler viewPortHandler, Bitmap barImage) {
super(chart, animator, viewPortHandler);
this.barImage = barImage;
}
@Override
public void drawData(Canvas c) {
super.drawData(c);
}
@Override
protected void drawDataSet(Canvas c, IBarDataSet dataSet, int index) {
super.drawDataSet(c, dataSet, index);
drawBarImages(c, dataSet, index);
}
protected void drawBarImages(Canvas c, IBarDataSet dataSet, int index) {
BarBuffer buffer = mBarBuffers[index];
float left; //avoid allocation inside loop
float right;
float top;
float bottom;
final Bitmap scaledBarImage = scaleBarImage(buffer);
int starWidth = scaledBarImage.getWidth();
int starOffset = starWidth/2;
for (int j = 0; j < buffer.buffer.length * mAnimator.getPhaseX(); j += 4) {
left = buffer.buffer[j];
right = buffer.buffer[j + 2];
top = buffer.buffer[j + 1];
bottom = buffer.buffer[j + 3];
float x = (left + right)/2f;
if (!mViewPortHandler.isInBoundsRight(x))
break;
if (!mViewPortHandler.isInBoundsY(top)
|| !mViewPortHandler.isInBoundsLeft(x))
continue;
BarEntry entry = dataSet.getEntryForIndex(j/4);
float val = entry.getY();
if (val > 50) {
drawImage(c, scaledBarImage, x - starOffset, top);
}
}
}
private Bitmap scaleBarImage(BarBuffer buffer) {
float firstLeft = buffer.buffer[0];
float firstRight = buffer.buffer[2];
int firstWidth = (int) Math.ceil(firstRight - firstLeft);
return Bitmap.createScaledBitmap(barImage, firstWidth, firstWidth, false);
}
protected void drawImage(Canvas c, Bitmap image, float x, float y) {
if (image != null) {
c.drawBitmap(image, x, y, null);
}
}
}
這裏有一個屏幕截圖 - 你可以看到,超過50值有星:
感謝答案。 –
不客氣。 –
你在這裏使用什麼版本的mpandroid圖表? – Amalo