Clean up unused reading of .wz and .img files
This server only reads from .xml files
This commit is contained in:
@@ -21,24 +21,14 @@
|
|||||||
*/
|
*/
|
||||||
package provider;
|
package provider;
|
||||||
|
|
||||||
import provider.wz.WZFile;
|
|
||||||
import provider.wz.WZFiles;
|
import provider.wz.WZFiles;
|
||||||
import provider.wz.XMLWZFile;
|
import provider.wz.XMLWZFile;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public class MapleDataProviderFactory {
|
public class MapleDataProviderFactory {
|
||||||
private static MapleDataProvider getWZ(File in) {
|
private static MapleDataProvider getWZ(File in) {
|
||||||
if (in.getName().toLowerCase().endsWith("wz") && !in.isDirectory()) {
|
return new XMLWZFile(in);
|
||||||
try {
|
|
||||||
return new WZFile(in, false);
|
|
||||||
} catch (IOException e) {
|
|
||||||
throw new RuntimeException("Loading WZ File failed", e);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return new XMLWZFile(in);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static MapleDataProvider getDataProvider(WZFiles in) {
|
public static MapleDataProvider getDataProvider(WZFiles in) {
|
||||||
|
|||||||
@@ -1,70 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import javax.imageio.ImageIO;
|
|
||||||
import provider.MapleCanvas;
|
|
||||||
|
|
||||||
public class FileStoredPngMapleCanvas implements MapleCanvas {
|
|
||||||
private File file;
|
|
||||||
private int width;
|
|
||||||
private int height;
|
|
||||||
private BufferedImage image;
|
|
||||||
|
|
||||||
public FileStoredPngMapleCanvas(int width, int height, File fileIn) {
|
|
||||||
this.width = width;
|
|
||||||
this.height = height;
|
|
||||||
this.file = fileIn;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getHeight() {
|
|
||||||
return height;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getWidth() {
|
|
||||||
return width;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public BufferedImage getImage() {
|
|
||||||
loadImageIfNecessary();
|
|
||||||
return image;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void loadImageIfNecessary() {
|
|
||||||
if (image == null) {
|
|
||||||
try {
|
|
||||||
image = ImageIO.read(file);
|
|
||||||
// replace the dimensions loaded from the wz by the REAL dimensions from the image - should be equal tho
|
|
||||||
width = image.getWidth();
|
|
||||||
height = image.getHeight();
|
|
||||||
} catch (IOException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,39 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
public class ImgMapleSound {
|
|
||||||
private int dataLength, offset;
|
|
||||||
|
|
||||||
public ImgMapleSound(int dataLength, int offset) {
|
|
||||||
this.dataLength = dataLength;
|
|
||||||
this.offset = offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getDataLength() {
|
|
||||||
return dataLength;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getOffset() {
|
|
||||||
return offset;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,82 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import tools.data.input.GenericLittleEndianAccessor;
|
|
||||||
import tools.data.input.InputStreamByteStream;
|
|
||||||
import tools.data.input.LittleEndianAccessor;
|
|
||||||
|
|
||||||
import java.io.BufferedInputStream;
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.FileInputStream;
|
|
||||||
import java.io.FileNotFoundException;
|
|
||||||
import java.util.*;
|
|
||||||
|
|
||||||
public class ListWZFile {
|
|
||||||
private LittleEndianAccessor lea;
|
|
||||||
private List<String> entries = new ArrayList<>();
|
|
||||||
private static Collection<String> modernImgs = new HashSet<>();
|
|
||||||
|
|
||||||
public static byte[] xorBytes(byte[] a, byte[] b) {
|
|
||||||
byte[] wusched = new byte[a.length];
|
|
||||||
for (int i = 0; i < a.length; i++) {
|
|
||||||
wusched[i] = (byte) (a[i] ^ b[i]);
|
|
||||||
}
|
|
||||||
return wusched;
|
|
||||||
}
|
|
||||||
|
|
||||||
public ListWZFile(File listwz) throws FileNotFoundException {
|
|
||||||
lea = new GenericLittleEndianAccessor(new InputStreamByteStream(new BufferedInputStream(new FileInputStream(listwz))));
|
|
||||||
while (lea.available() > 0) {
|
|
||||||
int l = lea.readInt() * 2;
|
|
||||||
byte[] chunk = new byte[l];
|
|
||||||
for (int i = 0; i < chunk.length; i++) {
|
|
||||||
chunk[i] = lea.readByte();
|
|
||||||
}
|
|
||||||
lea.readChar();
|
|
||||||
final String value = String.valueOf(WZTool.readListString(chunk));
|
|
||||||
entries.add(value);
|
|
||||||
}
|
|
||||||
entries = Collections.unmodifiableList(entries);
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<String> getEntries() {
|
|
||||||
return entries;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void init() {
|
|
||||||
final String listWz = System.getProperty("listwz");
|
|
||||||
if (listWz != null) {
|
|
||||||
ListWZFile listwz;
|
|
||||||
try {
|
|
||||||
listwz = new ListWZFile(WZFiles.LIST.getFile());
|
|
||||||
modernImgs = new HashSet<>(listwz.getEntries());
|
|
||||||
} catch (FileNotFoundException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static boolean isModernImgFile(String path) {
|
|
||||||
return modernImgs.contains(path);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,151 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import java.awt.Point;
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.awt.image.DataBuffer;
|
|
||||||
import java.awt.image.DataBufferByte;
|
|
||||||
import java.awt.image.PixelInterleavedSampleModel;
|
|
||||||
import java.awt.image.Raster;
|
|
||||||
import java.awt.image.SampleModel;
|
|
||||||
import java.awt.image.WritableRaster;
|
|
||||||
import java.util.zip.DataFormatException;
|
|
||||||
import java.util.zip.Inflater;
|
|
||||||
import provider.MapleCanvas;
|
|
||||||
|
|
||||||
public class PNGMapleCanvas implements MapleCanvas {
|
|
||||||
private static final int[] ZAHLEN = new int[]{2, 1, 0, 3};
|
|
||||||
private int height;
|
|
||||||
private int width;
|
|
||||||
private int dataLength;
|
|
||||||
private int format;
|
|
||||||
private byte[] data;
|
|
||||||
|
|
||||||
public PNGMapleCanvas(int width, int height, int dataLength, int format, byte[] data) {
|
|
||||||
super();
|
|
||||||
this.height = height;
|
|
||||||
this.width = width;
|
|
||||||
this.dataLength = dataLength;
|
|
||||||
this.format = format;
|
|
||||||
this.data = data;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getHeight() {
|
|
||||||
return height;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getWidth() {
|
|
||||||
return width;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getFormat() {
|
|
||||||
return format;
|
|
||||||
}
|
|
||||||
|
|
||||||
private byte[] getData() {
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public BufferedImage getImage() {
|
|
||||||
int sizeUncompressed = 0;
|
|
||||||
int size8888 = 0;
|
|
||||||
int maxWriteBuf = 2;
|
|
||||||
int maxHeight = 3;
|
|
||||||
byte[] writeBuf = new byte[maxWriteBuf];
|
|
||||||
@SuppressWarnings ("unused")
|
|
||||||
byte[] rowPointers = new byte[maxHeight];
|
|
||||||
switch (getFormat()) {
|
|
||||||
case 1:
|
|
||||||
case 513:
|
|
||||||
sizeUncompressed = getHeight() * getWidth() * 4;
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
sizeUncompressed = getHeight() * getWidth() * 8;
|
|
||||||
break;
|
|
||||||
case 517:
|
|
||||||
sizeUncompressed = getHeight() * getWidth() / 128;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
size8888 = getHeight() * getWidth() * 8;
|
|
||||||
if (size8888 > maxWriteBuf) {
|
|
||||||
maxWriteBuf = size8888;
|
|
||||||
writeBuf = new byte[maxWriteBuf];
|
|
||||||
}
|
|
||||||
if (getHeight() > maxHeight) {
|
|
||||||
maxHeight = getHeight();
|
|
||||||
rowPointers = new byte[maxHeight];
|
|
||||||
}
|
|
||||||
Inflater dec = new Inflater();
|
|
||||||
dec.setInput(getData(), 0, dataLength);
|
|
||||||
int declen = 0;
|
|
||||||
byte[] uc = new byte[sizeUncompressed];
|
|
||||||
try {
|
|
||||||
declen = dec.inflate(uc);
|
|
||||||
} catch (DataFormatException ex) {
|
|
||||||
throw new RuntimeException("zlib fucks", ex);
|
|
||||||
}
|
|
||||||
dec.end();
|
|
||||||
if (getFormat() == 1) {
|
|
||||||
for (int i = 0; i < sizeUncompressed; i++) {
|
|
||||||
byte low = (byte) (uc[i] & 0x0F);
|
|
||||||
byte high = (byte) (uc[i] & 0xF0);
|
|
||||||
writeBuf[(i << 1)] = (byte) (((low << 4) | low) & 0xFF);
|
|
||||||
writeBuf[(i << 1) + 1] = (byte) (high | ((high >>> 4) & 0xF));
|
|
||||||
}
|
|
||||||
} else if (getFormat() == 2) {
|
|
||||||
writeBuf = uc;
|
|
||||||
} else if (getFormat() == 513) {
|
|
||||||
for (int i = 0; i < declen; i += 2) {
|
|
||||||
byte bBits = (byte) ((uc[i] & 0x1F) << 3);
|
|
||||||
byte gBits = (byte) (((uc[i + 1] & 0x07) << 5) | ((uc[i] & 0xE0) >> 3));
|
|
||||||
byte rBits = (byte) (uc[i + 1] & 0xF8);
|
|
||||||
writeBuf[(i << 1)] = (byte) (bBits | (bBits >> 5));
|
|
||||||
writeBuf[(i << 1) + 1] = (byte) (gBits | (gBits >> 6));
|
|
||||||
writeBuf[(i << 1) + 2] = (byte) (rBits | (rBits >> 5));
|
|
||||||
writeBuf[(i << 1) + 3] = (byte) 0xFF;
|
|
||||||
}
|
|
||||||
} else if (getFormat() == 517) {
|
|
||||||
byte b = 0x00;
|
|
||||||
int pixelIndex = 0;
|
|
||||||
for (int i = 0; i < declen; i++) {
|
|
||||||
for (int j = 0; j < 8; j++) {
|
|
||||||
b = (byte) (((uc[i] & (0x01 << (7 - j))) >> (7 - j)) * 255);
|
|
||||||
for (int k = 0; k < 16; k++) {
|
|
||||||
pixelIndex = (i << 9) + (j << 6) + k * 2;
|
|
||||||
writeBuf[pixelIndex] = b;
|
|
||||||
writeBuf[pixelIndex + 1] = b;
|
|
||||||
writeBuf[pixelIndex + 2] = b;
|
|
||||||
writeBuf[pixelIndex + 3] = (byte) 0xFF;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
DataBufferByte imgData = new DataBufferByte(writeBuf, sizeUncompressed);
|
|
||||||
SampleModel sm = new PixelInterleavedSampleModel(DataBuffer.TYPE_BYTE, getWidth(), getHeight(), 4, getWidth() * 4, ZAHLEN);
|
|
||||||
WritableRaster imgRaster = Raster.createWritableRaster(sm, imgData, new Point(0, 0));
|
|
||||||
BufferedImage aa = new BufferedImage(getWidth(), getHeight(), BufferedImage.TYPE_INT_ARGB);
|
|
||||||
aa.setData(imgRaster);
|
|
||||||
return aa;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,146 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import provider.MapleData;
|
|
||||||
import provider.MapleDataDirectoryEntry;
|
|
||||||
import provider.MapleDataFileEntry;
|
|
||||||
import provider.MapleDataProvider;
|
|
||||||
import tools.data.input.*;
|
|
||||||
|
|
||||||
import java.io.*;
|
|
||||||
|
|
||||||
public class WZFile implements MapleDataProvider {
|
|
||||||
static {
|
|
||||||
ListWZFile.init();
|
|
||||||
}
|
|
||||||
private File wzfile;
|
|
||||||
private LittleEndianAccessor lea;
|
|
||||||
private SeekableLittleEndianAccessor slea;
|
|
||||||
private int headerSize;
|
|
||||||
private WZDirectoryEntry root;
|
|
||||||
private boolean provideImages;
|
|
||||||
private int cOffset;
|
|
||||||
|
|
||||||
public WZFile(File wzfile, boolean provideImages) throws IOException {
|
|
||||||
this.wzfile = wzfile;
|
|
||||||
lea = new GenericLittleEndianAccessor(new InputStreamByteStream(new BufferedInputStream(new FileInputStream(wzfile))));
|
|
||||||
RandomAccessFile raf = new RandomAccessFile(wzfile, "r");
|
|
||||||
slea = new GenericSeekableLittleEndianAccessor(new RandomAccessByteStream(raf));
|
|
||||||
root = new WZDirectoryEntry(wzfile.getName(), 0, 0, null);
|
|
||||||
this.provideImages = provideImages;
|
|
||||||
load();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void load() throws IOException {
|
|
||||||
lea.readAsciiString(4);
|
|
||||||
lea.readInt();
|
|
||||||
lea.readInt();
|
|
||||||
headerSize = lea.readInt();
|
|
||||||
lea.readNullTerminatedAsciiString();
|
|
||||||
lea.readShort();
|
|
||||||
parseDirectory(root);
|
|
||||||
cOffset = (int) lea.getBytesRead();
|
|
||||||
getOffsets(root);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void getOffsets(MapleDataDirectoryEntry dir) {
|
|
||||||
for (MapleDataFileEntry file : dir.getFiles()) {
|
|
||||||
file.setOffset(cOffset);
|
|
||||||
cOffset += file.getSize();
|
|
||||||
}
|
|
||||||
for (MapleDataDirectoryEntry sdir : dir.getSubdirectories()) {
|
|
||||||
getOffsets(sdir);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void parseDirectory(WZDirectoryEntry dir) {
|
|
||||||
int entries = WZTool.readValue(lea);
|
|
||||||
for (int i = 0; i < entries; i++) {
|
|
||||||
byte marker = lea.readByte();
|
|
||||||
String name = null;
|
|
||||||
int size, checksum;
|
|
||||||
switch (marker) {
|
|
||||||
case 0x02:
|
|
||||||
name = WZTool.readDecodedStringAtOffsetAndReset(slea, lea.readInt() + this.headerSize + 1);
|
|
||||||
size = WZTool.readValue(lea);
|
|
||||||
checksum = WZTool.readValue(lea);
|
|
||||||
lea.readInt(); //dummy int
|
|
||||||
dir.addFile(new WZFileEntry(name, size, checksum, dir));
|
|
||||||
break;
|
|
||||||
case 0x03:
|
|
||||||
case 0x04:
|
|
||||||
name = WZTool.readDecodedString(lea);
|
|
||||||
size = WZTool.readValue(lea);
|
|
||||||
checksum = WZTool.readValue(lea);
|
|
||||||
lea.readInt(); //dummy int
|
|
||||||
if (marker == 3) {
|
|
||||||
dir.addDirectory(new WZDirectoryEntry(name, size, checksum, dir));
|
|
||||||
} else {
|
|
||||||
dir.addFile(new WZFileEntry(name, size, checksum, dir));
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (MapleDataDirectoryEntry idir : dir.getSubdirectories()) {
|
|
||||||
parseDirectory((WZDirectoryEntry) idir);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public WZIMGFile getImgFile(String path) throws IOException {
|
|
||||||
String[] segments = path.split("/");
|
|
||||||
WZDirectoryEntry dir = root;
|
|
||||||
for (int x = 0; x < segments.length - 1; x++) {
|
|
||||||
dir = (WZDirectoryEntry) dir.getEntry(segments[x]);
|
|
||||||
if (dir == null) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
WZFileEntry entry = (WZFileEntry) dir.getEntry(segments[segments.length - 1]);
|
|
||||||
if (entry == null) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
String fullPath = wzfile.getName().substring(0, wzfile.getName().length() - 3).toLowerCase() + "/" + path;
|
|
||||||
return new WZIMGFile(this.wzfile, entry, provideImages, ListWZFile.isModernImgFile(fullPath));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public synchronized MapleData getData(String path) {
|
|
||||||
try {
|
|
||||||
WZIMGFile imgFile = getImgFile(path);
|
|
||||||
if (imgFile == null) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
MapleData ret = imgFile.getRoot();
|
|
||||||
return ret;
|
|
||||||
} catch (IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public MapleDataDirectoryEntry getRoot() {
|
|
||||||
return root;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,119 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import provider.MapleData;
|
|
||||||
import provider.MapleDataEntity;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.Iterator;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
public class WZIMGEntry implements MapleData {
|
|
||||||
private String name;
|
|
||||||
private MapleDataType type;
|
|
||||||
private List<MapleData> children = new ArrayList<>(10);
|
|
||||||
private Object data;
|
|
||||||
private MapleDataEntity parent;
|
|
||||||
|
|
||||||
public WZIMGEntry(MapleDataEntity parent) {
|
|
||||||
this.parent = parent;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getName() {
|
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public MapleDataType getType() {
|
|
||||||
return type;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public List<MapleData> getChildren() {
|
|
||||||
return Collections.unmodifiableList(children);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public MapleData getChildByPath(String path) {
|
|
||||||
String[] segments = path.split("/");
|
|
||||||
if (segments[0].equals("..")) {
|
|
||||||
return ((MapleData) getParent()).getChildByPath(path.substring(path.indexOf("/") + 1));
|
|
||||||
}
|
|
||||||
MapleData ret = this;
|
|
||||||
for (String segment : segments) {
|
|
||||||
boolean foundChild = false;
|
|
||||||
for (MapleData child : ret.getChildren()) {
|
|
||||||
if (child.getName().equals(segment)) {
|
|
||||||
ret = child;
|
|
||||||
foundChild = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!foundChild) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Object getData() {
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setName(String name) {
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setType(MapleDataType type) {
|
|
||||||
this.type = type;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setData(Object data) {
|
|
||||||
this.data = data;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addChild(WZIMGEntry entry) {
|
|
||||||
children.add(entry);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Iterator<MapleData> iterator() {
|
|
||||||
return getChildren().iterator();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String toString() {
|
|
||||||
return getName() + ":" + getData();
|
|
||||||
}
|
|
||||||
|
|
||||||
public MapleDataEntity getParent() {
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void finish() {
|
|
||||||
((ArrayList<MapleData>) children).trimToSize();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,224 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import tools.data.input.GenericSeekableLittleEndianAccessor;
|
|
||||||
import tools.data.input.RandomAccessByteStream;
|
|
||||||
import tools.data.input.SeekableLittleEndianAccessor;
|
|
||||||
|
|
||||||
import java.awt.*;
|
|
||||||
import java.io.*;
|
|
||||||
|
|
||||||
public class WZIMGFile {
|
|
||||||
private WZFileEntry file;
|
|
||||||
private WZIMGEntry root;
|
|
||||||
private boolean provideImages;
|
|
||||||
@SuppressWarnings ("unused")
|
|
||||||
private boolean modernImg;
|
|
||||||
|
|
||||||
public WZIMGFile(File wzfile, WZFileEntry file, boolean provideImages, boolean modernImg) throws IOException {
|
|
||||||
RandomAccessFile raf = new RandomAccessFile(wzfile, "r");
|
|
||||||
SeekableLittleEndianAccessor slea = new GenericSeekableLittleEndianAccessor(new RandomAccessByteStream(raf));
|
|
||||||
slea.seek(file.getOffset());
|
|
||||||
this.file = file;
|
|
||||||
this.provideImages = provideImages;
|
|
||||||
root = new WZIMGEntry(file.getParent());
|
|
||||||
root.setName(file.getName());
|
|
||||||
root.setType(MapleDataType.EXTENDED);
|
|
||||||
this.modernImg = modernImg;
|
|
||||||
parseExtended(root, slea, 0);
|
|
||||||
root.finish();
|
|
||||||
raf.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
protected void dumpImg(OutputStream out, SeekableLittleEndianAccessor slea) throws IOException {
|
|
||||||
DataOutputStream os = new DataOutputStream(out);
|
|
||||||
long oldPos = slea.getPosition();
|
|
||||||
slea.seek(file.getOffset());
|
|
||||||
for (int x = 0; x < file.getSize(); x++) {
|
|
||||||
os.write(slea.readByte());
|
|
||||||
}
|
|
||||||
slea.seek(oldPos);
|
|
||||||
}
|
|
||||||
|
|
||||||
public WZIMGEntry getRoot() {
|
|
||||||
return root;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void parse(WZIMGEntry entry, SeekableLittleEndianAccessor slea) {
|
|
||||||
byte marker = slea.readByte();
|
|
||||||
switch (marker) {
|
|
||||||
case 0: {
|
|
||||||
String name = WZTool.readDecodedString(slea);
|
|
||||||
entry.setName(name);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case 1: {
|
|
||||||
String name = WZTool.readDecodedStringAtOffsetAndReset(slea, file.getOffset() + slea.readInt());
|
|
||||||
entry.setName(name);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
System.out.println("Unknown Image identifier: " + marker + " at offset " + (slea.getPosition() - file.getOffset()));
|
|
||||||
}
|
|
||||||
marker = slea.readByte();
|
|
||||||
switch (marker) {
|
|
||||||
case 0:
|
|
||||||
entry.setType(MapleDataType.IMG_0x00);
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
case 11: //??? no idea, since 0.49
|
|
||||||
entry.setType(MapleDataType.SHORT);
|
|
||||||
entry.setData(slea.readShort());
|
|
||||||
break;
|
|
||||||
case 3:
|
|
||||||
entry.setType(MapleDataType.INT);
|
|
||||||
entry.setData(WZTool.readValue(slea));
|
|
||||||
break;
|
|
||||||
case 4:
|
|
||||||
entry.setType(MapleDataType.FLOAT);
|
|
||||||
entry.setData(WZTool.readFloatValue(slea));
|
|
||||||
break;
|
|
||||||
case 5:
|
|
||||||
entry.setType(MapleDataType.DOUBLE);
|
|
||||||
entry.setData(slea.readDouble());
|
|
||||||
break;
|
|
||||||
case 8:
|
|
||||||
entry.setType(MapleDataType.STRING);
|
|
||||||
byte iMarker = slea.readByte();
|
|
||||||
if (iMarker == 0) {
|
|
||||||
entry.setData(WZTool.readDecodedString(slea));
|
|
||||||
} else if (iMarker == 1) {
|
|
||||||
entry.setData(WZTool.readDecodedStringAtOffsetAndReset(slea, slea.readInt() + file.getOffset()));
|
|
||||||
} else {
|
|
||||||
System.out.println("Unknown String type " + iMarker);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 9:
|
|
||||||
entry.setType(MapleDataType.EXTENDED);
|
|
||||||
long endOfExtendedBlock = slea.readInt();
|
|
||||||
endOfExtendedBlock += slea.getPosition();
|
|
||||||
parseExtended(entry, slea, endOfExtendedBlock);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
System.out.println("Unknown Image type " + marker);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void parseExtended(WZIMGEntry entry, SeekableLittleEndianAccessor slea, long endOfExtendedBlock) {
|
|
||||||
byte marker = slea.readByte();
|
|
||||||
String type;
|
|
||||||
switch (marker) {
|
|
||||||
case 0x73:
|
|
||||||
type = WZTool.readDecodedString(slea);
|
|
||||||
break;
|
|
||||||
case 0x1B:
|
|
||||||
type = WZTool.readDecodedStringAtOffsetAndReset(slea, file.getOffset() + slea.readInt());
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
throw new RuntimeException("Unknown extended image identifier: " + marker + " at offset " +
|
|
||||||
(slea.getPosition() - file.getOffset()));
|
|
||||||
}
|
|
||||||
if (type.equals("Property")) {
|
|
||||||
entry.setType(MapleDataType.PROPERTY);
|
|
||||||
slea.readByte();
|
|
||||||
slea.readByte();
|
|
||||||
int children = WZTool.readValue(slea);
|
|
||||||
for (int i = 0; i < children; i++) {
|
|
||||||
WZIMGEntry cEntry = new WZIMGEntry(entry);
|
|
||||||
parse(cEntry, slea);
|
|
||||||
cEntry.finish();
|
|
||||||
entry.addChild(cEntry);
|
|
||||||
}
|
|
||||||
} else if (type.equals("Canvas")) {
|
|
||||||
entry.setType(MapleDataType.CANVAS);
|
|
||||||
slea.readByte();
|
|
||||||
marker = slea.readByte();
|
|
||||||
if (marker == 0) {
|
|
||||||
// do nothing
|
|
||||||
} else if (marker == 1) {
|
|
||||||
slea.readByte();
|
|
||||||
slea.readByte();
|
|
||||||
int children = WZTool.readValue(slea);
|
|
||||||
for (int i = 0; i < children; i++) {
|
|
||||||
WZIMGEntry child = new WZIMGEntry(entry);
|
|
||||||
parse(child, slea);
|
|
||||||
child.finish();
|
|
||||||
entry.addChild(child);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
System.out.println("Canvas marker != 1 (" + marker + ")");
|
|
||||||
}
|
|
||||||
int width = WZTool.readValue(slea);
|
|
||||||
int height = WZTool.readValue(slea);
|
|
||||||
int format = WZTool.readValue(slea);
|
|
||||||
int format2 = slea.readByte();
|
|
||||||
slea.readInt();
|
|
||||||
int dataLength = slea.readInt() - 1;
|
|
||||||
slea.readByte();
|
|
||||||
if (provideImages) {
|
|
||||||
byte[] pngdata = slea.read(dataLength);
|
|
||||||
entry.setData(new PNGMapleCanvas(width, height, dataLength, format + format2, pngdata));
|
|
||||||
} else {
|
|
||||||
entry.setData(new PNGMapleCanvas(width, height, dataLength, format + format2, null));
|
|
||||||
slea.skip(dataLength);
|
|
||||||
}
|
|
||||||
} else if (type.equals("Shape2D#Vector2D")) {
|
|
||||||
entry.setType(MapleDataType.VECTOR);
|
|
||||||
int x = WZTool.readValue(slea);
|
|
||||||
int y = WZTool.readValue(slea);
|
|
||||||
entry.setData(new Point(x, y));
|
|
||||||
} else if (type.equals("Shape2D#Convex2D")) {
|
|
||||||
int children = WZTool.readValue(slea);
|
|
||||||
for (int i = 0; i < children; i++) {
|
|
||||||
WZIMGEntry cEntry = new WZIMGEntry(entry);
|
|
||||||
parseExtended(cEntry, slea, 0);
|
|
||||||
cEntry.finish();
|
|
||||||
entry.addChild(cEntry);
|
|
||||||
}
|
|
||||||
} else if (type.equals("Sound_DX8")) {
|
|
||||||
entry.setType(MapleDataType.SOUND);
|
|
||||||
slea.readByte();
|
|
||||||
int dataLength = WZTool.readValue(slea);
|
|
||||||
WZTool.readValue(slea); // no clue what this is
|
|
||||||
int offset = (int) slea.getPosition();
|
|
||||||
entry.setData(new ImgMapleSound(dataLength, offset - file.getOffset()));
|
|
||||||
slea.seek(endOfExtendedBlock);
|
|
||||||
} else if (type.equals("UOL")) {
|
|
||||||
entry.setType(MapleDataType.UOL);
|
|
||||||
slea.readByte();
|
|
||||||
byte uolmarker = slea.readByte();
|
|
||||||
switch (uolmarker) {
|
|
||||||
case 0:
|
|
||||||
entry.setData(WZTool.readDecodedString(slea));
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
entry.setData(WZTool.readDecodedStringAtOffsetAndReset(slea, file.getOffset() + slea.readInt()));
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
System.out.println("Unknown UOL marker: " + uolmarker + " " + entry.getName());
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new RuntimeException("Unhandled extended type: " + type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,188 +0,0 @@
|
|||||||
/*
|
|
||||||
This file is part of the OdinMS Maple Story Server
|
|
||||||
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
|
|
||||||
Matthias Butz <matze@odinms.de>
|
|
||||||
Jan Christian Meyer <vimes@odinms.de>
|
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU Affero General Public License as
|
|
||||||
published by the Free Software Foundation version 3 as published by
|
|
||||||
the Free Software Foundation. You may not use, modify or distribute
|
|
||||||
this program under any other version of the GNU Affero General Public
|
|
||||||
License.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU Affero General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU Affero General Public License
|
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
package provider.wz;
|
|
||||||
|
|
||||||
import tools.data.input.LittleEndianAccessor;
|
|
||||||
import tools.data.input.SeekableLittleEndianAccessor;
|
|
||||||
|
|
||||||
import javax.crypto.BadPaddingException;
|
|
||||||
import javax.crypto.Cipher;
|
|
||||||
import javax.crypto.IllegalBlockSizeException;
|
|
||||||
import javax.crypto.NoSuchPaddingException;
|
|
||||||
import javax.crypto.spec.SecretKeySpec;
|
|
||||||
import java.security.InvalidKeyException;
|
|
||||||
import java.security.NoSuchAlgorithmException;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Ported Code, see WZFile.java for more info
|
|
||||||
*/
|
|
||||||
public class WZTool {
|
|
||||||
private static byte[] encKey;
|
|
||||||
|
|
||||||
static {
|
|
||||||
byte[] iv = new byte[]{(byte) 0x4d, (byte) 0x23, (byte) 0xc7, (byte) 0x2b,
|
|
||||||
(byte) 0x4d, (byte) 0x23, (byte) 0xc7, (byte) 0x2b,
|
|
||||||
(byte) 0x4d, (byte) 0x23, (byte) 0xc7, (byte) 0x2b,
|
|
||||||
(byte) 0x4d, (byte) 0x23, (byte) 0xc7, (byte) 0x2b,};
|
|
||||||
byte[] key = new byte[]{(byte) 0x13, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x08, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x06, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0xB4, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x1B, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x0F, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x33, 0x00, 0x00, 0x00,
|
|
||||||
(byte) 0x52, 0x00, 0x00, 0x00
|
|
||||||
};
|
|
||||||
Cipher cipher = null;
|
|
||||||
SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
|
|
||||||
try {
|
|
||||||
cipher = Cipher.getInstance("AES");
|
|
||||||
} catch (NoSuchAlgorithmException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (NoSuchPaddingException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
|
|
||||||
} catch (InvalidKeyException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
encKey = new byte[0xFFFF];
|
|
||||||
for (int i = 0; i < (0xFFFF / 16); i++) {
|
|
||||||
try {
|
|
||||||
iv = cipher.doFinal(iv);
|
|
||||||
} catch (IllegalBlockSizeException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (BadPaddingException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
System.arraycopy(iv, 0, encKey, (i * 16), 16);
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
iv = cipher.doFinal(iv);
|
|
||||||
} catch (IllegalBlockSizeException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (BadPaddingException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
System.arraycopy(iv, 0, encKey, 65520, 15);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static byte[] readListString(byte[] str) {
|
|
||||||
for (int i = 0; i < str.length; i++) {
|
|
||||||
str[i] = (byte) (str[i] ^ encKey[i]);
|
|
||||||
}
|
|
||||||
return str;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String readDecodedString(LittleEndianAccessor llea) {
|
|
||||||
int strLength;
|
|
||||||
byte b = llea.readByte();
|
|
||||||
if (b == 0x00) {
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
if (b >= 0) {
|
|
||||||
if (b == 0x7F) {
|
|
||||||
strLength = llea.readInt();
|
|
||||||
} else {
|
|
||||||
strLength = b;
|
|
||||||
}
|
|
||||||
if (strLength < 0) {
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
byte[] str = new byte[strLength * 2];
|
|
||||||
for (int i = 0; i < strLength * 2; i++) {
|
|
||||||
str[i] = llea.readByte();
|
|
||||||
}
|
|
||||||
return DecryptUnicodeStr(str);
|
|
||||||
} else {
|
|
||||||
if (b == -128) {
|
|
||||||
strLength = llea.readInt();
|
|
||||||
} else {
|
|
||||||
strLength = -b;
|
|
||||||
}
|
|
||||||
if (strLength < 0) {
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
byte[] str = new byte[strLength];
|
|
||||||
for (int i = 0; i < strLength; i++) {
|
|
||||||
str[i] = llea.readByte();
|
|
||||||
}
|
|
||||||
return DecryptAsciiStr(str);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String DecryptAsciiStr(byte[] str) {
|
|
||||||
byte xorByte = (byte) 0xAA;
|
|
||||||
for (int i = 0; i < str.length; i++) {
|
|
||||||
str[i] = (byte) (str[i] ^ xorByte ^ encKey[i]);
|
|
||||||
xorByte++;
|
|
||||||
}
|
|
||||||
return new String(str);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String DecryptUnicodeStr(byte[] str) {
|
|
||||||
int xorByte = 0xAAAA;
|
|
||||||
char[] charRet = new char[str.length / 2];
|
|
||||||
for (int i = 0; i < str.length; i++) {
|
|
||||||
str[i] = (byte) (str[i] ^ encKey[i]);
|
|
||||||
}
|
|
||||||
for (int i = 0; i < (str.length / 2); i++) {
|
|
||||||
char toXor = (char) ((str[i] << 8) | str[i + 1]);
|
|
||||||
charRet[i] = (char) (toXor ^ xorByte);
|
|
||||||
xorByte++;
|
|
||||||
}
|
|
||||||
return String.valueOf(charRet);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String readDecodedStringAtOffset(SeekableLittleEndianAccessor slea, int offset) {
|
|
||||||
slea.seek(offset);
|
|
||||||
return readDecodedString(slea);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String readDecodedStringAtOffsetAndReset(SeekableLittleEndianAccessor slea, int offset) {
|
|
||||||
long pos = 0;
|
|
||||||
pos = slea.getPosition();
|
|
||||||
slea.seek(offset);
|
|
||||||
String ret = readDecodedString(slea);
|
|
||||||
slea.seek(pos);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int readValue(LittleEndianAccessor lea) {
|
|
||||||
byte b = lea.readByte();
|
|
||||||
if (b == -128) {
|
|
||||||
return lea.readInt();
|
|
||||||
} else {
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static float readFloatValue(LittleEndianAccessor lea) {
|
|
||||||
byte b = lea.readByte();
|
|
||||||
if (b == -128) {
|
|
||||||
return lea.readFloat();
|
|
||||||
} else {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -147,12 +147,6 @@ public class XMLDomMapleData implements MapleData {
|
|||||||
String y = attributes.getNamedItem("y").getNodeValue();
|
String y = attributes.getNamedItem("y").getNodeValue();
|
||||||
return new Point(Integer.parseInt(x), Integer.parseInt(y));
|
return new Point(Integer.parseInt(x), Integer.parseInt(y));
|
||||||
}
|
}
|
||||||
case CANVAS: {
|
|
||||||
String width = attributes.getNamedItem("width").getNodeValue();
|
|
||||||
String height = attributes.getNamedItem("height").getNodeValue();
|
|
||||||
return new FileStoredPngMapleCanvas(Integer.parseInt(width), Integer.parseInt(height), new File(
|
|
||||||
imageDataDir, getName() + ".png"));
|
|
||||||
}
|
|
||||||
default:
|
default:
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user