实现了 柱状图 根据 SeekBar的滑动 改变的效果:
图示效果:
自定义View的代码:
package com.example.coustomviewdemo;
import android.R.color;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.graphics.Paint.Align;
import android.graphics.Paint.FontMetrics;
import android.util.AttributeSet;
import android.view.View;
public class StatscsView extends View {
public StatscsView(Context context) {
super(context);
// TODO Auto-generated constructor stub
init(context, null);
}
public StatscsView(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
init(context, attrs);
}
// 坐标轴 轴线 画笔:
private Paint axisLinePaint;
// 坐标轴水平内部 虚线画笔
private Paint hLinePaint;
// 绘制文本的画笔
private Paint titlePaint;
// 矩形画笔 柱状图的样式信息
private Paint recPaint;
private void init(Context context, AttributeSet attrs)
{
axisLinePaint = new Paint();
hLinePaint = new Paint();
titlePaint = new Paint();
recPaint = new Paint();
axisLinePaint.setColor(Color.DKGRAY);
hLinePaint.setColor(Color.LTGRAY);
titlePaint.setColor(Color.BLACK);
}
//7 条
private int[] thisYear;
//7 条
private int[] lastYear;
/**
* 跟新自身的数据 需要View子类重绘。
*
* 主线程 刷新控件的时候调用:
* this.invalidate(); 失效的意思。
* this.postInvalidate(); 可以子线程 更新视图的方法调用。
*
* */
//updata this year data
public void updateThisData(int[] thisData)
{
thisYear = thisData;
// this.invalidate(); //失效的意思。
this.postInvalidate(); //可以子线程 更新视图的方法调用。
}
//updata last year data
public void updateLastData(int[] lastData)
{
lastYear = lastData;
// this.invalidate(); //失效的意思。
this.postInvalidate(); //可以子线程 更新视图的方法调用。
}
private String[] yTitlesStrings =
new String[]{"80000","60000","40000","20000","0"};
private String[] xTitles =
new String[]{"1","2","3","4","5","6","7"};
@Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.onDraw(canvas);
int width = getWidth();
int height = getHeight();
// 1 绘制坐标线:
canvas.drawLine(100, 10, 100, 320, axisLinePaint);
canvas.drawLine(100, 320, width-10 , 320, axisLinePaint);
// 2 绘制坐标内部的水平线
int leftHeight = 300;// 左侧外周的 需要划分的高度:
int hPerHeight = leftHeight/4;
hLinePaint.setTextAlign(Align.CENTER);
for(int i=0;i<4;i++)
{
canvas.drawLine(100, 20+i*hPerHeight, width-10, 20+i*hPerHeight, hLinePaint);
}
// 3 绘制 Y 周坐标
FontMetrics metrics =titlePaint.getFontMetrics();
int descent = (int)metrics.descent;
titlePaint.setTextAlign(Align.RIGHT);
for(int i=0;i<yTitlesStrings.length;i++)
{
canvas.drawText(yTitlesStrings[i], 80, 20+i*hPerHeight+descent, titlePaint);
}
// 4 绘制 X 周 做坐标
int xAxisLength = width-110;
int columCount = xTitles.length+1;
int step = xAxisLength/columCount;
for(int i=0;i<columCount-1;i++)
{
canvas.drawText(xTitles[i], 100+step*(i+1), 360 , titlePaint);
}
// 5 绘制矩形
if(thisYear != null && thisYear.length >0)
{
int thisCount = thisYear.length;
for(int i=0;i<thisCount;i++)
{
int value = thisYear[i];
int num = 8 - value / 10000 ;
recPaint.setColor(0xFF1078CF);
Rect rect = new Rect();
rect.left = 100 + step * (i+1) - 10;
rect.right = 100 + step * (i+1) + 10;
// 当前的相对高度:
int rh = (leftHeight * num) / 8 ;
rect.top = rh + 20;
rect.bottom = 320 ;
canvas.drawRect(rect, recPaint);
}
}
if(lastYear != null && lastYear.length >0)
{
int thisCount = lastYear.length;
for(int i=0;i<thisCount;i++)
{
int value = lastYear[i];
int num = 8 - value / 10000 ;
recPaint.setColor(0xFFAA1122);
Rect rect = new Rect();
rect.left = 100 + step * (i+1) - 10;
rect.right = 100 + step * (i+1) + 10;
// 当前的相对高度:
int rh = (leftHeight * num) / 8 ;
rect.top = rh + 20;
rect.bottom = 320 ;
canvas.drawRect(rect, recPaint);
}
}
}
}
Activity:
package com.example.coustomviewdemo;
import android.app.Activity;
import android.os.Bundle;
import android.widget.SeekBar;
import android.widget.SeekBar.OnSeekBarChangeListener;
public class StatscsActivity extends Activity implements
OnSeekBarChangeListener {
private SeekBar seekBar;
private StatscsView statscsView;
public StatscsActivity() {
// TODO Auto-generated constructor stub
}
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.sycts);
seekBar = (SeekBar) this.findViewById(R.id.seekBar);
statscsView = (StatscsView) this.findViewById(R.id.statscsView1);
// seekerBar
seekBar.setOnSeekBarChangeListener(this);
}
private int[] lastData0 = new int[] { 70000, 10000, 20000, 40000, 50000,
80000, 40000 };
private int[] thisData0 = new int[] { 40000, 10000, 10000, 20000, 30000,
50000, 30000 };
private int[] lastData1 = new int[] { 70000, 60000, 60000, 40000, 50000,
80000, 80000 };
private int[] thisData1 = new int[] { 40000, 30000, 30000, 20000, 30000,
50000, 30000 };
private int[] lastData2 = new int[] { 70000, 50000, 70000, 80000, 80000,
80000, 70000 };
private int[] thisData2 = new int[] { 40000, 10000, 40000, 40000, 30000,
40000, 10000 };
private int[] lastData3 = new int[] { 70000, 80000, 70000, 40000, 50000,
80000, 40000 };
private int[] thisData3 = new int[] { 10000, 10000, 10000, 20000, 30000,
10000, 30000 };
@Override
public void onProgressChanged(SeekBar seekBar, int progress,
boolean fromUser) {
// TODO Auto-generated method stub
int cc = progress / 4;
switch (cc) {
case 0:
statscsView.updateThisData(lastData0);
statscsView.updateLastData(thisData0);
break;
case 1:
statscsView.updateThisData(lastData1);
statscsView.updateLastData(thisData1);
break;
case 2:
statscsView.updateThisData(lastData2);
statscsView.updateLastData(thisData2);
break;
case 3:
statscsView.updateThisData(lastData3);
statscsView.updateLastData(thisData3);
break;
default:
break;
}
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
}
}
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" >
<SeekBar
android:id="@+id/seekBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="48"
/>
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="10dp"
android:gravity="center"
>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="1"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="2"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="3"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="4"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="5"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="6"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="7"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="8"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="9"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="10"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="11"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1" android:gravity="center"
android:text="12"
/>
</LinearLayout>
<com.example.coustomviewdemo.StatscsView
android:id="@+id/statscsView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>