Merge pull request #4 from gravgun/master

Bunch of small improvements
This commit is contained in:
Steven Smith 2016-01-27 16:12:29 -08:00
commit 0e01fe0f49
11 changed files with 145 additions and 143 deletions

View file

@ -1,5 +1,5 @@
#ifndef __3DS_H__
#define __3DS_H__
#ifndef I_3DS_H
#define I_3DS_H
#include "cbmd.h"
#include "cwav.h"

View file

@ -1,5 +1,5 @@
#ifndef __CBMD_H__
#define __CBMD_H__
#ifndef CBMD_H
#define CBMD_H
#include "../types.h"

View file

@ -1,5 +1,5 @@
#ifndef __CWAV_H__
#define __CWAV_H__
#ifndef CWAV_H
#define CWAV_H
#include "../types.h"

View file

@ -1,5 +1,5 @@
#ifndef __LZ11_H__
#define __LZ11_H__
#ifndef LZ11_H
#define LZ11_H
#include "../types.h"

View file

@ -1,5 +1,5 @@
#ifndef __SMDH_H__
#define __SMDH_H__
#ifndef SMDH_H
#define SMDH_H
#include "../types.h"

View file

@ -34,75 +34,77 @@ u16 pack_color(u8 r, u8 g, u8 b, u8 a, PixelFormat format) {
return r << 12 | g << 8 | b << 4 | a;
}
return 0;
return 0;
}
u8* load_image(const char* image, u32 width, u32 height) {
unsigned char *img;
int imgWidth, imgHeight, imgDepth;
unsigned char *img;
int imgWidth, imgHeight, imgDepth;
img = stbi_load(image, &imgWidth, &imgHeight, &imgDepth, STBI_rgb_alpha);
img = stbi_load(image, &imgWidth, &imgHeight, &imgDepth, STBI_rgb_alpha);
if(img == NULL) {
printf("ERROR: Could not load image file: %s.\n", stbi_failure_reason());
return NULL;
}
if(img == NULL) {
printf("ERROR: Could not load image file: %s.\n", stbi_failure_reason());
return NULL;
}
if(width == 0) {
width = imgWidth;
}
if(width == 0) {
width = imgWidth;
}
if(height == 0) {
height = imgHeight;
}
if(height == 0) {
height = imgHeight;
}
if(imgWidth != width || imgHeight != height) {
printf("ERROR: Image must be exactly %d x %d in size.\n", width, height);
return NULL;
}
if(imgWidth != width || imgHeight != height) {
printf("ERROR: Image must be exactly %d x %d in size.\n", width, height);
stbi_image_free(img);
return NULL;
}
if(imgDepth != STBI_rgb_alpha) {
printf("ERROR: Decoded image does't match expected format (%d, wanted %d).\n",
imgDepth, STBI_rgb_alpha);
return NULL;
}
if(imgDepth != STBI_rgb_alpha) {
printf("ERROR: Decoded image does't match expected format (%d, wanted %d).\n",
imgDepth, STBI_rgb_alpha);
stbi_image_free(img);
return NULL;
}
return img;
return img;
}
void free_image(u8* img) {
stbi_image_free(img);
stbi_image_free(img);
}
u16* image_data_to_tiles(u8* img, u32 width, u32 height, PixelFormat format, u32* size) {
u16* converted = (u16*) malloc(width * height * sizeof(u16));
u32 n = 0;
for(int y = 0; y < height; y += 8) {
for(int x = 0; x < width; x += 8) {
for(int k = 0; k < 8 * 8; k++) {
u32 xx = (u32) (TILE_ORDER[k] & 0x7);
u32 yy = (u32) (TILE_ORDER[k] >> 3);
u16* converted = (u16*) malloc(width * height * sizeof(u16));
u32 n = 0;
for(int y = 0; y < height; y += 8) {
for(int x = 0; x < width; x += 8) {
for(int k = 0; k < 8 * 8; k++) {
u32 xx = (u32) (TILE_ORDER[k] & 0x7);
u32 yy = (u32) (TILE_ORDER[k] >> 3);
u8* pixel = img + (((y + yy) * width + (x + xx)) * 4);
converted[n++] = pack_color(pixel[0], pixel[1], pixel[2], pixel[3], format);
}
}
}
u8* pixel = img + (((y + yy) * width + (x + xx)) * 4);
converted[n++] = pack_color(pixel[0], pixel[1], pixel[2], pixel[3], format);
}
}
}
if(size != NULL) {
*size = width * height * (u32) sizeof(u16);
}
if(size != NULL) {
*size = width * height * (u32) sizeof(u16);
}
return converted;
return converted;
}
u16* image_to_tiles(const char* image, u32 width, u32 height, PixelFormat format, u32* size) {
u8* img = load_image(image, width, height);
if(img == NULL) {
return NULL;
}
u8* img = load_image(image, width, height);
if(img == NULL) {
return NULL;
}
u16* tiles = image_data_to_tiles(img, width, height, format, size);
free_image(img);
return tiles;
u16* tiles = image_data_to_tiles(img, width, height, format, size);
free_image(img);
return tiles;
}

View file

@ -1,5 +1,5 @@
#ifndef __UTIL_H__
#define __UTIL_H__
#ifndef UTIL_H
#define UTIL_H
#include "../types.h"

View file

@ -13,7 +13,7 @@
#include <string>
#include <vector>
u8* convert_to_cgfx(const std::string image, u32 width, u32 height, u32* size) {
u8* convert_to_cgfx(const std::string& image, u32 width, u32 height, u32* size) {
u32 convertedSize = 0;
u16* converted = image_to_tiles(image.c_str(), width, height, RGBA4444, &convertedSize);
if(converted == NULL) {
@ -29,7 +29,7 @@ u8* convert_to_cgfx(const std::string image, u32 width, u32 height, u32* size) {
return ret;
}
u8* convert_to_cwav(const std::string file, u32* size) {
u8* convert_to_cwav(const std::string& file, u32* size) {
u8* ret = NULL;
// Determine what file type we have
FILE* fd = fopen(file.c_str(), "rb");
@ -38,50 +38,50 @@ u8* convert_to_cwav(const std::string file, u32* size) {
rewind(fd); // equivalent to SEEK_SET to pos 0
if (magic[0] == 'R' && magic[1] == 'I' && magic[2] == 'F' && magic[3] == 'F') {
WAV* wav = wav_read(fd);
if(wav != NULL) {
CWAV cwav;
cwav.channels = wav->format.numChannels;
cwav.sampleRate = wav->format.sampleRate;
cwav.bitsPerSample = wav->format.bitsPerSample;
cwav.dataSize = wav->data.chunkSize;
cwav.data = wav->data.data;
WAV* wav = wav_read(fd);
if(wav != NULL) {
CWAV cwav;
cwav.channels = wav->format.numChannels;
cwav.sampleRate = wav->format.sampleRate;
cwav.bitsPerSample = wav->format.bitsPerSample;
cwav.dataSize = wav->data.chunkSize;
cwav.data = wav->data.data;
ret = cwav_build(cwav, size);
ret = cwav_build(cwav, size);
wav_free(wav);
}
wav_free(wav);
}
} else if (magic[0] == 'O' && magic[1] == 'g' && magic[2] == 'g' && magic[3] == 'S') {
int error;
stb_vorbis* vorb = stb_vorbis_open_file(fd, false, &error, NULL);
if(vorb != NULL) {
stb_vorbis_info info = stb_vorbis_get_info(vorb);
int error;
stb_vorbis* vorb = stb_vorbis_open_file(fd, false, &error, NULL);
if(vorb != NULL) {
stb_vorbis_info info = stb_vorbis_get_info(vorb);
CWAV cwav;
cwav.channels = info.channels;
cwav.sampleRate = info.sample_rate;
cwav.bitsPerSample = 16; // stb_vorbis always outputs 16 bit samples
int sampleCount = stb_vorbis_stream_length_in_samples(vorb) * info.channels;
cwav.dataSize = sampleCount * 2;
cwav.data = (u8*) calloc(sampleCount, 2);
stb_vorbis_get_samples_short_interleaved(vorb, info.channels, (short*) cwav.data, sampleCount);
CWAV cwav;
cwav.channels = info.channels;
cwav.sampleRate = info.sample_rate;
cwav.bitsPerSample = 16; // stb_vorbis always outputs 16 bit samples
int sampleCount = stb_vorbis_stream_length_in_samples(vorb) * info.channels;
cwav.dataSize = sampleCount * 2;
cwav.data = (u8*) calloc(sampleCount, 2);
stb_vorbis_get_samples_short_interleaved(vorb, info.channels, (short*) cwav.data, sampleCount);
ret = cwav_build(cwav, size);
ret = cwav_build(cwav, size);
free(cwav.data);
stb_vorbis_close(vorb);
} else {
printf("ERROR: Vorbis open failed, error %d.\n", error);
}
free(cwav.data);
stb_vorbis_close(vorb);
} else {
printf("ERROR: Vorbis open failed, error %d.\n", error);
}
} else {
printf("ERROR: Audio file header '%c%c%c%c' unrecognized.\n", magic[0], magic[1], magic[2], magic[3]);
printf("ERROR: Audio file header '%c%c%c%c' unrecognized.\n", magic[0], magic[1], magic[2], magic[3]);
}
fclose(fd);
return ret;
}
int cmd_make_banner(const std::string image, const std::string audio, const std::string cgfxFile, const std::string cwavFile, const std::string output) {
int cmd_make_banner(const std::string& image, const std::string& audio, const std::string& cgfxFile, const std::string& cwavFile, const std::string& output) {
u32 cgfxSize = 0;
u8* cgfx = NULL;
if(!cgfxFile.empty()) {
@ -154,11 +154,11 @@ int cmd_make_banner(const std::string image, const std::string audio, const std:
return 0;
}
int cmd_make_smdh(const std::string shortTitle, const std::string longTitle, const std::string publisher, const std::string icon, SMDHRegionFlag regionFlags, u64 matchMakerId, u32 smdhFlags, u16 eulaVersion, u32 optimalBannerFrame, u32 streetpassId, const std::string output) {
u8* icon48Data = load_image(icon.c_str(), 48, 48);
if(icon48Data == NULL) {
return 1;
}
int cmd_make_smdh(const std::string& shortTitle, const std::string& longTitle, const std::string& publisher, const std::string& icon, SMDHRegionFlag regionFlags, u64 matchMakerId, u32 smdhFlags, u16 eulaVersion, u32 optimalBannerFrame, u32 streetpassId, const std::string& output) {
u8* icon48Data = load_image(icon.c_str(), 48, 48);
if(icon48Data == NULL) {
return 1;
}
u16* icon48 = image_data_to_tiles(icon48Data, 48, 48, RGB565, NULL);
if(icon48 == NULL) {
@ -168,42 +168,42 @@ int cmd_make_smdh(const std::string shortTitle, const std::string longTitle, con
u8 icon24Data[24 * 24 * 4];
for(int y = 0; y < 48; y += 2) {
for(int x = 0; x < 48; x += 2) {
int i1 = (y * 48 + x) * 4;
u8 r1 = icon48Data[i1 + 0];
u8 g1 = icon48Data[i1 + 1];
u8 b1 = icon48Data[i1 + 2];
u8 a1 = icon48Data[i1 + 3];
int i1 = (y * 48 + x) * 4;
u8 r1 = icon48Data[i1 + 0];
u8 g1 = icon48Data[i1 + 1];
u8 b1 = icon48Data[i1 + 2];
u8 a1 = icon48Data[i1 + 3];
int i2 = (y * 48 + (x + 1)) * 4;
u8 r2 = icon48Data[i2 + 0];
u8 g2 = icon48Data[i2 + 1];
u8 b2 = icon48Data[i2 + 2];
u8 a2 = icon48Data[i2 + 3];
int i2 = (y * 48 + (x + 1)) * 4;
u8 r2 = icon48Data[i2 + 0];
u8 g2 = icon48Data[i2 + 1];
u8 b2 = icon48Data[i2 + 2];
u8 a2 = icon48Data[i2 + 3];
int i3 = ((y + 1) * 48 + x) * 4;
u8 r3 = icon48Data[i3 + 0];
u8 g3 = icon48Data[i3 + 1];
u8 b3 = icon48Data[i3 + 2];
u8 a3 = icon48Data[i3 + 3];
int i3 = ((y + 1) * 48 + x) * 4;
u8 r3 = icon48Data[i3 + 0];
u8 g3 = icon48Data[i3 + 1];
u8 b3 = icon48Data[i3 + 2];
u8 a3 = icon48Data[i3 + 3];
int i4 = ((y + 1) * 48 + (x + 1)) * 4;
u8 r4 = icon48Data[i4 + 0];
u8 g4 = icon48Data[i4 + 1];
u8 b4 = icon48Data[i4 + 2];
u8 a4 = icon48Data[i4 + 3];
int i4 = ((y + 1) * 48 + (x + 1)) * 4;
u8 r4 = icon48Data[i4 + 0];
u8 g4 = icon48Data[i4 + 1];
u8 b4 = icon48Data[i4 + 2];
u8 a4 = icon48Data[i4 + 3];
int id = ((y / 2) * 24 + (x / 2)) * 4;
icon24Data[id + 0] = (u8) ((r1 + r2 + r3 + r4) / 4);
icon24Data[id + 1] = (u8) ((g1 + g2 + g3 + g4) / 4);
icon24Data[id + 2] = (u8) ((b1 + b2 + b3 + b4) / 4);
icon24Data[id + 3] = (u8) ((a1 + a2 + a3 + a4) / 4);
int id = ((y / 2) * 24 + (x / 2)) * 4;
icon24Data[id + 0] = (u8) ((r1 + r2 + r3 + r4) / 4);
icon24Data[id + 1] = (u8) ((g1 + g2 + g3 + g4) / 4);
icon24Data[id + 2] = (u8) ((b1 + b2 + b3 + b4) / 4);
icon24Data[id + 3] = (u8) ((a1 + a2 + a3 + a4) / 4);
}
}
u16* icon24 = image_data_to_tiles(icon24Data, 24, 24, RGB565, NULL);
if(icon24 == NULL) {
return 1;
}
u16* icon24 = image_data_to_tiles(icon24Data, 24, 24, RGB565, NULL);
if(icon24 == NULL) {
return 1;
}
SMDH smdh;
for(int i = 0; i < 0x10; i++) {
@ -236,7 +236,7 @@ int cmd_make_smdh(const std::string shortTitle, const std::string longTitle, con
return 0;
}
int cmd_make_cwav(const std::string input, const std::string output) {
int cmd_make_cwav(const std::string& input, const std::string& output) {
u32 cwavSize = 0;
u8* cwav = convert_to_cwav(input, &cwavSize);
if(cwav == NULL) {
@ -258,7 +258,7 @@ int cmd_make_cwav(const std::string input, const std::string output) {
return 0;
}
int cmd_lz11(const std::string input, const std::string output) {
int cmd_lz11(const std::string& input, const std::string& output) {
FILE* in = fopen(input.c_str(), "r");
if(in == NULL) {
printf("ERROR: Could not open input file: %s\n", strerror(errno));
@ -312,11 +312,11 @@ std::map<std::string, std::string> cmd_get_args(int argc, char* argv[]) {
return args;
}
std::string cmd_find_arg(std::map<std::string, std::string> args, const std::string shortOpt, const std::string longOpt, const std::string def) {
std::string cmd_find_arg(const std::map<std::string, std::string>& args, const std::string& shortOpt, const std::string& longOpt, const std::string& def) {
std::string sopt = "-" + shortOpt;
std::string lopt = "--" + longOpt;
std::map<std::string, std::string>::iterator match = args.find(sopt);
std::map<std::string, std::string>::const_iterator match = args.find(sopt);
if(match != args.end()) {
return (*match).second;
}
@ -329,7 +329,7 @@ std::string cmd_find_arg(std::map<std::string, std::string> args, const std::str
return def;
}
std::vector<std::string> cmd_parse_list(const std::string list) {
std::vector<std::string> cmd_parse_list(const std::string& list) {
std::vector<std::string> ret;
std::string::size_type lastPos = 0;
std::string::size_type pos = 0;
@ -345,7 +345,7 @@ std::vector<std::string> cmd_parse_list(const std::string list) {
return ret;
}
void cmd_print_info(const std::string command) {
void cmd_print_info(const std::string& command) {
if(command.compare("makebanner") == 0) {
printf("makebanner - Creates a .bnr file.\n");
printf(" -i/--image: PNG file to use as the banner's image. Interchangeable with -ci.\n");
@ -387,22 +387,22 @@ void cmd_print_commands() {
cmd_print_info("lz11");
}
void cmd_print_usage(const std::string executedFrom) {
void cmd_print_usage(const std::string& executedFrom) {
printf("Usage: %s <command> <args>\n", executedFrom.c_str());
cmd_print_commands();
}
void cmd_missing_args(const std::string command) {
void cmd_missing_args(const std::string& command) {
printf("Missing arguments for command \"%s\".\n", command.c_str());
cmd_print_info(command);
}
void cmd_invalid_arg(const std::string argument, const std::string command) {
void cmd_invalid_arg(const std::string& argument, const std::string& command) {
printf("Invalid value for argument \"%s\" in command \"%s\".\n", argument.c_str(), command.c_str());
cmd_print_info(command);
}
void cmd_invalid_command(const std::string command) {
void cmd_invalid_command(const std::string& command) {
printf("Invalid command \"%s\".\n", command.c_str());
cmd_print_commands();
}

View file

@ -1,5 +1,5 @@
#ifndef __CMD_H__
#define __CMD_H__
#ifndef CMD_H
#define CMD_H
int cmd_process_command(int argc, char* argv[]);

View file

@ -1,5 +1,5 @@
#ifndef __WAV_H__
#define __WAV_H__
#ifndef WAV_H
#define WAV_H
#include <stdio.h>

View file

@ -1,5 +1,5 @@
#ifndef __TYPES_H__
#define __TYPES_H__
#ifndef TYPES_H
#define TYPES_H
#include <stddef.h>
#include <stdint.h>