Re: [X360] Star Wars Battlefront III pre-alpha (*.x2t)
Posted: Tue Feb 02, 2016 7:35 pm
[out]
Game Research Forum
https://forum.xentax.com/
Code: Select all
...
#DXT1
if imgFmt == 0x28:
data = rapi.imageUntile360DXT(rapi.swapEndianArray(data, 2), imgWidth, imgHeight, 8)
texFmt = noesis.NOESISTEX_DXT1
#DXT5
elif imgFmt == 0x33:
data = rapi.imageUntile360DXT(rapi.swapEndianArray(data, 2), imgWidth, imgHeight, 16)
texFmt = noesis.NOESISTEX_DXT5
#DXT5 packed normal map
elif imgFmt == 0x1C:
data = rapi.imageUntile360DXT(rapi.swapEndianArray(data, 2), imgWidth, imgHeight, 16)
data = rapi.imageDecodeDXT(data, imgWidth, imgHeight, noesis.FOURCC_ATI2)
texFmt = noesis.NOESISTEX_RGBA32
#DXT5 packed normal map2
elif imgFmt == 0x36:
data = rapi.imageUntile360DXT(rapi.swapEndianArray(data, 2), imgWidth, imgHeight, 16)
data = rapi.imageDecodeDXT(data, imgWidth, imgHeight, noesis.FOURCC_ATI1)
texFmt = noesis.NOESISTEX_RGBA32
#DXT1 packed normal map
elif imgFmt == 0x16:
data = rapi.imageUntile360DXT(rapi.swapEndianArray(data, 2), imgWidth, imgHeight, 8)
data = rapi.imageDecodeDXT(data, imgWidth, imgHeight, noesis.FOURCC_DXT1NORMAL)
texFmt = noesis.NOESISTEX_RGBA32
#raw
elif imgFmt == 0x1B:
data = rapi.imageUntile360Raw(rapi.swapEndianArray(data, 4), imgWidth, imgHeight, 4)
texFmt = noesis.NOESISTEX_RGBA32
#unknown, not handled
...
It seems like maybe it's pixelated like that cause the head is maybe 512x512 and not 1024x1024.Wobble wrote:Woohoo, you got it!
The data needs to be endian swapped before passing it to unswizzle functions.
But, it's not perfect. The pixels are still very jagged. I don't know if this is how the original texture is supposed to look like on the XBox 360,
or if the unswizzle function is not unswizzling the entire image.
This is really amazing it's just sad they didn't extract with the proper file names cause going down through noesis to find textures you want is pretty hard since there are so many.Wobble wrote:Last one:
- Added filename argument scanning for zero headers. Arguments must be separated by spaces.
Code: Select all
<filename> <width> <height> <bpp> <format>.x2t
Ah okay,AceWell wrote:The textures were extracted with the names that were stored in the str file, and these same names are referenced in the rax files, the names are correct for this build.
Code: Select all
// Uncompressed
if(image_format == 3) {
// BYTE *dst, BYTE *src, int dstSize, int imgW, int imgH, int bytesPerPix
rapi->Noesis_UntileImageRAW( unswizzled_buffer, image_buffer, image_size, image_width, image_height, (image_bpp/8) );
}
Code: Select all
#raw
elif imgFmt == 0x1B:
data = rapi.imageUntile360Raw(rapi.swapEndianArray(data, 4), imgWidth, imgHeight, 4)
texFmt = noesis.NOESISTEX_RGBA32
There are lots of image processing scripts of this nature to use as examples over on the old Google Code depot.
The Gamebryo NIF script shows how to do all kinds of untiling including 360-style and straight up Morton order. Use rapi.swapEndianArray to quickly endian-swap DXT blocks as commonly needed on the 360, this is demonstrated in the BulletWitch script in cprLoadTexture.
maybe it does have something to do with Morton order.Wobble wrote:The problem is with the imageUntile360Raw() function. It doesn't seem work for these textures.
Can't do nothing about it, because we don't know how it works. It is based on Morton order or something else?
Code: Select all
#run through and convert texture data
pixObject = nif.objects[texObject.pixLinkID]
noeFmt = noesis.NOESISTEX_UNKNOWN
pixelFormatObj = noeSafeGet(pixObject, "pixelFormat")
if pixelFormatObj is None:
print("WARNING: Object", texObject.pixLinkID, "type", pixObject.typeName, "should have contained a pixel format, but didn't.")
continue
pixelFormat = pixelFormatObj.format
imageData = pixObject.imageData
pixelImageInfo = [pixObject.numFaces, pixObject.mipLevels, pixObject.mipsTotalSize, pixObject.mipInfo]
if pixelFormat == NIFTEX_RGB:
noeFmt = noesis.NOESISTEX_RGBA32
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageDecodeRaw, "r8g8b8")
elif pixelFormat == NIFTEX_RGBA:
noeFmt = noesis.NOESISTEX_RGBA32
if pixObject.platform == NIF_PLATFORM_PS3: #alpha first on ps3 (or so we not always correctly assume)
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageDecodeRaw, "a8r8g8b8")
elif pixObject.platform == NIF_PLATFORM_XBOX360: #another potentially-faulty assumption - bgra for 360
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageDecodeRaw, "b8g8r8a8")
elif pixelFormat == NIFTEX_DXT1:
noeFmt = noesis.NOESISTEX_DXT1
elif pixelFormat == NIFTEX_DXT3:
noeFmt = noesis.NOESISTEX_DXT3
elif pixelFormat == NIFTEX_DXT5:
noeFmt = noesis.NOESISTEX_DXT5
elif pixelFormat == NIFTEX_MONO:
#expand out to rgba32
noeFmt = noesis.NOESISTEX_RGBA32
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageDecodeRaw, "r8")
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageKernelProcess, 4, nifImageExpandMonoColorKernel)
else:
print("WARNING: Unsupported texture format", pixelFormat)
if noeFmt != noesis.NOESISTEX_UNKNOWN:
if pixelFormatObj.tiling != 0:
#lots of games seem to have bad mip offsets when using tiling/swizzling modes,
#which don't take into account necessary platform-specific padding. so, sadly,
#we'll have to skip the mips.
pixelImageInfo[1] = 1
if pixelFormatObj.tiling == 1:
#360 untile
if noeFmt == noesis.NOESISTEX_RGBA32:
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageUntile360Raw, 4)
else: #dxt
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageUntile360DXT, 8 if noeFmt == noesis.NOESISTEX_DXT1 else 16)
elif pixelFormatObj.tiling == 3:
#morton untile
if noeFmt == noesis.NOESISTEX_RGBA32:
imageData = noeProcessImage(imageData, pixelImageInfo, rapi.imageFromMortonOrder, 4, 2 if pixObject.platform == NIF_PLATFORM_VITA else 0)
else: #dxt
dxtBlockBytes = 4 if noeFmt == noesis.NOESISTEX_DXT1 else 8
imageData = rapi.imageFromMortonOrder(imageData, pixObject.width>>1, pixObject.height>>2, dxtBlockBytes)
#possible todo - support untiling dxt blocks with multiple mips/faces
pixelImageInfo[0] = 1
pixelImageInfo[1] = 1