2013-01-20 501 views
2

是否有可能建立橢圓形/橢圓與沒有該「模糊」邊界類似更好招:畫布上的好橢圓?

我能以某種方式圍繞創建更清晰筆畫線橢圓形,還是我必須忍受那個「模糊」的邊界? enter image description here

+1

在我測試過的所有瀏覽器(Opera,Firefox和Chrome)中,對我來說這看起來很好。你能否更具體地瞭解邊界有什麼問題? – Philipp

+0

要做的最好的事情是添加一個描邊,它是橢圓和背景之間的一種顏色。 – Neil

+0

我附上截圖,以確定我的意思。 – membersound

回答

3

!你能行的 !通過做後期處理:

1)使用globalCompositeOperation:

編輯: 肯定的,但是沒有:在Chrome至少,「目的地 - 在」不 匹配的規範:使用源計算目的地 顏色,所以我們不能從一個陰影單一的顏色。
(我做了JSBin一試:http://jsbin.com/ecipiq/4/

OR

2)使用getImageData和性能陣:

  • 畫邊境的臨時畫布
  • getImageData畫布
  • 獲得底層數據的Uint32Array或Uint8Array視圖
  • 線性循環在數組中:if value>閾值將其設置爲邊框顏色
  • 在目標畫布上繪製橢圓的填充
  • putImageData在目標畫布上。

哪一個?

  • 第二個不需要globalCompositeOperation工作。
    但是在大多數瀏覽器上(全?)get/put ImageData都很慢,這個事實
    單獨可能使這個解決方案無效。
    好的是你可以準確地決定如何unal antialias。

其他StackOverflow成員可能對此有所瞭解。

這些解決方案中的任何一種都比手寫的非別名橢圓函數要快得多。

有用的鏈接,第一個解決方案:
http://www.html5rocks.com/en/tutorials/webgl/typed_arrays/

備註,讓你開始更快:
你可以得到一個UInt32Array查看您的ImageData有:

var myGetImageData = myTempCanvas.getImageData(0,0,sizeX, sizeY); 
sourceBuffer32  = new UInt32Array(myGetImageData.data.buffer); 

然後sourceBuffer32 [I]含有紅色,綠色,藍色和透明度包裝成一個 無符號32位整數。它比0知道,如果像素非黑(=(0,0,0,0)!)

或者你可以用Uint8Array觀點更精確:

var myGetImageData = myTempCanvas.getImageData(0,0,sizeX, sizeY); 
sourceBuffer8  = new Uint8Array(myGetImageData.data.buffer); 

如果你處理只用灰色,則R = G = B的色調,使手錶爲

sourceBuffer8[4*i]>Threshold 

並且可以使用UInt32Array視圖設置第i個像素爲黑色在一個時間:

sourceBuffer32[i]=(255<<24)||(255<<16)||(255<<8); 

你一定能弄清楚如何處理這個例子中灰色/黑色以外的其他顏色。

2

簡短的回答是否,對不起!

該規範不會評論瀏覽器必須使用的反鋸齒方法(或不),因此它在瀏覽器之間將是完全不同的。不同版本的Chrome(特別是如果您使用Chrome測試版或開發人員頻道)觸發器始終處於這種狀態。

之前已經發生了一些關於在規範中對此進行編纂的討論,但除了現在有關閉圖像平滑的選項的圖像(上下文的imageSmoothingEnabled屬性)之外沒有采取任何行動。但是,這絕不適用於路徑。

不幸的是,這種解決方案只能在最狹窄的環境下工作:如果你的橢圓是固定的,就是在Firefox中創建它們(可以說是具有最平滑反鋸齒的瀏覽器)並從它們生成圖像,然後用圖像在所有的瀏覽器上。

總之,如果你想在所有瀏覽器中使用像素相同的形狀,你必須使用圖像,目前沒有其他方法。

2

是的,你可以!下面是調用context.stroke() 25倍,而不是隻有一次的結果:

non-blurry ellipse

爲了便於比較,這裏的原文:

blurry ellipse

+2

這是一個昂貴的,但有趣的方法。 – membersound

+0

不錯。我不知道是否少於25次是不夠的。 – GameAlchemist