电脑做系统ppt下载网站,wordpress站点语言,东莞网站建设dgjcwl,延庆网站建设师我们的目标是渐变#xff01;渐变#xff01; 首先了解#xff0c;渐变分为线性渐变和径向渐变#xff0c;线性渐变可以是从左上角到右下角的渐变#xff0c;径向渐变是从中心向外的渐变。 JavaScript中实现渐变可以使用addColorStop的方法#xff0c;例如创建一个线性渐…我们的目标是渐变渐变 首先了解渐变分为线性渐变和径向渐变线性渐变可以是从左上角到右下角的渐变径向渐变是从中心向外的渐变。 JavaScript中实现渐变可以使用addColorStop的方法例如创建一个线性渐变的代码为
// 创建线性渐变
var linearGradient ctx.createLinearGradient(0, 0, 200, 0);
linearGradient.addColorStop(0, green);
linearGradient.addColorStop(1, white);// 应用渐变到矩形
ctx.fillStyle linearGradient;
ctx.fillRect(10, 10, 180, 80); 我们使用createLinearGradient(x1, y1, x2, y2)创建一个线性渐变。参数定义了渐变的开始和结束位置。 径向渐变也是类似的
// 创建径向渐变
var radialGradient ctx.createRadialGradient(100, 50, 10, 100, 50, 50);
radialGradient.addColorStop(0, red);
radialGradient.addColorStop(0.5, yellow);
radialGradient.addColorStop(1, green);// 应用渐变到矩形
ctx.fillStyle radialGradient;
ctx.fillRect(10, 10, 180, 80); 使用createRadialGradient(x1, y1, r1, x2, y2, r2)创建一个径向渐变。参数定义了内外圆的位置和半径。 接下去我希望区分填充渐变和描边渐变并且把这些代码写在一个函数里。创建drawCircle函数包括circle和isFill参数传入一个圆如果isFill为true则填充否则描边。
function drawCircle(circle, isFill) {var canvas document.getElementById(myCanvas);var ctx canvas.getContext(2d);// 创建径向渐变var radialGradient ctx.createRadialGradient(circle.x, circle.y, 0, circle.x, circle.y, circle.radius);radialGradient.addColorStop(0, red);radialGradient.addColorStop(0.5, yellow);radialGradient.addColorStop(1, green);if (isFill) {// 应用渐变填充ctx.fillStyle radialGradient;ctx.beginPath();ctx.arc(circle.x, circle.y, circle.radius, 0, Math.PI * 2);ctx.fill();} else {// 应用渐变描边ctx.strokeStyle radialGradient;ctx.lineWidth 10; // 可以根据需要调整线宽ctx.beginPath();ctx.arc(circle.x, circle.y, circle.radius, 0, Math.PI * 2);ctx.stroke();}
}// 圆的参数
var circle {x: 100,y: 100,radius: 50
};// 画一个填充的圆
drawCircle(circle, true);// 画一个描边的圆
// drawCircle(circle, false); 不过这个代码只实现了径向渐变有兴趣可以在这里停下来自己实现一下填充渐变。完成的代码如下
function drawCircle(circle, isFill, gradientType) {var canvas document.getElementById(myCanvas);var ctx canvas.getContext(2d);// 根据渐变类型创建渐变var gradient;if (gradientType linear) {// 创建线性渐变gradient ctx.createLinearGradient(circle.x, circle.y - circle.radius, circle.x circle.radius, circle.y circle.radius);gradient.addColorStop(0, red);gradient.addColorStop(1, green);} else if (gradientType radial) {// 创建径向渐变gradient ctx.createRadialGradient(circle.x, circle.y, 0, circle.x, circle.y, circle.radius);gradient.addColorStop(0, red);gradient.addColorStop(0.5, yellow);gradient.addColorStop(1, green);}if (isFill) {// 应用渐变填充ctx.fillStyle gradient;} else {// 应用渐变描边ctx.strokeStyle gradient;ctx.lineWidth 10; // 可以根据需要调整线宽}ctx.beginPath();ctx.arc(circle.x, circle.y, circle.radius, 0, Math.PI * 2);if (isFill) {ctx.fill();} else {ctx.stroke();}
}// 圆的参数
var circle {x: 100,y: 100,radius: 50
};// 画一个填充的线性渐变圆
drawCircle(circle, true, linear);// 画一个描边的径向渐变圆
// drawCircle(circle, false, radial);
拆分函数: 此时我们发现这个drawCircle函数已经很大了为了项目的可拓展性和可维护性我们应该进行一下区分。
function createLinearGradient(ctx, circle) {return ctx.createLinearGradient(0, 0, circle.x * 2, circle.y * 2);
}function createRadialGradient(ctx, circle) {return ctx.createRadialGradient(circle.x, circle.y, 0, circle.x, circle.y, circle.radius);
}function applyGradient(ctx, gradient, isFill) {if (isFill) {ctx.fillStyle gradient;} else {ctx.strokeStyle gradient;ctx.lineWidth 10; // 可以根据需要调整线宽}
}function drawCircleWithGradient(ctx, circle, isFill, gradient) {ctx.beginPath();ctx.arc(circle.x, circle.y, circle.radius, 0, Math.PI * 2);if (isFill) {ctx.fill();} else {ctx.stroke();}
}function drawCircle(circle, isFill, gradientType) {var canvas document.getElementById(myCanvas);var ctx canvas.getContext(2d);var gradient;if (gradientType linear) {gradient createLinearGradient(ctx, circle);gradient.addColorStop(0, red);gradient.addColorStop(1, green);} else if (gradientType radial) {gradient createRadialGradient(ctx, circle);gradient.addColorStop(0, red);gradient.addColorStop(0.5, yellow);gradient.addColorStop(1, green);}applyGradient(ctx, gradient, isFill);drawCircleWithGradient(ctx, circle, isFill, gradient);
}// 圆的参数
var circle {x: 200,y: 200,radius: 100
};// 画一个填充的线性渐变圆
drawCircle(circle, true, linear);// 画一个描边的径向渐变圆
// drawCircle(circle, false, radial);
拆分为四个函数 createLinearGradient: 创建线性渐变。 createRadialGradient: 创建径向渐变。 applyGradient: 应用渐变到填充或描边。 drawCircleWithGradient: 使用给定的渐变绘制圆。 drawCircle 函数: 根据传入的 gradientType 参数调用相应的函数创建渐变。
代码的拓展 上面我们已经初步实现了一个圆的渐变但是也许还可以传入正方形矩形三角形甚至是更多的类型 首先需要来实现这几种类型
// 绘制圆形
function drawCircle(ctx, x, y, radius, isFill) {ctx.beginPath();ctx.arc(x, y, radius, 0, Math.PI * 2);ctx.fill();ctx.stroke();
}// 绘制矩形
function drawRect(ctx, x, y, width, height, isFill) {ctx.beginPath();ctx.rect(x, y, width, height);ctx.fill();ctx.stroke();
}// 绘制三角形
function drawTriangle(ctx, x1, y1, x2, y2, x3, y3, isFill) {ctx.beginPath();ctx.moveTo(x1, y1);ctx.lineTo(x2, y2);ctx.lineTo(x3, y3);ctx.closePath();ctx.fill();ctx.stroke();
} 绘制的时候就要根据形状来选择分支。我们创建函数drawShape
// 绘制形状
function drawShape(ctx, shape, isFill) {let gradient;switch (shape.type) {case circle:gradient createRadialGradient(ctx, shape.x, shape.y, shape.radius);applyGradient(ctx, gradient, isFill);drawCircle(ctx, shape.x, shape.y, shape.radius, isFill);break;case rect:gradient createLinearGradient(ctx, 0, 0, shape.width, shape.height);applyGradient(ctx, gradient, isFill);drawRect(ctx, shape.x, shape.y, shape.width, shape.height, isFill);break;case triangle:gradient createLinearGradient(ctx, shape.x1, shape.y1, shape.x3, shape.y3);applyGradient(ctx, gradient, isFill);drawTriangle(ctx, shape.x1, shape.y1, shape.x2, shape.y2, shape.x3, shape.y3, isFill);break;// 可以添加更多形状}
} 布豪发现圆形的渐变似乎有问题我们来修改一下并且我们发现js文件已经太大了我们来拆分一下下面给出一个完整案例
!DOCTYPE html
html langzh-CN
headmeta charsetUTF-8meta nameviewport contentwidthdevice-width, initial-scale1.0titleCanvas 绘图示例/title!-- 引用外部CSS --link relstylesheet hrefstyles.css
/head
bodydiv classcontainercanvas idmyCanvas width600 height600您的浏览器不支持 HTML5 Canvas 标签。/canvas/div!-- 引用外部JavaScript文件 --script srcjs/gradients.js/scriptscript srcjs/shapes.js/scriptscript srcjs/main.js/script
/body
/html/* styles.css */body {margin: 0;padding: 0;font-family: Arial, sans-serif;background-color: #f0f0f0;
}.container {display: flex;justify-content: center;align-items: center;height: 100vh;
}canvas {border: 2px solid #000;background-color: #fff;box-shadow: 0 4px 8px rgba(0, 0, 0, 0.2);
}// gradients.js// 创建线性渐变
function createLinearGradient(ctx, x1, y1, x2, y2) {const gradient ctx.createLinearGradient(x1, y1, x2, y2);gradient.addColorStop(0, red);gradient.addColorStop(1, green);return gradient;
}// 创建径向渐变
function createRadialGradient(ctx, x, y, r) {const gradient ctx.createRadialGradient(x, y, 0, x, y, r);gradient.addColorStop(0, red);gradient.addColorStop(0.5, yellow);gradient.addColorStop(1, green);return gradient;
}// shapes.js// 应用渐变
function applyGradient(ctx, gradient, isFill) {if (isFill) {ctx.fillStyle gradient;} else {ctx.strokeStyle gradient;ctx.lineWidth 5; // 可以根据需要调整线宽}
}// 绘制圆形
function drawCircle(ctx, x, y, radius, isFill) {ctx.beginPath();ctx.arc(x, y, radius, 0, Math.PI * 2);if (isFill) {ctx.fill();} else {ctx.stroke();}
}// 绘制矩形
function drawRect(ctx, x, y, width, height, isFill) {ctx.beginPath();ctx.rect(x, y, width, height);if (isFill) {ctx.fill();} else {ctx.stroke();}
}// 绘制三角形
function drawTriangle(ctx, x1, y1, x2, y2, x3, y3, isFill) {ctx.beginPath();ctx.moveTo(x1, y1);ctx.lineTo(x2, y2);ctx.lineTo(x3, y3);ctx.closePath();if (isFill) {ctx.fill();} else {ctx.stroke();}
}// 绘制形状
function drawShape(ctx, shape, isFill) {let gradient;switch (shape.type) {case circle:gradient createRadialGradient(ctx, shape.x, shape.y, shape.radius);applyGradient(ctx, gradient, isFill);drawCircle(ctx, shape.x, shape.y, shape.radius, isFill);break;case rect:gradient createLinearGradient(ctx, shape.x, shape.y, shape.x shape.width, shape.y shape.height);applyGradient(ctx, gradient, isFill);drawRect(ctx, shape.x, shape.y, shape.width, shape.height, isFill);break;case triangle:gradient createLinearGradient(ctx, shape.x1, shape.y1, shape.x3, shape.y3);applyGradient(ctx, gradient, isFill);drawTriangle(ctx, shape.x1, shape.y1, shape.x2, shape.y2, shape.x3, shape.y3, isFill);break;// 可以添加更多形状default:console.warn(未知的形状类型: ${shape.type});}
}// main.js// 确保所有依赖的脚本已经加载
window.addEventListener(DOMContentLoaded, () {// 获取Canvas上下文const canvas document.getElementById(myCanvas);if (!canvas.getContext) {console.error(浏览器不支持 Canvas);return;}const ctx canvas.getContext(2d);// 定义要绘制的形状const shapes [{ type: circle, x: 300, y: 300, radius: 100, isFill: true },{ type: rect, x: 150, y: 150, width: 200, height: 100, isFill: false },{ type: triangle, x1: 50, y1: 50, x2: 150, y2: 50, x3: 100, y3: 150, isFill: false }];// 绘制所有形状shapes.forEach(shape {drawShape(ctx, shape, shape.isFill);});
});这个项目已经初步搭建了一个有意思的canvas页面当然我希望它更有意思
main.js文件上的花活
我们只需要修改main.js文件即可我们使用随机、循环等方式创建各类对象
// main.js// 确保所有依赖的脚本已经加载
window.addEventListener(DOMContentLoaded, () {// 获取Canvas上下文const canvas document.getElementById(myCanvas);if (!canvas.getContext) {console.error(浏览器不支持 Canvas);return;}const ctx canvas.getContext(2d);// 随机颜色生成函数function getRandomColor() {const letters 0123456789ABCDEF;let color #;for (let i 0; i 6; i) {color letters[Math.floor(Math.random() * 16)];}return color;}// 定义循环生成形状的函数function generateShapes() {const shapes [];// 生成圆形随机大小和位置大小范围拉大for (let i 0; i 100; i) {const radius 1 Math.random() * 30; // 随机大小30-130const x Math.random() * (canvas.width - radius * 2) radius;const y Math.random() * (canvas.height - radius * 2) radius;shapes.push({ type: circle, x, y, radius, isFill: true, color: getRandomColor() });}// 生成矩形随机旋转渐变颜色大小和位置随机for (let i 0; i 30; i) {const width 60 Math.random() * 40;const height 40 Math.random() * 30;const x Math.random() * (canvas.width - width);const y Math.random() * (canvas.height - height);const angle Math.random() * Math.PI; // 随机旋转角度shapes.push({ type: rect, x, y, width, height, isFill: false, angle });}// 生成三角形顶点随机颜色随机for (let i 0; i 20; i) {const x1 Math.random() * canvas.width;const y1 Math.random() * canvas.height;const x2 x1 Math.random() * 100;const y2 y1 Math.random() * 100;const x3 x1 Math.random() * 50;const y3 y1 - Math.random() * 100;shapes.push({ type: triangle, x1, y1, x2, y2, x3, y3, isFill: true, color: getRandomColor() });}return shapes;}// 获取生成的形状const shapes generateShapes();// 绘制所有形状shapes.forEach(shape {// 如果是矩形先旋转后绘制if (shape.type rect) {ctx.save();ctx.translate(shape.x shape.width / 2, shape.y shape.height / 2);ctx.rotate(shape.angle);ctx.translate(-(shape.x shape.width / 2), -(shape.y shape.height / 2));drawShape(ctx, shape, shape.isFill);ctx.restore();} else if (shape.type triangle) {ctx.fillStyle shape.color; // 使用随机颜色填充三角形drawShape(ctx, shape, shape.isFill);} else if (shape.type circle) {ctx.fillStyle shape.color; // 使用随机颜色填充圆形drawShape(ctx, shape, shape.isFill);}});
});当然这个项目看上去依然存在问题还可以进一步拓展等更多奇妙的故事等你自己去探索吧~