Skip to content

Commit

Permalink
Merge pull request #31 from C7-Game/FLCPerformance
Browse files Browse the repository at this point in the history
FLC Import Performance
  • Loading branch information
Andrew Jones authored Nov 29, 2021
2 parents 89f4db1 + fc51efa commit b711c0a
Show file tree
Hide file tree
Showing 4 changed files with 76 additions and 12 deletions.
1 change: 1 addition & 0 deletions C7/C7.csproj
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
<Project Sdk="Godot.NET.Sdk/3.3.0">
<PropertyGroup>
<TargetFramework>net472</TargetFramework>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\ConvertCiv3Media\ConvertCiv3Media.csproj" />
Expand Down
75 changes: 63 additions & 12 deletions C7/Civ3Unit/Civ3Unit.cs
Original file line number Diff line number Diff line change
Expand Up @@ -85,25 +85,76 @@ public override void Move(Direction direction, float speed = (float)0.6) {

// TODO: This is mostly duplicated in/from PCXToGodot.cs, but special indexes
// handled differently. Probably needs combining and refactoring
public static Image ByteArrayToImage(byte[] ba, byte[,] palette, int width, int height, int[] transparent = null, bool shadows = false) {
public static Image ByteArrayToImage(byte[] colorIndices, byte[,] palette, int width, int height, int[] transparent = null, bool shadows = false) {
Image OutImage = new Image();
OutImage.Create(width, height, false, Image.Format.Rgba8);
OutImage.Lock();
for (int i = 0; i < width * height; i++)
{
if (shadows && ba[i] > 239) {
// using black and transparency
OutImage.SetPixel(i % width, i / width, Color.Color8(0,0,0, (byte)((255 -ba[i]) * 16)));
// using the palette color but adding transparency
// OutImage.SetPixel(i % width, i / width, Color.Color8(palette[ba[i],0], palette[ba[i],1], palette[ba[i],2], (byte)((255 -ba[i]) * 16)));
} else {
OutImage.SetPixel(i % width, i / width, Color.Color8(palette[ba[i],0], palette[ba[i],1], palette[ba[i],2], ba[i] == 255 ? (byte)0 : (byte)255));
}
}
byte[] bmpBuffer = getBmpBuffer(colorIndices, palette, width, height, transparent, shadows);
OutImage.LoadBmpFromBuffer(bmpBuffer);
OutImage.Unlock();

return OutImage;
}

public static unsafe byte[] getBmpBuffer(byte[] colorIndices, byte[,] palette, int width, int height, int[] transparent = null, bool shadows = false) {

int bmpSize = width * height * 4 + 54; //54 = Windows 3 BMP header size.
byte[] bmpBuffer = new byte[bmpSize];
fixed (byte* fPtr = bmpBuffer) {
//BMP header. This is a mix of byte, short, and int. Probably a cleaner way to do this, but my C is rusty.
byte* bPtr = fPtr;
int* iPtr;
short* sPtr;
bPtr[0] = 66; //B
bPtr[1] = 77; //M
bPtr+=2;
iPtr = (int*)bPtr;
iPtr[0] = bmpSize; //size of BMP file in bytes
iPtr[1] = 0; //reserved, two shorts
iPtr[2] = 54; //offset of image data from start of file
iPtr[3] = 40; //size of Windows 3 BMP header
iPtr[4] = width;
iPtr[5] = height;
bPtr+=24; //6 * 4
sPtr = (short*)bPtr;
sPtr[0] = 1; //num color planes
sPtr[1] = 32; //bit depth. we want 32-bit with alpha
bPtr+=4;
iPtr = (int*)bPtr;
iPtr[0] = 0; //compression - none. Godot doesn't support compression
iPtr[1] = bmpSize - 54; //size, without headers
iPtr[2] = 0; //horizontal resolution. ignored.
iPtr[3] = 0; //vertical resolution. ignored.
iPtr[4] = 0; //num colors in palette. not relevant for 32-bit
iPtr[5] = 0; //num important colors in palette. not relevant.
bPtr+=24; //6 * 4
iPtr = (int*)bPtr;
//Ready for image data

int c = 0;
//The BMP data is stored bottom-to-top, whereas our data is top-to-bottom
//Thus we'll use c to calculate the index for each row
for (int y = height - 1; y > -1; y--)
{
c = width * y;
for (int x = 0; x < width; x++)
{
if (shadows && colorIndices[c] > 239) {
// using black and transparency
iPtr[0] = ((255 - colorIndices[c]) << 4) << 24;
// using the palette color but adding transparency
// OutImage.SetPixel(i % width, i / width, Color.Color8(palette[ba[i],0], palette[ba[i],1], palette[ba[i],2], (byte)((255 -ba[i]) * 16)));
} else {
// A, R, G, B
iPtr[0] = ((byte)255) << 24 | palette[colorIndices[c], 0] << 16 | palette[colorIndices[c], 1] << 8 | palette[colorIndices[c], 2] << 0;
}
c++;
iPtr++;
}
}
}
return bmpBuffer;
}
}
// This is just to add some movement to an AnimatedSprite
public class MovingSprite : AnimatedSprite {
Expand Down
4 changes: 4 additions & 0 deletions C7/project.godot
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,10 @@ window/size/height=768

theme/custom="res://C7Theme.tres"

[network]

limits/debugger_stdout/max_chars_per_second=16384

[rendering]

environment/default_environment="res://default_env.tres"
8 changes: 8 additions & 0 deletions ConvertCiv3Media/ReadFlic.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,12 @@ public class Flic {
public int Width = 0;
public int Height = 0;

private string path;

// constructors
public Flic(){}
public Flic(string path) {
this.path = path;
this.Load(path);
}
public void Load(string path) {
Expand Down Expand Up @@ -189,5 +192,10 @@ public void Load(string path) {
Offset += RingChunkLength;
}
}

public override string ToString()
{
return "FLIC " + this.path;
}
}
}

0 comments on commit b711c0a

Please sign in to comment.