protected internal override void OnCollectDrawcalls(Canvas canvas)
        {
            base.OnCollectDrawcalls(canvas);
            List <RigidBody> visibleColliders = this.QueryVisibleColliders().ToList();

            RigidBody selectedBody = this.QuerySelectedCollider();

            canvas.State.TextFont           = Font.GenericMonospace10;
            canvas.State.TextInvariantScale = true;
            canvas.State.ZOffset            = -1;
            Font textFont = canvas.State.TextFont.Res;

            // Draw Shape layer
            foreach (RigidBody c in visibleColliders)
            {
                if (!c.Shapes.Any())
                {
                    continue;
                }
                float   colliderAlpha = c == selectedBody ? 1.0f : (selectedBody != null ? 0.25f : 0.5f);
                float   maxDensity    = c.Shapes.Max(s => s.Density);
                float   minDensity    = c.Shapes.Min(s => s.Density);
                float   avgDensity    = (maxDensity + minDensity) * 0.5f;
                Vector3 colliderPos   = c.GameObj.Transform.Pos;
                float   colliderScale = c.GameObj.Transform.Scale;
                int     index         = 0;
                foreach (ShapeInfo s in c.Shapes)
                {
                    CircleShapeInfo circle = s as CircleShapeInfo;
                    PolyShapeInfo   poly   = s as PolyShapeInfo;
                    //	EdgeShapeInfo edge = s as EdgeShapeInfo;
                    LoopShapeInfo loop = s as LoopShapeInfo;

                    ObjectEditorCamViewState editorState = this.View.ActiveState as ObjectEditorCamViewState;
                    float     shapeAlpha      = colliderAlpha * (selectedBody == null || editorState == null || editorState.SelectedObjects.Any(sel => sel.ActualObject == s) ? 1.0f : 0.5f);
                    float     densityRelative = MathF.Abs(maxDensity - minDensity) < 0.01f ? 1.0f : s.Density / avgDensity;
                    ColorRgba clr             = s.IsSensor ? this.ShapeSensorColor : this.ShapeColor;
                    ColorRgba fontClr         = this.FgColor;
                    Vector2   center          = Vector2.Zero;

                    if (!c.IsAwake)
                    {
                        clr = clr.ToHsva().WithSaturation(0.0f).ToRgba();
                    }
                    if (!s.IsValid)
                    {
                        clr = this.ShapeErrorColor;
                    }

                    if (circle != null)
                    {
                        Vector2 circlePos = circle.Position * colliderScale;
                        MathF.TransformCoord(ref circlePos.X, ref circlePos.Y, c.GameObj.Transform.Angle);

                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha((0.25f + densityRelative * 0.25f) * shapeAlpha)));
                        canvas.FillCircle(
                            colliderPos.X + circlePos.X,
                            colliderPos.Y + circlePos.Y,
                            colliderPos.Z,
                            circle.Radius * colliderScale);
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha(shapeAlpha)));
                        canvas.DrawCircle(
                            colliderPos.X + circlePos.X,
                            colliderPos.Y + circlePos.Y,
                            colliderPos.Z,
                            circle.Radius * colliderScale);

                        center = circlePos;
                    }
                    else if (poly != null)
                    {
                        Vector2[] polyVert = poly.Vertices.ToArray();
                        for (int i = 0; i < polyVert.Length; i++)
                        {
                            center += polyVert[i];
                            Vector2.Multiply(ref polyVert[i], colliderScale, out polyVert[i]);
                            MathF.TransformCoord(ref polyVert[i].X, ref polyVert[i].Y, c.GameObj.Transform.Angle);
                        }
                        center /= polyVert.Length;
                        Vector2.Multiply(ref center, colliderScale, out center);
                        MathF.TransformCoord(ref center.X, ref center.Y, c.GameObj.Transform.Angle);

                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha((0.25f + densityRelative * 0.25f) * shapeAlpha)));
                        canvas.FillPolygon(polyVert, colliderPos.X, colliderPos.Y, colliderPos.Z);
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha(shapeAlpha)));
                        canvas.DrawPolygon(polyVert, colliderPos.X, colliderPos.Y, colliderPos.Z);
                    }
                    else if (loop != null)
                    {
                        Vector2[] loopVert = loop.Vertices.ToArray();
                        for (int i = 0; i < loopVert.Length; i++)
                        {
                            center += loopVert[i];
                            Vector2.Multiply(ref loopVert[i], colliderScale, out loopVert[i]);
                            MathF.TransformCoord(ref loopVert[i].X, ref loopVert[i].Y, c.GameObj.Transform.Angle);
                        }
                        center /= loopVert.Length;
                        Vector2.Multiply(ref center, colliderScale, out center);
                        MathF.TransformCoord(ref center.X, ref center.Y, c.GameObj.Transform.Angle);

                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha(shapeAlpha)));
                        canvas.DrawPolygon(loopVert, colliderPos.X, colliderPos.Y, colliderPos.Z);
                    }

                    // Draw shape index
                    if (c == selectedBody)
                    {
                        Vector2 textSize = textFont.MeasureText(index.ToString(CultureInfo.InvariantCulture));
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, fontClr.WithAlpha((shapeAlpha + 1.0f) * 0.5f)));
                        canvas.State.TransformHandle = textSize * 0.5f;
                        canvas.DrawText(index.ToString(CultureInfo.InvariantCulture),
                                        colliderPos.X + center.X,
                                        colliderPos.Y + center.Y,
                                        colliderPos.Z);
                        canvas.State.TransformHandle = Vector2.Zero;
                    }

                    index++;
                }

                // Draw center of mass
                if (c.BodyType == BodyType.Dynamic)
                {
                    Vector2 localMassCenter = c.LocalMassCenter;
                    MathF.TransformCoord(ref localMassCenter.X, ref localMassCenter.Y, c.GameObj.Transform.Angle, c.GameObj.Transform.Scale);
                    canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, this.MassCenterColor.WithAlpha(colliderAlpha)));
                    canvas.DrawLine(
                        colliderPos.X + localMassCenter.X - 5.0f,
                        colliderPos.Y + localMassCenter.Y,
                        colliderPos.Z,
                        colliderPos.X + localMassCenter.X + 5.0f,
                        colliderPos.Y + localMassCenter.Y,
                        colliderPos.Z);
                    canvas.DrawLine(
                        colliderPos.X + localMassCenter.X,
                        colliderPos.Y + localMassCenter.Y - 5.0f,
                        colliderPos.Z,
                        colliderPos.X + localMassCenter.X,
                        colliderPos.Y + localMassCenter.Y + 5.0f,
                        colliderPos.Z);
                }
            }
        }
Example #2
0
        protected internal override void OnCollectWorldOverlayDrawcalls(Canvas canvas)
        {
            base.OnCollectWorldOverlayDrawcalls(canvas);
            List <RigidBody> visibleColliders = this.QueryVisibleColliders().ToList();

            RigidBody selectedBody = this.QuerySelectedCollider();

            canvas.State.SetMaterial(DrawTechnique.Alpha);
            canvas.State.TextFont    = Font.GenericMonospace10;
            canvas.State.DepthOffset = this.depthOffset;
            Font textFont = canvas.State.TextFont.Res;

            // Retrieve selected shapes
            ObjectEditorCamViewState editorState = this.View.ActiveState as ObjectEditorCamViewState;

            object[] editorSelectedObjects = editorState != null?editorState.SelectedObjects.Select(item => item.ActualObject).ToArray() : new object[0];

            bool isAnyBodySelected  = (selectedBody != null);
            bool isAnyShapeSelected = isAnyBodySelected && editorSelectedObjects.OfType <ShapeInfo>().Any();

            // Draw Shape layer
            foreach (RigidBody body in visibleColliders)
            {
                if (!body.Shapes.Any())
                {
                    continue;
                }

                Vector3 objPos   = body.GameObj.Transform.Pos;
                float   objAngle = body.GameObj.Transform.Angle;
                float   objScale = body.GameObj.Transform.Scale;

                bool isBodySelected = (body == selectedBody);

                float bodyAlpha  = isBodySelected ? 1.0f : (isAnyBodySelected ? 0.5f : 1.0f);
                float maxDensity = body.Shapes.Max(s => s.Density);
                float minDensity = body.Shapes.Min(s => s.Density);
                float avgDensity = (maxDensity + minDensity) * 0.5f;

                int shapeIndex = 0;
                foreach (ShapeInfo shape in body.Shapes)
                {
                    bool isShapeSelected = isBodySelected && editorSelectedObjects.Contains(shape);

                    float     shapeAlpha      = bodyAlpha * (isShapeSelected ? 1.0f : (isAnyShapeSelected && isBodySelected ? 0.75f : 1.0f));
                    float     densityRelative = MathF.Abs(maxDensity - minDensity) < 0.01f ? 1.0f : shape.Density / avgDensity;
                    ColorRgba shapeColor      = shape.IsSensor ? this.ShapeSensorColor : this.ShapeColor;
                    ColorRgba fontColor       = this.FgColor;

                    if (!body.IsAwake)
                    {
                        shapeColor = shapeColor.ToHsva().WithSaturation(0.0f).ToRgba();
                    }
                    if (!shape.IsValid)
                    {
                        shapeColor = this.ShapeErrorColor;
                    }

                    // Draw the shape itself
                    ColorRgba fillColor    = shapeColor.WithAlpha((0.25f + densityRelative * 0.25f) * shapeAlpha);
                    ColorRgba outlineColor = ColorRgba.Lerp(shapeColor, fontColor, isShapeSelected ? 0.75f : 0.25f).WithAlpha(shapeAlpha);
                    this.DrawShape(canvas, body.GameObj.Transform, shape, fillColor, outlineColor);

                    // Calculate the center coordinate
                    Vector2 shapeCenter = Vector2.Zero;
                    if (shape is CircleShapeInfo)
                    {
                        CircleShapeInfo circleShape = shape as CircleShapeInfo;
                        shapeCenter = circleShape.Position * objScale;
                    }
                    else if (shape is VertexBasedShapeInfo)
                    {
                        VertexBasedShapeInfo vertexShape   = shape as VertexBasedShapeInfo;
                        Vector2[]            shapeVertices = vertexShape.Vertices;

                        for (int i = 0; i < shapeVertices.Length; i++)
                        {
                            shapeCenter += shapeVertices[i];
                        }

                        shapeCenter /= shapeVertices.Length;
                    }
                    MathF.TransformCoord(ref shapeCenter.X, ref shapeCenter.Y, objAngle, objScale);

                    // Draw shape index
                    if (body == selectedBody)
                    {
                        string  indexText = shapeIndex.ToString();
                        Vector2 textSize  = textFont.MeasureText(indexText);
                        canvas.State.ColorTint      = fontColor.WithAlpha((shapeAlpha + 1.0f) * 0.5f);
                        canvas.State.TransformScale = Vector2.One / canvas.DrawDevice.GetScaleAtZ(0.0f);
                        canvas.DrawText(indexText,
                                        objPos.X + shapeCenter.X,
                                        objPos.Y + shapeCenter.Y,
                                        0.0f);
                        canvas.State.TransformScale = Vector2.One;
                    }

                    shapeIndex++;
                }

                // Draw center of mass
                if (body.BodyType == BodyType.Dynamic)
                {
                    Vector2 localMassCenter = body.LocalMassCenter;
                    MathF.TransformCoord(ref localMassCenter.X, ref localMassCenter.Y, objAngle, objScale);

                    float size = this.GetScreenConstantScale(canvas, 6.0f);

                    canvas.State.ColorTint = this.MassCenterColor.WithAlpha(bodyAlpha);
                    canvas.DrawLine(
                        objPos.X + localMassCenter.X - size,
                        objPos.Y + localMassCenter.Y,
                        0.0f,
                        objPos.X + localMassCenter.X + size,
                        objPos.Y + localMassCenter.Y,
                        0.0f);
                    canvas.DrawLine(
                        objPos.X + localMassCenter.X,
                        objPos.Y + localMassCenter.Y - size,
                        0.0f,
                        objPos.X + localMassCenter.X,
                        objPos.Y + localMassCenter.Y + size,
                        0.0f);
                }

                // Draw transform center
                {
                    float size = this.GetScreenConstantScale(canvas, 3.0f);
                    canvas.State.ColorTint = this.ObjectCenterColor.WithAlpha(bodyAlpha);
                    canvas.FillCircle(objPos.X, objPos.Y, 0.0f, size);
                }
            }
        }
        protected internal override void OnCollectWorldOverlayDrawcalls(Canvas canvas)
        {
            base.OnCollectWorldOverlayDrawcalls(canvas);
            List <RigidBody> visibleColliders = this.QueryVisibleColliders().ToList();

            RigidBody selectedBody = this.QuerySelectedCollider();

            canvas.State.TextFont           = Font.GenericMonospace10;
            canvas.State.TextInvariantScale = true;
            canvas.State.ZOffset            = -0.5f;
            Font textFont = canvas.State.TextFont.Res;

            // Draw Shape layer
            foreach (RigidBody body in visibleColliders)
            {
                if (!body.Shapes.Any())
                {
                    continue;
                }
                float   colliderAlpha = body == selectedBody ? 1.0f : (selectedBody != null ? 0.25f : 0.5f);
                float   maxDensity    = body.Shapes.Max(s => s.Density);
                float   minDensity    = body.Shapes.Min(s => s.Density);
                float   avgDensity    = (maxDensity + minDensity) * 0.5f;
                Vector3 objPos        = body.GameObj.Transform.Pos;
                float   objAngle      = body.GameObj.Transform.Angle;
                float   objScale      = body.GameObj.Transform.Scale;
                int     index         = 0;
                foreach (ShapeInfo shape in body.Shapes)
                {
                    CircleShapeInfo circle = shape as CircleShapeInfo;
                    PolyShapeInfo   poly   = shape as PolyShapeInfo;
                    ChainShapeInfo  chain  = shape as ChainShapeInfo;
                    LoopShapeInfo   loop   = shape as LoopShapeInfo;

                    ObjectEditorCamViewState editorState = this.View.ActiveState as ObjectEditorCamViewState;
                    float     shapeAlpha      = colliderAlpha * (selectedBody == null || editorState == null || editorState.SelectedObjects.Any(sel => sel.ActualObject == shape) ? 1.0f : 0.5f);
                    float     densityRelative = MathF.Abs(maxDensity - minDensity) < 0.01f ? 1.0f : shape.Density / avgDensity;
                    ColorRgba clr             = shape.IsSensor ? this.ShapeSensorColor : this.ShapeColor;
                    ColorRgba fontClr         = this.FgColor;
                    Vector2   center          = Vector2.Zero;

                    if (!body.IsAwake)
                    {
                        clr = clr.ToHsva().WithSaturation(0.0f).ToRgba();
                    }
                    if (!shape.IsValid)
                    {
                        clr = this.ShapeErrorColor;
                    }

                    bool      fillShape     = (poly != null || circle != null);
                    Vector2[] shapeVertices = null;
                    if (poly != null)
                    {
                        shapeVertices = poly.Vertices;
                    }
                    else if (loop != null)
                    {
                        shapeVertices = loop.Vertices;
                    }
                    else if (chain != null)
                    {
                        shapeVertices = chain.Vertices;
                    }

                    if (circle != null)
                    {
                        Vector2 circlePos = circle.Position * objScale;
                        MathF.TransformCoord(ref circlePos.X, ref circlePos.Y, objAngle);

                        if (fillShape)
                        {
                            canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha((0.25f + densityRelative * 0.25f) * shapeAlpha)));
                            canvas.FillCircle(
                                objPos.X + circlePos.X,
                                objPos.Y + circlePos.Y,
                                objPos.Z,
                                circle.Radius * objScale);
                        }
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, clr.WithAlpha(shapeAlpha)));
                        canvas.DrawCircle(
                            objPos.X + circlePos.X,
                            objPos.Y + circlePos.Y,
                            objPos.Z,
                            circle.Radius * objScale);

                        center = circlePos;
                    }
                    else if (shapeVertices != null)
                    {
                        ColorRgba vertexFillColor    = canvas.State.ColorTint * clr.WithAlpha((0.25f + densityRelative * 0.25f) * shapeAlpha);
                        ColorRgba vertexOutlineColor = canvas.State.ColorTint * clr;

                        // Prepare vertices to submit. We can't use higher-level canvas functionality
                        // here, because we want direct control over the vertex mode.
                        float   viewSpaceScale = objScale;
                        Vector3 viewSpacePos   = objPos;
                        canvas.DrawDevice.PreprocessCoords(ref viewSpacePos, ref viewSpaceScale);
                        VertexC1P3T2[] drawVertices = new VertexC1P3T2[shapeVertices.Length];
                        for (int i = 0; i < drawVertices.Length; i++)
                        {
                            drawVertices[i].Pos.X = shapeVertices[i].X;
                            drawVertices[i].Pos.Y = shapeVertices[i].Y;
                            drawVertices[i].Pos.Z = 0.0f;
                            MathF.TransformCoord(ref drawVertices[i].Pos.X, ref drawVertices[i].Pos.Y, objAngle, viewSpaceScale);

                            drawVertices[i].Pos.X += viewSpacePos.X;
                            drawVertices[i].Pos.Y += viewSpacePos.Y;
                            drawVertices[i].Pos.Z += viewSpacePos.Z;
                            drawVertices[i].Color  = vertexOutlineColor;
                        }

                        // Calculate the center coordinate
                        for (int i = 0; i < drawVertices.Length; i++)
                        {
                            center += shapeVertices[i];
                        }
                        center /= shapeVertices.Length;
                        MathF.TransformCoord(ref center.X, ref center.Y, objAngle, objScale);

                        // Make sure to render using an alpha material
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, ColorRgba.White));

                        // Fill the shape
                        if (fillShape)
                        {
                            VertexC1P3T2[] fillVertices = drawVertices.Clone() as VertexC1P3T2[];
                            for (int i = 0; i < fillVertices.Length; i++)
                            {
                                fillVertices[i].Color = vertexFillColor;
                            }
                            canvas.DrawVertices(fillVertices, VertexMode.TriangleFan);
                        }

                        // Draw the outline
                        canvas.DrawVertices(drawVertices, shape is ChainShapeInfo ? VertexMode.LineStrip : VertexMode.LineLoop);
                    }

                    // Draw shape index
                    if (body == selectedBody)
                    {
                        string  indexText = index.ToString();
                        Vector2 textSize  = textFont.MeasureText(indexText);
                        canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, fontClr.WithAlpha((shapeAlpha + 1.0f) * 0.5f)));
                        canvas.DrawText(indexText,
                                        objPos.X + center.X,
                                        objPos.Y + center.Y,
                                        objPos.Z);
                    }

                    index++;
                }

                // Draw center of mass
                if (body.BodyType == BodyType.Dynamic)
                {
                    Vector2 localMassCenter = body.LocalMassCenter;
                    MathF.TransformCoord(ref localMassCenter.X, ref localMassCenter.Y, objAngle, objScale);
                    canvas.State.SetMaterial(new BatchInfo(DrawTechnique.Alpha, this.MassCenterColor.WithAlpha(colliderAlpha)));
                    canvas.DrawLine(
                        objPos.X + localMassCenter.X - 5.0f,
                        objPos.Y + localMassCenter.Y,
                        objPos.Z,
                        objPos.X + localMassCenter.X + 5.0f,
                        objPos.Y + localMassCenter.Y,
                        objPos.Z);
                    canvas.DrawLine(
                        objPos.X + localMassCenter.X,
                        objPos.Y + localMassCenter.Y - 5.0f,
                        objPos.Z,
                        objPos.X + localMassCenter.X,
                        objPos.Y + localMassCenter.Y + 5.0f,
                        objPos.Z);
                }
            }
        }
Example #4
0
        protected internal override void OnCollectDrawcalls(Canvas canvas)
        {
            base.OnCollectDrawcalls(canvas);
            IDrawDevice device = canvas.DrawDevice;

            float   scaleTemp = 1.0f;
            Vector3 posTemp   = Vector3.Zero;

            device.PreprocessCoords(ref posTemp, ref scaleTemp);
            if (posTemp.Z <= canvas.DrawDevice.NearZ)
            {
                return;
            }

            float alphaTemp = 0.5f;

            alphaTemp *= (float)Math.Min(1.0d, ((posTemp.Z - device.NearZ) / (device.NearZ * 5.0f)));
            if (alphaTemp <= 0.005f)
            {
                return;
            }

            float stepTemp     = 4.0f * this.gridSize * MathF.Max(0.25f, MathF.Pow(2.0f, -MathF.Round(1.0f - MathF.Log(1.0f / scaleTemp, 2.0f))));
            float scaledStep   = stepTemp * scaleTemp;
            float viewBoundRad = device.TargetSize.Length * 0.5f;
            int   lineCount    = (2 + (int)MathF.Ceiling(viewBoundRad * 2 / scaledStep)) * 4;

            ColorRgba gridColor = this.FgColor.WithAlpha(alphaTemp);

            VertexC1P3[] vertices = new VertexC1P3[lineCount * 4];

            float beginPos;
            float pos;
            int   lineIndex;
            int   vertOff = 0;

            beginPos  = posTemp.X % scaledStep - (lineCount / 8) * scaledStep;
            pos       = beginPos;
            lineIndex = 0;
            for (int x = 0; x < lineCount; x++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + x * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + x * 2 + 0].Pos.X = pos;
                vertices[vertOff + x * 2 + 0].Pos.Y = -viewBoundRad;
                vertices[vertOff + x * 2 + 0].Pos.Z = posTemp.Z + 1;

                vertices[vertOff + x * 2 + 1]       = vertices[vertOff + x * 2 + 0];
                vertices[vertOff + x * 2 + 1].Pos.Y = viewBoundRad;

                pos += scaledStep / 4;
                lineIndex++;
            }
            vertOff += lineCount * 2;

            beginPos  = posTemp.Y % scaledStep - (lineCount / 8) * scaledStep;
            pos       = beginPos;
            lineIndex = 0;
            for (int y = 0; y < lineCount; y++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + y * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + y * 2 + 0].Pos.X = -viewBoundRad;
                vertices[vertOff + y * 2 + 0].Pos.Y = pos;
                vertices[vertOff + y * 2 + 0].Pos.Z = posTemp.Z + 1;

                vertices[vertOff + y * 2 + 1]       = vertices[vertOff + y * 2 + 0];
                vertices[vertOff + y * 2 + 1].Pos.X = viewBoundRad;

                pos += scaledStep / 4;
                lineIndex++;
            }
            vertOff += lineCount * 2;

            device.AddVertices(new BatchInfo(DrawTechnique.Alpha, ColorRgba.White), VertexMode.Lines, vertices);
        }
Example #5
0
        protected internal override void OnCollectDrawcalls(Canvas canvas)
        {
            base.OnCollectDrawcalls(canvas);
            IDrawDevice device = canvas.DrawDevice;

            float   scaleTemp = 1.0f;
            Vector3 posTemp   = Vector3.Zero;

            device.PreprocessCoords(ref posTemp, ref scaleTemp);
            if (posTemp.Z <= canvas.DrawDevice.NearZ)
            {
                return;
            }

            float alphaTemp = 0.5f;

            alphaTemp *= (float)Math.Min(1.0d, ((posTemp.Z - device.NearZ) / (device.NearZ * 5.0f)));
            if (alphaTemp <= 0.005f)
            {
                return;
            }
            ColorRgba gridColor = this.FgColor.WithAlpha(alphaTemp);

            float   gridVisualMinSize = 50.0f;
            Vector2 gridBaseSize      = this.View.EditingUserGuides.GridSize.Xy;

            if (gridBaseSize.X <= 0.0f)
            {
                gridBaseSize.X = 100.0f;
            }
            if (gridBaseSize.Y <= 0.0f)
            {
                gridBaseSize.Y = 100.0f;
            }

            Vector2 adjustedGridBaseSize;

            adjustedGridBaseSize.X = gridBaseSize.X * MathF.NextPowerOfTwo((int)MathF.Ceiling(gridVisualMinSize / gridBaseSize.X));
            adjustedGridBaseSize.Y = gridBaseSize.Y * MathF.NextPowerOfTwo((int)MathF.Ceiling(gridVisualMinSize / gridBaseSize.Y));

            float   scaleAdjustmentFactor = 4.0f * MathF.Pow(2.0f, -MathF.Round(1.0f - MathF.Log(1.0f / scaleTemp, 2.0f)));
            Vector2 adjustedGridSize;

            adjustedGridSize.X = MathF.Max(adjustedGridBaseSize.X * scaleAdjustmentFactor, gridBaseSize.X);
            adjustedGridSize.Y = MathF.Max(adjustedGridBaseSize.Y * scaleAdjustmentFactor, gridBaseSize.Y);

            Vector2 stepTemp     = adjustedGridSize;
            Vector2 scaledStep   = stepTemp * scaleTemp;
            float   viewBoundRad = device.TargetSize.Length * 0.5f;
            int     lineCountX   = (2 + (int)MathF.Ceiling(viewBoundRad * 2 / scaledStep.X)) * 4;
            int     lineCountY   = (2 + (int)MathF.Ceiling(viewBoundRad * 2 / scaledStep.Y)) * 4;
            int     vertexCount  = (lineCountX * 2 + lineCountY * 2);

            if (this.vertexBuffer == null)
            {
                this.vertexBuffer = new RawList <VertexC1P3>(vertexCount);
            }
            this.vertexBuffer.Count = vertexCount;

            VertexC1P3[] vertices = this.vertexBuffer.Data;
            float        beginPos;
            float        pos;
            int          lineIndex;
            int          vertOff = 0;

            beginPos  = posTemp.X % scaledStep.X - (lineCountX / 8) * scaledStep.X;
            pos       = beginPos;
            lineIndex = 0;
            for (int x = 0; x < lineCountX; x++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + x * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + x * 2 + 0].Pos.X = pos;
                vertices[vertOff + x * 2 + 0].Pos.Y = -viewBoundRad;
                vertices[vertOff + x * 2 + 0].Pos.Z = posTemp.Z + 1;

                vertices[vertOff + x * 2 + 1]       = vertices[vertOff + x * 2 + 0];
                vertices[vertOff + x * 2 + 1].Pos.Y = viewBoundRad;

                pos += scaledStep.X / 4;
                lineIndex++;
            }
            vertOff += lineCountX * 2;

            beginPos  = posTemp.Y % scaledStep.Y - (lineCountY / 8) * scaledStep.Y;
            pos       = beginPos;
            lineIndex = 0;
            for (int y = 0; y < lineCountY; y++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + y * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + y * 2 + 0].Pos.X = -viewBoundRad;
                vertices[vertOff + y * 2 + 0].Pos.Y = pos;
                vertices[vertOff + y * 2 + 0].Pos.Z = posTemp.Z + 1;

                vertices[vertOff + y * 2 + 1]       = vertices[vertOff + y * 2 + 0];
                vertices[vertOff + y * 2 + 1].Pos.X = viewBoundRad;

                pos += scaledStep.Y / 4;
                lineIndex++;
            }
            vertOff += lineCountY * 2;

            device.AddVertices(new BatchInfo(DrawTechnique.Alpha, ColorRgba.White), VertexMode.Lines, vertices, this.vertexBuffer.Count);
        }
Example #6
0
        public override void OnWorldOverlayDrawcalls(Canvas canvas)
        {
            RigidBody body = this.Environment.ActiveBody;

            if (body == null)
            {
                return;
            }

            DesignTimeObjectData designTimeData = DesignTimeObjectData.Get(body.GameObj);

            if (designTimeData.IsHidden)
            {
                return;
            }

            float knobSize      = 7.0f;
            float worldKnobSize = knobSize / MathF.Max(0.0001f, canvas.DrawDevice.GetScaleAtZ(0.0f));

            // Determine the color in which we'll draw the interaction markers
            ColorRgba markerColor = this.Environment.FgColor;

            canvas.State.ZOffset = -1.0f;

            // Prepare the transform matrix for this object, so
            // we can move the RigidBody vertices into world space quickly
            Transform transform = body.GameObj.Transform;
            Vector2   bodyPos   = transform.Pos.Xy;
            Vector2   bodyDotX;
            Vector2   bodyDotY;

            MathF.GetTransformDotVec(transform.Angle, transform.Scale, out bodyDotX, out bodyDotY);

            // Draw an interaction indicator for every vertex of the active bodies shapes
            Vector3 mousePosWorld = this.Environment.ActiveWorldPos;

            foreach (ShapeInfo shape in body.Shapes)
            {
                if (shape is CircleShapeInfo)
                {
                    CircleShapeInfo circle = shape as CircleShapeInfo;

                    Vector2 circleWorldPos = circle.Position;
                    MathF.TransformDotVec(ref circleWorldPos, ref bodyDotX, ref bodyDotY);
                    circleWorldPos = bodyPos + circleWorldPos;

                    // Draw the circles center as a vertex
                    if (this.activeVertex == 0 && this.activeShape == shape)
                    {
                        canvas.State.ColorTint = markerColor;
                    }
                    else
                    {
                        canvas.State.ColorTint = markerColor.WithAlpha(0.75f);
                    }

                    canvas.FillRect(
                        circleWorldPos.X - worldKnobSize * 0.5f,
                        circleWorldPos.Y - worldKnobSize * 0.5f,
                        worldKnobSize,
                        worldKnobSize);
                }
                else
                {
                    Vector2[] vertices = this.GetVertices(shape);
                    if (vertices == null)
                    {
                        continue;
                    }

                    Vector2[] worldVertices = new Vector2[vertices.Length];

                    // Transform the shapes vertices into world space
                    for (int index = 0; index < vertices.Length; index++)
                    {
                        Vector2 vertex = vertices[index];
                        MathF.TransformDotVec(ref vertex, ref bodyDotX, ref bodyDotY);
                        worldVertices[index] = bodyPos + vertex;
                    }

                    // Draw the vertices
                    for (int i = 0; i < worldVertices.Length; i++)
                    {
                        if (this.activeVertex == i && this.activeShape == shape)
                        {
                            canvas.State.ColorTint = markerColor;
                        }
                        else
                        {
                            canvas.State.ColorTint = markerColor.WithAlpha(0.75f);
                        }

                        canvas.FillRect(
                            worldVertices[i].X - worldKnobSize * 0.5f,
                            worldVertices[i].Y - worldKnobSize * 0.5f,
                            worldKnobSize,
                            worldKnobSize);
                    }
                }
            }

            // Interaction indicator for an existing vertex
            if (this.activeVertex != -1)
            {
                canvas.State.ColorTint = markerColor;
                canvas.DrawRect(
                    this.activeEdgeWorldPos.X - worldKnobSize,
                    this.activeEdgeWorldPos.Y - worldKnobSize,
                    worldKnobSize * 2.0f,
                    worldKnobSize * 2.0f);
            }
            // Interaction indicator for a vertex-to-be-created
            else if (this.activeEdge != -1)
            {
                canvas.State.ColorTint = markerColor.WithAlpha(0.35f);
                canvas.FillRect(
                    this.activeEdgeWorldPos.X - worldKnobSize * 0.5f,
                    this.activeEdgeWorldPos.Y - worldKnobSize * 0.5f,
                    worldKnobSize * 1.0f,
                    worldKnobSize * 1.0f);
                canvas.State.ColorTint = markerColor;
                canvas.DrawRect(
                    this.activeEdgeWorldPos.X - worldKnobSize,
                    this.activeEdgeWorldPos.Y - worldKnobSize,
                    worldKnobSize * 2.0f,
                    worldKnobSize * 2.0f);
            }
        }
Example #7
0
        protected internal override void OnCollectDrawcalls(Canvas canvas)
        {
            base.OnCollectDrawcalls(canvas);
            IDrawDevice device = canvas.DrawDevice;

            GridLayerData displayedData = default(GridLayerData);

            this.View.ActiveState.GetDisplayedGridData(Point.Empty, ref displayedData);

            float distanceToCamera = 0.0f - device.ViewerPos.Z;

            if (distanceToCamera <= device.NearZ)
            {
                return;
            }

            float alphaTemp = 0.5f;

            alphaTemp *= (float)Math.Min(1.0d, ((distanceToCamera - device.NearZ) / (device.NearZ * 5.0f)));
            if (alphaTemp <= 0.005f)
            {
                return;
            }
            ColorRgba gridColor = this.FgColor.WithAlpha(alphaTemp);

            float   gridVisualMinSize = 50.0f;
            Vector2 gridBaseSize      = displayedData.GridBaseSize;

            if (gridBaseSize.X <= 0.0f)
            {
                gridBaseSize.X = 100.0f;
            }
            if (gridBaseSize.Y <= 0.0f)
            {
                gridBaseSize.Y = 100.0f;
            }

            Vector2 adjustedGridBaseSize;

            adjustedGridBaseSize.X = gridBaseSize.X * MathF.NextPowerOfTwo((int)MathF.Ceiling(gridVisualMinSize / gridBaseSize.X));
            adjustedGridBaseSize.Y = gridBaseSize.Y * MathF.NextPowerOfTwo((int)MathF.Ceiling(gridVisualMinSize / gridBaseSize.Y));

            float   scaleAtGrid           = device.GetScaleAtZ(0.0f);
            float   scaleAdjustmentFactor = 4.0f * MathF.Pow(2.0f, -MathF.Round(1.0f - MathF.Log(1.0f / scaleAtGrid, 2.0f)));
            Vector2 adjustedGridSize;

            adjustedGridSize.X = MathF.Max(adjustedGridBaseSize.X * scaleAdjustmentFactor, gridBaseSize.X);
            adjustedGridSize.Y = MathF.Max(adjustedGridBaseSize.Y * scaleAdjustmentFactor, gridBaseSize.Y);

            Vector2 stepSize     = adjustedGridSize;
            float   viewBoundRad = MathF.Distance(device.TargetSize.X, device.TargetSize.Y) * 0.5f / scaleAtGrid;
            int     lineCountX   = (2 + (int)MathF.Ceiling(viewBoundRad * 2 / stepSize.X)) * 4;
            int     lineCountY   = (2 + (int)MathF.Ceiling(viewBoundRad * 2 / stepSize.Y)) * 4;
            int     vertexCount  = (lineCountX * 2 + lineCountY * 2);

            if (this.vertexBuffer == null)
            {
                this.vertexBuffer = new RawList <VertexC1P3>(vertexCount);
            }
            this.vertexBuffer.Count = vertexCount;

            VertexC1P3[] vertices = this.vertexBuffer.Data;
            float        beginPos;
            float        pos;
            int          lineIndex;
            int          vertOff = 0;

            beginPos  = stepSize.X * (int)(device.ViewerPos.X / stepSize.X - (lineCountX / 8));
            pos       = beginPos;
            lineIndex = 0;
            for (int x = 0; x < lineCountX; x++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + x * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + x * 2 + 0].Pos.X       = pos;
                vertices[vertOff + x * 2 + 0].Pos.Y       = device.ViewerPos.Y - viewBoundRad;
                vertices[vertOff + x * 2 + 0].Pos.Z       = 0.0f;
                vertices[vertOff + x * 2 + 0].DepthOffset = 1.0f;

                vertices[vertOff + x * 2 + 1]       = vertices[vertOff + x * 2 + 0];
                vertices[vertOff + x * 2 + 1].Pos.Y = device.ViewerPos.Y + viewBoundRad;

                pos += stepSize.X / 4;
                lineIndex++;
            }
            vertOff += lineCountX * 2;

            beginPos  = stepSize.Y * (int)(device.ViewerPos.Y / stepSize.Y - (lineCountY / 8));
            pos       = beginPos;
            lineIndex = 0;
            for (int y = 0; y < lineCountY; y++)
            {
                bool primaryLine   = lineIndex % 4 == 0;
                bool secondaryLine = lineIndex % 4 == 2;

                vertices[vertOff + y * 2 + 0].Color = primaryLine ? gridColor : gridColor.WithAlpha(alphaTemp * (secondaryLine ? 0.5f : 0.25f));

                vertices[vertOff + y * 2 + 0].Pos.X       = device.ViewerPos.X - viewBoundRad;
                vertices[vertOff + y * 2 + 0].Pos.Y       = pos;
                vertices[vertOff + y * 2 + 0].Pos.Z       = 0.0f;
                vertices[vertOff + y * 2 + 0].DepthOffset = 1.0f;

                vertices[vertOff + y * 2 + 1]       = vertices[vertOff + y * 2 + 0];
                vertices[vertOff + y * 2 + 1].Pos.X = device.ViewerPos.X + viewBoundRad;

                pos += stepSize.Y / 4;
                lineIndex++;
            }
            vertOff += lineCountY * 2;

            BatchInfo material = device.RentMaterial();

            material.Technique = DrawTechnique.Alpha;
            device.AddVertices(material, VertexMode.Lines, vertices, this.vertexBuffer.Count);
        }