2012-12-02 25 views
16

Tôi đang cố gắng cắt một thao tác vẽ canvas thành hình nêm hình cung. Tuy nhiên, tôi không nhận được kết quả mong muốn sau khi thiết lập đường cắt cho khung vẽ.Canvas.clipPath (Đường dẫn) không cắt như mong đợi

Để minh hoạ, đây là những gì tôi đang làm:

enter image description here

path.reset(); 

//Move to point #1 
path.moveTo(rect.centerX(), rect.centerY()); 

//Per the documentation, this will draw a connecting line from the current 
//position to the starting position of the arc (at 0 degrees), add the arc 
//and my current position now lies at #2. 
path.arcTo(rect, 0, -30); 

//This should then close the path, finishing back at the center point (#3) 
path.close(); 

này hoạt động, và khi tôi chỉ đơn giản là vẽ con đường này (canvas.drawPath(path, paint)) nó thu hút sự nêm như trình bày ở trên. Tuy nhiên, khi tôi đặt con đường này như đường cắt của vải và vẽ vào nó:

//I've tried it with and without the Region.Op parameter 
canvas.clipPath(path, Region.Op.REPLACE); 
canvas.drawColor(Color.BLUE); 

tôi nhận được kết quả sau thay vì (các nêm còn lại chỉ để hiển thị tài liệu tham khảo):

enter image description here

Vì vậy, nó thay vào đó dường như clip để recting bound của Path, và không phải là Path chính nó. Bất kỳ ý tưởng gì đang xảy ra ở đây?

CHỈNH SỬA Cũng giống như bản cập nhật, tôi đã tìm thấy cách hiệu quả hơn để thực hiện việc này cho phép tăng tốc phần cứng. Đầu tiên, vẽ toàn bộ hình ảnh (mà bạn muốn cắt) thành một bitmap ngoài màn hình. Thực hiện một BitmapShader sử dụng Bitmap này, thiết lập đổ bóng đó để một Paint, sau đó vẽ đường nêm sử dụng mà Paint đối tượng:

drawMyBitmap(bitmap); 
Shader shader = new BitmapShader(bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP); 
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG); 
paint.setShader(shader); 

@Override 
public void onDraw(Canvas canvas) { 
    canvas.drawArc(rect,   //The rectangle bounding the circle 
        startAngle, //The angle (CW from 3 o'clock) to start 
        sweepAngle, //The angle (CW from 3 o'clock) of the arc 
        true,   //Boolean of whether to draw a filled arc (wedge) 
        paint   //The paint with the shader attached 
    ); 
} 
+1

Bạn đang sử dụng HC hoặc cao hơn hoặc bằng cách khác sử dụng tăng tốc phần cứng? http://developer.android.com/guide/topics/graphics/hardware-accel.html. Nếu vậy, clipPath không được hỗ trợ và có vấn đề. – Simon

+1

@Simon: Ôi trời ơi. Heh. Đáng buồn là tôi đã đề cập đến tài liệu đó rất nhiều trong tuần này, nhưng tôi hoàn toàn bỏ qua điều đó. Vô hiệu hóa HW Accel hoạt động hoàn hảo! Nếu bạn sẽ đăng câu trả lời này, tôi sẽ chấp nhận nó. Bạn là một phao cứu sinh! – kcoppock

+0

Rất vui khi được giúp đỡ. Chúc may mắn. – Simon

Trả lời

9

Bạn có sử dụng HC trở lên hoặc sử dụng tăng tốc phần cứng?

Nếu vậy, clipPath không được hỗ trợ và có vấn đề.

developer.android.com/guide/topics/graphics/hardware-accel.html.

+1

Đó là vấn đề. :) Đã di chuyển phần cắt của thao tác vẽ thành bitmap ngoài màn hình, sau đó kéo nó trở lại canvas được tăng tốc HW và nó hoạt động như một nét duyên dáng! Cảm ơn một lần nữa! – kcoppock

+1

@kcoppock Nghe có vẻ hơi lạc hậu. Tại sao bạn không chỉ chuyển đổi kiểu lớp của khung nhìn thành phần mềm, và vẫn vẽ bản vẽ của bạn trong 'onDraw()'? –

+0

@ RichardJ.RossIII Điều đó sẽ có ý nghĩa hơn.:) Tôi có một chút không quen thuộc với điều đó vào thời điểm đó. Tôi đã chỉnh sửa theo cách mới mà tôi đang xử lý vấn đề này ngay bây giờ, cảm ơn cho đầu vào mặc dù! – kcoppock

2

Câu hỏi của OP dành riêng cho việc sử dụng vùng cắt và đã được trả lời bởi @Simon. Hãy nhớ, tuy nhiên, có một cách đơn giản hơn vẽ một vòng cung điền:

Tạo một Paint:

mPaint = new Paint(); 
mPaint.setColor(Color.BLUE); 
mPaint.setStyle(Style.FILL); 
mPaint.setAntiAlias(true); 

Khi vẽ, chỉ cần vẽ đường dẫn:

canvas.drawPath(path, mPaint); 
Các vấn đề liên quan