简体   繁体   中英

Advanced JavaScript/HTML5 canvases

I am learning about HTML5 (canvases) and advanced JavaScript (modules, prototypes, etc.) and would like to re-factor a basic snippet I have put together.

How can I reuse my function to work with multiple canvas elements on the same page? I found this post that describes the general idea I am hoping to achieve. However, I run into issues because I am calling my draw() method when I update an input on the page, which causes me to lose the context. Here is a snippet of what I have so far:

 var sliderModule = (function(win, doc) { win.onload = init; // canvas and context variables var canvas1, canvas2, canvas3; var context1, context2, context3; function init() { // draw the initial pattern drawPattern1(); drawPattern2(); drawPattern3(); } // called whenever the slider value changes function drawPattern1() { const canvas = document.getElementById('bullsEye1'); const context = canvas.getContext('2d'); canvas.width = 100; canvas.height = 100; const colors = ['#F00', '#00F']; const outerRadius = 50; let bandSize = doc.getElementById("bandWidth1").value; doc.getElementById("currentBandWidth1").innerHTML = bandSize; for ( let r = outerRadius, colorIndex = 0; r > 0; r -= bandSize, colorIndex = (colorIndex + 1) % colors.length ) { context.fillStyle = colors[colorIndex]; context.beginPath(); context.arc(canvas.width / 2, canvas.height / 2, r, 0, Math.PI * 2); context.closePath(); context.fill(); } } function drawPattern2() { const canvas = document.getElementById('bullsEye2'); const context = canvas.getContext('2d'); canvas.width = 100; canvas.height = 100; const colors = ['#F00', '#00F']; const outerRadius = 50; let bandSize = doc.getElementById("bandWidth2").value; doc.getElementById("currentBandWidth2").innerHTML = bandSize; for ( let r = outerRadius, colorIndex = 0; r > 0; r -= bandSize, colorIndex = (colorIndex + 1) % colors.length ) { context.fillStyle = colors[colorIndex]; context.beginPath(); context.arc(canvas.width / 2, canvas.height / 2, r, 0, Math.PI * 2); context.closePath(); context.fill(); } } function drawPattern3() { const canvas = document.getElementById('bullsEye3'); const context = canvas.getContext('2d'); canvas.width = 100; canvas.height = 100; const colors = ['#F00', '#00F']; const outerRadius = 50; let bandSize = doc.getElementById("bandWidth3").value; doc.getElementById("currentBandWidth3").innerHTML = bandSize; for ( let r = outerRadius, colorIndex = 0; r > 0; r -= bandSize, colorIndex = (colorIndex + 1) % colors.length ) { context.fillStyle = colors[colorIndex]; context.beginPath(); context.arc(canvas.width / 2, canvas.height / 2, r, 0, Math.PI * 2); context.closePath(); context.fill(); } } return { drawPattern1: drawPattern1, drawPattern2: drawPattern2, drawPattern3: drawPattern3 }; })(window, document); 
 main { width: 100%; } div { width: 30%; } #left { float: left; margin-left: 2%; } #middle { position: relative; left: 0px; right: 0px; margin: auto; } #right { float: right; margin-right: 2%; } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <!DOCTYPE html> <html> <title>Bulls Eye</title> <head> </head> <body> <main> <div id="left"> <canvas id="bullsEye1" style="border: 1px solid;"> </canvas><br> <label for="bandWidth1">BandWidth:</label> <input type="range" id="bandWidth1" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern1()"></input> <p>Current band width: <span id="currentBandWidth1"></span></p> </div> <div id="right"> <canvas id="bullsEye2" style="border: 1px solid;"></canvas><br> <label for="bandWidth2">BandWidth:</label> <input type="range" id="bandWidth2" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern2()"></input> <p>Current band width: <span id="currentBandWidth2"></span></p> </div> <div id="middle"> <canvas id="bullsEye3" style="border: 1px solid;"></canvas><br> <label for="bandWidth3">BandWidth:</label> <input type="range" id="bandWidth3" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern3()"></input> <p>Current band width: <span id="currentBandWidth3"></span></p> </div> <br style="clear:both;" /> </main> </html> 

您需要使用对象,使用您的函数创建一个类,然后实例化一个对象以使用它的函数。

I hope it helps you :

  var sliderModule = (function(win, doc) { win.onload = init; // canvas and context variables var canvas1, canvas2, canvas3; var context1, context2, context3; function init() { // draw the initial pattern drawPattern(1); drawPattern(2); drawPattern(3); } // called whenever the slider value changes function drawPattern(num) { const canvas = document.getElementById('bullsEye'+num); const context = canvas.getContext('2d'); canvas.width = 100; canvas.height = 100; const colors = ['#F00', '#00F']; const outerRadius = 50; let bandSize = doc.getElementById("bandWidth"+num).value; doc.getElementById("currentBandWidth"+num).innerHTML = bandSize; for ( let r = outerRadius, colorIndex = 0; r > 0; r -= bandSize, colorIndex = (colorIndex + 1) % colors.length ) { context.fillStyle = colors[colorIndex]; context.beginPath(); context.arc(canvas.width / 2, canvas.height / 2, r, 0, Math.PI * 2); context.closePath(); context.fill(); } } return { drawPattern }; })(window, document); 
 main { width: 100%; } div { width: 30%; } #left { float: left; margin-left: 2%; } #middle { position: relative; left: 0px; right: 0px; margin: auto; } #right { float: right; margin-right: 2%; } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <!DOCTYPE html> <html> <title>Bulls Eye</title> <head> </head> <body> <main> <div id="left"> <canvas id="bullsEye1" style="border: 1px solid;"> </canvas><br> <label for="bandWidth1">BandWidth:</label> <input type="range" id="bandWidth1" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern(1)"></input> <p>Current band width: <span id="currentBandWidth1"></span></p> </div> <div id="right"> <canvas id="bullsEye2" style="border: 1px solid;"></canvas><br> <label for="bandWidth2">BandWidth:</label> <input type="range" id="bandWidth2" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern(2)"></input> <p>Current band width: <span id="currentBandWidth2"></span></p> </div> <div id="middle"> <canvas id="bullsEye3" style="border: 1px solid;"></canvas><br> <label for="bandWidth3">BandWidth:</label> <input type="range" id="bandWidth3" min="5" max="50" step="5" value="25" oninput="sliderModule.drawPattern(3)"></input> <p>Current band width: <span id="currentBandWidth3"></span></p> </div> <br style="clear:both;" /> </main> </html> 

Is this homework you should be doing yourself? I won't rewrite so you'll get an A, but here's something to show get you going...

 var sliderModule = (function(win, doc) { win.onload = init; // canvas and context variables var canvas1, canvas2, canvas3; var context1, context2, context3; function init() { // draw the initial pattern draw('bullsEye1',doc.getElementById('bandWidth1').value, 'currentBandWidth1'); draw('bullsEye2',doc.getElementById('bandWidth2').value, 'currentBandWidth2'); draw('bullsEye3',doc.getElementById('bandWidth3').value, 'currentBandWidth3'); } function draw(can,val, outid){ const canvas=doc.getElementById(can); const context = canvas.getContext('2d'); const output=doc.getElementById(outid) canvas.width = 100; canvas.height = 100; const colors = ['#F00', '#00F']; const outerRadius = 50; let bandSize = val; output.innerHTML = bandSize; for ( let r = outerRadius, colorIndex = 0; r > 0; r -= bandSize, colorIndex = (colorIndex + 1) % colors.length ) { context.fillStyle = colors[colorIndex]; context.beginPath(); context.arc(canvas.width / 2, canvas.height / 2, r, 0, Math.PI * 2); context.closePath(); context.fill(); } } return { draw:draw }; })(window, document); 
 main { width: 100%; } div { width: 30%; } #left { float: left; margin-left: 2%; } #middle { position: relative; left: 0px; right: 0px; margin: auto; } #right { float: right; margin-right: 2%; } 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <!DOCTYPE html> <html> <title>Bulls Eye</title> <head> </head> <body> <main> <div id="left"> <canvas id="bullsEye1" style="border: 1px solid;"> </canvas><br> <label for="bandWidth1">BandWidth:</label> <input type="range" id="bandWidth1" min="5" max="50" step="5" value="25" oninput="sliderModule.draw('bullsEye1',this.value,'currentBandWidth1')"></input> <p>Current band width: <span id="currentBandWidth1"></span></p> </div> <div id="right"> <canvas id="bullsEye2" style="border: 1px solid;"></canvas><br> <label for="bandWidth2">BandWidth:</label> <input type="range" id="bandWidth2" min="5" max="50" step="5" value="25" oninput="sliderModule.draw('bullsEye2',this.value,'currentBandWidth2')"></input> <p>Current band width: <span id="currentBandWidth2"></span></p> </div> <div id="middle"> <canvas id="bullsEye3" style="border: 1px solid;"></canvas><br> <label for="bandWidth3">BandWidth:</label> <input type="range" id="bandWidth3" min="5" max="50" step="5" value="25" oninput="sliderModule.draw('bullsEye3',this.value,'currentBandWidth3')"></input> <p>Current band width: <span id="currentBandWidth3"></span></p> </div> <br style="clear:both;" /> </main> </html> 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM