Day 5 : Android Graphview

Day 5 : Android Graphview Cover Image

สวัสดีครับ บทความนี้เป็นบทความที่ 5 แล้วนะครับ ที่ผมจะมาเขียน ในซีรีย์ Learn 30 Android Libraries in 30 days สำหรับบทความตอนก่อน อ่านได้จากด้านล่างครับ

สำหรับบทความทั้งหมด อ่านได้จากด้านล่างครับ

ส่วนวันนี้นำเสนอ Library ตัวที่ห้า ชื่อว่า Android GraphView ครับ ซึ่ง Library ตัวนี้มันเอาไว้ช่วยให้เราแสดงพวก Graph ต่างๆบน Android ได้ครับ ส่วนตัวผมยังไม่เคยใช้ แต่ว่าเคยใช้ AChartEngine มาบ้าง โดยรวมคิดว่าน่าจะคล้ายๆกัน

Android GraphView คืออะไร?

Android GraphView เป็น Library ที่เอาไว้แสดง Graph ได้ทั้ง Line Chart และ Bar Chart จุดเด่นของมัน หลังจากที่ได้อ่าน Document ดู พบว่า มันเข้าใจง่ายมากๆ มี Demo และตัวอย่างให้ดูค่อนข้างดี และสามารถปรับแต่งได้หลากหลาย

หากอยากรู้ว่ามันทำอะไรได้บ้าง ดูหน้า Showcase ครับ

Installaton

ในส่วนขั้นตอนการติดตั้ง เผอิญว่ามันไม่มี Maven Repository ฉะนั้นก็ต้องโหลดไฟล์ .jar มาใส่ในโฟลเดอร์ libs เอาเอง โดยการ ดาวน์โหลด GraphView-3.1.2.jar จากนั้นก็อปไปไว้ในโฟลเดอร์ libs สำหรับ Android Studio ที่ไฟล์ build.gradle ใส่เป็น

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
}

เพื่อให้มันทำการ compile ไฟล์ .jar ทั้งหมดที่อยู่ในโฟลเดอร์ libs ครับ แล้วกด Sync Project with Gradle file

Getting Started

เนื่องจากผมเคยใช้ AChartEngine มาก่อน ทำให้เวลามาดู Android GraphView แล้วรู้สึกว่ามันคล้ายๆกันมากๆ ขออธิบายในส่วนสำคัญๆ ที่จะใช้ในการสร้างกราฟเลยละกันนะครับ เริ่มที่

  • GraphView : ตัวนี้จะเป็นคลาส View ตัวนึง ที่เอาไว้แสดง Graph ครับ
  • GraphViewData : ตัวนี้จะเป็น static class ที่เอาไว้สร้างข้อมูล ในแกน x, y
  • GraphViewSeries : ตัวนี้คือ set ของข้อมูลของเรา โดยสร้างมาจาก GraphViewData
  • GraphViewStyle : ตัวนี้เป็นคลาสที่จะเอาไว้ช่วยในการปรับแต่งหน้าตาของกราฟครับ
  • GraphViewSeriesStyle : อันนี้ก็เอาปรับแต่งเหมือนกัน แต่จะปรับแต่งตาม Series ของกราฟ ไม่ใช่ตัวกราฟทั้งตัว

เอาละ เมื่อรู้ว่าแต่ละคลาสใช้ทำอะไรแล้วนั้น ก็มาเริ่มสร้างโปรเจ็คกันเลย ตัวอย่างนี้ผมใช้ 2 ไฟล์ครับ คือ day5_activity_graphview.xml และ GraphViewActivity.java

ในส่วนไฟล์ xml มีแค่ LinearLayout แบบนี

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
              android:id="@+id/linear_layout"
              android:orientation="vertical"
              android:layout_width="match_parent"
              android:layout_height="match_parent">

</LinearLayout>

ในขณะที่ไฟล์ java ผมก็อปโค๊ด sample จากหน้าเว็บมาทดสอบ แบบนี้

package com.devahoy.learn30androidlibraries.day5;

import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.widget.LinearLayout;

import com.devahoy.learn30androidlibraries.R;
import com.jjoe64.graphview.GraphView;
import com.jjoe64.graphview.GraphViewSeries;
import com.jjoe64.graphview.LineGraphView;

public class GraphViewActivity extends ActionBarActivity {
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.day_5_activity_graphview);

        GraphViewSeries exampleSeries = new GraphViewSeries(new GraphView.GraphViewData[] {
                new GraphView.GraphViewData(1, 2.0d)
                , new GraphView.GraphViewData(2, 1.5d)
                , new GraphView.GraphViewData(3, 2.5d)
                , new GraphView.GraphViewData(4, 1.0d)
        });

        GraphView graphView = new LineGraphView(this, "GraphViewDemo");
        graphView.addSeries(exampleSeries);

        LinearLayout layout = (LinearLayout) findViewById(R.id.linear_layout);
        layout.addView(graphView);

    }
}

LineGraphView

ใน Docs บอก สามารถสร้าง GraphView จาก BarGraphView ได้ ลองสร้าง แล้วทดสอบรัน ก็ได้ผลลัพธ์ดังนี้

GraphView barGraphView = new BarGraphView(this, "GraphViewDemo");
barGraphView.addSeries(exampleSeries);

// layout.addView(graphView);
layout.addView(barGraphView);

BarGraphView

Multiple Series

การทำ Multiple Series ก็ไม่ยากเท่าไหร่ ผมจะใช้ข้อมูลแบบเดียวกับที่เคยทำ AChartEngine จากโพสนี้นะครับ สร้างกราฟ Line Chart บน Android ด้วย AChartEngine

private void sampleMultipleSeries() {
    String[] months = {
            "JAN", "FEB", "MAR", "APR", "MAY", "JUN",
            "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"
    };

    int[] index = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};

    int[] incomeA = {4000, 5500, 2300, 2100, 2500, 2900, 3200, 2400, 1800, 2100, 3500, 5900};
    int[] incomeB = {3600, 4500, 3200, 3600, 2800, 1800, 2100, 2900, 2200, 2500, 4000, 3500};
    int[] incomeC = {4300, 4000, 3000, 3200, 2400, 2500, 2600, 3400, 3900, 4500, 5000, 4500};


    int num = 100;
    GraphView.GraphViewData[] data = new GraphView.GraphViewData[index.length];
    for (int i = 0; i < index.length; i++) {
        data[i] = new GraphView.GraphViewData(i, incomeA[i]);
    }
    GraphViewSeries seriesA = new GraphViewSeries("Googla",
            new GraphViewSeries.GraphViewSeriesStyle(Color.RED, 5), data);

    data = new GraphView.GraphViewData[index.length];
    for (int i = 0; i < index.length; i++) {
        data[i] = new GraphView.GraphViewData(i, incomeB[i]);
    }
    GraphViewSeries seriesB = new GraphViewSeries("Microsa",
            new GraphViewSeries.GraphViewSeriesStyle(Color.BLUE, 5), data);

    data = new GraphView.GraphViewData[index.length];
        for (int i = 0; i < index.length; i++) {
            data[i] = new GraphView.GraphViewData(i, incomeC[i]);
        }
        GraphViewSeries seriesC = new GraphViewSeries("Appla",
                new GraphViewSeries.GraphViewSeriesStyle(Color.GREEN, 5), data);

    GraphView graphView = new LineGraphView(this, "Multiple Series");
    graphView.addSeries(seriesA);
    graphView.addSeries(seriesB);
    graphView.addSeries(seriesC);

    graphView.setShowLegend(true);

    LinearLayout layout = (LinearLayout) findViewById(R.id.linear_layout);
    layout.addView(graphView);

}

จากตัวอย่าง การสร้าง Multiple Series ก็ไม่ต่างจากการสร้าง Series ธรรมดาเท่าไหร่ครับ MultipleSeries มีกราฟๆหลายๆเส้น ฉะนั้น ก็ต้องสร้างแต่ละเส้นด้วย new GraphViewData(); แล้วก็นำค่าจาก incomeA-C มาใส่ จากนั้น เมื่อได้ข้อมูลทั้ง 3 จำนวนแล้ว ก็ให้ GraphView.addSeries() เพื่อเพิ่ม กราฟแต่ละเส้นเข้าไปใน Series

โดยการสร้าง GraphViewSeries จะรับ parameter 3 ค่าคือ

  • ชื่อ Title
  • GraphViewStyle(สี, ความหนาของเส้น)
  • ข้อมูลจาก GraphViewData

เพิ่มคำสั่งเพื่อให้มันโชว์ Label ซักหน่อย ว่ากราฟแต่ละเส้นคืออะไรบ้าง

graphView.setShowLegend(true);

Multiple Series รองรับเฉพาะ LineGraphView เท่านั้น ไม่รองรับ BarGraphView

Multiple Series

Viewport

Viewport คือภาพในส่วนที่เรามองเห็นจาก View ทั้งหมด ลองนึกถึงเกม Cookie Run ก็ได้ Viewport เราจะมองเห็นแค่ตัวละครเราวิ่งๆไปเรื่อยๆ Viewport ก้เปลี่ยนไปเรื่อยๆ ในขณะที่ View ทั้งหมดมันยาวๆมากๆ คอนเซป ก็ราวๆนี้ ใครงงๆ ก็ไปหาอ่านเพิ่มเติมครับ Game Viewport มีเยอะเลย ส่วนตัวผมไม่รู้จะอธิบายเพิ่มเติมยังไงเหมือนกัน

เราสามารถให้เลื่อน Viewport ของ Graph ได้ โดยใช้เมธอด setScalable() ส่งค่าเป็น true

graphView.setScalable(true);

การ Customize

เราสามารถปรับแต่ง Graph ได้หลากหลายมากครับ ส่วนมากจะเป็นการเรียกใช้เมธอด .getGraphViewStyle() จาก GraphView

Customize

ส่วนการ Custom ก็ลองไปปรับแต่งกันดูนะครับ Document และ API มีรายละเอียดเยอะมาก และครบถ้วน มีบางเมธอด ที่อาจจะ deprecated ไปแล้ว แต่ API ก็เขียนระบุไว้ว่าควรจะเปลี่ยนไปใช้อะไร เช่น

graphView.setLegendWidth(200);

ก็เปลี่ยนไปใช้

graphView.getGraphViewStyle().setLegendWidth(200);
Chai

Chai Phonbopit : Developer แห่งหนึ่ง • ผู้ชายธรรมดาๆ ที่ชื่นชอบ Node.js, JavaScript และ Open Source มีงานอดิเรกเป็น Acoustic Guitar และ Football

บทความล่าสุด