易经网站开发公司,网站知识介绍,百度推广登录入口官网网址,哪个网站专注做微信模板本文简介
戴尬猴#xff0c;我是德育处主任 欢迎来到《物理世界的互动之旅#xff1a;Matter.js入门指南》。
本文将带您探索 Matter.js#xff0c;一个强大而易于使用的 JavaScript 物理引擎库。
我将介绍 Matter.js 的基本概念#xff0c;包括引擎、世界、物体和约束等…本文简介
戴尬猴我是德育处主任 欢迎来到《物理世界的互动之旅Matter.js入门指南》。
本文将带您探索 Matter.js一个强大而易于使用的 JavaScript 物理引擎库。
我将介绍 Matter.js 的基本概念包括引擎、世界、物体和约束等。
本文还提供丰富的代码示例帮助各位工友更好地理解如何使用 Matter.js 创建令人惊叹的物理场景先画个饼吧。 本文是我的学习笔记和个人理解在翻译和部分概念的理解上可能存在一点偏差如果发现本文有什么错漏的地方请自行调节呼吸频率。我懒得改 本文前1000字都在讲一些基础概念你觉得无聊可以先看后面的内容看完再回来过一遍基础概念就行了。 Matter.js是什么
在现实世界中物理是无处不在的。从行星和恒星的运动到电子的运动物理定律描述了我们周围几乎所有事物的运动和相互作用。
在计算机科学中物理引擎是一种模拟物理现象的软件程序。它们通常用于创建物理游戏、虚拟现实和仿真等应用程序。物理引擎可以模拟各种现象例如重力、碰撞和摩擦等。物理引擎通常是非常复杂的因为它必须模拟现实世界中的各种效果。
在Web浏览器想模拟真实世界的物理现象其实也有很多库2D方面有 Matter.js、P2.js 等3D方面有 Cannon.js、ammo.js 等。
而本文是将 Matter.js 的所以我在这只会说 Matter.js 的好话。
Matter.js 是一个非常强大的 JavaScript 2D物理引擎它能够帮助你在Web应用程序中实现逼真的物理效果。
Matter.js 提供了可定制的碰撞检测、重力、力学效应和运动控制等功能让你可以快速、简单地构建交互式的物理模拟。无论是模拟游戏、建筑模型还是实验室实验Matter.js 都可以满足你的需求。
Matter.js官网 ⚡️ 基础概念
在学习 Matter.js 前我们需要了解一些基础概念。由于本文是入门篇所以我只介绍常用的基础概念。
模块名称说明引擎Engine引擎 Engine 是 Matter.js 的核心组件用于管理物理世界中的所有对象、计算物体的运动和相互作用。用来模拟真实环境的。渲染器Render渲染器 Render 用于将物理世界中的对象可视化。意思就是它能将物体渲染到屏幕上。复合体Composite是包含多个刚体和约束的容器它们可以作为单个物理对象进行操作。刚体Body表示具有物理属性的实体如形状、质量和速度等。刚体可以是各种形状例如矩形、圆形、多边形等。约束Constraint用于约束刚体的相对运动例如让两个刚体之间的距离保持不变、限制旋转等。循环模块 (Runner)Runner 用于管理和控制物理引擎的主循环。
我用自己的话粗略总结一下但我感觉我总结得不太正确工友们有更好的理解可以到评论区留句话没什么好说的也可以写句“到此一游”。
引擎 Engine 可以模拟我们真实世界的一些物理法则。
刚体 Body 可以粗略理解为现实世界中的物体比如一个球、一张凳子。
复合体 Composite 是一个容器可以将多个物体整合起来让它们产生联系。比如创建了一个球刚体然后用 Composite 将球和引擎连接起来这样球就会收到物理规则的影响了。
渲染器 Render 就是个眼睛的作用它能帮助我们看到 Matter.js 创建出来的世界。
约束 Constraint 就是约束比如一个跷跷板由一根很长的模板和一个底座组成底座固定在地面木板的中间锁定在底座上面这个锁定动作就是约束。正因为有这个约束所以跷跷板才能成为跷跷板。
循环模块 Runner 可以粗略的理解为现实世界中的时间。如果没有循环模块页面的所有元素都是定格的。你可以理解为现实世界没有时间的话整个世界都会静止。 以上就是我觉得 Matter.js 入门阶段需要了解的一些基础概念。
除此之外其实还需要掌握一些基础物理概念比如知道什么是碰撞什么事摩擦力、阻力、重力等。这类概念会在接下来的案例中讲解。 安装Matter.js
在开始使用 Matter.js 之前需要确保在项目中安装了它。
可以通过 npm 在命令行中安装也可以通过 cdn 的方式引入。
CDN
在 github 上下载并引入到你的项目即可 github地址️⚡️。
你也可以 在这找到指定版本⚡️。
如果你不想把 Matter.js 下载到本地也可以在 bootcdn 搜索 Matter.js 并引入。
script srchttps://cdn.bootcdn.net/ajax/libs/matter-js/0.19.0/matter.js/script NPM
Matter.js 的 npm 地址⚡️
npm install matter-js 起步第一个 Matter.js 应用
这个例子是 Matter.js 官方的起步案例通过这个例子你可以快速理解到前面讲的 Matter.js 基础概念。
先看效果。 从这个动图我们可以看出
这个世界有2个正方形和一个地面底部的长方形。正方形出现在空中然后做自由落体运动。左边的正方形碰到地面后出现了一点回弹。右边的正方形落地前砸到左边的正方形阻止了左边正方形的回弹并且自己往右滚动了一下。 要使用 Matter.js 实现上面的效果需要做以下几步
创建容器。引入 Matter.js。创建引擎。创建渲染器绑定画布上。创建正方形和地面并且让地面元素保持静止。将创建好的元素添加到“世界”里没错你就是创世神。最后为这个世界添加“时间”属性让它可以运转起来Matter.Runner。 上面所说的步骤还需要对应基础概念的表格配合理解。
转换成代码
!-- 1. 创建容器 --
div idc/div!-- 2. 引入 matter --
script src../js/matter.js/script
scriptconst Engine Matter.Engineconst Render Matter.Renderconst Bodies Matter.Bodiesconst Composite Matter.Compositeconst Runner Matter.Runner// 3. 创建引擎let engine Engine.create()// 4. 创建渲染器并将引擎连接到画布上let render Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎})// 5-1. 创建两个正方形let boxA Bodies.rectangle(400, 200, 80, 80)let boxB Bodies.rectangle(450, 50, 80, 80)// 5-2. 创建地面将isStatic设为true表示物体静止let ground Bodies.rectangle(400, 610, 810, 60, { isStatic: true })// 6. 将所有物体添加到世界中Composite.add(engine.world, [boxA, boxB, ground])// 7. 执行渲染操作Render.run(render)// 8. 创建运行方法var runner Runner.create()// 9. 运行渲染器Runner.run(runner, engine)
/script
我们使用 Engine 创建引擎Matter.js 的这个引擎默认帮我们定义好这个世界的基本运行规律。
然后我们使用 Render 创建渲染器这个渲染器可以将引擎和页面绑定在一起。
Bodies 是刚体的意思用它来创建物体的本例就创建了2个正方形和1个地面。
Composite 就是前面讲到的复合体它可以让世界和物体产生关联也就是说可以将物体添加到世界中。
最后通过 Render 让这个世界有了“时间”的概念物体也会根据世界的规则在时间的运行下产生运动。
上面的代码也许你还不理解每个方法的具体使用方式但结合我前面的分析我相信你已经大概了解 Matter.js “创造世界”的基本流程也许听完我的解析后更懵了。 渲染器 在前面的例子中我们使用 Matter.Render.create 将画布和页面元素绑定在一起。此时默认的画布尺寸是 800px * 600px。
// 省略部分代码let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎
})
其实它还支持其他属性配置可以设置画布宽高等信息。 设置画布宽高
使用 Matter.Render.create 时还能传入 options 参数。
// 省略部分代码let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400}
}) 关闭线框模式
Matter.js 创建的形状默认是线框模式的你可以手动关闭这个模式Matter.js 就会自动帮你填充一些颜色到基础图形上。
关闭线框模式的方式是将 wireframes 设置为 false。 // 省略部分代码let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {wireframes: false}
})
其他代码包括创建图形的代码都和“起步第一个 Matter.js 应用”一样。
options 还支持其他的配置有兴趣的工友可以看看 文档⚡️。 图形元素
Matter.js 支持多种基础图形包括矩形、圆形、三角形、梯形、多边形等。这些图形还支持配置颜色、摩擦力等属性。 基础图形
先说说基础。
在 Matter.js 文档中你会留意到创建物体使用的是 Body 或者 Bodies翻译成中文就是“刚体”。
在物理世界中刚体是指在运动中和受力作用后形状和大小不变而且内部各点的相对位置不变的物体。
在 Matter.js 中刚体(Body) 是一种物理对象它具有质量、位置、速度、加速度和形状等属性可以被添加到物理世界中并受到物理引擎的模拟。例如矩形和圆形。 在入门阶段我们可以使用 Bodies 创建基础图形。 矩形 rectangle
前面我们已经使用过矩形了。在这小节粗略讲解一下创建矩形的一些必传参数。
创建矩形使用的是 Matter.Bodies.rectangle(x, y, width, height) 方法。
参数 x 和 y 是矩形中心点的坐标width 和 height 是矩形的宽高。
如果创建一个 80*80 的矩形希望它的左上角在 (0, 0) 的位置那 x 和 y 分别设置成 width 和 height 的一半。 // 省略部分代码// 创建矩形
let rect Matter.Bodies.rectangle(40, 40, 80, 80)// 将矩形添加到世界里
Matter.Composite.add(engine.world, rect) 圆形 circle
创建圆形的方法是 Matter.Bodies.circle(x, y, radius)。
x 和 y 是圆心坐标 radius 是半径。 // 省略部分代码// 创建圆形
let circle Matter.Bodies.circle(40, 40, 40)// 将矩形添加到世界里
Matter.Composite.add(engine.world, circle) 梯形 trapezoid
创建梯形的方法是 Matter.Bodies.trapezoid(x, y, width, height, slope)。
x 和 y 定义了梯形的中心点坐标width 和 height 是梯形的宽高slope 是斜率。
当斜率 slope 大于0小于1时梯形的上边小于下边。当斜率 slope 等于0时梯形的上边和下边相等看起来就是一个矩形。当斜率 slope 小于0时上边大于下边。当斜率 slope 大于等于1时就会呈现出三角形的样子。 // 省略部分代码let trapezoid Matter.Bodies.trapezoid(200, 200, 80, 80, 0.5) 三角形 trapezoid
创建三角形的方法和梯形一样只需将斜率 slope 设置成大于等于1的值即可。 // 省略部分代码let triangle Matter.Bodies.trapezoid(200, 200, 80, 80, 1) // 省略部分代码let triangle Matter.Bodies.trapezoid(200, 200, 80, 80, 2) 正多边形 polygon
Matter.js 使用 Matter.Bodies.polygon(x, y, sides, radius) 创建正多边形。
注意是正多边形
参数 x 和 y 是多边形中心点的坐标sides 可以设置多边形的边的数量radius 设置多边形的半径。 // 省略部分代码let polygon Matter.Bodies.polygon(200, 200, 7, 40) 自定义多边形
使用Matter.js创建自定义多边形可以使用 Matter.Bodies.fromVertices(x, y, vertexSets) 方法。
x 和 y 定义多变西女中心的坐标vertexSets 定义多边形顶点集合。
// 省略部分代码// 定义顶点
const vertices [{ x: 0, y: 0 },{ x: 50, y: 0 },{ x: 50, y: 50 },{ x: 25, y: 75 },{ x: 0, y: 50 }
]// 自定义多边形
const trapezoid Matter.Bodies.fromVertices(100, 100, vertices)// 将自定义多边形添加到世界里
Matter.Composite.add(engine.world, trapezoid) 图形状态和属性配置
前面使用 Matter.bodies 创建的图形时可以在最后加多一个对象参数这个参数可以配置图形的状态和属性。
填充色 render.fillStyle
如果您想为Matter.js中的形状添加填充色可以在 render 属性中配置 fillStyle 属性的值。例如要将圆形的填充色设置为橙色可以使用以下代码 // 省略部分代码// 创建渲染器
let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400,wireframes: false, // 关闭线框模式}
})// 省略部分代码// 创建矩形
let rect Matter.Bodies.rectangle(200, 200, 80, 80, {render: {fillStyle: orange}
})
需要注意的是使用填充色功能时要关掉渲染器的线框模式。 边框颜色和线宽 render.strokeStyle render.lineWidth
使用 render.strokeStyle 可以设置边框颜色使用 render.lineWidth 可以设置边框的宽度。 // 省略部分代码// 创建渲染器
let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400,wireframes: false, // 关闭线框模式}
})// 省略部分代码// 创建矩形
let rect Matter.Bodies.rectangle(200, 200, 80, 80, {render: {strokeStyle: #3490de, // 设置边框颜色lineWidth: 20 // 设置边框宽度}
}) render.fillStyle 和 render.strokeStyle 都支持 颜色关键字、#开头的十六进制、rgb、rgba等 颜色值。
但不支持 0x 开头的十六进制颜色。 贴图 render.sprite
一个优秀的前端必须懂得贴图Matter.js 也提供了贴图功能。
只需要配置一下 render.sprite 即可。
我用矩形举例。 // 省略部分代码// 创建矩形
let rect Matter.Bodies.rectangle(200, 200, 200, 200, {render: {sprite: { // 使用精灵texture: ./monkey.jpg // 图片纹理位置}}
})// 将所有物体添加到世界中
Matter.Composite.add(engine.world, rect) 缩放贴图 scale
如果需要设置贴图的宽高还可以修改 xScale 和 yScale 属性。
但这两个属性只会影响贴图的尺寸图形的真实尺寸并不会受到影响。 // 省略部分代码let rect Matter.Bodies.rectangle(200, 200, 200, 200, {render: {sprite: {texture: ./monkey.jpg,xScale: 0.5,yScale: 1.5}}
}) 贴图偏移 offset
可以设置精灵图的 xOffset 和 yOffset。
// 省略部分代码let rect Matter.Bodies.rectangle(200, 200, 200, 200, {render: {sprite: {texture: ./monkey.jpg,xOffset: 0.5,yOffset: 1}}
}) 不透明度 render.opacity
opacity 的取值范围是 0 ~ 1 。
// 省略部分代码let rect Matter.Bodies.rectangle(80, 100, 80, 80, {render: {opacity: 0.5}
}) 元素可见性 render.visible
当 render.visible 为 false 时元素会隐藏反之元素就显示。render.visible 的默认值是 true。
// 省略部分代码let rect Matter.Bodies.rectangle(80, 100, 80, 80, {render: {visible: false // 隐藏元素}
}) 旋转 angle
angle 属性可以设置元素的旋转弧度。
为了方便理解我还是更习惯用“角度”这个单位。
弧度转角度可以用这个公式
Math.PI / 180 * 角度 // 省略部分代码// 矩形
let rect Matter.Bodies.rectangle(80, 100, 80, 80, {angle: Math.PI / 180 * 45
})
上面这段代码创建了一个矩形并且让他旋转45度。结合上面的公式应该比较容易理解。 空气阻力 frictionAir
前面简单的介绍了一下基础图形怎么填充颜色、怎么使用贴图这些都前菜。
Matter.js 真正的亮点是物理引擎。
在前面有讲到要让物理引擎动起来需要用到下面这段代码
// 省略部分代码// 创建运行方法
let runner Runner.create()// 运行渲染器
Runner.run(runner, engine)
如果忘了可以看看前面的 “起步第一个 Matter.js 应用” 这章节。 先介绍一下空气阻力。
我们知道在地球上当一个物体做自由落体运动时会受到空气阻力的影响。
Matter.js 提供了 frictionAir 这个属性可以让我们给指定物体配置具体的空气阻力。 // 省略部分代码let rectA Matter.Bodies.rectangle(80, 100, 80, 80, {frictionAir: 0.1 // 设置空气阻力
})let rectB Matter.Bodies.rectangle(200, 100, 80, 80, {frictionAir: 0.5 // 设置空气阻力
})let rectC Matter.Bodies.rectangle(320, 100, 80, 80, {frictionAir: 1 // 设置空气阻力
})// 地面
let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}
})// 6. 将所有物体添加到世界中
Matter.Composite.add(engine.world, [rectA, rectB, rectC, ground])
从左往右的立方体中我分别给它们配置的空气阻力时 0.1、0.5 和 1 数值越大空气阻力就越大自由落体的速度也就越慢。 回弹力 restitution
前面的例子中创建的物体都是没有弹力的它们掉到地面时不会回弹。
如果希望物体有弹性可以配置它的 restitution 。 // 省略部分代码let rectA Matter.Bodies.rectangle(80, 100, 80, 80, {restitution: 0 // 设置弹力
})let rectB Matter.Bodies.rectangle(200, 100, 80, 80, {restitution: 1 // 设置弹力
})let rectC Matter.Bodies.rectangle(320, 100, 80, 80, {restitution: 1.2 // 设置弹力
})// 地面
let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}
})// 6. 将所有物体添加到世界中
Matter.Composite.add(engine.world, [rectA, rectB, rectC, ground])
在 Matter.js 中物体的回弹力正常取值范围是 0 ~ 1。其中0表示碰撞后不反弹1表示碰撞后完全反弹。
如果反弹系数大于1就意味着碰撞后物体的能量增加这是不符合物理规律的。
但如果你在做游戏在处理游戏角色的某些技能时也可以让回弹力超出1。毕竟这是你的世界。 质量 mass
在初中物理课上我们知道质量越大惯性越大。也就是说物体更难改变它的状态静止或运动状态。当施加力或者撞击物体时质量越大的物体会更难加速或者减速需要更长的时间来达到相同的速度或者停止。而质量越小的物体则更容易改变它的状态可以更快地加速或减速。
在 Matter.js 中碰撞响应的计算是基于物体的质量和速度等参数的。比如当两个物体相撞时质量越大的物体会对速度的改变产生更小的影响而质量越小的物体会对速度的改变产生更大的影响。
举个例子我在画布中创建3个质量不同的矩形左边的矩形的质量最小右边的最大。在回弹力相同的情况下质量越小回弹的程度就越大。 // 省略部分代码// 矩形A
let rectA Matter.Bodies.rectangle(80, 100, 80, 80, {restitution: 1,mass: 0.1
})// 矩形B
let rectB Matter.Bodies.rectangle(200, 100, 80, 80, {restitution: 1,mass: 5
})// 矩形C
let rectC Matter.Bodies.rectangle(320, 100, 80, 80, {restitution: 1,mass: 10
})// 地面
let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}
})Matter.Composite.add(engine.world, [rectA, rectB, rectC, ground]) 静止 isStatic
前面几个例子中空中的几个矩形都会往下掉但地面却不会。
这是因为地面元素将 isStatic 设置为 true 了所以元素就不会动了。
// 省略部分代码let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}
}) 关于基础元素的其他属性配置可以看看 『Matter.js官方文档的 Body 内容』。 堆 stack
在 Matter.js 中允许你将多个物体组合在一起以便更方便地管理和操作它们。这个方法叫做“堆 stack”。
你可以将多个矩形放在一个 stack 中然后一起移动它们或者一起旋转它们而不需要分别操作每个矩形。这可以大大简化代码并提高代码的可维护性。
要创建一个 stack可以使用 Matter.Composites.stack 方法。
用法Matter.Composites.stack(xx, yy, columns, rows, columnGap, rowGap, callback)
其中的参数作用
xx 和 yy: stack 的起始位置。columns 和 rows: stack 的列数和行数。columnGap: 相邻两个物体之间的列间隔。rowGap: 相邻两个物体之间的行间隔。callback: 回调函数通常用于生成 stack 中的每个物体。
举个完整例子 div idc/divscript src../js/matter.js/script
scriptlet engine Matter.Engine.create()let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400,wireframes: false,}})// 堆// 起始位置是 (20, 20)一共6列3行列间距10行间距20let stack Matter.Composites.stack(20, 20, 6, 3, 10, 20, function (x, y) {return Matter.Bodies.rectangle(x, y, 30, 30)})// 地面let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}})// 将堆和地面添加到世界里Matter.Composite.add(engine.world, [stack, ground])Matter.Render.run(render)let runner Matter.Runner.create()Matter.Runner.run(runner, engine)
/script
这个例子我只给堆和地面添加了注释方便工友们寻找这段主要的代码。
在使用 stack 时最后的用来创建物体的回调函数有 x 和 y 参数这两个参数是 Matter.js 提供的它会根据前面几个参数 (xx, yy, columns, rows, columnGap, rowGap) 来计算每次 x 和 y 的值是多少而这个 x 和 y 通常用来定义图形元素的位置。 stack 更大的意义是方便我们集中管理堆中的元素比如在上面这个例子中要让所有立方体自身旋转30度可以直接在回调函数里写上。 // 省略部分代码let stack Matter.Composites.stack(20, 20, 6, 3, 10, 20, function (x, y) {return Matter.Bodies.rectangle(x, y, 30, 30, {angle: Math.PI / 180 * 30, // 旋转30度restitution: 0.5 // 添加一点回弹力})
})
在这个例子中我还给每个矩形增加了一点回弹力让矩形在落地散开后的动画看上去更符合真实世界的逻辑。 除了能够方便地给每个矩形都添加属性外你还可以给整个堆进行调整。
比如整体旋转30度这个效果和上面的例子不一样。 // 省略部分代码let stack Matter.Composites.stack(20, 20, 6, 3, 10, 20, function (x, y) {return Matter.Bodies.rectangle(x, y, 30, 30, {restitution: 0.5 // 添加一点回弹力})
})// 整个堆旋转30度
Matter.Composite.rotate(stack, Math.PI / 180 * 30, { x: 0, y: 200 }) 约束 Constraint
在 Matter.js 里约束 Constraint 可以理解为将2个物体绑在一起。
生活中常见的例子跷跷板。 不好意思放错图了下面这张才对 一个简单的跷跷板分为2部分横着的板和底座。
把这两部分绑定在一起就形成跷跷板。
在 Matter.js 中要实现这个功能用到的就是约束 Constraint。
先简单体验一下再说用法。 div idc/divscript src../js/matter.js/script
scriptlet engine Matter.Engine.create()let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400,wireframes: false,}})// 板子A红色let rectA Matter.Bodies.rectangle(200, 330, 20, 100, {isStatic: true,render: {fillStyle: #f00},collisionFilter: {group: -1}})// 板子B蓝色let rectB Matter.Bodies.rectangle(200, 330, 200, 20, {render: {fillStyle: #00f},collisionFilter: {group: -1}})// 创建旋转约束let rotateConstraint Matter.Constraint.create({bodyA: rectA,bodyB: rectB,length: 0})// 矩形的堆let stack Matter.Composites.stack(20, 30, 4, 3, 10, 20, function (x, y) {return Matter.Bodies.rectangle(x, y, 40, 20)})// 圆形的堆let stack_circle Matter.Composites.stack(220, 60, 3, 4, 10, 20, function (x, y) {return Matter.Bodies.circle(x, y, 16)})// 地面let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}})// 将 蓝色和红色矩形、约束、矩形堆、圆形堆、地面 都添加到世界里Matter.Composite.add(engine.world, [rectA, rectB, rotateConstraint, stack, stack_circle, ground])Matter.Render.run(render)let runner Matter.Runner.create()Matter.Runner.run(runner, engine)
/script
在上面的例子中我创建了1个跷跷板由红色和蓝色矩形组合而成1堆小矩形1堆小圆形1个地面。
小矩形堆和小圆形堆都做自由落体。
跷跷板使用了 Matter.Constraint.create 做约束处理其中的参数 bodyA 和 bodyB 用来指定要约束的两个物体。length 表示约束的长度设置为0的话他们之间的约束点就没有任何挪动的空间这就和跷跷板的原理一样了。 Matter.Constraint.create(options) 的配置对象包含以下属性
options约束的选项。options.bodyA类型为 Matter.Body约束连接的第一个物体。options.pointA类型为 Matter.Vector约束连接的第一个物体上的点。options.bodyB类型为 Matter.Body约束连接的第二个物体。options.pointB类型为 Matter.Vector约束连接的第二个物体上的点。options.length类型为 number约束的初始长度。options.stiffness类型为 number约束的刚度系数。options.damping类型为 number约束的阻尼系数。options.render约束的渲染选项。options.render.visible类型为 boolean表示约束是否可见默认为 true。options.render.lineWidth类型为 number表示约束线条的宽度。options.render.strokeStyle类型为 string表示约束线条的颜色。 鼠标约束
这里所指的耗子约束是指给鼠标添加操作物体的功能。
要实现拖拽物体的功能需要以下几个步骤
创建鼠标实例 Matter.Mouse.create。给鼠标添加约束 Matter.MouseConstraint.create。将鼠标约束添加到物理引擎中。 div idc/divscript src../js/matter.js/script
scriptlet engine Matter.Engine.create()let render Matter.Render.create({element: document.getElementById(c), // 绑定页面元素engine: engine, // 绑定引擎options: {width: 400,height: 400,wireframes: false,}})let box Matter.Bodies.rectangle(80, 100, 80, 80, {restitution: 0.3,mass: 0.1})let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}})// 创建鼠标实例let mouse Matter.Mouse.create(render.canvas)// 给鼠标添加约束let mouseConstraint Matter.MouseConstraint.create(engine, {mouse: mouse,constraint: {stiffness: 0.2,render: {visible: false // 默认为 true会显示鼠标拖拽轨迹}}})// 将鼠标约束添加到物理引擎中Matter.Composite.add(engine.world, [box, ground, mouseConstraint]);Matter.Render.run(render)let runner Matter.Runner.create()Matter.Runner.run(runner, engine)
/script 事件监听
在 Matter.js 中可以使用 Events.on 方法来监听各种事件包括鼠标事件、碰撞事件等等。 常用鼠标事件
例如这样监听鼠标的各种事件随便举点例子
// 省略部分代码// 创建一个 Mouse 实例
let mouse Matter.Mouse.create(render.canvas)let mouseConstraint Matter.MouseConstraint.create(engine, {mouse: mouse
})// 监听鼠标事件// 监听鼠标按下事件
Matter.Events.on(mouseConstraint, mousedown, function(event) {console.log(按下)
})// 监听鼠标移动事件
Matter.Events.on(mouseConstraint, mousemove, function(event) {console.log(移动)
})// 监听鼠标抬起事件
Matter.Events.on(mouseConstraint, mouseup, function(event) {console.log(抬起)
})// 监听鼠标拖拽刚体 - 开始拖拽
Matter.Events.on(mouseConstraint, startdrag, function(event) {console.log(开始拖拽)
})// 监听鼠标拖拽刚体 - 结束拖拽
Matter.Events.on(mouseConstraint, enddrag, function(event) {console.log(结束拖拽)
})Matter.Composite.add(engine.world, mouseConstraint) 监听碰撞
在 Matter.js 中用 Matter.Events.on 去监听 collisionStart 事件就能知道物体的碰撞。
除了 collisionStart 外还有其他监听周期。
collisionStart当两个物体开始碰撞时触发。collisionActive当两个物体持续碰撞时触发。collisionEnd当两个物体停止碰撞时触发。 我用 collisionStart 举例 // 省略部分代码// 创建一个矩形
var box Matter.Bodies.rectangle(200, 100, 80, 80, {restitution: 1
})// 地面
let ground Matter.Bodies.rectangle(200, 390, 400, 20, {isStatic: true,render: {fillStyle: #cccccc}
})// 添加刚体到引擎中
Matter.Composite.add(engine.world, [box, ground]);// 监听碰撞事件
Matter.Events.on(engine, collisionStart, function(event) {const pairs event.pairspairs.forEach(pair {console.log(pair)})
})
上面这个例子中我给 box 设置了回弹力它首次落地后回弹了2次首次落地加2次回弹一共就触发了3次碰撞所以在控制台输出了3次碰撞的结果。
其中pairs 是指一对正在碰撞的物体。当两个物体相互碰撞时它们就被组成为一个 pair 对象。
我们可以通过 event.pairs 属性来访问有关碰撞的更多信息。 代码仓库
点击下面的链接可以获取到本文所有完整demo仓库的代码还会不定期更新
⭐ Matter.js 案例仓库 推荐阅读
《眨个眼就学会了Pixi.js》
《P5.js 光速入门》
《Fabric.js从入门到膨胀》 点赞 关注 收藏 学会了 代码仓库