internal void PrepareTextureForDrawDevice(IDrawDevice device)
        {
            System.Drawing.PointF[] points = new System.Drawing.PointF[_verticesPositions.Count];

            /**
             * Drawing texture based on displacement for each camera
             **/
            Vector3 start = _absoluteStart * device.GetScaleAtZ(_absoluteStart.Z);
            Vector3 end   = _absoluteEnd * device.GetScaleAtZ(_absoluteEnd.Z);

            Vector2 tangent = (end - start).Xy;
            float   length  = tangent.Length;

            for (int i = 0; i < points.Length; i++)
            {
                points[i] = new System.Drawing.PointF(_verticesPositions[i].X * length, _verticesPositions[i].Y);
            }

            System.Drawing.Bitmap pixelData = new System.Drawing.Bitmap((int)MathF.Ceiling(length), (int)MathF.Ceiling(_sway2));

            using (System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(pixelData))
            {
                g.Clear(System.Drawing.Color.Transparent);
                g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighSpeed;
                g.DrawLines(_pen, points);
            }

            if (!BatchInfos.ContainsKey(device))
            {
                BatchInfo bi = new BatchInfo(
                    DrawTechnique.Add,
                    Colors.White,
                    new ContentRef <Texture>(
                        new Texture(new ContentRef <Pixmap>(new Pixmap()))
                {
                    FilterMin   = TextureMinFilter.LinearMipmapLinear,
                    FilterMag   = TextureMagFilter.LinearSharpenSgis,
                    WrapX       = TextureWrapMode.ClampToEdge,
                    WrapY       = TextureWrapMode.ClampToEdge,
                    TexSizeMode = Texture.SizeMode.Stretch
                }));

                BatchInfos.Add(device, new BoltData()
                {
                    BatchInfo = bi
                });
            }

            BoltData bd = BatchInfos[device];

            Texture tx = bd.BatchInfo.MainTexture.Res;

            tx.BasePixmap.Res.MainLayer.FromBitmap(pixelData);
            tx.ReloadData();

            bd.Start   = start;
            bd.End     = end;
            bd.IsReady = true;
        }
Exemplo n.º 2
0
        public int CalcPriority(IDrawDevice device)
        {
            if (!this.IsDirectional)
            {
                float   uniformScale = this.GameObj.Transform.Scale;
                Vector3 pos          = this.GameObj.Transform.Pos;
                float   scale        = device.GetScaleAtZ(pos.Z);

                float planarDist = (this.GameObj.Transform.Pos.Xy - device.ViewerPos.Xy).Length;

                float rangeFactor = 1.0f / (this.range * uniformScale);
                float distFactor  = (MathF.Min(scale, 1.0f) * planarDist);

                float spotFactor;
                if (this.dir != Vector3.Zero)
                {
                    spotFactor = 0.5f * (1.0f + Vector3.Dot((device.ViewerPos - this.GameObj.Transform.Pos).Normalized, this.dir));
                }
                else
                {
                    spotFactor = 1.0f;
                }

                return(MathF.RoundToInt(1000000.0f * spotFactor * distFactor * MathF.Pow(rangeFactor, 1.5f) * MathF.Pow(1.0f / this.intensity, 0.5f)));
            }
            else
            {
                return(MathF.RoundToInt(100.0f * MathF.Pow(1.0f / this.intensity, 0.5f)));
            }
        }
Exemplo n.º 3
0
        /// <summary>
        /// Determines the rectangular tile area that is visible to the specified <see cref="IDrawDevice"/>.
        /// </summary>
        /// <param name="device"></param>
        /// <param name="input"></param>
        public static TileOutput GetVisibleTileRect(IDrawDevice device, TileInput input)
        {
            TileOutput output;

            // Determine the view space transform of the tilemap
            float   cameraScaleAtObj   = device.GetScaleAtZ(input.TilemapPos.Z);
            Vector3 viewCenterWorldPos = device.GetWorldPos(new Vector3(device.TargetSize * 0.5f, input.TilemapPos.Z));

            // Early-out, if so small that it might break the math behind rendering a single tile.
            if (cameraScaleAtObj <= 0.000000001f)
            {
                return(EmptyOutput);
            }

            // Determine transformed X and Y axis in world space
            output.XAxisWorld = Vector2.UnitX;
            output.YAxisWorld = Vector2.UnitY;
            MathF.TransformCoord(ref output.XAxisWorld.X, ref output.XAxisWorld.Y, input.TilemapAngle, input.TilemapScale);
            MathF.TransformCoord(ref output.YAxisWorld.X, ref output.YAxisWorld.Y, input.TilemapAngle, input.TilemapScale);

            // Determine which tile is in the center of view space.
            Point2 viewCenterTile = Point2.Zero;
            {
                Vector2 localViewCenter = (viewCenterWorldPos - input.TilemapPos).Xy;
                localViewCenter = new Vector2(
                    Vector2.Dot(localViewCenter, output.XAxisWorld.Normalized),
                    Vector2.Dot(localViewCenter, output.YAxisWorld.Normalized)) / input.TilemapScale;
                viewCenterTile = new Point2(
                    (int)MathF.Floor(localViewCenter.X / input.TileSize.X),
                    (int)MathF.Floor(localViewCenter.Y / input.TileSize.Y));
            }

            // Determine the edge length of a square that is big enough to enclose the world space rect of the Camera view
            float   visualAngle  = input.TilemapAngle - device.ViewerAngle;
            Vector2 visualBounds = new Vector2(
                device.TargetSize.Y * MathF.Abs(MathF.Sin(visualAngle)) + device.TargetSize.X * MathF.Abs(MathF.Cos(visualAngle)),
                device.TargetSize.X * MathF.Abs(MathF.Sin(visualAngle)) + device.TargetSize.Y * MathF.Abs(MathF.Cos(visualAngle)));
            Vector2 localVisualBounds      = visualBounds / cameraScaleAtObj;
            Point2  targetVisibleTileCount = new Point2(
                3 + (int)MathF.Ceiling(localVisualBounds.X / (MathF.Min(input.TileSize.X, input.TileSize.Y) * input.TilemapScale)),
                3 + (int)MathF.Ceiling(localVisualBounds.Y / (MathF.Min(input.TileSize.X, input.TileSize.Y) * input.TilemapScale)));

            // Determine the tile indices (xy) that are visible within that rect
            output.VisibleTileStart = new Point2(
                MathF.Max(viewCenterTile.X - targetVisibleTileCount.X / 2, 0),
                MathF.Max(viewCenterTile.Y - targetVisibleTileCount.Y / 2, 0));
            Point2 tileGridEndPos = new Point2(
                MathF.Min(viewCenterTile.X + targetVisibleTileCount.X / 2, input.TileCount.X),
                MathF.Min(viewCenterTile.Y + targetVisibleTileCount.Y / 2, input.TileCount.Y));

            output.VisibleTileCount = new Point2(
                MathF.Clamp(tileGridEndPos.X - output.VisibleTileStart.X, 0, input.TileCount.X),
                MathF.Clamp(tileGridEndPos.Y - output.VisibleTileStart.Y, 0, input.TileCount.Y));

            // Determine start position for rendering
            output.RenderOriginWorld = input.TilemapPos + new Vector3(
                output.VisibleTileStart.X * output.XAxisWorld * input.TileSize.X +
                output.VisibleTileStart.Y * output.YAxisWorld * input.TileSize.Y);

            return(output);
        }
Exemplo n.º 4
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);
        }
Exemplo n.º 5
0
        void ICmpRenderer.Draw(IDrawDevice device)
        {
            if (_inEditor)
            {
                if (FXSource != null && FXTarget != null)
                {
                    Canvas c = new Canvas(device);

                    FXSource.DrawInEditor(c);
                    FXTarget.DrawInEditor(c);

                    Vector3 src = FXSource.GameObj.Transform.Pos;
                    Vector3 tar = FXTarget.GameObj.Transform.Pos;

                    c.PushState();

                    Vector3 line   = tar - src;
                    Vector2 normal = line.Xy.PerpendicularLeft;

                    Vector3 p1 = line * 0.33f;
                    Vector3 p2 = line * 0.33f;
                    Vector3 p3 = line * 0.67f;
                    Vector3 p4 = line * 0.67f;

                    p1 += src + new Vector3(normal * .04f, p1.Z);
                    p2 += src + new Vector3(normal * -.02f, p2.Z);
                    p3 += src + new Vector3(normal * .02f, p3.Z);
                    p4 += src + new Vector3(normal * -.04f, p4.Z);

                    c.State.ColorTint = Colors.Pink;
                    c.DrawLine(src.X, src.Y, src.Z, p1.X, p1.Y, p1.Z);
                    c.DrawLine(p1.X, p1.Y, p1.Z, p2.X, p2.Y, p2.Z);
                    c.DrawLine(p2.X, p2.Y, p2.Z, p3.X, p3.Y, p3.Z);
                    c.DrawLine(p3.X, p3.Y, p3.Z, p4.X, p4.Y, p4.Z);
                    c.DrawLine(p4.X, p4.Y, p4.Z, tar.X, tar.Y, tar.Z);

                    c.PopState();
                }
            }
            else
            {
                foreach (LightningBolt bolt in _bolts)
                {
                    if (bolt.IsAlive)
                    {
                        if (!bolt.BatchInfos.ContainsKey(device) || !bolt.BatchInfos[device].IsReady)
                        {
                            bolt.PrepareTextureForDrawDevice(device);
                        }

                        LightningBolt.BoltData bd = bolt.BatchInfos[device];

                        float scaleAtStart = device.GetScaleAtZ(FXSource.GameObj.Transform.Pos.Z);
                        float scaleAtEnd   = device.GetScaleAtZ(FXTarget.GameObj.Transform.Pos.Z);

                        Vector2 axis   = (bd.End - bd.Start).Xy;
                        Vector2 normal = axis.PerpendicularLeft.Normalized;

                        VertexC1P3T2[] v = new VertexC1P3T2[4];

                        v[0]          = new VertexC1P3T2();
                        v[0].Pos      = bd.Start - new Vector3(normal * Sway * scaleAtStart, 0);
                        v[0].TexCoord = new Vector2(0, 0);
                        v[0].Color    = bolt.CurrentColor;

                        v[1]          = new VertexC1P3T2();
                        v[1].Pos      = bd.Start + new Vector3(normal * Sway * scaleAtStart, 0);
                        v[1].TexCoord = new Vector2(0, 1);
                        v[1].Color    = bolt.CurrentColor;

                        v[2]          = new VertexC1P3T2();
                        v[2].Pos      = bd.End + new Vector3(normal * Sway * scaleAtEnd, 0);
                        v[2].TexCoord = new Vector2(1, 1);
                        v[2].Color    = bolt.CurrentColor;

                        v[3]          = new VertexC1P3T2();
                        v[3].Pos      = bd.End - new Vector3(normal * Sway * scaleAtEnd, 0);
                        v[3].TexCoord = new Vector2(1, 0);
                        v[3].Color    = bolt.CurrentColor;

                        device.AddVertices(bd.BatchInfo, VertexMode.Quads, v);
                    }
                }
            }
        }