Skip to content

Commit c8e99cc

Browse files
committed
Improve vostok/gagarin page
1 parent bfe8854 commit c8e99cc

File tree

12 files changed

+261
-213
lines changed

12 files changed

+261
-213
lines changed

public/build/assets/app-BRdgaViA.js renamed to public/build/assets/app-CksF0F1t.js

Lines changed: 17 additions & 17 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

public/build/assets/app-BcioR0Sg.css renamed to public/build/assets/app-tHIwFuYL.css

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

public/build/manifest.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,12 +12,12 @@
1212
"src": "public/img/ui/warning.svg"
1313
},
1414
"resources/css/app.scss": {
15-
"file": "assets/app-BcioR0Sg.css",
15+
"file": "assets/app-tHIwFuYL.css",
1616
"src": "resources/css/app.scss",
1717
"isEntry": true
1818
},
1919
"resources/js/app.js": {
20-
"file": "assets/app-BRdgaViA.js",
20+
"file": "assets/app-CksF0F1t.js",
2121
"src": "resources/js/app.js",
2222
"isEntry": true,
2323
"css": [

public/img/gagarin/space.jpg

-2.13 MB
Binary file not shown.

public/img/ui/vostok/space.jpg

1 MB
Loading

public/sound/vostok/background.mp3

3.39 MB
Binary file not shown.

resources/css/gagarin.scss

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,17 @@
2525
position: relative;
2626
@extend .rounded;
2727

28+
.space {
29+
background-image: url(/img/ui/vostok/space.jpg);
30+
background-size: cover;
31+
animation: rotation-space 300s infinite linear;
32+
position: absolute;
33+
bottom: -50%;
34+
top: -50%;
35+
left: -50%;
36+
right: -50%
37+
}
38+
2839
svg {
2940
display: block;
3041
animation: rotation-space-item 3s infinite linear;

resources/js/controllers/gagarin_controller.js

Whitespace-only changes.

resources/js/controllers/sound-toggle_controller.js

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,17 +8,17 @@ export default class extends Controller {
88
}
99

1010
toggle() {
11-
this.toggleButtons();
12-
1311
const audios = document.querySelectorAll('audio');
1412
audios.forEach((audio) => {
1513
audio.muted = !audio.muted;
1614
});
15+
16+
this.toggleButtons();
1717
}
1818

1919
toggleButtons() {
20-
this.muteButtonTarget.classList.toggle('d-none', this.isMuted);
21-
this.unmuteButtonTarget.classList.toggle('d-none', !this.isMuted);
20+
this.muteButtonTarget.classList.toggle('d-none', !this.isMuted);
21+
this.unmuteButtonTarget.classList.toggle('d-none', this.isMuted);
2222
}
2323

2424
get isMuted() {
Lines changed: 180 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,180 @@
1+
import { Controller } from '@hotwired/stimulus';
2+
3+
4+
export default class extends Controller {
5+
static targets = ["game", "ship", "comet", "message", "timer", "audioBackground", "startPlaceholder", "endPlaceholder"];
6+
7+
connect() {
8+
this.svg = this.gameTarget;
9+
this.shipWidth = 100;
10+
this.shipHeight = 100;
11+
this.shipSpeed = 5;
12+
this.baseCometSpeed = 3;
13+
this.cometWidth = 60;
14+
this.cometHeight = 60;
15+
this.cometInterval = 1000;
16+
document.addEventListener("keydown", this.keyDownHandler.bind(this));
17+
document.addEventListener("keyup", this.keyUpHandler.bind(this));
18+
this.audioBackgroundTarget.loop = true;
19+
}
20+
21+
disconnect() {
22+
document.removeEventListener("keydown", this.keyDownHandler.bind(this));
23+
document.removeEventListener("keyup", this.keyUpHandler.bind(this));
24+
}
25+
26+
fresh() {
27+
while (this.svg.firstChild) {
28+
this.svg.removeChild(this.svg.firstChild);
29+
}
30+
31+
this.timer = 0
32+
this.cometSpeed = this.baseCometSpeed;
33+
this.shipX = (this.svg.width.baseVal.value - this.shipWidth) / 2;
34+
this.shipY = this.svg.height.baseVal.value - this.shipHeight - 10;
35+
this.leftPressed = false;
36+
this.rightPressed = false;
37+
this.comets = [];
38+
this.shipElement = this.createShipElement();
39+
this.intervalComet = null;
40+
this.intervalGame = null;
41+
}
42+
43+
keyDownHandler(event) {
44+
if (event.key === "ArrowLeft") {
45+
this.leftPressed = true;
46+
} else if (event.key === "ArrowRight") {
47+
this.rightPressed = true;
48+
}
49+
}
50+
51+
keyUpHandler(event) {
52+
if (event.key === "ArrowLeft") {
53+
this.leftPressed = false;
54+
} else if (event.key === "ArrowRight") {
55+
this.rightPressed = false;
56+
}
57+
}
58+
59+
createShipElement() {
60+
const shipElement = this.shipTarget.cloneNode(true);
61+
shipElement.setAttribute("x", this.shipX);
62+
shipElement.setAttribute("y", this.shipY);
63+
shipElement.setAttribute("width", this.shipWidth);
64+
shipElement.setAttribute("height", this.shipHeight);
65+
shipElement.setAttribute("fill", "#FFFFFF");
66+
this.svg.appendChild(shipElement);
67+
return shipElement;
68+
}
69+
70+
moveShip() {
71+
if (this.leftPressed && this.shipX > 0) {
72+
this.shipX -= this.shipSpeed;
73+
} else if (this.rightPressed && this.shipX < this.svg.width.baseVal.value - this.shipWidth) {
74+
this.shipX += this.shipSpeed;
75+
}
76+
this.shipElement.setAttribute("x", this.shipX);
77+
}
78+
79+
createCometElement(x, y) {
80+
const cometElement = this.cometTarget.cloneNode(true);
81+
cometElement.setAttribute("x", x);
82+
cometElement.setAttribute("y", y);
83+
cometElement.setAttribute("width", this.cometWidth);
84+
cometElement.setAttribute("height", this.cometHeight);
85+
cometElement.setAttribute("fill", "#FF0000");
86+
this.svg.appendChild(cometElement);
87+
return cometElement;
88+
}
89+
90+
moveComets() {
91+
this.comets.forEach(comet => {
92+
comet.y += this.cometSpeed;
93+
comet.x = comet.element.getAttribute('x');
94+
comet.x -= this.cometSpeed;
95+
const dx = this.shipX - comet.x;
96+
const dy = this.shipY - comet.y;
97+
const distance = Math.sqrt(dx * dx + dy * dy);
98+
const vx = dx / distance;
99+
const vy = dy / distance;
100+
if(distance > 100){
101+
comet.x += vx;
102+
comet.y += vy;
103+
}
104+
comet.element.setAttribute("x", comet.x);
105+
comet.element.setAttribute("y", comet.y);
106+
if (comet.y > this.svg.height.baseVal.value) {
107+
this.svg.removeChild(comet.element);
108+
this.comets.splice(this.comets.indexOf(comet), 1);
109+
}
110+
});
111+
}
112+
113+
createComet() {
114+
let x = Math.random() * this.svg.width.baseVal.value + (this.svg.width.baseVal.value * 0.5);
115+
if (this.shipX > this.svg.width.baseVal.value / 3) {
116+
x += (this.shipX * 0.5);
117+
}
118+
const y = 0;
119+
const cometElement = this.createCometElement(x, y);
120+
this.comets.push({element: cometElement, y: y});
121+
}
122+
123+
collisionDetection(fuzziness) {
124+
const shipRect = this.shipElement.getBoundingClientRect();
125+
this.comets.forEach(comet => {
126+
const cometRect = comet.element.getBoundingClientRect();
127+
const fuzzinessFactor = fuzziness * Math.min(shipRect.width, shipRect.height, cometRect.width, cometRect.height);
128+
if (
129+
shipRect.left + fuzzinessFactor < cometRect.right &&
130+
shipRect.right - fuzzinessFactor > cometRect.left &&
131+
shipRect.top + fuzzinessFactor < cometRect.bottom &&
132+
shipRect.bottom - fuzzinessFactor > cometRect.top
133+
) {
134+
clearInterval(this.intervalComet);
135+
clearInterval(this.intervalGame);
136+
137+
this.messageTarget.innerText = 'Игра окончена';
138+
this.startPlaceholderTarget.style.visibility = 'visible';
139+
}
140+
});
141+
}
142+
143+
stats(){
144+
this.timer = this.timer + 0.5;
145+
let value = (this.timer / 100).toFixed(2)
146+
147+
this.timerTarget.innerText = value;
148+
this.cometSpeed = this.baseCometSpeed + value * 0.1;
149+
150+
151+
if(value > 20) {
152+
clearInterval(this.intervalComet);
153+
clearInterval(this.intervalGame);
154+
155+
this.endPlaceholderTarget.classList.remove('visually-hidden');
156+
}
157+
}
158+
159+
draw() {
160+
this.moveShip();
161+
this.moveComets();
162+
this.collisionDetection(0.4); // Погрешность 40%
163+
this.stats();
164+
}
165+
166+
start() {
167+
if(this.audioBackgroundTarget.currentTime === 0) {
168+
this.audioBackgroundTarget.play();
169+
}
170+
171+
this.fresh();
172+
this.intervalComet = setInterval(this.createComet.bind(this), this.cometInterval);
173+
this.intervalGame = setInterval(this.draw.bind(this), 10);
174+
175+
this.messageTarget.innerText = 'Поехали!';
176+
177+
this.startPlaceholderTarget.style.visibility = 'hidden';
178+
this.endPlaceholderTarget.classList.add('visually-hidden');
179+
}
180+
}

0 commit comments

Comments
 (0)