Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Loading/Creating an image into SharpDX in a .NET program

I'm trying to use SharpDX to create a simple maze-like 2D program using DirectX.

To that end I want to create bitmaps that I can render on-screen for the walls, hallways, outside of the maze, etc.

However, I can't seem to figure out how to either load an existing image file into the Bitmap class in the SharpDX library, or how to create a new such Bitmap class from scratch.

Since all the classes are said to be mapped directly to DirectX types, I guess this just means I need to learn more DirectX, but I was hoping there was a simple example somewhere that could show me what I need to do.

If I have to construct a new Bitmap from scratch and draw to it, I can do that, it's not difficult getting the pixels I need right, however I can't even seem to figure out that part.

Does anyone have any experience with the SharpDX library and can give me some pointers?

like image 779
Lasse V. Karlsen Avatar asked Mar 01 '11 21:03

Lasse V. Karlsen


1 Answers

You should ask directly this question to the "Issue" tab on Sharpdx project, as I would be able to give you a quick response from there (you are lucky that I'm sometimes checking its usage from the net ;) ). If you were asking this officially, I could make an improvement to the library and keep a record of your request in the issue database.

Concerning your particular issue, it's not clear what kind of DirectX API you are using. I assume that you are using Direct2D?

If yes, there is no API to load directly a SharpDX.Direct2D1.Bitmap from a file (I will add this method to the API). I have just uploaded a bitmap sample that is performing this.

/// <summary>
/// Loads a Direct2D Bitmap from a file using System.Drawing.Image.FromFile(...)
/// </summary>
/// <param name="renderTarget">The render target.</param>
/// <param name="file">The file.</param>
/// <returns>A D2D1 Bitmap</returns>
public static Bitmap LoadFromFile(RenderTarget renderTarget, string file)
{
    // Loads from file using System.Drawing.Image
    using (var bitmap = (System.Drawing.Bitmap)System.Drawing.Image.FromFile(file))
    {
        var sourceArea = new System.Drawing.Rectangle(0, 0, bitmap.Width, bitmap.Height);
        var bitmapProperties = new BitmapProperties(new PixelFormat(Format.R8G8B8A8_UNorm, AlphaMode.Premultiplied));
        var size = new System.Drawing.Size(bitmap.Width, bitmap.Height);

        // Transform pixels from BGRA to RGBA
        int stride = bitmap.Width * sizeof(int);
        using (var tempStream = new DataStream(bitmap.Height * stride, true, true))
        {
            // Lock System.Drawing.Bitmap
            var bitmapData = bitmap.LockBits(sourceArea, ImageLockMode.ReadOnly, System.Drawing.Imaging.PixelFormat.Format32bppPArgb);

            // Convert all pixels 
            for (int y = 0; y < bitmap.Height; y++)
            {
                int offset = bitmapData.Stride*y;
                for (int x = 0; x < bitmap.Width; x++)
                {
                    // Not optimized 
                    byte B = Marshal.ReadByte(bitmapData.Scan0, offset++);
                    byte G = Marshal.ReadByte(bitmapData.Scan0, offset++);
                    byte R = Marshal.ReadByte(bitmapData.Scan0, offset++);
                    byte A = Marshal.ReadByte(bitmapData.Scan0, offset++);
                    int rgba = R | (G << 8) | (B << 16) | (A << 24);
                    tempStream.Write(rgba);
                }

            }
            bitmap.UnlockBits(bitmapData);
            tempStream.Position = 0;

            return new Bitmap(renderTarget, size, tempStream, stride, bitmapProperties);
        }
    }
}

As you said, SharpDX is giving access to the raw-low-level DirectX API (unlike for example XNA that is giving a higher level API), so you definitely need to understand how program raw DirectX in order to use SharpDX.

like image 110
Alexandre Mutel Avatar answered Nov 02 '22 15:11

Alexandre Mutel