jingwood / d2dlib

A .NET library for hardware-accelerated, high performance, immediate mode rendering via Direct2D.
MIT License
245 stars 43 forks source link

Usage of System.Numerics.VectorX #64

Closed nikeee closed 1 year ago

nikeee commented 3 years ago

I love this library.

One thing I noticed: I often need to convert the structs D2DPoint to Vector2. One reason being that VectorX structs have operator overloading. The other reason is that they support JIT intrinsics and take advantage of SIMD extensions of the CPU, so math operations are much faster with them.

Is it possible to use them directly with this library? Vector2 is basically this struct:

struct Vector2 {
    float x;
    float y;
}

Notice: It does not have the SequentialLayout attribute, so it might be padded during runtime. However, the .NET docs state:

C#, Visual Basic, and C++ compilers apply the Sequential layout value to structures by default. For classes, you must apply the LayoutKind.Sequential value explicitly.

To get an idea, this is the Vector2 implementation: https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/Vector2.cs

If these structs are ABI compatible, one could just pass them instead of D2DPoint etc. Ist would eliminate conversions as well as increase performance due to hardware acceleration.

Edit: Matrix3x2 also seems that it has the same binary layout as the one in System.Numerics: https://github.com/dotnet/runtime/blob/01b7e73cd378145264a7cb7a09365b41ed42b240/src/libraries/System.Private.CoreLib/src/System/Numerics/Matrix3x2.cs#L82

Any chances on something in that direction?

jingwood commented 3 years ago

Hi @nikeee!

Thanks for the suggestions! I think it's a nice idea!

The D2DPoint was designed to keep the same layout compared to the structure defined on C++ side. So it's the first goal is to keep API calling is safe and fast, then the calculation performance. But maybe the Vector2 works well also, I will have a check.

You may consider performing calculations using System.Numerics.* then pass the result to D2DLib using D2DPoint etc. I think there is also a good idea to make more implicit conversion available between System.Numerics.* and D2DPoint classes.

@drewnoakes Any suggestions will be helpful!

drewnoakes commented 3 years ago

Using the System.Numerics types seems like a good idea.

Vector2 appears to be an intrinsic: https://github.com/dotnet/runtime/blob/9cb0ab915e971f6408aae662a8dec7fcf365930e/src/libraries/System.Private.CoreLib/src/System/Numerics/Vector2.cs#L18-L25

I doubt the layout would change though. It looks identical to D2DPoint. Try it and see I guess.

Implicit conversions can be convenient but can also be suprising. They can also result in redundant copying of values, compared to reusing Vector2.

nikeee commented 3 years ago

I tried this one out (with Vector2 and Matrix3x2) and it works pretty well: https://github.com/nikeee/nud2dlib

nikeee commented 1 year ago

Is it possible to tackle this or find any solution?

I see that the library was ported to .NET 6, which was one of my core goals for nud2dlib (though at that time, it was .NET 5).

They both do basically the same, the only difference for now being that nud2dlib uses Vector2/Vector3 and Matrix3x2 in in some places where D2DPoint or D2DSize is used.

However, the projects start to diverge in some ways. For example, d2dlib recently enhanced the text rendering capabilities. While I'm fine with backporting stuff, I'd also like to give back some of my efforts (like #30, #65 and #82).

One non-breaking solution would be to add a some overloads to the functions recieving D2DPoints. This wouldn't require automatic/implicit conversions from Vector2 to D2DPoint. The C wrapper library could remain the same, since both structs are binary compatible.

I that something you'd see in the scope of this project?

drewnoakes commented 1 year ago

@jingwood would it be feasible to remove D2DPoint altogether, and use Vector2 instead?

jingwood commented 1 year ago

@nikeee @drewnoakes OK, use System.Numerics.* from the next version!

jingwood commented 1 year ago

@nikeee @drewnoakes If possible please have a review for #97

nikeee commented 1 year ago

Very cool! I'll do a review tomorrow! :)

drewnoakes commented 1 year ago

Fixed in #97.