From 9cad290a682d50375a5ddf9beaf4f8ce2d35a4ab Mon Sep 17 00:00:00 2001 From: Voomra Date: Thu, 12 Feb 2026 00:54:58 +0300 Subject: [PATCH] refac: PcxFile --- src/lwjake2/client/SCR.java | 20 +++---- src/lwjake2/qcommon/qfiles.java | 58 ------------------- src/lwjake2/render/lwjgl/Image.java | 25 +++++---- src/ru/di9/lwjake2/PcxFile.java | 87 +++++++++++++++++++++++++++++ 4 files changed, 110 insertions(+), 80 deletions(-) create mode 100644 src/ru/di9/lwjake2/PcxFile.java diff --git a/src/lwjake2/client/SCR.java b/src/lwjake2/client/SCR.java index 4a3d973..0ed6f0e 100644 --- a/src/lwjake2/client/SCR.java +++ b/src/lwjake2/client/SCR.java @@ -27,11 +27,11 @@ import lwjake2.qcommon.Cvar; import lwjake2.qcommon.FS; import lwjake2.qcommon.MSG; import lwjake2.qcommon.SZ; -import lwjake2.qcommon.qfiles; import lwjake2.sound.S; import lwjake2.sys.Timer; import lwjake2.util.Lib; import lwjake2.util.Vargs; +import ru.di9.lwjake2.PcxFile; import java.awt.Dimension; import java.nio.ByteBuffer; @@ -1366,7 +1366,7 @@ public final class SCR extends Globals { * LoadPCX */ static int LoadPCX(String filename, byte[] palette, cinematics_t cin) { - qfiles.pcx_t pcx; + PcxFile pcx; // load the file ByteBuffer raw = FS.LoadMappedFile(filename); @@ -1378,18 +1378,18 @@ public final class SCR extends Globals { } // parse the PCX file - pcx = new qfiles.pcx_t(raw); + pcx = new PcxFile(raw); - if (pcx.manufacturer != 0x0a || pcx.version != 5 || pcx.encoding != 1 - || pcx.bits_per_pixel != 8 || pcx.xmax >= 640 - || pcx.ymax >= 480) { + if (pcx.getManufacturer() != 0x0a || pcx.getVersion() != 5 || pcx.getEncoding() != 1 + || pcx.getBitsPerPixel() != 8 || pcx.getXmax() >= 640 + || pcx.getYmax() >= 480) { VID.Printf(Defines.PRINT_ALL, "Bad pcx file " + filename + '\n'); return 0; } - int width = pcx.xmax - pcx.xmin + 1; - int height = pcx.ymax - pcx.ymin + 1; + int width = pcx.getXmax() - pcx.getXmin() + 1; + int height = pcx.getYmax() - pcx.getYmin() + 1; byte[] pix = new byte[width * height]; @@ -1418,11 +1418,11 @@ public final class SCR extends Globals { for (y = 0; y < height; y++) { for (x = 0; x < width;) { - dataByte = pcx.data.get(p++); + dataByte = pcx.getData().get(p++); if ((dataByte & 0xC0) == 0xC0) { runLength = dataByte & 0x3F; - dataByte = pcx.data.get(p++); + dataByte = pcx.getData().get(p++); // write runLength pixel while (runLength-- > 0) { pix[count++] = dataByte; diff --git a/src/lwjake2/qcommon/qfiles.java b/src/lwjake2/qcommon/qfiles.java index 8f97858..dee8e7b 100644 --- a/src/lwjake2/qcommon/qfiles.java +++ b/src/lwjake2/qcommon/qfiles.java @@ -47,64 +47,6 @@ public class qfiles { /* ======================================================================== - PCX files are used for as many images as possible - - ======================================================================== - */ - public static class pcx_t { - - // size of byte arrays - static final int PALETTE_SIZE = 48; - static final int FILLER_SIZE = 58; - - public byte manufacturer; - public byte version; - public byte encoding; - public byte bits_per_pixel; - public int xmin, ymin, xmax, ymax; // unsigned short - public int hres, vres; // unsigned short - public byte[] palette; //unsigned byte; size 48 - public byte reserved; - public byte color_planes; - public int bytes_per_line; // unsigned short - public int palette_type; // unsigned short - public byte[] filler; // size 58 - public ByteBuffer data; //unbounded data - - public pcx_t(byte[] dataBytes) { - this(ByteBuffer.wrap(dataBytes)); - } - - public pcx_t(ByteBuffer b) { - // is stored as little endian - b.order(ByteOrder.LITTLE_ENDIAN); - - // fill header - manufacturer = b.get(); - version = b.get(); - encoding = b.get(); - bits_per_pixel = b.get(); - xmin = b.getShort() & 0xffff; - ymin = b.getShort() & 0xffff; - xmax = b.getShort() & 0xffff; - ymax = b.getShort() & 0xffff; - hres = b.getShort() & 0xffff; - vres = b.getShort() & 0xffff; - b.get(palette = new byte[PALETTE_SIZE]); - reserved = b.get(); - color_planes = b.get(); - bytes_per_line = b.getShort() & 0xffff; - palette_type = b.getShort() & 0xffff; - b.get(filler = new byte[FILLER_SIZE]); - - // fill data - data = b.slice(); - } - } - - /* - ======================================================================== - TGA files are used for sky planes ======================================================================== diff --git a/src/lwjake2/render/lwjgl/Image.java b/src/lwjake2/render/lwjgl/Image.java index 0374fd7..13fd8be 100644 --- a/src/lwjake2/render/lwjgl/Image.java +++ b/src/lwjake2/render/lwjgl/Image.java @@ -44,6 +44,7 @@ import org.lwjgl.opengl.ARBImaging; import org.lwjgl.opengl.ARBMultitexture; import org.lwjgl.opengl.EXTSharedTexturePalette; import org.lwjgl.opengl.GL11; +import ru.di9.lwjake2.PcxFile; /** * Image @@ -445,7 +446,7 @@ public abstract class Image extends Main { ============== */ byte[] LoadPCX(String filename, byte[][] palette, Dimension dim) { - qfiles.pcx_t pcx; + PcxFile pcx; // // load the file @@ -460,21 +461,21 @@ public abstract class Image extends Main { // // parse the PCX file // - pcx = new qfiles.pcx_t(raw); + pcx = new PcxFile(ByteBuffer.wrap(raw)); - if (pcx.manufacturer != 0x0a - || pcx.version != 5 - || pcx.encoding != 1 - || pcx.bits_per_pixel != 8 - || pcx.xmax >= 640 - || pcx.ymax >= 480) { + if (pcx.getManufacturer() != 0x0a + || pcx.getVersion() != 5 + || pcx.getEncoding() != 1 + || pcx.getBitsPerPixel() != 8 + || pcx.getXmax() >= 640 + || pcx.getYmax() >= 480) { VID.Printf(Defines.PRINT_ALL, "Bad pcx file " + filename + '\n'); return null; } - int width = pcx.xmax - pcx.xmin + 1; - int height = pcx.ymax - pcx.ymin + 1; + int width = pcx.getXmax() - pcx.getXmin() + 1; + int height = pcx.getYmax() - pcx.getYmin() + 1; byte[] pix = new byte[width * height]; @@ -499,11 +500,11 @@ public abstract class Image extends Main { for (y = 0; y < height; y++) { for (x = 0; x < width;) { - dataByte = pcx.data.get(); + dataByte = pcx.getData().get(); if ((dataByte & 0xC0) == 0xC0) { runLength = dataByte & 0x3F; - dataByte = pcx.data.get(); + dataByte = pcx.getData().get(); // write runLength pixel while (runLength-- > 0) { pix[count++] = dataByte; diff --git a/src/ru/di9/lwjake2/PcxFile.java b/src/ru/di9/lwjake2/PcxFile.java new file mode 100644 index 0000000..d3072fc --- /dev/null +++ b/src/ru/di9/lwjake2/PcxFile.java @@ -0,0 +1,87 @@ +package ru.di9.lwjake2; + +import java.nio.ByteBuffer; +import java.nio.ByteOrder; + +public class PcxFile { + private static final int PALETTE_SIZE = 48; + private static final int FILLER_SIZE = 58; + + private final byte manufacturer; + private final byte version; + private final byte encoding; + private final byte bits_per_pixel; + + private final int xmin; // unsigned short + private final int xmax; // unsigned short + private final int ymax; // unsigned short + private final int ymin; // unsigned short + + private final ByteBuffer data; //unbounded data + + public PcxFile(ByteBuffer buffer) { + // is stored as little endian + buffer.order(ByteOrder.LITTLE_ENDIAN); + + // fill header + manufacturer = buffer.get(); + version = buffer.get(); + encoding = buffer.get(); + bits_per_pixel = buffer.get(); + xmin = buffer.getShort() & 0xffff; + ymin = buffer.getShort() & 0xffff; + xmax = buffer.getShort() & 0xffff; + ymax = buffer.getShort() & 0xffff; + + // Skip bytes + buffer.position(buffer.position() + + 2 // unsigned short 'hres' + + 2 // unsigned short 'vres' + + PALETTE_SIZE // array unsigned bytes 'palette' + + 1 // byte 'reserved' + + 1 // byte 'color_planes' + + 2 // unsigned short 'bytes_per_line' + + 2 // unsigned short 'palette_type' + + FILLER_SIZE // array unsigned bytes 'filler' + ); + + // fill data + data = buffer.slice(); + } + + public byte getManufacturer() { + return manufacturer; + } + + public byte getVersion() { + return version; + } + + public byte getEncoding() { + return encoding; + } + + public byte getBitsPerPixel() { + return bits_per_pixel; + } + + public int getXmax() { + return xmax; + } + + public int getYmax() { + return ymax; + } + + public int getXmin() { + return xmin; + } + + public int getYmin() { + return ymin; + } + + public ByteBuffer getData() { + return data; + } +}