Javascript 如何使用画布中的元素调整画布的大小? 背景资料
我目前正在做一个项目,我希望背景是一个空白的画布,球从墙上弹下来 到目前为止我一直在努力,但我遇到了一个问题。 每当我调整浏览器窗口的大小时,画布或其中的球都不会跟随。我不知道我做错了什么 代码Javascript 如何使用画布中的元素调整画布的大小? 背景资料,javascript,html,css,canvas,resize,Javascript,Html,Css,Canvas,Resize,我目前正在做一个项目,我希望背景是一个空白的画布,球从墙上弹下来 到目前为止我一直在努力,但我遇到了一个问题。 每当我调整浏览器窗口的大小时,画布或其中的球都不会跟随。我不知道我做错了什么 代码 const canvas=document.querySelector(“#响应画布”) canvas.width=window.innerWidth; canvas.height=window.innerHeight; 设c=canvas.getContext('2d'); 功能圆(x、y、dx、
const canvas=document.querySelector(“#响应画布”)
canvas.width=window.innerWidth;
canvas.height=window.innerHeight;
设c=canvas.getContext('2d');
功能圆(x、y、dx、dy、半径、颜色){
这个.x=x;
这个。y=y;
this.dx=dx;
this.dy=dy;
这个半径=半径;
这个颜色=颜色;
this.draw=函数(){
this.getNewColor=函数(){
让符号、色彩;
symbols=“0123456789ABCDEF”;
color=“#”;
for(设i=0;i<6;i++){
颜色+=符号[Math.floor(Math.random()*16)];
}
c、 strokeStyle=颜色;
c、 填充样式=颜色;
}
这个.getNewColor();
这个.x=x;
这个。y=y;
这个半径=半径;
//this.getNewColor().color=color;
c、 beginPath();
c、 圆弧(x,y,半径,0,Math.PI*2,假);
//c.strokeStyle=‘蓝色’;
c、 笔划();
//c、 填充();
}
this.update=函数(){
这个.x=x;
这个。y=y;
this.dx=dx;
this.dy=dy;
这个半径=半径;
如果(x+半径>内宽| | x-半径<0){
dx=-dx;
}
如果(y+半径>内高| | y-半径<0){
dy=-dy;
}
x+=dx;
y+=dy;
这个.draw();
}
}
设Circlear=[];
for(设i=0;i<23;i++){
设半径=50;
设x=Math.random()*(innerWidth-radius*2)+半径;
设y=Math.random()*(内部高度-半径*2)+半径;
设dx=(Math.random()-0.5);
设dy=(Math.random()-0.5);
圆推动(新的圆(x,y,dx,dy,半径));
};
函数animate(){
请求动画帧(动画);
c、 clearRect(0,0,innerWidth,innerHeight)
对于(变量i=0;i
*{
框大小:边框框;
保证金:0;
填充:0;
}
/*身体
*/
html,
身体{
宽度:100%;
身高:100%;
保证金:0;
}
您可以使用
ctx.scale(x,y)代码>
要按给定的因子缩放画布上的所有对象,X和Y分别在X和Y轴上缩放
您可能需要使用重置画布
ctx.resetTransform()
或ctx.setTransform(1,0,0,1,0,0)代码>
然后从0,0到canvas.width和canvas.height绘制背景
然后画所有的东西(所有的圆),最后将缩放设置为你想要的值。如果你想改变宽度和高度,你只需要在“{border box}”所在的CSS区域中添加宽度和高度
但是,如果您想使其中的图像不被拉伸,则需要使用上述注释方法访问画布中的特定高度
最好使用:
width:() => document.documentElement.clientWidth
首先必须修复冲突逻辑,然后可以根据需要安全地更改画布大小
始终完全解决冲突。
未解决的碰撞意味着您的sim卡处于不可能的状态(如球在墙上)。从那时起,以下状态的意义将减少
修理
球移出画布的原因是,如果球在画布外部,则不会将其移回画布
此外,当球击中侧面时改变球的方向时,也不能确保方向是正确的标志
// if the dx = 1 and x > innerWidth + 1000 then dx becomes -1
// Next tine x is still > innerWidth + 1000 and you flip the sign of dx again to 1,
// Then dx to -1 and so on. You never move the ball
if(x + radius > innerWidth || x - radius < 0) {
dx = -dx;
}
注意更改画布大小也会清除画布,这就是为什么在else
子句中会清除画布
复制粘贴演示
代码中有许多缺点。您可以将下面的代码段复制粘贴到代码笔中,或使用上面的信息以您的样式修改代码
const canvas = document.querySelector('#responsive-canvas')
canvas.width = innerWidth;
canvas.height = innerHeight;
// Set constants in one place so you can make changes quickly and easily
const DEFAULT_RADIUS = 50;
const MAX_SPEED = 5;
const CIRCLE_COUNT = 100;
Math.TAU = Math.PI * 2
// Use function to do repetitive code
Math.rand = (min, max) => Math.random() * (max - min) + min; //
function randomHexColor() {
return "#" + ((Math.random() * 0xFFFFFF | 0).toString(16).padStart(6,"0"));
}
// pulral names for arrays and variables that do not change should be constants
const circles = [];
const ctx = canvas.getContext('2d');
requestAnimationFrame(animate); // start frame renderer with a request, dont call it directly
function Circle( // using default params to set random values
radius = Math.rand(DEFAULT_RADIUS/4, DEFAULT_RADIUS), // radius must be first argument as its used to set random x, and y
x = Math.rand(radius, ctx.canvas.width - radius),
y = Math.rand(radius, ctx.canvas.height - radius),
dx = Math.rand(-MAX_SPEED, MAX_SPEED),
dy = Math.rand(-MAX_SPEED, MAX_SPEED),
colour = randomHexColor()
) {
this.x = x;
this.y = y;
this.dx = dx;
this.dy = dy;
this.radius = radius;
this.colour = colour;
}
// Define Circle functions as prototype outside the function Circle (runs faster)
Circle.prototype = {
draw() {
ctx.strokeStyle = ctx.fillStyle = this.colour;
ctx.beginPath();
ctx.arc(this.x, this.y, this.radius, 0, Math.TAU);
ctx.stroke();
},
update() {
this.x += this.dx;
this.y += this.dy;
if (this.x < this.radius) {
this.x = this.radius;
this.dx = Math.abs(this.dx);
}
if (this.y < this.radius) {
this.y = this.radius;
this.dy = Math.abs(this.dy);
}
if (this.x > ctx.canvas.width - this.radius) {
this.x = ctx.canvas.width - this.radius;
this.dx = -Math.abs(this.dx);
}
if (this.y > ctx.canvas.height - this.radius) {
this.y = ctx.canvas.height - this.radius;
this.dy = -Math.abs(this.dy);
}
}
};
for (let i = 0; i < CIRCLE_COUNT; i++) { circles.push(new Circle()) }
function animate () {
if (ctx.canvas.width !== innerWidth || ctx.canvas.height !== innerHeight) {
ctx.canvas.width = innerWidth;
ctx.canvas.height = innerHeight;
} else {
ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height)
}
// use for of loop (saves having to mess with index)
for (const circle of circles) {
circle.update(); // seperate update and draw
circle.draw()
}
requestAnimationFrame(animate);
}
const canvas=document.querySelector(“#响应画布”)
canvas.width=内部宽度;
canvas.height=内部高度;
//在一个位置设置常量,以便快速轻松地进行更改
常数默认值_半径=50;
const MAX_SPEED=5;
常数圆计数=100;
Math.TAU=Math.PI*2
//使用函数执行重复代码
Math.rand=(min,max)=>Math.random()*(max-min)+min;//
函数randomHexColor(){
返回“#”+((Math.random()*0xFFFFFF | 0).toString(16).padStart(6,0”);
}
//不改变的数组和变量的脉冲名称应该是常量
常数圆=[];
const ctx=canvas.getContext('2d');
请求动画帧(动画);//使用请求启动帧渲染器,不要直接调用它
函数圆(//使用默认参数设置随机值
radius=Math.rand(默认半径/4,默认半径),//radius必须是第一个参数,因为它用于设置随机x和y
x=数学.rand(半径,ctx.canvas.width-半径),
y=数学.rand(半径,ctx.canvas.height-半径),
dx=数学随机数(-MAX_SPEED,MAX_SPEED),
dy=数学.rand(-MAX\u SPEED,MAX\u SPEED),
颜色=随机六边形颜色()
) {
这个.x=x;
这个。y=y;
this.dx=dx;
this.dy=dy;
这个半径=半径;
这个颜色=颜色;
}
//将圆函数定义为函数圆外的原型(运行速度更快)
圆圈。原型={
画(){
ctx.strokeStyle=ctx.fillStyle=this.color;
ctx.beginPath();
弧(this.x,this.y,this.radius,0,Math.TAU);
ctx.stroke();
},
更新(){
this.x+=this.dx;
this.y+=this.dy;
if(此.x<此半径){
这个.x=这个半径;
this.dx=Math.abs(this.dx);
}
if(此.y<此半径){
this.y=this.radius;
this.dy=Math.abs(this.dy);
}
if(this.x>ctx.canvas.width-this.radius){
this.x=ctx.canvas.width-t
function animate () {
if (ctx.canvas.width !== innerWidth || ctx.canvas.height !== innerHeight) {
ctx.canvas.width = innerWidth;
ctx.canvas.height = innerHeight;
} else {
ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height)
}
// ... do stuff
requestAnimationFrame(animate);
}
const canvas = document.querySelector('#responsive-canvas')
canvas.width = innerWidth;
canvas.height = innerHeight;
// Set constants in one place so you can make changes quickly and easily
const DEFAULT_RADIUS = 50;
const MAX_SPEED = 5;
const CIRCLE_COUNT = 100;
Math.TAU = Math.PI * 2
// Use function to do repetitive code
Math.rand = (min, max) => Math.random() * (max - min) + min; //
function randomHexColor() {
return "#" + ((Math.random() * 0xFFFFFF | 0).toString(16).padStart(6,"0"));
}
// pulral names for arrays and variables that do not change should be constants
const circles = [];
const ctx = canvas.getContext('2d');
requestAnimationFrame(animate); // start frame renderer with a request, dont call it directly
function Circle( // using default params to set random values
radius = Math.rand(DEFAULT_RADIUS/4, DEFAULT_RADIUS), // radius must be first argument as its used to set random x, and y
x = Math.rand(radius, ctx.canvas.width - radius),
y = Math.rand(radius, ctx.canvas.height - radius),
dx = Math.rand(-MAX_SPEED, MAX_SPEED),
dy = Math.rand(-MAX_SPEED, MAX_SPEED),
colour = randomHexColor()
) {
this.x = x;
this.y = y;
this.dx = dx;
this.dy = dy;
this.radius = radius;
this.colour = colour;
}
// Define Circle functions as prototype outside the function Circle (runs faster)
Circle.prototype = {
draw() {
ctx.strokeStyle = ctx.fillStyle = this.colour;
ctx.beginPath();
ctx.arc(this.x, this.y, this.radius, 0, Math.TAU);
ctx.stroke();
},
update() {
this.x += this.dx;
this.y += this.dy;
if (this.x < this.radius) {
this.x = this.radius;
this.dx = Math.abs(this.dx);
}
if (this.y < this.radius) {
this.y = this.radius;
this.dy = Math.abs(this.dy);
}
if (this.x > ctx.canvas.width - this.radius) {
this.x = ctx.canvas.width - this.radius;
this.dx = -Math.abs(this.dx);
}
if (this.y > ctx.canvas.height - this.radius) {
this.y = ctx.canvas.height - this.radius;
this.dy = -Math.abs(this.dy);
}
}
};
for (let i = 0; i < CIRCLE_COUNT; i++) { circles.push(new Circle()) }
function animate () {
if (ctx.canvas.width !== innerWidth || ctx.canvas.height !== innerHeight) {
ctx.canvas.width = innerWidth;
ctx.canvas.height = innerHeight;
} else {
ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height)
}
// use for of loop (saves having to mess with index)
for (const circle of circles) {
circle.update(); // seperate update and draw
circle.draw()
}
requestAnimationFrame(animate);
}