読者です 読者をやめる 読者になる 読者になる

新しいノートブック

Android大好き

Canvasでベジェ曲線描画とクリッピング

ベジェ曲線とは

n個の制御点から得られるn-1次曲線です (wikipediaより)

こちらに解りやすく図解していました。
sigbus.info: 中学生でもわかるベジェ曲線

ベジェ曲線を描く

Pathクラスにベジェ曲線を描くAPIが用意されています。

前者が2次ベジェ, 後者が3次ベジェです。制御点の数が違います。

引数 : 制御点1X, 制御点1Y, 終点1X, 終点2Y
Path#quadTo (float x1, float y1, float x2, float y2)

引数 : 制御点1X, 制御点1Y, 制御点2X, 制御点2Y, 終点1X, 終点2Y
Path#cubicTo (float x1, float y1, float x2, float y2, float x3, float y3)

始点はPathの現在地になります。(デフォルト値はx0, y0)

cubicToで一角描画してみます。

  @Override
  protected void onDraw(Canvas canvas) {
      super.onDraw(canvas);
      
      Paint paint = new Paint();
      paint.setStrokeWidth(2f);
      paint.setColor(Color.WHITE);
      paint.setAntiAlias(true);
      paint.setStyle(Paint.Style.STROKE);
      
      Path path = new Path();
      // スタート地点を移動
      path.moveTo(250, 0);
      // 制御点1 X, 制御点1 Y, 制御点2 X, 制御点2Y, 終点X, 終点Y
      path.cubicTo(450, 0, 500, 50, 500, 250);
      
      canvas.drawPath(path, paint);
  }

f:id:sooch:20160912221823p:plain

クリッピング

クリッピングするには矩形を描画する必要があります。
隙間があると失敗します。

  @Override
  protected void onDraw(Canvas canvas) {
      super.onDraw(canvas);
           
      Path path = new Path();
      // スタート地点を移動
      path.moveTo(250, 0);
      // 制御点1 X, 制御点1 Y, 制御点2 X, 制御点2Y, 終点X, 終点Y
      path.cubicTo(450, 0, 500, 50, 500, 250);
      path.cubicTo(500, 450, 450, 500, 250, 500);
      path.cubicTo(50, 500, 0, 450, 0, 250);
      path.cubicTo(0, 50, 50, 0, 250, 0);
      canvas.clipPath(path);
      
      Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.eventnews1082);
      canvas.drawBitmap(bitmap, 0, 0, null);
  }

f:id:sooch:20160912221825p:plain