Всем привет! Подскажите, пожалуйста: какая технология используется для реализации кнопки меню как на сайте https://www.panoply.co.uk/? Заказчик просит скопировать.. Вижу что canvas, но не могу понять в ручную ли написан код или может фреймворк какой.. Заранее благодарен за любую информацию.
Вот собрал вам нечто похожее из подручных средств, в этом примере нет WebGL, все посчитано и нарисовано через 2d контекст.
let ctx = canvas.getContext('2d');
let k = 300, a1 = 0, a2 = 0, dir = 0, far = 300,
w = canvas.width, h = canvas.height, planes = [];
ctx.translate(w/2, h/2);
for (var i=-20; i<21; i+=20) {
addRect(10,10,20,i,-20)
addRect(10,10,-20,i,-20)
addDiag(15,10,20,i,-20)
addDiag(-15,10,20,i,-20)
}
addTopDiag(25,15,-25,20)
addTopDiag(-25,-15,-25,20)
function addTopDiag(x1,x2,dy,dz) {
whitePlane([
pt(-x1, dy, -dz),
pt(-x2, dy, -dz),
pt(x1, dy, dz),
pt(x2, dy, dz)
]);
}
function addDiag(w, h, dx=0, dy=0, dz=0){
whitePlane([
pt(0, h/2+dy, -5),
pt(0, -h/2+dy, -5),
pt(w, -h/2+dy, dz),
pt(w, h/2+dy, dz)
]);
}
function addRect(w, h, dx=0, dy=0, dz=0){
whitePlane([
pt(-w/2+dx, -h/2+dy, dz),
pt(-w/2+dx, h/2+dy, dz),
pt(w/2+dx, h/2+dy, dz),
pt(w/2+dx, -h/2+dy,dz)
]);
}
requestAnimationFrame(render)
function whitePlane(points){
planes.push({color: 'white', points});
}
function pt(x,y,z) {
return {x, y, z};
}
function project(p) {
let sinA1 = Math.sin(a1), cosA1 = Math.cos(a1);
let sinA2 = Math.sin(a2), cosA2 = Math.cos(a2);
let x = p.x*cosA1 + p.z*sinA1;
let z = p.z*cosA1 - p.x*sinA1;
let y = p.y*cosA2 + z*sinA2;
let kd = k/(z*cosA2 - p.y*sinA2 + far);
p.X = kd*x;
p.Y = kd*y;
}
function render() {
a2 += dir * 0.1;
if (a2 < -Math.PI/2 || a2 > 0) {
dir = 0;
a2 = a2 > 0 ? 0 : -Math.PI/2;
}
if (a2 < 0 && a2 > -Math.PI/2)
requestAnimationFrame(render);
planes.forEach(plane => plane.points.forEach(project));
ctx.clearRect(-w/2, -h/2, w, h);
planes.forEach(drawPlane);
}
function drawPlane(plane) {
ctx.fillStyle = plane.color;
ctx.beginPath();
ctx.moveTo(plane.points[0].X, plane.points[0].Y);
for (var i = 1; i < plane.points.length; i++)
ctx.lineTo(plane.points[i].X, plane.points[i].Y);
ctx.fill();
ctx.closePath();
}
function toggle() {
if (a2 < 0 && a2 > -Math.PI/2)
return;
dir = a2 === 0 ? -1 : 1
requestAnimationFrame(render);
}
body {
background: url(https://picsum.photos/id/22/700/200);
}
canvas {
cursor: pointer;
}
<canvas id=canvas width=90 height=90 onclick="toggle()" ></canvas>
В отличие от соседнего ответа, посчитал почти все точки по формуле и нарисовал при помощи SVG...
let cos = Math.cos, sin = Math.sin,
k = 1000, a1 = 0, a2 = 0, far = 1000,
dir = 0, planes = [];
let pts = Array(8).fill(0).map((e, i) => {
let a = Math.PI*(.25+.5*Math.floor(i/2)) + (i%2?.2:-.2);
return [cos(a)*30, sin(a)*30];
});
let t = -25;
whitePlane([pt(0,t),pt(1,t),pt(4,t),pt(5,t)])
whitePlane([pt(2,t),pt(3,t),pt(6,t),pt(7,t)])
for (var i=0; i<3;i++){
let t2 = t+20*i;
let t3 = -15+20*i;
whitePlane([
pt(4,t2),pt(5,t2),{x:0,y:t2,z:-7},pt(6,t2),pt(7,t2),
pt(7,t3),pt(6,t3),{x:0,y:t3,z:-7},pt(5,t3),pt(4,t3),
])
}
requestAnimationFrame(render)
function whitePlane(points) {
let id = "plane_" + planes.length;
svg.innerHTML += `<polygon id="${id}" ></polygon>`;
planes.push({points, id});
}
function pt(i, y=0) {
return {x:pts[i][0], y, z:pts[i][1]};
}
function project(p) {
let x = p.x*cos(a1) + p.z*sin(a1);
let z = p.z*cos(a1) - p.x*sin(a1);
let y = p.y*cos(a2) + z*sin(a2);
let d = z*cos(a2) - p.y*sin(a2) + far;
return [ (k/d)*x ,(k/d)*y ];
}
function render() {
a2 += dir * 0.1
if (a2 < -Math.PI/2 || a2 > 0){
dir = 0;
a2 = a2 > 0 ? 0 : -Math.PI/2;
}
dir !== 0 && requestAnimationFrame(render)
planes.forEach(plane => window[plane.id]
.setAttribute("points", plane.points.map(project)));
}
function toggle() {
if (dir !== 0)
return;
requestAnimationFrame(render);
dir = a2 === 0 ? -1 : 1
}
body {
background-color: black;
overflow: hidden;
}
svg {
width: 200px;
height: 200px;
cursor: pointer;
}
polygon {
fill: white;
}
<svg id=svg onclick=toggle() viewbox="-50 -50 100 100"></svg>
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
Перевод документов на английский язык: Важность и ключевые аспекты
При прочтении книги в ней попалась задачка, вроде пустяк, но я никак не могу понять, как правильно это реализовать, подскажите кто нибудь
Идея такая: есть локальный state (hook), в нем массив из четырех элементовНа экране есть кнопка добавления нового элемента в этот массив
Собираю проект через GulpТакая проблема: написал код, после "прогона" через babel выдал ошибку: regeneratorRuntime is not defined