Collisions editing progress

This commit is contained in:
dexy 2020-01-12 22:53:57 +11:00
parent dab6c7101e
commit 8f903610bf
4 changed files with 305 additions and 48 deletions

View File

@ -981,30 +981,9 @@ namespace CodeWalker.GameFiles
byte b0 = polygonData[offset]; byte b0 = polygonData[offset];
polygonData[offset] = (byte)(b0 & 0xF8);//mask it off polygonData[offset] = (byte)(b0 & 0xF8);//mask it off
BoundPolygonType type = (BoundPolygonType)(b0 & 7); BoundPolygonType type = (BoundPolygonType)(b0 & 7);
BoundPolygon p = null; BoundPolygon p = CreatePolygon(type);
switch (type)
{
case BoundPolygonType.Triangle:
p = new BoundPolygonTriangle();
break;
case BoundPolygonType.Sphere:
p = new BoundPolygonSphere();
break;
case BoundPolygonType.Capsule:
p = new BoundPolygonCapsule();
break;
case BoundPolygonType.Box:
p = new BoundPolygonBox();
break;
case BoundPolygonType.Cylinder:
p = new BoundPolygonCylinder();
break;
default:
break;
}
if (p != null) if (p != null)
{ {
p.Owner = this;
p.Index = i; p.Index = i;
p.Read(polygonData, offset); p.Read(polygonData, offset);
} }
@ -1728,15 +1707,26 @@ namespace CodeWalker.GameFiles
var verts = Vertices.ToList(); var verts = Vertices.ToList();
var verts2 = Vertices2?.ToList(); var verts2 = Vertices2?.ToList();
var vertcols = VertexColours?.ToList(); var vertcols = VertexColours?.ToList();
var vertobjs = VertexObjects?.ToList();
verts.RemoveAt(index); verts.RemoveAt(index);
verts2?.RemoveAt(index); verts2?.RemoveAt(index);
vertcols?.RemoveAt(index); vertcols?.RemoveAt(index);
vertobjs?.RemoveAt(index);
Vertices = verts.ToArray(); Vertices = verts.ToArray();
Vertices2 = verts2?.ToArray(); Vertices2 = verts2?.ToArray();
VertexColours = vertcols?.ToArray(); VertexColours = vertcols?.ToArray();
VertexObjects = vertobjs?.ToArray();
VerticesCount = (uint)verts.Count; VerticesCount = (uint)verts.Count;
Vertices2Count = VerticesCount; Vertices2Count = VerticesCount;
if (VertexObjects != null)
{
for (int i = 0; i < VertexObjects.Length; i++)
{
if (VertexObjects[i] != null) VertexObjects[i].Index = i;
}
}
if (Polygons != null) if (Polygons != null)
{ {
var delpolys = new List<BoundPolygon>(); var delpolys = new List<BoundPolygon>();
@ -1777,6 +1767,87 @@ namespace CodeWalker.GameFiles
return false; return false;
} }
public int AddVertex()
{
var verts = Vertices?.ToList() ?? new List<Vector3>();
var verts2 = Vertices2?.ToList();
var vertcols = VertexColours?.ToList();
var vertobjs = VertexObjects?.ToList();
var index = verts.Count;
verts.Add(Vector3.Zero);
verts2?.Add(Vector3.Zero);
vertcols?.Add(new BoundMaterialColour());
vertobjs?.Add(null);
Vertices = verts.ToArray();
Vertices2 = verts2?.ToArray();
VertexColours = vertcols?.ToArray();
VertexObjects = vertobjs?.ToArray();
VerticesCount = (uint)verts.Count;
Vertices2Count = VerticesCount;
return index;
}
public BoundPolygon AddPolygon(BoundPolygonType type)
{
var p = CreatePolygon(type);
var polys = Polygons?.ToList() ?? new List<BoundPolygon>();
var polymats = PolygonMaterialIndices?.ToList() ?? new List<byte>();
p.Index = polys.Count;
polys.Add(p);
polymats.Add(0);
Polygons = polys.ToArray();
PolygonMaterialIndices = polymats.ToArray();
PolygonsCount = (uint)polys.Count;
var vinds = p.VertexIndices; //just get the required array size
if (vinds != null)
{
for (int i = 0; i < vinds.Length; i++)
{
vinds[i] = AddVertex();
}
p.VertexIndices = vinds;
}
return p;
}
private BoundPolygon CreatePolygon(BoundPolygonType type)
{
BoundPolygon p = null;
switch (type)
{
case BoundPolygonType.Triangle:
p = new BoundPolygonTriangle();
break;
case BoundPolygonType.Sphere:
p = new BoundPolygonSphere();
break;
case BoundPolygonType.Capsule:
p = new BoundPolygonCapsule();
break;
case BoundPolygonType.Box:
p = new BoundPolygonBox();
break;
case BoundPolygonType.Cylinder:
p = new BoundPolygonCylinder();
break;
default:
break;
}
if (p != null)
{
p.Owner = this;
}
return p;
}
} }
[TC(typeof(EXP))] public class BoundBVH : BoundGeometry [TC(typeof(EXP))] public class BoundBVH : BoundGeometry
{ {
@ -2519,6 +2590,35 @@ namespace CodeWalker.GameFiles
} }
} }
public BoundMaterial_s? MaterialCustom; //for editing, when assigning a new material. public BoundMaterial_s? MaterialCustom; //for editing, when assigning a new material.
public Vector3[] VertexPositions
{
get
{
var inds = VertexIndices;
var va = new Vector3[inds.Length];
if (Owner != null)
{
for (int i = 0; i < inds.Length; i++)
{
va[i] = Owner.GetVertexPos(inds[i]);
}
}
return va;
}
set
{
if (value == null) return;
var inds = VertexIndices;
if (Owner != null)
{
var imax = Math.Min(inds.Length, value.Length);
for (int i = 0; i < imax; i++)
{
Owner.SetVertexPos(inds[i], value[i]);
}
}
}
}
public int Index { get; set; } //for editing convenience, not stored public int Index { get; set; } //for editing convenience, not stored
public abstract Vector3 BoxMin { get; } public abstract Vector3 BoxMin { get; }
public abstract Vector3 BoxMax { get; } public abstract Vector3 BoxMax { get; }

View File

@ -176,7 +176,7 @@ namespace CodeWalker.Project.Panels
if (CollisionCylinder != null) if (CollisionCylinder != null)
{ {
CylVertex1TextBox.Text = FloatUtil.GetVector3String(CollisionCylinder.Vertex1); CylVertex1TextBox.Text = FloatUtil.GetVector3String(CollisionCylinder.Vertex1);
CylVertex2TextBox.Text = FloatUtil.GetVector3String(CollisionCylinder.Vertex1); CylVertex2TextBox.Text = FloatUtil.GetVector3String(CollisionCylinder.Vertex2);
CylRadiusTextBox.Text = FloatUtil.ToString(CollisionCylinder.cylinderRadius); CylRadiusTextBox.Text = FloatUtil.ToString(CollisionCylinder.cylinderRadius);
if (!PolyTabControl.TabPages.Contains(CylinderTabPage)) PolyTabControl.TabPages.Add(CylinderTabPage); if (!PolyTabControl.TabPages.Contains(CylinderTabPage)) PolyTabControl.TabPages.Add(CylinderTabPage);
} }

View File

@ -1496,7 +1496,7 @@ namespace CodeWalker.Project
public object NewObject(MapSelection sel, bool copyPosition = false, bool selectNew = true) public object NewObject(MapSelection sel, bool copyPosition = false, bool selectNew = true)
{ {
//general method to add a new object, given a map selection //general method to add a new object, given a map selection
SelectObject(ref sel); SetObject(ref sel);
if (sel.MultipleSelectionItems != null) if (sel.MultipleSelectionItems != null)
{ {
var objs = new List<object>(); var objs = new List<object>();
@ -1517,11 +1517,13 @@ namespace CodeWalker.Project
else if (sel.ScenarioNode != null) return NewScenarioNode(sel.ScenarioNode, copyPosition, selectNew); else if (sel.ScenarioNode != null) return NewScenarioNode(sel.ScenarioNode, copyPosition, selectNew);
else if (sel.Audio?.AudioZone != null) return NewAudioZone(sel.Audio, copyPosition, selectNew); else if (sel.Audio?.AudioZone != null) return NewAudioZone(sel.Audio, copyPosition, selectNew);
else if (sel.Audio?.AudioEmitter != null) return NewAudioEmitter(sel.Audio, copyPosition, selectNew); else if (sel.Audio?.AudioEmitter != null) return NewAudioEmitter(sel.Audio, copyPosition, selectNew);
else if (sel.CollisionPoly != null) return NewCollisionPoly(sel.CollisionPoly.Type, sel.CollisionPoly, copyPosition, selectNew);
else if (sel.CollisionBounds != null) return NewCollisionBounds(sel.CollisionBounds.Type, sel.CollisionBounds, copyPosition, selectNew);
return null; return null;
} }
public void DeleteObject(MapSelection sel) public void DeleteObject(MapSelection sel)
{ {
SelectObject(ref sel); SetObject(ref sel);
if (sel.MultipleSelectionItems != null) if (sel.MultipleSelectionItems != null)
{ {
for (int i = 0; i < sel.MultipleSelectionItems.Length; i++) for (int i = 0; i < sel.MultipleSelectionItems.Length; i++)
@ -1543,7 +1545,7 @@ namespace CodeWalker.Project
else if (sel.CollisionPoly != null) DeleteCollisionPoly(); else if (sel.CollisionPoly != null) DeleteCollisionPoly();
else if (sel.CollisionBounds != null) DeleteCollisionBounds(); else if (sel.CollisionBounds != null) DeleteCollisionBounds();
} }
public void SelectObject(ref MapSelection sel) private void SetObject(ref MapSelection sel)
{ {
if (sel.MultipleSelectionItems != null) { } //todo... if (sel.MultipleSelectionItems != null) { } //todo...
else if (sel.EntityDef != null) SetProjectItem(sel.EntityDef, false); else if (sel.EntityDef != null) SetProjectItem(sel.EntityDef, false);
@ -1930,6 +1932,11 @@ namespace CodeWalker.Project
CurrentEntity = null; CurrentEntity = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool IsCurrentEntity(YmapEntityDef ent) public bool IsCurrentEntity(YmapEntityDef ent)
@ -2047,6 +2054,11 @@ namespace CodeWalker.Project
CurrentGrassBatch = null; CurrentGrassBatch = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public void PaintGrass(SpaceRayIntersectResult mouseRay, bool erase) public void PaintGrass(SpaceRayIntersectResult mouseRay, bool erase)
@ -2197,6 +2209,11 @@ namespace CodeWalker.Project
CurrentCarGen = null; CurrentCarGen = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool IsCurrentCarGen(YmapCarGen cargen) public bool IsCurrentCarGen(YmapCarGen cargen)
@ -2844,6 +2861,11 @@ namespace CodeWalker.Project
CurrentArchetype = null; CurrentArchetype = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool DeleteMloEntity() public bool DeleteMloEntity()
@ -2902,7 +2924,11 @@ namespace CodeWalker.Project
ClosePanel((EditYmapEntityPanel p) => { return p.Tag == delent; }); ClosePanel((EditYmapEntityPanel p) => { return p.Tag == delent; });
CurrentEntity = null; CurrentEntity = null;
CurrentMloEntity = null; CurrentMloEntity = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null); WorldForm.SelectItem(null);
}
return true; return true;
} }
@ -2928,6 +2954,11 @@ namespace CodeWalker.Project
ClosePanel((EditYtypMloRoomPanel p) => { return p.Tag == CurrentMloRoom; }); ClosePanel((EditYtypMloRoomPanel p) => { return p.Tag == CurrentMloRoom; });
CurrentMloRoom = null; CurrentMloRoom = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool DeleteMloPortal() public bool DeleteMloPortal()
@ -2952,6 +2983,11 @@ namespace CodeWalker.Project
ClosePanel((EditYtypMloPortalPanel p) => { return p.Tag == CurrentMloPortal; }); ClosePanel((EditYtypMloPortalPanel p) => { return p.Tag == CurrentMloPortal; });
CurrentMloPortal = null; CurrentMloPortal = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool DeleteMloEntitySet() public bool DeleteMloEntitySet()
@ -2977,6 +3013,11 @@ namespace CodeWalker.Project
ClosePanel((EditYtypMloEntSetPanel p) => { return p.Tag == CurrentMloEntitySet; }); ClosePanel((EditYtypMloEntSetPanel p) => { return p.Tag == CurrentMloEntitySet; });
CurrentMloEntitySet = null; CurrentMloEntitySet = null;
if (WorldForm != null)
{
WorldForm.SelectItem(null);
}
return true; return true;
} }
@ -3292,14 +3333,16 @@ namespace CodeWalker.Project
CurrentCollisionBounds = null; CurrentCollisionBounds = null;
if (parent != null)
{
if (WorldForm != null) if (WorldForm != null)
{
if (parent != null)
{ {
WorldForm.UpdateCollisionBoundsGraphics(parent); WorldForm.UpdateCollisionBoundsGraphics(parent);
} }
WorldForm.SelectItem(null);
} }
return true; return true;
} }
public bool IsCurrentCollisionBounds(Bounds bounds) public bool IsCurrentCollisionBounds(Bounds bounds)
@ -3309,11 +3352,118 @@ namespace CodeWalker.Project
public BoundPolygon NewCollisionPoly(BoundPolygonType type, BoundPolygon copy = null, bool copyPosition = false, bool selectNew = true) public BoundPolygon NewCollisionPoly(BoundPolygonType type, BoundPolygon copy = null, bool copyPosition = false, bool selectNew = true)
{ {
if (CurrentYbnFile == null) return null; var bgeom = CurrentCollisionBounds as BoundGeometry;
if (bgeom == null) return null;
//////// TODO!!
return null; var poly = bgeom.AddPolygon(type);
var ptri = poly as BoundPolygonTriangle;
var psph = poly as BoundPolygonSphere;
var pcap = poly as BoundPolygonCapsule;
var pbox = poly as BoundPolygonBox;
var pcyl = poly as BoundPolygonCylinder;
var ctri = copy as BoundPolygonTriangle;
var csph = copy as BoundPolygonSphere;
var ccap = copy as BoundPolygonCapsule;
var cbox = copy as BoundPolygonBox;
var ccyl = copy as BoundPolygonCylinder;
if (ptri != null)
{
ptri.edgeIndex1 = -1;
ptri.edgeIndex2 = -1;
ptri.edgeIndex3 = -1;
}
if (copy != null)
{
poly.VertexPositions = copy.VertexPositions;
poly.Material = copy.Material;
switch (type)
{
case BoundPolygonType.Triangle:
if ((ptri != null) && (ctri != null))
{
ptri.vertFlag1 = ctri.vertFlag1;
ptri.vertFlag2 = ctri.vertFlag2;
ptri.vertFlag3 = ctri.vertFlag3;
}
break;
case BoundPolygonType.Sphere:
if ((psph != null) && (csph != null))
{
psph.sphereRadius = csph.sphereRadius;
}
break;
case BoundPolygonType.Capsule:
if ((pcap != null) && (ccap != null))
{
pcap.capsuleRadius = ccap.capsuleRadius;
}
break;
case BoundPolygonType.Box:
if ((pbox != null) && (cbox != null))
{
}
break;
case BoundPolygonType.Cylinder:
if ((pcyl != null) && (ccyl != null))
{
pcyl.cylinderRadius = ccyl.cylinderRadius;
}
break;
default:
break;
}
}
else
{
var pos = GetSpawnPos(10.0f);
var x = Vector3.UnitX;
var y = Vector3.UnitY;
var z = Vector3.UnitZ;
if (ptri != null)
{
ptri.VertexPositions = new[] { pos, pos + x, pos + y };
}
if (psph != null)
{
psph.VertexPositions = new[] { pos };
psph.sphereRadius = 1.0f;
}
if (pcap != null)
{
pcap.VertexPositions = new[] { pos - x, pos + x };
pcap.capsuleRadius = 1.0f;
}
if (pbox != null)
{
pbox.VertexPositions = new[] { pos - x + y - z, pos - x - y + z, pos + x + y + z, pos + x - y - z };
}
if (pcyl != null)
{
pcyl.VertexPositions = new[] { pos - x, pos + x };
pcyl.cylinderRadius = 1.0f;
}
}
if (selectNew)
{
//LoadProjectTree();//is this necessary?
ProjectExplorer?.TrySelectCollisionPolyTreeNode(poly);
CurrentCollisionPoly = poly;
//ShowEditYbnPanel(false);;
ShowEditYbnBoundPolyPanel(false);
}
if (WorldForm != null)
{
WorldForm.UpdateCollisionBoundsGraphics(bgeom);
}
return poly;
} }
public void AddCollisionPolyToProject() public void AddCollisionPolyToProject()
{ {
@ -3385,6 +3535,7 @@ namespace CodeWalker.Project
if (WorldForm != null) if (WorldForm != null)
{ {
WorldForm.UpdateCollisionBoundsGraphics(CurrentCollisionBounds); WorldForm.UpdateCollisionBoundsGraphics(CurrentCollisionBounds);
WorldForm.SelectItem(null);
} }
return true; return true;
@ -3461,6 +3612,12 @@ namespace CodeWalker.Project
CurrentCollisionVertex = null; CurrentCollisionVertex = null;
if (WorldForm != null)
{
WorldForm.UpdateCollisionBoundsGraphics(CurrentCollisionBounds);
WorldForm.SelectItem(null);
}
return true; return true;
} }
public bool IsCurrentCollisionVertex(BoundVertex vertex) public bool IsCurrentCollisionVertex(BoundVertex vertex)
@ -3764,6 +3921,7 @@ namespace CodeWalker.Project
if (WorldForm != null) if (WorldForm != null)
{ {
WorldForm.UpdatePathYndGraphics(CurrentYndFile, false); WorldForm.UpdatePathYndGraphics(CurrentYndFile, false);
WorldForm.SelectItem(null);
} }
return true; return true;
@ -4247,6 +4405,7 @@ namespace CodeWalker.Project
if (WorldForm != null) if (WorldForm != null)
{ {
WorldForm.UpdateTrainTrackGraphics(CurrentTrainTrack, false); WorldForm.UpdateTrainTrackGraphics(CurrentTrainTrack, false);
WorldForm.SelectItem(null);
} }
return true; return true;
@ -4526,9 +4685,9 @@ namespace CodeWalker.Project
if (WorldForm != null) if (WorldForm != null)
{ {
WorldForm.UpdateScenarioGraphics(CurrentScenario, false); WorldForm.UpdateScenarioGraphics(CurrentScenario, false);
WorldForm.SelectItem(null);
} }
return true; return true;
} }
public bool IsCurrentScenarioNode(ScenarioNode node) public bool IsCurrentScenarioNode(ScenarioNode node)
@ -5705,13 +5864,10 @@ namespace CodeWalker.Project
CurrentAudioZone = null; CurrentAudioZone = null;
//if (WorldForm != null) if (WorldForm != null)
//{ {
// lock (WorldForm.RenderSyncRoot) WorldForm.SelectItem(null);
// { }
// WorldForm.SelectItem(null);
// }
//}
return true; return true;
} }
@ -5826,13 +5982,11 @@ namespace CodeWalker.Project
ClosePanel((EditAudioEmitterPanel p) => { return p.CurrentEmitter.AudioEmitter == delem.AudioEmitter; }); ClosePanel((EditAudioEmitterPanel p) => { return p.CurrentEmitter.AudioEmitter == delem.AudioEmitter; });
//if (WorldForm != null)
//{ if (WorldForm != null)
// lock (WorldForm.RenderSyncRoot) {
// { WorldForm.SelectItem(null);
// WorldForm.SelectItem(null); }
// }
//}
return true; return true;
} }
@ -6439,7 +6593,7 @@ namespace CodeWalker.Project
if (ybn.Bounds != null) if (ybn.Bounds != null)
{ {
var hit = ybn.Bounds.RayIntersect(ref mray); //TODO: interior ybns! var hit = ybn.Bounds.RayIntersect(ref mray); //TODO: interior ybns!
if (hit.Hit) if (hit.Hit && (hit.HitDist < curHit.HitDist))
{ {
curHit.UpdateCollisionFromRayHit(ref hit, camera); curHit.UpdateCollisionFromRayHit(ref hit, camera);
} }

View File

@ -804,6 +804,9 @@ namespace CodeWalker
else if (ScenarioNode != null) return true; else if (ScenarioNode != null) return true;
else if (Audio?.AudioZone != null) return true; else if (Audio?.AudioZone != null) return true;
else if (Audio?.AudioEmitter != null) return true; else if (Audio?.AudioEmitter != null) return true;
else if (CollisionVertex != null) return false;//can't copy just a vertex..
else if (CollisionPoly != null) return true;
else if (CollisionBounds != null) return true;
return false; return false;
} }
} }