昨天翻了翻Android的Canvas函数,发现这玩意和以前用VC时,用的API差不多搞法,以前做数据库方面的系统时,都是直接用API画的报表,
现在用Android来再试试手看看,感受感受,弄了下,不完善,但大致效果出来了,效果图如下:
用Android的API,要比VC的那一套灵活多了,就是分辨率太多,还有个横向的问题。
代码简单,实现的部份代码在下面。
1. 主程序文件:
package com.xcl.canvas; /** * Canvas练习 * 画一张报表玩玩,反正这事以前用VC时没少干. * author:xcl * date:2014-4-5 */ import com.xcl.canvas.box.DrawRptFooter; import com.xcl.canvas.box.DrawRptHeader; import com.xcl.canvas.box.DrawRptTable; import com.xcl.canvas.box.XclRptInterface; import android.os.Bundle; import android.app.Activity; import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Matrix; import android.graphics.Paint; import android.util.DisplayMetrics; import android.view.Menu; import android.view.View; public class MainActivity extends Activity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); //setContentView(R.layout.activity_main); setContentView(new PanelRpt(this)); } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.main, menu); return true; } public void onDraw(Canvas canvas){ } class PanelRpt extends View { Paint paint; private int ScrHeight; private int ScrWidth; private XclRptInterface xRpt = null; public PanelRpt(Context context){ super(context); DisplayMetrics dm = getResources().getDisplayMetrics(); ScrHeight = dm.heightPixels; ScrWidth = dm.widthPixels; paint = new Paint(); paint.setColor(Color.RED);// 设置红色 } public void onDraw(Canvas canvas){ int HeaderHeight = 200; int FooterHeight = 100; int startx = 10; int starty = 10; //报表Logo Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.xcllogo); canvas.drawColor(Color.WHITE); canvas.drawBitmap(bitmap, startx,starty, paint); //表头 xRpt = new DrawRptHeader(); xRpt.SetRptSize(ScrWidth,HeaderHeight); xRpt.draw(canvas); //表明细 DrawRptTable xRptTable = new DrawRptTable(); xRptTable.SetRptSize(ScrWidth,ScrHeight); xRptTable.SetRptSpan(HeaderHeight,FooterHeight); xRptTable.draw(canvas); //表尾 DrawRptFooter xRptFooter = new DrawRptFooter(); xRptFooter.SetRptSize(ScrWidth,ScrHeight); xRptFooter.SetRptSpan(FooterHeight); xRptFooter.draw(canvas); } } }
2. 接口类
package com.xcl.canvas.box; /** * Canvas练习 --报表接口 * * author:xcl * date:2014-4-5 */ import android.graphics.Canvas; public interface XclRptInterface { //左间距 public final int PageLeftSpan = 10; //右间距 public final int PageRightSpan = 10; //上间距 public final int PageTopSpan = 10; //字体大小 public final int RptFontHeader = 40; public final int RptFontTable = 18; //设置线条粗细 public final int RptStrokeWidth = 12; //报表显示页画布大小 public void SetRptSize(int width,int height); //画布 public void draw(Canvas canvas); }
3.画报表表格的代码如下:
package com.xcl.canvas.box; /** * Canvas练习 --表明细 * * author:xcl * date:2014-4-5 */ import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.RectF; import android.graphics.Typeface; public class DrawRptTable implements XclRptInterface { private Paint PaintText = null; private Paint PaintLine = null; //报表页面大小 private int RptHeight = 0; private int RptWidth = 0; //总行数 private int RowCount = 6; //表头高度 private int RptHeader = 0; //表尾高度 private int RptFooter = 0; //确定列分隔线的X坐标 private int TabCol0PosLn = 0; private int TabCol1PosLn = 0; private int TabCol2PosLn = 0; private int TabCol3PosLn = 0; //确定列中文字显示位置(X坐标) private int TabCol0PosText = 0; private int TabCol1PosText = 0; private int TabCol2PosText = 0; //文字上移间距 private final int RowTextMvSpan = 20; //表格最上面的间距 private final int TabTopPosY = 100; public DrawRptTable() { // TODO Auto-generated constructor stub //画文字的画笔 PaintText = new Paint(); PaintText.setAntiAlias(true); //绘制直线 PaintText.setColor(Color.BLUE); //设置线条粗细 PaintText.setStrokeWidth(12); //设置字体及大小 Typeface serif_italic = Typeface.create(Typeface.SERIF,Typeface.ITALIC); PaintText.setTypeface(serif_italic); PaintText.setTextSize(RptFontTable); //划线的画笔 PaintLine = new Paint(); PaintLine.setStrokeWidth(2); PaintLine.setColor(Color.BLACK); PaintLine.setStyle(Paint.Style.STROKE); } @Override public void draw(Canvas canvas) { // TODO Auto-generated method stub //当前显示页可显示的高度 int TableHeight = RptHeight - RptHeader - RptFooter; //依高度与总行数算出行间距 int RowSpan = TableHeight / RowCount; //初始化表格显示位置 int startx = PageTopSpan ; int starty = TabTopPosY; int endx = RptWidth - PageRightSpan; int endy = TabTopPosY; //确定列分隔线的X坐标 TabCol0PosLn = PageLeftSpan; TabCol1PosLn = RptWidth - PageRightSpan; TabCol2PosLn = RptWidth/10*2; TabCol3PosLn = RptWidth/10*6; //确定列中文字显示位置(X坐标) TabCol0PosText = RptWidth/10; TabCol1PosText = RptWidth/10*2; TabCol2PosText = RptWidth/10*6; int CurTextPosY = 0; //开始画表格 canvas.drawLine( startx ,starty,endx,endy, PaintLine); for(int i=0;i<RowCount;i++) { starty = starty + RowSpan; endy = endy + RowSpan; CurTextPosY = starty - RowTextMvSpan; if( i == 0) //表头 { canvas.drawText("ID", TabCol0PosText,CurTextPosY, PaintText); canvas.drawText("NAME",TabCol1PosText,CurTextPosY, PaintText); canvas.drawText("MAIL",TabCol2PosText,CurTextPosY, PaintText); }else{ //表格内容 canvas.drawText(Integer.toString(i), TabCol0PosText,CurTextPosY, PaintText); canvas.drawText("xiongchuanliang", TabCol1PosText,CurTextPosY, PaintText); canvas.drawText("xcl_168@aliyun.com",TabCol2PosText,CurTextPosY, PaintText); } //画行分隔线 canvas.drawLine( startx ,starty,endx,endy, PaintLine); } //画列分隔线 //左边线 canvas.drawLine( TabCol0PosLn ,TabTopPosY,TabCol0PosLn,endy, PaintLine); //列间隔线1 canvas.drawLine( TabCol1PosLn ,TabTopPosY,TabCol1PosLn,endy, PaintLine); //列间隔线2 canvas.drawLine( TabCol2PosLn ,TabTopPosY,TabCol2PosLn,endy, PaintLine); //右边线 canvas.drawLine( TabCol3PosLn ,TabTopPosY,TabCol3PosLn,endy, PaintLine); } @Override public void SetRptSize(int width,int height) { // TODO Auto-generated method stub RptWidth = width; RptHeight = height; } public void SetRptSpan(int headerHeight,int footerHeight) { // TODO Auto-generated method stub RptHeader = headerHeight; RptFooter = footerHeight; } }例子中的表头和表尾高度是写死的,适配时可以去计算得出。
报表中表格的数据需要连上数据库,再加上分页及导出功能才算实用,不弄这些了。
MAIL: xcl_168@aliyun.com
BLOG: http://blog.csdn.net/xcl168