{"id":16195,"date":"2022-10-14T14:42:42","date_gmt":"2022-10-14T09:12:42","guid":{"rendered":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/"},"modified":"2022-10-14T14:42:42","modified_gmt":"2022-10-14T09:12:42","slug":"solved-why-does-the-canvas-have-a-black-background","status":"publish","type":"post","link":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/","title":{"rendered":"[Solved] Why does the canvas have a black background?"},"content":{"rendered":"<p> [ad_1]<br \/>\n<\/p>\n<div id=\"answer-71674102\" class=\"answer js-answer accepted-answer js-accepted-answer\" data-answerid=\"71674102\" data-parentid=\"71645601\" data-score=\"1\" data-position-on-page=\"1\" data-highest-scored=\"1\" data-question-has-accepted-highest-score=\"1\" itemprop=\"acceptedAnswer\" itemscope itemtype=\"https:\/\/schema.org\/Answer\">\n<div class=\"post-layout\">\n<div class=\"votecell post-layout--left\"><\/div>\n<div class=\"answercell post-layout--right\">\n<div class=\"s-prose js-post-body\" itemprop=\"text\">\n<p>One solution is to use many layers, which will be responsible of the overall fading.<\/p>\n<p>So at each frame, you create a new layer, and you decrease the opacity of all the previous ones. When that opacity is below a certain threshold, you remove it from the list.<br \/>\nThen you change your <code>draw()<\/code> methods to register the drawing commands in these layers instead of making the context draw directly. The layer will be responsible of setting the correct alpha (based on its own opacity and the one of the item to be drawn), and it will draw all the items from its frame.<\/p>\n<p>Basically these layers will be still of the current frame, but instead of storing the pixels data, we only store the drawing commands. This is quite easy in your situation since you have a rather limited number of drawing settings (only color, alpha, x, and y), but someone else may need a more complex API.<\/p>\n<p>Anyway, here is a messy rewrite as a proof-of-concept:<\/p>\n<\/p>\n<div class=\"snippet\" data-lang=\"js\" data-hide=\"false\" data-console=\"true\" data-babel=\"false\">\n<div class=\"snippet-code\">\n<pre class=\"snippet-code-js lang-js prettyprint-override\"><code>class Layer {\n  constructor(ctx) {\n    this.ctx = ctx;\n    this.commands = [];\n    this.alpha = 1;\n  }\n  update(delta) {\n    this.alpha *= 1 - (0.1 * delta);\n    return this.alpha &lt; 0.1;\n  }\n  draw() {\n    this.commands.forEach(([color, alpha, x, y, width, height]) =&gt; {\n      this.ctx.fillStyle = color;\n      this.ctx.globalAlpha = this.alpha * alpha;\n      this.ctx.fillRect(x, y, width, height);\n    });\n  }\n}\nclass Particle {\n  constructor(x, y, col) {\n    this.x = x;\n    this.y = y;\n    this.col = col;\n    this.vel = randomVec(2);\n    this.lifetime = 0;\n  }\n\n  update(delta) {\n    delta = 1;\n    this.x += this.vel.x;\n    this.y += this.vel.y;\n    this.vel.y += 0.02 * delta;\n    this.vel.x *= 1 - (delta * 0.01);\n    this.vel.y *= 1 - (delta * 0.01);\n    this.lifetime += delta;\n    return this.lifetime &gt; 80;\n  }\n\n  draw() {\n    const color = this.col;\n    const alpha = Math.max(1 - this.lifetime \/ 80, 0);\n    const x = this.x;\n    const y = this.y;\n    const rad = 2;\n    currentLayer.commands.push([color, alpha, x, y, rad, rad]);\n  }\n}\n\nclass Firework {\n  constructor(x) {\n    this.x = x;\n    this.y = height;\n    this.isBlown = false;\n    this.col = randomCol();\n  }\n\n  update(delta) {\n    this.y -= 3 * delta;\n    if (this.y &lt; 350 - Math.sqrt(Math.random() * 500) * 40) {\n      this.isBlown = true;\n      for (let i = 0; i &lt; 60; i++) {\n        particles.push(new Particle(this.x, this.y, this.col))\n      }\n    }\n    return this.isBlown;\n  }\n\n  draw() {\n    const color = this.col;\n    const alpha = 1;\n    const x = this.x;\n    const y = this.y;\n    const rad = 2;\n    currentLayer.commands.push([color, alpha, x, y, rad, rad]);\n  }\n}\n\nconst canvas = document.querySelector(\"canvas\");\nlet width, height, currentLayer;\nconst layers = [];\nconst fireworks = [];\nconst particles = [];\nsetSize(canvas);\nconst ctx = canvas.getContext(\"2d\");\nfireworks.push(new Firework(Math.random() * (width - 200) + 100));\n\nwindow.addEventListener(\"resize\", windowResized);\ndocument.addEventListener(\"click\", onClick);\n\nlet lastTime = document.timeline?.currentTime || performance.now();\nrequestAnimationFrame(loop);\n\nfunction loop(time) {\n  \/\/ values were defined with a 60FPS base\n  \/\/ we now use rAF and thus need a delta time\n  \/\/ to honor the same expected speed on all devices\n  const delta = (time - lastTime) \/ (1000 \/ 60);\n  lastTime = time;\n  ctx.globalAlpha = 1;\n  ctx.clearRect(0, 0, width, height);\n  currentLayer = new Layer(ctx);\n  layers.push(currentLayer);\n\n  const ended = [];\n  fireworks.forEach((firework, index) =&gt; {\n    const done = firework.update(delta);\n    if (done) {\n      ended.push(index);\n    }\n    firework.draw();\n  });\n  \/\/ remove all ended, for last to first\n  ended.reverse().forEach((index) =&gt; {\n    fireworks.splice(index, 1);\n  });\n  ended.length = 0;\n\n  particles.forEach((particle, index) =&gt; {\n    const done = particle.update(delta);\n    particle.draw();\n    if (done) {\n      ended.push(index);\n    }\n  });\n\n  ended.reverse().forEach((index) =&gt; {\n    particles.splice(index, 1);\n  });\n  ended.length = 0;\n\n  layers.forEach((layer, index) =&gt; {\n    const done = layer.update(delta);\n    if (done) {\n      ended.push(index);\n    }\n    layer.draw();\n  });\n\n  ended.reverse().forEach((index) =&gt; {\n    layers.splice(index, 1);\n  });\n\n  if (Math.random() &lt; 1 \/ 60) {\n\n    fireworks.push(new Firework(Math.random() * (width - 200) + 100));\n  }\n  requestAnimationFrame(loop);\n}\n\nfunction randomCol() {\n  var letter=\"0123456789ABCDEF\";\n  var nums = [];\n\n  for (var i = 0; i &lt; 3; i++) {\n    nums[i] = Math.floor(Math.random() * 256);\n  }\n\n  let brightest = 0;\n  for (var i = 0; i &lt; 3; i++) {\n    if (brightest &lt; nums[i]) brightest = nums[i];\n  }\n\n  brightest \/= 255;\n  for (var i = 0; i &lt; 3; i++) {\n    nums[i] \/= brightest;\n  }\n\n  let color = \"#\";\n  for (var i = 0; i &lt; 3; i++) {\n    color += letter[Math.floor(nums[i] \/ 16)];\n    color += letter[Math.floor(nums[i] % 16)];\n  }\n  return color;\n}\n\nfunction randomVec(max) {\n  let dir = Math.random() * Math.PI * 2;\n  let spd = Math.random() * max;\n  return {\n    x: Math.cos(dir) * spd,\n    y: Math.sin(dir) * spd\n  };\n}\n\nfunction setSize(canv) {\n  canv.style.width = (innerWidth) + \"px\";\n  canv.style.height = (innerHeight) + \"px\";\n  width = innerWidth;\n  height = innerHeight;\n\n  canv.width = innerWidth * window.devicePixelRatio;\n  canv.height = innerHeight * window.devicePixelRatio;\n  canvas.getContext(\"2d\").scale(window.devicePixelRatio, window.devicePixelRatio);\n}\n\nfunction onClick(e) {\n  fireworks.push(new Firework(e.clientX));\n}\n\nfunction windowResized() {\n  setSize(canvas);\n}<\/code><\/pre>\n<pre class=\"snippet-code-css lang-css prettyprint-override\"><code>body{margin:0;\/* checkered effect from https:\/\/stackoverflow.com\/a\/51054396\/3702797 *\/\n  --tint:rgba(255,255,255,0.9);background-image:linear-gradient(to right,var(--tint),var(--tint)),linear-gradient(to right,black 50%,white 50%),linear-gradient(to bottom,black 50%,white 50%);background-blend-mode:normal,difference,normal;background-size:2em 2em;\n}\ncanvas{display: block}<\/code><\/pre>\n<pre class=\"snippet-code-html lang-html prettyprint-override\"><code>&lt;canvas&gt;&lt;\/canvas&gt;<\/code><\/pre>\n<\/div>\n<\/div><\/div>\n<div class=\"mt24\"><\/div>\n<\/div>\n<p>            <span class=\"d-none\" itemprop=\"commentCount\">0<\/span> <\/p><\/div>\n<\/div>\n<p>[ad_2]<\/p>\n<p>solved Why does the canvas have a black background? <\/p>\n","protected":false},"excerpt":{"rendered":"<p>[ad_1] One solution is to use many layers, which will be responsible of the overall fading. So at each frame, you create a new layer, and you decrease the opacity of all the previous ones. When that opacity is below a certain threshold, you remove it from the list. Then you change your draw() methods &#8230; <a title=\"[Solved] Why does the canvas have a black background?\" class=\"read-more\" href=\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\" aria-label=\"More on [Solved] Why does the canvas have a black background?\">Read more<\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[320],"tags":[464,346,896,333],"class_list":["post-16195","post","type-post","status-publish","format-standard","hentry","category-solved","tag-css","tag-html","tag-html5-canvas","tag-javascript"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v26.5 - https:\/\/yoast.com\/wordpress\/plugins\/seo\/ -->\n<title>[Solved] Why does the canvas have a black background? - JassWeb<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"[Solved] Why does the canvas have a black background? - JassWeb\" \/>\n<meta property=\"og:description\" content=\"[ad_1] One solution is to use many layers, which will be responsible of the overall fading. So at each frame, you create a new layer, and you decrease the opacity of all the previous ones. When that opacity is below a certain threshold, you remove it from the list. Then you change your draw() methods ... Read more\" \/>\n<meta property=\"og:url\" content=\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\" \/>\n<meta property=\"og:site_name\" content=\"JassWeb\" \/>\n<meta property=\"article:published_time\" content=\"2022-10-14T09:12:42+00:00\" \/>\n<meta name=\"author\" content=\"Kirat\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"Kirat\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"4 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#article\",\"isPartOf\":{\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\"},\"author\":{\"name\":\"Kirat\",\"@id\":\"https:\/\/jassweb.com\/solved\/#\/schema\/person\/65c9c7b7958150c0dc8371fa35dd7c31\"},\"headline\":\"[Solved] Why does the canvas have a black background?\",\"datePublished\":\"2022-10-14T09:12:42+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\"},\"wordCount\":186,\"publisher\":{\"@id\":\"https:\/\/jassweb.com\/solved\/#organization\"},\"keywords\":[\"css\",\"html\",\"html5-canvas\",\"javascript\"],\"articleSection\":[\"Solved\"],\"inLanguage\":\"en-US\"},{\"@type\":\"WebPage\",\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\",\"url\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\",\"name\":\"[Solved] Why does the canvas have a black background? - JassWeb\",\"isPartOf\":{\"@id\":\"https:\/\/jassweb.com\/solved\/#website\"},\"datePublished\":\"2022-10-14T09:12:42+00:00\",\"breadcrumb\":{\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/jassweb.com\/solved\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"[Solved] Why does the canvas have a black background?\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/jassweb.com\/solved\/#website\",\"url\":\"https:\/\/jassweb.com\/solved\/\",\"name\":\"JassWeb\",\"description\":\"Build High-quality Websites\",\"publisher\":{\"@id\":\"https:\/\/jassweb.com\/solved\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/jassweb.com\/solved\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\/\/jassweb.com\/solved\/#organization\",\"name\":\"Jass Web\",\"url\":\"https:\/\/jassweb.com\/solved\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/jassweb.com\/solved\/#\/schema\/logo\/image\/\",\"url\":\"https:\/\/jassweb.com\/wp-content\/uploads\/2021\/02\/jass-website-logo-1.png\",\"contentUrl\":\"https:\/\/jassweb.com\/wp-content\/uploads\/2021\/02\/jass-website-logo-1.png\",\"width\":693,\"height\":132,\"caption\":\"Jass Web\"},\"image\":{\"@id\":\"https:\/\/jassweb.com\/solved\/#\/schema\/logo\/image\/\"}},{\"@type\":\"Person\",\"@id\":\"https:\/\/jassweb.com\/solved\/#\/schema\/person\/65c9c7b7958150c0dc8371fa35dd7c31\",\"name\":\"Kirat\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/jassweb.com\/solved\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/jassweb.com\/solved\/wp-content\/litespeed\/avatar\/1261af3c9451399fa1336d28b98ea3bb.jpg?ver=1775193939\",\"contentUrl\":\"https:\/\/jassweb.com\/solved\/wp-content\/litespeed\/avatar\/1261af3c9451399fa1336d28b98ea3bb.jpg?ver=1775193939\",\"caption\":\"Kirat\"},\"sameAs\":[\"http:\/\/jassweb.com\"],\"url\":\"https:\/\/jassweb.com\/solved\/author\/jaspritsinghghumangmail-com\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"[Solved] Why does the canvas have a black background? - JassWeb","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/","og_locale":"en_US","og_type":"article","og_title":"[Solved] Why does the canvas have a black background? - JassWeb","og_description":"[ad_1] One solution is to use many layers, which will be responsible of the overall fading. So at each frame, you create a new layer, and you decrease the opacity of all the previous ones. When that opacity is below a certain threshold, you remove it from the list. Then you change your draw() methods ... Read more","og_url":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/","og_site_name":"JassWeb","article_published_time":"2022-10-14T09:12:42+00:00","author":"Kirat","twitter_card":"summary_large_image","twitter_misc":{"Written by":"Kirat","Est. reading time":"4 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#article","isPartOf":{"@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/"},"author":{"name":"Kirat","@id":"https:\/\/jassweb.com\/solved\/#\/schema\/person\/65c9c7b7958150c0dc8371fa35dd7c31"},"headline":"[Solved] Why does the canvas have a black background?","datePublished":"2022-10-14T09:12:42+00:00","mainEntityOfPage":{"@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/"},"wordCount":186,"publisher":{"@id":"https:\/\/jassweb.com\/solved\/#organization"},"keywords":["css","html","html5-canvas","javascript"],"articleSection":["Solved"],"inLanguage":"en-US"},{"@type":"WebPage","@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/","url":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/","name":"[Solved] Why does the canvas have a black background? - JassWeb","isPartOf":{"@id":"https:\/\/jassweb.com\/solved\/#website"},"datePublished":"2022-10-14T09:12:42+00:00","breadcrumb":{"@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/jassweb.com\/solved\/solved-why-does-the-canvas-have-a-black-background\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/jassweb.com\/solved\/"},{"@type":"ListItem","position":2,"name":"[Solved] Why does the canvas have a black background?"}]},{"@type":"WebSite","@id":"https:\/\/jassweb.com\/solved\/#website","url":"https:\/\/jassweb.com\/solved\/","name":"JassWeb","description":"Build High-quality Websites","publisher":{"@id":"https:\/\/jassweb.com\/solved\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/jassweb.com\/solved\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/jassweb.com\/solved\/#organization","name":"Jass Web","url":"https:\/\/jassweb.com\/solved\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/jassweb.com\/solved\/#\/schema\/logo\/image\/","url":"https:\/\/jassweb.com\/wp-content\/uploads\/2021\/02\/jass-website-logo-1.png","contentUrl":"https:\/\/jassweb.com\/wp-content\/uploads\/2021\/02\/jass-website-logo-1.png","width":693,"height":132,"caption":"Jass Web"},"image":{"@id":"https:\/\/jassweb.com\/solved\/#\/schema\/logo\/image\/"}},{"@type":"Person","@id":"https:\/\/jassweb.com\/solved\/#\/schema\/person\/65c9c7b7958150c0dc8371fa35dd7c31","name":"Kirat","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/jassweb.com\/solved\/#\/schema\/person\/image\/","url":"https:\/\/jassweb.com\/solved\/wp-content\/litespeed\/avatar\/1261af3c9451399fa1336d28b98ea3bb.jpg?ver=1775193939","contentUrl":"https:\/\/jassweb.com\/solved\/wp-content\/litespeed\/avatar\/1261af3c9451399fa1336d28b98ea3bb.jpg?ver=1775193939","caption":"Kirat"},"sameAs":["http:\/\/jassweb.com"],"url":"https:\/\/jassweb.com\/solved\/author\/jaspritsinghghumangmail-com\/"}]}},"_links":{"self":[{"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/posts\/16195","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/comments?post=16195"}],"version-history":[{"count":0,"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/posts\/16195\/revisions"}],"wp:attachment":[{"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/media?parent=16195"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/categories?post=16195"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/jassweb.com\/solved\/wp-json\/wp\/v2\/tags?post=16195"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}