mirror of
https://github.com/libretro/scummvm.git
synced 2024-12-14 21:59:17 +00:00
a2a5f2575d
From upstream ea1f8b9ece69fc7c49c4d3aa7b9af51c4ca736e5
279 lines
7.8 KiB
C++
279 lines
7.8 KiB
C++
/* ScummVM - Graphic Adventure Engine
|
|
*
|
|
* ScummVM is the legal property of its developers, whose names
|
|
* are too numerous to list here. Please refer to the COPYRIGHT
|
|
* file distributed with this source distribution.
|
|
*
|
|
* This program is free software: you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* 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 General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
*
|
|
*/
|
|
|
|
#include "ags/console.h"
|
|
#include "ags/ags.h"
|
|
#include "ags/globals.h"
|
|
#include "ags/shared/ac/sprite_cache.h"
|
|
#include "ags/shared/gfx/allegro_bitmap.h"
|
|
#include "ags/shared/script/cc_common.h"
|
|
#include "image/png.h"
|
|
|
|
namespace AGS {
|
|
|
|
AGSConsole::AGSConsole(AGSEngine *vm) : GUI::Debugger(), _vm(vm), _logOutputTarget(nullptr), _agsDebuggerOutput(nullptr) {
|
|
registerCmd("ags_debug_groups_list", WRAP_METHOD(AGSConsole, Cmd_listDebugGroups));
|
|
registerCmd("ags_debug_groups_set", WRAP_METHOD(AGSConsole, Cmd_setDebugGroupLevel));
|
|
registerCmd("ags_set_script_dump", WRAP_METHOD(AGSConsole, Cmd_SetScriptDump));
|
|
registerCmd("ags_sprite_info", WRAP_METHOD(AGSConsole, Cmd_getSpriteInfo));
|
|
registerCmd("ags_sprite_dump", WRAP_METHOD(AGSConsole, Cmd_dumpSprite));
|
|
|
|
_logOutputTarget = new LogOutputTarget();
|
|
_agsDebuggerOutput = _GP(DbgMgr).RegisterOutput("ScummVMLog", _logOutputTarget, AGS3::AGS::Shared::kDbgMsg_None);
|
|
}
|
|
|
|
AGSConsole::~AGSConsole() {
|
|
delete _logOutputTarget;
|
|
}
|
|
|
|
struct LevelName {
|
|
const char *name;
|
|
AGS3::AGS::Shared::MessageType level;
|
|
};
|
|
|
|
static const LevelName levelNames[] = {
|
|
{"none", AGS3::AGS::Shared::kDbgMsg_None},
|
|
{"alerts", AGS3::AGS::Shared::kDbgMsg_Alert},
|
|
{"fatal", AGS3::AGS::Shared::kDbgMsg_Fatal},
|
|
{"errors", AGS3::AGS::Shared::kDbgMsg_Error},
|
|
{"warnings", AGS3::AGS::Shared::kDbgMsg_None},
|
|
{"info", AGS3::AGS::Shared::kDbgMsg_Info},
|
|
{"debug", AGS3::AGS::Shared::kDbgMsg_Debug},
|
|
{nullptr, AGS3::AGS::Shared::kDbgMsg_None}
|
|
};
|
|
|
|
struct GroupName {
|
|
const char *name;
|
|
AGS3::uint32_t group;
|
|
};
|
|
|
|
static const GroupName groupNames[] = {
|
|
{"Main", AGS3::AGS::Shared::kDbgGroup_Main},
|
|
{"Game", AGS3::AGS::Shared::kDbgGroup_Game},
|
|
{"Script", AGS3::AGS::Shared::kDbgGroup_Script},
|
|
{"SpriteCache", AGS3::AGS::Shared::kDbgGroup_SprCache},
|
|
{"ManObj", AGS3::AGS::Shared::kDbgGroup_ManObj},
|
|
{nullptr, (AGS3::uint32_t)-1}
|
|
};
|
|
|
|
bool AGSConsole::Cmd_listDebugGroups(int argc, const char **argv) {
|
|
if (argc != 1) {
|
|
debugPrintf("Usage: %s\n", argv[0]);
|
|
return true;
|
|
}
|
|
|
|
debugPrintf("%-16s %-16s\n", "Name", "Level");
|
|
for (int i = 0 ; groupNames[i].name != nullptr ; ++i)
|
|
debugPrintf("%-16s %-16s\n", groupNames[i].name, getVerbosityLevel(groupNames[i].group));
|
|
return true;
|
|
}
|
|
|
|
bool AGSConsole::Cmd_setDebugGroupLevel(int argc, const char **argv) {
|
|
if (argc != 3) {
|
|
debugPrintf("Usage: %s group level\n", argv[0]);
|
|
debugPrintf(" valid groups: ");
|
|
printGroupList();
|
|
debugPrintf("\n");
|
|
debugPrintf(" valid levels: ");
|
|
printLevelList();
|
|
debugPrintf("\n");
|
|
return true;
|
|
}
|
|
|
|
bool found = false;
|
|
AGS3::uint32_t group = parseGroup(argv[1], found);
|
|
if (!found) {
|
|
debugPrintf("Unknown debug group '%s'\n", argv[1]);
|
|
debugPrintf("Valid groups are: ");
|
|
printGroupList();
|
|
debugPrintf("\n");
|
|
return true;
|
|
}
|
|
|
|
AGS3::AGS::Shared::MessageType level = parseLevel(argv[2], found);
|
|
if (!found) {
|
|
debugPrintf("Unknown level '%s'\n", argv[2]);
|
|
debugPrintf("Valid levels are: ");
|
|
printLevelList();
|
|
debugPrintf("\n");
|
|
return true;
|
|
}
|
|
|
|
_agsDebuggerOutput->SetGroupFilter(group, level);
|
|
return true;
|
|
}
|
|
|
|
const char *AGSConsole::getVerbosityLevel(AGS3::uint32_t groupID) const {
|
|
int i = 1;
|
|
while (levelNames[i].name != nullptr) {
|
|
if (!_agsDebuggerOutput->TestGroup(groupID, levelNames[i].level))
|
|
break;
|
|
++i;
|
|
}
|
|
return levelNames[i - 1].name;
|
|
}
|
|
|
|
AGS3::uint32_t AGSConsole::parseGroup(const char *name, bool &found) const {
|
|
int i = 0;
|
|
while (groupNames[i].name != nullptr) {
|
|
if (scumm_stricmp(name, groupNames[i].name) == 0) {
|
|
found = true;
|
|
return groupNames[i].group;
|
|
}
|
|
++i;
|
|
}
|
|
|
|
found = false;
|
|
return (AGS3::uint32_t)-1;
|
|
}
|
|
|
|
AGS3::AGS::Shared::MessageType AGSConsole::parseLevel(const char *name, bool &found) const {
|
|
int i = 0;
|
|
while (levelNames[i].name != nullptr) {
|
|
if (scumm_stricmp(name, levelNames[i].name) == 0) {
|
|
found = true;
|
|
return levelNames[i].level;
|
|
}
|
|
++i;
|
|
}
|
|
|
|
found = false;
|
|
return AGS3::AGS::Shared::kDbgMsg_None;
|
|
}
|
|
|
|
void AGSConsole::printGroupList() {
|
|
debugPrintf("%s", groupNames[0].name);
|
|
for (int i = 1 ; groupNames[i].name != nullptr ; ++i)
|
|
debugPrintf(", %s", groupNames[i].name);
|
|
}
|
|
|
|
void AGSConsole::printLevelList() {
|
|
debugPrintf("%s", levelNames[0].name);
|
|
for (int i = 1 ; levelNames[i].name != nullptr ; ++i)
|
|
debugPrintf(", %s", levelNames[i].name);
|
|
}
|
|
|
|
bool AGSConsole::Cmd_SetScriptDump(int argc, const char **argv) {
|
|
if (argc != 2) {
|
|
debugPrintf("Usage: %s [on|off]\n", argv[0]);
|
|
return true;
|
|
}
|
|
|
|
if (strcmp(argv[1], "on") == 0 || strcmp(argv[1], "true") == 0)
|
|
AGS3::ccSetOption(SCOPT_DEBUGRUN, 1);
|
|
else
|
|
AGS3::ccSetOption(SCOPT_DEBUGRUN, 0);
|
|
return true;
|
|
}
|
|
|
|
bool AGSConsole::Cmd_getSpriteInfo(int argc, const char **argv) {
|
|
if (argc != 2) {
|
|
debugPrintf("Usage: %s SpriteNumber\n", argv[0]);
|
|
return true;
|
|
}
|
|
|
|
int spriteId = atoi(argv[1]);
|
|
if (!_GP(spriteset).DoesSpriteExist(spriteId)) {
|
|
debugPrintf("Sprite %d does not exist\n", spriteId);
|
|
return true;
|
|
}
|
|
|
|
AGS3::Shared::Bitmap *sprite = _GP(spriteset)[spriteId];
|
|
if (!sprite) {
|
|
debugPrintf("Failed to get sprite %d\n", spriteId);
|
|
return true;
|
|
}
|
|
|
|
debugPrintf("Size: %dx%d\n", sprite->GetWidth(), sprite->GetHeight());
|
|
debugPrintf("Color depth: %d\n", sprite->GetColorDepth());
|
|
return true;
|
|
}
|
|
|
|
bool AGSConsole::Cmd_dumpSprite(int argc, const char **argv) {
|
|
if (argc != 2) {
|
|
debugPrintf("Usage: %s SpriteNumber\n", argv[0]);
|
|
return true;
|
|
}
|
|
|
|
int spriteId = atoi(argv[1]);
|
|
if (!_GP(spriteset).DoesSpriteExist(spriteId)) {
|
|
debugPrintf("Sprite %d does not exist\n", spriteId);
|
|
return true;
|
|
}
|
|
|
|
AGS3::Shared::Bitmap *sprite = _GP(spriteset)[spriteId];
|
|
if (!sprite) {
|
|
debugPrintf("Failed to get sprite %d\n", spriteId);
|
|
return true;
|
|
}
|
|
|
|
Common::String pngFile = Common::String::format("%s-sprite%03d.png", _vm->getGameId().c_str(), spriteId);
|
|
Common::DumpFile df;
|
|
if (df.open(pngFile)) {
|
|
byte *palette = nullptr;
|
|
if (sprite->GetColorDepth() == 8) {
|
|
palette = new byte[256 * 3];
|
|
for (int c = 0, i = 0 ; c < 256 ; ++c, i += 3) {
|
|
palette[i] = _G(current_palette)[c].r * 255 / 63;
|
|
palette[i + 1] = _G(current_palette)[c].g * 255 / 63;
|
|
palette[i + 2] = _G(current_palette)[c].b * 255 / 63;
|
|
}
|
|
}
|
|
Image::writePNG(df, sprite->GetAllegroBitmap()->getSurface().rawSurface(), palette);
|
|
delete[] palette;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
LogOutputTarget::LogOutputTarget() {
|
|
}
|
|
|
|
LogOutputTarget::~LogOutputTarget() {
|
|
}
|
|
|
|
void LogOutputTarget::PrintMessage(const AGS3::AGS::Shared::DebugMessage &msg) {
|
|
LogMessageType::Type msgType = LogMessageType::kInfo;
|
|
switch (msg.MT) {
|
|
case AGS3::AGS::Shared::kDbgMsg_None:
|
|
return;
|
|
case AGS3::AGS::Shared::kDbgMsg_Alert:
|
|
case AGS3::AGS::Shared::kDbgMsg_Fatal:
|
|
case AGS3::AGS::Shared::kDbgMsg_Error:
|
|
msgType = LogMessageType::kError;
|
|
break;
|
|
case AGS3::AGS::Shared::kDbgMsg_Warn:
|
|
msgType = LogMessageType::kWarning;
|
|
break;
|
|
case AGS3::AGS::Shared::kDbgMsg_Info:
|
|
msgType = LogMessageType::kInfo;
|
|
break;
|
|
case AGS3::AGS::Shared::kDbgMsg_Debug:
|
|
msgType = LogMessageType::kDebug;
|
|
break;
|
|
}
|
|
Common::String text = Common::String::format("%s\n", msg.Text.GetCStr());
|
|
g_system->logMessage(msgType, text.c_str());
|
|
}
|
|
|
|
|
|
} // End of namespace AGS
|