public void Pack()
    {
        atlasPath = null;
        jsonPath  = null;

        //@todo
        if (_PURE_WHITE == null)
        {
            _PURE_WHITE = AssetDatabase.LoadAssetAtPath <Texture2D>("Assets/SeinJSUnityToolkit/Shaders/white.png");
        }

        atlasTexture = new Texture2D(maxWidth, maxHeight);
        Graphics.CopyTexture(_PURE_WHITE, 0, 0, 0, 0, maxWidth, maxHeight, atlasTexture, 0, 0, 0, 0);

        Utils.DoActionForTextures(ref images, (texs) =>
        {
            rects = BinPacker.Pack(texs, atlasTexture, padding);
            atlasTexture.Apply();
        });

        if (rects == null)
        {
            EditorUtility.DisplayDialog("Error!", "Pack failed, atlas' size may be too small !", "OK");
            return;
        }

        if (saveAfterPack)
        {
            Save();
        }
    }
示例#2
0
        public void Pack_AdjustedGlyphs_All()
        {
            // Arrange
            var glyphs = new List <Bitmap>();

            glyphs.Add(new Bitmap(5, 5));
            glyphs[0].SetPixel(2, 1, Color.White);
            glyphs[0].SetPixel(2, 2, Color.White);
            glyphs[0].SetPixel(2, 3, Color.White);
            glyphs[0].SetPixel(1, 2, Color.White);
            glyphs[0].SetPixel(3, 2, Color.White);
            glyphs.Add(new Bitmap(5, 5));
            glyphs[1].SetPixel(2, 2, Color.White);
            glyphs[1].SetPixel(2, 1, Color.White);
            glyphs[1].SetPixel(3, 2, Color.White);
            glyphs.Add(new Bitmap(2, 2));
            glyphs[2].SetPixel(0, 0, Color.White);
            glyphs[2].SetPixel(1, 0, Color.White);
            var adjustedGlyphs = FontMeasurement.MeasureWhiteSpace(glyphs);
            var binPacker      = new BinPacker(new Size(5, 3));

            // Act
            var boxes = binPacker.Pack(adjustedGlyphs).ToArray();

            // Assert
            boxes.Length.Should().Be(3);
            boxes[0].position.Should().Be(Point.Empty);
            boxes[1].position.Should().Be(new Point(3, 0));
            boxes[2].position.Should().Be(new Point(3, 2));
        }
示例#3
0
        static void TestBinPack()
        {
            List <Bin> bins = new List <Bin>();

            for (int i = 0; i < 10; ++i)
            {
                Bin b = new Bin();
                b.Size = new Vec2i(100, 100);
                bins.Add(b);
            }

            Bin b2 = new Bin();

            b2.Size = new Vec2i(12, 200);
            bins.Add(b2);

            Bin b3 = new Bin();

            b3.Size = new Vec2i(1, 90);
            bins.Add(b3);

            BinPacker bp = new BinPacker(512);

            bp.Pack(bins);

            Console.WriteLine("Total size: {0} x {1}", bp.Width, bp.Height);
        }
示例#4
0
        static void Main(string[] args)
        {
            var binPacker            = BinPacker.GetDefault(BinPackerVerifyOption.All);
            var bestAlgorithmRecords = new Dictionary <string, int>();
            var round = 0;

            while (true)
            {
                var result = TestBinPacker(binPacker);
                if (bestAlgorithmRecords.ContainsKey(result.BestAlgorithmName))
                {
                    bestAlgorithmRecords[result.BestAlgorithmName]++;
                }
                else
                {
                    bestAlgorithmRecords[result.BestAlgorithmName] = 1;
                }
                round++;
                var binCount    = result.BestResult.Count;
                var cuboidCount = result.BestResult.Sum(x => x.Count);
                Console.WriteLine($"Round {round} finished, {binCount} bins contains {cuboidCount} cuboids");
                Console.WriteLine($"Best algorithm records:");
                foreach (var pair in bestAlgorithmRecords.OrderByDescending(x => x.Value))
                {
                    Console.WriteLine($"{pair.Key}: {pair.Value}");
                }
                Console.WriteLine();
                Thread.Sleep(1);
            }
        }
示例#5
0
        static Tuple <BinPackResult, decimal> TestBinPacker(IBinPacker binPacker)
        {
            var binWidth              = RandomInstance.Next(100, 5001);
            var binHeight             = RandomInstance.Next(100, 5001);
            var binDepth              = RandomInstance.Next(100, 5001);
            var binWeight             = RandomInstance.Next(100, 5001);
            var cuboidsCount          = RandomInstance.Next(50, 501);
            var allowRotateVertically = RandomInstance.Next(0, 2) == 0;
            var cuboids = new List <Cuboid>();

            for (var x = 0; x < cuboidsCount; ++x)
            {
                var width  = RandomInstance.Next(1, binWidth + 1);
                var height = RandomInstance.Next(1, binHeight + 1);
                var depth  = RandomInstance.Next(1, binDepth + 1);
                var weight = RandomInstance.Next(1, binWeight / 20 + 1);
                cuboids.Add(new Cuboid(width, height, depth, weight, null));
            }
            var parameter = new BinPackParameter(
                binWidth, binHeight, binDepth, binWeight, allowRotateVertically, cuboids);
            var result     = binPacker.Pack(parameter);
            var volumeRate = BinPacker.GetVolumeRate(parameter, result.BestResult);

            return(Tuple.Create(result, volumeRate));
        }
示例#6
0
        static void Main(string[] args)
        {
            // Define the size of bin
            var binWidth  = 1000;
            var binHeight = 1000;
            var binDepth  = 1000;
            // Define the cuboids to pack
            var parameter = new BinPackParameter(binWidth, binHeight, binDepth, new[]
            {
                new Cuboid(150, 100, 150),
                new Cuboid(500, 500, 500),
                new Cuboid(500, 550, 700),
                new Cuboid(350, 350, 350),
                new Cuboid(650, 750, 850),
            });
            // Create a bin packer instance
            // The default bin packer will test all algorithms and try to find the best result
            // BinPackerVerifyOption is used to avoid bugs, it will check whether the result is correct
            var binPacker = BinPacker.GetDefault(BinPackerVerifyOption.BestOnly);
            // The result contains bins which contains packed cuboids whith their coordinates
            var result = binPacker.Pack(parameter);

            foreach (var bins in result.BestResult)
            {
                Console.WriteLine("Bin:");
                foreach (var cuboid in bins)
                {
                    Console.WriteLine(cuboid);
                }
            }
        }
示例#7
0
        public void EmptyImageTest()
        {
            BinPacker pkr1 = new BinPacker();
            BinPacker pkr2 = new BinPacker();

            byte [] img = pkr1.GetBinaryImage();
            pkr2.SetBinaryImage(img);
            Assert.AreEqual(0,pkr2.Files.Count);
        }
示例#8
0
        public void BadImageTest()
        {
            byte [] image1 = {1,2,3,4};
            BinPacker pkr1 = new BinPacker();

            try
            {
                pkr1.SetBinaryImage(image1);
                Assert.IsTrue(false);
            }
            catch(SerializationException ex)
            {
                Console.WriteLine(ex.Message);
            }
        }
示例#9
0
        public void Pack_AdjustedGlyphs_Space()
        {
            // Arrange
            var glyphs = new List <Bitmap>();

            glyphs.Add(new Bitmap(5, 5));
            var adjustedGlyphs = FontMeasurement.MeasureWhiteSpace(glyphs);
            var binPacker      = new BinPacker(new Size(6, 6));

            // Act
            var boxes = binPacker.Pack(adjustedGlyphs).ToArray();

            // Assert
            boxes.Length.Should().Be(1);
            boxes[0].position.Should().Be(new Point(1, 1));
        }
示例#10
0
        static void Main(string[] args)
        {
            var binPacker         = BinPacker.GetDefault(BinPackerVerifyOption.All);
            var averageVolumeRate = 0m;
            var round             = 0;

            while (true)
            {
                var tuple      = TestBinPacker(binPacker);
                var result     = tuple.Item1;
                var volumeRate = tuple.Item2;
                averageVolumeRate = (averageVolumeRate * round + volumeRate) / (round + 1);
                round++;
                var binCount    = result.BestResult.Count;
                var cuboidCount = result.BestResult.Sum(x => x.Count);
                Console.WriteLine(
                    $"Round {round} finished, {binCount} bins contains {cuboidCount} cuboids, " +
                    $"average volume rate {averageVolumeRate.ToString("0.0000")}");
                Thread.Sleep(1);
            }
        }
示例#11
0
 static void Main(string[] args)
 {
     DisplayIntro();
     SetUpLogging();
     if (args.Length == 0)
     {
         DisplayHelpText();
     }
     else
     {
         string folderPath = args[0];
         string prefix     = "P";
         if (args.Length == 2)
         {
             prefix = args[1];
         }
         BinPacker binPacker = new BinPacker(folderPath, prefix);
         binPacker.ProcessFolder();
         string binListing = binPacker.GetBinListing();
         Console.WriteLine(binListing);
         binPacker.MoveFilesIntoBins();
     }
 }
        /*
         * This function try to rearranges all objects on the build platform so they
         * do not touch each other
         */
        public void RearrangeObjects()
        {
            BinPacker bp = new BinPacker();
            List<BinPacker.BinRect> rects = new List<BinPacker.BinRect>();
            foreach (Object3d obj in m_objects)
            {
                if (obj.tag != Object3d.OBJ_NORMAL)
                    continue;
                float w = obj.m_max.x - obj.m_min.x;
                float h = obj.m_max.y - obj.m_min.y;
                BinPacker.BinRect rc = new BinPacker.BinRect(w, h, obj);
                rects.Add(rc);
            }

            float pw = (float)UVDLPApp.Instance().m_printerinfo.m_PlatXSize;
            float ph = (float)UVDLPApp.Instance().m_printerinfo.m_PlatYSize;
            bp.Pack(rects, (int)pw, (int)ph, true);

            // find pack size
            int maxw = 0;
            int maxh = 0;
            foreach (BinPacker.BinRect rc in rects)
            {
                if (rc.packed && ((rc.x + rc.w) > maxw))
                    maxw = rc.x + rc.w;
                if (rc.packed && ((rc.y + rc.h) > maxh))
                    maxh = rc.y + rc.h;
            }

            // find offsets to center all objects
            float offsx = -(float)maxw / 2f + 0.5f;
            float offsy = -(float)maxh / 2f + 0.5f;

            // move all objects to new positions
            foreach (BinPacker.BinRect rc in rects)
            {
                Object3d obj = (Object3d)rc.obj;
                if (rc.packed)
                {
                    if (rc.rotated)
                        obj.Rotate(0, 0, 1.570796326f);
                    float dx = rc.x - obj.m_min.x + offsx;
                    float dy = rc.y - obj.m_min.y + offsy;
                    obj.Translate(dx, dy, 0, true);
                }
                else
                {
                    // object could not fit, place outside platform
                    obj.Translate(pw / 2f - obj.m_min.x, 0, 0, true);
                }
            }
            UVDLPApp.Instance().RaiseAppEvent(eAppEvent.eReDraw,"Redraw new arrangement");
        }
示例#13
0
        public void GenereteUserTexture()
        {
            if (mUserTexture >= 0)
            {
                DeleteTexture(mUserTexture);
            }

            // step 1, arrange all textures in a one big bitmap;
            Bitmap bmp = new Bitmap(2048, 2048, System.Drawing.Imaging.PixelFormat.Format32bppArgb);
            float  tw  = bmp.Width;
            float  th  = bmp.Height;

            BinPacker bp = new BinPacker();
            List <BinPacker.BinRect> rects = new List <BinPacker.BinRect>();

            foreach (C2DImage img in mNewImages)
            {
                BinPacker.BinRect rc = new BinPacker.BinRect(img.w, img.h, img);
                rects.Add(rc);
            }

            bp.Pack(rects, bmp.Width, bmp.Height, false);

            List <C2DImage> packedImages = new List <C2DImage>();

            foreach (BinPacker.BinRect rc in rects)
            {
                C2DImage img = (C2DImage)rc.obj;
                if (rc.packed)
                {
                    img.x      = rc.x;
                    img.y      = rc.y;
                    img.x1     = (img.x + 0.5f) / tw;
                    img.y1     = (img.y + 0.5f) / th;
                    img.x2     = img.x1 + (float)(img.w - 1) / tw;
                    img.y2     = img.y1 + (float)(img.h - 1) / th;
                    img.scalex = tw;
                    img.scaley = th;
                    for (int i = 0; i < img.bmp.Height; i++)
                    {
                        System.Drawing.Imaging.BitmapData ddata = bmp.LockBits(new Rectangle((int)img.x, (int)img.y + i, img.bmp.Width, 1),
                                                                               System.Drawing.Imaging.ImageLockMode.ReadWrite, System.Drawing.Imaging.PixelFormat.Format32bppArgb);
                        System.Drawing.Imaging.BitmapData sdata = img.bmp.LockBits(new Rectangle(0, i, img.bmp.Width, 1),
                                                                                   System.Drawing.Imaging.ImageLockMode.ReadOnly, System.Drawing.Imaging.PixelFormat.Format32bppArgb);
                        int    numBytes  = 4 * img.bmp.Width;
                        byte[] rgbValues = new byte[numBytes];
                        Marshal.Copy(sdata.Scan0, rgbValues, 0, numBytes);
                        Marshal.Copy(rgbValues, 0, ddata.Scan0, numBytes);
                        bmp.UnlockBits(ddata);
                        img.bmp.UnlockBits(sdata);
                    }
                    packedImages.Add(img);
                    mNewImages.Remove(img);
                }
            }
            if (mNewImages.Count != 0)
            {
                DebugLogger.Instance().LogError("Not all user images could be loaded");
            }
            //bmp.Save("packedbmp.png", System.Drawing.Imaging.ImageFormat.Png);
            mUserTexture = LoadTextureImage(bmp);
            foreach (C2DImage img in packedImages)
            {
                img.tex            = mUserTexture;
                ImgDbase[img.name] = img;
            }
            needPacking = false;
        }
示例#14
0
        /*
         * This function try to rearranges all objects on the build platform so they
         * do not touch each other
         */
        public void RearrangeObjects()
        {
            BinPacker bp = new BinPacker();
            List <BinPacker.BinRect> rects = new List <BinPacker.BinRect>();

            foreach (Object3d obj in m_objects)
            {
                if (obj.tag != Object3d.OBJ_NORMAL)
                {
                    continue;
                }
                float             w  = obj.m_max.x - obj.m_min.x;
                float             h  = obj.m_max.y - obj.m_min.y;
                BinPacker.BinRect rc = new BinPacker.BinRect(w, h, obj);
                rects.Add(rc);
            }

            float pw = (float)UVDLPApp.Instance().m_printerinfo.m_PlatXSize;
            float ph = (float)UVDLPApp.Instance().m_printerinfo.m_PlatYSize;

            bp.Pack(rects, (int)pw, (int)ph, true);

            // find pack size
            int maxw = 0;
            int maxh = 0;

            foreach (BinPacker.BinRect rc in rects)
            {
                if (rc.packed && ((rc.x + rc.w) > maxw))
                {
                    maxw = rc.x + rc.w;
                }
                if (rc.packed && ((rc.y + rc.h) > maxh))
                {
                    maxh = rc.y + rc.h;
                }
            }

            // find offsets to center all objects
            float offsx = -(float)maxw / 2f + 0.5f;
            float offsy = -(float)maxh / 2f + 0.5f;

            // move all objects to new positions
            foreach (BinPacker.BinRect rc in rects)
            {
                Object3d obj = (Object3d)rc.obj;
                if (rc.packed)
                {
                    if (rc.rotated)
                    {
                        obj.Rotate(0, 0, 1.570796326f);
                    }
                    float dx = rc.x - obj.m_min.x + offsx;
                    float dy = rc.y - obj.m_min.y + offsy;
                    obj.Translate(dx, dy, 0, true);
                }
                else
                {
                    // object could not fit, place outside platform
                    obj.Translate(pw / 2f - obj.m_min.x, 0, 0, true);
                }
            }
            UVDLPApp.Instance().RaiseAppEvent(eAppEvent.eReDraw, "Redraw new arrangement");
        }
示例#15
0
        public void BinPackerBasicTest()
        {
            const string image_name1 = "first";
            const string image_name2 = "second";
            const string image_name3 = "third";


            BinPacker pkr1 = new BinPacker();
            BinPacker pkr2 = new BinPacker();

            pkr1.Files.Add(new FileToTransmit(image_name1,image1));
            pkr1.Files.Add(new FileToTransmit(image_name2,image2));
            pkr1.Files.Add(new FileToTransmit(image_name3,image3));
            byte [] binImage = pkr1.GetBinaryImage();
            pkr2.SetBinaryImage(binImage);
            Assert.AreEqual(3,pkr2.Files.Count);
            bool first_seen = false;
            bool second_seen = false;
            bool third_seen = false;
            byte [] compare_img = null;
            foreach(FileToTransmit ftt in pkr2.Files)
            {
                switch(ftt.Filename)
                {
                    case image_name1:
                        first_seen = true;
                        compare_img = image1;
                        break;
                    case image_name2:
                        second_seen = true;
                        compare_img = image2;
                        break;
                    case image_name3:
                        third_seen = true;
                        compare_img = image3;
                        break;
                }
                int curr_byte = 0;
                foreach(byte b in ftt.File_image)
                {
                    Assert.AreEqual(b,compare_img[curr_byte]);
                    curr_byte++;
                }
            }

            Assert.IsTrue(first_seen);
            Assert.IsTrue(second_seen);
            Assert.IsTrue(third_seen);
        }
示例#16
0
        public List <HSolution> BuildSolutions(HAnalysis analysis)
        {
            List <ContentItem> contentItems = new List <ContentItem>(analysis.Content);
            // *** Sharp3DBinPacking : begin
            // create cuboid list
            List <Cuboid> listCuboids           = new List <Cuboid>();
            bool          bAllowAllOrientations = true;

            foreach (ContentItem ci in contentItems)
            {
                for (int i = 0; i < ci.Number; ++i)
                {
                    if (ci.Pack is BoxProperties b)
                    {
                        listCuboids.Add(
                            new Cuboid((decimal)b.Length, (decimal)b.Width, (decimal)b.Height)
                        {
                            Tag          = b,
                            AllowOrientX = ci.AllowOrientX,
                            AllowOrientY = ci.AllowOrientY,
                            AllowOrientZ = ci.AllowOrientZ
                        }
                            );
                    }
                    if (!ci.AllowOrientX || !ci.AllowOrientY || !ci.AllowOrientZ)
                    {
                        bAllowAllOrientations = false;
                    }
                }
            }
            // dim container + offset
            Vector3D dimContainer = analysis.DimContainer(0), offset = analysis.Offset(0);

            // Create a bin packer instance
            // The default bin packer will test all algorithms and try to find the best result
            // BinPackerVerifyOption is used to avoid bugs, it will check whether the result is correct
            var binPacker = BinPacker.GetDefault(BinPackerVerifyOption.BestOnly, bAllowAllOrientations);
            // The result contains bins which contains packed cuboids whith their coordinates
            var parameter = new BinPackParameter(
                (decimal)dimContainer.X, (decimal)dimContainer.Y, (decimal)dimContainer.Z,
                listCuboids.ToArray())
            {
            };

            var binPackResult = binPacker.Pack(parameter);

            List <HSolution> solutions = new List <HSolution>();
            //foreach (var result in binPackResult.BestResult)
            //{
            HSolution sol = new HSolution("")
            {
                Analysis = analysis
            };

            foreach (var bins in binPackResult.BestResult)
            {
                HSolItem hSolItem = sol.CreateSolItem();
                foreach (var cuboid in bins)
                {
                    CuboidToSolItem(contentItems, offset, cuboid, out int index, out BoxPosition pos);
                    hSolItem.InsertContainedElt(index, pos);
                }
            }
            solutions.Add(sol);
            //}
            // *** Sharp3DBinPacking : end

            return(solutions);
        }
示例#17
0
        public List <HSolution> BuildSolutions(AnalysisHetero analysis)
        {
            // dim container + offset
            Vector3D dimContainer = analysis.DimContainer(0), offset = analysis.Offset(0);
            // content items
            List <ContentItem> contentItems = new List <ContentItem>(analysis.Content);
            // solutions
            List <HSolution> solutions = new List <HSolution>();

            // *** Sharp3DBinPacking : begin
            // create cuboid list
            List <Cuboid> listCuboids           = new List <Cuboid>();
            bool          bAllowAllOrientations = true;

            foreach (ContentItem ci in contentItems)
            {
                for (int i = 0; i < ci.Number; ++i)
                {
                    if (!ci.AllowOrientX && !ci.AllowOrientY && !ci.AllowOrientZ)
                    {
                        continue;
                    }
                    if (ci.Pack is BoxProperties b)
                    {
                        listCuboids.Add(
                            new Cuboid((decimal)b.Length, (decimal)b.Width, (decimal)b.Height)
                        {
                            Tag            = b
                            , AllowOrientX = ci.AllowOrientX
                            , AllowOrientY = ci.AllowOrientY
                            , AllowOrientZ = ci.AllowOrientZ
                        }
                            );
                    }
                }
                if (!ci.AllowOrientX || !ci.AllowOrientY || !ci.AllowOrientZ)
                {
                    bAllowAllOrientations = false;
                }
            }

            // Create a bin packer instance
            // The default bin packer will test all algorithms and try to find the best result
            // BinPackerVerifyOption is used to avoid bugs, it will check whether the result is correct
            var binPacker = BinPacker.GetDefault(BinPackerVerifyOption.BestOnly, bAllowAllOrientations);
            // The result contains bins which contains packed cuboids whith their coordinates
            var parameter = new BinPackParameter(
                (decimal)dimContainer.X, (decimal)dimContainer.Y, (decimal)dimContainer.Z,
                listCuboids.ToArray())
            {
            };

            var binPackResult = binPacker.Pack(parameter);
            {
                HSolution sol = new HSolution("Sharp3DBinPacking")
                {
                    Analysis = analysis
                };
                foreach (var bins in binPackResult.BestResult)
                {
                    HSolItem hSolItem = sol.CreateSolItem();
                    foreach (var cuboid in bins)
                    {
                        CuboidToSolItem(contentItems, offset, cuboid, out int index, out BoxPosition pos);
                        hSolItem.InsertContainedElt(index, pos);
                    }
                }
                solutions.Add(sol);
            }
            // *** Sharp3DBinPacking : end

            // *** BoxoLogic : begin
            List <BoxItem> listItems = new List <BoxItem>();

            foreach (ContentItem ci in contentItems)
            {
                for (int i = 0; i < ci.Number; ++i)
                {
                    if (ci.Pack is BoxProperties b)
                    {
                        listItems.Add(
                            new BoxItem()
                        {
                            ID     = BoxToID(b),
                            Boxx   = (decimal)b.Length,
                            Boxy   = (decimal)b.Width,
                            Boxz   = (decimal)b.Height,
                            AllowX = ci.AllowOrientX,
                            AllowY = ci.AllowOrientY,
                            AllowZ = ci.AllowOrientZ,
                            N      = 1
                        }
                            );
                    }
                }
            }
            var bl = new Boxlogic()
            {
                OutputFilePath = string.Empty
            };
            var solArray = new SolutionArray();

            bl.Run(listItems.ToArray(), (decimal)dimContainer.X, (decimal)dimContainer.Y, (decimal)dimContainer.Z, ref solArray);
            foreach (var solution in solArray.Solutions)
            {
                HSolution sol = new HSolution($"Boxologic - Variant {solution.Variant}")
                {
                    Analysis = analysis
                };
                HSolItem hSolItem = sol.CreateSolItem();

                Transform3D transform;
                switch (solution.Variant)
                {
                case 1: transform = Transform3D.Translation(new Vector3D(0.0, dimContainer.Y, 0.0)) * Transform3D.RotationX(90.0); break;

                case 2: transform = Transform3D.Translation(new Vector3D(dimContainer.X, 0.0, 0.0)) * Transform3D.RotationZ(90.0); break;

                case 3: transform = Transform3D.Translation(new Vector3D(dimContainer.X, 0.0, 0.0)) * Transform3D.RotationZ(90.0); break;

                case 4: transform = Transform3D.Translation(new Vector3D(dimContainer.X, 0.0, 0.0)) * Transform3D.RotationY(-90.0); break;

                case 5: transform = Transform3D.Translation(new Vector3D(0.0, dimContainer.Y, 0.0)) * Transform3D.RotationX(90.0); break;

                default: transform = Transform3D.Identity; break;
                }

                foreach (var item in solution.ItemsPacked)
                {
                    BoxInfoToSolItem(contentItems, offset, item, transform, out int index, out BoxPosition pos);
                    hSolItem.InsertContainedElt(index, pos.Adjusted(new Vector3D((double)item.DimX, (double)item.DimY, (double)item.DimZ)));
                }
                solutions.Add(sol);
            }
            // *** BoxoLogic : end

            return(solutions);
        }
示例#18
0
        public List <HSolution> BuildSolutions(AnalysisHetero analysis)
        {
            // dim container + offset
            Vector3D dimContainer = analysis.DimContainer(0), offset = analysis.Offset(0);
            // content items
            List <ContentItem> contentItems = new List <ContentItem>(analysis.Content);
            // solutions
            List <HSolution> solutions = new List <HSolution>();

            // *** Sharp3DBinPacking : begin
            // create cuboid list
            List <Cuboid> listCuboids           = new List <Cuboid>();
            bool          bAllowAllOrientations = true;

            foreach (ContentItem ci in contentItems)
            {
                for (int i = 0; i < ci.Number; ++i)
                {
                    if (!ci.AllowOrientX && !ci.AllowOrientY && !ci.AllowOrientZ)
                    {
                        continue;
                    }
                    if (ci.Pack is BoxProperties b)
                    {
                        listCuboids.Add(
                            new Cuboid((decimal)b.Length, (decimal)b.Width, (decimal)b.Height)
                        {
                            Tag             = BoxToID(ci.Pack as BoxProperties)
                            , AllowOrientX  = ci.AllowOrientX
                            , AllowOrientY  = ci.AllowOrientY
                            , AllowOrientZ  = ci.AllowOrientZ
                            , PriorityLevel = ci.PriorityLevel
                        }
                            );
                    }
                }
                if (!ci.AllowOrientX || !ci.AllowOrientY || !ci.AllowOrientZ)
                {
                    bAllowAllOrientations = false;
                }
            }

            // Create a bin packer instance
            // The default bin packer will test all algorithms and try to find the best result
            // BinPackerVerifyOption is used to avoid bugs, it will check whether the result is correct
            var binPacker = BinPacker.GetDefault(BinPackerVerifyOption.BestOnly, bAllowAllOrientations);
            // The result contains bins which contains packed cuboids whith their coordinates
            var parameter = new BinPackParameter(
                (decimal)dimContainer.X, (decimal)dimContainer.Y, (decimal)dimContainer.Z,
                listCuboids.ToArray())
            {
                ShuffleCount = 0
            };

            var binPackResult = binPacker.Pack(parameter);
            {
                HSolution sol = new HSolution("Sharp3DBinPacking")
                {
                    Analysis = analysis
                };
                foreach (var bins in binPackResult.BestResult)
                {
                    HSolItem hSolItem = sol.CreateSolItem();
                    foreach (var cuboid in bins)
                    {
                        CuboidToSolItem(contentItems, offset, cuboid, out int index, out BoxPosition pos);
                        hSolItem.InsertContainedElt(index, pos);
                    }
                }
                solutions.Add(sol);
            }
            // *** Sharp3DBinPacking : end

            // *** BoxoLogic : begin

            bool singleSol = true;

            for (int variant = singleSol? 5 : 1; variant < 6; ++variant)
            {
                HSolution sol = new HSolution($"Boxologic - Variant {variant}")
                {
                    Analysis = analysis
                };
                RunBoxologic(variant, sol, dimContainer, offset, contentItems);
                solutions.Add(sol);
            } // for
            // *** BoxoLogic : end
            return(solutions);
        }
 public void SetUp()
 {
     _binPacker = new BinPacker();
 }
示例#20
0
        public void GenereteUserTexture()
        {
            if (mUserTexture >= 0)
                DeleteTexture(mUserTexture);

            // step 1, arrange all textures in a one big bitmap;
            Bitmap bmp = new Bitmap(2048, 2048, System.Drawing.Imaging.PixelFormat.Format32bppArgb);
            Graphics gr = Graphics.FromImage(bmp);
            gr.CompositingMode = System.Drawing.Drawing2D.CompositingMode.SourceCopy;
            //gr.ResetTransform();
            //gr.PageUnit = GraphicsUnit.Pixel;
            using (Brush br = new SolidBrush(Color.FromArgb(0, 0, 0, 0)))
            {
                gr.FillRectangle(br, new Rectangle(0,0,bmp.Width,bmp.Height));
            }
            float tw = bmp.Width;
            float th = bmp.Height;

            BinPacker bp = new BinPacker();
            List<BinPacker.BinRect> rects = new List<BinPacker.BinRect>();
            foreach (C2DImage img in mNewImages)
            {
                BinPacker.BinRect rc = new BinPacker.BinRect(img.w, img.h, img);
                rects.Add(rc);
            }

            bp.Pack(rects, bmp.Width, bmp.Height, false);

            List<C2DImage> packedImages = new List<C2DImage>();
            foreach (BinPacker.BinRect rc in rects)
            {
                C2DImage img = (C2DImage)rc.obj;
                if (rc.packed)
                {
                    img.x = rc.x;
                    img.y = rc.y;
                    img.x1 = (img.x + 0.5f) / tw;
                    img.y1 = (img.y + 0.5f) / th;
                    img.x2 = img.x1 + (float)(img.w - 1) / tw;
                    img.y2 = img.y1 + (float)(img.h - 1) / th;
                    img.scalex = tw;
                    img.scaley = th;
                    gr.DrawImage(img.bmp, img.x, img.y, img.bmp.Width, img.bmp.Height);
                    //img.bmp.Save("origbmp.png", System.Drawing.Imaging.ImageFormat.Png);
                    packedImages.Add(img);
                    mNewImages.Remove(img);
                }
            }
            if (mNewImages.Count != 0)
            {
                DebugLogger.Instance().LogError("Not all user images could be loaded");
            }
            //bmp.Save("packedbmp.png", System.Drawing.Imaging.ImageFormat.Png);
            mUserTexture = LoadTextureImage(bmp);
            foreach (C2DImage img in packedImages)
            {
                img.tex = mUserTexture;
                ImgDbase[img.name] = img;
            }
            needPacking = false;
        }