/** 构造函数,主要对一些对象初始化 */ public MySurfaceView(Context context) { super(context); mHolder = this.getHolder(); // 获得SurfaceHolder对象 mHolder.addCallback(this); // 添加状态监听 mPaint = new Paint(); // 创建一个画笔对象 mPaint.setColor(Color.WHITE); // 设置画笔的颜色为白色 qPaint = new Paint(); // 创建一个画笔对象 qPaint.setAntiAlias(true); // 消除锯齿 qPaint.setStyle(Paint.Style.STROKE); // 设置画笔风格为描边 qPaint.setStrokeWidth(3); // 设置描边的宽度为3 qPaint.setColor(Color.GREEN); // 设置画笔的颜色为绿色 // 创建路径对象 mPath = new Path(); qPath = new Path(); tPath = new Path(); // 设置坐标为50,100 mX = 50; mY = 100; // 设置贝塞尔曲线的开始坐标为(10,200) qStartX = 10; qStartY = 200; setFocusable(true); // 设置焦点 }
/** * 画左右侧的边界区域(将超出的chart图形覆盖) * * @param canvas */ private void drawLimitRect(Canvas canvas) { Paint paint = new Paint(); paint.setColor(backColor); paint.setStyle(Style.FILL); canvas.drawRect(0, 0, leftPadding + yTextWidth, height - bottomPadding, paint); canvas.drawRect(width - rightPadding, 0, width, height - bottomPadding, paint); }
public void onDraw(Canvas canvas) { // 검정색 배경으로 지운다. 빈 화면이면 지우기만 하고 리턴 canvas.drawColor(Color.BLACK); if (status == BLANK) { return; } // 도형 목록을 순회하면서 도형 정보대로 출력한다. int idx; for (idx = 0; idx < arShape.size(); idx++) { Paint Pnt = new Paint(); Pnt.setAntiAlias(true); Pnt.setColor(arShape.get(idx).color); Rect rt = arShape.get(idx).rt; switch (arShape.get(idx).what) { case Shape.RECT: canvas.drawRect(rt, Pnt); break; case Shape.CIRCLE: canvas.drawCircle( rt.left + rt.width() / 2, rt.top + rt.height() / 2, rt.width() / 2, Pnt); break; case Shape.TRIANGLE: Path path = new Path(); path.moveTo(rt.left + rt.width() / 2, rt.top); path.lineTo(rt.left, rt.bottom); path.lineTo(rt.right, rt.bottom); canvas.drawPath(path, Pnt); break; } } }
public void onDraw(Canvas canvas) { canvas.drawColor(Color.LTGRAY); Paint Pnt = new Paint(); String str = "Custom Font Test"; Pnt.setAntiAlias(true); Pnt.setTypeface(mFont); Pnt.setTextSize(30); canvas.drawText(str, 10, 40, Pnt); }
// 그리기 void Draw(Canvas canvas) { Paint pnt = new Paint(); pnt.setAntiAlias(true); int r; int alpha; for (r = rad, alpha = 1; r > 4; r--, alpha += 5) { pnt.setColor(Color.argb(alpha, Color.red(color), Color.green(color), Color.blue(color))); canvas.drawCircle(x, y, r, pnt); } }
public MyView(Context context) { super(context); paint = new Paint(); paint.setColor(Color.BLUE); paint.setStyle(Paint.Style.STROKE); // 设置画笔风格为描边 paint.setStrokeWidth(10); random = new Random(); setFocusable(true); holder = getHolder(); holder.addCallback(this); path = new Path(); }
protected void onDraw(Canvas cs) { super.onDraw(cs); // 描画方法の設定 Paint p = new Paint(); p.setColor(Color.BLACK); p.setStyle(Paint.Style.FILL); p.setStrokeWidth(8); // 円の描画 cs.drawCircle(x, y, 50, p); }
// ============================================================================== public final int[] renderGlyph( char glyph, Paint paint, android.graphics.Matrix matrix, Rect bounds) { Path p = new Path(); paint.getTextPath(String.valueOf(glyph), 0, 1, 0.0f, 0.0f, p); RectF boundsF = new RectF(); p.computeBounds(boundsF, true); matrix.mapRect(boundsF); boundsF.roundOut(bounds); bounds.left--; bounds.right++; final int w = bounds.width(); final int h = bounds.height(); Bitmap bm = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888); Canvas c = new Canvas(bm); matrix.postTranslate(-bounds.left, -bounds.top); c.setMatrix(matrix); c.drawPath(p, paint); final int sizeNeeded = w * h; if (cachedRenderArray.length < sizeNeeded) cachedRenderArray = new int[sizeNeeded]; bm.getPixels(cachedRenderArray, 0, w, 0, 0, w, h); bm.recycle(); return cachedRenderArray; }
private void init() { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) { setLayerType(LAYER_TYPE_SOFTWARE, null); } else { setDrawingCacheEnabled(true); } boolean hasShot = getContext() .getSharedPreferences(PREFS_SHOWCASE_INTERNAL, Context.MODE_PRIVATE) .getBoolean("hasShot" + getConfigOptions().showcaseId, false); if (hasShot && mOptions.shotType == TYPE_ONE_SHOT) { // The showcase has already been shot once, so we don't need to do anything setVisibility(View.GONE); isRedundant = true; return; } showcase = getContext().getResources().getDrawable(R.drawable.cling); showcaseRadius = metricScale * INNER_CIRCLE_RADIUS; PorterDuffXfermode mBlender = new PorterDuffXfermode(PorterDuff.Mode.MULTIPLY); setOnTouchListener(this); mPaintTitle = new Paint(); mPaintTitle.setColor(titleTextColor); mPaintTitle.setShadowLayer(2.0f, 0f, 2.0f, Color.DKGRAY); mPaintTitle.setTextSize(24 * metricScale); mPaintTitle.setAntiAlias(true); mPaintDetail = new TextPaint(); mPaintDetail.setColor(detailTextColor); mPaintDetail.setShadowLayer(2.0f, 0f, 2.0f, Color.DKGRAY); mPaintDetail.setTextSize(16 * metricScale); mPaintDetail.setAntiAlias(true); mEraser = new Paint(); mEraser.setColor(0xFFFFFF); mEraser.setAlpha(0); mEraser.setXfermode(mBlender); mEraser.setAntiAlias(true); if (!mOptions.noButton && mEndButton.getParent() == null) { RelativeLayout.LayoutParams lps = (LayoutParams) generateDefaultLayoutParams(); lps.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM); lps.addRule(RelativeLayout.ALIGN_PARENT_RIGHT); int margin = ((Number) (metricScale * 12)).intValue(); lps.setMargins(margin, margin, margin, margin); lps.height = LayoutParams.WRAP_CONTENT; lps.width = LayoutParams.WRAP_CONTENT; mEndButton.setLayoutParams(lps); mEndButton.setText(buttonText != null ? buttonText : getResources().getString(R.string.ok)); if (!hasCustomClickListener) mEndButton.setOnClickListener(this); addView(mEndButton); } }
/** * ************************************************************** put text in figure coordinates * (0,0) is bottom left side. ************************************************************** */ private void textFigure(String txt, float x, float y, float deg, Canvas canvas) { mPlotPaint.setStrokeWidth(0); if (deg != 0) { canvas.save(); canvas.rotate(deg, x, y); } canvas.drawText(txt, x, y, mPlotPaint); if (deg != 0) { canvas.restore(); } }
/** * 画X,Y轴和边框 * * @param canvas */ private void drawAxesLine(Canvas canvas) { XYpaint = new Paint(); XYpaint.setColor(axesLineColor); XYpaint.setAntiAlias(true); XYpaint.setStyle(Style.FILL_AND_STROKE); XYpaint.setStrokeWidth(chartFrameLineSize); // 左侧Y轴 canvas.drawLine( leftPadding + yTextWidth, topPadding + topTextHeight, leftPadding + yTextWidth, height - bottomPadding - xTextHeight, XYpaint); // 三角箭头 Path yTriangle = new Path(); yTriangle.moveTo(leftPadding + yTextWidth - 10, topPadding + topTextHeight); yTriangle.lineTo(leftPadding + yTextWidth, topPadding + topTextHeight - 20); yTriangle.lineTo(leftPadding + yTextWidth + 10, topPadding + topTextHeight); yTriangle.close(); canvas.drawPath(yTriangle, XYpaint); // 下方X轴 canvas.drawLine( leftPadding + yTextWidth, height - bottomPadding - xTextHeight, width - rightPadding, height - bottomPadding - xTextHeight, XYpaint); // 三角箭头 Path xTriangle = new Path(); xTriangle.moveTo(width - rightPadding, height - bottomPadding - xTextHeight + 10); xTriangle.lineTo(width - rightPadding + 15, height - bottomPadding - xTextHeight); xTriangle.lineTo(width - rightPadding, height - bottomPadding - xTextHeight - 10); xTriangle.close(); canvas.drawPath(xTriangle, XYpaint); // 上方封顶 // canvas.drawLine(leftPadding + xTextHeight, topPadding + topTextHeight, width - rightPadding, // topPadding + topTextHeight, XYpaint); // 右侧封边 // canvas.drawLine(width - rightPadding, topPadding + topTextHeight, width - rightPadding, // height - bottomPadding - xTextHeight, XYpaint); }
public ShowcaseView setTextColors(int titleTextColor, int detailTextColor) { this.titleTextColor = titleTextColor; this.detailTextColor = detailTextColor; if (mPaintTitle != null) { mPaintTitle.setColor(titleTextColor); } if (mPaintDetail != null) { mPaintDetail.setColor(detailTextColor); } invalidate(); return this; }
/** * 通过x轴间距,计算出字体大小,自动适应宽度 * * @param paint the Paint to set the text size for * @param desiredWidth the desired width * @param text the text that should be that width * @return */ private void setTextSizeForWidth(Paint paint, float desiredWidth, String text) { // Pick a reasonably large value for the test. Larger values produce // more accurate results, but may cause problems with hardware // acceleration. But there are workarounds for that, too; refer to // http://stackoverflow.com/questions/6253528/font-size-too-large-to-fit-in-cache final float testTextSize = 48f; // Get the bounds of the text, using our testTextSize. paint.setTextSize(testTextSize); Rect bounds = new Rect(); paint.getTextBounds(text, 0, text.length(), bounds); // Calculate the desired size as a proportion of our testTextSize. float desiredTextSize = testTextSize * desiredWidth / bounds.width(); // 如果计算出的字体高度小于预设值 if (bottomTextSize > desiredTextSize) { // Set the paint for that size. paint.setTextSize(desiredTextSize); } else { paint.setTextSize(bottomTextSize); } }
public void onDraw(Canvas canvas) { canvas.drawColor(Color.LTGRAY); Paint Pnt = new Paint(); int y = 1; Pnt.setAntiAlias(true); Pnt.setTextSize(30); Pnt.setTypeface(Typeface.create(Typeface.DEFAULT, Typeface.NORMAL)); canvas.drawText("Font:Default", 10, y++ * 40, Pnt); Pnt.setTypeface(Typeface.create(Typeface.DEFAULT_BOLD, Typeface.NORMAL)); canvas.drawText("Font:Default Bold", 10, y++ * 40, Pnt); Pnt.setTypeface(Typeface.create(Typeface.MONOSPACE, Typeface.NORMAL)); canvas.drawText("Font:Monospace", 10, y++ * 40, Pnt); Pnt.setTypeface(Typeface.create(Typeface.SANS_SERIF, Typeface.NORMAL)); canvas.drawText("Font:Sans Serif", 10, y++ * 40, Pnt); Pnt.setTypeface(Typeface.create(Typeface.SERIF, Typeface.NORMAL)); canvas.drawText("Font:Serif", 10, y++ * 40, Pnt); }
@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); if (paint == null) { paint = new Paint(); luar = new LinearGradient( 0.f, 0.f, 0.f, this.getMeasuredHeight(), 0xffffffff, 0xff000000, TileMode.CLAMP); } int rgb = Color.HSVToColor(color); Shader dalam = new LinearGradient(0.f, 0.f, this.getMeasuredWidth(), 0.f, 0xffffffff, rgb, TileMode.CLAMP); ComposeShader shader = new ComposeShader(luar, dalam, PorterDuff.Mode.MULTIPLY); paint.setShader(shader); canvas.drawRect(0.f, 0.f, this.getMeasuredWidth(), this.getMeasuredHeight(), paint); }
/** * 背景画网格的横线 * * @param canvas */ private void drawGridLine(Canvas canvas) { Paint paint = new Paint(); paint.setColor(gridLineColor); paint.setAntiAlias(true); paint.setStyle(Style.STROKE); paint.setStrokeWidth(gridLineSize); paint.setPathEffect(new DashPathEffect(new float[] {10, 20}, 0)); for (int i = 1; i <= yNum; i++) { // 画网格的横线 canvas.drawLine( leftPadding + yTextWidth, height - bottomPadding - xTextHeight - (spaceYLength * i), width - rightPadding, height - bottomPadding - xTextHeight - (spaceYLength * i), paint); } }
/** * Y周的刻度值 * * @param canvas */ private void drawYValueText(Canvas canvas) { Paint paint = new Paint(); paint.setColor(axesLineColor); paint.setAntiAlias(true); paint.setSubpixelText(true); paint.setTypeface(Typeface.MONOSPACE); paint.setTextSize(leftTextSize); paint.setTextAlign(Align.RIGHT); /*int yHeight = height - topPadding - bottomPadding - topTextHeight; int spaceLength = yHeight / yNum; int spaceValue = (yMaxValue - yMinValue) / yNum; for (int i = 0; i < 6; i++) { canvas.drawText((yMinValue + spaceValue * i) + "", leftPadding + yTextWidth - 5, height - bottomPadding - yTextWidth - (spaceLength * i), paint); }*/ canvas.drawText( "优秀", leftPadding + (yTextWidth + leftTextSize) / 2, height - bottomPadding - xTextHeight - (spaceYLength * 5) + leftTextSize / 2, paint); canvas.drawText( "良好", leftPadding + (yTextWidth + leftTextSize) / 2, height - bottomPadding - xTextHeight - (spaceYLength * 4) + leftTextSize / 2, paint); canvas.drawText( "一般", leftPadding + (yTextWidth + leftTextSize) / 2, height - bottomPadding - xTextHeight - (spaceYLength * 3) + leftTextSize / 2, paint); canvas.drawText( "差劲", leftPadding + (yTextWidth + leftTextSize) / 2, height - bottomPadding - xTextHeight - (spaceYLength * 2) + leftTextSize / 2, paint); canvas.drawText( "恶劣", leftPadding + (yTextWidth + leftTextSize) / 2, height - bottomPadding - xTextHeight - (spaceYLength * 1) + leftTextSize / 2, paint); }
@Override protected void onSizeChanged(int w, int h, int oldw, int oldh) { super.onSizeChanged(w, h, oldw, oldh); Log.d(TAG, "Slice Count: " + mData.size()); if (mData.size() > 0) { // // Set dimensions for text, pie chart, etc // // Account for padding float xpad = (float) (getPaddingLeft() + getPaddingRight()); float ypad = (float) (getPaddingTop() + getPaddingBottom()); // Account for the label if (mShowText) xpad += mTextWidth; float ww = (float) w - xpad; float hh = (float) h - ypad; // Figure out how big we can make the pie. float diameter = Math.min(ww, hh); mPieBounds = new RectF(0.0f, 0.0f, diameter, diameter); mPieBounds.offsetTo(getPaddingLeft(), getPaddingTop()); // Log.d(TAG, "mPieBounds>> "+mPieBounds); mPointerY = mTextY - (mTextHeight / 2.0f); float pointerOffset = mPieBounds.centerY() - mPointerY; // Make adjustments based on text position if (mTextPos == TEXTPOS_LEFT) { mTextPaint.setTextAlign(Paint.Align.RIGHT); if (mShowText) mPieBounds.offset(mTextWidth, 0.0f); mTextX = mPieBounds.left; if (pointerOffset < 0) { pointerOffset = -pointerOffset; mCurrentItemAngle = 225; } else { mCurrentItemAngle = 135; } mPointerX = mPieBounds.centerX() - pointerOffset; } else { mTextPaint.setTextAlign(Paint.Align.LEFT); mTextX = mPieBounds.right; if (pointerOffset < 0) { pointerOffset = -pointerOffset; mCurrentItemAngle = 315; } else { mCurrentItemAngle = 45; } mPointerX = mPieBounds.centerX() + pointerOffset; } mShadowBounds = new RectF( mPieBounds.left + 10, mPieBounds.bottom + 10, mPieBounds.right - 10, mPieBounds.bottom + 20); // Lay out the child view that actually draws the pie. mPieView.layout( (int) mPieBounds.left, (int) mPieBounds.top, (int) mPieBounds.right, (int) mPieBounds.bottom); mPieView.setPivot(mPieBounds.width() / 2, mPieBounds.height() / 2); mPointerView.layout(0, 0, w, h); onDataChanged(); } }
public void onDraw(Canvas canvas) { Paint p = new Paint(); p.setColor(Color.GREEN); canvas.drawCircle(x, y, 16, p); }
/** * 画折线图,网格竖线,X坐标值 * * @param canvas */ private void drawChartLine(Canvas canvas) { Paint paintChart = new Paint(); paintChart.setColor(chartLineColor); paintChart.setAntiAlias(true); paintChart.setStyle(Style.STROKE); paintChart.setStrokeWidth(chartLineSize); Paint paintGrid = new Paint(); paintGrid.setColor(gridLineColor); paintGrid.setAntiAlias(true); paintGrid.setStyle(Style.STROKE); paintGrid.setStrokeWidth(gridLineSize); Paint paintTopText = new Paint(); paintTopText.setColor(axesLineColor); paintTopText.setAntiAlias(true); paintTopText.setSubpixelText(true); paintTopText.setTypeface(Typeface.MONOSPACE); paintTopText.setTextSize(topTextSize); paintTopText.setTextAlign(Align.CENTER); Paint paintBottomText = new Paint(); paintBottomText.setColor(axesLineColor); paintBottomText.setAntiAlias(true); paintBottomText.setSubpixelText(true); paintBottomText.setTypeface(Typeface.MONOSPACE); paintBottomText.setTextSize(bottomTextSize); paintBottomText.setTextAlign(Align.CENTER); Paint paintPoint = new Paint(); paintPoint.setColor(pointColor); paintPoint.setAntiAlias(true); paintPoint.setStyle(Style.FILL); pressedPaint = new Paint(); pressedPaint.setColor(pressedColor); pressedPaint.setAntiAlias(true); pressedPaint.setStyle(Style.FILL); Paint paintShape = new Paint(); paintShape.setStyle(Style.FILL); paintShape.setColor(shapeColor); paintShape.setAlpha(shapeAlpha); if (axesData.size() > 0) { for (int i = 0; i < axesData.size(); i++) { if (i < axesData.size() - 1) { // 画折线 canvas.drawLine( axesData.get(i).X, axesData.get(i).Y, axesData.get(i + 1).X, axesData.get(i + 1).Y, paintChart); if (isShapeShow) { // 画阴影 Path path = new Path(); path.moveTo(axesData.get(i).X, height - bottomPadding - xTextHeight); path.lineTo(axesData.get(i).X, axesData.get(i).Y + chartLineSize / 2); path.lineTo(axesData.get(i + 1).X, axesData.get(i + 1).Y + chartLineSize / 2); path.lineTo(axesData.get(i + 1).X, height - bottomPadding - xTextHeight); canvas.drawPath(path, paintShape); } } // 画网格竖线 // canvas.drawLine(axesData.get(i).X, height - bottomPadding - xTextHeight, // axesData.get(i).X, topPadding + topTextHeight, paintGrid); // 写X轴坐标的刻度值 if (!TextUtils.isEmpty(axesData.get(i).getxText())) { setTextSizeForWidth( paintBottomText, spaceXLength - 10, axesData.get(i).getxText()); // 10为相邻日期文字间隔 canvas.drawText( axesData.get(i).getxText(), axesData.get(i).X, height - bottomPadding - xTextHeight / 2, paintBottomText); } // 写顶部的刻度值 if (!TextUtils.isEmpty(axesData.get(i).getTopText())) { // 取消了顶部隔年显示的数据 // canvas.drawText(axesData.get(i).getTopText(), axesData.get(i).X, topPadding, // paintTopText); } // 画数据点 if (pointBitmap == null) { canvas.drawCircle(axesData.get(i).X, axesData.get(i).Y, pointSize + 1, paintChart); canvas.drawCircle(axesData.get(i).X, axesData.get(i).Y, pointSize, paintPoint); } else { Matrix matrix = new Matrix(); canvas.drawBitmap(pointBitmap, matrix, paintPoint); } } // 画最后一个数据的网格竖线 // canvas.drawLine(axesData.get(axesData.size() - 1).X, height - bottomPadding - xTextHeight, // axesData.get(axesData.size() - 1).X, // topPadding + topTextHeight, paintGrid); // 写X轴坐标的最后一个值的刻度值 /* * canvas.drawText(axesData.get(axesData.size() - 1).X + "", * axesData.get(axesData.size() - 1).X, height - bottomPadding - * xTextHeight / 2, paintBottomText); */ // 写顶部的最后一个刻度值 // canvas.drawText("2014", axesData.get(axesData.size() - 1).X, // topPadding, paintTopText); // 画数最后一个据点 if (pointBitmap == null) { // canvas.drawCircle(axesData.get(axesData.size() - 1).X, // axesData.get(axesData.size() - 1).Y, pointSize + 1, // paintChart); // canvas.drawCircle(axesData.get(axesData.size() - 1).X, // axesData.get(axesData.size() - 1).Y, pointSize, paintPoint); } else { Matrix matrix = new Matrix(); canvas.drawBitmap(pointBitmap, matrix, paintPoint); } } if (currentPressedPoint != null) { // canvas.drawCircle(currentPressedPoint.X, currentPressedPoint.Y, pointSize, pressedPaint); } }
@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); // draw border mPlotPaint.setStyle(Paint.Style.STROKE); mPlotPaint.setColor(Color.BLACK); canvas.drawRect(mPlotBounds, mPlotPaint); // draw grid mPlotPaint.setColor(gridColor); // x grid if (xTicks != null) { for (float tick : xTicks) { int x = calcX(tick); canvas.drawLine(x, mPlotBounds.bottom, x, mPlotBounds.top, mPlotPaint); } } if (yTicks != null) { for (float tick : yTicks) { int y = calcY(tick); canvas.drawLine(mPlotBounds.left, y, mPlotBounds.right, y, mPlotPaint); } } /* ************************* * draw the data ***************************/ for (Seria s : mData) { stroke(s, canvas); } // draw rectangles that hide out of bounds lines mPlotPaint.setStyle(Style.FILL); mPlotPaint.setColor(Color.WHITE); // left canvas.drawRect(0, 0, mPlotBounds.left, this.getBottom(), mPlotPaint); // bottom canvas.drawRect(0, mPlotBounds.bottom + 1, this.getRight(), this.getBottom(), mPlotPaint); // right canvas.drawRect(mPlotBounds.right + 1, 0, this.getRight(), this.getBottom(), mPlotPaint); // top canvas.drawRect(0, 0, this.getRight(), mPlotBounds.top, mPlotPaint); // x ticks mPlotPaint.setStyle(Paint.Style.STROKE); mPlotPaint.setTextAlign(Align.CENTER); mPlotPaint.setTextSize(xTickTextHeight); mPlotPaint.setColor(xTickColor); if (xTicks != null) { for (float tick : xTicks) { textFigure( xTickFormat.format(tick).toString(), calcX(tick), mPlotBounds.bottom + xTickTextHeight, canvas); } } mPlotPaint.setTextSize(labelTextHeight); mPlotPaint.setTextAlign(Align.RIGHT); if (labelX != null) { textFigure(labelX, mPlotBounds.right, mPlotBounds.bottom + axisXSpacing, canvas); } // y ticks mPlotPaint.setTextAlign(Align.CENTER); mPlotPaint.setTextSize(yTickTextHeight); mPlotPaint.setColor(yTickColor); if (yTicks != null) { for (float tick : yTicks) { textFigure( yTickFormat.format(tick).toString(), mPlotBounds.left - yTickTextHeight, calcY(tick), 90, canvas); } } mPlotPaint.setTextSize(labelTextHeight); mPlotPaint.setTextAlign(Align.RIGHT); if (labelX != null) { textFigure(labelX, mPlotBounds.right, mPlotBounds.bottom + axisXSpacing, canvas); } mPlotPaint.setTextAlign(Align.LEFT); if (labelY != null) { textFigure(labelY, mPlotBounds.left - axisYSpacing, mPlotBounds.top, 90, canvas); } }
private void stroke(Seria s, Canvas canvas) { mPlotPaint.setStyle(Paint.Style.STROKE); // draw line if (s.mWidth > 0) { // create the path mPath.reset(); mPath.moveTo(calcX(s.x[0]), calcY(s.y[0])); for (int i = 1; i < s.sz(); i++) { mPath.lineTo(calcX(s.x[i]), calcY(s.y[i])); } // draw the path mPlotPaint.setColor(s.mColor); mPlotPaint.setStrokeWidth(s.mWidth); mPlotPaint.setPathEffect(s.mEffect); canvas.drawPath(mPath, mPlotPaint); } // draw images seria if (s.bms != null) { for (int i = 0; i < s.sz(); i++) { Bitmap bm; if (s.bms.length > 1) { bm = s.bms[i]; } else { bm = s.bms[0]; } float left = calcX(s.x[i]); float top = calcY(s.y[i]); if (s.hAlign == HALIGN.CENTER) { left -= bm.getWidth() / 2; } else if (s.hAlign == HALIGN.RIGHT) { left -= bm.getWidth(); } if (s.vAlign == VALIGN.CENTER) { top -= bm.getHeight() / 2; } else if (s.vAlign == VALIGN.BOTTOM) { top -= bm.getHeight(); } canvas.drawBitmap(s.bms[i], left, top, mPlotPaint); } } if (s.texts != null) { Align align = Align.CENTER; switch (s.hAlign) { case LEFT: align = Align.RIGHT; case RIGHT: align = Align.LEFT; } mPlotPaint.setTextAlign(align); mPlotPaint.setStrokeWidth(0); mPlotPaint.setColor(s.mColor); for (int i = 0; i < s.sz(); i++) { float x = calcX(s.x[i]); float y = calcY(s.y[i]); switch (s.vAlign) { case TOP: y -= mPlotPaint.getTextSize(); case CENTER: y -= 0.5 * mPlotPaint.getTextSize(); } if (s.deg != 0) { canvas.save(); canvas.rotate(s.deg, x, y); } canvas.drawText(s.texts[i], x, y, mPlotPaint); if (s.deg != 0) { canvas.restore(); } } } }
protected void initCompassView() { setFocusable(true); Resources r = this.getResources(); circlePaint = new Paint(Paint.ANTI_ALIAS_FLAG); circlePaint.setColor(R.color.transparent_color); circlePaint.setStrokeWidth(1); circlePaint.setStyle(Paint.Style.STROKE); textPaint = new Paint(Paint.ANTI_ALIAS_FLAG); textPaint.setColor(r.getColor(R.color.text_color)); textPaint.setFakeBoldText(true); textPaint.setSubpixelText(true); textPaint.setTextAlign(Align.LEFT); textHeight = (int) textPaint.measureText("yY"); markerPaint = new Paint(Paint.ANTI_ALIAS_FLAG); markerPaint.setColor(r.getColor(R.color.transparent_color)); markerPaint.setAlpha(200); markerPaint.setStrokeWidth(1); markerPaint.setStyle(Paint.Style.STROKE); markerPaint.setShadowLayer(2, 1, 1, r.getColor(R.color.transparent_color)); borderGradientColors = new int[4]; borderGradientPositions = new float[4]; borderGradientColors[3] = r.getColor(R.color.transparent_color); borderGradientColors[2] = r.getColor(R.color.transparent_color); borderGradientColors[1] = r.getColor(R.color.transparent_color); borderGradientColors[0] = r.getColor(R.color.transparent_color); borderGradientPositions[3] = 0.0f; borderGradientPositions[2] = 1 - 0.03f; borderGradientPositions[1] = 1 - 0.06f; borderGradientPositions[0] = 1.0f; glassGradientColors = new int[5]; glassGradientPositions = new float[5]; int glassColor = 245; glassGradientColors[4] = Color.argb(65, glassColor, glassColor, glassColor); glassGradientColors[3] = Color.argb(100, glassColor, glassColor, glassColor); glassGradientColors[2] = Color.argb(50, glassColor, glassColor, glassColor); glassGradientColors[1] = Color.argb(0, glassColor, glassColor, glassColor); glassGradientColors[0] = Color.argb(0, glassColor, glassColor, glassColor); glassGradientPositions[4] = 1 - 0.0f; glassGradientPositions[3] = 1 - 0.06f; glassGradientPositions[2] = 1 - 0.10f; glassGradientPositions[1] = 1 - 0.20f; glassGradientPositions[0] = 1 - 1.0f; skyHorizonColorFrom = r.getColor(R.color.transparent_color); skyHorizonColorTo = r.getColor(R.color.transparent_color); groundHorizonColorFrom = r.getColor(R.color.transparent_color); groundHorizonColorTo = r.getColor(R.color.transparent_color); }
@Override protected void onDraw(Canvas canvas) { float ringWidth = textHeight + 4; int height = getMeasuredHeight(); int width = getMeasuredWidth(); int px = width / 2; int py = height / 2; Point center = new Point(px, py); int radius = Math.min(px, py) - 2; RectF boundingBox = new RectF(center.x - radius, center.y - radius, center.x + radius, center.y + radius); RectF innerBoundingBox = new RectF( center.x - radius + ringWidth, center.y - radius + ringWidth, center.x + radius - ringWidth, center.y + radius - ringWidth); float innerRadius = innerBoundingBox.height() / 2; RadialGradient borderGradient = new RadialGradient( px, py, radius, borderGradientColors, borderGradientPositions, TileMode.CLAMP); Paint pgb = new Paint(); pgb.setShader(borderGradient); Path outerRingPath = new Path(); outerRingPath.addOval(boundingBox, Direction.CW); canvas.drawPath(outerRingPath, pgb); LinearGradient skyShader = new LinearGradient( center.x, innerBoundingBox.top, center.x, innerBoundingBox.bottom, skyHorizonColorFrom, skyHorizonColorTo, TileMode.CLAMP); Paint skyPaint = new Paint(); skyPaint.setShader(skyShader); LinearGradient groundShader = new LinearGradient( center.x, innerBoundingBox.top, center.x, innerBoundingBox.bottom, groundHorizonColorFrom, groundHorizonColorTo, TileMode.CLAMP); Paint groundPaint = new Paint(); groundPaint.setShader(groundShader); float tiltDegree = pitch; while (tiltDegree > 90 || tiltDegree < -90) { if (tiltDegree > 90) tiltDegree = -90 + (tiltDegree - 90); if (tiltDegree < -90) tiltDegree = 90 - (tiltDegree + 90); } float rollDegree = roll; while (rollDegree > 180 || rollDegree < -180) { if (rollDegree > 180) rollDegree = -180 + (rollDegree - 180); if (rollDegree < -180) rollDegree = 180 - (rollDegree + 180); } Path skyPath = new Path(); skyPath.addArc(innerBoundingBox, -rollDegree, (180 + (2 * rollDegree))); canvas.rotate(-tiltDegree, px, py); canvas.drawOval(innerBoundingBox, groundPaint); canvas.drawPath(skyPath, skyPaint); canvas.drawPath(skyPath, markerPaint); int markWidth = radius / 3; int startX = center.x - markWidth; int endX = center.x + markWidth; Log.d("PAARV ", "Roll " + String.valueOf(rollDegree)); Log.d("PAARV ", "Pitch " + String.valueOf(tiltDegree)); double h = innerRadius * Math.cos(Math.toRadians(90 - tiltDegree)); double justTiltX = center.x - h; float pxPerDegree = (innerBoundingBox.height() / 2) / 45f; for (int i = 90; i >= -90; i -= 10) { double ypos = justTiltX + i * pxPerDegree; if ((ypos < (innerBoundingBox.top + textHeight)) || (ypos > innerBoundingBox.bottom - textHeight)) continue; canvas.drawLine(startX, (float) ypos, endX, (float) ypos, markerPaint); int displayPos = (int) (tiltDegree - i); String displayString = String.valueOf(displayPos); float stringSizeWidth = textPaint.measureText(displayString); canvas.drawText( displayString, (int) (center.x - stringSizeWidth / 2), (int) (ypos) + 1, textPaint); } markerPaint.setStrokeWidth(2); canvas.drawLine( center.x - radius / 2, (float) justTiltX, center.x + radius / 2, (float) justTiltX, markerPaint); markerPaint.setStrokeWidth(1); Path rollArrow = new Path(); rollArrow.moveTo(center.x - 3, (int) innerBoundingBox.top + 14); rollArrow.lineTo(center.x, (int) innerBoundingBox.top + 10); rollArrow.moveTo(center.x + 3, innerBoundingBox.top + 14); rollArrow.lineTo(center.x, innerBoundingBox.top + 10); canvas.drawPath(rollArrow, markerPaint); String rollText = String.valueOf(rollDegree); double rollTextWidth = textPaint.measureText(rollText); canvas.drawText( rollText, (float) (center.x - rollTextWidth / 2), innerBoundingBox.top + textHeight + 2, textPaint); canvas.restore(); canvas.save(); canvas.rotate(180, center.x, center.y); for (int i = -180; i < 180; i += 10) { if (i % 30 == 0) { String rollString = String.valueOf(i * -1); float rollStringWidth = textPaint.measureText(rollString); PointF rollStringCenter = new PointF(center.x - rollStringWidth / 2, innerBoundingBox.top + 1 + textHeight); canvas.drawText(rollString, rollStringCenter.x, rollStringCenter.y, textPaint); } else { canvas.drawLine( center.x, (int) innerBoundingBox.top, center.x, (int) innerBoundingBox.top + 5, markerPaint); } canvas.rotate(10, center.x, center.y); } canvas.restore(); canvas.save(); canvas.rotate(-1 * (bearing), px, py); double increment = 22.5; for (double i = 0; i < 360; i += increment) { CompassDirection cd = CompassDirection.values()[(int) (i / 22.5)]; String headString = cd.toString(); float headStringWidth = textPaint.measureText(headString); PointF headStringCenter = new PointF(center.x - headStringWidth / 2, boundingBox.top + 1 + textHeight); if (i % increment == 0) canvas.drawText(headString, headStringCenter.x, headStringCenter.y, textPaint); else canvas.drawLine( center.x, (int) boundingBox.top, center.x, (int) boundingBox.top + 3, markerPaint); canvas.rotate((int) increment, center.x, center.y); } canvas.restore(); RadialGradient glassShader = new RadialGradient( px, py, (int) innerRadius, glassGradientColors, glassGradientPositions, TileMode.CLAMP); Paint glassPaint = new Paint(); glassPaint.setShader(glassShader); canvas.drawOval(innerBoundingBox, glassPaint); canvas.drawOval(boundingBox, circlePaint); circlePaint.setStrokeWidth(2); canvas.drawOval(innerBoundingBox, circlePaint); canvas.restore(); }
/** * Initialize the control. This code is in a separate method so that it can be called from both * constructors. */ private void init() { // Force the background to software rendering because otherwise the Blur // filter won't work. setLayerToSW(this); // Set up the paint for the label text mTextPaint = new Paint(Paint.ANTI_ALIAS_FLAG); mTextPaint.setColor(mTextColor); if (mTextHeight == 0) { mTextHeight = mTextPaint.getTextSize(); } else { mTextPaint.setTextSize(mTextHeight); } // Set up the paint for the pie slices mPiePaint = new Paint(Paint.ANTI_ALIAS_FLAG); mPiePaint.setStyle(Paint.Style.FILL); mPiePaint.setTextSize(mTextHeight); cSlicePaint = new Paint(Paint.ANTI_ALIAS_FLAG); cSlicePaint.setStyle(Paint.Style.FILL); // Set up the paint for the shadow mShadowPaint = new Paint(0); mShadowPaint.setColor(0xff101010); mShadowPaint.setMaskFilter(new BlurMaskFilter(8, BlurMaskFilter.Blur.NORMAL)); // Add a child view to draw the pie. Putting this in a child view // makes it possible to draw it on a separate hardware layer that rotates // independently mPieView = new PieView(getContext()); addView(mPieView); mPieView.rotateTo(mPieRotation); // The pointer doesn't need hardware acceleration, but in order to show up // in front of the pie it also needs to be on a separate view. mPointerView = new PointerView(getContext()); addView(mPointerView); // Set up an animator to animate the PieRotation property. This is used to // correct the pie's orientation after the user lets go of it. if (Build.VERSION.SDK_INT >= 11) { mAutoCenterAnimator = ObjectAnimator.ofInt(PieChart.this, "PieRotation", 0); // Add a listener to hook the onAnimationEnd event so that we can do // some cleanup when the pie stops moving. mAutoCenterAnimator.addListener( new Animator.AnimatorListener() { public void onAnimationStart(Animator animator) {} public void onAnimationEnd(Animator animator) { mPieView.decelerate(); } public void onAnimationCancel(Animator animator) {} public void onAnimationRepeat(Animator animator) {} }); } // Create a Scroller to handle the fling gesture. if (Build.VERSION.SDK_INT < 11) { mScroller = new Scroller(getContext()); } else { mScroller = new Scroller(getContext(), null, true); } // The scroller doesn't have any built-in animation functions--it just supplies // values when we ask it to. So we have to have a way to call it every frame // until the fling ends. This code (ab)uses a ValueAnimator object to generate // a callback on every animation frame. We don't use the animated value at all. if (Build.VERSION.SDK_INT >= 11) { mScrollAnimator = ValueAnimator.ofFloat(0, 1); mScrollAnimator.addUpdateListener( new ValueAnimator.AnimatorUpdateListener() { public void onAnimationUpdate(ValueAnimator valueAnimator) { tickScrollAnimation(); } }); } // Create a gesture detector to handle onTouch messages mDetector = new GestureDetector(PieChart.this.getContext(), new GestureListener()); // Turn off long press--this control doesn't use it, and if long press is enabled, // you can't scroll for a bit, pause, then scroll some more (the pause is interpreted // as a long press, apparently) mDetector.setIsLongpressEnabled(false); }