アンドロイドキャンバスで塗りつぶされた三角形を描く方法は?


87

だから私は私のdrawメソッドで以下のコードを使用してAndroidマップでこの三角形を描いています:

paint.setARGB(255, 153, 29, 29);
paint.setStyle(Paint.Style.FILL_AND_STROKE);
paint.setAntiAlias(true);

Path path = new Path();
path.moveTo(point1_returned.x, point1_returned.y);
path.lineTo(point2_returned.x, point2_returned.y);
path.moveTo(point2_returned.x, point2_returned.y);
path.lineTo(point3_returned.x, point3_returned.y);
path.moveTo(point3_returned.x, point3_returned.y);
path.lineTo(point1_returned.x, point1_returned.y);
path.close();

canvas.drawPath(path, paint);

pointX_returnedは、フィールドから取得した座標です。それらは基本的に緯度と経度です。結果は素敵な三角形になりますが、インサイダーは空なので、マップを見ることができます。どういうわけかそれを埋める方法はありますか?


回答に投稿したように、各lineTo()の後にmoveTo()を移動しないでください。これですべてです。
oli.G 2017

私はそれがすでに(間違った)受け入れられた答えを持っている古い質問であることを知っています、そしてあなたはまたうまくいくあなたの最終的な解決策を投稿しました...しかしあなたはそれがうまくいく理由を述べていません、そして私のコメントが誰かに私が時間を節約できることを願っていますこれに費やしたばかりです:)
oli.G 2017

回答:


41

あなたはおそらく次のようなことをする必要があります:

Paint red = new Paint();

red.setColor(android.graphics.Color.RED);
red.setStyle(Paint.Style.FILL);

また、ARGBの代わりに、この色をパスに使用してください。パスの最後のポイントが最初のポイントで終了することを確認してください。これも理にかなっています。

それがうまくいくかどうか教えてください!


残念ながら、これは役に立ちません
oli.G 2017

@Nicolas事前定義された値を使用する代わりに、RGB値で色をカスタマイズする必要がある場合、ARGBの代わりに何を使用しますか?
pallav bohara 2017年

75

はい、やりました。他の誰かがそれを必要とする場合に備えて、私はこのコードを共有しています:

super.draw(canvas, mapView, true);

Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);

paint.setStrokeWidth(2);
paint.setColor(android.graphics.Color.RED);     
paint.setStyle(Paint.Style.FILL_AND_STROKE);
paint.setAntiAlias(true);

Point point1_draw = new Point();        
Point point2_draw = new Point();    
Point point3_draw = new Point();

mapView.getProjection().toPixels(point1, point1_draw);
mapView.getProjection().toPixels(point2, point2_draw);
mapView.getProjection().toPixels(point3, point3_draw);

Path path = new Path();
path.setFillType(Path.FillType.EVEN_ODD);
path.moveTo(point1_draw.x,point1_draw.y);
path.lineTo(point2_draw.x,point2_draw.y);
path.lineTo(point3_draw.x,point3_draw.y);
path.lineTo(point1_draw.x,point1_draw.y);
path.close();

canvas.drawPath(path, paint);

//canvas.drawLine(point1_draw.x,point1_draw.y,point2_draw.x,point2_draw.y, paint);

return true;

ヒントニコラスをありがとう!


7
私はあなたが最後を必要としないとかなり確信していますlineTo()close()それを自動的に行います。
Timmmm 2012

@Timmmm私はテストしました、あなたは正しいです、最後のlineTo()は必要ありません。ありがとう。
banxi1988 2013年

どうもありがとうございます。なぜ三角形を描くのにこんなに多くの問題があったのかわかりませんが、この小さな問題についてさまざまなバグで過去20分間過ごしました。
Achal Dave 2013

1
コピー貼り付けの簡単な方法は次のとおり
ZirconCode

1
pathインスタンス変数に変更した場合は、のpath.reset()後に呼び出すことを忘れないでくださいcanvas.drawPath()
シララム2018

11

頂点を使用することもできます:

private static final int verticesColors[] = {
    Color.LTGRAY, Color.LTGRAY, Color.LTGRAY, 0xFF000000, 0xFF000000, 0xFF000000
};
float verts[] = {
    point1.x, point1.y, point2.x, point2.y, point3.x, point3.y
};
canvas.drawVertices(Canvas.VertexMode.TRIANGLES, verts.length, verts, 0, null, 0, verticesColors,   0, null, 0, 0, new Paint());

2
このソリューションは塗りつぶされた形状を処理するとは思いません。(テストできません

3
これはよりパフォーマンスの高いソリューションのように見えますが、残念ながら、この方法はハードウェアアクセラレーションビューではサポートされていません。ハードウェアアクセラレーションを無効にすることはできますが、パフォーマンスの向上は失われます:developer.android.com/guide/topics/graphics/hardware-accel.html
SurlyDre 2013年

8

ここに画像の説明を入力してください

この関数は、ビットマップから三角形を作成する方法を示しています。つまり、三角形のトリミングされた画像を作成します。以下のコードを試すか、デモ例をダウンロードしてください

 public static Bitmap getTriangleBitmap(Bitmap bitmap, int radius) {
        Bitmap finalBitmap;
        if (bitmap.getWidth() != radius || bitmap.getHeight() != radius)
            finalBitmap = Bitmap.createScaledBitmap(bitmap, radius, radius,
                    false);
        else
            finalBitmap = bitmap;
        Bitmap output = Bitmap.createBitmap(finalBitmap.getWidth(),
                finalBitmap.getHeight(), Bitmap.Config.ARGB_8888);
        Canvas canvas = new Canvas(output);

        Paint paint = new Paint();
        final Rect rect = new Rect(0, 0, finalBitmap.getWidth(),
                finalBitmap.getHeight());

        Point point1_draw = new Point(75, 0);
        Point point2_draw = new Point(0, 180);
        Point point3_draw = new Point(180, 180);

        Path path = new Path();
        path.moveTo(point1_draw.x, point1_draw.y);
        path.lineTo(point2_draw.x, point2_draw.y);
        path.lineTo(point3_draw.x, point3_draw.y);
        path.lineTo(point1_draw.x, point1_draw.y);
        path.close();
        canvas.drawARGB(0, 0, 0, 0);
        paint.setColor(Color.parseColor("#BAB399"));
        canvas.drawPath(path, paint);
        paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
        canvas.drawBitmap(finalBitmap, rect, rect, paint);

        return output;
    }

上記の関数は、キャンバスに描画された三角形の画像を返します。続きを読む


7

@Pavelの回答をガイドとして使用して、ポイントがなくても開始x、y、高さと幅がある場合のヘルパーメソッドを次に示します。また、逆さま/逆さまに描くこともできます。これは、垂直棒グラフの端として使用されていたので、私にとって便利です。

 private void drawTriangle(int x, int y, int width, int height, boolean inverted, Paint paint, Canvas canvas){

        Point p1 = new Point(x,y);
        int pointX = x + width/2;
        int pointY = inverted?  y + height : y - height;

        Point p2 = new Point(pointX,pointY);
        Point p3 = new Point(x+width,y);


        Path path = new Path();
        path.setFillType(Path.FillType.EVEN_ODD);
        path.moveTo(p1.x,p1.y);
        path.lineTo(p2.x,p2.y);
        path.lineTo(p3.x,p3.y);
        path.close();

        canvas.drawPath(path, paint);
    }

4
private void drawArrows(Point[] point, Canvas canvas, Paint paint) {

    float [] points  = new float[8];             
    points[0] = point[0].x;      
    points[1] = point[0].y;      
    points[2] = point[1].x;      
    points[3] = point[1].y;         
    points[4] = point[2].x;      
    points[5] = point[2].y;              
    points[6] = point[0].x;      
    points[7] = point[0].y;

    canvas.drawVertices(VertexMode.TRIANGLES, 8, points, 0, null, 0, null, 0, null, 0, 0, paint);
    Path path = new Path();
    path.moveTo(point[0].x , point[0].y);
    path.lineTo(point[1].x,point[1].y);
    path.lineTo(point[2].x,point[2].y);
    canvas.drawPath(path,paint);

}

これは機能しています!滑らかな三角形を取得するには、paint.setAntiAlias(true)を使用することを忘れないでください。
Boldijar Paul 2014

2
drawVerticesは何を求めていますか?
psiX 2014

3

最初のイニシャルの後にpath.moveToを削除する必要があります。

Path path = new Path();
path.moveTo(point1_returned.x, point1_returned.y);
path.lineTo(point2_returned.x, point2_returned.y);
path.lineTo(point3_returned.x, point3_returned.y);
path.lineTo(point1_returned.x, point1_returned.y);
path.close();

私は3つの点を持っていませんが、1つの点しか持っていませんx nad yどうすればその点から三角形を描くことができますか?
プラナフ2015年

2

moveTo()それぞれの後にしないでくださいlineTo()

つまり、moveTo()最初のものを除くすべてを削除します。

真剣に、OPのコードをコピーして貼り付け、不要なものを削除すると moveTo()呼び出しと、機能します。

他に何もする必要はありません。


編集:私はOPがすでに彼の「最終的な実用的な解決策」を投稿したことを知っています、しかし彼はそれがなぜ働くのかを述べませんでした。実際の理由は私にはかなり驚きだったので、答えを追加する必要があると感じました。


これについてコメントを追加する必要があります。これは答えではありません。
アンガドシン2018
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.