【第4章 图像与视频】4.4 离屏 canvas

文章目录

  • 前言
  • 为什么要使用 offscreenCanvas
  • 为什么要使用 OffscreenCanvas
  • 如何使用 OffscreenCanvas
    • 第一种使用方式
    • 第二种使用方式
  • 计算时长超过多长时间适合用Web Worker


前言

在 Canvas 开发中,我们经常需要处理复杂的图形和动画,这些操作可能会影响页面的性能和用户体验。为了解决这个问题,现代浏览器引入了 OffscreenCanvas 接口,它允许我们在后台线程(Web Workers)中进行画布操作,从而提高性能和响应速度。


为什么要使用 offscreenCanvas

OffscreenCanvas 是 HTML5 Canvas API 的扩展,它允许在独立的后台线程中执行画布操作,而不会阻塞主线程。这对于处理大型图像、复杂的绘图或者动画非常有用。


为什么要使用 OffscreenCanvas

传统的 Canvas 操作通常是在主线程中执行的,这可能会导致页面在复杂的绘图任务中出现卡顿或者延迟。使用 OffscreenCanvas 可以将这些操作移到后台线程中,这样可以避免阻塞主线程,提升整体的性能和响应速度。


如何使用 OffscreenCanvas

第一种使用方式

transferControlToOffscreen() 将控制转移到一个在主线程或者 web worker 的 OffscreenCanvas 对象上。并且在这个OffscreenCanvas上进行绘制的同时,也会在原始的canvas元素上进行绘制。

/* 主线程 */
const canvas = document.getElementById('mainCanvas')
const offscreen = canvas.transferControlToOffscreen()
const worker = new Worker('worker.js')// 将 OffscreenCanvas 传递给 Worker
worker.postMessage({ canvas: offscreen }, [offscreen])
/* worker线程 */
self.onmessage = function (event) {const offscreenCanvas = event.data.canvasconst ctx = offscreenCanvas.getContext('2d')// 绘制内容ctx.fillStyle = 'red'ctx.fillRect(50, 50, 200, 200)
}

第二种使用方式

/* 主线程 */
const canvas = document.getElementById('mainCanvas')
const ctx = canvas.getContext('2d')const worker = new Worker('./worker2.js')
worker.postMessage({ msg: 'init' })
worker.onmessage = function (e) {// 这里就接受到work 传来的离屏canvas位图ctx.drawImage(e.data.imageBitmap, 0, 0)
}ctx.arc(100, 75, 50, 0, 2 * Math.PI)
ctx.stroke()
/* worker线程 */
let offscreen, ctxfunction init() {offscreen = new OffscreenCanvas(512, 512)ctx = offscreen.getContext('2d')
}
// 绘制图形
function draw() {ctx.clearRect(0, 0, offscreen.width, offscreen.height)for (var i = 0; i < 10000; i++) {for (var j = 0; j < 1000; j++) {ctx.fillRect(i * 3, j * 3, 2, 2)}}const imageBitmap = offscreen.transferToImageBitmap()// 传送给主线程self.postMessage({ imageBitmap }, [imageBitmap])
}// 监听主线程发的信息
self.onmessage = function (e) {if (e.data.msg == 'init') {init()draw()}
}

计算时长超过多长时间适合用Web Worker

原则上,运算时间超过50ms会造成页面卡顿,属于Long task,这种情况就可以考虑使用Web Worker,但还要先考虑通信时长的问题,假如一个运算执行时长为100ms, 但是通信时长为300ms, 用了Web Worker可能会更慢。

计算的运算时长 - 通信时长 > 50ms,推荐使用Web Worker。

通信时长:新建一个web worker时, 浏览器会加载对应的worker.js资源,下图中的Time是这个 js 资源的加载时长。
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.pswp.cn/bicheng/83183.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Go语言事件总线EventBus本地事件总线系统的完整实现框架

在Go语言中&#xff0c;EventBus是一种非常有用的工具&#xff0c;它通过事件驱动的编程方式&#xff0c;帮助开发者实现组件之间的解耦&#xff0c;提高代码的可维护性和扩展性。 背景 软件架构的发展需求&#xff1a;随着软件系统的规模和复杂度不断增大&#xff0c;传统的紧…

Go语言接口:灵活多态的核心机制

引言 Go语言的接口系统是其​​面向对象编程​​的核心&#xff0c;它摒弃了传统语言的类继承体系&#xff0c;采用独特的​​隐式实现​​和​​鸭子类型​​设计。这种设计使得Go接口既灵活又强大&#xff0c;成为构建松耦合系统的关键工具。本文将深入剖析Go接口的实现机制…

DeviceNET转EtherCAT网关:医院药房自动化的智能升级神经中枢

在现代医院药房自动化系统中&#xff0c;高效、精准、可靠的设备通信是保障患者用药安全与效率的核心。当面临既有支持DeviceNET协议的传感器、执行器&#xff08;如药盒状态传感器、机械臂限位开关&#xff09;需接入先进EtherCAT高速实时网络时&#xff0c;JH-DVN-ECT疆鸿智能…

android实现使用RecyclerView详细

显示页面代码&#xff1a;activity_category_inventory.xml代码&#xff1a; <?xml version"1.0" encoding"utf-8"?> <LinearLayout xmlns:android"http://schemas.android.com/apk/res/android" xmlns:app"http://schemas.and…

【SpringBoot实战】优雅关闭服务

文章目录 一、什么是优雅关闭&#xff1f;二、优雅关闭的核心步骤三、SpringBoot优雅关闭实现四、关键注意事项1. 超时时间必须配置2. 信号支持局限性3. 特殊请求处理 五、底层实现原理六、总结 一、什么是优雅关闭&#xff1f; 优雅关闭&#xff08;Graceful Shutdown&#x…

C++哈希表:unordered系列容器详解

本节目标 1.unordered系列关联式容器 2.底层结构 3.模拟实现 4.哈希的应用 5.海量数据处理面试题 unordered系列关联式容器 在c98中&#xff0c;STL提供了底层为红黑树结构的一系列关联式容器&#xff0c;在查询时效率可以达到logN&#xff0c;即最差的情况下需要比较红…

java操作服务器文件(把解析过的文件迁移到历史文件夹地下)

第一步导出依赖 <dependency><groupId>org.apache.sshd</groupId><artifactId>sshd-core</artifactId><version>2.13.0</version></dependency> 第二步写代码 public void moveFile( List<HmAnalysisFiles> hmAnalys…

Oracle OCP认证的技术定位怎么样?

一、引言&#xff1a;Oracle OCP认证的技术定位​ Oracle Certified Professional&#xff08;OCP&#xff09;认证是数据库领域含金量最高的国际认证之一&#xff0c;其核心价值在于培养具备企业级数据库全生命周期管理能力的专业人才。随着数字化转型加速&#xff0c;OCP认证…

TK海外抢单源码/指定卡单

​ 抢单源码&#xff0c;有指定派单&#xff0c;打针&#xff0c;这套二改过充值跳转客服 前端vue 后端php 两端分离 可二开 可以指定卡第几单&#xff0c;金额多少&#xff0c; 前后端开源 PHP7.2 MySQL5.6 前端要www.域名&#xff0c;后端要admin.域名 前端直接静态 伪静…

远程线程注入

注入简单来说就是让别人的程序执行 你想要让他执行的dll #include<iostream> #include<Windows.h> using namespace std;char szBuffer[] "C:\\Users\\20622\\source\\repos\\Dll1\\Debug\\test.dll"; //dll路径void RemoteThreadInject(DWORD Pid,PCH…

【Java实战】集合排序方法与长度获取方法辨析(易懂版)

一、排序方法 1. 对List排序的两种方式 方式一Collections.sort() List<Integer> numbers Arrays.asList(3,1,4,2); Collections.sort(numbers); // 直接修改原list → [1,2,3,4]方式二&#xff1a;list.sort()&#xff08;Java8推荐&#xff09; List<String>…

企业级安全实践:SSL/TLS 加密与权限管理(一)

引言 ** 在数字化转型的浪潮中&#xff0c;企业对网络的依赖程度与日俱增&#xff0c;从日常办公到核心业务的开展&#xff0c;都离不开网络的支持。与此同时&#xff0c;网络安全问题也日益严峻&#xff0c;成为企业发展过程中不可忽视的重要挑战。 一旦企业遭遇网络安全事…

Java 大视界 -- Java 大数据在智能医疗影像数据压缩与传输优化中的技术应用(227)

&#x1f496;亲爱的朋友们&#xff0c;热烈欢迎来到 青云交的博客&#xff01;能与诸位在此相逢&#xff0c;我倍感荣幸。在这飞速更迭的时代&#xff0c;我们都渴望一方心灵净土&#xff0c;而 我的博客 正是这样温暖的所在。这里为你呈上趣味与实用兼具的知识&#xff0c;也…

Python编程基础(一) | 变量和简单数据类型

引言&#xff1a;很久没有写 Python 了&#xff0c;有一点生疏。这是学习《Python 编程&#xff1a;从入门到实践&#xff08;第3版&#xff09;》的课后练习记录&#xff0c;主要目的是快速回顾基础知识。 练习1&#xff1a; 简单消息 将一条消息赋给变量&#xff0c;并将其…

鸿蒙 HarmonyOS - SideBarContainer 组件自学指南

在日常开发中&#xff0c;如果你有类似「左侧导航 右侧内容」的布局需求&#xff0c;比如后台管理界面、文件管理器、设置页等&#xff0c;​​SideBarContainer​​ 是非常值得掌握的组件。它自带侧边栏和主内容区的分离机制&#xff0c;还支持折叠、拖拽、控制按钮和多种显示…

CppCon 2014 学习:Practical Functional Programming

这段内容是对**在 C 中使用函数式编程&#xff08;Functional Programming, FP&#xff09;**可以做什么的简要介绍&#xff0c;下面是逐条的翻译与理解&#xff1a; Introduction 简介 在 C 中使用函数式编程&#xff08;FP&#xff09;可以做什么&#xff1f; 1. 编写强大…

飞牛NAS+Docker技术搭建个人博客站:公网远程部署实战指南

文章目录 前言1. Docker下载源设置2. Docker下载WordPress3. Docker部署Mysql数据库4. WordPress 参数设置5. 飞牛云安装Cpolar工具6. 固定Cpolar公网地址7. 修改WordPress配置文件8. 公网域名访问WordPress总结 前言 在数字化浪潮中&#xff0c;传统网站搭建方式正面临前所未…

ComfyUI+阿里Wan2.1+内网穿透技术:本地AI视频生成系统搭建实战

文章目录 前言1.软件准备1.1 ComfyUI1.2 文本编码器1.3 VAE1.4 视频生成模型 2.整合配置3. 本地运行测试4. 公网使用Wan2.1模型生成视频4.1 创建远程连接公网地址 5. 固定远程访问公网地址总结 前言 各位技术爱好者&#xff0c;今天为您带来一组创新性的AI应用方案&#xff01…

n8n:技术团队的智能工作流自动化助手

在当前数字化时代,自动化已经成为提高效率和减轻人工工作负担的一大推动力。今天,我们要为大家介绍一款极具潜力的开源项目——n8n,它不仅拥有广泛的应用场景,还具备内置AI功能,能够完全满足技术团队的高效工作需求。n8n的出现,为技术团队提供了自由编程与快速自动化构建…

1,QT的编译教程

目录 整体流程: 1,新建project文件 2,编写源代码 3,打开QT的命令行窗口 4,生成工程文件(QT_demo.pro) 5,生成Make file 6,编译工程 7,运行编译好的可执行文件 整体流程: 1,新建project文件 新建文本文件,后缀改为.cpp 2,编写源代码