Plot numbers as Line graph on canvas

The following code plots an array of integers as a line graph on canvas of a View class.

Create a new file SkView.java.

package com.example.graphdemo;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.view.View;

public class SkView extends View {

    private Paint myPaint;
    int viewWidth = 0;
    int viewHeight = 0;

    int[] humidity = new int[]{40, 36, 79, 90, 54, 62, 80};

    public SkView(Context context) {
        super(context);
        init();
    }

    public SkView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public SkView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    private void init() {
        myPaint = new Paint();
        myPaint.setAntiAlias(true);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);

        viewWidth = this.getMeasuredWidth();
        viewHeight = this.getMeasuredHeight();

        myPaint.setStyle(Paint.Style.STROKE);
        myPaint.setStrokeWidth(4);
        myPaint.setColor(Color.BLACK);

        // Draw X and Y axes
        canvas.drawLine(viewWidth / 10f, viewHeight * 9f / 10f, viewWidth * 9f / 10f, viewHeight * 9f / 10f, myPaint);
        canvas.drawLine(viewWidth / 10f, viewHeight * 9f / 10f, viewWidth / 10f, viewHeight / 10f, myPaint);

        int marginWidth = viewWidth / 10;
        int marginHeight = viewHeight / 10;
        int graphLeft = marginWidth;
        int graphBottom = viewHeight - marginHeight;
        int graphWidth = viewWidth * 8 / 10;
        int graphHeight = viewHeight * 8 / 10;

        int gap = graphWidth / humidity.length;

        int max = humidity[0];
        for (int i = 0; i < humidity.length; i++) {
            if (max < humidity[i]) {
                max = humidity[i];
            }
        }

        float factor = (float) graphHeight / max;

        // Change color for data line
        myPaint.setColor(Color.BLUE);
        myPaint.setStrokeWidth(6);

        // Draw data lines
        for (int n = 0; n < humidity.length - 1; n++) {
            float startX = marginWidth + n * gap;
            float startY = graphBottom - (humidity[n] * factor);
            float stopX = marginWidth + (n + 1) * gap;
            float stopY = graphBottom - (humidity[n + 1] * factor);
            canvas.drawLine(startX, startY, stopX, stopY, myPaint);
        }

        // Optional: draw data points
        myPaint.setColor(Color.RED);
        for (int n = 0; n < humidity.length; n++) {
            float x = marginWidth + n * gap;
            float y = graphBottom - (humidity[n] * factor);
            canvas.drawCircle(x, y, 8, myPaint);
        }
    }
}

Put this in Put this in activity_main.xml.

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:gravity="center"
    android:background="#FFFFFF">

    <com.example.graphdemo.SkView
        android:id="@+id/skView"
        android:layout_width="match_parent"
        android:layout_height="400dp"
        android:layout_margin="16dp" />
</LinearLayout>

Put following code in MainActivity.java.

package com.example.graphdemo;

import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }
}

Output

  • A white background.
  • X and Y axes in black.
  • A blue line graph connecting humidity values.
  • Red dots showing data points.
  • The graph auto-scales based on max humidity.

Leave a Reply

Discover more from Apktutor

Subscribe now to keep reading and get access to the full archive.

Continue reading