예제 #1
0
 // switching colors
 private unsafe void BackgroundRadioButton_Checked(object sender, RoutedEventArgs e)
 {
     fixed (Color* colorptr = &BackgroundColor)
     {
         selectedcolor = colorptr;
     }
     UpdateControls();
 }
        /// <summary>
        /// Applies the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);

            var tempPixels = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, tempPixels, image.Pixels.Length);
            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * Pointer = &image.Pixels[(y * image.Width) + targetLocation.Left])
                {
                    Color *OutputPointer = Pointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        var XValue    = new Vector4(0, 0, 0, 0);
                        var YValue    = new Vector4(0, 0, 0, 0);
                        float WeightX = 0;
                        float WeightY = 0;
                        int XCurrent  = -Width >> 1;
                        int YCurrent  = -Height >> 1;
                        int Start     = 0;
                        fixed(float *XMatrixPointer = &XMatrix[0])
                        {
                            fixed(float *YMatrixPointer = &YMatrix[0])
                            {
                                float *XMatrixValue = XMatrixPointer;
                                float *YMatrixValue = YMatrixPointer;
                                for (int MatrixIndex = 0; MatrixIndex < XMatrix.Length; ++MatrixIndex)
                                {
                                    if (MatrixIndex % Width == 0 && MatrixIndex != 0)
                                    {
                                        ++YCurrent;
                                        XCurrent = 0;
                                    }
                                    if (XCurrent + x < image.Width && XCurrent + x >= 0 &&
                                        YCurrent + y < image.Height && YCurrent + y >= 0)
                                    {
                                        if (*XMatrixValue != 0 || *YMatrixValue != 0)
                                        {
                                            Start         = ((YCurrent + y) * image.Width) + (x + XCurrent);
                                            var TempPixel = tempPixels[Start];
                                            XValue        = XValue + new Vector4((*XMatrixValue * TempPixel.Red),
                                                                                 (*XMatrixValue * TempPixel.Green),
                                                                                 (*XMatrixValue * TempPixel.Blue),
                                                                                 (*XMatrixValue * TempPixel.Alpha));
                                            YValue = YValue + new Vector4((*YMatrixValue * TempPixel.Red),
                                                                          (*YMatrixValue * TempPixel.Green),
                                                                          (*YMatrixValue * TempPixel.Blue),
                                                                          (*YMatrixValue * TempPixel.Alpha));
                                            WeightX += *XMatrixValue;
                                            WeightY += *YMatrixValue;
                                        }
                                        ++XMatrixValue;
                                        ++YMatrixValue;
                                    }
                                    ++XCurrent;
                                }
                            }
                        }
                        if (WeightX == 0)
                        {
                            WeightX = 1;
                        }
                        if (WeightY == 0)
                        {
                            WeightY = 1;
                        }
                        if (WeightX > 0 && WeightY > 0)
                        {
                            if (Absolute)
                            {
                                YValue = Vector4.Abs(YValue);
                                XValue = Vector4.Abs(XValue);
                            }
                            XValue        /= WeightX;
                            YValue        /= WeightY;
                            var TempResult = Vector4.SquareRoot((XValue * XValue) + (YValue * YValue));
                            TempResult     = Vector4.Clamp(TempResult, Vector4.Zero, new Vector4(255, 255, 255, 255)) / 255f;
                            *OutputPointer = TempResult;
                            ++OutputPointer;
                        }
                        else
                        {
                            ++OutputPointer;
                        }
                    }
                }
            });
            return(image);
        }
예제 #3
0
        /// <summary>
        /// Applies the filter to the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var Result = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, Result, Result.Length);
            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * Pointer = &image.Pixels[(y * image.Width) + targetLocation.Left])
                {
                    Color *SourcePointer = Pointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        uint[] RValues   = { 0, 0, 0, 0 };
                        uint[] GValues   = { 0, 0, 0, 0 };
                        uint[] BValues   = { 0, 0, 0, 0 };
                        uint[] NumPixels = { 0, 0, 0, 0 };
                        uint[] MaxRValue = { 0, 0, 0, 0 };
                        uint[] MaxGValue = { 0, 0, 0, 0 };
                        uint[] MaxBValue = { 0, 0, 0, 0 };
                        uint[] MinRValue = { 255, 255, 255, 255 };
                        uint[] MinGValue = { 255, 255, 255, 255 };
                        uint[] MinBValue = { 255, 255, 255, 255 };

                        for (int i = 0; i < 4; ++i)
                        {
                            for (int x2 = ApetureMinX[i]; x2 < ApetureMaxX[i]; ++x2)
                            {
                                int TempX = x + x2;
                                if (TempX >= 0 && TempX < image.Width)
                                {
                                    for (int y2 = ApetureMinY[i]; y2 < ApetureMaxY[i]; ++y2)
                                    {
                                        int TempY = y + y2;
                                        if (TempY >= 0 && TempY < image.Height)
                                        {
                                            RValues[i] += image.Pixels[(TempY * image.Width) + TempX].Red;
                                            GValues[i] += image.Pixels[(TempY * image.Width) + TempX].Green;
                                            BValues[i] += image.Pixels[(TempY * image.Width) + TempX].Blue;

                                            if (image.Pixels[(TempY * image.Width) + TempX].Red > MaxRValue[i])
                                            {
                                                MaxRValue[i] = image.Pixels[(TempY * image.Width) + TempX].Red;
                                            }
                                            else if (image.Pixels[(TempY * image.Width) + TempX].Red < MinRValue[i])
                                            {
                                                MinRValue[i] = image.Pixels[(TempY * image.Width) + TempX].Red;
                                            }

                                            if (image.Pixels[(TempY * image.Width) + TempX].Green > MaxGValue[i])
                                            {
                                                MaxGValue[i] = image.Pixels[(TempY * image.Width) + TempX].Green;
                                            }
                                            else if (image.Pixels[(TempY * image.Width) + TempX].Green < MinGValue[i])
                                            {
                                                MinGValue[i] = image.Pixels[(TempY * image.Width) + TempX].Green;
                                            }

                                            if (image.Pixels[(TempY * image.Width) + TempX].Blue > MaxBValue[i])
                                            {
                                                MaxBValue[i] = image.Pixels[(TempY * image.Width) + TempX].Blue;
                                            }
                                            else if (image.Pixels[(TempY * image.Width) + TempX].Blue < MinBValue[i])
                                            {
                                                MinBValue[i] = image.Pixels[(TempY * image.Width) + TempX].Blue;
                                            }

                                            ++NumPixels[i];
                                        }
                                    }
                                }
                            }
                        }

                        int j = 0;
                        uint MinDifference = uint.MaxValue;
                        for (int i = 0; i < 4; ++i)
                        {
                            uint CurrentDifference = (MaxRValue[i] - MinRValue[i]) + (MaxGValue[i] - MinGValue[i]) + (MaxBValue[i] - MinBValue[i]);
                            if (CurrentDifference < MinDifference && NumPixels[i] > 0)
                            {
                                j             = i;
                                MinDifference = CurrentDifference;
                            }
                        }
                        RValues[j] = RValues[j] / NumPixels[j];
                        GValues[j] = GValues[j] / NumPixels[j];
                        BValues[j] = BValues[j] / NumPixels[j];

                        Result[(y * image.Width) + x].Red   = (byte)RValues[j];
                        Result[(y * image.Width) + x].Green = (byte)GValues[j];
                        Result[(y * image.Width) + x].Blue  = (byte)BValues[j];
                    }
                }
            });
            return(image.ReCreate(image.Width, image.Height, Result));
        }
        unsafe void WarpingAlgorithm.WarpImage(MarkerSet markerSet, Morphing.ImageData inputImage, Morphing.ImageData outputImage, bool startImage)
        {
            System.Diagnostics.Debug.Assert(markerSet != null && inputImage != null && outputImage != null);

            PointMarkerSet pointMarkerSet = markerSet as PointMarkerSet;

            System.Diagnostics.Debug.Assert(pointMarkerSet != null);

            // minor precomputation - movevector & interppos (for more mem consistency)
            WarpMarker[] markers;
            if (startImage)
            {
                markers = pointMarkerSet.Points.Select(x => new WarpMarker
                {
                    CurrentPos = x.InterpolatedMarker,
                    MoveVec    = x.StartMarker - x.InterpolatedMarker
                }).ToArray();
            }
            else
            {
                markers = pointMarkerSet.Points.Select(x => new WarpMarker
                {
                    CurrentPos = x.InterpolatedMarker,
                    MoveVec    = x.EndMarker - x.InterpolatedMarker
                }).ToArray();
            }
            double xStep = 1.0 / outputImage.Width;

            if (markers.Length == 0)
            {
                return;
            }

            Parallel.For(0, outputImage.Height, yi =>
            {
                Color *outputDataPixel     = outputImage.Data + yi * outputImage.Width;
                Color *lastOutputDataPixel = outputDataPixel + outputImage.Width;
                double y = (double)yi / outputImage.Height;

                for (double x = 0; outputDataPixel != lastOutputDataPixel; x += xStep, ++outputDataPixel)
                {
                    Vector position     = new Vector(x, y);
                    Vector displacement = new Vector(0, 0);

                    // fixed ptr won't work inside loop! // for(WarpMarker* pMarker = pMarkerFirst; pMarker != pMarkerEnd; ++pMarker)
                    double weightSum = 0.0f;
                    foreach (var marker in markers)
                    {
                        double distSq = (position - marker.CurrentPos).LengthSquared;
                        double weight = Math.Exp(-distSq / POINT_WEIGHT);//1.0f / (1.0f + distSq / POINT_WEIGHT);        // inverse quadratic!
                        weightSum    += weight;
                        displacement += marker.MoveVec * weight;
                    }
                    displacement /= weightSum;
                    position     += displacement;
                    position      = position.ClampToImageArea();

                    *outputDataPixel = inputImage.Sample(position.X, position.Y);
                }
            });
        }
    public void Quantize(IColorQuantizer quantizer, int colorCount)
    {
        if (Disposed)
        {
            return;
        }
        int    myWidth  = Width;
        int    myHeight = Height;
        Color *colors   = GetColors();

        quantizer.Prepare(this);
        bool usesAlpha = false;
        // weird stuff to make the quantizer work with alpha
        Color lastColor       = new Color(255, 255, 255, 0);
        bool  firstColorFound = false;

        for (int y = 0; y < myHeight; y++)
        {
            for (int x = 0; x < myWidth; x++)
            {
                int idx = x + y * myWidth;
                var col = *(colors + idx);
                if (col.A > 128)
                {
                    col.A = 255;
                    (*(colors + x + y * myWidth)) = col;
                    if (!firstColorFound && usesAlpha)
                    {
                        for (int i = 0; i < idx; i++)
                        {
                            quantizer.AddColor(col, i % myWidth, Mathf.FloorToInt(i / myWidth));
                        }
                    }
                    firstColorFound = true;
                    lastColor       = col;
                    quantizer.AddColor(col, x, y);
                }
                else
                {
                    col = new Color(255, 255, 255, 0);
                    (*(colors + x + y * myWidth)) = col;
                    usesAlpha = true;

                    if (firstColorFound)
                    {
                        quantizer.AddColor(lastColor, x, y);
                    }
                }
            }
        }
        var palette = quantizer.GetPalette(colorCount);

        for (int y = 0; y < myHeight; y++)
        {
            for (int x = 0; x < myWidth; x++)
            {
                if ((*(colors + x + y * myWidth)).A == 255)
                {
                    int index = quantizer.GetPaletteIndex(*(colors + x + y * myWidth), x, y);
                    //Debug.Log(index);
                    *(colors + x + y * myWidth) = palette[index];
                }
            }
        }
        quantizer.Finish();
    }
예제 #6
0
        public unsafe void CreateTexture(int index, out Texture2D diffuseTexture, out Texture2D normalTexture)
        {
            diffuseTexture = null;
            normalTexture  = null;

            if (!_fileIndex.FilesExist)
            {
                return;
            }

            int  length, extra;
            bool patched;

            Stream stream = _fileIndex.Seek(index, out length, out extra, out patched);

            if (stream == null)
            {
                return;
            }

            int size       = extra == 0 ? 64 : 128;
            int pixelCount = size * size;

            byte[]   buffer = new byte[pixelCount * 2];
            ushort[] pixels = new ushort[pixelCount];
            Color[]  colors = new Color[pixelCount];

            stream.Read(buffer, 0, buffer.Length);
            Buffer.BlockCopy(buffer, 0, pixels, 0, pixelCount * 2);

            fixed(ushort *pPtr = pixels)
            fixed(Color * cPtr = colors)
            {
                ushort *pixelPtr = pPtr;
                Color * colorPtr = cPtr;

                int count = pixels.Length;

                for (int i = 0; i < count; i++)
                {
                    colorPtr->R = (byte)((*pixelPtr & 0x1F) & multiplier);
                    colorPtr->G = (byte)(((*pixelPtr >> 5) & 0x1F) & multiplier);
                    colorPtr->B = (byte)(((*pixelPtr >> 10) & 0x1F) & multiplier);
                    colorPtr->A = 255;
                    colorPtr++;
                }
            }

            diffuseTexture = new Texture2D(GraphicsDeviceManager.Current.GraphicsDevice, size, size, false, SurfaceFormat.Color);
            diffuseTexture.SetData(colors);

            float[]   heights      = GenerateHeightFields(pixels, size);
            Vector3[] normals      = GenerateNormalFields(heights, size, false);
            Color[]   normalColors = new Color[heights.Length];

            fixed(Vector3 *normal = normals)
            fixed(Color * color = normalColors)
            {
                Vector3 *nPtr = normal;
                Color *  cPtr = color;

                int count = normalColors.Length;

                for (int i = 0; i < count; i++)
                {
                    cPtr->R = (byte)(nPtr->X * 255);
                    cPtr->G = (byte)(nPtr->Y * 255);
                    cPtr->B = (byte)(nPtr->Z * 255);

                    nPtr++;
                    cPtr++;
                }
            }

            normalTexture = new Texture2D(GraphicsDeviceManager.Current.GraphicsDevice, size, size, false, SurfaceFormat.Color);
            normalTexture.SetData(normalColors);
        }
예제 #7
0
 public unsafe static extern void RenderPixels(int width, int height, Color *pixels);
예제 #8
0
        /// <summary>
        /// Applies the filter to the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var TempValues = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, TempValues, TempValues.Length);
            int ApetureMin = -ApetureRadius;
            int ApetureMax = ApetureRadius;

            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * TargetPointer = &image.Pixels[(y * image.Width) + targetLocation.Left])
                {
                    Color *TargetPointer2 = TargetPointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        byte RValue = byte.MaxValue;
                        byte GValue = byte.MaxValue;
                        byte BValue = byte.MaxValue;
                        for (int y2 = ApetureMin; y2 < ApetureMax; ++y2)
                        {
                            int TempY = y + y2;
                            int TempX = x + ApetureMin;
                            if (TempY >= 0 && TempY < image.Height)
                            {
                                int Length = ApetureRadius * 2;
                                if (TempX < 0)
                                {
                                    Length += TempX;
                                    TempX   = 0;
                                }
                                var Start = ((TempY * image.Width) + TempX);
                                fixed(Color * ImagePointer = &TempValues[Start])
                                {
                                    Color *ImagePointer2 = ImagePointer;
                                    for (int x2 = 0; x2 < Length; ++x2)
                                    {
                                        if (TempX >= image.Width)
                                        {
                                            break;
                                        }
                                        var TempR = (*ImagePointer2).Red;
                                        var TempG = (*ImagePointer2).Green;
                                        var TempB = (*ImagePointer2).Blue;
                                        ++ImagePointer2;
                                        RValue = RValue < TempR ? RValue : TempR;
                                        GValue = GValue < TempG ? GValue : TempG;
                                        BValue = BValue < TempB ? BValue : TempB;
                                        ++TempX;
                                    }
                                }
                            }
                        }
                        (*TargetPointer2).Red   = RValue;
                        (*TargetPointer2).Green = GValue;
                        (*TargetPointer2).Blue  = BValue;
                        ++TargetPointer2;
                    }
                }
            });
            return(image);
        }
예제 #9
0
    unsafe void ThreadedCopy(uint *Frame, Color *Pixels, int Frame2D_width, int Frame2D_height, int FrameArray_Length, int PixelsArray_Length)
    {
        int PixelsDrawn  = 0;
        int PixelsQueued = 0;

        bool Aborted = false;

        System.Action <int, int> CopyPixels = (PixelIndex, PixelCount) =>
        {
            try
            {
                var rgba = new Color();

                for (int p = PixelIndex; p < PixelIndex + PixelCount; p++)
                {
                    var x = p % Frame2D_width;
                    var y = p / Frame2D_width;

                    if (Flip)
                    {
                        y = Frame2D_height - 1 - y;
                    }

                    var FrameIndex = x + (y * Frame2D_width);
                    var rgba32     = Frame [FrameIndex];

                    var a = (rgba32 >> 24) & 0xff;
                    var r = (rgba32 >> 16) & 0xff;
                    var g = (rgba32 >> 8) & 0xff;
                    var b = (rgba32 >> 0) & 0xff;

                    if (ForceOpaque)
                    {
                        a = 255;
                    }

                    rgba.r     = r / 255.0f;
                    rgba.g     = g / 255.0f;
                    rgba.b     = b / 255.0f;
                    rgba.a     = a / 255.0f;
                    Pixels [p] = rgba;
                }
            }
            catch
            {
                Aborted = true;
            }

            Interlocked.Add(ref PixelsDrawn, PixelCount);
        };


        var TotalPixels = Mathf.Min(PixelCountClip, Mathf.Min(FrameArray_Length, PixelsArray_Length));
        int ThreadCount = TotalPixels / WritePixelsPerThread;

        for (int t = 0; t < ThreadCount + 1; t++)
        {
            int FirstPixel   = WritePixelsPerThread * t;
            int PixelsToDraw = WritePixelsPerThread;

            if (FirstPixel + PixelsToDraw > TotalPixels)
            {
                PixelsToDraw = TotalPixels - FirstPixel;
            }

            PixelsQueued += PixelsToDraw;

            if (PixelsToDraw > 0)
            {
                ThreadPool.QueueUserWorkItem((x) => { CopyPixels(FirstPixel, PixelsToDraw); });
            }
        }

        while (PixelsDrawn < PixelsQueued && !Aborted)
        {
            //Debug.Log ("Waiting for " + (PixelsQueued - PixelsDrawn) + " pixels to draw");
            Thread.Sleep(1);
        }
    }
예제 #10
0
 public override unsafe void Draw()
 {
     List <MyPhysics.HitInfo> .Enumerator enumerator2;
     base.Draw();
     foreach (MyCubeBlock block in this.m_grid.BlocksForDraw)
     {
         if (MyRenderProxy.VisibleObjectsRead.Contains(block.Render.RenderObjectIDs[0]))
         {
             block.Render.Draw();
         }
     }
     if ((MyCubeGrid.ShowCenterOfMass && (!this.IsStatic && (base.Container.Entity.Physics != null))) && base.Container.Entity.Physics.HasRigidBody)
     {
         MatrixD  worldMatrix       = base.Container.Entity.Physics.GetWorldMatrix();
         Vector3D centerOfMassWorld = base.Container.Entity.Physics.CenterOfMassWorld;
         Vector3D position          = MySector.MainCamera.Position;
         float    num  = Vector3.Distance((Vector3)position, (Vector3)centerOfMassWorld);
         bool     flag = false;
         if (num < 30f)
         {
             flag = true;
         }
         else if (num < 200f)
         {
             flag = true;
             MyPhysics.CastRay(position, centerOfMassWorld, m_tmpHitList, 0x10);
             using (enumerator2 = m_tmpHitList.GetEnumerator())
             {
                 while (enumerator2.MoveNext())
                 {
                     if (!ReferenceEquals(enumerator2.Current.HkHitInfo.GetHitEntity(), this))
                     {
                         flag = false;
                         break;
                     }
                 }
             }
             m_tmpHitList.Clear();
         }
         if (flag)
         {
             float      num2      = MathHelper.Lerp((float)1f, (float)9f, (float)(num / 200f));
             MyStringId id        = ID_WEAPON_LASER_IGNORE_DEPTH;
             Vector4    color     = Color.Yellow.ToVector4();
             float      thickness = 0.02f * num2;
             MySimpleObjectDraw.DrawLine(centerOfMassWorld - ((worldMatrix.Up * 0.5) * num2), centerOfMassWorld + ((worldMatrix.Up * 0.5) * num2), new MyStringId?(id), ref color, thickness, MyBillboard.BlendTypeEnum.AdditiveTop);
             MySimpleObjectDraw.DrawLine(centerOfMassWorld - ((worldMatrix.Forward * 0.5) * num2), centerOfMassWorld + ((worldMatrix.Forward * 0.5) * num2), new MyStringId?(id), ref color, thickness, MyBillboard.BlendTypeEnum.AdditiveTop);
             MySimpleObjectDraw.DrawLine(centerOfMassWorld - ((worldMatrix.Right * 0.5) * num2), centerOfMassWorld + ((worldMatrix.Right * 0.5) * num2), new MyStringId?(id), ref color, thickness, MyBillboard.BlendTypeEnum.AdditiveTop);
             MyTransparentGeometry.AddBillboardOriented(ID_RED_DOT_IGNORE_DEPTH, Color.White.ToVector4(), centerOfMassWorld, MySector.MainCamera.LeftVector, MySector.MainCamera.UpVector, 0.1f * num2, MyBillboard.BlendTypeEnum.AdditiveTop, -1, 0f);
         }
     }
     if (MyCubeGrid.ShowGridPivot)
     {
         MatrixD  worldMatrix = base.Container.Entity.WorldMatrix;
         Vector3D translation = worldMatrix.Translation;
         Vector3D position    = MySector.MainCamera.Position;
         float    num4        = Vector3.Distance((Vector3)position, (Vector3)translation);
         bool     flag2       = false;
         if (num4 < 30f)
         {
             flag2 = true;
         }
         else if (num4 < 200f)
         {
             flag2 = true;
             MyPhysics.CastRay(position, translation, m_tmpHitList, 0x10);
             using (enumerator2 = m_tmpHitList.GetEnumerator())
             {
                 while (enumerator2.MoveNext())
                 {
                     if (!ReferenceEquals(enumerator2.Current.HkHitInfo.GetHitEntity(), this))
                     {
                         flag2 = false;
                         break;
                     }
                 }
             }
             m_tmpHitList.Clear();
         }
         if (flag2)
         {
             float      num5      = MathHelper.Lerp((float)1f, (float)9f, (float)(num4 / 200f));
             MyStringId id2       = ID_WEAPON_LASER_IGNORE_DEPTH;
             float      thickness = 0.02f * num5;
             Vector4    color     = Color.Green.ToVector4();
             MySimpleObjectDraw.DrawLine(translation, translation + ((worldMatrix.Up * 0.5) * num5), new MyStringId?(id2), ref color, thickness, MyBillboard.BlendTypeEnum.Standard);
             color = Color.Blue.ToVector4();
             MySimpleObjectDraw.DrawLine(translation, translation + ((worldMatrix.Forward * 0.5) * num5), new MyStringId?(id2), ref color, thickness, MyBillboard.BlendTypeEnum.Standard);
             color = Color.Red.ToVector4();
             MySimpleObjectDraw.DrawLine(translation, translation + ((worldMatrix.Right * 0.5) * num5), new MyStringId?(id2), ref color, thickness, MyBillboard.BlendTypeEnum.Standard);
             MyTransparentGeometry.AddBillboardOriented(ID_RED_DOT_IGNORE_DEPTH, Color.White.ToVector4(), translation, MySector.MainCamera.LeftVector, MySector.MainCamera.UpVector, 0.1f * num5, MyBillboard.BlendTypeEnum.Standard, -1, 0f);
             MyRenderProxy.DebugDrawAxis(worldMatrix, 0.5f, false, false, false);
         }
     }
     if (!MyCubeGrid.ShowStructuralIntegrity)
     {
         if ((this.m_grid.StructuralIntegrity != null) && this.m_grid.StructuralIntegrity.EnabledOnlyForDraw)
         {
             this.m_grid.CloseStructuralIntegrity();
         }
     }
     else if (this.m_grid.StructuralIntegrity != null)
     {
         this.m_grid.StructuralIntegrity.Draw();
     }
     else if (MyFakes.ENABLE_STRUCTURAL_INTEGRITY)
     {
         this.m_grid.CreateStructuralIntegrity();
         if (this.m_grid.StructuralIntegrity != null)
         {
             this.m_grid.StructuralIntegrity.EnabledOnlyForDraw = true;
         }
     }
     if (MyFakes.ENABLE_ATMOSPHERIC_ENTRYEFFECT)
     {
         this.DrawAtmosphericEntryEffect();
     }
     if (this.m_grid.MarkedAsTrash)
     {
         BoundingBoxD localAABB   = this.m_grid.PositionComp.LocalAABB;
         Vector3D *   vectordPtr1 = (Vector3D *)ref localAABB.Max;
         vectordPtr1[0] += 0.2f;
         Vector3D *vectordPtr2 = (Vector3D *)ref localAABB.Min;
         vectordPtr2[0] -= 0.20000000298023224;
         MatrixD worldMatrix = this.m_grid.PositionComp.WorldMatrix;
         Color   red         = Color.Red;
         red.A = (byte)(((100.0 * (Math.Sin((double)(((float)this.m_grid.TrashHighlightCounter) / 10f)) + 1.0)) / 2.0) + 100.0);
         red.R = (byte)(((200.0 * (Math.Sin((double)(((float)this.m_grid.TrashHighlightCounter) / 10f)) + 1.0)) / 2.0) + 50.0);
         Color *    colorPtr1    = (Color *)ref red;
         MyStringId?faceMaterial = null;
         faceMaterial = null;
         MySimpleObjectDraw.DrawTransparentBox(ref worldMatrix, ref localAABB, ref (Color) ref colorPtr1, ref red, MySimpleObjectRasterizer.SolidAndWireframe, 1, 0.008f, faceMaterial, faceMaterial, false, -1, MyBillboard.BlendTypeEnum.LDR, 1f, null);
     }
 }
예제 #11
0
        private unsafe Color[] Sample(Image image, double xScale, double yScale, int oldWidth, int oldHeight)
        {
            Filter.Precompute(image.Width, image.Height, Width, Height);
            var    targetLocation       = new Rectangle(0, 0, image.Width, image.Height);
            var    Output               = new Color[Width * Height];
            var    TransformationMatrix = GetMatrix(image, targetLocation);
            double TempWidth            = Width < 0 ? image.Width : Width;
            double TempHeight           = Height < 0 ? image.Width : Height;
            double XScale               = TempWidth / image.Width;
            double YScale               = TempHeight / image.Height;
            var    YRadius              = YScale < 1f ? (Filter.FilterRadius / YScale) : Filter.FilterRadius;
            var    XRadius              = XScale < 1f ? (Filter.FilterRadius / XScale) : Filter.FilterRadius;

            Parallel.For(0, Height, y =>
            {
                fixed(Color * OutputPointer = &Output[y * Width])
                {
                    Color *OutputPointer2 = OutputPointer;
                    for (int x = 0; x < Width; ++x)
                    {
                        var Values   = new Vector4(0, 0, 0, 0);
                        float Weight = 0;

                        var rotated  = Vector2.Transform(new Vector2(x, y), TransformationMatrix);
                        var rotatedY = (int)rotated.Y;
                        var rotatedX = (int)rotated.X;
                        var Left     = (int)(rotatedX - XRadius);
                        var Right    = (int)(rotatedX + XRadius);
                        var Top      = (int)(rotatedY - YRadius);
                        var Bottom   = (int)(rotatedY + YRadius);
                        if (Top < 0)
                        {
                            Top = 0;
                        }
                        if (Bottom >= image.Height)
                        {
                            Bottom = image.Height - 1;
                        }
                        if (Left < 0)
                        {
                            Left = 0;
                        }
                        if (Right >= image.Width)
                        {
                            Right = image.Width - 1;
                        }
                        for (int i = Top, YCount = 0; i <= Bottom; ++i, ++YCount)
                        {
                            fixed(Color * PixelPointer = &image.Pixels[i * image.Width])
                            {
                                Color *PixelPointer2 = PixelPointer + Left;
                                for (int j = Left, XCount = 0; j <= Right; ++j, ++XCount)
                                {
                                    var TempYWeight = Filter.YWeights[rotatedY].Values[YCount];
                                    var TempXWeight = Filter.XWeights[rotatedX].Values[XCount];
                                    var TempWeight  = TempYWeight * TempXWeight;

                                    if (YRadius == 0 && XRadius == 0)
                                    {
                                        TempWeight = 1;
                                    }

                                    if (TempWeight == 0)
                                    {
                                        ++PixelPointer2;
                                        continue;
                                    }
                                    Values.X = Values.X + ((*PixelPointer2).Red * (float)TempWeight);
                                    Values.Y = Values.Y + ((*PixelPointer2).Green * (float)TempWeight);
                                    Values.Z = Values.Z + ((*PixelPointer2).Blue * (float)TempWeight);
                                    Values.W = Values.W + ((*PixelPointer2).Alpha * (float)TempWeight);
                                    ++PixelPointer2;
                                    Weight += (float)TempWeight;
                                }
                            }
                        }
                        if (Weight == 0)
                        {
                            Weight = 1;
                        }
                        if (Weight > 0)
                        {
                            Values = Vector4.Clamp(Values, Vector4.Zero, new Vector4(255, 255, 255, 255));
                            (*OutputPointer2).Red   = (byte)Values.X;
                            (*OutputPointer2).Green = (byte)Values.Y;
                            (*OutputPointer2).Blue  = (byte)Values.Z;
                            (*OutputPointer2).Alpha = (byte)Values.W;
                            ++OutputPointer2;
                        }
                        else
                        {
                            ++OutputPointer2;
                        }
                    }
                }
            });
            return(Output);
        }
예제 #12
0
        /// <summary>
        /// GIF文件写入器
        /// </summary>
        /// <param name="filename">文件名称</param>
        /// <param name="width">素数宽度</param>
        /// <param name="height">素数高度</param>
        /// <param name="globalColors">全局颜色列表</param>
        /// <param name="backgroundColorIndex">背景颜色在全局颜色列表中的索引,如果没有全局颜色列表,该值没有意义</param>
        /// <param name="log">日志处理</param>
        public unsafe FileWriter(string filename, short width, short height, Color[] globalColors = null, byte backgroundColorIndex = 0, ILog log = null)
        {
            this.log = log ?? AutoCSer.Log.Pub.Log;
            if (width <= 0)
            {
                throw new IndexOutOfRangeException("width[" + width.toString() + "] <= 0");
            }
            if (height <= 0)
            {
                throw new IndexOutOfRangeException("height[" + height.toString() + "] <= 0");
            }
            if (string.IsNullOrEmpty(filename))
            {
                throw new ArgumentNullException("filename is null or empty");
            }
            fileStream       = new FileStream(filename, FileMode.CreateNew, FileAccess.Write, FileShare.None, 1, FileOptions.WriteThrough);
            Width            = width;
            Height           = height;
            globalColorCount = globalColors.length();
            int pixel = 0;

            if (globalColorCount != 0)
            {
                if (globalColorCount < 256)
                {
                    pixel = ((uint)globalColorCount).bits() - 1;
                    if (globalColorCount != (1 << pixel))
                    {
                        ++pixel;
                    }
                }
                else
                {
                    globalColorCount = 256;
                    pixel            = 7;
                }
                pixel |= 0x80;
            }

            fixed(byte *bufferFixed = fileBuffer)
            {
                *(ulong *)bufferFixed      = fileVersion | ((ulong)width << 48);
                *(uint *)(bufferFixed + 8) = (uint)(int)height | (globalColorCount == 0 ? 0 : ((uint)pixel << 16)) | (7 << (16 + 4))
                                             | (backgroundColorIndex >= globalColorCount ? 0 : ((uint)backgroundColorIndex << 24));
                bufferIndex = 13;
                if (globalColorCount != 0)
                {
                    byte *currentBuffer = bufferFixed + 13;
                    fixed(Color *colorFixed = globalColors)
                    {
                        for (Color *currentColor = colorFixed, colorEnd = colorFixed + globalColorCount; currentColor != colorEnd; ++currentColor)
                        {
                            Color color           = *currentColor;
                            *     currentBuffer++ = color.Red;
                            *     currentBuffer++ = color.Green;
                            *     currentBuffer++ = color.Blue;
                        }
                    }

                    bufferIndex += 3 << (pixel ^ 0x80);
                }
            }

            colors      = new Color[(int)Width * Height];
            colorCounts = new int[colors.Length];
            colorIndexs = DictionaryCreator <Color> .Create <int>();
        }
예제 #13
0
        /// <summary>
        /// 添加图片
        /// </summary>
        /// <param name="bitmap">位图</param>
        /// <param name="leftOffset">X方向偏移量</param>
        /// <param name="topOffset">Y方向偏移量</param>
        /// <param name="width">图象宽度</param>
        /// <param name="height">图象高度</param>
        /// <param name="bitmapLeftOffset">位图剪切X方向偏移量</param>
        /// <param name="bitmapTopOffset">位图剪切Y方向偏移量</param>
        /// <param name="isInterlace">图象数据是否连续方式排列,否则使用顺序排列</param>
        /// <param name="maxPixel">最大色彩深度</param>
        /// <returns>图片是否添加成功</returns>
        internal unsafe bool addImage(BitmapData bitmap, int bitmapLeftOffset, int bitmapTopOffset
                                      , int leftOffset, int topOffset, int width, int height, bool isInterlace, byte maxPixel)
        {
            if (fileBuffer == null)
            {
                return(false);

                fixed(Color *colorFixed = colors)
                fixed(int *colorCountFixed = colorCounts)
                {
                    byte * bitmapFixed = (byte *)bitmap.Scan0, currentBitmap = bitmapFixed + bitmap.Stride * (bitmapTopOffset - 1) + (bitmapLeftOffset + width) * 3;
                    Color *currentColor = colorFixed;
                    int    bitMapSpace  = bitmap.Stride - (width << 1) - width;

                    colorIndexs.Clear();
                    for (int colorIndex, row = height; row != 0; --row)
                    {
                        currentBitmap += bitMapSpace;
                        for (int col = width; col != 0; --col)
                        {
                            Color color = new Color {
                                Green = *currentBitmap++, Blue = *currentBitmap++, Red = *currentBitmap++
                            };
                            if (colorIndexs.TryGetValue(color, out colorIndex))
                            {
                                ++colorCountFixed[colorIndex];
                            }
                            else
                            {
                                colorIndexs.Add(color, colorIndex = (int)(currentColor - colorFixed));
                                colorCountFixed[colorIndex]       = 1;
                            }
                            *currentColor++ = color;
                        }
                    }
                    int pixel = ((uint)colorIndexs.Count).bits() - 1;

                    if ((1 << pixel) != colorIndexs.Count)
                    {
                        ++pixel;
                    }
                    if (pixel > maxPixel)
                    {
                        pixel = maxPixel;
                    }
                    else if (pixel < 2)
                    {
                        pixel = 2;
                    }
                    int maxColorCount = 1 << pixel;

                    fixed(byte *bufferFixed = fileBuffer)
                    {
                        byte *currentBuffer = bufferFixed + bufferIndex;

                        *currentBuffer = 0x2c;
                        *(short *)(currentBuffer + 1) = (short)leftOffset;
                        *(short *)(currentBuffer + 3) = (short)topOffset;
                        *(short *)(currentBuffer + 5) = (short)width;
                        *(short *)(currentBuffer + 7) = (short)height;
                        *(currentBuffer + 9)          = (byte)(0x80 + (isInterlace ? 0x40 : 0) + (pixel - 1));
                        if (!checkBuffer(bufferFixed, 10))
                        {
                            return(false);
                        }
                    }

                    if (colorIndexs.Count <= maxColorCount)
                    {
                        fixed(byte *bufferFixed = fileBuffer)
                        {
                            int *currentColorCount = colorCountFixed;

                            foreach (Color colorKey in colorIndexs.Keys)
                            {
                                *currentColorCount++ = colorKey.Value;
                            }
                            Color color             = new Color();
                            int   currentColorIndex = 0;
                            byte *currentBuffer     = bufferFixed + bufferIndex;

                            while (currentColorCount != colorCountFixed)
                            {
                                color.Value = *--currentColorCount;
                                *currentBuffer++ = color.Red;
                                *currentBuffer++ = color.Blue;
                                *currentBuffer++ = color.Green;
                                colorIndexs[color] = currentColorIndex++;
                            }
                            *(bufferFixed + bufferIndex + (maxColorCount << 1) + maxColorCount) = (byte)pixel;
                            if (!checkBuffer(bufferFixed, (maxColorCount << 1) + maxColorCount + 1))
                            {
                                return(false);
                            }
                        }
                    }
                    else
                    {
                        int           indexCount = colorIndexs.Count;
                        UnmanagedPool pool       = UnmanagedPool.GetDefaultPool(indexCount * sizeof(IntSortIndex));
                        Pointer.Size  sizeBuffer = pool.GetSize(indexCount * (sizeof(IntSortIndex) + sizeof(int)));
                        int *         buffer     = sizeBuffer.Int;
                        try
                        {
                            IntSortIndex *indexFixed = (IntSortIndex *)(buffer + indexCount), currentSortIndex = indexFixed;
                            foreach (KeyValuePair <Color, int> colorIndex in colorIndexs)
                            {
                                int color0 = colorIndex.Key.Value;
                                int color3 = ((color0 >> 3) & 0x111111) * 0x1020400;
                                int color2 = ((color0 >> 2) & 0x111111) * 0x1020400;
                                int color1 = ((color0 >> 1) & 0x111111) * 0x1020400;
                                color0 = (color0 & 0x111111) * 0x1020400;
                                (*currentSortIndex++).Set((color3 & 0x70000000) | ((color2 >> 4) & 0x7000000)
                                                          | ((color1 >> 8) & 0x700000) | ((color0 >> 12) & 0x70000) | ((color3 >> 12) & 0x7000)
                                                          | ((color2 >> 16) & 0x700) | ((color1 >> 20) & 0x70) | ((color0 >> 24) & 7), colorIndex.Value);
                            }
                            AutoCSer.Algorithm.FixedArrayQuickSort.sort(indexFixed, indexFixed + indexCount - 1);
                            int *currentSortArray;
                            if (maxColorCount != 2)
                            {
                                currentSortArray = buffer;
                                for (int currentColorCode, lastColorCode = (*--currentSortIndex).Value; currentSortIndex != indexFixed; lastColorCode = currentColorCode)
                                {
                                    currentColorCode = (*--currentSortIndex).Value;
                                    *currentSortArray++ = lastColorCode - currentColorCode;
                                }
                                currentSortArray = buffer + (maxColorCount >> 1) - 2;
                                new AutoCSer.Algorithm.FixedArrayQuickRangeSort.IntRangeSorterDesc {
                                    SkipCount = currentSortArray, GetEndIndex = currentSortArray
                                }.Sort(buffer, buffer + indexCount - 2);
                                int minColorDifference = *currentSortArray, minColorDifferenceCount = 1;
                                while (currentSortArray != buffer)
                                {
                                    if (*--currentSortArray == minColorDifference)
                                    {
                                        ++minColorDifferenceCount;
                                    }
                                }
                                currentSortIndex = indexFixed + indexCount;
                                int maxCountIndex = (*--currentSortIndex).Index, maxCount = *(colorCountFixed + maxCountIndex);
                                for (int currentColorCode, lastColorCode = (*currentSortIndex).Value; currentSortIndex != indexFixed; lastColorCode = currentColorCode)
                                {
                                    currentColorCode = (*--currentSortIndex).Value;
                                    int colorDifference = lastColorCode - currentColorCode;
                                    if (colorDifference >= minColorDifference)
                                    {
                                        if (colorDifference == minColorDifference && --minColorDifferenceCount == 0)
                                        {
                                            ++minColorDifference;
                                        }
                                        *(colorCountFixed + maxCountIndex) = int.MaxValue;
                                        maxCount = *(colorCountFixed + (maxCountIndex = (*currentSortIndex).Index));
                                    }
                                    else
                                    {
                                        int countIndex = (*currentSortIndex).Index, count = *(colorCountFixed + countIndex);
                                        if (count > maxCount)
                                        {
                                            maxCountIndex = countIndex;
                                            maxCount      = count;
                                        }
                                    }
                                }
                                *(colorCountFixed + maxCountIndex) = int.MaxValue;
                            }
                            for (currentSortArray = buffer + indexCount, currentSortIndex = indexFixed; currentSortArray != buffer; *(--currentSortArray) = *(colorCountFixed + (*currentSortIndex++).Index))
                            {
                                ;
                            }
                            currentSortArray = buffer + maxColorCount - 1;
                            new AutoCSer.Algorithm.FixedArrayQuickRangeSort.IntRangeSorterDesc {
                                SkipCount = currentSortArray, GetEndIndex = currentSortArray
                            }.Sort(buffer, buffer + indexCount - 1);
                            int minColorCount = *currentSortArray, minColorCounts = 1;
                            while (currentSortArray != buffer)
                            {
                                if (*--currentSortArray == minColorCount)
                                {
                                    ++minColorCounts;
                                }
                            }
                            fixed(byte *fileBufferFixed = fileBuffer)
                            {
                                byte *        currentBuffer = fileBufferFixed + bufferIndex;
                                IntSortIndex *lastSortIndex = indexFixed, endSortIndex = indexFixed + indexCount;

                                while (*(colorCountFixed + (*lastSortIndex).Index) < minColorCount)
                                {
                                    colorIndexs[*(colorFixed + (*lastSortIndex++).Index)] = 0;
                                }
                                if (*(colorCountFixed + (*lastSortIndex).Index) == minColorCount && --minColorCounts == 0)
                                {
                                    ++minColorCount;
                                }
                                Color outputColor = *(colorFixed + (*lastSortIndex).Index);

                                *currentBuffer++ = outputColor.Red;
                                *currentBuffer++ = outputColor.Blue;
                                *currentBuffer++ = outputColor.Green;
                                colorIndexs[outputColor] = 0;
                                for (--maxColorCount; *(colorCountFixed + (*--endSortIndex).Index) < minColorCount; colorIndexs[*(colorFixed + (*endSortIndex).Index)] = maxColorCount)
                                {
                                    ;
                                }
                                if (*(colorCountFixed + (*endSortIndex).Index) == minColorCount && --minColorCounts == 0)
                                {
                                    ++minColorCount;
                                }
                                colorIndexs[*(colorFixed + (*endSortIndex).Index)] = maxColorCount++;
                                int currentColorIndex = 0;

                                for (int *lastColorCount = colorCountFixed + (*endSortIndex).Index; lastSortIndex != endSortIndex;)
                                {
                                    for (*lastColorCount = 0; *(colorCountFixed + (*++lastSortIndex).Index) >= minColorCount; colorIndexs[outputColor] = ++currentColorIndex)
                                    {
                                        if (*(colorCountFixed + (*lastSortIndex).Index) == minColorCount && --minColorCounts == 0)
                                        {
                                            ++minColorCount;
                                        }
                                        outputColor = *(colorFixed + (*lastSortIndex).Index);
                                        *currentBuffer++ = outputColor.Red;
                                        *currentBuffer++ = outputColor.Blue;
                                        *currentBuffer++ = outputColor.Green;
                                    }
                                    if (lastSortIndex == endSortIndex)
                                    {
                                        break;
                                    }
                                    *lastColorCount = int.MaxValue;
                                    IntSortIndex *nextSortIndex = lastSortIndex;
                                    while (*(colorCountFixed + (*++nextSortIndex).Index) < minColorCount)
                                    {
                                        ;
                                    }
                                    for (int lastColorCode = (*(lastSortIndex - 1)).Value, nextColorCode = (*nextSortIndex).Value; lastSortIndex != nextSortIndex; ++lastSortIndex)
                                    {
                                        colorIndexs[*(colorFixed + (*lastSortIndex).Index)] = (*lastSortIndex).Value - lastColorCode <= nextColorCode - (*lastSortIndex).Value ? currentColorIndex : (currentColorIndex + 1);
                                    }
                                    if (lastSortIndex != endSortIndex)
                                    {
                                        if (*(colorCountFixed + (*lastSortIndex).Index) == minColorCount && --minColorCounts == 0)
                                        {
                                            ++minColorCount;
                                        }
                                        outputColor = *(colorFixed + (*lastSortIndex).Index);
                                        *currentBuffer++ = outputColor.Red;
                                        *currentBuffer++ = outputColor.Blue;
                                        *currentBuffer++ = outputColor.Green;
                                        colorIndexs[outputColor] = ++currentColorIndex;
                                    }
                                }
                                outputColor = *(colorFixed + (*lastSortIndex).Index);
                                *currentBuffer++ = outputColor.Red;
                                *currentBuffer++ = outputColor.Blue;
                                *currentBuffer++ = outputColor.Green;
                                *currentBuffer   = (byte)pixel;
                                if (!checkBuffer(fileBufferFixed, (maxColorCount << 1) + maxColorCount + 1))
                                {
                                    return(false);
                                }
                            }
                        }
                        finally { pool.Push(ref sizeBuffer); }
                    }
                    byte *colorIndexFixed = (byte *)colorCountFixed;

                    if (isInterlace)
                    {
                        Color *colorEnd   = colorFixed + width * height;
                        int    inputSpace = (width << 3) - width;
                        for (Color *inputColor = colorFixed; inputColor < colorEnd; inputColor += inputSpace)
                        {
                            for (Color *inputEnd = inputColor + width; inputColor != inputEnd; *colorIndexFixed++ = (byte)colorIndexs[*inputColor++])
                            {
                                ;
                            }
                        }
                        for (Color *inputColor = colorFixed + (width << 2); inputColor < colorEnd; inputColor += inputSpace)
                        {
                            for (Color *inputEnd = inputColor + width; inputColor != inputEnd; *colorIndexFixed++ = (byte)colorIndexs[*inputColor++])
                            {
                                ;
                            }
                        }
                        inputSpace -= width << 2;
                        for (Color *inputColor = colorFixed + (width << 1); inputColor < colorEnd; inputColor += inputSpace)
                        {
                            for (Color *inputEnd = inputColor + width; inputColor != inputEnd; *colorIndexFixed++ = (byte)colorIndexs[*inputColor++])
                            {
                                ;
                            }
                        }
                        for (Color *inputColor = colorFixed + width; inputColor < colorEnd; inputColor += width)
                        {
                            for (Color *inputEnd = inputColor + width; inputColor != inputEnd; *colorIndexFixed++ = (byte)colorIndexs[*inputColor++])
                            {
                                ;
                            }
                        }
                    }
                    else
                    {
                        for (Color *inputColor = colorFixed, inputEnd = colorFixed + width * height; inputColor != inputEnd; *colorIndexFixed++ = (byte)colorIndexs[*inputColor++])
                        {
                            ;
                        }
                    }
                    return(lzwEncode((byte *)colorCountFixed, colorIndexFixed, pixel));
                }
        }
예제 #14
0
 public void Dispose()
 {
     System.Runtime.InteropServices.Marshal.FreeHGlobal((IntPtr)Data);
     Data = null;
 }
예제 #15
0
 public unsafe static extern void RenderText(int scrW, int scrH, int width, int height, Color *pixels);
예제 #16
0
 public void Dispose()
 {
     System.Runtime.InteropServices.Marshal.FreeHGlobal((IntPtr)Data);
     Data = null;
 }
예제 #17
0
 public static extern void GlTexImage2D(uint target, int level, uint internalformat, int width, int height, int border, uint format, uint type, Color *pixels);
        /// <summary>
        /// Applies the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var tempPixels = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, tempPixels, image.Pixels.Length);
            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * Pointer = &image.Pixels[(y * image.Width) + targetLocation.Left])
                {
                    Color *OutputPointer = Pointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        var Values   = new Vector4(0, 0, 0, 0);
                        float Weight = 0;
                        int XCurrent = -Width >> 1;
                        int YCurrent = -Height >> 1;
                        int Start    = 0;
                        fixed(float *MatrixPointer = &Matrix[0])
                        {
                            float *MatrixValue = MatrixPointer;
                            for (int MatrixIndex = 0; MatrixIndex < Matrix.Length; ++MatrixIndex)
                            {
                                if (MatrixIndex % Width == 0 && MatrixIndex != 0)
                                {
                                    ++YCurrent;
                                    XCurrent = 0;
                                }
                                if (XCurrent + x < image.Width && XCurrent + x >= 0 &&
                                    YCurrent + y < image.Height && YCurrent + y >= 0)
                                {
                                    if (*MatrixValue != 0)
                                    {
                                        Start         = ((YCurrent + y) * image.Width) + (x + XCurrent);
                                        var TempPixel = tempPixels[Start];
                                        Values       += new Vector4(*MatrixValue * TempPixel.Red,
                                                                    *MatrixValue * TempPixel.Green,
                                                                    *MatrixValue * TempPixel.Blue,
                                                                    TempPixel.Alpha);
                                        Weight += *MatrixValue;
                                    }
                                    ++MatrixValue;
                                }
                                ++XCurrent;
                            }
                        }
                        if (Weight == 0)
                        {
                            Weight = 1;
                        }
                        if (Weight > 0)
                        {
                            if (Absolute)
                            {
                                Values = Vector4.Abs(Values);
                            }
                            Values /= Weight;
                            Values  = new Vector4(Values.X + Offset, Values.Y + Offset, Values.Z + Offset, 1);
                            Values  = Vector4.Clamp(Values, Vector4.Zero, new Vector4(255, 255, 255, 255));
                            (*OutputPointer).Red   = (byte)Values.X;
                            (*OutputPointer).Green = (byte)Values.Y;
                            (*OutputPointer).Blue  = (byte)Values.Z;
                            ++OutputPointer;
                        }
                        else
                        {
                            ++OutputPointer;
                        }
                    }
                }
            });
            return(image);
        }
예제 #19
0
 public static extern void GlTexSubImage2D(uint target, int level, int xoffset, int yoffset, int width, int height, uint format, uint type, Color *pixels);
예제 #20
0
        private unsafe void InternalPrepareDraw(Rectangle drawArea)
        {
            Rectangle rectangle = new Rectangle(drawArea.X - 2, drawArea.Y - 2, drawArea.Width + 4, drawArea.Height + 4);

            _drawArea = drawArea;
            if (_cache.Length < rectangle.Width * rectangle.Height + 1)
            {
                _cache = new LiquidCache[rectangle.Width * rectangle.Height + 1];
            }
            if (_drawCache.Length < drawArea.Width * drawArea.Height + 1)
            {
                _drawCache = new LiquidDrawCache[drawArea.Width * drawArea.Height + 1];
            }
            if (_waveMask.Length < drawArea.Width * drawArea.Height)
            {
                _waveMask = new Color[drawArea.Width * drawArea.Height];
            }
            Tile tile = null;

            fixed(LiquidCache *ptr = &_cache[1])
            {
                LiquidCache *ptr2 = ptr;
                int          num  = rectangle.Height * 2 + 2;

                ptr2 = ptr;
                for (int i = rectangle.X; i < rectangle.X + rectangle.Width; i++)
                {
                    for (int j = rectangle.Y; j < rectangle.Y + rectangle.Height; j++)
                    {
                        tile = Tiles[i, j];
                        if (tile == null)
                        {
                            tile = new Tile();
                        }
                        ptr2->LiquidLevel        = (float)(int)tile.liquid / 255f;
                        ptr2->IsHalfBrick        = (tile.halfBrick() && ptr2[-1].HasLiquid && !TileID.Sets.Platforms[tile.type]);
                        ptr2->IsSolid            = WorldGen.SolidOrSlopedTile(tile);
                        ptr2->HasLiquid          = (tile.liquid != 0);
                        ptr2->VisibleLiquidLevel = 0f;
                        ptr2->HasWall            = (tile.wall != 0);
                        ptr2->Type = tile.liquidType();
                        if (ptr2->IsHalfBrick && !ptr2->HasLiquid)
                        {
                            ptr2->Type = ptr2[-1].Type;
                        }
                        ptr2++;
                    }
                }
                ptr2 = ptr;
                float num2 = 0f;

                ptr2 += num;
                for (int k = 2; k < rectangle.Width - 2; k++)
                {
                    for (int l = 2; l < rectangle.Height - 2; l++)
                    {
                        num2 = 0f;
                        if (ptr2->IsHalfBrick && ptr2[-1].HasLiquid)
                        {
                            num2 = 1f;
                        }
                        else if (!ptr2->HasLiquid)
                        {
                            LiquidCache liquidCache  = ptr2[-1];
                            LiquidCache liquidCache2 = ptr2[1];
                            LiquidCache liquidCache3 = ptr2[-rectangle.Height];
                            LiquidCache liquidCache4 = ptr2[rectangle.Height];
                            if (liquidCache.HasLiquid && liquidCache2.HasLiquid && liquidCache.Type == liquidCache2.Type && !liquidCache.IsSolid && !liquidCache2.IsSolid)
                            {
                                num2       = liquidCache.LiquidLevel + liquidCache2.LiquidLevel;
                                ptr2->Type = liquidCache.Type;
                            }
                            if (liquidCache3.HasLiquid && liquidCache4.HasLiquid && liquidCache3.Type == liquidCache4.Type && !liquidCache3.IsSolid && !liquidCache4.IsSolid)
                            {
                                num2       = Math.Max(num2, liquidCache3.LiquidLevel + liquidCache4.LiquidLevel);
                                ptr2->Type = liquidCache3.Type;
                            }
                            num2 *= 0.5f;
                        }
                        else
                        {
                            num2 = ptr2->LiquidLevel;
                        }
                        ptr2->VisibleLiquidLevel = num2;
                        ptr2->HasVisibleLiquid   = (num2 != 0f);
                        ptr2++;
                    }
                    ptr2 += 4;
                }
                ptr2 = ptr;
                for (int m = 0; m < rectangle.Width; m++)
                {
                    for (int n = 0; n < rectangle.Height - 10; n++)
                    {
                        if (ptr2->HasVisibleLiquid && (!ptr2->IsSolid || ptr2->IsHalfBrick))
                        {
                            ptr2->Opacity     = 1f;
                            ptr2->VisibleType = ptr2->Type;
                            float num3 = 1f / (float)(WATERFALL_LENGTH[ptr2->Type] + 1);
                            float num4 = 1f;
                            for (int num5 = 1; num5 <= WATERFALL_LENGTH[ptr2->Type]; num5++)
                            {
                                num4 -= num3;
                                if (ptr2[num5].IsSolid)
                                {
                                    break;
                                }
                                ptr2[num5].VisibleLiquidLevel = Math.Max(ptr2[num5].VisibleLiquidLevel, ptr2->VisibleLiquidLevel * num4);
                                ptr2[num5].Opacity            = num4;
                                ptr2[num5].VisibleType        = ptr2->Type;
                            }
                        }
                        if (ptr2->IsSolid && !ptr2->IsHalfBrick)
                        {
                            ptr2->VisibleLiquidLevel = 1f;
                            ptr2->HasVisibleLiquid   = false;
                        }
                        else
                        {
                            ptr2->HasVisibleLiquid = (ptr2->VisibleLiquidLevel != 0f);
                        }
                        ptr2++;
                    }
                    ptr2 += 10;
                }
                ptr2  = ptr;
                ptr2 += num;
                for (int num6 = 2; num6 < rectangle.Width - 2; num6++)
                {
                    for (int num7 = 2; num7 < rectangle.Height - 2; num7++)
                    {
                        if (!ptr2->HasVisibleLiquid)
                        {
                            ptr2->HasLeftEdge   = false;
                            ptr2->HasTopEdge    = false;
                            ptr2->HasRightEdge  = false;
                            ptr2->HasBottomEdge = false;
                        }
                        else
                        {
                            LiquidCache liquidCache        = ptr2[-1];
                            LiquidCache liquidCache2       = ptr2[1];
                            LiquidCache liquidCache3       = ptr2[-rectangle.Height];
                            LiquidCache liquidCache4       = ptr2[rectangle.Height];
                            float       num8               = 0f;
                            float       num9               = 1f;
                            float       num10              = 0f;
                            float       num11              = 1f;
                            float       visibleLiquidLevel = ptr2->VisibleLiquidLevel;
                            if (!liquidCache.HasVisibleLiquid)
                            {
                                num10 += liquidCache2.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache2.HasVisibleLiquid && !liquidCache2.IsSolid && !liquidCache2.IsHalfBrick)
                            {
                                num11 -= liquidCache.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache3.HasVisibleLiquid && !liquidCache3.IsSolid && !liquidCache3.IsHalfBrick)
                            {
                                num8 += liquidCache4.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache4.HasVisibleLiquid && !liquidCache4.IsSolid && !liquidCache4.IsHalfBrick)
                            {
                                num9 -= liquidCache3.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            ptr2->LeftWall   = num8;
                            ptr2->RightWall  = num9;
                            ptr2->BottomWall = num11;
                            ptr2->TopWall    = num10;
                            Point zero = Point.Zero;
                            ptr2->HasTopEdge    = ((!liquidCache.HasVisibleLiquid && !liquidCache.IsSolid) || num10 != 0f);
                            ptr2->HasBottomEdge = ((!liquidCache2.HasVisibleLiquid && !liquidCache2.IsSolid) || num11 != 1f);
                            ptr2->HasLeftEdge   = ((!liquidCache3.HasVisibleLiquid && !liquidCache3.IsSolid) || num8 != 0f);
                            ptr2->HasRightEdge  = ((!liquidCache4.HasVisibleLiquid && !liquidCache4.IsSolid) || num9 != 1f);
                            if (!ptr2->HasLeftEdge)
                            {
                                if (ptr2->HasRightEdge)
                                {
                                    zero.X += 32;
                                }
                                else
                                {
                                    zero.X += 16;
                                }
                            }
                            if (ptr2->HasLeftEdge && ptr2->HasRightEdge)
                            {
                                zero.X  = 16;
                                zero.Y += 32;
                                if (ptr2->HasTopEdge)
                                {
                                    zero.Y = 16;
                                }
                            }
                            else if (!ptr2->HasTopEdge)
                            {
                                if (!ptr2->HasLeftEdge && !ptr2->HasRightEdge)
                                {
                                    zero.Y += 48;
                                }
                                else
                                {
                                    zero.Y += 16;
                                }
                            }
                            if (zero.Y == 16 && (ptr2->HasLeftEdge ^ ptr2->HasRightEdge) && (num7 + rectangle.Y) % 2 == 0)
                            {
                                zero.Y += 16;
                            }
                            ptr2->FrameOffset = zero;
                        }
                        ptr2++;
                    }
                    ptr2 += 4;
                }
                ptr2  = ptr;
                ptr2 += num;
                for (int num12 = 2; num12 < rectangle.Width - 2; num12++)
                {
                    for (int num13 = 2; num13 < rectangle.Height - 2; num13++)
                    {
                        if (ptr2->HasVisibleLiquid)
                        {
                            LiquidCache liquidCache  = ptr2[-1];
                            LiquidCache liquidCache2 = ptr2[1];
                            LiquidCache liquidCache3 = ptr2[-rectangle.Height];
                            LiquidCache liquidCache4 = ptr2[rectangle.Height];
                            ptr2->VisibleLeftWall   = ptr2->LeftWall;
                            ptr2->VisibleRightWall  = ptr2->RightWall;
                            ptr2->VisibleTopWall    = ptr2->TopWall;
                            ptr2->VisibleBottomWall = ptr2->BottomWall;
                            if (liquidCache.HasVisibleLiquid && liquidCache2.HasVisibleLiquid)
                            {
                                if (ptr2->HasLeftEdge)
                                {
                                    ptr2->VisibleLeftWall = (ptr2->LeftWall * 2f + liquidCache.LeftWall + liquidCache2.LeftWall) * 0.25f;
                                }
                                if (ptr2->HasRightEdge)
                                {
                                    ptr2->VisibleRightWall = (ptr2->RightWall * 2f + liquidCache.RightWall + liquidCache2.RightWall) * 0.25f;
                                }
                            }
                            if (liquidCache3.HasVisibleLiquid && liquidCache4.HasVisibleLiquid)
                            {
                                if (ptr2->HasTopEdge)
                                {
                                    ptr2->VisibleTopWall = (ptr2->TopWall * 2f + liquidCache3.TopWall + liquidCache4.TopWall) * 0.25f;
                                }
                                if (ptr2->HasBottomEdge)
                                {
                                    ptr2->VisibleBottomWall = (ptr2->BottomWall * 2f + liquidCache3.BottomWall + liquidCache4.BottomWall) * 0.25f;
                                }
                            }
                        }
                        ptr2++;
                    }
                    ptr2 += 4;
                }
                ptr2  = ptr;
                ptr2 += num;
                for (int num14 = 2; num14 < rectangle.Width - 2; num14++)
                {
                    for (int num15 = 2; num15 < rectangle.Height - 2; num15++)
                    {
                        if (ptr2->HasLiquid)
                        {
                            LiquidCache liquidCache  = ptr2[-1];
                            LiquidCache liquidCache2 = ptr2[1];
                            LiquidCache liquidCache3 = ptr2[-rectangle.Height];
                            LiquidCache liquidCache4 = ptr2[rectangle.Height];
                            if (ptr2->HasTopEdge && !ptr2->HasBottomEdge && (ptr2->HasLeftEdge ^ ptr2->HasRightEdge))
                            {
                                if (ptr2->HasRightEdge)
                                {
                                    ptr2->VisibleRightWall = liquidCache2.VisibleRightWall;
                                    ptr2->VisibleTopWall   = liquidCache3.VisibleTopWall;
                                }
                                else
                                {
                                    ptr2->VisibleLeftWall = liquidCache2.VisibleLeftWall;
                                    ptr2->VisibleTopWall  = liquidCache4.VisibleTopWall;
                                }
                            }
                            else if (liquidCache2.FrameOffset.X == 16 && liquidCache2.FrameOffset.Y == 32)
                            {
                                if (ptr2->VisibleLeftWall > 0.5f)
                                {
                                    ptr2->VisibleLeftWall = 0f;
                                    ptr2->FrameOffset     = new Point(0, 0);
                                }
                                else if (ptr2->VisibleRightWall < 0.5f)
                                {
                                    ptr2->VisibleRightWall = 1f;
                                    ptr2->FrameOffset      = new Point(32, 0);
                                }
                            }
                        }
                        ptr2++;
                    }
                    ptr2 += 4;
                }
                ptr2  = ptr;
                ptr2 += num;
                for (int num16 = 2; num16 < rectangle.Width - 2; num16++)
                {
                    for (int num17 = 2; num17 < rectangle.Height - 2; num17++)
                    {
                        if (ptr2->HasLiquid)
                        {
                            LiquidCache liquidCache  = ptr2[-1];
                            LiquidCache liquidCache2 = ptr2[1];
                            LiquidCache liquidCache3 = ptr2[-rectangle.Height];
                            LiquidCache liquidCache4 = ptr2[rectangle.Height];
                            if (!ptr2->HasBottomEdge && !ptr2->HasLeftEdge && !ptr2->HasTopEdge && !ptr2->HasRightEdge)
                            {
                                if (liquidCache3.HasTopEdge && liquidCache.HasLeftEdge)
                                {
                                    ptr2->FrameOffset.X     = Math.Max(4, (int)(16f - liquidCache.VisibleLeftWall * 16f)) - 4;
                                    ptr2->FrameOffset.Y     = 48 + Math.Max(4, (int)(16f - liquidCache3.VisibleTopWall * 16f)) - 4;
                                    ptr2->VisibleLeftWall   = 0f;
                                    ptr2->VisibleTopWall    = 0f;
                                    ptr2->VisibleRightWall  = 1f;
                                    ptr2->VisibleBottomWall = 1f;
                                }
                                else if (liquidCache4.HasTopEdge && liquidCache.HasRightEdge)
                                {
                                    ptr2->FrameOffset.X     = 32 - Math.Min(16, (int)(liquidCache.VisibleRightWall * 16f) - 4);
                                    ptr2->FrameOffset.Y     = 48 + Math.Max(4, (int)(16f - liquidCache4.VisibleTopWall * 16f)) - 4;
                                    ptr2->VisibleLeftWall   = 0f;
                                    ptr2->VisibleTopWall    = 0f;
                                    ptr2->VisibleRightWall  = 1f;
                                    ptr2->VisibleBottomWall = 1f;
                                }
                            }
                        }
                        ptr2++;
                    }
                    ptr2 += 4;
                }
                ptr2  = ptr;
                ptr2 += num;
                fixed(LiquidDrawCache *ptr3 = &_drawCache[0])
                {
                    fixed(Color *ptr5 = &_waveMask[0])
                    {
                        LiquidDrawCache *ptr4 = ptr3;
                        Color *          ptr6 = ptr5;

                        for (int num18 = 2; num18 < rectangle.Width - 2; num18++)
                        {
                            for (int num19 = 2; num19 < rectangle.Height - 2; num19++)
                            {
                                if (ptr2->HasVisibleLiquid)
                                {
                                    float num20 = Math.Min(0.75f, ptr2->VisibleLeftWall);
                                    float num21 = Math.Max(0.25f, ptr2->VisibleRightWall);
                                    float num22 = Math.Min(0.75f, ptr2->VisibleTopWall);
                                    float num23 = Math.Max(0.25f, ptr2->VisibleBottomWall);
                                    if (ptr2->IsHalfBrick && ptr2->IsSolid && num23 > 0.5f)
                                    {
                                        num23 = 0.5f;
                                    }
                                    ptr4->IsVisible       = (ptr2->HasWall || !ptr2->IsHalfBrick || !ptr2->HasLiquid || !(ptr2->LiquidLevel < 1f));
                                    ptr4->SourceRectangle = new Rectangle((int)(16f - num21 * 16f) + ptr2->FrameOffset.X, (int)(16f - num23 * 16f) + ptr2->FrameOffset.Y, (int)Math.Ceiling((num21 - num20) * 16f), (int)Math.Ceiling((num23 - num22) * 16f));
                                    ptr4->IsSurfaceLiquid = (ptr2->FrameOffset.X == 16 && ptr2->FrameOffset.Y == 0 && (double)(num19 + rectangle.Y) > Main.worldSurface - 40.0);
                                    ptr4->Opacity         = ptr2->Opacity;
                                    ptr4->LiquidOffset    = new Vector2((float)Math.Floor(num20 * 16f), (float)Math.Floor(num22 * 16f));
                                    ptr4->Type            = ptr2->VisibleType;
                                    ptr4->HasWall         = ptr2->HasWall;
                                    byte b = WAVE_MASK_STRENGTH[ptr2->VisibleType];
                                    byte g = ptr6->R = (byte)(b >> 1);
                                    ptr6->G = g;
                                    ptr6->B = VISCOSITY_MASK[ptr2->VisibleType];
                                    ptr6->A = b;
                                    LiquidCache *ptr7 = ptr2 - 1;
                                    if (num19 != 2 && !ptr7->HasVisibleLiquid && !ptr7->IsSolid && !ptr7->IsHalfBrick)
                                    {
                                        *(ptr6 - 1) = *ptr6;
                                    }
                                }
                                else
                                {
                                    ptr4->IsVisible = false;
                                    int  num24 = (!ptr2->IsSolid && !ptr2->IsHalfBrick) ? 4 : 3;
                                    byte b3    = WAVE_MASK_STRENGTH[num24];
                                    byte g2    = ptr6->R = (byte)(b3 >> 1);
                                    ptr6->G = g2;
                                    ptr6->B = VISCOSITY_MASK[num24];
                                    ptr6->A = b3;
                                }
                                ptr2++;
                                ptr4++;
                                ptr6++;
                            }
                            ptr2 += 4;
                        }
                    }
                }

                ptr2 = ptr;
                for (int num25 = rectangle.X; num25 < rectangle.X + rectangle.Width; num25++)
                {
                    for (int num26 = rectangle.Y; num26 < rectangle.Y + rectangle.Height; num26++)
                    {
                        if (ptr2->VisibleType == 1 && ptr2->HasVisibleLiquid && Dust.lavaBubbles < 200)
                        {
                            if (_random.Next(700) == 0)
                            {
                                Dust.NewDust(new Vector2(num25 * 16, num26 * 16), 16, 16, 35, 0f, 0f, 0, Color.White);
                            }
                            if (_random.Next(350) == 0)
                            {
                                int num27 = Dust.NewDust(new Vector2(num25 * 16, num26 * 16), 16, 8, 35, 0f, 0f, 50, Color.White, 1.5f);
                                Main.dust[num27].velocity   *= 0.8f;
                                Main.dust[num27].velocity.X *= 2f;
                                Main.dust[num27].velocity.Y -= (float)_random.Next(1, 7) * 0.1f;
                                if (_random.Next(10) == 0)
                                {
                                    Main.dust[num27].velocity.Y *= _random.Next(2, 5);
                                }
                                Main.dust[num27].noGravity = true;
                            }
                        }
                        ptr2++;
                    }
                }
            }

            if (this.WaveFilters != null)
            {
                this.WaveFilters(_waveMask, GetCachedDrawArea());
            }
        }
예제 #21
0
파일: Image.cs 프로젝트: tsurupettan/SFML
 unsafe static extern void sfImage_UpdatePixels(IntPtr This, Color *Pixels, IntRect Rectangle);
    public void ResampleAndCrop(ResamplingFilters filter, CropMode mode, int newWidth, int newHeight)
    {
        if (Disposed)
        {
            return;
        }
        // fit
        int w = newWidth;
        int h = newHeight;

        if (mode == CropMode.Fit)
        {
            float factor1 = ((float)w / (float)h);
            float factor2 = ((float)Width / (float)Height);
            if (factor1 > factor2)
            {
                h = newHeight;
                w = (int)((((float)h) / ((float)Height)) * Width);
            }
            else
            {
                w = newWidth;
                h = (int)((((float)w) / ((float)Width)) * Height);
            }
        }
        else if (mode == CropMode.Cover)
        {
            float factor1 = ((float)w / (float)h);
            float factor2 = ((float)Width / (float)Height);
            if (factor1 > factor2)
            {
                w = newWidth;
                h = (int)((((float)w) / ((float)Width)) * Height);
            }
            else
            {
                h = newHeight;
                w = (int)((((float)h) / ((float)Height)) * Width);
            }
        }

        this.Resample(filter, w, h);

        Color *myPointer   = (Color *)Bytes.ToPointer();
        var    copy        = Marshal.AllocHGlobal(w * h * PixelSize);
        Color *copyPointer = (Color *)copy.ToPointer();

        Buffer.MemoryCopy(myPointer, copyPointer, w * h * PixelSize, w * h * PixelSize);

        this.InternalResize(newWidth, newHeight);
        myPointer = (Color *)Bytes.ToPointer();

        int ox = (newWidth - w) / 2;
        int oy = (newHeight - h) / 2;

        for (int y = 0; y < newHeight; y++)
        {
            for (int x = 0; x < newWidth; x++)
            {
                if (x >= ox && x < ox + w && y >= oy && y < oy + h)
                {
                    *(myPointer + x + y * newWidth) = *(copyPointer + (x - ox) + (y - oy) * w);
                }
                else
                {
                    *(myPointer + x + y * newWidth) = new Color(0, 0, 0, 0);
                }
            }
        }
    }
        private unsafe void InternalPrepareDraw(Rectangle drawArea)
        {
            ReplacementLiquidRenderer.LiquidCache height;
            ReplacementLiquidRenderer.LiquidCache liquidCache;
            ReplacementLiquidRenderer.LiquidCache height1;
            ReplacementLiquidRenderer.LiquidCache liquidCache1;
            bool      flag;
            Rectangle rectangle = new Rectangle(drawArea.X - 2, drawArea.Y - 2, drawArea.Width + 4, drawArea.Height + 4);

            this._drawArea = drawArea;
            Tile tile = null;

            fixed(ReplacementLiquidRenderer.LiquidCache *liquidCachePointer = &this._cache[1])
            {
                ReplacementLiquidRenderer.LiquidCache *type = liquidCachePointer;
                int num = rectangle.Height * 2 + 2;

                type = liquidCachePointer;
                for (int i = rectangle.X; i < rectangle.X + rectangle.Width; i++)
                {
                    for (int j = rectangle.Y; j < rectangle.Y + rectangle.Height; j++)
                    {
                        tile = this._tiles[i, j] ?? new Tile();
                        (*type).LiquidLevel        = (float)tile.liquid / 255f;
                        (*type).IsHalfBrick        = (!tile.halfBrick() ? false : (*(type - 1)).HasLiquid);
                        (*type).IsSolid            = (!WorldGen.SolidOrSlopedTile(tile) ? false : !(*type).IsHalfBrick);
                        (*type).HasLiquid          = tile.liquid != 0;
                        (*type).VisibleLiquidLevel = 0f;
                        (*type).HasWall            = tile.wall != 0;
                        (*type).Type = tile.liquidType();
                        if ((*type).IsHalfBrick && !(*type).HasLiquid)
                        {
                            (*type).Type = (*(type - 1)).Type;
                        }
                        type = type + 1;
                    }
                }
                type = liquidCachePointer;
                float liquidLevel = 0f;

                type = type + num;
                for (int k = 2; k < rectangle.Width - 2; k++)
                {
                    for (int l = 2; l < rectangle.Height - 2; l++)
                    {
                        liquidLevel = 0f;
                        if ((*type).IsHalfBrick && (*(type - 1)).HasLiquid)
                        {
                            liquidLevel = 1f;
                        }
                        else if ((*type).HasLiquid)
                        {
                            liquidLevel = (*type).LiquidLevel;
                        }
                        else
                        {
                            height       = *(type + -rectangle.Height);
                            liquidCache  = *(type + rectangle.Height);
                            height1      = *(type - 1);
                            liquidCache1 = *(type + 1);
                            if (height.HasLiquid && liquidCache.HasLiquid && height.Type == liquidCache.Type)
                            {
                                liquidLevel  = height.LiquidLevel + liquidCache.LiquidLevel;
                                (*type).Type = height.Type;
                            }
                            if (height1.HasLiquid && liquidCache1.HasLiquid && height1.Type == liquidCache1.Type)
                            {
                                liquidLevel  = Math.Max(liquidLevel, height1.LiquidLevel + liquidCache1.LiquidLevel);
                                (*type).Type = height1.Type;
                            }
                            liquidLevel = liquidLevel * 0.5f;
                        }
                        (*type).VisibleLiquidLevel = liquidLevel;
                        (*type).HasVisibleLiquid   = liquidLevel != 0f;
                        type = type + 1;
                    }
                    type = type + 4;
                }
                type = liquidCachePointer;
                for (int m = 0; m < rectangle.Width; m++)
                {
                    for (int n = 0; n < rectangle.Height - 10; n++)
                    {
                        if ((*type).HasVisibleLiquid && !(*type).IsSolid)
                        {
                            (*type).Opacity     = 1f;
                            (*type).VisibleType = (*type).Type;
                            float wATERFALLLENGTH = 1f / (float)(ReplacementLiquidRenderer.WATERFALL_LENGTH[(*type).Type] + 1);
                            float single          = 1f;
                            for (int o = 1; o <= ReplacementLiquidRenderer.WATERFALL_LENGTH[(*type).Type]; o++)
                            {
                                single = single - wATERFALLLENGTH;
                                if ((*(type + o)).IsSolid)
                                {
                                    break;
                                }
                                (*(type + o)).VisibleLiquidLevel = Math.Max((*(type + o)).VisibleLiquidLevel, (*type).VisibleLiquidLevel * single);
                                (*(type + o)).Opacity            = single;
                                (*(type + o)).VisibleType        = (*type).Type;
                            }
                        }
                        if (!(*type).IsSolid)
                        {
                            (*type).HasVisibleLiquid = (*type).VisibleLiquidLevel != 0f;
                        }
                        else
                        {
                            (*type).VisibleLiquidLevel = 1f;
                            (*type).HasVisibleLiquid   = false;
                        }
                        type = type + 1;
                    }
                    type = type + 10;
                }
                type = liquidCachePointer;
                type = type + num;
                for (int p = 2; p < rectangle.Width - 2; p++)
                {
                    for (int q = 2; q < rectangle.Height - 2; q++)
                    {
                        if (!(*type).HasVisibleLiquid || (*type).IsSolid)
                        {
                            (*type).HasLeftEdge   = false;
                            (*type).HasTopEdge    = false;
                            (*type).HasRightEdge  = false;
                            (*type).HasBottomEdge = false;
                        }
                        else
                        {
                            height       = *(type - 1);
                            liquidCache  = *(type + 1);
                            height1      = *(type + -rectangle.Height);
                            liquidCache1 = *(type + rectangle.Height);
                            float visibleLiquidLevel  = 0f;
                            float visibleLiquidLevel1 = 1f;
                            float single1             = 0f;
                            float visibleLiquidLevel2 = 1f;
                            float single2             = (*type).VisibleLiquidLevel;
                            if (!height.HasVisibleLiquid)
                            {
                                single1 = single1 + liquidCache.VisibleLiquidLevel * (1f - single2);
                            }
                            if (!liquidCache.HasVisibleLiquid && !liquidCache.IsSolid && !liquidCache.IsHalfBrick)
                            {
                                visibleLiquidLevel2 = visibleLiquidLevel2 - height.VisibleLiquidLevel * (1f - single2);
                            }
                            if (!height1.HasVisibleLiquid && !height1.IsSolid && !height1.IsHalfBrick)
                            {
                                visibleLiquidLevel = visibleLiquidLevel + liquidCache1.VisibleLiquidLevel * (1f - single2);
                            }
                            if (!liquidCache1.HasVisibleLiquid && !liquidCache1.IsSolid && !liquidCache1.IsHalfBrick)
                            {
                                visibleLiquidLevel1 = visibleLiquidLevel1 - height1.VisibleLiquidLevel * (1f - single2);
                            }
                            (*type).LeftWall   = visibleLiquidLevel;
                            (*type).RightWall  = visibleLiquidLevel1;
                            (*type).BottomWall = visibleLiquidLevel2;
                            (*type).TopWall    = single1;
                            Point zero = Point.Zero;
                            (*type).HasTopEdge    = (height.HasVisibleLiquid || height.IsSolid ? single1 != 0f : true);
                            (*type).HasBottomEdge = (liquidCache.HasVisibleLiquid || liquidCache.IsSolid ? visibleLiquidLevel2 != 1f : true);
                            (*type).HasLeftEdge   = (height1.HasVisibleLiquid || height1.IsSolid ? visibleLiquidLevel != 0f : true);
                            (*type).HasRightEdge  = (liquidCache1.HasVisibleLiquid || liquidCache1.IsSolid ? visibleLiquidLevel1 != 1f : true);
                            if (!(*type).HasLeftEdge)
                            {
                                if (!(*type).HasRightEdge)
                                {
                                    zero.X = zero.X + 16;
                                }
                                else
                                {
                                    zero.X = zero.X + 32;
                                }
                            }
                            if ((*type).HasLeftEdge && (*type).HasRightEdge)
                            {
                                zero.X = 16;
                                zero.Y = zero.Y + 32;
                                if ((*type).HasTopEdge)
                                {
                                    zero.Y = 16;
                                }
                            }
                            else if (!(*type).HasTopEdge)
                            {
                                if ((*type).HasLeftEdge || (*type).HasRightEdge)
                                {
                                    zero.Y = zero.Y + 16;
                                }
                                else
                                {
                                    zero.Y = zero.Y + 48;
                                }
                            }
                            if (zero.Y == 16 && (*type).HasLeftEdge ^ (*type).HasRightEdge && q + rectangle.Y % 2 == 0)
                            {
                                zero.Y = zero.Y + 16;
                            }
                            (*type).FrameOffset = zero;
                        }
                        type = type + 1;
                    }
                    type = type + 4;
                }
                type = liquidCachePointer;
                type = type + num;
                for (int r = 2; r < rectangle.Width - 2; r++)
                {
                    for (int s = 2; s < rectangle.Height - 2; s++)
                    {
                        if ((*type).HasVisibleLiquid)
                        {
                            height                    = *(type - 1);
                            liquidCache               = *(type + 1);
                            height1                   = *(type + -rectangle.Height);
                            liquidCache1              = *(type + rectangle.Height);
                            (*type).VisibleLeftWall   = (*type).LeftWall;
                            (*type).VisibleRightWall  = (*type).RightWall;
                            (*type).VisibleTopWall    = (*type).TopWall;
                            (*type).VisibleBottomWall = (*type).BottomWall;
                            if (height.HasVisibleLiquid && liquidCache.HasVisibleLiquid)
                            {
                                if ((*type).HasLeftEdge)
                                {
                                    (*type).VisibleLeftWall = ((*type).LeftWall * 2f + height.LeftWall + liquidCache.LeftWall) * 0.25f;
                                }
                                if ((*type).HasRightEdge)
                                {
                                    (*type).VisibleRightWall = ((*type).RightWall * 2f + height.RightWall + liquidCache.RightWall) * 0.25f;
                                }
                            }
                            if (height1.HasVisibleLiquid && liquidCache1.HasVisibleLiquid)
                            {
                                if ((*type).HasTopEdge)
                                {
                                    (*type).VisibleTopWall = ((*type).TopWall * 2f + height1.TopWall + liquidCache1.TopWall) * 0.25f;
                                }
                                if ((*type).HasBottomEdge)
                                {
                                    (*type).VisibleBottomWall = ((*type).BottomWall * 2f + height1.BottomWall + liquidCache1.BottomWall) * 0.25f;
                                }
                            }
                        }
                        type = type + 1;
                    }
                    type = type + 4;
                }
                type = liquidCachePointer;
                type = type + num;
                for (int t = 2; t < rectangle.Width - 2; t++)
                {
                    for (int u = 2; u < rectangle.Height - 2; u++)
                    {
                        if ((*type).HasLiquid)
                        {
                            height       = *(type - 1);
                            liquidCache  = *(type);
                            height1      = *(type + -rectangle.Height);
                            liquidCache1 = *(type + rectangle.Height);
                            if ((*type).HasTopEdge && !(*type).HasBottomEdge && (*type).HasLeftEdge ^ (*type).HasRightEdge)
                            {
                                if (!(*type).HasRightEdge)
                                {
                                    (*type).VisibleLeftWall = liquidCache.VisibleLeftWall;
                                    (*type).VisibleTopWall  = liquidCache1.VisibleTopWall;
                                }
                                else
                                {
                                    (*type).VisibleRightWall = liquidCache.VisibleRightWall;
                                    (*type).VisibleTopWall   = height1.VisibleTopWall;
                                }
                            }
                            else if (liquidCache.FrameOffset.X == 16 && liquidCache.FrameOffset.Y == 32)
                            {
                                if ((*type).VisibleLeftWall > 0.5f)
                                {
                                    (*type).VisibleLeftWall = 0f;
                                    (*type).FrameOffset     = new Point(0, 0);
                                }
                                else if ((*type).VisibleRightWall < 0.5f)
                                {
                                    (*type).VisibleRightWall = 1f;
                                    (*type).FrameOffset      = new Point(32, 0);
                                }
                            }
                        }
                        type = type + 1;
                    }
                    type = type + 4;
                }
                type = liquidCachePointer;
                type = type + num;
                for (int v = 2; v < rectangle.Width - 2; v++)
                {
                    for (int w = 2; w < rectangle.Height - 2; w++)
                    {
                        if ((*type).HasLiquid)
                        {
                            height       = *(type - 1);
                            liquidCache  = *(type);
                            height1      = *(type + -rectangle.Height);
                            liquidCache1 = *(type + rectangle.Height);
                            if (!(*type).HasBottomEdge && !(*type).HasLeftEdge && !(*type).HasTopEdge && !(*type).HasRightEdge)
                            {
                                if (height1.HasTopEdge && height.HasLeftEdge)
                                {
                                    (*type).FrameOffset.X     = Math.Max(4, (int)(16f - height.VisibleLeftWall * 16f)) - 4;
                                    (*type).FrameOffset.Y     = 48 + Math.Max(4, (int)(16f - height1.VisibleTopWall * 16f)) - 4;
                                    (*type).VisibleLeftWall   = 0f;
                                    (*type).VisibleTopWall    = 0f;
                                    (*type).VisibleRightWall  = 1f;
                                    (*type).VisibleBottomWall = 1f;
                                }
                                else if (liquidCache1.HasTopEdge && height.HasRightEdge)
                                {
                                    (*type).FrameOffset.X     = 32 - Math.Min(16, (int)(height.VisibleRightWall * 16f) - 4);
                                    (*type).FrameOffset.Y     = 48 + Math.Max(4, (int)(16f - liquidCache1.VisibleTopWall * 16f)) - 4;
                                    (*type).VisibleLeftWall   = 0f;
                                    (*type).VisibleTopWall    = 0f;
                                    (*type).VisibleRightWall  = 1f;
                                    (*type).VisibleBottomWall = 1f;
                                }
                            }
                        }
                        type = type + 1;
                    }
                    type = type + 4;
                }
                type = liquidCachePointer;
                type = type + num;
                fixed(ReplacementLiquidRenderer.LiquidDrawCache *liquidDrawCachePointer = &this._drawCache[0])
                {
                    fixed(Color *colorPointer = &this._waveMask[0])
                    {
                        ReplacementLiquidRenderer.LiquidDrawCache *opacity = liquidDrawCachePointer;
                        Color *vISCOSITYMASK = colorPointer;

                        for (int x = 2; x < rectangle.Width - 2; x++)
                        {
                            Color *colorPointer1 = vISCOSITYMASK;
                            for (int y = 2; y < rectangle.Height - 2; y++)
                            {
                                if (!(*type).HasVisibleLiquid)
                                {
                                    (*opacity).IsVisible = false;
                                    int  num1             = ((*type).IsSolid || (*type).IsHalfBrick ? 3 : 4);
                                    byte wAVEMASKSTRENGTH = ReplacementLiquidRenderer.WAVE_MASK_STRENGTH[num1];
                                    byte num2             = (byte)(wAVEMASKSTRENGTH >> 1);
                                    (*vISCOSITYMASK).R = num2;
                                    (*vISCOSITYMASK).G = num2;
                                    (*vISCOSITYMASK).B = ReplacementLiquidRenderer.VISCOSITY_MASK[num1];
                                    (*vISCOSITYMASK).A = wAVEMASKSTRENGTH;
                                }
                                else
                                {
                                    float single3 = Math.Min(0.75f, (*type).VisibleLeftWall);
                                    float single4 = Math.Max(0.25f, (*type).VisibleRightWall);
                                    float single5 = Math.Min(0.75f, (*type).VisibleTopWall);
                                    float single6 = Math.Max(0.25f, (*type).VisibleBottomWall);
                                    if ((*type).IsHalfBrick && single6 > 0.5f)
                                    {
                                        single6 = 0.5f;
                                    }
                                    ReplacementLiquidRenderer.LiquidDrawCache *liquidDrawCachePointer1 = opacity;
                                    if ((*type).HasWall)
                                    {
                                        flag = true;
                                    }
                                    else
                                    {
                                        flag = (!(*type).IsHalfBrick ? true : !(*type).HasLiquid);
                                    }
                                    (*liquidDrawCachePointer1).IsVisible = flag;
                                    (*opacity).SourceRectangle           = new Rectangle((int)(16f - single4 * 16f) + (*type).FrameOffset.X, (int)(16f - single6 * 16f) + (*type).FrameOffset.Y, (int)Math.Ceiling((double)((single4 - single3) * 16f)), (int)Math.Ceiling((double)((single6 - single5) * 16f)));
                                    (*opacity).IsSurfaceLiquid           = ((*type).FrameOffset.X != 16 || (*type).FrameOffset.Y != 0 ? false : (double)(y + rectangle.Y) > Main.worldSurface - 40);
                                    (*opacity).Opacity      = (*type).Opacity;
                                    (*opacity).LiquidOffset = new Vector2((float)Math.Floor((double)(single3 * 16f)), (float)Math.Floor((double)(single5 * 16f)));
                                    (*opacity).Type         = (*type).VisibleType;
                                    (*opacity).HasWall      = (*type).HasWall;
                                    byte wAVEMASKSTRENGTH1 = ReplacementLiquidRenderer.WAVE_MASK_STRENGTH[(*type).VisibleType];
                                    byte num3 = (byte)(wAVEMASKSTRENGTH1 >> 1);
                                    (*vISCOSITYMASK).R = num3;
                                    (*vISCOSITYMASK).G = num3;
                                    (*vISCOSITYMASK).B = ReplacementLiquidRenderer.VISCOSITY_MASK[(*type).VisibleType];
                                    (*vISCOSITYMASK).A = wAVEMASKSTRENGTH1;
                                    ReplacementLiquidRenderer.LiquidCache *liquidCachePointer1 = type - 1;
                                    if (y != 2 && !(*liquidCachePointer1).HasVisibleLiquid && !(*liquidCachePointer1).IsSolid && !(*liquidCachePointer1).IsHalfBrick)
                                    {
                                        if (vISCOSITYMASK - 200 < colorPointer)
                                        {
                                            System.Diagnostics.Debugger.Launch();
                                        }
                                        *(vISCOSITYMASK - 200) = *vISCOSITYMASK;
                                    }
                                }
                                type          = type + 1;
                                opacity       = opacity + 1;
                                vISCOSITYMASK = vISCOSITYMASK + 200;
                            }
                            type          = type + 4;
                            vISCOSITYMASK = colorPointer1 + 1;
                        }
                    }
                }

                type = liquidCachePointer;
                for (int a = rectangle.X; a < rectangle.X + rectangle.Width; a++)
                {
                    for (int b = rectangle.Y; b < rectangle.Y + rectangle.Height; b++)
                    {
                        if ((*type).VisibleType == 1 && (*type).HasVisibleLiquid && Dust.lavaBubbles < 200)
                        {
                            if (this._random.Next(700) == 0)
                            {
                                Dust.NewDust(new Vector2((float)(a * 16), (float)(b * 16)), 16, 16, 35, 0f, 0f, 0, Color.White, 1f);
                            }
                            if (this._random.Next(350) == 0)
                            {
                                int  num4 = Dust.NewDust(new Vector2((float)(a * 16), (float)(b * 16)), 16, 8, 35, 0f, 0f, 50, Color.White, 1.5f);
                                Dust dust = Main.dust[num4];
                                dust.velocity = dust.velocity * 0.8f;
                                Main.dust[num4].velocity.X = Main.dust[num4].velocity.X * 2f;
                                Main.dust[num4].velocity.Y = Main.dust[num4].velocity.Y - (float)this._random.Next(1, 7) * 0.1f;
                                if (this._random.Next(10) == 0)
                                {
                                    Main.dust[num4].velocity.Y = Main.dust[num4].velocity.Y * (float)this._random.Next(2, 5);
                                }
                                Main.dust[num4].noGravity = true;
                            }
                        }
                        type = type + 1;
                    }
                }
            }

            if (this.ViscosityFilters != null)
            {
                this.ViscosityFilters(this._waveMask, this.GetCachedDrawArea());
            }
        }
예제 #24
0
 public static extern int SDL_SetPaletteColors(
     Palette palette,
     /*const*/ Color *colors,
     int firstcolor,
     int ncolors
     );
예제 #25
0
        /// <summary>
        /// Applies the filter to the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Numerics.Rectangle targetLocation = default(Numerics.Rectangle))
        {
            targetLocation = targetLocation == default(Numerics.Rectangle) ? new Numerics.Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var PointSize2 = PointSize * 2;
            var Copy       = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, Copy, Copy.Length);
            var EllipseDrawer = new Ellipse(Color.AliceBlue, true, PointSize, PointSize, new Vector2(0, 0));

            for (int y = targetLocation.Bottom; y < targetLocation.Top; y += PointSize2)
            {
                var MinY = (y - PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                var MaxY = (y + PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                fixed(Color *TargetPointer = &Copy[(y * image.Width) + targetLocation.Left])
                {
                    Color *TargetPointer2 = TargetPointer;

                    for (int x = targetLocation.Left; x < targetLocation.Right; x += PointSize2)
                    {
                        uint RValue       = 0;
                        uint GValue       = 0;
                        uint BValue       = 0;
                        var  MinX         = (x - PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        var  MaxX         = (x + PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        int  NumberPixels = 0;
                        for (int x2 = MinX; x2 < MaxX; ++x2)
                        {
                            for (int y2 = MinY; y2 < MaxY; ++y2)
                            {
                                var Offset = ((y * image.Width) + x);
                                RValue += Copy[Offset].Red;
                                GValue += Copy[Offset].Green;
                                BValue += Copy[Offset].Blue;
                                ++NumberPixels;
                            }
                        }
                        RValue /= (uint)NumberPixels;
                        GValue /= (uint)NumberPixels;
                        BValue /= (uint)NumberPixels;
                        EllipseDrawer.Center = new Vector2(x, y);
                        EllipseDrawer.Color  = new Color((byte)RValue, (byte)GValue, (byte)BValue);
                        EllipseDrawer.Apply(image, targetLocation);
                    }
                }
            }
            for (int y = targetLocation.Bottom + PointSize; y < targetLocation.Top; y += PointSize2)
            {
                var MinY = (y - PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                var MaxY = (y + PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                fixed(Color *TargetPointer = &Copy[(y *image.Width) + targetLocation.Left])
                {
                    Color *TargetPointer2 = TargetPointer;

                    for (int x = targetLocation.Left + PointSize; x < targetLocation.Right; x += PointSize2)
                    {
                        uint RValue       = 0;
                        uint GValue       = 0;
                        uint BValue       = 0;
                        var  MinX         = (x - PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        var  MaxX         = (x + PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        int  NumberPixels = 0;
                        for (int x2 = MinX; x2 < MaxX; ++x2)
                        {
                            for (int y2 = MinY; y2 < MaxY; ++y2)
                            {
                                var Offset = ((y * image.Width) + x);
                                RValue += Copy[Offset].Red;
                                GValue += Copy[Offset].Green;
                                BValue += Copy[Offset].Blue;
                                ++NumberPixels;
                            }
                        }
                        RValue /= (uint)NumberPixels;
                        GValue /= (uint)NumberPixels;
                        BValue /= (uint)NumberPixels;
                        EllipseDrawer.Center = new Vector2(x, y);
                        EllipseDrawer.Color  = new Color((byte)RValue, (byte)GValue, (byte)BValue);
                        EllipseDrawer.Apply(image, targetLocation);
                    }
                }
            }
            for (int y = targetLocation.Bottom; y < targetLocation.Top; y += PointSize2)
            {
                var TempY = y + new Random(y).Next(-PointSize, PointSize);
                var MinY  = (TempY - PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                var MaxY  = (TempY + PointSize).Clamp(targetLocation.Bottom, targetLocation.Top - 1);
                fixed(Color *TargetPointer = &Copy[(y *image.Width) + targetLocation.Left])
                {
                    Color *TargetPointer2 = TargetPointer;

                    for (int x = targetLocation.Left + PointSize; x < targetLocation.Right; x += PointSize2)
                    {
                        uint RValue       = 0;
                        uint GValue       = 0;
                        uint BValue       = 0;
                        var  TempX        = x + new Random(x).Next(-PointSize, PointSize);
                        var  MinX         = (TempX - PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        var  MaxX         = (TempX + PointSize).Clamp(targetLocation.Left, targetLocation.Right - 1);
                        int  NumberPixels = 0;
                        for (int x2 = MinX; x2 < MaxX; ++x2)
                        {
                            for (int y2 = MinY; y2 < MaxY; ++y2)
                            {
                                var Offset = ((y * image.Width) + x);
                                RValue += Copy[Offset].Red;
                                GValue += Copy[Offset].Green;
                                BValue += Copy[Offset].Blue;
                                ++NumberPixels;
                            }
                        }
                        RValue /= (uint)NumberPixels;
                        GValue /= (uint)NumberPixels;
                        BValue /= (uint)NumberPixels;
                        EllipseDrawer.Center = new Vector2(TempX, TempY);
                        EllipseDrawer.Color  = new Color((byte)RValue, (byte)GValue, (byte)BValue);
                        EllipseDrawer.Apply(image, targetLocation);
                    }
                }
            }
            return(image);
        }
        public static ColorVertexes Create(int nx, int ny, int nz, float radius, float minValue, float maxValue)
        {
            int           points        = nx * ny * nz;
            ColorVertexes colorVertexes = new ColorVertexes(points);
            Random        random        = new Random();
            Random        colorRandom   = new Random();

            float xmin = 0, xmax = 0, ymin = 0, ymax = 0, zmin = 0, zmax = 0;
            bool  isInit = false;

            unsafe
            {
                for (long i = 0; i < colorVertexes.Size; i++)
                {
                    float x = minValue + ((float)random.NextDouble()) * maxValue;
                    float y = minValue + ((float)random.NextDouble()) * maxValue;
                    float z = minValue + ((float)random.NextDouble()) * maxValue;
                    if (!isInit)
                    {
                        xmin   = x;
                        xmax   = x;
                        ymin   = y;
                        ymax   = y;
                        zmin   = z;
                        zmax   = z;
                        isInit = true;
                    }
                    if (x < xmin)
                    {
                        xmin = x;
                    }
                    if (x > xmax)
                    {
                        xmax = x;
                    }
                    if (y < ymin)
                    {
                        ymin = y;
                    }
                    if (y > ymax)
                    {
                        ymax = y;
                    }
                    if (z < zmin)
                    {
                        zmin = z;
                    }
                    if (z > zmax)
                    {
                        zmax = z;
                    }

                    Vertex *centers = colorVertexes.Centers;
                    centers[i].X = x;
                    centers[i].Y = y;
                    centers[i].Z = z;

                    Color *colors = colorVertexes.Colors;
                    colors[i].red   = (byte)colorRandom.Next(0, 256);
                    colors[i].green = (byte)colorRandom.Next(0, 256);
                    colors[i].blue  = (byte)colorRandom.Next(0, 256);
                }
                Vertex location = new Vertex(xmin, ymin, zmin);

                Size3D size;
                size.x = (xmax - xmin);
                size.y = (ymax - ymin);
                size.z = (zmax - zmin);
                Rect3D rect = new Rect3D(location, size);
                colorVertexes.Bounds = rect;
            }
            return(colorVertexes);
        }
예제 #27
0
        /// <summary>
        /// Applies the filter to the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var TempValues = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, TempValues, TempValues.Length);
            int ApetureMin = -ApetureRadius;
            int ApetureMax = ApetureRadius;

            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * TargetPointer = &TempValues[(y * image.Width) + targetLocation.Left])
                {
                    Color *TargetPointer2 = TargetPointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        uint RValue   = 0;
                        uint GValue   = 0;
                        uint BValue   = 0;
                        int NumPixels = 0;
                        for (int x2 = ApetureMin; x2 < ApetureMax; ++x2)
                        {
                            int TempX1 = x + x2;
                            int TempX2 = x - x2;
                            if (TempX1 >= targetLocation.Left && TempX1 < targetLocation.Right && TempX2 >= targetLocation.Left && TempX2 < targetLocation.Right)
                            {
                                for (int y2 = ApetureMin; y2 < ApetureMax; ++y2)
                                {
                                    int TempY1 = y + y2;
                                    int TempY2 = y - y2;
                                    if (TempY1 >= targetLocation.Bottom && TempY1 < targetLocation.Top && TempY2 >= targetLocation.Bottom && TempY2 < targetLocation.Top)
                                    {
                                        var TempValue1 = image.Pixels[(y * image.Width) + x];
                                        var TempValue2 = image.Pixels[(TempY1 * image.Width) + TempX1];
                                        var TempValue3 = image.Pixels[(TempY2 * image.Width) + TempX2];
                                        if (Distance.Euclidean(TempValue1, TempValue2) < Distance.Euclidean(TempValue1, TempValue3))
                                        {
                                            RValue += TempValue2.Red;
                                            GValue += TempValue2.Green;
                                            BValue += TempValue2.Blue;
                                        }
                                        else
                                        {
                                            RValue += TempValue3.Red;
                                            GValue += TempValue3.Green;
                                            BValue += TempValue3.Blue;
                                        }
                                        ++NumPixels;
                                    }
                                }
                            }
                        }
                        TempValues[(y * image.Width) + x].Red   = (byte)(RValue / NumPixels);
                        TempValues[(y * image.Width) + x].Green = (byte)(GValue / NumPixels);
                        TempValues[(y * image.Width) + x].Blue  = (byte)(BValue / NumPixels);
                        TempValues[(y * image.Width) + x].Alpha = image.Pixels[(y * image.Width) + x].Alpha;
                    }
                }
            });
            return(image.ReCreate(image.Width, image.Height, TempValues));
        }
예제 #28
0
        /// <summary>
        /// Applies the filter to the specified image.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <param name="targetLocation">The target location.</param>
        /// <returns>The image</returns>
        public unsafe Image Apply(Image image, Rectangle targetLocation = default(Rectangle))
        {
            Filter.Precompute(image.Width, image.Height, Width, Height);
            targetLocation = targetLocation == default(Rectangle) ? new Rectangle(0, 0, image.Width, image.Height) : targetLocation.Clamp(image);
            var Copy = new Color[image.Pixels.Length];

            Array.Copy(image.Pixels, Copy, Copy.Length);
            TransformationMatrix = GetMatrix(image, targetLocation);
            double TempWidth  = Width < 0 ? image.Width : Width;
            double TempHeight = Height < 0 ? image.Width : Height;
            double XScale     = TempWidth / image.Width;
            double YScale     = TempHeight / image.Height;

            YRadius = YScale < 1f ? (Filter.FilterRadius / YScale) : Filter.FilterRadius;
            XRadius = XScale < 1f ? (Filter.FilterRadius / XScale) : Filter.FilterRadius;

            Parallel.For(targetLocation.Bottom, targetLocation.Top, y =>
            {
                fixed(Color * OutputPointer = &image.Pixels[(y * image.Width) + targetLocation.Left])
                {
                    Color *OutputPointer2 = OutputPointer;
                    for (int x = targetLocation.Left; x < targetLocation.Right; ++x)
                    {
                        var Values   = new Vector4(0, 0, 0, 0);
                        float Weight = 0;

                        var rotated  = Vector2.Transform(new Vector2(x, y), TransformationMatrix);
                        var rotatedY = (int)rotated.Y;
                        var rotatedX = (int)rotated.X;
                        if (rotatedY >= image.Height ||
                            rotatedY < 0 ||
                            rotatedX >= image.Width ||
                            rotatedX < 0)
                        {
                            (*OutputPointer2).Red   = 0;
                            (*OutputPointer2).Green = 0;
                            (*OutputPointer2).Blue  = 0;
                            (*OutputPointer2).Alpha = 255;
                            ++OutputPointer2;
                            continue;
                        }
                        var Left   = (int)(rotatedX - XRadius);
                        var Right  = (int)(rotatedX + XRadius);
                        var Top    = (int)(rotatedY - YRadius);
                        var Bottom = (int)(rotatedY + YRadius);
                        if (Top < 0)
                        {
                            Top = 0;
                        }
                        if (Bottom >= image.Height)
                        {
                            Bottom = image.Height - 1;
                        }
                        if (Left < 0)
                        {
                            Left = 0;
                        }
                        if (Right >= image.Width)
                        {
                            Right = image.Width - 1;
                        }
                        for (int i = Top, YCount = 0; i <= Bottom; ++i, ++YCount)
                        {
                            fixed(Color * PixelPointer = &Copy[i * image.Width])
                            {
                                Color *PixelPointer2 = PixelPointer + Left;
                                for (int j = Left, XCount = 0; j <= Right; ++j, ++XCount)
                                {
                                    var TempYWeight = Filter.YWeights[rotatedY].Values[YCount];
                                    var TempXWeight = Filter.XWeights[rotatedX].Values[XCount];
                                    var TempWeight  = TempYWeight * TempXWeight;

                                    if (YRadius == 0 && XRadius == 0)
                                    {
                                        TempWeight = 1;
                                    }

                                    if (TempWeight == 0)
                                    {
                                        ++PixelPointer2;
                                        continue;
                                    }
                                    Values.X = Values.X + ((*PixelPointer2).Red * (float)TempWeight);
                                    Values.Y = Values.Y + ((*PixelPointer2).Green * (float)TempWeight);
                                    Values.Z = Values.Z + ((*PixelPointer2).Blue * (float)TempWeight);
                                    Values.W = Values.W + ((*PixelPointer2).Alpha * (float)TempWeight);
                                    ++PixelPointer2;
                                    Weight += (float)TempWeight;
                                }
                            }
                        }
                        if (Weight == 0)
                        {
                            Weight = 1;
                        }
                        if (Weight > 0)
                        {
                            Values = Vector4.Clamp(Values, Vector4.Zero, new Vector4(255, 255, 255, 255));
                            (*OutputPointer2).Red   = (byte)Values.X;
                            (*OutputPointer2).Green = (byte)Values.Y;
                            (*OutputPointer2).Blue  = (byte)Values.Z;
                            (*OutputPointer2).Alpha = (byte)Values.W;
                            ++OutputPointer2;
                        }
                        else
                        {
                            ++OutputPointer2;
                        }
                    }
                }
            });
            return(image);
        }
예제 #29
0
        public static unsafe void Paint()
        {
            Vector2 shapeCoord = new Vector2();
            float   num        = P3D_Helper.Reciprocal(P3D_Brush.canvasW * P3D_Brush.detailScale.x);
            float   num2       = P3D_Helper.Reciprocal(P3D_Brush.canvasH * P3D_Brush.detailScale.y);
            Color * colorPtr1  = &P3D_Brush.color;

            colorPtr1->a *= P3D_Brush.opacity;
            if ((P3D_Brush.shape != null) && (P3D_Brush.shape.format != TextureFormat.Alpha8))
            {
                int xMin = P3D_Brush.rect.XMin;
                while (xMin < P3D_Brush.rect.XMax)
                {
                    int yMin = P3D_Brush.rect.YMin;
                    while (true)
                    {
                        if (yMin >= P3D_Brush.rect.YMax)
                        {
                            xMin++;
                            break;
                        }
                        if (P3D_Brush.IsInsideShape(P3D_Brush.inverse, xMin, yMin, ref shapeCoord))
                        {
                            Vector3 a       = ColorToNormalXY(P3D_Brush.canvas.GetPixel(xMin, yMin));
                            Vector3 vector4 = ColorToNormalXY(P3D_Brush.shape.GetPixelBilinear(shapeCoord.x, shapeCoord.y));
                            if (P3D_Brush.detail != null)
                            {
                                vector4 = CombineNormalsXY(vector4, ColorToNormalXY(P3D_Brush.SampleRepeat(P3D_Brush.detail, num * xMin, num2 * yMin)));
                            }
                            P3D_Brush.canvas.SetPixel(xMin, yMin, NormalToColor(Vector3.Normalize(ComputeZ(CombineNormalsXY(a, vector4, P3D_Brush.opacity)))));
                        }
                        yMin++;
                    }
                }
            }
            else
            {
                int xMin = P3D_Brush.rect.XMin;
                while (xMin < P3D_Brush.rect.XMax)
                {
                    int yMin = P3D_Brush.rect.YMin;
                    while (true)
                    {
                        if (yMin >= P3D_Brush.rect.YMax)
                        {
                            xMin++;
                            break;
                        }
                        if (P3D_Brush.IsInsideShape(P3D_Brush.inverse, xMin, yMin, ref shapeCoord))
                        {
                            Vector3 a         = ColorToNormalXY(P3D_Brush.canvas.GetPixel(xMin, yMin));
                            Vector2 direction = P3D_Brush.direction;
                            float   opacity   = P3D_Brush.opacity;
                            if (P3D_Brush.shape != null)
                            {
                                opacity *= P3D_Brush.shape.GetPixelBilinear(shapeCoord.x, shapeCoord.y).a;
                            }
                            if (P3D_Brush.detail != null)
                            {
                                Vector3 b = ColorToNormalXY(P3D_Brush.SampleRepeat(P3D_Brush.detail, num * xMin, num2 * yMin));
                                direction = CombineNormalsXY((Vector3)direction, b);
                            }
                            P3D_Brush.canvas.SetPixel(xMin, yMin, NormalToColor(Vector3.Normalize(ComputeZ(CombineNormalsXY(a, direction, opacity)))));
                        }
                        yMin++;
                    }
                }
            }
        }
예제 #30
0
        private unsafe void InternalPrepareDraw(Rectangle drawArea)
        {
            Rectangle rectangle = new Rectangle(drawArea.X - 2, drawArea.Y - 2, drawArea.Width + 4, drawArea.Height + 4);

            this._drawArea = drawArea;
            fixed(LiquidRenderer.LiquidCache *liquidCachePtr1 = &this._cache[1])
            {
                int num1 = rectangle.Height * 2 + 2;

                LiquidRenderer.LiquidCache *liquidCachePtr2 = liquidCachePtr1;
                for (int x = rectangle.X; x < rectangle.X + rectangle.Width; ++x)
                {
                    for (int y = rectangle.Y; y < rectangle.Y + rectangle.Height; ++y)
                    {
                        Tile tile = this._tiles[x, y] ?? new Tile();
                        liquidCachePtr2->LiquidLevel        = (float)tile.liquid / (float)byte.MaxValue;
                        liquidCachePtr2->IsHalfBrick        = tile.halfBrick() && liquidCachePtr2[-1].HasLiquid;
                        liquidCachePtr2->IsSolid            = WorldGen.SolidOrSlopedTile(tile) && !liquidCachePtr2->IsHalfBrick;
                        liquidCachePtr2->HasLiquid          = (int)tile.liquid != 0;
                        liquidCachePtr2->VisibleLiquidLevel = 0.0f;
                        liquidCachePtr2->HasWall            = (int)tile.wall != 0;
                        liquidCachePtr2->Type = tile.liquidType();
                        if (liquidCachePtr2->IsHalfBrick && !liquidCachePtr2->HasLiquid)
                        {
                            liquidCachePtr2->Type = liquidCachePtr2[-1].Type;
                        }
                        ++liquidCachePtr2;
                    }
                }
                LiquidRenderer.LiquidCache *liquidCachePtr3 = liquidCachePtr1 + num1;
                LiquidRenderer.LiquidCache  liquidCache1;
                LiquidRenderer.LiquidCache  liquidCache2;
                LiquidRenderer.LiquidCache  liquidCache3;
                LiquidRenderer.LiquidCache  liquidCache4;
                for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                {
                    for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                    {
                        float val1 = 0.0f;
                        float num2;
                        if (liquidCachePtr3->IsHalfBrick && liquidCachePtr3[-1].HasLiquid)
                        {
                            num2 = 1f;
                        }
                        else if (!liquidCachePtr3->HasLiquid)
                        {
                            liquidCache1 = liquidCachePtr3[-rectangle.Height];
                            liquidCache2 = liquidCachePtr3[rectangle.Height];
                            liquidCache3 = liquidCachePtr3[-1];
                            liquidCache4 = liquidCachePtr3[1];
                            if (liquidCache1.HasLiquid && liquidCache2.HasLiquid && (int)liquidCache1.Type == (int)liquidCache2.Type)
                            {
                                val1 = liquidCache1.LiquidLevel + liquidCache2.LiquidLevel;
                                liquidCachePtr3->Type = liquidCache1.Type;
                            }
                            if (liquidCache3.HasLiquid && liquidCache4.HasLiquid && (int)liquidCache3.Type == (int)liquidCache4.Type)
                            {
                                val1 = Math.Max(val1, liquidCache3.LiquidLevel + liquidCache4.LiquidLevel);
                                liquidCachePtr3->Type = liquidCache3.Type;
                            }
                            num2 = val1 * 0.5f;
                        }
                        else
                        {
                            num2 = liquidCachePtr3->LiquidLevel;
                        }
                        liquidCachePtr3->VisibleLiquidLevel = num2;
                        liquidCachePtr3->HasVisibleLiquid   = (double)num2 != 0.0;
                        ++liquidCachePtr3;
                    }
                    liquidCachePtr3 += 4;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr4 = liquidCachePtr1;
                for (int index1 = 0; index1 < rectangle.Width; ++index1)
                {
                    for (int index2 = 0; index2 < rectangle.Height - 10; ++index2)
                    {
                        if (liquidCachePtr4->HasVisibleLiquid && !liquidCachePtr4->IsSolid)
                        {
                            liquidCachePtr4->Opacity     = 1f;
                            liquidCachePtr4->VisibleType = liquidCachePtr4->Type;
                            float num2 = 1f / (float)(LiquidRenderer.WATERFALL_LENGTH[(int)liquidCachePtr4->Type] + 1);
                            float num3 = 1f;
                            for (int index3 = 1; index3 <= LiquidRenderer.WATERFALL_LENGTH[(int)liquidCachePtr4->Type]; ++index3)
                            {
                                num3 -= num2;
                                if (!liquidCachePtr4[index3].IsSolid)
                                {
                                    liquidCachePtr4[index3].VisibleLiquidLevel = Math.Max(liquidCachePtr4[index3].VisibleLiquidLevel, liquidCachePtr4->VisibleLiquidLevel * num3);
                                    liquidCachePtr4[index3].Opacity            = num3;
                                    liquidCachePtr4[index3].VisibleType        = liquidCachePtr4->Type;
                                }
                                else
                                {
                                    break;
                                }
                            }
                        }
                        if (liquidCachePtr4->IsSolid)
                        {
                            liquidCachePtr4->VisibleLiquidLevel = 1f;
                            liquidCachePtr4->HasVisibleLiquid   = false;
                        }
                        else
                        {
                            liquidCachePtr4->HasVisibleLiquid = (double)liquidCachePtr4->VisibleLiquidLevel != 0.0;
                        }
                        ++liquidCachePtr4;
                    }
                    liquidCachePtr4 += 10;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr5 = liquidCachePtr1 + num1;
                for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                {
                    for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                    {
                        if (liquidCachePtr5->HasVisibleLiquid && !liquidCachePtr5->IsSolid)
                        {
                            liquidCache1 = liquidCachePtr5[-1];
                            liquidCache2 = liquidCachePtr5[1];
                            liquidCache3 = liquidCachePtr5[-rectangle.Height];
                            liquidCache4 = liquidCachePtr5[rectangle.Height];
                            float num2 = 0.0f;
                            float num3 = 1f;
                            float num4 = 0.0f;
                            float num5 = 1f;
                            float visibleLiquidLevel = liquidCachePtr5->VisibleLiquidLevel;
                            if (!liquidCache1.HasVisibleLiquid)
                            {
                                num4 += liquidCache2.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache2.HasVisibleLiquid && !liquidCache2.IsSolid && !liquidCache2.IsHalfBrick)
                            {
                                num5 -= liquidCache1.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache3.HasVisibleLiquid && !liquidCache3.IsSolid && !liquidCache3.IsHalfBrick)
                            {
                                num2 += liquidCache4.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            if (!liquidCache4.HasVisibleLiquid && !liquidCache4.IsSolid && !liquidCache4.IsHalfBrick)
                            {
                                num3 -= liquidCache3.VisibleLiquidLevel * (1f - visibleLiquidLevel);
                            }
                            liquidCachePtr5->LeftWall   = num2;
                            liquidCachePtr5->RightWall  = num3;
                            liquidCachePtr5->BottomWall = num5;
                            liquidCachePtr5->TopWall    = num4;
                            Point zero = Point.Zero;
                            liquidCachePtr5->HasTopEdge    = !liquidCache1.HasVisibleLiquid && !liquidCache1.IsSolid || (double)num4 != 0.0;
                            liquidCachePtr5->HasBottomEdge = !liquidCache2.HasVisibleLiquid && !liquidCache2.IsSolid || (double)num5 != 1.0;
                            liquidCachePtr5->HasLeftEdge   = !liquidCache3.HasVisibleLiquid && !liquidCache3.IsSolid || (double)num2 != 0.0;
                            liquidCachePtr5->HasRightEdge  = !liquidCache4.HasVisibleLiquid && !liquidCache4.IsSolid || (double)num3 != 1.0;
                            if (!liquidCachePtr5->HasLeftEdge)
                            {
                                if (liquidCachePtr5->HasRightEdge)
                                {
                                    zero.X += 32;
                                }
                                else
                                {
                                    zero.X += 16;
                                }
                            }
                            if (liquidCachePtr5->HasLeftEdge && liquidCachePtr5->HasRightEdge)
                            {
                                zero.X  = 16;
                                zero.Y += 32;
                                if (liquidCachePtr5->HasTopEdge)
                                {
                                    zero.Y = 16;
                                }
                            }
                            else if (!liquidCachePtr5->HasTopEdge)
                            {
                                if (!liquidCachePtr5->HasLeftEdge && !liquidCachePtr5->HasRightEdge)
                                {
                                    zero.Y += 48;
                                }
                                else
                                {
                                    zero.Y += 16;
                                }
                            }
                            if (zero.Y == 16 && liquidCachePtr5->HasLeftEdge ^ liquidCachePtr5->HasRightEdge && (index2 + rectangle.Y) % 2 == 0)
                            {
                                zero.Y += 16;
                            }
                            liquidCachePtr5->FrameOffset = zero;
                        }
                        else
                        {
                            liquidCachePtr5->HasLeftEdge   = false;
                            liquidCachePtr5->HasTopEdge    = false;
                            liquidCachePtr5->HasRightEdge  = false;
                            liquidCachePtr5->HasBottomEdge = false;
                        }
                        ++liquidCachePtr5;
                    }
                    liquidCachePtr5 += 4;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr6 = liquidCachePtr1 + num1;
                for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                {
                    for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                    {
                        if (liquidCachePtr6->HasVisibleLiquid)
                        {
                            liquidCache1 = liquidCachePtr6[-1];
                            liquidCache2 = liquidCachePtr6[1];
                            liquidCache3 = liquidCachePtr6[-rectangle.Height];
                            liquidCache4 = liquidCachePtr6[rectangle.Height];
                            liquidCachePtr6->VisibleLeftWall   = liquidCachePtr6->LeftWall;
                            liquidCachePtr6->VisibleRightWall  = liquidCachePtr6->RightWall;
                            liquidCachePtr6->VisibleTopWall    = liquidCachePtr6->TopWall;
                            liquidCachePtr6->VisibleBottomWall = liquidCachePtr6->BottomWall;
                            if (liquidCache1.HasVisibleLiquid && liquidCache2.HasVisibleLiquid)
                            {
                                if (liquidCachePtr6->HasLeftEdge)
                                {
                                    liquidCachePtr6->VisibleLeftWall = (float)(((double)liquidCachePtr6->LeftWall * 2.0 + (double)liquidCache1.LeftWall + (double)liquidCache2.LeftWall) * 0.25);
                                }
                                if (liquidCachePtr6->HasRightEdge)
                                {
                                    liquidCachePtr6->VisibleRightWall = (float)(((double)liquidCachePtr6->RightWall * 2.0 + (double)liquidCache1.RightWall + (double)liquidCache2.RightWall) * 0.25);
                                }
                            }
                            if (liquidCache3.HasVisibleLiquid && liquidCache4.HasVisibleLiquid)
                            {
                                if (liquidCachePtr6->HasTopEdge)
                                {
                                    liquidCachePtr6->VisibleTopWall = (float)(((double)liquidCachePtr6->TopWall * 2.0 + (double)liquidCache3.TopWall + (double)liquidCache4.TopWall) * 0.25);
                                }
                                if (liquidCachePtr6->HasBottomEdge)
                                {
                                    liquidCachePtr6->VisibleBottomWall = (float)(((double)liquidCachePtr6->BottomWall * 2.0 + (double)liquidCache3.BottomWall + (double)liquidCache4.BottomWall) * 0.25);
                                }
                            }
                        }
                        ++liquidCachePtr6;
                    }
                    liquidCachePtr6 += 4;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr7 = liquidCachePtr1 + num1;
                for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                {
                    for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                    {
                        if (liquidCachePtr7->HasLiquid)
                        {
                            liquidCache1 = liquidCachePtr7[-1];
                            liquidCache2 = liquidCachePtr7[1];
                            liquidCache3 = liquidCachePtr7[-rectangle.Height];
                            liquidCache4 = liquidCachePtr7[rectangle.Height];
                            if (liquidCachePtr7->HasTopEdge && !liquidCachePtr7->HasBottomEdge && liquidCachePtr7->HasLeftEdge ^ liquidCachePtr7->HasRightEdge)
                            {
                                if (liquidCachePtr7->HasRightEdge)
                                {
                                    liquidCachePtr7->VisibleRightWall = liquidCache2.VisibleRightWall;
                                    liquidCachePtr7->VisibleTopWall   = liquidCache3.VisibleTopWall;
                                }
                                else
                                {
                                    liquidCachePtr7->VisibleLeftWall = liquidCache2.VisibleLeftWall;
                                    liquidCachePtr7->VisibleTopWall  = liquidCache4.VisibleTopWall;
                                }
                            }
                            else if (liquidCache2.FrameOffset.X == 16 && liquidCache2.FrameOffset.Y == 32)
                            {
                                if ((double)liquidCachePtr7->VisibleLeftWall > 0.5)
                                {
                                    liquidCachePtr7->VisibleLeftWall = 0.0f;
                                    liquidCachePtr7->FrameOffset     = new Point(0, 0);
                                }
                                else if ((double)liquidCachePtr7->VisibleRightWall < 0.5)
                                {
                                    liquidCachePtr7->VisibleRightWall = 1f;
                                    liquidCachePtr7->FrameOffset      = new Point(32, 0);
                                }
                            }
                        }
                        ++liquidCachePtr7;
                    }
                    liquidCachePtr7 += 4;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr8 = liquidCachePtr1 + num1;
                for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                {
                    for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                    {
                        if (liquidCachePtr8->HasLiquid)
                        {
                            liquidCache1 = liquidCachePtr8[-1];
                            liquidCache2 = liquidCachePtr8[1];
                            liquidCache3 = liquidCachePtr8[-rectangle.Height];
                            liquidCache4 = liquidCachePtr8[rectangle.Height];
                            if (!liquidCachePtr8->HasBottomEdge && !liquidCachePtr8->HasLeftEdge && (!liquidCachePtr8->HasTopEdge && !liquidCachePtr8->HasRightEdge))
                            {
                                if (liquidCache3.HasTopEdge && liquidCache1.HasLeftEdge)
                                {
                                    liquidCachePtr8->FrameOffset.X     = Math.Max(4, (int)(16.0 - (double)liquidCache1.VisibleLeftWall * 16.0)) - 4;
                                    liquidCachePtr8->FrameOffset.Y     = 48 + Math.Max(4, (int)(16.0 - (double)liquidCache3.VisibleTopWall * 16.0)) - 4;
                                    liquidCachePtr8->VisibleLeftWall   = 0.0f;
                                    liquidCachePtr8->VisibleTopWall    = 0.0f;
                                    liquidCachePtr8->VisibleRightWall  = 1f;
                                    liquidCachePtr8->VisibleBottomWall = 1f;
                                }
                                else if (liquidCache4.HasTopEdge && liquidCache1.HasRightEdge)
                                {
                                    liquidCachePtr8->FrameOffset.X     = 32 - Math.Min(16, (int)((double)liquidCache1.VisibleRightWall * 16.0) - 4);
                                    liquidCachePtr8->FrameOffset.Y     = 48 + Math.Max(4, (int)(16.0 - (double)liquidCache4.VisibleTopWall * 16.0)) - 4;
                                    liquidCachePtr8->VisibleLeftWall   = 0.0f;
                                    liquidCachePtr8->VisibleTopWall    = 0.0f;
                                    liquidCachePtr8->VisibleRightWall  = 1f;
                                    liquidCachePtr8->VisibleBottomWall = 1f;
                                }
                            }
                        }
                        ++liquidCachePtr8;
                    }
                    liquidCachePtr8 += 4;
                }
                LiquidRenderer.LiquidCache *liquidCachePtr9 = liquidCachePtr1 + num1;
                fixed(LiquidRenderer.LiquidDrawCache *liquidDrawCachePtr1 = &this._drawCache[0])
                fixed(Color * colorPtr1 = &this._waveMask[0])
                {
                    LiquidRenderer.LiquidDrawCache *liquidDrawCachePtr2 = liquidDrawCachePtr1;
                    Color *colorPtr2 = colorPtr1;

                    for (int index1 = 2; index1 < rectangle.Width - 2; ++index1)
                    {
                        Color *colorPtr3 = colorPtr2;
                        for (int index2 = 2; index2 < rectangle.Height - 2; ++index2)
                        {
                            if (liquidCachePtr9->HasVisibleLiquid)
                            {
                                float num2 = Math.Min(0.75f, liquidCachePtr9->VisibleLeftWall);
                                float num3 = Math.Max(0.25f, liquidCachePtr9->VisibleRightWall);
                                float num4 = Math.Min(0.75f, liquidCachePtr9->VisibleTopWall);
                                float num5 = Math.Max(0.25f, liquidCachePtr9->VisibleBottomWall);
                                if (liquidCachePtr9->IsHalfBrick && (double)num5 > 0.5)
                                {
                                    num5 = 0.5f;
                                }
                                liquidDrawCachePtr2->IsVisible       = liquidCachePtr9->HasWall || (!liquidCachePtr9->IsHalfBrick || !liquidCachePtr9->HasLiquid);
                                liquidDrawCachePtr2->SourceRectangle = new Rectangle((int)(16.0 - (double)num3 * 16.0) + liquidCachePtr9->FrameOffset.X, (int)(16.0 - (double)num5 * 16.0) + liquidCachePtr9->FrameOffset.Y, (int)Math.Ceiling(((double)num3 - (double)num2) * 16.0), (int)Math.Ceiling(((double)num5 - (double)num4) * 16.0));
                                liquidDrawCachePtr2->IsSurfaceLiquid = liquidCachePtr9->FrameOffset.X == 16 && liquidCachePtr9->FrameOffset.Y == 0 && (double)(index2 + rectangle.Y) > Main.worldSurface - 40.0;
                                liquidDrawCachePtr2->Opacity         = liquidCachePtr9->Opacity;
                                liquidDrawCachePtr2->LiquidOffset    = new Vector2((float)Math.Floor((double)num2 * 16.0), (float)Math.Floor((double)num4 * 16.0));
                                liquidDrawCachePtr2->Type            = liquidCachePtr9->VisibleType;
                                liquidDrawCachePtr2->HasWall         = liquidCachePtr9->HasWall;
                                byte num6 = LiquidRenderer.WAVE_MASK_STRENGTH[(int)liquidCachePtr9->VisibleType];
                                byte num7 = (byte)((uint)num6 >> 1);
                                colorPtr2->R = num7;
                                colorPtr2->G = num7;
                                colorPtr2->B = LiquidRenderer.VISCOSITY_MASK[(int)liquidCachePtr9->VisibleType];
                                colorPtr2->A = num6;
                                LiquidRenderer.LiquidCache *liquidCachePtr10 = liquidCachePtr9 - 1;
                                if (index2 != 2 && !liquidCachePtr10->HasVisibleLiquid && (!liquidCachePtr10->IsSolid && !liquidCachePtr10->IsHalfBrick))
                                {
                                    *(colorPtr2 - 200) = *colorPtr2;
                                }
                            }
                            else
                            {
                                liquidDrawCachePtr2->IsVisible = false;
                                int  index3 = liquidCachePtr9->IsSolid || liquidCachePtr9->IsHalfBrick ? 3 : 4;
                                byte num2   = LiquidRenderer.WAVE_MASK_STRENGTH[index3];
                                byte num3   = (byte)((uint)num2 >> 1);
                                colorPtr2->R = num3;
                                colorPtr2->G = num3;
                                colorPtr2->B = LiquidRenderer.VISCOSITY_MASK[index3];
                                colorPtr2->A = num2;
                            }
                            ++liquidCachePtr9;
                            ++liquidDrawCachePtr2;
                            colorPtr2 += 200;
                        }
                        liquidCachePtr9 += 4;
                        colorPtr2        = colorPtr3 + 1;
                    }
                }
                LiquidRenderer.LiquidCache *liquidCachePtr11 = liquidCachePtr1;
                for (int x = rectangle.X; x < rectangle.X + rectangle.Width; ++x)
                {
                    for (int y = rectangle.Y; y < rectangle.Y + rectangle.Height; ++y)
                    {
                        if ((int)liquidCachePtr11->VisibleType == 1 && liquidCachePtr11->HasVisibleLiquid && Dust.lavaBubbles < 200)
                        {
                            if (this._random.Next(700) == 0)
                            {
                                Dust.NewDust(new Vector2((float)(x * 16), (float)(y * 16)), 16, 16, 35, 0.0f, 0.0f, 0, Color.White, 1f);
                            }
                            if (this._random.Next(350) == 0)
                            {
                                int index = Dust.NewDust(new Vector2((float)(x * 16), (float)(y * 16)), 16, 8, 35, 0.0f, 0.0f, 50, Color.White, 1.5f);
                                Main.dust[index].velocity   *= 0.8f;
                                Main.dust[index].velocity.X *= 2f;
                                Main.dust[index].velocity.Y -= (float)this._random.Next(1, 7) * 0.1f;
                                if (this._random.Next(10) == 0)
                                {
                                    Main.dust[index].velocity.Y *= (float)this._random.Next(2, 5);
                                }
                                Main.dust[index].noGravity = true;
                            }
                        }
                        ++liquidCachePtr11;
                    }
                }
            }

            if (this.ViscosityFilters == null)
            {
                return;
            }
            this.ViscosityFilters(this._waveMask, this.GetCachedDrawArea());
        }
예제 #31
0
        public unsafe void LoadTextureData(Texture2D _texture, string _name = "")
        {
            _textureName = _name;
            Image  img           = Raylib.GetTextureData(_texture);         //load into an image
            IntPtr mapPixelsData = Raylib.LoadImageColors(img);             //get image data IntPtr
            Color *mapPixels     = (Color *)mapPixelsData.ToPointer();      //IntPtr points to Color data

            //
            // Find color DATA going thru width of the texture
            //
            ImageData = new Color[img.height * img.width];

            for (int x = 0; x < img.width; x++)
            {
                for (int y = 0; y < img.height; y++)
                {
                    ImageData[y * img.width + x] = mapPixels[y * img.width + x];
                }
            }
            Raylib.UnloadImage(img);                                        // Unload image from RAM

            float darkness = 1.0f;

            //
            // arrange the Data to be in 2d coordinants [x,y]
            //
            _textureData = new List <Color[, ]>();
            for (int d = 0; d <= DARKNESSLEVLES; d++)
            {
                Color[,] ShadeOfDarkData = new Color[img.width, img.height];
                for (int x = 0; x < img.width; x++)
                {
                    for (int y = 0; y < img.height; y++)
                    {
                        var   index    = x + (img.width * y);           //find pixel going across the texture image
                        Color pixel    = ImageData[index];
                        Color tmpPixel = new Color();
                        //
                        // pack the color bytes into int, shift the bits to get dark color
                        //
                        int tmp = (Byte)pixel.a << 24 | (Byte)(pixel.b / darkness) << 16 | (Byte)(pixel.g / darkness) << 8 |
                                  (Byte)(pixel.r / darkness);
                        //
                        // unpack the int back to bytes to update the Color values (with darkness)
                        //
                        var bytes = BitConverter.GetBytes(tmp);

                        tmpPixel.r = bytes[0];
                        tmpPixel.g = bytes[1];
                        tmpPixel.b = bytes[2];
                        tmpPixel.a = bytes[3];

                        ShadeOfDarkData[x, y] = tmpPixel;
                    }
                }
                //
                // add a shade of dark data
                //
                _textureData.Add(ShadeOfDarkData);
                darkness += 0.0f + (d * 0.0125f) + (d * d * 0.00025f);          //change darkness
            }
        }
예제 #32
0
        public unsafe static int Main()
        {
            // Initialization
            //--------------------------------------------------------------------------------------
            const int screenWidth  = 800;
            const int screenHeight = 450;

            InitWindow(screenWidth, screenHeight, "raylib [models] example - first person maze");

            // Define the camera to look into our 3d world
            Camera3D camera = new Camera3D(new Vector3(0.2f, 0.4f, 0.2f), new Vector3(0.0f, 0.0f, 0.0f), new Vector3(0.0f, 1.0f, 0.0f), 45.0f, CameraType.CAMERA_PERSPECTIVE);

            Image     imMap    = LoadImage("resources/cubicmap.png"); // Load cubicmap image (RAM)
            Texture2D cubicmap = LoadTextureFromImage(imMap);         // Convert image to texture to display (VRAM)
            Mesh      mesh     = GenMeshCubicmap(imMap, new Vector3(1.0f, 1.0f, 1.0f));
            Model     model    = LoadModelFromMesh(mesh);

            // NOTE: By default each cube is mapped to one part of texture atlas
            Texture2D texture = LoadTexture("resources/cubicmap_atlas.png");    // Load map texture

            // Set map diffuse texture
            Utils.SetMaterialTexture(ref model, 0, MAP_ALBEDO, ref texture);

            // Get map image data to be used for collision detection
            IntPtr mapPixelsData = GetImageData(imMap);

            UnloadImage(imMap);                                        // Unload image from RAM

            Vector3 mapPosition    = new Vector3(-16.0f, 0.0f, -8.0f); // Set model position
            Vector3 playerPosition = camera.position;                  // Set player position

            SetCameraMode(camera, CAMERA_FIRST_PERSON);                // Set camera mode

            SetTargetFPS(60);                                          // Set our game to run at 60 frames-per-second
            //--------------------------------------------------------------------------------------

            // Main game loop
            while (!WindowShouldClose())    // Detect window close button or ESC key
            {
                // Update
                //----------------------------------------------------------------------------------
                Vector3 oldCamPos = camera.position; // Store old camera position

                UpdateCamera(ref camera);            // Update camera

                // Check player collision (we simplify to 2D collision detection)
                Vector2 playerPos    = new Vector2(camera.position.X, camera.position.Z);
                float   playerRadius = 0.1f; // Collision radius (player is modelled as a cilinder for collision)

                int playerCellX = (int)(playerPos.X - mapPosition.X + 0.5f);
                int playerCellY = (int)(playerPos.Y - mapPosition.Z + 0.5f);

                // Out-of-limits security check
                if (playerCellX < 0)
                {
                    playerCellX = 0;
                }
                else if (playerCellX >= cubicmap.width)
                {
                    playerCellX = cubicmap.width - 1;
                }

                if (playerCellY < 0)
                {
                    playerCellY = 0;
                }
                else if (playerCellY >= cubicmap.height)
                {
                    playerCellY = cubicmap.height - 1;
                }

                // Check map collisions using image data and player position
                // TODO: Improvement: Just check player surrounding cells for collision
                for (int y = 0; y < cubicmap.height; y++)
                {
                    for (int x = 0; x < cubicmap.width; x++)
                    {
                        Color *mapPixels = (Color *)mapPixelsData.ToPointer();
                        if ((mapPixels[y * cubicmap.width + x].r == 255) &&       // Collision: white pixel, only check R channel
                            (CheckCollisionCircleRec(playerPos, playerRadius,
                                                     new Rectangle(mapPosition.X - 0.5f + x * 1.0f, mapPosition.Z - 0.5f + y * 1.0f, 1.0f, 1.0f))))
                        {
                            // Collision detected, reset camera position
                            camera.position = oldCamPos;
                        }
                    }
                }
                //----------------------------------------------------------------------------------

                // Draw
                //----------------------------------------------------------------------------------
                BeginDrawing();

                ClearBackground(RAYWHITE);

                BeginMode3D(camera);

                DrawModel(model, mapPosition, 1.0f, WHITE);                     // Draw maze map
                // DrawCubeV(playerPosition, new Vector3( 0.2f, 0.4f, 0.2f ), RED);  // Draw player

                EndMode3D();

                DrawTextureEx(cubicmap, new Vector2(GetScreenWidth() - cubicmap.width * 4 - 20, 20), 0.0f, 4.0f, WHITE);
                DrawRectangleLines(GetScreenWidth() - cubicmap.width * 4 - 20, 20, cubicmap.width * 4, cubicmap.height * 4, GREEN);

                // Draw player position radar
                DrawRectangle(GetScreenWidth() - cubicmap.width * 4 - 20 + playerCellX * 4, 20 + playerCellY * 4, 4, 4, RED);

                DrawFPS(10, 10);

                EndDrawing();
                //----------------------------------------------------------------------------------
            }

            // De-Initialization
            //--------------------------------------------------------------------------------------
            UnloadTexture(cubicmap);    // Unload cubicmap texture
            UnloadTexture(texture);     // Unload map texture
            UnloadModel(model);         // Unload map model

            CloseWindow();              // Close window and OpenGL context
            //--------------------------------------------------------------------------------------

            return(0);
        }
예제 #33
0
            public ImageData(int width, int height)
            {
                Stride = width * sizeof(Color);
                BufferSize = Stride * height;

                Data = (Color*)System.Runtime.InteropServices.Marshal.AllocHGlobal(BufferSize);
                Width = width;
                Height = height;

                widthSub1 = width - 1;
                heightSub1 = height - 1;
                lastValidAdress = Data + BufferSize - 1;
            }