Add screenshot capture by pressing Y

Also fixed for 800px mode
This commit is contained in:
RocketRobz 2020-06-25 12:45:26 -06:00
parent f7b8753896
commit 65d35f0e1e
4 changed files with 159 additions and 0 deletions

View File

@ -33,6 +33,7 @@ As such features are not normally available in-game, you may risk a possible ban
# Credits
* devkitPro: libctru, citro2d/3d, nds-hb-menu's file/folder browsing code
* Universal Team: Universal Core
* @joel16: Screenshot code from [3DShell](https://github.com/joel16/3DShell)
* Pixel Perfect: [Music icon](https://www.flaticon.com/free-icon/musical-note_727218)
* Mike Dexter: Original MIDI sequence of the Sega CD Model 2 BIOS music
* rog9001: His New Style Boutique 3 Save Editor tool has motivated me to work on this further.

14
include/screenshot.h Normal file
View File

@ -0,0 +1,14 @@
#ifndef SCREENSHOT_H
#define SCREENSHOT_H
#ifdef __cplusplus
extern "C" {
#endif
void Screenshot_Capture(void);
#ifdef __cplusplus
}
#endif
#endif

View File

@ -14,6 +14,7 @@
#include "rocketRobz.hpp"
#include "savedata.h"
#include "screen.hpp"
#include "screenshot.h"
#include "sound.h"
#include "thread.h"
@ -411,6 +412,10 @@ int main()
if (bg_xPos >= 72) bg_xPos = 0.0f;
if (bg_yPos <= -136) bg_yPos = 0.0f;
if (hDown & KEY_Y) {
Screenshot_Capture();
}
if (hDown) {
svcSignalEvent(threadRequest);
}

139
source/screenshot.c Normal file
View File

@ -0,0 +1,139 @@
#include <3ds.h>
#include <stdio.h>
#include <dirent.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h> // access
#include "screenshot.h"
static Result Screenshot_GenerateScreenshot(const char *path) {
int x = 0, y = 0;
int width = gfxIsWide() ? 800 : 400;
int fileSize = gfxIsWide() ? 576000 : 288000;
size_t size = 0x36;
// Get top/bottom framebuffers
//u8 *top_framebuf = gfxGetFramebuffer(GFX_BOTTOM, GFX_BOTTOM, NULL, NULL);
u8 *bottom_framebuf = gfxGetFramebuffer(GFX_TOP, GFX_LEFT, NULL, NULL);
u8 *buf = NULL;
buf = linearAlloc(size + fileSize);
memset(buf, 0, size + fileSize);
buf[size + fileSize] = 0;
*(u16*)&buf[0x0] = 0x4D42;
*(u32*)&buf[0x2] = size + fileSize;
*(u32*)&buf[0xA] = size;
*(u32*)&buf[0xE] = 0x28;
*(u32*)&buf[0x12] = width;
*(u32*)&buf[0x16] = 240;
*(u32*)&buf[0x1A] = 0x00180001;
*(u32*)&buf[0x22] = fileSize;
// Generate top left
u8 *framebuf = bottom_framebuf;
if (gfxIsWide()) {
// Left half
int i = 0;
for (y = 0; y < 240; y++) {
for (x = 0; x < 400; x++) {
int si = ((239 - y) + (x * 240)) * 3;
int di = size + (i + ((239 - y) * 800)) * 3;
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
i++;
if (i == 400) i = 0;
}
}
// Right half
i = 400;
for (y = 0; y < 240; y++) {
for (x = 400; x < 800; x++) {
int si = ((239 - y) + (x * 240)) * 3;
int di = size + (i + ((239 - y) * 800)) * 3;
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
i++;
if (i == 800) i = 400;
}
}
} else {
for (y = 0; y < 240; y++) {
for (x = 0; x < 400; x++) {
int si = ((239 - y) + (x * 240)) * 3;
int di = size + (x + ((239 - y) * 400)) * 3;
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
}
}
}
// Generate bottom right
/*framebuf = top_framebuf;
for (y = 0; y < 240; y++) {
for (x = 0; x < 320; x++) {
int si = ((239 - y) + (x * 240)) * 3;
int di = size + ((x+40) + ((239 - y) * 400)) * 3;
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
buf[di++] = framebuf[si++];
}
// Make adjustments for the smaller width
for (x = 0; x < 40; x++) {
int di = size + (x + ((239 - y) * 400)) * 3;
buf[di++] = 0;
buf[di++] = 0;
buf[di++] = 0;
}
for (x = 360; x < 400; x++) {
int di = size + (x + ((239 - y) * 400)) * 3;
buf[di++] = 0;
buf[di++] = 0;
buf[di++] = 0;
}
}*/
FILE* bmpFile = fopen(path, "wb");
fwrite((u32 *)buf, 1, size + fileSize, bmpFile);
fclose(bmpFile);
if (access(path, F_OK) != 0) {
free(buf);
}
linearFree(buf);
return 0;
}
static void Screenshot_GenerateFilename(int count, char *file_name) {
time_t t = time(0);
int day = localtime(&t)->tm_mday;
int month = localtime(&t)->tm_mon + 1;
int year = localtime(&t)->tm_year + 1900;
mkdir("sdmc:/3ds/SavvyManager/screenshots", 0777);
sprintf(file_name, "sdmc:/3ds/SavvyManager/screenshots/Screenshot_%02d%02d%02d-%i.bmp", year, month, day, count);
}
void Screenshot_Capture(void) {
int num = 0;
static char file_name[256];
sprintf(file_name, "%s", "screenshot");
Screenshot_GenerateFilename(num, file_name);
while (access(file_name, F_OK) == 0) {
num++;
Screenshot_GenerateFilename(num, file_name);
}
Screenshot_GenerateScreenshot(file_name);
num++;
}