public void Read(BinaryReaderEx br) { magic = br.ReadUInt32(); size = br.ReadUInt32(); numTex = br.ReadInt16(); numPals = br.ReadInt16(); skipToTex = br.ReadUInt32(); skipToPal = br.ReadUInt32(); skipToUnk = br.ReadUInt32(); ptrNext = br.ReadUInt32(); zero = br.ReadUInt32(); for (int i = 0; i < numPals; i++) { int numCols = br.ReadInt32(); List <Color> palette = new List <Color>(); for (int j = 0; j < numCols; j++) { palette.Add(Tim.Convert16(br.ReadUInt16(), false)); } pals.Add(palette); } for (int i = 0; i < numTex; i++) { Console.WriteLine(br.HexPos()); tex.Add(new Tex(br)); } }
/// <summary> /// Builds CTR model from raw data arrays. /// </summary> /// <param name="name">Model name.</param> /// <param name="vertices">Vertex array.</param> /// <param name="colors">Color array.</param> /// <param name="faces">Face indices array.</param> /// <returns>CtrHeader object.</returns> public static CtrMesh FromRawData(string name, List <Vector3f> vertices, List <Vector4b> colors, List <Vector3i> faces) { CtrMesh model = new CtrMesh(); model.name = name + "_hi"; model.lodDistance = -1; List <Vector4b> cc = new List <Vector4b>(); foreach (var c in colors) { System.Drawing.Color cl = Tim.Convert16(Tim.ConvertTo16(System.Drawing.Color.FromArgb(c.W, c.Z, c.Y, c.X)), false); if (cl.R == 255 && cl.G == 0 && cl.B == 255) { cl = System.Drawing.Color.Black; } cc.Add(new Vector4b(cl.R, cl.G, cl.B, 0)); } colors = cc; //get distinct values from input lists List <Vector3f> dVerts = new List <Vector3f>(); List <Vector4b> dColors = new List <Vector4b>(); foreach (var v in vertices) { if (!dVerts.Contains(v)) { dVerts.Add(v); } } foreach (var c in colors) { if (!dColors.Contains(c)) { dColors.Add(c); } } //recalculate indices for distinct arrays List <Vector3i> vfaces = new List <Vector3i>(); List <Vector3i> cfaces = new List <Vector3i>(); if (dVerts.Count != vertices.Count) { foreach (var f in faces) { vfaces.Add(new Vector3i( dVerts.IndexOf(vertices[f.X]), dVerts.IndexOf(vertices[f.Y]), dVerts.IndexOf(vertices[f.Z]) )); } } if (dColors.Count != colors.Count) { foreach (var f in faces) { cfaces.Add(new Vector3i( dColors.IndexOf(colors[f.X]), dColors.IndexOf(colors[f.Y]), dColors.IndexOf(colors[f.Z]) )); } } if (vfaces.Count == 0) { vfaces = faces; } if (cfaces.Count == 0) { cfaces = faces; } int clutlimit = 128; //check for clut overflow if (dColors.Count > clutlimit) { Helpers.Panic("CtrHeader", "More than 128 distinct colors! Truncating..."); dColors = dColors.GetRange(0, clutlimit); foreach (var x in cfaces) { if (x.X >= clutlimit) { x.X = 0; } if (x.Y >= clutlimit) { x.Y = 0; } if (x.Z >= clutlimit) { x.Z = 0; } } } //get bbox BoundingBox bb = BoundingBox.GetBB(dVerts); //offset the bbox to world origin BoundingBox bb2 = bb - bb.minf; //offset all vertices to world origin for (int i = 0; i < dVerts.Count; i++) { dVerts[i] -= bb.minf; } //save converted offset to model model.posOffset = new Vector4s( (short)(bb.minf.X / bb2.maxf.X * 255), (short)(bb.minf.Y / bb2.maxf.Y * 255), (short)(bb.minf.Z / bb2.maxf.Z * 255), 0); //save scale to model model.scale = new Vector4s( (short)(bb2.maxf.X * 1000f), (short)(bb2.maxf.Y * 1000f), (short)(bb2.maxf.Z * 1000f), 0); //compress vertices to byte vector model.vtx.Clear(); foreach (var v in dVerts) { Vector3b vv = new Vector3b( (byte)(v.X / bb2.maxf.X * 255), (byte)(v.Z / bb2.maxf.Z * 255), (byte)(v.Y / bb2.maxf.Y * 255) ); model.vtx.Add(vv); } //save colors if (dColors.Count > 0) { model.cols = dColors; } else { model.cols.Add(new Vector4b(0x40, 0x40, 0x40, 0)); model.cols.Add(new Vector4b(0x80, 0x80, 0x80, 0)); model.cols.Add(new Vector4b(0xC0, 0xC0, 0xC0, 0)); } //create new vertex array and loop through all faces List <Vector3b> newlist = new List <Vector3b>(); for (int i = 0; i < faces.Count; i++) { CtrDraw[] cmd = new CtrDraw[3]; cmd[0] = new CtrDraw() { texIndex = 0, colorIndex = (byte)cfaces[i].X, stackIndex = 87, flags = CtrDrawFlags.s | CtrDrawFlags.d //| CtrDrawFlags.k }; cmd[1] = new CtrDraw() { texIndex = 0, colorIndex = (byte)cfaces[i].Z, stackIndex = 88, flags = CtrDrawFlags.d //| CtrDrawFlags.k }; cmd[2] = new CtrDraw() { texIndex = 0, colorIndex = (byte)cfaces[i].Y, stackIndex = 89, flags = CtrDrawFlags.d //| CtrDrawFlags.k }; newlist.Add(model.vtx[vfaces[i].X]); newlist.Add(model.vtx[vfaces[i].Z]); newlist.Add(model.vtx[vfaces[i].Y]); model.drawList.AddRange(cmd); } model.vtx = newlist; return(model); }