gg.easy.airship 0.1.1661 → 0.1.1663
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Runtime/Code/VoxelWorld/{SelectionZone.cs → Editor/SelectionZone.cs} +309 -72
- package/Runtime/Code/VoxelWorld/Editor/VoxelBuilderEditorWindow.cs +60 -5
- package/Runtime/Code/VoxelWorld/Editor/VoxelWorldEditor.cs +120 -27
- package/Runtime/Code/VoxelWorld/Resources/SelectIcon.png +0 -0
- package/Runtime/Code/VoxelWorld/Resources/SelectIcon.png.meta +153 -0
- package/Runtime/Code/VoxelWorld/VoxelWorld.cs +5 -0
- package/package.json +1 -1
- /package/Runtime/Code/VoxelWorld/{SelectionZone.cs.meta → Editor/SelectionZone.cs.meta} +0 -0
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
using System;
|
|
2
2
|
using UnityEngine;
|
|
3
|
+
using System.Collections.Generic;
|
|
3
4
|
|
|
4
5
|
#if UNITY_EDITOR
|
|
5
6
|
using UnityEditor;
|
|
@@ -32,6 +33,9 @@ public class SelectionZone : MonoBehaviour
|
|
|
32
33
|
[NonSerialized]
|
|
33
34
|
private float previousThickness;
|
|
34
35
|
|
|
36
|
+
[NonSerialized]
|
|
37
|
+
public VoxelWorld voxelWorld;
|
|
38
|
+
|
|
35
39
|
void OnEnable()
|
|
36
40
|
{
|
|
37
41
|
mesh = new Mesh();
|
|
@@ -253,105 +257,338 @@ public class SelectionZone : MonoBehaviour
|
|
|
253
257
|
|
|
254
258
|
|
|
255
259
|
#if UNITY_EDITOR
|
|
260
|
+
|
|
256
261
|
[CustomEditor(typeof(SelectionZone))]
|
|
257
|
-
public class SelectionZoneEditor : Editor {
|
|
258
|
-
private const float handleSize = 0.
|
|
259
|
-
|
|
262
|
+
public class SelectionZoneEditor : UnityEditor.Editor {
|
|
263
|
+
private const float handleSize = 0.3f;
|
|
264
|
+
|
|
265
|
+
private bool mouseDown = false;
|
|
266
|
+
|
|
267
|
+
static bool haveCopiedData = false;
|
|
268
|
+
static UInt16[] copiedData;
|
|
269
|
+
static Vector3Int copiedSize;
|
|
270
|
+
|
|
271
|
+
// Define local handle positions based on the cube's size
|
|
272
|
+
Vector3[] localHandleVectors = new Vector3[6] {
|
|
273
|
+
new Vector3(1, 0, 0), // Right
|
|
274
|
+
new Vector3(-1, 0, 0), // Left
|
|
275
|
+
new Vector3(0, 1, 0), // Top
|
|
276
|
+
new Vector3(0, -1, 0), // Bottom
|
|
277
|
+
new Vector3(0, 0, 1), // Front
|
|
278
|
+
new Vector3(0, 0, -1) // Back
|
|
279
|
+
};
|
|
280
|
+
|
|
281
|
+
Color[] axisColors = new Color[6] {
|
|
282
|
+
Color.red,
|
|
283
|
+
Color.red,
|
|
284
|
+
Color.green,
|
|
285
|
+
Color.green,
|
|
286
|
+
Color.blue,
|
|
287
|
+
Color.blue
|
|
288
|
+
};
|
|
289
|
+
|
|
290
|
+
float[] handleOffset = new float[6] {
|
|
291
|
+
1,1,1,1,1,1
|
|
292
|
+
};
|
|
293
|
+
|
|
294
|
+
float[] trueHandleOffset = new float[6] {
|
|
295
|
+
1,1,1,1,1,1
|
|
296
|
+
};
|
|
297
|
+
|
|
298
|
+
//Gui
|
|
299
|
+
public override void OnInspectorGUI() {
|
|
300
|
+
//draw default
|
|
301
|
+
//DrawDefaultInspector();
|
|
302
|
+
|
|
303
|
+
//Add typeins for size x y and z
|
|
304
|
+
SelectionZone cube = (SelectionZone)target;
|
|
305
|
+
Vector3Int oldSize = new Vector3Int((int)cube.size.x, (int)cube.size.y, (int)cube.size.z);
|
|
306
|
+
Vector3Int newSize = EditorGUILayout.Vector3IntField("Size", oldSize);
|
|
307
|
+
|
|
308
|
+
if (newSize != oldSize) {
|
|
309
|
+
cube.size = newSize;
|
|
310
|
+
SnapToGrid();
|
|
311
|
+
cube.BuildCube();
|
|
312
|
+
ResetHandles();
|
|
313
|
+
}
|
|
260
314
|
|
|
261
|
-
|
|
315
|
+
//Draw a reset button
|
|
316
|
+
if (GUILayout.Button("Reset")) {
|
|
317
|
+
handleOffset = new float[6] {
|
|
318
|
+
1,1,1,1,1,1
|
|
319
|
+
};
|
|
320
|
+
trueHandleOffset = new float[6] {
|
|
321
|
+
1,1,1,1,1,1
|
|
322
|
+
};
|
|
323
|
+
|
|
324
|
+
cube.size = new Vector3(1, 1, 1);
|
|
325
|
+
cube.BuildCube();
|
|
326
|
+
}
|
|
327
|
+
if (cube.voxelWorld == null) {
|
|
328
|
+
return;
|
|
329
|
+
}
|
|
330
|
+
if (cube.voxelWorld.voxelBlocks == null) {
|
|
331
|
+
return;
|
|
332
|
+
}
|
|
333
|
+
VoxelEditManager voxelEditManager = VoxelEditManager.Instance;
|
|
334
|
+
|
|
335
|
+
//Add Copy Button
|
|
336
|
+
if (GUILayout.Button("Fill")) {
|
|
337
|
+
//walk the bounds
|
|
338
|
+
float dx = cube.size.x / 2;
|
|
339
|
+
float dy = cube.size.y / 2;
|
|
340
|
+
float dz = cube.size.z / 2;
|
|
341
|
+
float px = cube.transform.localPosition.x;
|
|
342
|
+
float py = cube.transform.localPosition.y;
|
|
343
|
+
float pz = cube.transform.localPosition.z;
|
|
344
|
+
|
|
345
|
+
if (cube.voxelWorld) {
|
|
346
|
+
|
|
347
|
+
List<VoxelEditAction.EditInfo> edits = new();
|
|
348
|
+
|
|
349
|
+
int selectedIndex = cube.voxelWorld.selectedBlockIndex;
|
|
350
|
+
//Walk the current selection zone
|
|
351
|
+
for (int x = Mathf.FloorToInt(px - dx); x < Mathf.CeilToInt(px + dx); x++) {
|
|
352
|
+
for (int y = Mathf.FloorToInt(py - dy); y < Mathf.CeilToInt(py + dy); y++) {
|
|
353
|
+
for (int z = Mathf.FloorToInt(pz - dz); z < Mathf.CeilToInt(pz + dz); z++) {
|
|
354
|
+
UInt16 prevData = cube.voxelWorld.ReadVoxelAt(new Vector3Int(x, y, z));
|
|
355
|
+
edits.Add(new VoxelEditAction.EditInfo(new Vector3Int(x, y, z), prevData, (UInt16)selectedIndex));
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
voxelEditManager.AddEdits(cube.voxelWorld, edits, "Fill Voxels");
|
|
360
|
+
}
|
|
361
|
+
}
|
|
262
362
|
|
|
263
|
-
|
|
264
|
-
|
|
363
|
+
if (GUILayout.Button("Copy")) {
|
|
364
|
+
//walk the bounds
|
|
365
|
+
float dx = cube.size.x / 2;
|
|
366
|
+
float dy = cube.size.y / 2;
|
|
367
|
+
float dz = cube.size.z / 2;
|
|
368
|
+
float px = cube.transform.localPosition.x;
|
|
369
|
+
float py = cube.transform.localPosition.y;
|
|
370
|
+
float pz = cube.transform.localPosition.z;
|
|
371
|
+
|
|
372
|
+
haveCopiedData = true;
|
|
373
|
+
copiedSize = new Vector3Int((int)cube.size.x, (int)cube.size.y, (int)cube.size.z);
|
|
374
|
+
|
|
375
|
+
copiedData = new UInt16[(int)cube.size.x * (int)cube.size.y * (int)cube.size.z];
|
|
376
|
+
|
|
377
|
+
if (cube.voxelWorld) {
|
|
378
|
+
|
|
379
|
+
int index = 0;
|
|
380
|
+
//Walk the current selection zone
|
|
381
|
+
for (int x = Mathf.FloorToInt(px - dx); x < Mathf.CeilToInt(px + dx); x++) {
|
|
382
|
+
for (int y = Mathf.FloorToInt(py - dy); y < Mathf.CeilToInt(py + dy); y++) {
|
|
383
|
+
for (int z = Mathf.FloorToInt(pz - dz); z < Mathf.CeilToInt(pz + dz); z++) {
|
|
384
|
+
copiedData[index++] = cube.voxelWorld.ReadVoxelAt(new Vector3Int(x, y, z));
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
}
|
|
388
|
+
}
|
|
389
|
+
}
|
|
390
|
+
|
|
391
|
+
if (haveCopiedData == false) {
|
|
392
|
+
//Disable ui
|
|
393
|
+
GUI.enabled = false;
|
|
394
|
+
//Make fake paste button
|
|
395
|
+
if (GUILayout.Button("Paste")) {
|
|
396
|
+
//Do nothing
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
GUI.enabled = true;
|
|
400
|
+
}else {
|
|
401
|
+
//Actual paste
|
|
402
|
+
if (GUILayout.Button("Paste")) {
|
|
403
|
+
//walk the bouns
|
|
404
|
+
float dx = copiedSize.x / 2;
|
|
405
|
+
float dy = copiedSize.y / 2;
|
|
406
|
+
float dz = copiedSize.z / 2;
|
|
407
|
+
float px = cube.transform.localPosition.x;
|
|
408
|
+
float py = cube.transform.localPosition.y;
|
|
409
|
+
float pz = cube.transform.localPosition.z;
|
|
410
|
+
|
|
411
|
+
if (cube.voxelWorld) {
|
|
412
|
+
int index = 0;
|
|
413
|
+
|
|
414
|
+
List<VoxelEditAction.EditInfo> edits = new();
|
|
415
|
+
|
|
416
|
+
//Walk the current selection zone
|
|
417
|
+
for (int x = Mathf.FloorToInt(px - dx); x < Mathf.CeilToInt(px + dx); x++) {
|
|
418
|
+
for (int y = Mathf.FloorToInt(py - dy); y < Mathf.CeilToInt(py + dy); y++) {
|
|
419
|
+
for (int z = Mathf.FloorToInt(pz - dz); z < Mathf.CeilToInt(pz + dz); z++) {
|
|
420
|
+
//cube.voxelWorld.WriteVoxelAt(new Vector3Int(x, y, z), copiedData[index++], false);
|
|
421
|
+
UInt16 prevData = cube.voxelWorld.ReadVoxelAt(new Vector3Int(x, y, z));
|
|
422
|
+
edits.Add(new VoxelEditAction.EditInfo(new Vector3Int(x, y, z), prevData, copiedData[index++]));
|
|
423
|
+
}
|
|
424
|
+
}
|
|
425
|
+
}
|
|
426
|
+
voxelEditManager.AddEdits(cube.voxelWorld, edits, "Paste Voxels");
|
|
427
|
+
|
|
428
|
+
|
|
429
|
+
}
|
|
430
|
+
|
|
431
|
+
//resize the box to whatever we pasted
|
|
432
|
+
cube.size = new Vector3(copiedSize.x, copiedSize.y, copiedSize.z);
|
|
433
|
+
SnapToGrid();
|
|
434
|
+
cube.BuildCube();
|
|
435
|
+
ResetHandles();
|
|
436
|
+
}
|
|
437
|
+
}
|
|
265
438
|
}
|
|
266
439
|
|
|
440
|
+
|
|
441
|
+
void Awake() {
|
|
442
|
+
// Add a handler for the gizmo refresh event
|
|
443
|
+
SceneView.duringSceneGui += GizmoRefreshEvent;
|
|
444
|
+
|
|
445
|
+
SnapToGrid();
|
|
446
|
+
}
|
|
447
|
+
|
|
448
|
+
private void ResetHandles() {
|
|
449
|
+
SelectionZone cube = (SelectionZone)target;
|
|
450
|
+
trueHandleOffset[0] = (cube.size.x / 2) + 0.5f;
|
|
451
|
+
trueHandleOffset[1] = (cube.size.x / 2) + 0.5f;
|
|
452
|
+
trueHandleOffset[2] = (cube.size.y / 2) + 0.5f;
|
|
453
|
+
trueHandleOffset[3] = (cube.size.y / 2) + 0.5f;
|
|
454
|
+
trueHandleOffset[4] = (cube.size.z / 2) + 0.5f;
|
|
455
|
+
trueHandleOffset[5] = (cube.size.z / 2) + 0.5f;
|
|
456
|
+
for (int j = 0; j < 6; j++) {
|
|
457
|
+
handleOffset[j] = trueHandleOffset[j];
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
private void OnDestroy() {
|
|
461
|
+
|
|
462
|
+
SceneView.duringSceneGui -= GizmoRefreshEvent;
|
|
463
|
+
}
|
|
464
|
+
|
|
465
|
+
public void SnapToGrid() {
|
|
466
|
+
SelectionZone cube = (SelectionZone)target;
|
|
467
|
+
Transform cubeTransform = cube.transform;
|
|
468
|
+
|
|
469
|
+
// Snap the position to the nearest 0.5 unit grid
|
|
470
|
+
float x = Mathf.Floor(cubeTransform.localPosition.x);
|
|
471
|
+
float y = Mathf.Floor(cubeTransform.localPosition.y);
|
|
472
|
+
float z = Mathf.Floor(cubeTransform.localPosition.z);
|
|
473
|
+
|
|
474
|
+
// Adjust snapping if the size is even
|
|
475
|
+
if (Mathf.Round(cube.size.x) % 2 == 1) {
|
|
476
|
+
x += 0.5f;
|
|
477
|
+
}
|
|
478
|
+
if (Mathf.Round(cube.size.y) % 2 == 1) {
|
|
479
|
+
y += 0.5f;
|
|
480
|
+
}
|
|
481
|
+
if (Mathf.Round(cube.size.z) % 2 == 1) {
|
|
482
|
+
z += 0.5f;
|
|
483
|
+
}
|
|
484
|
+
|
|
485
|
+
// Set the snapped position
|
|
486
|
+
cubeTransform.localPosition = new Vector3(x, y, z);
|
|
487
|
+
cubeTransform.localRotation = Quaternion.identity;
|
|
488
|
+
cubeTransform.localScale = Vector3.one;
|
|
489
|
+
}
|
|
490
|
+
|
|
267
491
|
void GizmoRefreshEvent(SceneView obj) {
|
|
268
492
|
SelectionZone cube = (SelectionZone)target;
|
|
493
|
+
if (target == null) {
|
|
494
|
+
return;
|
|
495
|
+
}
|
|
269
496
|
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
cube.transform.
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
497
|
+
if (cube.transform.hasChanged) {
|
|
498
|
+
//Debug.Log("Has changed");
|
|
499
|
+
SnapToGrid();
|
|
500
|
+
cube.transform.hasChanged = false;
|
|
501
|
+
}
|
|
502
|
+
|
|
503
|
+
|
|
504
|
+
|
|
505
|
+
//capture mouse up and mouse down
|
|
506
|
+
if (Event.current.type == EventType.MouseUp) {
|
|
507
|
+
mouseDown = false;
|
|
508
|
+
|
|
509
|
+
}
|
|
510
|
+
if (Event.current.type == EventType.MouseDown) {
|
|
511
|
+
mouseDown = true;
|
|
512
|
+
}
|
|
280
513
|
|
|
514
|
+
Transform cubeTransform = cube.transform;
|
|
515
|
+
|
|
281
516
|
EditorGUI.BeginChangeCheck();
|
|
282
517
|
|
|
518
|
+
Vector3 motion = Vector3.zero;
|
|
519
|
+
|
|
283
520
|
// Move handles with constraints
|
|
284
|
-
for (int i = 0; i <
|
|
521
|
+
for (int i = 0; i < localHandleVectors.Length; i++) {
|
|
522
|
+
Vector3 localHandleStartPos = localHandleVectors[i] * handleOffset[i];
|
|
523
|
+
Vector3 worldHandleStartPos = cubeTransform.TransformPoint(localHandleStartPos);
|
|
285
524
|
Vector3 axis = Vector3.zero;
|
|
286
|
-
|
|
525
|
+
float isNegativeHandle = 1;
|
|
526
|
+
|
|
287
527
|
switch (i) {
|
|
288
528
|
case 0: axis = Vector3.right; break;
|
|
289
|
-
case 1: axis = Vector3.right; isNegativeHandle =
|
|
529
|
+
case 1: axis = Vector3.right; isNegativeHandle = -1; break;
|
|
290
530
|
case 2: axis = Vector3.up; break;
|
|
291
|
-
case 3: axis = Vector3.up; isNegativeHandle =
|
|
531
|
+
case 3: axis = Vector3.up; isNegativeHandle = -1; break;
|
|
292
532
|
case 4: axis = Vector3.forward; break;
|
|
293
|
-
case 5: axis = Vector3.forward; isNegativeHandle =
|
|
533
|
+
case 5: axis = Vector3.forward; isNegativeHandle = -1; break;
|
|
294
534
|
}
|
|
295
535
|
|
|
536
|
+
|
|
296
537
|
// Draw spheres as handles and constrain movement
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
float movement = Mathf.Floor((newPos - handles[i]).magnitude / snapValue) * snapValue * Mathf.Sign(Vector3.Dot(newPos - handles[i], axis));
|
|
538
|
+
//Set the color
|
|
539
|
+
Handles.color = axisColors[i];
|
|
540
|
+
Vector3 newWorldPos = Handles.Slider(worldHandleStartPos, cubeTransform.TransformDirection(axis), handleSize, Handles.SphereHandleCap,0);
|
|
301
541
|
|
|
302
|
-
|
|
542
|
+
Handles.color = Color.white;
|
|
303
543
|
|
|
304
|
-
|
|
305
|
-
// Invert the movement for negative handles
|
|
306
|
-
if (isNegativeHandle) {
|
|
307
|
-
resize = -resize;
|
|
308
|
-
}
|
|
544
|
+
Vector3 localHandlePos = cubeTransform.InverseTransformPoint(newWorldPos);
|
|
309
545
|
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
cube.size.x += resize;
|
|
314
|
-
cube.transform.position += axis * (movement / 2);
|
|
315
|
-
break;
|
|
316
|
-
case 2:
|
|
317
|
-
case 3:
|
|
318
|
-
cube.size.y += resize;
|
|
319
|
-
cube.transform.position += axis * (movement / 2);
|
|
320
|
-
break;
|
|
321
|
-
case 4:
|
|
322
|
-
case 5:
|
|
323
|
-
cube.size.z += resize;
|
|
324
|
-
cube.transform.position += axis * (movement / 2);
|
|
325
|
-
break;
|
|
326
|
-
}
|
|
546
|
+
bool moved = false;
|
|
547
|
+
if ((newWorldPos - worldHandleStartPos).magnitude > 0) {
|
|
548
|
+
moved = true;
|
|
327
549
|
}
|
|
328
|
-
}
|
|
329
|
-
|
|
330
|
-
if (EditorGUI.EndChangeCheck()) {
|
|
331
|
-
Undo.RecordObject(cube, "Resize Cube");
|
|
332
|
-
cube.size = new Vector3(Mathf.Max(1, Mathf.Round(cube.size.x)), Mathf.Max(1, Mathf.Round(cube.size.y)), Mathf.Max(1, Mathf.Round(cube.size.z)));
|
|
333
|
-
|
|
334
|
-
//Snap the position
|
|
335
|
-
//cube.transform.position = new Vector3(Mathf.Floor(cube.transform.position.x), Mathf.Floor(cube.transform.position.y), Mathf.Floor(cube.transform.position.z));
|
|
336
550
|
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
float y = Mathf.Floor(cube.transform.position.y);
|
|
340
|
-
float z = Mathf.Floor(cube.transform.position.z);
|
|
341
|
-
|
|
342
|
-
if (Mathf.Round(cube.size.x) % 2 == 0) {
|
|
343
|
-
x += 0.5f;
|
|
344
|
-
}
|
|
345
|
-
if (Mathf.Round(cube.size.y) % 2 == 0) {
|
|
346
|
-
y += 0.5f;
|
|
347
|
-
}
|
|
348
|
-
if (Mathf.Round(cube.size.z) % 2 == 0) {
|
|
349
|
-
z += 0.5f;
|
|
551
|
+
if (mouseDown == false && Mathf.Abs(trueHandleOffset[i] - handleOffset[i]) > Mathf.Epsilon) {
|
|
552
|
+
handleOffset[i] = trueHandleOffset[i]; //Reset it
|
|
350
553
|
}
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
554
|
+
|
|
555
|
+
if (moved == true) {
|
|
556
|
+
|
|
557
|
+
float distance = localHandlePos.magnitude - trueHandleOffset[i];
|
|
558
|
+
float steps = Mathf.Floor(distance);
|
|
559
|
+
|
|
560
|
+
handleOffset[i] = localHandlePos.magnitude;
|
|
561
|
+
|
|
562
|
+
if (steps != 0) {
|
|
563
|
+
|
|
564
|
+
cube.size += steps * axis;
|
|
565
|
+
cube.transform.localPosition += (steps * axis / 2) * isNegativeHandle;
|
|
566
|
+
SnapToGrid();
|
|
567
|
+
|
|
568
|
+
//Recalc handle pos
|
|
569
|
+
trueHandleOffset[0] = (cube.size.x / 2) + 0.5f;
|
|
570
|
+
trueHandleOffset[1] = (cube.size.x / 2) + 0.5f;
|
|
571
|
+
trueHandleOffset[2] = (cube.size.y / 2) + 0.5f;
|
|
572
|
+
trueHandleOffset[3] = (cube.size.y / 2) + 0.5f;
|
|
573
|
+
trueHandleOffset[4] = (cube.size.z / 2) + 0.5f;
|
|
574
|
+
trueHandleOffset[5] = (cube.size.z / 2) + 0.5f;
|
|
575
|
+
for (int j = 0; j < 6; j++) {
|
|
576
|
+
//Reset all handles except the one being dragged
|
|
577
|
+
if (j==i) {
|
|
578
|
+
continue;
|
|
579
|
+
}
|
|
580
|
+
handleOffset[j] = trueHandleOffset[j];
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
handleOffset[i] -= (steps * 0.5f);
|
|
354
584
|
|
|
585
|
+
}
|
|
586
|
+
|
|
587
|
+
}
|
|
588
|
+
}
|
|
589
|
+
|
|
590
|
+
if (EditorGUI.EndChangeCheck()) {
|
|
591
|
+
|
|
355
592
|
cube.BuildCube();
|
|
356
593
|
EditorUtility.SetDirty(cube);
|
|
357
594
|
}
|
|
@@ -53,6 +53,14 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
53
53
|
return voxelWorld;
|
|
54
54
|
}
|
|
55
55
|
}
|
|
56
|
+
|
|
57
|
+
if (selectedObject) {
|
|
58
|
+
var selectionZone = selectedObject.GetComponentInParent<SelectionZone>();
|
|
59
|
+
if (selectionZone && selectionZone.voxelWorld) {
|
|
60
|
+
return selectionZone.voxelWorld;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
|
|
56
64
|
return null;
|
|
57
65
|
}
|
|
58
66
|
|
|
@@ -64,9 +72,13 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
64
72
|
|
|
65
73
|
//Shows a list of all the VoxelWorld objects in the scene as clickable buttons
|
|
66
74
|
VoxelWorld[] voxelWorlds = GameObject.FindObjectsOfType<VoxelWorld>();
|
|
75
|
+
|
|
67
76
|
for (int i = 0; i < voxelWorlds.Length; i++) {
|
|
68
77
|
|
|
69
|
-
|
|
78
|
+
|
|
79
|
+
SelectionZone selectionZone = voxelWorlds[i].GetComponentInChildren<SelectionZone>();
|
|
80
|
+
|
|
81
|
+
if (Selection.activeGameObject == voxelWorlds[i].gameObject || (selectionZone!=null && Selection.activeGameObject == selectionZone.gameObject)) {
|
|
70
82
|
GUI.backgroundColor = Color.green;
|
|
71
83
|
}
|
|
72
84
|
else {
|
|
@@ -85,6 +97,7 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
85
97
|
|
|
86
98
|
GUI.backgroundColor = Color.white;
|
|
87
99
|
}
|
|
100
|
+
|
|
88
101
|
|
|
89
102
|
void OnGUI() {
|
|
90
103
|
//Create an active toggle as a button that toggles on and off
|
|
@@ -96,11 +109,43 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
96
109
|
|
|
97
110
|
ShowSelectionGui();
|
|
98
111
|
|
|
112
|
+
|
|
113
|
+
|
|
99
114
|
VoxelWorld world = GetVoxelWorld();
|
|
115
|
+
SelectionZone selection = null;
|
|
100
116
|
if (world == null || world.voxelBlocks == null) {
|
|
101
|
-
GUI.enabled = true;
|
|
117
|
+
GUI.enabled = true; //cleanup from above
|
|
102
118
|
return;
|
|
103
119
|
}
|
|
120
|
+
|
|
121
|
+
|
|
122
|
+
//See if we're in the selection mode
|
|
123
|
+
if (VoxelWorldSelectionToolBase.buttonActive == true) {
|
|
124
|
+
//Find or create the SelectionZone for this voxelWorld
|
|
125
|
+
|
|
126
|
+
selection = world.GetComponentInChildren<SelectionZone>();
|
|
127
|
+
if (selection == null) {
|
|
128
|
+
selection = new GameObject("SelectionZone").AddComponent<SelectionZone>();
|
|
129
|
+
selection.hideFlags = HideFlags.DontSave;
|
|
130
|
+
selection.transform.parent = world.transform;
|
|
131
|
+
selection.transform.localPosition = Vector3.zero;
|
|
132
|
+
selection.voxelWorld = world;
|
|
133
|
+
}
|
|
134
|
+
//Select this
|
|
135
|
+
Selection.activeGameObject = selection.gameObject;
|
|
136
|
+
}
|
|
137
|
+
if (VoxelWorldEditorToolBase.buttonActive == true) {
|
|
138
|
+
|
|
139
|
+
//If we're not in selection mode, destroy the selection zone
|
|
140
|
+
selection = world.GetComponentInChildren<SelectionZone>();
|
|
141
|
+
|
|
142
|
+
if (selection) {
|
|
143
|
+
//Select the world
|
|
144
|
+
Selection.activeGameObject = world.gameObject;
|
|
145
|
+
//Destroy it
|
|
146
|
+
DestroyImmediate(selection.gameObject);
|
|
147
|
+
}
|
|
148
|
+
}
|
|
104
149
|
|
|
105
150
|
//Show a foldable help box
|
|
106
151
|
EditorGUILayout.HelpBox("Left click to add\nShift+click to delete\nCtrl+click for repeat placement", MessageType.Info);
|
|
@@ -119,13 +164,19 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
119
164
|
|
|
120
165
|
GUIStyle selectedStyle = new GUIStyle(GUI.skin.button);
|
|
121
166
|
selectedStyle.normal.textColor = Color.green;
|
|
122
|
-
|
|
167
|
+
selectedStyle.hover.textColor = Color.green;
|
|
123
168
|
|
|
124
169
|
foreach (var pair in world.voxelBlocks.loadedBlocks) {
|
|
170
|
+
|
|
171
|
+
string name = pair.Value.definition.name;
|
|
172
|
+
if (name == "") {
|
|
173
|
+
name = "Air";
|
|
174
|
+
}
|
|
175
|
+
|
|
125
176
|
if (pair.Key == world.selectedBlockIndex) {
|
|
126
|
-
GUILayout.Button(
|
|
177
|
+
GUILayout.Button(name, selectedStyle);
|
|
127
178
|
} else {
|
|
128
|
-
if (GUILayout.Button(
|
|
179
|
+
if (GUILayout.Button(name)) {
|
|
129
180
|
world.selectedBlockIndex = pair.Key;
|
|
130
181
|
}
|
|
131
182
|
}
|
|
@@ -133,6 +184,10 @@ namespace Code.Airship.Resources.VoxelRenderer.Editor {
|
|
|
133
184
|
GUILayout.EndScrollView();
|
|
134
185
|
GUI.enabled = true;
|
|
135
186
|
}
|
|
187
|
+
|
|
188
|
+
void OnEnable() {
|
|
189
|
+
base.autoRepaintOnSceneChange = true;
|
|
190
|
+
}
|
|
136
191
|
}
|
|
137
192
|
}
|
|
138
193
|
#endif
|
|
@@ -7,17 +7,32 @@ using UnityEditor.EditorTools;
|
|
|
7
7
|
using UnityEngine;
|
|
8
8
|
using System;
|
|
9
9
|
using static UnityEditor.PlayerSettings;
|
|
10
|
+
using static VoxelEditAction;
|
|
10
11
|
|
|
11
12
|
public class VoxelEditAction {
|
|
12
|
-
|
|
13
|
-
public
|
|
14
|
-
|
|
13
|
+
|
|
14
|
+
public struct EditInfo{
|
|
15
|
+
public Vector3Int position;
|
|
16
|
+
public ushort oldValue;
|
|
17
|
+
public ushort newValue;
|
|
18
|
+
//constructor
|
|
19
|
+
public EditInfo(Vector3Int position, ushort oldValue, ushort newValue){
|
|
20
|
+
this.position = position;
|
|
21
|
+
this.oldValue = oldValue;
|
|
22
|
+
this.newValue = newValue;
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
public List<EditInfo> edits = new List<EditInfo>();
|
|
26
|
+
|
|
15
27
|
[NonSerialized]
|
|
16
28
|
public WeakReference<VoxelWorld> world;
|
|
17
|
-
public void
|
|
18
|
-
|
|
19
|
-
this.
|
|
20
|
-
|
|
29
|
+
public void CreateSingleEdit(VoxelWorld world, Vector3Int position, ushort oldValue, ushort newValue) {
|
|
30
|
+
edits.Add(new EditInfo(position, oldValue, newValue));
|
|
31
|
+
this.world = new(world);
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
public void CreateMultiEdit(VoxelWorld world, List<EditInfo> edits) {
|
|
35
|
+
this.edits = edits;
|
|
21
36
|
this.world = new(world);
|
|
22
37
|
}
|
|
23
38
|
}
|
|
@@ -30,11 +45,10 @@ public class VoxelEditManager : Singleton<VoxelEditManager> {
|
|
|
30
45
|
VoxelEditMarker undoObject;
|
|
31
46
|
public List<VoxelEditAction> edits = new List<VoxelEditAction>();
|
|
32
47
|
public List<VoxelEditAction> redos = new List<VoxelEditAction>();
|
|
33
|
-
|
|
34
|
-
|
|
48
|
+
|
|
35
49
|
public void AddEdit(VoxelWorld world, Vector3Int position, ushort oldValue, ushort newValue, string name) {
|
|
36
50
|
VoxelEditAction edit = new VoxelEditAction();
|
|
37
|
-
edit.
|
|
51
|
+
edit.CreateSingleEdit(world, position, oldValue, newValue);
|
|
38
52
|
edits.Add(edit);
|
|
39
53
|
|
|
40
54
|
//If we're adding a new edit, clear the redos
|
|
@@ -52,9 +66,33 @@ public class VoxelEditManager : Singleton<VoxelEditManager> {
|
|
|
52
66
|
world.DirtyNeighborMeshes(position);
|
|
53
67
|
|
|
54
68
|
world.hasUnsavedChanges = true;
|
|
55
|
-
|
|
56
69
|
}
|
|
57
70
|
|
|
71
|
+
public void AddEdits(VoxelWorld world, List<EditInfo> editInfos, string name) {
|
|
72
|
+
VoxelEditAction edit = new VoxelEditAction();
|
|
73
|
+
edit.CreateMultiEdit(world, editInfos);
|
|
74
|
+
edits.Add(edit);
|
|
75
|
+
|
|
76
|
+
//If we're adding a new edit, clear the redos
|
|
77
|
+
redos.Clear();
|
|
78
|
+
|
|
79
|
+
if (undoObject == null) {
|
|
80
|
+
undoObject = ScriptableObject.CreateInstance<VoxelEditMarker>();
|
|
81
|
+
}
|
|
82
|
+
undoObject.lastAction = edit;
|
|
83
|
+
|
|
84
|
+
//Save the state of this whole object into the undo system
|
|
85
|
+
Undo.RegisterCompleteObjectUndo(undoObject, name);
|
|
86
|
+
|
|
87
|
+
foreach (EditInfo editInfo in editInfos) {
|
|
88
|
+
world.WriteVoxelAtInternal(editInfo.position, editInfo.newValue);
|
|
89
|
+
world.DirtyNeighborMeshes(editInfo.position);
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
world.hasUnsavedChanges = true;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
|
|
58
96
|
//Constructor
|
|
59
97
|
public VoxelEditManager() {
|
|
60
98
|
Undo.undoRedoEvent += UndoRedoEvent;
|
|
@@ -69,8 +107,10 @@ public class VoxelEditManager : Singleton<VoxelEditManager> {
|
|
|
69
107
|
|
|
70
108
|
edit.world.TryGetTarget(out VoxelWorld currentWorld);
|
|
71
109
|
if (currentWorld){
|
|
72
|
-
|
|
73
|
-
|
|
110
|
+
foreach (var editInfo in edit.edits) {
|
|
111
|
+
currentWorld.WriteVoxelAtInternal(editInfo.position, editInfo.oldValue);
|
|
112
|
+
currentWorld.DirtyNeighborMeshes(editInfo.position);
|
|
113
|
+
}
|
|
74
114
|
currentWorld.hasUnsavedChanges = true;
|
|
75
115
|
}
|
|
76
116
|
|
|
@@ -83,8 +123,10 @@ public class VoxelEditManager : Singleton<VoxelEditManager> {
|
|
|
83
123
|
redos.RemoveAt(redos.Count - 1);
|
|
84
124
|
edit.world.TryGetTarget(out VoxelWorld currentWorld);
|
|
85
125
|
if (currentWorld) {
|
|
86
|
-
|
|
87
|
-
|
|
126
|
+
foreach (var editInfo in edit.edits) {
|
|
127
|
+
currentWorld.WriteVoxelAtInternal(editInfo.position, editInfo.newValue);
|
|
128
|
+
currentWorld.DirtyNeighborMeshes(editInfo.position);
|
|
129
|
+
}
|
|
88
130
|
currentWorld.hasUnsavedChanges = true;
|
|
89
131
|
}
|
|
90
132
|
|
|
@@ -380,9 +422,7 @@ public class VoxelWorldEditor : UnityEditor.Editor {
|
|
|
380
422
|
handle.name = "_SelectionHandle";
|
|
381
423
|
handle.hideFlags = HideFlags.HideAndDontSave;
|
|
382
424
|
}
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
425
|
+
|
|
386
426
|
if (faceHandle == null) {
|
|
387
427
|
faceHandle = GameObject.CreatePrimitive(PrimitiveType.Quad);
|
|
388
428
|
faceHandle.transform.localScale = new Vector3(1.01f, 1.01f, 1.01f);
|
|
@@ -396,13 +436,12 @@ public class VoxelWorldEditor : UnityEditor.Editor {
|
|
|
396
436
|
if (Event.current.shift) { //Delete
|
|
397
437
|
DestroyImmediate(faceHandle);
|
|
398
438
|
faceHandle = null;
|
|
399
|
-
|
|
400
439
|
}
|
|
401
|
-
|
|
402
440
|
|
|
403
441
|
if (handle) {
|
|
404
442
|
handle.transform.position = world.TransformPointToWorldSpace(lastPos + new Vector3(0.5f,0.5f,0.5f));
|
|
405
443
|
handle.transform.localScale = new Vector3(1.01f, 1.01f, 1.01f);
|
|
444
|
+
handle.transform.localRotation = Quaternion.identity;
|
|
406
445
|
|
|
407
446
|
WireCube wireCube = handle.GetComponent<WireCube>();
|
|
408
447
|
if (wireCube) {
|
|
@@ -422,7 +461,7 @@ public class VoxelWorldEditor : UnityEditor.Editor {
|
|
|
422
461
|
|
|
423
462
|
if (faceHandle) {
|
|
424
463
|
faceHandle.transform.position = world.TransformPointToWorldSpace(lastPos + new Vector3(0.5f, 0.5f, 0.5f) + lastNormal * 0.51f);
|
|
425
|
-
faceHandle.transform.rotation = Quaternion.LookRotation(lastNormal);
|
|
464
|
+
faceHandle.transform.rotation = Quaternion.LookRotation(world.TransformVectorToWorldSpace(lastNormal));
|
|
426
465
|
|
|
427
466
|
MeshRenderer ren = faceHandle.GetComponent<MeshRenderer>();
|
|
428
467
|
if (leftControlDown == true) {
|
|
@@ -447,7 +486,7 @@ public class VoxelWorldEditor : UnityEditor.Editor {
|
|
|
447
486
|
Event e = Event.current;
|
|
448
487
|
|
|
449
488
|
//Only allow editing if both the editor window is active and the gizmo toolbar is active
|
|
450
|
-
bool enabled = VoxelBuilderEditorWindow.Enabled() &&
|
|
489
|
+
bool enabled = VoxelBuilderEditorWindow.Enabled() && VoxelWorldEditorToolBase.buttonActive;
|
|
451
490
|
|
|
452
491
|
if (enabled != lastEnabled) {
|
|
453
492
|
CleanupHandles();
|
|
@@ -567,26 +606,35 @@ public class VoxelWorldEditor : UnityEditor.Editor {
|
|
|
567
606
|
SceneView.duringSceneGui += GizmoRefreshEvent;
|
|
568
607
|
}
|
|
569
608
|
|
|
570
|
-
void
|
|
609
|
+
private void OnDestroy() {
|
|
610
|
+
//Remove selection handler
|
|
611
|
+
Selection.selectionChanged -= OnSelectionChanged;
|
|
612
|
+
|
|
613
|
+
//Remove the gizmo refresh event handler
|
|
614
|
+
SceneView.duringSceneGui -= GizmoRefreshEvent;
|
|
615
|
+
}
|
|
616
|
+
|
|
617
|
+
void OnSelectionChanged() {
|
|
571
618
|
if (target == null) {
|
|
572
619
|
return;
|
|
573
620
|
}
|
|
574
621
|
//If we're seleceted
|
|
575
622
|
if (Selection.activeGameObject == ((VoxelWorld)target).gameObject) {
|
|
576
|
-
ToolManager.SetActiveTool<
|
|
623
|
+
ToolManager.SetActiveTool<VoxelWorldEditorToolBase>();
|
|
577
624
|
}
|
|
625
|
+
|
|
626
|
+
|
|
578
627
|
|
|
579
628
|
}
|
|
580
629
|
}
|
|
581
630
|
|
|
582
631
|
|
|
583
632
|
//Create the spiffy toolbar addition
|
|
584
|
-
|
|
585
|
-
public class VoxelWorldEditorTool : EditorTool {
|
|
633
|
+
public class VoxelWorldEditorToolBase : EditorTool {
|
|
586
634
|
|
|
587
635
|
public static bool buttonActive = false;
|
|
588
636
|
|
|
589
|
-
GUIContent iconContent = null;
|
|
637
|
+
static GUIContent iconContent = null;
|
|
590
638
|
|
|
591
639
|
public override void OnActivated() {
|
|
592
640
|
buttonActive = true;
|
|
@@ -608,4 +656,49 @@ public class VoxelWorldEditorTool : EditorTool {
|
|
|
608
656
|
}
|
|
609
657
|
}
|
|
610
658
|
|
|
659
|
+
|
|
660
|
+
|
|
661
|
+
public class VoxelWorldSelectionToolBase : EditorTool {
|
|
662
|
+
|
|
663
|
+
public static bool buttonActive = false;
|
|
664
|
+
|
|
665
|
+
static GUIContent iconContent = null;
|
|
666
|
+
|
|
667
|
+
public override void OnActivated() {
|
|
668
|
+
buttonActive = true;
|
|
669
|
+
|
|
670
|
+
}
|
|
671
|
+
public override void OnWillBeDeactivated() {
|
|
672
|
+
buttonActive = false;
|
|
673
|
+
}
|
|
674
|
+
public override GUIContent toolbarIcon {
|
|
675
|
+
get {
|
|
676
|
+
if (iconContent == null) {
|
|
677
|
+
iconContent = new GUIContent() {
|
|
678
|
+
image = Resources.Load<Texture>("SelectIcon"),
|
|
679
|
+
tooltip = "Selection"
|
|
680
|
+
};
|
|
681
|
+
}
|
|
682
|
+
return iconContent;
|
|
683
|
+
}
|
|
684
|
+
}
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
[EditorTool("Edit Voxel World", typeof(VoxelWorld))]
|
|
688
|
+
public class VoxelWorldSelectionToolVW : VoxelWorldSelectionToolBase {
|
|
689
|
+
}
|
|
690
|
+
|
|
691
|
+
[EditorTool("Edit Voxel Selection", typeof(VoxelWorld))]
|
|
692
|
+
public class VoxelWorldEditorToolVW : VoxelWorldEditorToolBase {
|
|
693
|
+
}
|
|
694
|
+
|
|
695
|
+
//Same again for SelectionZone
|
|
696
|
+
[EditorTool("Edit Voxel World", typeof(SelectionZone))]
|
|
697
|
+
public class VoxelWorldSelectionToolSZ : VoxelWorldSelectionToolBase {
|
|
698
|
+
}
|
|
699
|
+
|
|
700
|
+
[EditorTool("Edit Voxel Selection", typeof(SelectionZone))]
|
|
701
|
+
public class VoxelWorldEditorToolSZ : VoxelWorldEditorToolBase {
|
|
702
|
+
}
|
|
703
|
+
|
|
611
704
|
#endif
|
|
Binary file
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
fileFormatVersion: 2
|
|
2
|
+
guid: e096bf0b5cc9a8240915e1374148925c
|
|
3
|
+
TextureImporter:
|
|
4
|
+
internalIDToNameTable: []
|
|
5
|
+
externalObjects: {}
|
|
6
|
+
serializedVersion: 13
|
|
7
|
+
mipmaps:
|
|
8
|
+
mipMapMode: 0
|
|
9
|
+
enableMipMap: 0
|
|
10
|
+
sRGBTexture: 1
|
|
11
|
+
linearTexture: 0
|
|
12
|
+
fadeOut: 0
|
|
13
|
+
borderMipMap: 0
|
|
14
|
+
mipMapsPreserveCoverage: 0
|
|
15
|
+
alphaTestReferenceValue: 0.5
|
|
16
|
+
mipMapFadeDistanceStart: 1
|
|
17
|
+
mipMapFadeDistanceEnd: 3
|
|
18
|
+
bumpmap:
|
|
19
|
+
convertToNormalMap: 0
|
|
20
|
+
externalNormalMap: 0
|
|
21
|
+
heightScale: 0.25
|
|
22
|
+
normalMapFilter: 0
|
|
23
|
+
flipGreenChannel: 0
|
|
24
|
+
isReadable: 0
|
|
25
|
+
streamingMipmaps: 0
|
|
26
|
+
streamingMipmapsPriority: 0
|
|
27
|
+
vTOnly: 0
|
|
28
|
+
ignoreMipmapLimit: 0
|
|
29
|
+
grayScaleToAlpha: 0
|
|
30
|
+
generateCubemap: 6
|
|
31
|
+
cubemapConvolution: 0
|
|
32
|
+
seamlessCubemap: 0
|
|
33
|
+
textureFormat: 1
|
|
34
|
+
maxTextureSize: 2048
|
|
35
|
+
textureSettings:
|
|
36
|
+
serializedVersion: 2
|
|
37
|
+
filterMode: 1
|
|
38
|
+
aniso: 1
|
|
39
|
+
mipBias: 0
|
|
40
|
+
wrapU: 1
|
|
41
|
+
wrapV: 1
|
|
42
|
+
wrapW: 0
|
|
43
|
+
nPOTScale: 0
|
|
44
|
+
lightmap: 0
|
|
45
|
+
compressionQuality: 50
|
|
46
|
+
spriteMode: 0
|
|
47
|
+
spriteExtrude: 1
|
|
48
|
+
spriteMeshType: 1
|
|
49
|
+
alignment: 0
|
|
50
|
+
spritePivot: {x: 0.5, y: 0.5}
|
|
51
|
+
spritePixelsToUnits: 100
|
|
52
|
+
spriteBorder: {x: 0, y: 0, z: 0, w: 0}
|
|
53
|
+
spriteGenerateFallbackPhysicsShape: 1
|
|
54
|
+
alphaUsage: 1
|
|
55
|
+
alphaIsTransparency: 1
|
|
56
|
+
spriteTessellationDetail: -1
|
|
57
|
+
textureType: 2
|
|
58
|
+
textureShape: 1
|
|
59
|
+
singleChannelComponent: 0
|
|
60
|
+
flipbookRows: 1
|
|
61
|
+
flipbookColumns: 1
|
|
62
|
+
maxTextureSizeSet: 0
|
|
63
|
+
compressionQualitySet: 0
|
|
64
|
+
textureFormatSet: 0
|
|
65
|
+
ignorePngGamma: 0
|
|
66
|
+
applyGammaDecoding: 0
|
|
67
|
+
swizzle: 50462976
|
|
68
|
+
cookieLightType: 0
|
|
69
|
+
platformSettings:
|
|
70
|
+
- serializedVersion: 3
|
|
71
|
+
buildTarget: DefaultTexturePlatform
|
|
72
|
+
maxTextureSize: 2048
|
|
73
|
+
resizeAlgorithm: 0
|
|
74
|
+
textureFormat: -1
|
|
75
|
+
textureCompression: 1
|
|
76
|
+
compressionQuality: 50
|
|
77
|
+
crunchedCompression: 1
|
|
78
|
+
allowsAlphaSplitting: 0
|
|
79
|
+
overridden: 0
|
|
80
|
+
ignorePlatformSupport: 0
|
|
81
|
+
androidETC2FallbackOverride: 0
|
|
82
|
+
forceMaximumCompressionQuality_BC6H_BC7: 0
|
|
83
|
+
- serializedVersion: 3
|
|
84
|
+
buildTarget: Standalone
|
|
85
|
+
maxTextureSize: 2048
|
|
86
|
+
resizeAlgorithm: 0
|
|
87
|
+
textureFormat: -1
|
|
88
|
+
textureCompression: 1
|
|
89
|
+
compressionQuality: 50
|
|
90
|
+
crunchedCompression: 0
|
|
91
|
+
allowsAlphaSplitting: 0
|
|
92
|
+
overridden: 0
|
|
93
|
+
ignorePlatformSupport: 0
|
|
94
|
+
androidETC2FallbackOverride: 0
|
|
95
|
+
forceMaximumCompressionQuality_BC6H_BC7: 0
|
|
96
|
+
- serializedVersion: 3
|
|
97
|
+
buildTarget: Server
|
|
98
|
+
maxTextureSize: 2048
|
|
99
|
+
resizeAlgorithm: 0
|
|
100
|
+
textureFormat: -1
|
|
101
|
+
textureCompression: 1
|
|
102
|
+
compressionQuality: 50
|
|
103
|
+
crunchedCompression: 0
|
|
104
|
+
allowsAlphaSplitting: 0
|
|
105
|
+
overridden: 0
|
|
106
|
+
ignorePlatformSupport: 0
|
|
107
|
+
androidETC2FallbackOverride: 0
|
|
108
|
+
forceMaximumCompressionQuality_BC6H_BC7: 0
|
|
109
|
+
- serializedVersion: 3
|
|
110
|
+
buildTarget: Android
|
|
111
|
+
maxTextureSize: 2048
|
|
112
|
+
resizeAlgorithm: 0
|
|
113
|
+
textureFormat: -1
|
|
114
|
+
textureCompression: 1
|
|
115
|
+
compressionQuality: 50
|
|
116
|
+
crunchedCompression: 0
|
|
117
|
+
allowsAlphaSplitting: 0
|
|
118
|
+
overridden: 0
|
|
119
|
+
ignorePlatformSupport: 0
|
|
120
|
+
androidETC2FallbackOverride: 0
|
|
121
|
+
forceMaximumCompressionQuality_BC6H_BC7: 0
|
|
122
|
+
- serializedVersion: 3
|
|
123
|
+
buildTarget: iPhone
|
|
124
|
+
maxTextureSize: 2048
|
|
125
|
+
resizeAlgorithm: 0
|
|
126
|
+
textureFormat: -1
|
|
127
|
+
textureCompression: 1
|
|
128
|
+
compressionQuality: 50
|
|
129
|
+
crunchedCompression: 0
|
|
130
|
+
allowsAlphaSplitting: 0
|
|
131
|
+
overridden: 0
|
|
132
|
+
ignorePlatformSupport: 0
|
|
133
|
+
androidETC2FallbackOverride: 0
|
|
134
|
+
forceMaximumCompressionQuality_BC6H_BC7: 0
|
|
135
|
+
spriteSheet:
|
|
136
|
+
serializedVersion: 2
|
|
137
|
+
sprites: []
|
|
138
|
+
outline: []
|
|
139
|
+
physicsShape: []
|
|
140
|
+
bones: []
|
|
141
|
+
spriteID:
|
|
142
|
+
internalID: 0
|
|
143
|
+
vertices: []
|
|
144
|
+
indices:
|
|
145
|
+
edges: []
|
|
146
|
+
weights: []
|
|
147
|
+
secondaryTextures: []
|
|
148
|
+
nameFileIdTable: {}
|
|
149
|
+
mipmapLimitGroupName:
|
|
150
|
+
pSDRemoveMatte: 0
|
|
151
|
+
userData:
|
|
152
|
+
assetBundleName:
|
|
153
|
+
assetBundleVariant:
|
|
@@ -138,6 +138,11 @@ public partial class VoxelWorld : MonoBehaviour {
|
|
|
138
138
|
return transform.localToWorldMatrix.MultiplyPoint(point);
|
|
139
139
|
}
|
|
140
140
|
|
|
141
|
+
public Vector3 TransformVectorToWorldSpace(Vector3 vec) {
|
|
142
|
+
return transform.localToWorldMatrix.MultiplyVector(vec);
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
|
|
141
146
|
public void InvokeOnFinishedReplicatingChunksFromServer() {
|
|
142
147
|
this.finishedReplicatingChunksFromServer = true;
|
|
143
148
|
this.OnFinishedReplicatingChunksFromServer?.Invoke();
|
package/package.json
CHANGED
|
File without changes
|