akhaliq HF Staff commited on
Commit
37e0660
·
verified ·
1 Parent(s): ceb8f53

Upload folder using huggingface_hub

Browse files
Files changed (2) hide show
  1. index.html +92 -19
  2. js/voxel-scene.js +362 -0
index.html CHANGED
@@ -1,19 +1,92 @@
1
- <!doctype html>
2
- <html>
3
- <head>
4
- <meta charset="utf-8" />
5
- <meta name="viewport" content="width=device-width" />
6
- <title>My static Space</title>
7
- <link rel="stylesheet" href="style.css" />
8
- </head>
9
- <body>
10
- <div class="card">
11
- <h1>Welcome to your static Space!</h1>
12
- <p>You can modify this app directly by editing <i>index.html</i> in the Files and versions tab.</p>
13
- <p>
14
- Also don't forget to check the
15
- <a href="https://huggingface.co/docs/hub/spaces" target="_blank">Spaces documentation</a>.
16
- </p>
17
- </div>
18
- </body>
19
- </html>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
6
+ <title>Voxel Pagoda Garden</title>
7
+ <meta name="description" content="An immersive voxel art scene featuring a beautiful pagoda surrounded by cherry blossoms in a serene Japanese garden">
8
+ <style>
9
+ body {
10
+ margin: 0;
11
+ padding: 0;
12
+ background: linear-gradient(135deg, #87CEEB 0%, #98FB98 100%);
13
+ font-family: 'Arial', sans-serif;
14
+ overflow: hidden;
15
+ }
16
+
17
+ #info {
18
+ position: absolute;
19
+ top: 10px;
20
+ width: 100%;
21
+ text-align: center;
22
+ color: #2c3e50;
23
+ z-index: 100;
24
+ pointer-events: none;
25
+ }
26
+
27
+ #info h1 {
28
+ font-size: 2.5em;
29
+ margin: 0;
30
+ text-shadow: 2px 2px 4px rgba(255,255,255,0.7);
31
+ }
32
+
33
+ #info p {
34
+ font-size: 1.2em;
35
+ margin: 10px 0;
36
+ text-shadow: 1px 1px 2px rgba(255,255,255,0.7);
37
+ }
38
+
39
+ #built-with {
40
+ position: absolute;
41
+ bottom: 20px;
42
+ right: 20px;
43
+ z-index: 100;
44
+ }
45
+
46
+ #built-with a {
47
+ color: #2c3e50;
48
+ text-decoration: none;
49
+ font-weight: bold;
50
+ background: rgba(255,255,255,0.8);
51
+ padding: 8px 15px;
52
+ border-radius: 20px;
53
+ box-shadow: 0 2px 10px rgba(0,0,0,0.2);
54
+ pointer-events: all;
55
+ }
56
+
57
+ #built-with a:hover {
58
+ background: rgba(255,255,255,1);
59
+ transform: translateY(-2px);
60
+ }
61
+
62
+ #loading {
63
+ position: absolute;
64
+ top: 50%;
65
+ left: 50%;
66
+ transform: translate(-50%, -50%);
67
+ color: #2c3e50;
68
+ font-size: 1.5em;
69
+ z-index: 1000;
70
+ }
71
+
72
+ canvas {
73
+ display: block;
74
+ }
75
+ </style>
76
+ </head>
77
+ <body>
78
+ <div id="info">
79
+ <h1>Voxel Pagoda Garden</h1>
80
+ <p>A serene Japanese garden with cherry blossoms</p>
81
+ </div>
82
+
83
+ <div id="built-with">
84
+ <a href="https://huggingface.co/spaces/akhaliq/anycoder" target="_blank">Built with anycoder</a>
85
+ </div>
86
+
87
+ <div id="loading">Loading beautiful voxel garden...</div>
88
+
89
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script>
90
+ <script src="js/voxel-scene.js"></script>
91
+ </body>
92
+ </html>
js/voxel-scene.js ADDED
@@ -0,0 +1,362 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ document.addEventListener('DOMContentLoaded', function() {
2
+ // Remove loading message after 2 seconds
3
+ setTimeout(() => {
4
+ document.getElementById('loading').style.display = 'none';
5
+ }, 2000);
6
+
7
+ // Scene setup
8
+ const scene = new THREE.Scene();
9
+ const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
10
+ const renderer = new THREE.WebGLRenderer({ antialias: true });
11
+
12
+ renderer.setSize(window.innerWidth, window.innerHeight);
13
+ renderer.setClearColor(0x87CEEB);
14
+ renderer.shadowMap.enabled = true;
15
+ renderer.shadowMap.type = THREE.PCFSoftShadowMap;
16
+ document.body.appendChild(renderer.domElement);
17
+
18
+ // Lighting
19
+ const ambientLight = new THREE.AmbientLight(0xffffff, 0.6);
20
+ scene.add(ambientLight);
21
+
22
+ const directionalLight = new THREE.DirectionalLight(0xffffff, 0.8);
23
+ directionalLight.position.set(50, 100, 50);
24
+ directionalLight.castShadow = true;
25
+ directionalLight.shadow.mapSize.width = 2048;
26
+ directionalLight.shadow.mapSize.height = 2048;
27
+ scene.add(directionalLight);
28
+
29
+ // Create a simple voxel (cube)
30
+ function createVoxel(x, y, z, color, size = 1) {
31
+ const geometry = new THREE.BoxGeometry(size, size, size);
32
+ const material = new THREE.MeshLambertMaterial({ color: color });
33
+ const voxel = new THREE.Mesh(geometry, material);
34
+ voxel.position.set(x, y, z);
35
+ voxel.castShadow = true;
36
+ voxel.receiveShadow = true;
37
+ return voxel;
38
+ }
39
+
40
+ // Create ground
41
+ function createGround() {
42
+ const groundGeometry = new THREE.PlaneGeometry(200, 200);
43
+ const groundMaterial = new THREE.MeshLambertMaterial({
44
+ color: 0x90EE90,
45
+ side: THREE.DoubleSide
46
+ });
47
+ const ground = new THREE.Mesh(groundGeometry, groundMaterial);
48
+ ground.rotation.x = -Math.PI / 2;
49
+ ground.position.y = -0.5;
50
+ ground.receiveShadow = true;
51
+ scene.add(ground);
52
+
53
+ // Add grass texture with smaller voxels
54
+ for (let i = -80; i <= 80; i += 2) {
55
+ for (let j = -80; j <= 80; j += 2) {
56
+ if (Math.random() > 0.7) {
57
+ const grassVoxel = createVoxel(i, 0, j, 0x7CFC00, 1);
58
+ scene.add(grassVoxel);
59
+ }
60
+ }
61
+ }
62
+ }
63
+
64
+ // Create pagoda
65
+ function createPagoda() {
66
+ const pagodaGroup = new THREE.Group();
67
+
68
+ // Base platform
69
+ for (let x = -8; x <= 8; x++) {
70
+ for (let z = -8; z <= 8; z++) {
71
+ const voxel = createVoxel(x, 0, z, 0x8B4513);
72
+ pagodaGroup.add(voxel);
73
+ }
74
+ }
75
+
76
+ // First level
77
+ for (let y = 1; y <= 6; y++) {
78
+ for (let x = -6; x <= 6; x++) {
79
+ for (let z = -6; z <= 6; z++) {
80
+ if (x === -6 || x === 6 || z === -6 || z === 6 || y === 1 || y === 6) {
81
+ const voxel = createVoxel(x, y, z, 0xCD853F);
82
+ pagodaGroup.add(voxel);
83
+ }
84
+ }
85
+ }
86
+ }
87
+
88
+ // Second level (smaller)
89
+ for (let y = 7; y <= 10; y++) {
90
+ for (let x = -4; x <= 4; x++) {
91
+ for (let z = -4; z <= 4; z++) {
92
+ if (x === -4 || x === 4 || z === -4 || z === 4 || y === 7 || y === 10) {
93
+ const voxel = createVoxel(x, y, z, 0xD2691E);
94
+ pagodaGroup.add(voxel);
95
+ }
96
+ }
97
+ }
98
+ }
99
+
100
+ // Third level (even smaller)
101
+ for (let y = 11; y <= 13; y++) {
102
+ for (let x = -2; x <= 2; x++) {
103
+ for (let z = -2; z <= 2; z++) {
104
+ if (x === -2 || x === 2 || z === -2 || z === 2 || y === 11 || y === 13) {
105
+ const voxel = createVoxel(x, y, z, 0xA0522D);
106
+ pagodaGroup.add(voxel);
107
+ }
108
+ }
109
+ }
110
+ }
111
+
112
+ // Roof decorations
113
+ for (let y = 14; y <= 16; y++) {
114
+ for (let x = -1; x <= 1; x++) {
115
+ for (let z = -1; z <= 1; z++) {
116
+ if ((x === -1 || x === 1 || z === -1 || z === 1) && y === 14) {
117
+ const voxel = createVoxel(x, y, z, 0xFF0000);
118
+ pagodaGroup.add(voxel);
119
+ }
120
+ }
121
+ }
122
+ }
123
+
124
+ // Spire
125
+ for (let y = 15; y <= 20; y++) {
126
+ const voxel = createVoxel(0, y, 0, 0xFFD700);
127
+ pagodaGroup.add(voxel);
128
+ }
129
+
130
+ // Entrance
131
+ for (let x = -2; x <= 2; x++) {
132
+ for (let z = 7; z <= 8; z++) {
133
+ if (!(x >= -1 && x <= 1 && z === 7)) {
134
+ const voxel = createVoxel(x, 1, z, 0x8B4513);
135
+ pagodaGroup.add(voxel);
136
+ }
137
+ }
138
+ }
139
+
140
+ pagodaGroup.position.set(0, 0, 0);
141
+ scene.add(pagodaGroup);
142
+ }
143
+
144
+ // Create cherry blossom trees
145
+ function createCherryBlossomTree(x, z) {
146
+ const treeGroup = new THREE.Group();
147
+
148
+ // Trunk
149
+ for (let y = 0; y < 8; y++) {
150
+ const voxel = createVoxel(0, y, 0, 0x8B4513);
151
+ treeGroup.add(voxel);
152
+ }
153
+
154
+ // Leaves and blossoms
155
+ for (let y = 6; y <= 12; y++) {
156
+ for (let dx = -3; dx <= 3; dx++) {
157
+ for (let dz = -3; dz <= 3; dz++) {
158
+ const distance = Math.sqrt(dx * dx + dz * dz);
159
+ if (distance <= 3 && Math.random() > 0.3) {
160
+ let color;
161
+ if (Math.random() > 0.7) {
162
+ // Cherry blossoms
163
+ color = Math.random() > 0.5 ? 0xFFB6C1 : 0xFF69B4;
164
+ } else {
165
+ // Leaves
166
+ color = Math.random() > 0.5 ? 0x90EE90 : 0x32CD32;
167
+ }
168
+ const voxel = createVoxel(dx, y, dz, color);
169
+ treeGroup.add(voxel);
170
+ }
171
+ }
172
+ }
173
+ }
174
+
175
+ treeGroup.position.set(x, 0, z);
176
+ scene.add(treeGroup);
177
+ return treeGroup;
178
+ }
179
+
180
+ // Create garden elements
181
+ function createGarden() {
182
+ // Pond
183
+ const pondGeometry = new THREE.CircleGeometry(10, 32);
184
+ const pondMaterial = new THREE.MeshLambertMaterial({
185
+ color: 0x4682B4,
186
+ transparent: true,
187
+ opacity: 0.8
188
+ });
189
+ const pond = new THREE.Mesh(pondGeometry, pondMaterial);
190
+ pond.rotation.x = -Math.PI / 2;
191
+ pond.position.set(25, 0.1, 25);
192
+ scene.add(pond);
193
+
194
+ // Bridge over pond
195
+ for (let x = -3; x <= 3; x++) {
196
+ for (let z = 20; z <= 30; z++) {
197
+ if (Math.abs(x) <= 2) {
198
+ const voxel = createVoxel(x, 1, z, 0x8B4513);
199
+ scene.add(voxel);
200
+ }
201
+ }
202
+ }
203
+
204
+ // Stone path
205
+ for (let i = -40; i <= 40; i += 2) {
206
+ if (Math.random() > 0.3) {
207
+ const voxel = createVoxel(i, 0.5, 0, 0x808080);
208
+ scene.add(voxel);
209
+ }
210
+ }
211
+
212
+ // Lanterns along path
213
+ for (let x = -35; x <= 35; x += 15) {
214
+ createLantern(x, 2, 3);
215
+ }
216
+ }
217
+
218
+ // Create traditional lantern
219
+ function createLantern(x, y, z) {
220
+ const lanternGroup = new THREE.Group();
221
+
222
+ // Base
223
+ for (let dy = 0; dy < 2; dy++) {
224
+ const voxel = createVoxel(0, dy, 0, 0x696969);
225
+ lanternGroup.add(voxel);
226
+ }
227
+
228
+ // Light section
229
+ for (let dx = -1; dx <= 1; dx++) {
230
+ for (let dz = -1; dz <= 1; dz++) {
231
+ if (dx === 0 || dz === 0) {
232
+ const voxel = createVoxel(dx, 2, dz, 0xFFD700);
233
+ }
234
+ }
235
+ }
236
+
237
+ // Top
238
+ const topVoxel = createVoxel(0, 3, 0, 0x8B4513);
239
+ lanternGroup.add(topVoxel);
240
+
241
+ lanternGroup.position.set(x, y, z);
242
+ scene.add(lanternGroup);
243
+ }
244
+
245
+ // Create falling cherry blossoms
246
+ function createFallingBlossoms() {
247
+ const blossomGroup = new THREE.Group();
248
+ const blossomCount = 50;
249
+
250
+ for (let i = 0; i < blossomCount; i++) {
251
+ const geometry = new THREE.SphereGeometry(0.3, 4, 4);
252
+ const material = new THREE.MeshLambertMaterial({
253
+ color: Math.random() > 0.5 ? 0xFFB6C1 : 0xFF69B4
254
+ });
255
+ const blossom = new THREE.Mesh(geometry, material);
256
+
257
+ blossom.position.set(
258
+ Math.random() * 60 - 30,
259
+ Math.random() * 20 + 10,
260
+ Math.random() * 60 - 30
261
+ );
262
+
263
+ blossom.userData = {
264
+ velocity: Math.random() * 0.02 + 0.01,
265
+ rotationSpeed: (Math.random() - 0.5) * 0.02
266
+ };
267
+
268
+ blossomGroup.add(blossom);
269
+ }
270
+
271
+ scene.add(blossomGroup);
272
+ return blossomGroup;
273
+ }
274
+
275
+ // Initialize scene
276
+ createGround();
277
+ createPagoda();
278
+ createGarden();
279
+
280
+ // Create multiple cherry blossom trees
281
+ const treePositions = [
282
+ [-20, -20], [20, -20], [-20, 20], [20, 20],
283
+ [30, 0], [-30, 0], [0, 30], [0, -30],
284
+ [15, -25], [-15, 25], [25, 15], [-25, -15]
285
+ ];
286
+
287
+ treePositions.forEach(pos => {
288
+ createCherryBlossomTree(pos[0], pos[1]);
289
+ });
290
+
291
+ const fallingBlossoms = createFallingBlossoms();
292
+
293
+ // Camera position
294
+ camera.position.set(40, 25, 40);
295
+ camera.lookAt(0, 10, 0);
296
+
297
+ // Animation
298
+ function animate() {
299
+ requestAnimationFrame(animate);
300
+
301
+ // Animate falling blossoms
302
+ fallingBlossoms.children.forEach(blossom => {
303
+ blossom.position.y -= blossom.userData.velocity;
304
+ blossom.rotation.x += blossom.userData.rotationSpeed;
305
+ blossom.rotation.z += blossom.userData.rotationSpeed;
306
+
307
+ // Reset blossom position when it falls below ground
308
+ if (blossom.position.y < 0) {
309
+ blossom.position.y = 20;
310
+ blossom.position.x = Math.random() * 60 - 30;
311
+ blossom.position.z = Math.random() * 60 - 30;
312
+ }
313
+ });
314
+
315
+ renderer.render(scene, camera);
316
+ }
317
+
318
+ animate();
319
+
320
+ // Handle window resize
321
+ window.addEventListener('resize', function() {
322
+ camera.aspect = window.innerWidth / window.innerHeight;
323
+ camera.updateProjectionMatrix();
324
+ renderer.setSize(window.innerWidth, window.innerHeight);
325
+ });
326
+
327
+ // Add mouse controls for camera rotation
328
+ let mouseDown = false;
329
+ let mouseX = 0;
330
+ let mouseY = 0;
331
+
332
+ document.addEventListener('mousedown', function(e) {
333
+ mouseDown = true;
334
+ mouseX = e.clientX;
335
+ mouseY = e.clientY;
336
+ });
337
+
338
+ document.addEventListener('mouseup', function() {
339
+ mouseDown = false;
340
+ });
341
+
342
+ document.addEventListener('mousemove', function(e) {
343
+ if (!mouseDown) return;
344
+
345
+ const deltaX = e.clientX - mouseX;
346
+ const deltaY = e.clientY - mouseY;
347
+
348
+ camera.position.x -= deltaX * 0.01;
349
+ camera.position.y += deltaY * 0.01;
350
+
351
+ camera.lookAt(0, 10, 0);
352
+
353
+ mouseX = e.clientX;
354
+ mouseY = e.clientY;
355
+ });
356
+
357
+ // Add zoom with mouse wheel
358
+ document.addEventListener('wheel', function(e) {
359
+ camera.position.multiplyScalar(1 + e.deltaY * 0.001);
360
+ camera.lookAt(0, 10, 0);
361
+ });
362
+ });