2025-06-30 22:57:40 +02:00

129 lines
4.1 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading.Tasks;
using SDL2;
namespace testdrid.SdlWrapper
{
internal class Surface : IDisposable
{
private Surface() {}
internal Surface(IntPtr pointer)
{
IntPointer = pointer;
}
public static Surface LoadFromBMP(string filename)
{
FileInfo fi = new FileInfo(filename);
if (!fi.Exists)
throw new FileNotFoundException(filename);
Surface result = new Surface();
result.IntPointer = SDL.SDL_LoadBMP(fi.FullName);
if (result.IntPointer == IntPtr.Zero)
throw SdlException.GenerateException();
return result;
}
public static Surface ImageLoad(string filename)
{
FileInfo fi = new FileInfo(filename);
if (!fi.Exists)
throw new FileNotFoundException(filename);
Surface result = new Surface();
result.IntPointer = SDL_image.IMG_Load(fi.FullName);
if (result.IntPointer == IntPtr.Zero)
throw SdlException.GenerateException();
return result;
}
public static Surface ImageLoadFromPtr(byte[] buffer)
{
IntPtr unmanagedPointer = Marshal.AllocHGlobal(buffer.Length);
Marshal.Copy(buffer, 0, unmanagedPointer, buffer.Length);
IntPtr sdlRwFromMem = SDL.SDL_RWFromMem(unmanagedPointer, buffer.Length);
//IMG_Load_RW
Surface result = new Surface();
result.IntPointer = SDL_image.IMG_Load_RW(sdlRwFromMem, 1);
if (result.IntPointer == IntPtr.Zero)
throw SdlException.GenerateException();
Marshal.FreeHGlobal(unmanagedPointer);
return result;
}
public static Surface Create(int width, int height)
{
uint rmask, gmask, bmask, amask;
if (!BitConverter.IsLittleEndian)
{
rmask = 0xff000000;
gmask = 0x00ff0000;
bmask = 0x0000ff00;
amask = 0x000000ff;
}
else
{
rmask = 0x000000ff;
gmask = 0x0000ff00;
bmask = 0x00ff0000;
amask = 0xff000000;
}
Surface result = new Surface();
result.IntPointer = SDL.SDL_CreateRGBSurface(0, width, height, 32, rmask, gmask, bmask, amask);
if (result.IntPointer == IntPtr.Zero)
throw SdlException.GenerateException();
return result;
}
internal IntPtr IntPointer { get; set; }
public void SetColorKey(int flag, uint key)
{
SDL.SDL_SetColorKey(IntPointer, flag, key);
}
public void Dispose()
{
SDL.SDL_FreeSurface(IntPointer);
IntPointer = IntPtr.Zero;
}
public void Fill(uint color)
{
int sdlFillRect = SDL.SDL_FillRect(IntPointer, IntPtr.Zero, color);
if (sdlFillRect != 0)
{
throw SdlException.GenerateException();
}
}
public void SetPixel(int x, int y, byte r, byte g, byte b)
{
SDL.SDL_Surface sdlSurface = Marshal.PtrToStructure<SDL.SDL_Surface>(IntPointer);
SDL.SDL_PixelFormat sdlPixelFormat = Marshal.PtrToStructure<SDL.SDL_PixelFormat>(sdlSurface.format);
int offset = (sdlPixelFormat.BytesPerPixel * sdlSurface.w) * y;
offset += (sdlPixelFormat.BytesPerPixel * x);
Marshal.WriteByte(sdlSurface.pixels, offset + 0, r);
Marshal.WriteByte(sdlSurface.pixels, offset + 1, g);
Marshal.WriteByte(sdlSurface.pixels, offset + 2, b);
Marshal.WriteByte(sdlSurface.pixels, offset + 3, 0xff);
}
public SDL2.SDL.SDL_Surface GetSurfaceData()
{
SDL.SDL_Surface ptrToStructure = Marshal.PtrToStructure<SDL.SDL_Surface>(IntPointer);
return ptrToStructure;
}
}
}