ก่อนอื่นให้ดูที่ผืนผ้าใบปกติที่วาดไวยากรณ์:
ctx.arc (centerx, centery, รัศมี, 0, pi*2, true);
ctx.shadowcolor = 'rgba (0,0,0,0.5)';
ctx.shadowblur = "10";
ctx.fill ();
ctx.beginpath ();
ctx.shadowcolor = 'rgba (0,0,0,0)';
ctx.moveto (centerx-radius, centery);
ctx.lineto (centerx -radius, centery - 50);
ctx.lineto (Centerx+Radius, Centery - 50);
ctx.lineto (centerx+รัศมี, ศูนย์กลาง);
// ctx.lineto (centerx-radius, centery);
ctx.fill ();
ctx.beginpath ();
ctx.fillstyle = 'rgba (255,0,0,1)';
ctx.arc (centerx, centery-50, รัศมี, 0, pi*2, true);
ctx.fill ();
มีสองสิ่งที่ฉันไม่พอใจกับไวยากรณ์ดั้งเดิมของผืนผ้าใบ: 1. แต่ละประโยคได้เขียน CTX (เช่นวัตถุบริบทของผืนผ้าใบ) และ 2 ฟังก์ชั่นหรือทรัพย์สินแต่ละรายการต้องครอบครองหนึ่งบรรทัด
ฉันมีความกตัญญูมากมายสำหรับไวยากรณ์โซ่ของ JQuery เช่น:
$ ('#div1'). แสดง (300) .html (p) .delay (3000) .Slideup (300) .remove ();
ดังนั้นฉันยังต้องการใช้ไวยากรณ์นี้เพื่อวาดภาพผืนผ้าใบ:
ctx.moveto (500,0) .lineto (500,500) .strokestyle ('#f00'). stroke ();
มีวิธีจำลองวัตถุบริบท 2D วัตถุนี้รองรับวิธีการบริบทดั้งเดิมทั้งหมดทั้งหมด แต่ยังรองรับวิธีการที่ถูกล่ามโซ่
อย่างไรก็ตามไม่สามารถมีรหัสมากเกินไปได้เนื่องจากไม่มีใครชอบที่จะใช้
ต่อไปนี้เป็นเซ็กเมนต์โค้ดที่สมบูรณ์ ฉันตั้งชื่อคลาสนี้ xtendcanvas (เริ่มต้นด้วย x อีกครั้ง):
// ให้ Canvas สนับสนุนโซ่ไวยากรณ์จากแสงสิบปี
~ function () {var pro = ['บันทึก', 'คืนค่า', 'สเกล', 'หมุน', 'แปล', 'แปลง', 'createLineargradient', 'createradialgradient', 'getlinedash', 'lineto', 'lineto' 'Beziercurveto', 'Arcto', 'rect', 'arc', 'เติม', 'stroke', 'clip', 'ispointinpath', 'measuretext', 'clearshadow', 'filltext', 'stroketext', 'strokerect' 'createimagedata', 'getimagedata', 'linewidth', 'strokestyle', 'globalalpha', 'Fillstyle', 'Font', 'Shadowoffsetx', 'Shadowoffsety', 'Shadowblur', 'Shadowcolor'
ฟังก์ชั่น xtendcanvas (Canvas) {
var ctx = canvas.getContext ('2d')
fn = function () {}
fnp = fn.prototype;
สำหรับ (var j = 0, p = pro [0]; p; p = pro [j ++]) {
fn.prototype [p] = function (p) {
return function () {
var args = array.prototype.slice.call (อาร์กิวเมนต์);
// console.log (args);
if (typeof ctx [p] == 'function') {
CTX [P] .Apply (CTX, ARGS);
} อื่น {
ctx [p] = args+'';
-
ส่งคืน FNP;
-
} (p);
-
คืน FN ใหม่;
-
window.xtendCanvas = xtendCanvas;
-
วิธีการใช้งานง่ายมาก ส่งผ่านวัตถุผืนผ้าใบและจะส่งคืนวัตถุที่คล้ายกับ context2d คุณสามารถใช้มันได้เช่นบริบททั่วไป 2D แต่ความแตกต่างคือมันรองรับไวยากรณ์โซ่:
var cvs = document.getElementById ('CVS');
var ctx = xtendCanvas (CVS);
ctx.moveto (500,0) .lineto (500,500) .strokestyle ('#f00'). stroke ();
วิธีนี้คุณสามารถวางการดำเนินการทั้งหมดในประโยคเดียวและคุณสามารถขัดจังหวะได้ตลอดเวลาทำสิ่งอื่น ๆ แล้วดำเนินการต่อ
รหัสนี้ไม่ได้เป็นการเพิ่มประสิทธิภาพของผ้าใบ แต่รองรับไวยากรณ์โซ่ แต่ข้อได้เปรียบคือมีรหัสเล็ก ๆ น้อย ๆ และสามารถฝังอยู่ในไลบรารี JS ใด ๆ ฉันหวังว่าจะได้รับคำแนะนำจากคุณที่นี่
มีบางสิ่งที่คุ้มค่าในการปรับปรุงรหัสและทุกคนสามารถปรับปรุงได้ด้วยตนเอง แต่ - ฉันไม่ลืมขุดบ่อน้ำเมื่อฉันวาดน้ำ ฉันหวังว่าทุกคนจะจำฉันได้ สิ่งที่สำคัญที่สุดคือความคิดใช่มั้ย นี่คือแนวคิด:
อย่างที่คุณเห็นส่วนที่ยาวที่สุดของรหัสคืออาร์เรย์โปรที่บันทึกชื่อวิธีและรหัสหลักนั้นสั้นมาก ทำไมฉันถึงต้องการสร้างอาร์เรย์เช่นนี้?
เดิมทีฉันต้องการสืบทอดวิธีการดั้งเดิมทั้งหมดโดยตรงจาก CanvasrenderingContext2D แต่เบราว์เซอร์แต่ละตัวผ่าน CanvasrenderingContext2D และผลลัพธ์ไม่สอดคล้องกัน หากฉันสืบทอดพวกเขาโดยตรงจากนั้นเมื่อคุณต้องการใช้วิธีการใน Chrome เพื่อดำเนินการมันจะมีการรายงานข้อผิดพลาด
ดังนั้นฉันเพิ่งแยกวิธีการทั่วไปที่ไม่มีวัตถุประสงค์และชื่อแอตทริบิวต์ใน CanvasrenderingContext2d ไม่มีทางฉันสามารถสร้างอาร์เรย์ที่คงที่เท่านั้น - ทุกคนสามารถตัดสินใจเพิ่มวิธีการของคุณได้
วิธีการและแอตทริบิวต์จะถูกสกัดจากนั้นวิธีการดั้งเดิมจะถูกเพิ่มเข้าไปในวัตถุใหม่ของฉัน ฉันสร้างฟังก์ชั่นว่างเปล่าที่เรียกว่า FN และวางวิธีการของฉัน
เนื่องจากองค์ประกอบเหล่านี้ในอาร์เรย์มีทั้งฟังก์ชั่นและคุณลักษณะฉันจึงตัดสินในวงว่าเป็นฟังก์ชั่นหรือไม่ หากเป็นฟังก์ชั่นมันจะถูกดำเนินการด้วยพารามิเตอร์ หากไม่ใช่ฟังก์ชั่น - มันจะต้องเป็นคุณสมบัติดังนั้นฉันจึงกำหนดพารามิเตอร์ให้กับคุณสมบัตินี้
ด้วยวิธีนี้เมื่อคุณพบการตั้งค่าแอตทริบิวต์ Canvas คุณไม่จำเป็นต้องขัดจังหวะลิงก์เพียงแค่ผ่านค่าแอตทริบิวต์เป็นพารามิเตอร์ตัวอย่างเช่น:
ctx.strokestyle ('#f00')
ในที่สุดกุญแจสำคัญคือการส่งคืน FN เคล็ดลับนี้ได้เรียนรู้จาก jQuery และเป็นกุญแจสำคัญในการรองรับไวยากรณ์โซ่
ย่อหน้านี้ใช้ฟังก์ชั่นที่ไม่ระบุชื่อการปิดต้นแบบและแปลกสำหรับลูปที่ฉันได้พูดคุยเกี่ยวกับบทความก่อนหน้านี้
ดูเหมือนจะค่อนข้างง่ายที่จะพูด แต่ฉันคิดเกี่ยวกับมันมานานโดยหวังว่ามันจะเป็นประโยชน์สำหรับทุกคน
ในระหว่างกระบวนการเขียนรหัสฉันพบว่า Chrome ทำได้ดีมาก มันมีสตริงของฟังก์ชั่นที่เริ่มต้นด้วยชุดเช่น SetStrokecolor, SetLineCap และฟังก์ชั่นอื่น ๆ โดยการส่งผ่านพารามิเตอร์ไปยังพวกเขามันสามารถแทนที่แอตทริบิวต์ที่เกี่ยวข้องเช่น strokestyle และ linecap กล่าวอีกนัยหนึ่งผืนผ้าใบของมันเต็มไปด้วยฟังก์ชั่นและไม่มีคุณสมบัติดังนั้นฉันไม่ต้องตัดสินว่ามันเป็นฟังก์ชั่นหรือแอตทริบิวต์ แต่ไม่มีสิ่งนั้นใน Firefox ดังนั้นฉันจึงสามารถใช้ความคิดก่อนหน้านี้ได้เท่านั้น
ฉันจะใส่สตริงของฟังก์ชั่นชุด :var bak = ['setTransform', 'setalpha', 'setCompositeOperation', 'setlineWidth', 'setlinecap', 'setlinejoin', 'setMiterlimit', 'setlinedash', 'setShadow', 'SetStrokecolor', 'SetFillColor'];
พวกเขาสามารถเข้าใจการใช้งานได้อย่างรวดเร็ว นอกจากนี้คุณยังสามารถเลือกอาร์เรย์ PRO บางตัวที่เพิ่มลงในรหัสก่อนหน้า
ในที่สุดฉันก็สงสัยว่าทำไมรหัสของฉันถึงไม่ถูกเน้น - - หากคุณเห็นจุดจบให้คำแนะนำและให้ฉันไร้สาระ