RectpackSharp 1.2.0

dotnet add package RectpackSharp --version 1.2.0                
NuGet\Install-Package RectpackSharp -Version 1.2.0                
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="RectpackSharp" Version="1.2.0" />                
For projects that support PackageReference, copy this XML node into the project file to reference the package.
paket add RectpackSharp --version 1.2.0                
#r "nuget: RectpackSharp, 1.2.0"                
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
// Install RectpackSharp as a Cake Addin
#addin nuget:?package=RectpackSharp&version=1.2.0

// Install RectpackSharp as a Cake Tool
#tool nuget:?package=RectpackSharp&version=1.2.0                

RectpackSharp

NuGet

A rectangle packing library made in C# for .NET Standard.

Loosely based on the well-known C++ rectpack-2D library

This started as a side-project for the TrippyGL graphics library but as it grew, I decided to give it it's own repository and open the project for everyone to use.

The libary is quite small, so you can even just chuck the files directly onto your project if you don't want additional DLLs!

Usage

Once you have the library, just add using RectpackSharp to access the library types.

You will see the PackingRectangle type and the RectanglePacker static class.

Create a PackingRectangle for each rectangle you want and put them all in a single array. You can identify your rectangles using the PackingRectangle.Id field, as the order of the rectangles is not preserved. Afterwards, just call RectanglePacker.Pack. That's it!

PackingRectangle[] rectangles = new PackingRectangle[amount];
// Set the width and height of your rectangles
// ...

RectanglePacker.Pack(rectangles, out PackingRectangle bounds);
// All the rectangles in the array were assigned X and Y values. Bounds contains the width and height of the bin.

Specifying no extra parameters means the library will try all it's tools in order to find the best bin it can. If performance is important, you can trade space efficiency for performance with the optional parameters:

  • packingHint allows you to specify which methods to try when packing. Default is PackingHints.FindBest.
  • acceptableDensity makes the library stop searching once it found a solution with said density or better. Density is calculated as usedArea/binArea, so a density of 0 will yield the fastest solution it can, but possibly not an efficient one. Default is 1.
  • stepSize is by how much to vary the bin size after each try. Higher values might be faster but skip possibly better solutions. Default is 1.

So for example, if you know all your rectangles are squares, you might wanna try

RectanglePacker.Pack(rectangles, out PackingRectangle bounds, PackingHints.Width, 1, 1);

Pack also provides two additional arguments of type uint?, called maxBoundsWidth and maxBoundsHeight. These may be used to constrain the resulting bin to a given width and/or height. If, for example, you want a max bin height of 500, you may do something like this:

RectanglePacker.Pack(rectangles, out PackingRectangle bounds, PackingHints.FindBest, 1, 1, null, 500);

Need Help?

Feel free to come ask questions over at the TrippyGL Discord server!

Here's a test case where the rectangles have relatively similar dimentions. alternate text is missing from this package README image

In this test case, all the squares are the same size. Currently, the library doesn't handle the edges very well on these cases. alternate text is missing from this package README image

It also works like a charm for texture atlases or sprite sheets! alternate text is missing from this package README image alternate text is missing from this package README image

The most complicated cases are when the rectangles have very irregular dimentions, because there's no good answer to "what to put where". For these next test cases, we simply generated 512 or 2048 random rectangles (each side being from 20 to 200) and packed them. alternate text is missing from this package README image alternate text is missing from this package README image

Fuck it, here's 65536 random rectangles in a ~24k x 24k bin. alternate text is missing from this package README image

Product Compatible and additional computed target framework versions.
.NET net5.0 is compatible.  net5.0-windows was computed.  net6.0 was computed.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 was computed.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 was computed. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages

This package is not used by any NuGet packages.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last updated
1.2.0 1,415 1/9/2024
1.1.0 1,860 8/8/2023
1.0.2 1,175 7/20/2021
1.0.1 428 10/14/2020
1.0.0 419 10/14/2020

- Added Span support on .NET 5.0 and greater