MarkerView显示位置问题

Home / Android MrLee 2018-3-27 6754

Android图表控件MPAndroidChart库非常强大,支各种图表。虽然已经很强大,但是有些时候还是不能满足我们的需求,类似MarkerView的显示问题,如果不加以修改显示内容会在屏幕之外,达不到预期的效果。如下图:

完成看不到值。

解决方案:判断当前位置和显示控件的宽度超过图表的宽度则重新计算绘制坐标

重新写一个NewMarkerView,源码和官方基本上一致,稍微加上我们自己的判断即可。

import android.content.Context;
import android.graphics.Canvas;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.RelativeLayout;
import com.github.mikephil.charting.charts.Chart;
import com.github.mikephil.charting.components.IMarker;
import com.github.mikephil.charting.data.Entry;
import com.github.mikephil.charting.highlight.Highlight;
import com.github.mikephil.charting.utils.MPPointF;
import java.lang.ref.WeakReference;
public class NewMarkerView extends RelativeLayout implements IMarker {
    private MPPointF mOffset = new MPPointF();
    private MPPointF mOffset2 = new MPPointF();
    private WeakReference<Chart> mWeakChart;
    /**
     * Constructor. Sets up the MarkerView with a custom layout resource.
     *
     * @param context
     * @param layoutResource the layout resource to use for the MarkerView
     */
    public NewMarkerView(Context context, int layoutResource) {
        super(context);
        setupLayoutResource(layoutResource);
    }
    /**
     * Sets the layout resource for a custom MarkerView.
     *
     * @param layoutResource
     */
    private void setupLayoutResource(int layoutResource) {
        View inflated = LayoutInflater.from(getContext()).inflate(layoutResource, this);
        inflated.setLayoutParams(new LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT));
        inflated.measure(MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED), MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED));
        // measure(getWidth(), getHeight());
        inflated.layout(0, 0, inflated.getMeasuredWidth(), inflated.getMeasuredHeight());
    }
    public void setOffset(MPPointF offset) {
        mOffset = offset;
        if (mOffset == null) {
            mOffset = new MPPointF();
        }
    }
    public void setOffset(float offsetX, float offsetY) {
        mOffset.x = offsetX;
        mOffset.y = offsetY;
    }
    @Override
    public MPPointF getOffset() {
        return mOffset;
    }
    public MPPointF getOffsetRight() {
        return mOffset;
    }
    public void setChartView(Chart chart) {
        mWeakChart = new WeakReference<>(chart);
        chart.setMarker(this);
    }
    public Chart getChartView() {
        return mWeakChart == null ? null : mWeakChart.get();
    }
    @Override
    public MPPointF getOffsetForDrawingAtPoint(float posX, float posY) {
        Chart chart = getChartView();
        MPPointF offset = getOffset();
        float width = getWidth();
        float height = getHeight();
        mOffset2.x = offset.x;
        if (chart != null && posX + width + mOffset2.x > chart.getWidth()) {
            offset = getOffsetRight();
            mOffset2.x = offset.x;
        }
        mOffset2.y = offset.y;
        if (posX + mOffset2.x < 0) {
            mOffset2.x = -posX;
        } /*else if (chart != null && posX + width + mOffset2.x > chart.getWidth()) {
            mOffset2.x = chart.getWidth() - posX - width;
        }*/
        if (posY + mOffset2.y < 0) {
            mOffset2.y = -posY;
        } else if (chart != null && posY + height + mOffset2.y > chart.getHeight()) {
            mOffset2.y = chart.getHeight() - posY - height;
        }
        return mOffset2;
    }
    @Override
    public void refreshContent(Entry e, Highlight highlight) {
        measure(MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED),
                MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED));
        layout(0, 0, getMeasuredWidth(), getMeasuredHeight());
    }
    @Override
    public void draw(Canvas canvas, float posX, float posY) {
        MPPointF offset = getOffsetForDrawingAtPoint(posX, posY);
        int saveId = canvas.save();
        // translate to the correct position and draw
        canvas.translate(posX + offset.x, posY + offset.y);
        draw(canvas);
        canvas.restoreToCount(saveId);
    }
}

主要是加了一个getOffsetRight函数,在getOffsetForDrawingAtPoint函数中判断,何时调用getOffsetRight即可。演示代码如下

      NewMarkerView marker = new NewMarkerView(this, R.layout.layout_markview) {
            private TextView view;
            @Override
            protected void onLayout(boolean changed, int l, int t, int r, int b) {
                super.onLayout(changed, l, t, r, b);
                view = (TextView) super.findViewById(R.id.id_value);
            }
            @Override
            public void refreshContent(Entry e, Highlight l) {
                // TODO Auto-generated method stub
                StringBuffer buffer = new StringBuffer();
                if (e.getData() instanceof Data) {
                    Data data = (Data) e.getData();
                    buffer.append(data.getDate());
                    buffer.append("\r\n");
                    buffer.append(data.getData());
                    buffer.append(data.getStatus());
                }
                view.setText(buffer);
                super.refreshContent(e, l);//必须加上该句话;This sentence must be added.
            }
            @Override
            public MPPointF getOffset() {
                return new MPPointF(0, -getHeight() >> 1);
            }
            @Override
            public MPPointF getOffsetRight() {
                return new MPPointF(-getWidth(), -getHeight());
            }
        };
        marker.setChartView(chart);

最终效果图:

本文链接:https://www.it72.com/12316.htm

推荐阅读
最新回复 (0)
返回