Ejemplo n.º 1
0
 public uint this[IntVector3 pos]
 {
     get
     {
         return data[GetIndexForVoxel(pos)];
     }
     set
     {
         data[GetIndexForVoxel(pos)] = value;
     }
 }
Ejemplo n.º 2
0
        public void GenerateTextureAndUV(VoxelModel model, MeshSlices slices, out Bitmap bitmap, IProgressListener progress)
        {
            // Collect colors
            var colors = new List<int>(); // Marshal.Copy doesn't support uint[] lol

            int totalSlices = 0;
            foreach (var slicelist in slices)
            {
                totalSlices += slicelist.Length;
            }

            int sliceIndex = 0;

            progress?.Report("Collecting colors");

            foreach (var slicelist in slices)
            {
                foreach (var slice in slicelist)
                {
                    ++sliceIndex;
                    progress?.Report((double)sliceIndex / totalSlices);

                    var verts = slice.Positions;
                    Axis3 paxis1, paxis2;
                    GetPerpendicularAxises(slice.Axis, out paxis1, out paxis2);

                    var pt = new IntVector3();
                    pt[slice.Axis] = slice.Layer;

                    foreach (var face in slice.MeshSliceFaces)
                    {
                        var scoord = FindSliceCoordForFace(slice, face, slice.Axis, paxis1, paxis2);
                        pt[paxis1] = scoord.X;
                        pt[paxis2] = scoord.Y;

                        colors.Add((int) (model[pt] | 0xff000000));
                    }
                }
            }

            // Determine the dimensions of the texture
            int texwidth = (int)Math.Ceiling(Math.Sqrt(colors.Count));
            int texheight = (colors.Count + texwidth - 1) / texwidth;

            // And then create the texture
            bitmap = new Bitmap(texwidth * 2, texheight * 2,
                                System.Drawing.Imaging.PixelFormat.Format32bppRgb);
            var bmpdata = bitmap.LockBits(new Rectangle(0, 0, bitmap.Width, bitmap.Height),
                                          System.Drawing.Imaging.ImageLockMode.WriteOnly,
                                          System.Drawing.Imaging.PixelFormat.Format32bppRgb);

            System.Runtime.InteropServices.Marshal.Copy(Scale2x(colors.ToArray(), texwidth, texheight), 0,
                                                        bmpdata.Scan0, colors.Count * 4);

            bitmap.UnlockBits(bmpdata);

            // Assign UVs
            int faceu = 0, facev = 0;

            sliceIndex = 0;
            progress?.Report("Assigning UV coordinates");

            foreach (var slicelist in slices)
            {
                foreach (var slice in slicelist)
                {
                    ++sliceIndex;
                    progress?.Report((double)sliceIndex / totalSlices);

                    var verts = slice.Positions;
                    var uvs = slice.UVs = new Vector2[slice.Positions.Length];
                    Axis3 paxis1, paxis2;
                    GetPerpendicularAxises(slice.Axis, out paxis1, out paxis2);

                    foreach (var face in slice.MeshSliceFaces)
                    {
                        var scoord = FindSliceCoordForFace(slice, face, slice.Axis, paxis1, paxis2);

                        var uv = new Vector2((float) (faceu << 1) + 0.5f, (float) (facev << 1) + 0.5f);
                        for (int i = face.StartIndex; i < face.EndIndex; ++i)
                        {
                            var vt = verts[i];
                            float u = uv.X + (float)(vt[paxis1] - scoord.X);
                            float v = uv.Y + (float)(vt[paxis2] - scoord.Y);
                            uvs[i] = new Vector2(u, v);
                        }

                        faceu += 1;
                        if (faceu == texwidth)
                        {
                            faceu = 0;
                            facev += 1;
                        }
                    }
                }
            }
        }
Ejemplo n.º 3
0
        public MeshSlices GenerateSlices(VoxelModel model, IProgressListener progress)
        {
            var slices = new MeshSlices();
            var dims = model.Dimensions;

            int totalsteps = 2 * (model.Width + model.Height + model.Depth);
            int step = 0;

            progress?.Report("Generating slices");

            for (int iaxis = 0; iaxis < 3; ++iaxis)
            {
                for (int iface = 0; iface < 2; ++iface)
                {

                    var axis = (Axis3) iaxis;
                    var paxis1 = (Axis3) ((iaxis + 1) % 3);
                    var paxis2 = (Axis3) ((iaxis + 2) % 3);
                    bool face = iface != 0;

                    int dim0 = dims[axis];
                    int dim1 = dims[paxis1];
                    int dim2 = dims[paxis2];

                    var slicelist = new MeshSlice[dim0];
                    slices[axis, face] = slicelist;

                    for (int layer = 0; layer < dim0; ++layer)
                    {
                        ++step;
                        progress?.Report((double)step / totalsteps);

                        var faces = new List<int>();
                        var ret = new List<IntVector3>();

                        var pt1 = new IntVector3();
                        pt1[axis] = layer;
                        for (int x = 0; x < dim1; ++x)
                        {
                            pt1[paxis1] = x;
                            for (int y = 0; y < dim2; ++y)
                            {
                                pt1[paxis2] = y;

                                bool solid1 = model.IsVoxelSolid(pt1);

                                var pt2 = pt1;
                                bool solid2 = false;
                                if (face)
                                {
                                    pt2[axis] += 1;
                                    if (pt2[axis] < dim0)
                                    {
                                        solid2 = model.IsVoxelSolid(pt2);
                                    }
                                }
                                else
                                {
                                    pt2[axis] -= 1;
                                    if (pt2[axis] >= 0)
                                    {
                                        solid2 = model.IsVoxelSolid(pt2);
                                    }
                                }

                                if (!solid1 || solid2)
                                {
                                    continue;
                                }

                                // Create quad
                                var qpt1 = pt1;
                                if (face)
                                {
                                    qpt1[axis] += 1;
                                    qpt1[paxis2] += 1;
                                }
                                var qpt2 = qpt1;
                                qpt2[paxis1] += 1;
                                var qpt3 = qpt1;
                                var qpt4 = qpt2;
                                if (face)
                                {
                                    qpt3[paxis2] -= 1;
                                    qpt4[paxis2] -= 1;
                                }
                                else
                                {
                                    qpt3[paxis2] += 1;
                                    qpt4[paxis2] += 1;
                                }

                                // Emit polygons
                                faces.Add(ret.Count);
                                ret.Add(qpt3);
                                ret.Add(qpt4);
                                ret.Add(qpt2);
                                ret.Add(qpt1);
                            } // for y
                        } // for x

                        slicelist[layer] = new MeshSlice()
                        {
                            Positions = ret.ToArray(),
                            Faces = faces.ToArray(),

                            Face = face,
                            Axis = axis,
                            Layer = layer
                        };

                    } // for slice
                } // iface
            } // iaxis
            return slices;
        }
Ejemplo n.º 4
0
 int GetIndexForVoxel(IntVector3 p)
 {
     return (p.X * height + p.Y) * depth + p.Z;
 }
Ejemplo n.º 5
0
 public bool IsVoxelSolid(IntVector3 p)
 {
     return this[p] != EmptyVoxel;
 }