Esempio n. 1
0
        public static void DrawILayer(Graphics3D graphics, ILayer layer, Packable packable, bool showDimensions)
        {
            bool show3D = Properties.Settings.Default.LayerView3D;

            graphics.CameraPosition = show3D ? Graphics3D.Corner_0 : Graphics3D.Top;

            uint   pickId = 0;
            BBox3D bbox   = new BBox3D();

            // ### layer of boxes ###
            if (layer is Layer3DBox layerBox)
            {
                foreach (BoxPosition bPosition in layerBox)
                {
                    Box b = null;
                    if (packable is PackProperties)
                    {
                        b = new Pack(pickId++, packable as PackProperties, bPosition);
                    }
                    else
                    {
                        b = new Box(pickId++, packable as PackableBrick, bPosition);
                    }
                    graphics.AddBox(b);
                    bbox.Extend(b.BBox);
                }
            }
            // ###
            // ### layer of cylinders ###
            if (layer is Layer3DCyl layerCyl)
            {
                foreach (Vector3D vPos in layerCyl)
                {
                    Cyl cyl = null;
                    if (packable is CylinderProperties cylinderProp)
                    {
                        cyl = new Cylinder(pickId++, cylinderProp, new CylPosition(vPos, HalfAxis.HAxis.AXIS_Z_P));
                    }
                    else if (packable is BottleProperties bottleProp)
                    {
                        cyl = new Bottle(pickId++, bottleProp, new CylPosition(vPos, HalfAxis.HAxis.AXIS_Z_P));
                    }
                    graphics.AddCylinder(cyl);
                    bbox.Extend(cyl.BBox);
                }
            }
            // ###
            if (showDimensions)
            {
                graphics.AddDimensions(new DimensionCube(bbox, Color.Black, false));
            }
        }
Esempio n. 2
0
        public BBox3D GetBBox(Transform3D transf)
        {
            BBox3D bbox = new BBox3D();

            foreach (var pt in Points)
            {
                bbox.Extend(transf.transform(pt));
            }
            return(bbox);
        }
Esempio n. 3
0
        public Transform3D GetCurrentTransformation()
        {
            if (null == CurrentTransf)
            {
                // get transformations
                Transform3D world2eye        = GetWorldToEyeTransformation();
                Transform3D orthographicProj = GetOrthographicProjection(
                    new Vector3D(_viewport[0], _viewport[1], -10000.0)
                    , new Vector3D(_viewport[2], _viewport[3], 10000.0));

                // build automatic viewport
                if (_autoViewport)
                {
                    BBox3D bbox = new BBox3D();

                    // boxes
                    foreach (var box in Boxes)
                    {
                        bbox.Extend(box.GetBBox(world2eye));
                    }
                    // triangles
                    foreach (var tr in Triangles)
                    {
                        foreach (Vector3D pt in tr.Points)
                        {
                            bbox.Extend(world2eye.transform(pt));
                        }
                    }
                    // cylinders
                    foreach (var cyl in Cylinders)
                    {
                        bbox.Extend(cyl.GetBBox(world2eye));
                    }
                    // faces
                    foreach (Face face in Faces)
                    {
                        foreach (Vector3D pt in face.Points)
                        {
                            bbox.Extend(world2eye.transform(pt));
                        }
                    }
                    // segments
                    foreach (Segment seg in Segments)
                    {
                        foreach (Vector3D pt in seg.Points)
                        {
                            bbox.Extend(world2eye.transform(pt));
                        }
                    }
                    // cube dimensions
                    foreach (DimensionCube dimCube in _dimensions)
                    {
                        foreach (Vector3D pt in dimCube.DrawingPoints(this))
                        {
                            bbox.Extend(world2eye.transform(pt));
                        }
                    }
                    // image inst
                    foreach (var imageInst in _listImageInst)
                    {
                        bbox.Extend(world2eye.transform(imageInst.PointBase));
                    }

                    if (bbox.IsValid)
                    {
                        Vector3D vecMin1 = bbox.PtMin, vecMax1 = bbox.PtMax;
                        // adjust width/height
                        if ((bbox.PtMax.Y - bbox.PtMin.Y) / Size.Height > (bbox.PtMax.X - bbox.PtMin.X) / Size.Width)
                        {
                            double actualWidth = (bbox.PtMax.Y - bbox.PtMin.Y) * Size.Width / Size.Height;
                            vecMin1.X = 0.5 * (bbox.PtMin.X + bbox.PtMax.X) - 0.5 * actualWidth;
                            vecMax1.X = 0.5 * (bbox.PtMin.X + bbox.PtMax.X) + 0.5 * actualWidth;
                        }
                        else
                        {
                            double actualHeight = (bbox.PtMax.X - bbox.PtMin.X) * Size.Height / Size.Width;
                            vecMin1.Y = 0.5 * (bbox.PtMin.Y + bbox.PtMax.Y) - 0.5 * actualHeight;
                            vecMax1.Y = 0.5 * (bbox.PtMin.Y + bbox.PtMax.Y) + 0.5 * actualHeight;
                        }
                        // set margins
                        double width = vecMax1.X - vecMin1.X;
                        vecMin1.X -= MarginPercentage * width;
                        vecMax1.X += MarginPercentage * width;
                        double height = vecMax1.Y - vecMin1.Y;
                        vecMin1.Y -= MarginPercentage * height;
                        vecMax1.Y += MarginPercentage * height;

                        orthographicProj = GetOrthographicProjection(vecMin1, vecMax1);
                    }
                    else
                    {
                        _log.Warn("Graphics3D.GetCurrentTransformation() -> BBox invalid : can not compute viewport automatically");
                    }
                }
                CurrentTransf = orthographicProj * world2eye;
            }
            return(CurrentTransf);
        }
Esempio n. 4
0
        public override void Draw(Graphics3D graphics, Transform3D transform)
        {
            // clear list of picking box
            ClearPickingBoxes();

            if (null == _solution)
            {
                return;
            }
            AnalysisHomo analysis = _solution.Analysis;

            if (analysis is AnalysisPackablePallet analysisPackablePallet)
            {
                // ### draw pallet
                Pallet pallet = new Pallet(analysisPackablePallet.PalletProperties);
                pallet.Draw(graphics, transform);
            }
            else if (analysis is AnalysisPackableCase analysisPackableCase)
            {
                // ### draw case (inside)
                Case case_ = new Case(analysisPackableCase.CaseProperties);
                case_.DrawInside(graphics, transform);
            }
            else if (analysis is AnalysisPackableTruck analysisPackableTruck)
            {
                // ### draw truck
                Truck truck = new Truck(analysisPackableTruck.TruckProperties);
                truck.DrawBegin(graphics);
            }
            else if (analysis is AnalysisPalletTruck analysisPalletTruck)
            {
                // ### draw truck
                Truck truck = new Truck(analysisPalletTruck.TruckProperties);
                truck.DrawBegin(graphics);
            }
            // ### draw solution
            uint          layerId = 0, pickId = 0;
            List <ILayer> layers = _solution.Layers;

            foreach (ILayer layer in layers)
            {
                BBox3D bbox = new BBox3D();
                // ### layer of boxes
                Layer3DBox layerBox = layer as Layer3DBox;
                if (null != layerBox)
                {
                    if (analysis.Content is LoadedPallet)
                    {
                        LoadedPallet loadedPallet = analysis.Content as LoadedPallet;
                        BBox3D       solBBox      = loadedPallet.ParentAnalysis.Solution.BBoxGlobal;
                        foreach (BoxPosition bPosition in layerBox)
                        {
                            bool simplified = false;
                            if (simplified)
                            {
                                BoxProperties bProperties = new BoxProperties(null, solBBox.Dimensions);
                                bProperties.SetColor(Color.Chocolate);
                                Box b = new Box(pickId++, bProperties, bPosition.Transform(transform));
                                graphics.AddBox(b);
                                bbox.Extend(b.BBox);
                            }
                            else
                            {
                                graphics.AddImage(loadedPallet.ParentAnalysis, solBBox.DimensionsVec, bPosition.Transform(transform));
                            }
                        }
                    }
                    else
                    {
                        bool        aboveSelectedLayer = (_solution.SelectedLayerIndex != -1) && (layerId > _solution.SelectedLayerIndex);
                        Transform3D upTranslation      = Transform3D.Translation(new Vector3D(0.0, 0.0, aboveSelectedLayer ? DistanceAboveSelectedLayer : 0.0));

                        foreach (BoxPosition bPosition in layerBox)
                        {
                            BoxPosition boxPositionModified = bPosition.Transform(transform * upTranslation);
                            Box         b = null;
                            if (analysis.Content is PackProperties)
                            {
                                b = new Pack(pickId++, analysis.Content as PackProperties, boxPositionModified);
                            }
                            else
                            {
                                b = new Box(pickId++, analysis.Content as PackableBrick, boxPositionModified);
                            }
                            graphics.AddBox(b);
                            bbox.Extend(b.BBox);
                        }
                    }
                }
                Layer3DCyl layerCyl = layer as Layer3DCyl;
                if (null != layerCyl)
                {
                    foreach (Vector3D vPos in layerCyl)
                    {
                        Cylinder c = new Cylinder(pickId++, analysis.Content as CylinderProperties, new CylPosition(transform.transform(vPos), HalfAxis.HAxis.AXIS_Z_P));
                        graphics.AddCylinder(c);
                        bbox.Extend(c.BBox);
                    }
                }
                if (null != layerBox || null != layerCyl)
                {
                    // add layer BBox
                    AddPickingBox(bbox, layerId);
                    // draw bounding box around selected layer
                    if (layerId == _solution.SelectedLayerIndex)
                    {
                        DrawLayerBoundingBox(graphics, bbox);
                    }
                    ++layerId;
                }

                // ### interlayer
                if (layer is InterlayerPos interlayerPos)
                {
                    InterlayerProperties interlayerProp = _solution.Interlayers[interlayerPos.TypeId];
                    if (null != interlayerProp)
                    {
                        bool        aboveSelectedLayer = (_solution.SelectedLayerIndex != -1) && (layerId > _solution.SelectedLayerIndex);
                        Transform3D upTranslation      = Transform3D.Translation(new Vector3D(0.0, 0.0, aboveSelectedLayer ? DistanceAboveSelectedLayer : 0.0));

                        BoxPosition bPosition = new BoxPosition(
                            new Vector3D(
                                analysis.Offset.X + 0.5 * (analysis.ContainerDimensions.X - interlayerProp.Length)
                                , analysis.Offset.Y + 0.5 * (analysis.ContainerDimensions.Y - interlayerProp.Width)
                                , interlayerPos.ZLow
                                ), HalfAxis.HAxis.AXIS_X_P, HalfAxis.HAxis.AXIS_Y_P);
                        Box box = new Box(pickId++, interlayerProp, bPosition.Transform(transform * upTranslation));
                        graphics.AddBox(box);
                        bbox.Extend(box.BBox);
                    }
                }
            }
            BBox3D loadBBox      = _solution.BBoxLoad;
            BBox3D loadBBoxWDeco = _solution.BBoxLoadWDeco;

            if (analysis is AnalysisCasePallet analysisCasePallet)
            {
                #region Pallet corners
                // ### pallet corners : Begin
                Corner[] corners = new Corner[4];
                if (analysisCasePallet.HasPalletCorners)
                {
                    // positions
                    Vector3D[] cornerPositions =
                    {
                        loadBBox.PtMin
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMin.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMin.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                    };
                    // length axes
                    HalfAxis.HAxis[] lAxes =
                    {
                        HalfAxis.HAxis.AXIS_X_P,
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N
                    };
                    // width axes
                    HalfAxis.HAxis[] wAxes =
                    {
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N,
                        HalfAxis.HAxis.AXIS_X_P
                    };
                    // corners
                    if (analysisCasePallet.HasPalletCorners)
                    {
                        for (int i = 0; i < 4; ++i)
                        {
                            corners[i] = new Corner(0, analysisCasePallet.PalletCornerProperties)
                            {
                                Height = Math.Min(analysisCasePallet.PalletCornerProperties.Length, loadBBox.Height)
                            };
                            corners[i].SetPosition(
                                transform.transform(cornerPositions[i])
                                , HalfAxis.Transform(lAxes[i], transform), HalfAxis.Transform(wAxes[i], transform)
                                );
                            corners[i].DrawBegin(graphics);
                        }
                    }
                }
                #endregion

                #region Pallet film
                // ### pallet film
                Film film = null;
                if (analysisCasePallet.HasPalletFilm && -1 == _solution.SelectedLayerIndex)
                {
                    // instantiate film
                    PalletFilmProperties palletFilmProperties = analysisCasePallet.PalletFilmProperties;
                    film = new Film(
                        palletFilmProperties.Color,
                        palletFilmProperties.UseTransparency,
                        palletFilmProperties.UseHatching,
                        palletFilmProperties.HatchSpacing,
                        palletFilmProperties.HatchAngle);
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis + loadBBoxWDeco.Width * Vector3D.YAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_N, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Width * Vector3D.YAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_N, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Height * Vector3D.ZAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Width)
                                                        , UnitsManager.ConvertLengthFrom(200.0, UnitsManager.UnitSystem.UNIT_METRIC1)));
                    film.DrawBegin(graphics);
                }
                #endregion

                #region Pallet corners
                // pallet corners : End
                if (analysisCasePallet.HasPalletCorners)
                {
                    for (int i = 0; i < 4; ++i)
                    {
                        corners[i].DrawEnd(graphics);
                    }
                }
                #endregion

                #region Pallet Cap
                // ### pallet cap
                if (analysisCasePallet.HasPalletCap)
                {
                    PalletCapProperties capProperties = analysisCasePallet.PalletCapProperties;
                    BoxPosition         bPosition     = new BoxPosition(new Vector3D(
                                                                            0.5 * (analysisCasePallet.PalletProperties.Length - capProperties.Length),
                                                                            0.5 * (analysisCasePallet.PalletProperties.Width - capProperties.Width),
                                                                            loadBBox.PtMax.Z - capProperties.InsideHeight)
                                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform)
                                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform)
                                                                        );

                    Transform3D upTranslation = Transform3D.Translation(new Vector3D(0.0, 0.0, -1 != _solution.SelectedLayerIndex ? DistanceAboveSelectedLayer : 0.0));
                    PalletCap   cap           = new PalletCap(0, capProperties, bPosition.Transform(upTranslation));
                    cap.DrawEnd(graphics);
                }
                #endregion

                #region Pallet film
                // pallet film : End
                if (analysisCasePallet.HasPalletFilm && null != film)
                {
                    film.DrawEnd(graphics);
                }
                #endregion
            }
            else if (analysis is AnalysisPackableTruck analysisPackableTruck2)
            {
                Truck truck = new Truck(analysisPackableTruck2.TruckProperties);
                truck.DrawEnd(graphics);
            }
            else if (analysis is AnalysisPalletTruck analysisPalletTruck)
            {
                Truck truck = new Truck(analysisPalletTruck.TruckProperties);
                truck.DrawEnd(graphics);
            }
            // ### dimensions
            // dimensions should only be shown when no layer is selected
            if (graphics.ShowDimensions && (-1 == _solution.SelectedLayerIndex))
            {
                graphics.AddDimensions(new DimensionCube(BoundingBoxDim(DimCasePalletSol1), Color.Black, false));
                graphics.AddDimensions(new DimensionCube(BoundingBoxDim(DimCasePalletSol2), Color.Red, true));
            }
            // ###
        }
Esempio n. 5
0
        public override void Draw(Graphics3D graphics, Transform3D transform)
        {
            // clear list of picking box
            ClearPickingBoxes();

            if (null == Solution)
            {
                return;
            }
            AnalysisHomo analysis = Solution.Analysis;

            if (analysis is AnalysisPackablePallet analysisPackablePallet)
            {
                // ### draw pallet
                Pallet pallet = new Pallet(analysisPackablePallet.PalletProperties);
                pallet.Draw(graphics, transform);

                if (analysis is AnalysisCasePallet && -1 == Solution.SelectedLayerIndex)
                {
                    // ### strappers
                    SolutionLayered sol = Solution;
                    foreach (var sd in sol.Strappers)
                    {
                        if (null != sd.Points && sd.Points.Count > 0)
                        {
                            Strapper s = new Strapper(
                                transform.transform(IntToAxis(sd.Strapper.Axis)),
                                sd.Strapper.Width,
                                sd.Strapper.Color,
                                sd.Points.ConvertAll(p => transform.transform(p)).ToList());
                            s.DrawBegin(graphics);
                        }
                    }
                }
            }
            else if (analysis is AnalysisPackableCase analysisPackableCase)
            {
                // ### draw case (inside)
                Case case_ = new Case(analysisPackableCase.CaseProperties);
                case_.DrawInside(graphics, transform);
            }
            else if (analysis is AnalysisPackableTruck analysisPackableTruck)
            {
                // ### draw truck
                Truck truck = new Truck(analysisPackableTruck.TruckProperties);
                truck.DrawBegin(graphics);
            }
            else if (analysis is AnalysisPalletTruck analysisPalletTruck)
            {
                // ### draw truck
                Truck truck = new Truck(analysisPalletTruck.TruckProperties);
                truck.DrawBegin(graphics);
            }
            // ### draw solution
            uint          layerId = 0, pickId = 0;
            List <ILayer> layers = Solution.Layers;

            foreach (ILayer layer in layers)
            {
                bool        aboveSelectedLayer = (Solution.SelectedLayerIndex != -1) && (layerId > Solution.SelectedLayerIndex);
                Transform3D upTranslation      = Transform3D.Translation(new Vector3D(0.0, 0.0, aboveSelectedLayer ? DistanceAboveSelectedLayer : 0.0));
                BBox3D      bbox = new BBox3D();
                // ### layer of boxes
                if (layer is Layer3DBox layerBox)
                {
                    if (analysis.Content is LoadedPallet)
                    {
                        LoadedPallet loadedPallet = analysis.Content as LoadedPallet;
                        BBox3D       solBBox      = loadedPallet.ParentAnalysis.Solution.BBoxGlobal;
                        foreach (BoxPosition bPosition in layerBox)
                        {
                            var dim = solBBox.DimensionsVec;
                            graphics.AddImage(++pickId, new SubContent(loadedPallet.ParentAnalysis as AnalysisHomo), solBBox.DimensionsVec, bPosition.Transform(transform));
                            // bbox used for picking
                            bbox.Extend(new BBox3D(bPosition.Transform(transform), solBBox.DimensionsVec));
                        }
                    }
                    else if (analysis.Content is PackProperties packProperties)
                    {
                        foreach (BoxPosition bPosition in layerBox)
                        {
                            BoxPosition boxPositionModified = bPosition.Transform(transform * upTranslation);
                            graphics.AddImage(++pickId, new SubContent(packProperties), packProperties.OuterDimensions, boxPositionModified);
                            // bbox used for picking
                            bbox.Extend(new BBox3D(boxPositionModified, packProperties.OuterDimensions));
                        }
                    }
                    else if (analysis.Content is BagProperties bagProperties)
                    {
                        foreach (BoxPosition bPosition in layerBox)
                        {
                            BoxPosition boxPositionModified = bPosition.Transform(transform * upTranslation);
                            graphics.AddImage(++pickId, new SubContent(bagProperties), bagProperties.OuterDimensions, boxPositionModified);
                            // bbox used for picking
                            bbox.Extend(new BBox3D(boxPositionModified, bagProperties.OuterDimensions));
                        }
                    }
                    else
                    {
                        foreach (BoxPosition bPosition in layerBox)
                        {
                            BoxPosition boxPositionModified = bPosition.Transform(transform * upTranslation);
                            BoxGeneric  b;
                            if (analysis.Content is BagProperties bagProp)
                            {
                                b = new BoxRounded(pickId++, bagProp.Length, bagProp.Width, bagProp.Height, bagProp.Radius, boxPositionModified)
                                {
                                    ColorFill = bagProp.ColorFill
                                }
                            }
                            ;
                            else
                            {
                                b = new Box(pickId++, analysis.Content as PackableBrick, boxPositionModified);
                            }
                            graphics.AddBox(b);
                            bbox.Extend(b.BBox);
                        }
                    }
                }
                else if (layer is Layer3DBoxIndexed layerBoxIndexed)
                {
                    foreach (var bpi in layerBoxIndexed)
                    {
                        BoxPosition boxPositionModified = bpi.BPos.Transform(transform * upTranslation);
                        var         bProperties         = analysis.Content as PackableBrick;
                        BoxGeneric  b = new Box(pickId++, analysis.Content as PackableBrick, boxPositionModified);
                        graphics.AddBox(b);
                        // bbox used for picking
                        bbox.Extend(new BBox3D(boxPositionModified, bProperties.OuterDimensions));
                    }
                }
                else if (layer is Layer3DCyl layerCyl)
                {
                    foreach (Vector3D vPos in layerCyl)
                    {
                        CylPosition cylPosition         = new CylPosition(transform.transform(vPos), HalfAxis.HAxis.AXIS_Z_P);
                        CylPosition cylPositionModified = cylPosition.Transform(transform * upTranslation);
                        Cyl         cyl = null;
                        if (analysis.Content is CylinderProperties cylProp)
                        {
                            cyl = new Cylinder(pickId++, cylProp, cylPositionModified);
                        }
                        else if (analysis.Content is BottleProperties bottleProperties)
                        {
                            cyl = new Bottle(pickId++, bottleProperties, cylPositionModified);
                        }
                        graphics.AddCylinder(cyl);
                        bbox.Extend(cyl.BBox);
                    }
                }
                // ### interlayer
                else if (layer is InterlayerPos interlayerPos)
                {
                    InterlayerProperties interlayerProp = Solution.Interlayers[interlayerPos.TypeId];
                    if (null != interlayerProp)
                    {
                        BoxPosition bPosition = new BoxPosition(
                            new Vector3D(
                                analysis.Offset.X + 0.5 * (analysis.ContainerDimensions.X - interlayerProp.Length)
                                , analysis.Offset.Y + 0.5 * (analysis.ContainerDimensions.Y - interlayerProp.Width)
                                , interlayerPos.ZLow
                                ), HalfAxis.HAxis.AXIS_X_P, HalfAxis.HAxis.AXIS_Y_P);
                        BoxPosition boxPositionModified = bPosition.Transform(transform * upTranslation);

                        Box box = new Box(pickId++, interlayerProp, boxPositionModified);
                        if (analysis.Content is PackProperties)
                        {
                            graphics.AddImage(pickId, new SubContent(interlayerProp), interlayerProp.Dimensions, boxPositionModified);
                        }
                        else
                        {
                            graphics.AddBox(box);
                        }
                        bbox.Extend(box.BBox);
                    }
                }

                if (layer is Layer3DBox || layer is Layer3DCyl)
                {
                    // add layer BBox
                    AddPickingBox(bbox, layerId);
                    // draw bounding box around selected layer
                    if (layerId == Solution.SelectedLayerIndex)
                    {
                        DrawLayerBoundingBox(graphics, bbox);
                    }
                    ++layerId;
                }
            }
            BBox3D loadBBox      = Solution.BBoxLoad;
            BBox3D loadBBoxWDeco = Solution.BBoxLoadWDeco;

            if (analysis is AnalysisCasePallet analysisCasePallet)
            {
                #region Pallet corners
                // ### pallet corners : Begin
                Corner[] corners = new Corner[4];
                if (analysisCasePallet.HasPalletCorners)
                {
                    // positions
                    Vector3D[] cornerPositions =
                    {
                        loadBBox.PtMin
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMin.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMin.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                    };
                    // length axes
                    HalfAxis.HAxis[] lAxes =
                    {
                        HalfAxis.HAxis.AXIS_X_P,
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N
                    };
                    // width axes
                    HalfAxis.HAxis[] wAxes =
                    {
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N,
                        HalfAxis.HAxis.AXIS_X_P
                    };
                    for (int i = 0; i < 4; ++i)
                    {
                        corners[i] = new Corner(0, analysisCasePallet.PalletCornerProperties)
                        {
                            Height = Math.Min(analysisCasePallet.PalletCornerProperties.Length, loadBBox.Height)
                        };
                        corners[i].SetPosition(
                            transform.transform(cornerPositions[i])
                            , HalfAxis.Transform(lAxes[i], transform), HalfAxis.Transform(wAxes[i], transform)
                            );
                        corners[i].DrawBegin(graphics);
                    }
                }
                #endregion

                #region Top corners
                Corner[] cornersTop = new Corner[4];
                if (analysisCasePallet.HasPalletCornersTopX || analysisCasePallet.HasPalletCornersTopY)
                {
                    double cornerWidth  = analysisCasePallet.PalletCornerTopProperties.Width;
                    double lengthInLDir = Math.Min(analysisCasePallet.PalletCornerTopProperties.Length, loadBBox.Length - 2.0 * cornerWidth);
                    double widthInWDir  = Math.Min(analysisCasePallet.PalletCornerTopProperties.Length, loadBBox.Width - 2.0 * cornerWidth);
                    double offsetInLDir = 0.5 * (loadBBox.Length - lengthInLDir);
                    double offsetInWdir = 0.5 * (loadBBox.Width - widthInWDir);

                    Transform3D upTranslation = Transform3D.Translation(new Vector3D(0.0, 0.0, -1 != Solution.SelectedLayerIndex ? DistanceAboveSelectedLayer : 0.0));


                    // positions
                    Vector3D[] cornerPositions =
                    {
                        new Vector3D(loadBBox.PtMin.X + offsetInLDir, loadBBox.PtMin.Y,                             loadBBox.PtMax.Z)
                        ,                                             new Vector3D(loadBBox.PtMax.X - offsetInLDir, loadBBox.PtMax.Y, loadBBox.PtMax.Z)
                        ,                                             new Vector3D(loadBBox.PtMax.X,                loadBBox.PtMin.Y + offsetInWdir, loadBBox.PtMax.Z)
                        ,                                             new Vector3D(loadBBox.PtMin.X,                loadBBox.PtMax.Y - offsetInWdir, loadBBox.PtMax.Z)
                    };
                    // length axes
                    HalfAxis.HAxis[] lAxes =
                    {
                        HalfAxis.HAxis.AXIS_Z_N,
                        HalfAxis.HAxis.AXIS_Z_N,
                        HalfAxis.HAxis.AXIS_Z_N,
                        HalfAxis.HAxis.AXIS_Z_N,
                    };
                    // width axes
                    HalfAxis.HAxis[] wAxes =
                    {
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_Y_N,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_X_P
                    };
                    for (int i = 0; i < 4; ++i)
                    {
                        cornersTop[i] = new Corner(0, analysisCasePallet.PalletCornerTopProperties)
                        {
                            Height = Math.Min(analysisCasePallet.PalletCornerTopProperties.Length, (i < 2 ? loadBBox.Length : loadBBox.Width) - 2.0 * cornerWidth)
                        };
                        cornersTop[i].SetPosition(
                            transform.transform(upTranslation.transform(cornerPositions[i]))
                            , HalfAxis.Transform(lAxes[i], transform), HalfAxis.Transform(wAxes[i], transform)
                            );
                    }
                    // drawing
                    if (analysisCasePallet.HasPalletCornersTopX)
                    {
                        for (int i = 0; i < 2; ++i)
                        {
                            cornersTop[i].DrawBegin(graphics);
                        }
                    }
                    if (analysisCasePallet.HasPalletCornersTopY)
                    {
                        for (int i = 2; i < 4; ++i)
                        {
                            cornersTop[i].DrawBegin(graphics);
                        }
                    }
                }
                #endregion
                #region Pallet film
                // ### pallet film
                Film film = null;
                if (analysisCasePallet.HasPalletFilm && -1 == Solution.SelectedLayerIndex)
                {
                    // instantiate film
                    PalletFilmProperties palletFilmProperties = analysisCasePallet.PalletFilmProperties;
                    film = new Film(
                        palletFilmProperties.Color,
                        palletFilmProperties.UseTransparency,
                        palletFilmProperties.UseHatching,
                        palletFilmProperties.HatchSpacing,
                        palletFilmProperties.HatchAngle);
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), -1.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), -1.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis + loadBBoxWDeco.Width * Vector3D.YAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_N, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), -1.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Width * Vector3D.YAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_N, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Z_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), -1.0));
                    film.AddRectangle(new FilmRectangle(transform.transform(loadBBoxWDeco.PtMin + loadBBoxWDeco.Height * Vector3D.ZAxis)
                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform), HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform)
                                                        , new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Width)
                                                        , analysisCasePallet.PalletFilmTopCovering));
                    film.DrawBegin(graphics);
                }
                #endregion

                #region Pallet corners
                // pallet corners : End
                if (analysisCasePallet.HasPalletCorners)
                {
                    for (int i = 0; i < 4; ++i)
                    {
                        corners[i].DrawEnd(graphics);
                    }
                }
                if (analysisCasePallet.HasPalletCornersTopX)
                {
                    for (int i = 0; i < 2; ++i)
                    {
                        cornersTop[i].DrawEnd(graphics);
                    }
                }
                if (analysisCasePallet.HasPalletCornersTopY)
                {
                    for (int i = 2; i < 4; ++i)
                    {
                        cornersTop[i].DrawEnd(graphics);
                    }
                }
                #endregion

                #region Pallet sleeves
                // ### pallet sleeve
                if (analysisCasePallet.HasPalletSleeve)
                {
                    var ps = new PalletSleeve(0, loadBBox, analysisCasePallet.PalletSleeveColor);
                    ps.DrawEnd(graphics);
                }
                #endregion

                #region Pallet Cap
                // ### pallet cap
                if (analysisCasePallet.HasPalletCap)
                {
                    PalletCapProperties capProperties = analysisCasePallet.PalletCapProperties;
                    BoxPosition         bPosition     = new BoxPosition(new Vector3D(
                                                                            0.5 * (analysisCasePallet.PalletProperties.Length - capProperties.Length),
                                                                            0.5 * (analysisCasePallet.PalletProperties.Width - capProperties.Width),
                                                                            loadBBox.PtMax.Z - capProperties.InsideHeight)
                                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_X_P, transform)
                                                                        , HalfAxis.Transform(HalfAxis.HAxis.AXIS_Y_P, transform)
                                                                        );

                    Transform3D upTranslation = Transform3D.Translation(new Vector3D(0.0, 0.0, -1 != Solution.SelectedLayerIndex ? DistanceAboveSelectedLayer : 0.0));
                    PalletCap   cap           = new PalletCap(0, capProperties, bPosition.Transform(upTranslation));
                    cap.DrawEnd(graphics);
                }
                #endregion

                #region Pallet labels
                // ### pallet labels
                if (null != analysisCasePallet)
                {
                    foreach (var pli in analysisCasePallet.PalletLabels)
                    {
                        var pl = new PalletLabel(++pickId, pli.PalletLabelProperties, pli.ToBoxPosition(loadBBox));
                        pl.DrawEnd(graphics);
                    }
                }
                #endregion

                #region Strappers
                // ### strappers
                if (-1 == Solution.SelectedLayerIndex)
                {
                    foreach (var sd in Solution.Strappers)
                    {
                        if (null == sd.Points && sd.Points.Count > 0)
                        {
                            var strapper = new Strapper(
                                transform.transform(IntToAxis(sd.Strapper.Axis)),
                                sd.Strapper.Width,
                                sd.Strapper.Color,
                                sd.Points.Select(p => transform.transform(p)).ToList());
                            strapper.DrawEnd(graphics);
                        }
                    }
                }
                #endregion

                #region Pallet film
                // pallet film : End
                if (analysisCasePallet.HasPalletFilm && null != film)
                {
                    film.DrawEnd(graphics);
                }
                #endregion
            }
            else if (analysis is AnalysisPackableTruck analysisPackableTruck2)
            {
                Truck truck = new Truck(analysisPackableTruck2.TruckProperties);
                truck.DrawEnd(graphics);
            }
            else if (analysis is AnalysisPalletTruck analysisPalletTruck)
            {
                Truck truck = new Truck(analysisPalletTruck.TruckProperties);
                truck.DrawEnd(graphics);
            }
            // ### dimensions
            // dimensions should only be shown when no layer is selected
            if (graphics.ShowDimensions && (-1 == Solution.SelectedLayerIndex))
            {
                graphics.AddDimensions(new DimensionCube(BoundingBoxDim(DimCasePalletSol1), Color.Black, false));
                graphics.AddDimensions(new DimensionCube(BoundingBoxDim(DimCasePalletSol2), Color.Red, true));
            }
            // ###
        }
        public override void Draw(Graphics3D graphics, bool showDimensions)
        {
            // clear list of picking box
            ClearPickingBoxes();

            if (null == _solution)
            {
                return;
            }
            Analysis           analysis           = _solution.Analysis;
            AnalysisCasePallet analysisCasePallet = analysis as AnalysisCasePallet;
            AnalysisBoxCase    analysisBoxCase    = analysis as AnalysisBoxCase;

            if (null != analysisCasePallet)
            {
                // ### draw pallet
                Pallet pallet = new Pallet(analysisCasePallet.PalletProperties);
                pallet.Draw(graphics, Transform3D.Identity);
            }
            else if (null != analysisBoxCase)
            {
                // draw case (inside)
                Case case_ = new Case(analysisBoxCase._caseProperties);
                case_.DrawInside(graphics);
            }

            // ### draw solution
            uint          layerId = 0, pickId = 0;
            List <ILayer> layers = _solution.Layers;

            foreach (ILayer layer in layers)
            {
                // ### layer of boxes
                BoxLayer blayer = layer as BoxLayer;
                if (null != blayer)
                {
                    BBox3D bbox = new BBox3D();
                    foreach (BoxPosition bPosition in blayer)
                    {
                        Box b = null;
                        if (analysis.Content is PackProperties)
                        {
                            b = new Pack(pickId++, analysis.Content as PackProperties, bPosition);
                        }
                        else
                        {
                            b = new Box(pickId++, analysis.Content, bPosition);
                        }
                        graphics.AddBox(b);
                        bbox.Extend(b.BBox);
                    }
                    // add layer BBox
                    AddPickingBox(bbox, layerId);
                    // draw bounding box around selected layer
                    if (layerId == _solution.SelectedLayerIndex)
                    {
                        DrawLayerBoundingBox(graphics, bbox);
                    }
                    ++layerId;
                }
                // ### interlayer
                InterlayerPos interlayerPos = layer as InterlayerPos;
                if (null != interlayerPos)
                {
                    InterlayerProperties interlayerProp = _solution.Interlayers[interlayerPos.TypeId];
                    if (null != interlayerProp)
                    {
                        Box box = new Box(pickId++, interlayerProp);
                        box.Position = new Vector3D(
                            0.5 * (analysis.ContainerDimensions.X - interlayerProp.Length)
                            , 0.5 * (analysis.ContainerDimensions.Y - interlayerProp.Width)
                            , interlayerPos.ZLow
                            );
                        graphics.AddBox(box);
                    }
                }
            }
            BBox3D loadBBox      = _solution.BBoxLoad;
            BBox3D loadBBoxWDeco = _solution.BBoxLoadWDeco;

            if (null != analysisCasePallet)
            {
                #region Pallet corners
                // ### pallet corners : Begin
                Corner[] corners = new Corner[4];
                if (analysisCasePallet.HasPalletCorners)
                {
                    // positions
                    Vector3D[] cornerPositions =
                    {
                        loadBBox.PtMin
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMin.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMax.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                        , new Vector3D(loadBBox.PtMin.X, loadBBox.PtMax.Y, loadBBox.PtMin.Z)
                    };
                    // length axes
                    HalfAxis.HAxis[] lAxes =
                    {
                        HalfAxis.HAxis.AXIS_X_P,
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N
                    };
                    // width axes
                    HalfAxis.HAxis[] wAxes =
                    {
                        HalfAxis.HAxis.AXIS_Y_P,
                        HalfAxis.HAxis.AXIS_X_N,
                        HalfAxis.HAxis.AXIS_Y_N,
                        HalfAxis.HAxis.AXIS_X_P
                    };
                    // corners
                    if (analysisCasePallet.HasPalletCorners)
                    {
                        for (int i = 0; i < 4; ++i)
                        {
                            corners[i]        = new Corner(0, analysisCasePallet.PalletCornerProperties);
                            corners[i].Height = Math.Min(analysisCasePallet.PalletCornerProperties.Length, loadBBox.Height);
                            corners[i].SetPosition(cornerPositions[i], lAxes[i], wAxes[i]);
                            corners[i].DrawBegin(graphics);
                        }
                    }
                }
                #endregion

                #region Pallet film
                // ### pallet film
                Film film = null;
                if (analysisCasePallet.HasPalletFilm)
                {
                    PalletFilmProperties palletFilmProperties = analysisCasePallet.PalletFilmProperties;
                    film = new Film(
                        palletFilmProperties.Color,
                        palletFilmProperties.UseTransparency,
                        palletFilmProperties.UseHatching,
                        palletFilmProperties.HatchSpacing,
                        palletFilmProperties.HatchAngle);
                    film.AddRectangle(new FilmRectangle(loadBBoxWDeco.PtMin,
                                                        HalfAxis.HAxis.AXIS_X_P, HalfAxis.HAxis.AXIS_Z_P, new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis,
                                                        HalfAxis.HAxis.AXIS_Y_P, HalfAxis.HAxis.AXIS_Z_P, new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(loadBBoxWDeco.PtMin + loadBBoxWDeco.Length * Vector3D.XAxis + loadBBoxWDeco.Width * Vector3D.YAxis,
                                                        HalfAxis.HAxis.AXIS_X_N, HalfAxis.HAxis.AXIS_Z_P, new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(loadBBoxWDeco.PtMin + loadBBoxWDeco.Width * Vector3D.YAxis,
                                                        HalfAxis.HAxis.AXIS_Y_N, HalfAxis.HAxis.AXIS_Z_P, new Vector2D(loadBBoxWDeco.Width, loadBBoxWDeco.Height), 0.0));
                    film.AddRectangle(new FilmRectangle(loadBBoxWDeco.PtMin + loadBBoxWDeco.Height * Vector3D.ZAxis,
                                                        HalfAxis.HAxis.AXIS_X_P, HalfAxis.HAxis.AXIS_Y_P, new Vector2D(loadBBoxWDeco.Length, loadBBoxWDeco.Width),
                                                        UnitsManager.ConvertLengthFrom(200.0, UnitsManager.UnitSystem.UNIT_METRIC1)));
                    film.DrawBegin(graphics);
                }
                #endregion

                #region Pallet corners
                // pallet corners : End
                if (analysisCasePallet.HasPalletCorners)
                {
                    for (int i = 0; i < 4; ++i)
                    {
                        corners[i].DrawEnd(graphics);
                    }
                }
                #endregion

                #region Pallet Cap
                // ### pallet cap
                if (analysisCasePallet.HasPalletCap)
                {
                    PalletCapProperties capProperties = analysisCasePallet.PalletCapProperties;
                    Vector3D            pos           = new Vector3D(
                        0.5 * (analysisCasePallet.PalletProperties.Length - capProperties.Length),
                        0.5 * (analysisCasePallet.PalletProperties.Width - capProperties.Width),
                        loadBBox.PtMax.Z - capProperties.InsideHeight);
                    PalletCap cap = new PalletCap(0, capProperties, pos);
                    cap.DrawEnd(graphics);
                }
                #endregion

                #region Pallet film
                // pallet film : End
                if (analysisCasePallet.HasPalletFilm)
                {
                    film.DrawEnd(graphics);
                }
                #endregion
            }

            // ### dimensions
            if (showDimensions)
            {
                graphics.AddDimensions(
                    new DimensionCube(BoundingBoxDim(Properties.Settings.Default.DimCasePalletSol1)
                                      , Color.Black, false));
                graphics.AddDimensions(
                    new DimensionCube(BoundingBoxDim(Properties.Settings.Default.DimCasePalletSol2)
                                      , Color.Red, true));
            }
        }