|
@@ -0,0 +1,483 @@
|
|
|
|
|
+package hr.tacitus.graphs;
|
|
|
|
|
+
|
|
|
|
|
+import android.content.Context;
|
|
|
|
|
+import android.content.res.TypedArray;
|
|
|
|
|
+import android.graphics.Canvas;
|
|
|
|
|
+import android.graphics.Color;
|
|
|
|
|
+import android.graphics.Paint;
|
|
|
|
|
+import android.graphics.RectF;
|
|
|
|
|
+import android.support.annotation.Nullable;
|
|
|
|
|
+import android.text.Layout;
|
|
|
|
|
+import android.text.StaticLayout;
|
|
|
|
|
+import android.text.TextPaint;
|
|
|
|
|
+import android.text.TextUtils;
|
|
|
|
|
+import android.util.AttributeSet;
|
|
|
|
|
+import android.util.Log;
|
|
|
|
|
+import android.view.View;
|
|
|
|
|
+
|
|
|
|
|
+import java.util.ArrayList;
|
|
|
|
|
+import java.util.List;
|
|
|
|
|
+
|
|
|
|
|
+import static android.R.attr.ellipsize;
|
|
|
|
|
+import static android.R.attr.value;
|
|
|
|
|
+
|
|
|
|
|
+/**
|
|
|
|
|
+ * Created by Bero on 7.7.2017..
|
|
|
|
|
+ */
|
|
|
|
|
+
|
|
|
|
|
+public class PieChartView extends View {
|
|
|
|
|
+
|
|
|
|
|
+ class PieChartItem {
|
|
|
|
|
+ float value;
|
|
|
|
|
+ // color for this pie chart item
|
|
|
|
|
+ Paint paint;
|
|
|
|
|
+ // text
|
|
|
|
|
+ String description;
|
|
|
|
|
+
|
|
|
|
|
+ // cached value
|
|
|
|
|
+ int descriptionWidth;
|
|
|
|
|
+ StaticLayout descriptionLayout;
|
|
|
|
|
+
|
|
|
|
|
+ String valueDescription;
|
|
|
|
|
+ int valueDescriptionWidth;
|
|
|
|
|
+ int valueDescriptionHeight;
|
|
|
|
|
+
|
|
|
|
|
+ float getAngle() {
|
|
|
|
|
+ return value * 3.6f;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private static float MAX_LEGEND_WIDTH_PERCENTAGE = 35f;
|
|
|
|
|
+ private static float MAX_LEGEND_WIDTH_PX = 300;
|
|
|
|
|
+ private static float LEGEND_PADDING_HORIZONTAL = 20f;
|
|
|
|
|
+ private static float LEGEND_PADDING_TOP = 20f;
|
|
|
|
|
+
|
|
|
|
|
+ private float titleTextSizeSp = 16.f;
|
|
|
|
|
+
|
|
|
|
|
+ private boolean showLegend = true;
|
|
|
|
|
+ private float legendTextSizeSp = 10.f;
|
|
|
|
|
+ private float legendSquareSize = 20f;
|
|
|
|
|
+ private float legendWidth;
|
|
|
|
|
+ private float legendMaxTextWidth;
|
|
|
|
|
+
|
|
|
|
|
+ private float CHART_PADDING_DP = 24.f;
|
|
|
|
|
+ private float chartTextSizeSp = 10.f;
|
|
|
|
|
+ private float chartPaddingPx;
|
|
|
|
|
+
|
|
|
|
|
+ private PieChartAdapter adapter;
|
|
|
|
|
+ private PieChartColorProvider colorProvider;
|
|
|
|
|
+
|
|
|
|
|
+ private String title;
|
|
|
|
|
+
|
|
|
|
|
+ private List<Integer> colors;
|
|
|
|
|
+
|
|
|
|
|
+ private int textColor;
|
|
|
|
|
+
|
|
|
|
|
+ private TextPaint titlePaint;
|
|
|
|
|
+ private TextPaint valuePaint;
|
|
|
|
|
+ private TextPaint legendDescriptionPaint;
|
|
|
|
|
+ private StaticLayout titleTextLayout;
|
|
|
|
|
+
|
|
|
|
|
+ private RectF titleRect;
|
|
|
|
|
+ private RectF legendRect;
|
|
|
|
|
+ private RectF pieChartRect;
|
|
|
|
|
+
|
|
|
|
|
+ private List<PieChartItem> items = new ArrayList<>();
|
|
|
|
|
+
|
|
|
|
|
+ private boolean readyToDraw = false;
|
|
|
|
|
+
|
|
|
|
|
+ public PieChartView(Context context) {
|
|
|
|
|
+ super(context);
|
|
|
|
|
+ init(null);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public PieChartView(Context context, AttributeSet attrs) {
|
|
|
|
|
+ super(context, attrs);
|
|
|
|
|
+ init(attrs);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public PieChartView(Context context, AttributeSet attrs, int defStyle) {
|
|
|
|
|
+ super(context, attrs, defStyle);
|
|
|
|
|
+ init(attrs);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void readAttributes(AttributeSet attributeSet) {
|
|
|
|
|
+ TypedArray a = getContext().obtainStyledAttributes(attributeSet, R.styleable.PieChartView);
|
|
|
|
|
+ if (a != null) {
|
|
|
|
|
+ try {
|
|
|
|
|
+ title = a.getString(R.styleable.PieChartView_title);
|
|
|
|
|
+ showLegend = a.getBoolean(R.styleable.PieChartView_showLegend, true);
|
|
|
|
|
+ textColor = a.getColor(R.styleable.PieChartView_textColor, Color.BLACK);
|
|
|
|
|
+ } finally {
|
|
|
|
|
+ a.recycle();
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private float getLegendHeight() {
|
|
|
|
|
+ if (!showLegend) {
|
|
|
|
|
+ return 0;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ float height = 0;
|
|
|
|
|
+ for (PieChartItem item : items) {
|
|
|
|
|
+ height += item.descriptionLayout.getHeight();
|
|
|
|
|
+ Log.d("SL-HEIGHT-2", String.format("%d", item.descriptionLayout.getHeight()));
|
|
|
|
|
+ }
|
|
|
|
|
+ return height;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Nullable
|
|
|
|
|
+ private RectF getLegendRect() {
|
|
|
|
|
+ if (showLegend) {
|
|
|
|
|
+ float legendHeight = getLegendHeight() + 2 * LEGEND_PADDING_TOP;
|
|
|
|
|
+
|
|
|
|
|
+ float left = getRight() - legendWidth;
|
|
|
|
|
+ float right = getRight(); // titleRect.right;
|
|
|
|
|
+ float top = titleRect != null ? titleRect.bottom : 0;
|
|
|
|
|
+ float bottom = getHeight() - top;
|
|
|
|
|
+
|
|
|
|
|
+ RectF rect = new RectF(left, top, right, bottom);
|
|
|
|
|
+ float centerY = rect.centerY();
|
|
|
|
|
+
|
|
|
|
|
+ rect.top = centerY - legendHeight / 2;
|
|
|
|
|
+ if (rect.top <= LEGEND_PADDING_TOP) {
|
|
|
|
|
+ rect.top = LEGEND_PADDING_TOP;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ rect.bottom = centerY + legendHeight / 2;
|
|
|
|
|
+ if (rect.bottom >= getHeight() - top - LEGEND_PADDING_TOP) {
|
|
|
|
|
+ rect.bottom = getHeight() - top - LEGEND_PADDING_TOP;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return rect;
|
|
|
|
|
+ }
|
|
|
|
|
+ return null;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private RectF getPieChartRect() {
|
|
|
|
|
+ // Pie chart max rectangle
|
|
|
|
|
+ float left = getPaddingLeft() + chartPaddingPx;
|
|
|
|
|
+ float top = (titleRect != null ? titleRect.bottom : 0) + chartPaddingPx;
|
|
|
|
|
+ float right = getWidth() - getPaddingRight() - chartPaddingPx;
|
|
|
|
|
+ if (showLegend)
|
|
|
|
|
+ right -= legendRect.width();
|
|
|
|
|
+ float bottom = getHeight() - getPaddingBottom() - chartPaddingPx;
|
|
|
|
|
+ RectF rectF = new RectF(left, top, right, bottom);
|
|
|
|
|
+ // width must be equal to height
|
|
|
|
|
+ if (rectF.width() != rectF.height()) {
|
|
|
|
|
+ float width = Math.min(rectF.width(), rectF.height());
|
|
|
|
|
+ left = rectF.centerX() - width / 2;
|
|
|
|
|
+ right = left + width;
|
|
|
|
|
+ top = rectF.centerY() - width / 2;
|
|
|
|
|
+ bottom = top + width;
|
|
|
|
|
+
|
|
|
|
|
+ rectF = new RectF(left, top, right, bottom);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return rectF;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private RectF getTitleRect() {
|
|
|
|
|
+ if (title != null)
|
|
|
|
|
+ return new RectF(getPaddingLeft(), getPaddingTop(),
|
|
|
|
|
+ getWidth() - getPaddingRight(), 32.f);
|
|
|
|
|
+ return null;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void initTitleText() {
|
|
|
|
|
+ // int width = (int) titlePaint.measureText(title);
|
|
|
|
|
+ if (titleRect != null) {
|
|
|
|
|
+ titleTextLayout = new StaticLayout(title, titlePaint, (int) titleRect.width(),
|
|
|
|
|
+ Layout.Alignment.ALIGN_CENTER, 1.0f, 0, false);
|
|
|
|
|
+ }
|
|
|
|
|
+ else {
|
|
|
|
|
+ titleTextLayout = null;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void init(AttributeSet attributeSet) {
|
|
|
|
|
+ chartPaddingPx = Utils.dipsToPixels(CHART_PADDING_DP, getResources());
|
|
|
|
|
+
|
|
|
|
|
+ if (attributeSet != null)
|
|
|
|
|
+ readAttributes(attributeSet);
|
|
|
|
|
+
|
|
|
|
|
+ titlePaint = new TextPaint();
|
|
|
|
|
+ titlePaint.setAntiAlias(true);
|
|
|
|
|
+ titlePaint.setTextSize(Utils.spsToPixels(titleTextSizeSp, getResources()));
|
|
|
|
|
+ titlePaint.setColor(textColor);
|
|
|
|
|
+
|
|
|
|
|
+ valuePaint = new TextPaint();
|
|
|
|
|
+ valuePaint.setAntiAlias(true);
|
|
|
|
|
+ valuePaint.setTextSize(Utils.spsToPixels(chartTextSizeSp, getResources()));
|
|
|
|
|
+ valuePaint.setColor(textColor);
|
|
|
|
|
+
|
|
|
|
|
+ legendDescriptionPaint = new TextPaint();
|
|
|
|
|
+ legendDescriptionPaint.setAntiAlias(true);
|
|
|
|
|
+ legendDescriptionPaint.setTextSize(Utils.spsToPixels(legendTextSizeSp, getResources()));
|
|
|
|
|
+ legendDescriptionPaint.setColor(textColor);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void initRectangles() {
|
|
|
|
|
+ titleRect = getTitleRect();
|
|
|
|
|
+ if (showLegend) {
|
|
|
|
|
+ updateLegendWidth();
|
|
|
|
|
+ }
|
|
|
|
|
+ legendRect = getLegendRect();
|
|
|
|
|
+ pieChartRect = getPieChartRect();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void drawTitle(Canvas canvas) {
|
|
|
|
|
+ if (titleTextLayout != null)
|
|
|
|
|
+ titleTextLayout.draw(canvas);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void drawChart(Canvas canvas) {
|
|
|
|
|
+// Paint p = new Paint();
|
|
|
|
|
+// p.setColor(Color.CYAN);
|
|
|
|
|
+// canvas.drawRect(pieChartRect, p);
|
|
|
|
|
+
|
|
|
|
|
+ if (items.size() == 0) {
|
|
|
|
|
+ int width = titleRect != null ? (int)titleRect.width() : getWidth();
|
|
|
|
|
+
|
|
|
|
|
+ StaticLayout staticLayout = new StaticLayout("No data available", valuePaint, width, Layout.Alignment.ALIGN_CENTER,
|
|
|
|
|
+ 0, 0, false);
|
|
|
|
|
+
|
|
|
|
|
+ canvas.save();
|
|
|
|
|
+ canvas.translate(0, pieChartRect.top);
|
|
|
|
|
+
|
|
|
|
|
+ staticLayout.draw(canvas);
|
|
|
|
|
+
|
|
|
|
|
+ canvas.restore();
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ float startAngle = -90.f;
|
|
|
|
|
+ for (PieChartItem item : items) {
|
|
|
|
|
+ canvas.drawArc(pieChartRect, startAngle, item.getAngle(), true, item.paint);
|
|
|
|
|
+ startAngle += item.getAngle();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ startAngle = 90.f;
|
|
|
|
|
+ for (PieChartItem item : items) {
|
|
|
|
|
+ if (item.valueDescription == null)
|
|
|
|
|
+ continue;
|
|
|
|
|
+
|
|
|
|
|
+ float angleMiddle = startAngle - item.getAngle() / 2;
|
|
|
|
|
+ float r = pieChartRect.width() / 2;
|
|
|
|
|
+ float x = (float) Math.cos(Math.toRadians(angleMiddle)) * r;
|
|
|
|
|
+ float y = (float) Math.sin(Math.toRadians(angleMiddle)) * r;
|
|
|
|
|
+
|
|
|
|
|
+ float left = x + pieChartRect.centerX();
|
|
|
|
|
+ float top = pieChartRect.centerY() - y;
|
|
|
|
|
+
|
|
|
|
|
+ // Adjust text position based on quadrant.
|
|
|
|
|
+ // negative x have left shift by valueDescriptionWidth
|
|
|
|
|
+ float modAngle = (angleMiddle + 360) % 360;
|
|
|
|
|
+ if (modAngle > 90 && modAngle < 270) {
|
|
|
|
|
+ left -= item.valueDescriptionWidth;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // TODO: left padding?
|
|
|
|
|
+ if (left < 0)
|
|
|
|
|
+ left = 0;
|
|
|
|
|
+
|
|
|
|
|
+ // negative y have top shift by text height
|
|
|
|
|
+ if ((angleMiddle + 360) % 360 > 180) {
|
|
|
|
|
+ top += item.valueDescriptionHeight;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ canvas.drawText(item.valueDescription, left, top, valuePaint);
|
|
|
|
|
+
|
|
|
|
|
+ startAngle -= item.getAngle();
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void drawLegend(Canvas canvas) {
|
|
|
|
|
+// Paint p = new Paint();
|
|
|
|
|
+// p.setColor(Color.RED);
|
|
|
|
|
+// canvas.drawRect(legendRect, p);
|
|
|
|
|
+
|
|
|
|
|
+ float left = legendRect.left + LEGEND_PADDING_HORIZONTAL;
|
|
|
|
|
+ float top = legendRect.top + LEGEND_PADDING_TOP;
|
|
|
|
|
+
|
|
|
|
|
+ // Draw color explanations
|
|
|
|
|
+ for (int i = 0; i < items.size(); ++i) {
|
|
|
|
|
+ PieChartItem item = items.get(i);
|
|
|
|
|
+
|
|
|
|
|
+ canvas.drawRect(new RectF(left, top, left + legendSquareSize, top + legendSquareSize), item.paint);
|
|
|
|
|
+
|
|
|
|
|
+// StaticLayout staticLayout = new StaticLayout(item.description,
|
|
|
|
|
+// 0, item.description.length(),
|
|
|
|
|
+// legendDescriptionPaint, item.descriptionWidth,
|
|
|
|
|
+// Layout.Alignment.ALIGN_NORMAL, 0, 0, false, TextUtils.TruncateAt.END, (int)legendMaxTextWidth);
|
|
|
|
|
+
|
|
|
|
|
+// StaticLayout staticLayout = new StaticLayout(item.description, legendDescriptionPaint,
|
|
|
|
|
+// (int)legendMaxTextWidth, Layout.Alignment.ALIGN_NORMAL, 1f, 0f, false);
|
|
|
|
|
+//
|
|
|
|
|
+// Log.d("SL-HEIGHT", String.format("%d", staticLayout.getHeight()));
|
|
|
|
|
+
|
|
|
|
|
+ canvas.save();
|
|
|
|
|
+ canvas.translate(left + (legendSquareSize * 1.5f), top);
|
|
|
|
|
+ item.descriptionLayout.draw(canvas);
|
|
|
|
|
+
|
|
|
|
|
+ // staticLayout.draw(canvas);
|
|
|
|
|
+
|
|
|
|
|
+ canvas.restore();
|
|
|
|
|
+
|
|
|
|
|
+ top += item.descriptionLayout.getHeight();
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public void onDraw(Canvas canvas) {
|
|
|
|
|
+ if (!readyToDraw)
|
|
|
|
|
+ return;
|
|
|
|
|
+
|
|
|
|
|
+ drawTitle(canvas);
|
|
|
|
|
+ drawChart(canvas);
|
|
|
|
|
+ if (showLegend)
|
|
|
|
|
+ drawLegend(canvas);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public void onSizeChanged(int xNew, int yNew, int xOld, int yOld) {
|
|
|
|
|
+ super.onSizeChanged(xNew, yNew, xOld, yOld);
|
|
|
|
|
+
|
|
|
|
|
+ adapterChanged();
|
|
|
|
|
+// initRectangles();
|
|
|
|
|
+// initTitleText();
|
|
|
|
|
+
|
|
|
|
|
+ readyToDraw = true;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void initColors() {
|
|
|
|
|
+ colors = new ArrayList<>();
|
|
|
|
|
+ int count = adapter.getCount();
|
|
|
|
|
+ if (colorProvider != null) {
|
|
|
|
|
+ for (int i = 0; i < adapter.getCount(); ++i) {
|
|
|
|
|
+ colors.add(colorProvider.getColor(i));
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ else {
|
|
|
|
|
+ // 3 sets of 2 main colors - rb, rg, bg
|
|
|
|
|
+ int maxValue = 220;
|
|
|
|
|
+ int perSetGain = (int) (maxValue / (Math.ceil(count / 6.) + 1));
|
|
|
|
|
+
|
|
|
|
|
+ float r = maxValue, g = 0, b = 0;
|
|
|
|
|
+ for (int i = 0; i < count; ++i) {
|
|
|
|
|
+ int color = Color.rgb((int) r, (int) g, (int) b);
|
|
|
|
|
+ colors.add(color);
|
|
|
|
|
+
|
|
|
|
|
+ r = Color.green(color);
|
|
|
|
|
+ g = Color.blue(color);
|
|
|
|
|
+ b = Color.red(color);
|
|
|
|
|
+
|
|
|
|
|
+ if (i != 0 && (i + 1) % 3 == 0) {
|
|
|
|
|
+ if (i == 2) {
|
|
|
|
|
+ g = maxValue;
|
|
|
|
|
+ } else {
|
|
|
|
|
+ r -= perSetGain;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void createItems() {
|
|
|
|
|
+ for (int i = 0; i < adapter.getCount(); ++i) {
|
|
|
|
|
+ PieChartItem pieChartItem = new PieChartItem();
|
|
|
|
|
+ pieChartItem.value = adapter.getValue(i);
|
|
|
|
|
+ pieChartItem.paint = new Paint(Paint.ANTI_ALIAS_FLAG);
|
|
|
|
|
+ pieChartItem.paint.setColor(colors.get(i));
|
|
|
|
|
+ pieChartItem.description = adapter.getDescription(i);
|
|
|
|
|
+ pieChartItem.valueDescription = adapter.getValueDescription(i);
|
|
|
|
|
+
|
|
|
|
|
+ if (pieChartItem.description != null) {
|
|
|
|
|
+ pieChartItem.descriptionWidth = Utils.textWidth(pieChartItem.description, legendDescriptionPaint, true);
|
|
|
|
|
+ }
|
|
|
|
|
+ if (pieChartItem.valueDescription != null) {
|
|
|
|
|
+ pieChartItem.valueDescriptionWidth = Utils.textWidth(pieChartItem.valueDescription, valuePaint, true);
|
|
|
|
|
+ pieChartItem.valueDescriptionHeight = Utils.textHeight(pieChartItem.valueDescription, valuePaint);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ items.add(pieChartItem);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private float getMaxLegendWidth() {
|
|
|
|
|
+ float width = getWidth();
|
|
|
|
|
+ float maxPercWidth = width * MAX_LEGEND_WIDTH_PERCENTAGE;
|
|
|
|
|
+ return Math.min(maxPercWidth, MAX_LEGEND_WIDTH_PX);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * Calculates required legend width.
|
|
|
|
|
+ */
|
|
|
|
|
+ private void updateLegendWidth() {
|
|
|
|
|
+ float maxWidth = getMaxLegendWidth();
|
|
|
|
|
+
|
|
|
|
|
+ legendWidth = 0;
|
|
|
|
|
+ for (PieChartItem item : items) {
|
|
|
|
|
+ float width = item.descriptionWidth + 2 * LEGEND_PADDING_HORIZONTAL + legendSquareSize * 1.5f;
|
|
|
|
|
+ if (width > legendWidth)
|
|
|
|
|
+ legendWidth = width;
|
|
|
|
|
+
|
|
|
|
|
+ if (legendWidth >= maxWidth) {
|
|
|
|
|
+ legendWidth = maxWidth;
|
|
|
|
|
+ break;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (legendWidth > 0) {
|
|
|
|
|
+ legendMaxTextWidth = legendWidth - 2 * LEGEND_PADDING_HORIZONTAL - legendSquareSize * 1.5f;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ for (PieChartItem item : items) {
|
|
|
|
|
+ item.descriptionLayout = new StaticLayout(item.description, legendDescriptionPaint,
|
|
|
|
|
+ (int)legendMaxTextWidth, Layout.Alignment.ALIGN_NORMAL, 1f, 0f, false);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public PieChartAdapter getAdapter() {
|
|
|
|
|
+ return adapter;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public void setAdapter(PieChartAdapter adapter) {
|
|
|
|
|
+ this.adapter = adapter;
|
|
|
|
|
+
|
|
|
|
|
+ adapterChanged();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public void setColorProvider(PieChartColorProvider colorProvider) {
|
|
|
|
|
+ this.colorProvider = colorProvider;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private void adapterChanged() {
|
|
|
|
|
+ items.clear();
|
|
|
|
|
+
|
|
|
|
|
+ if (adapter != null) {
|
|
|
|
|
+ initColors();
|
|
|
|
|
+ createItems();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ initRectangles();
|
|
|
|
|
+ initTitleText();
|
|
|
|
|
+
|
|
|
|
|
+ invalidate();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public String getTitle() {
|
|
|
|
|
+ return title;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public void setTitle(String title) {
|
|
|
|
|
+ this.title = title;
|
|
|
|
|
+
|
|
|
|
|
+ adapterChanged();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ public void notifyDatasetChanged() {
|
|
|
|
|
+ adapterChanged();
|
|
|
|
|
+ }
|
|
|
|
|
+}
|