Files
bsnes/higan/target-ethos/general/presentation.cpp
Tim Allen d59ae34e12 Update to higan v091r14 and ananke v00r03 releases.
byuu says:

higan changelog:
- generates title displayed in emulator window by asking the core
- core builds title solely from "information/title" ... if it's not
  there, you don't get a title at all
- sub-system load menu is gone ... since there are multiple revisions of
  the SGB, this never really worked well anyway
- to load an SGB, BS-X or ST cartridge, load the base cartridge first
- "File->Load Game" moved to "Load->Import Game" ... may cause a bit of
  confusion to new users, but I don't like having a single-item menu,
  we'll just have to explain it to new users
- browser window redone to look like ananke
  - home button here goes to ~/Emulation rather than just ~ like ananke,
    since this is the home of game folders
  - game folder icon is now the executable icon for the Tango theme
    (orange diamond), meant to represent a complete game rather than
    a game file or archive

ananke changelog:
- outputs GBC games to "Game Boy Color/" instead of "Game Boy/"
- adds the file basename to "information/title"

Known issues:
- using ananke to load a GB game trips the Super Famicom SGB mode and
  fails (need to make the full-path auto-detection ignore non-bootable
  systems)
- need to dump and test some BS-X media before releasing
- ananke lacks BS-X Satellaview cartridge support
- v092 isn't going to let you retarget the ananke/higan game folder path
  of ~/Emulation, you will have to wait for a future version if that
  bothers you so greatly

[Later, after the v092 release, byuu posted this additional changelog:
    - kill laevateinn
    - add title()
    - add bootable, remove load
    - combine file, library
    - combine [][][] paths
    - fix SFC subtype handling XML->BML
    - update file browser to use buttons
    - update file browser keyboard handling
    - update system XML->BML
    - fix sufami turbo hashing
    - remove Cartridge::manifest
]
2013-01-14 23:13:48 +11:00

232 lines
9.0 KiB
C++
Executable File

Presentation *presentation = nullptr;
void Presentation::synchronize() {
for(auto &emulator : emulatorList) emulator->menu.setVisible(false);
for(auto &emulator : emulatorList) {
if(emulator->interface == application->active) {
active = emulator;
emulator->menu.setVisible(true);
}
}
shaderNone.setChecked();
if(config->video.shader == "None") shaderNone.setChecked();
if(config->video.shader == "Blur") shaderBlur.setChecked();
for(auto &shader : shaderList) {
string name = notdir(nall::basename(config->video.shader));
if(auto position = name.position(".")) name[position()] = 0;
if(name == shader->text()) shader->setChecked();
}
switch(config->video.scaleMode) {
case 0: centerVideo.setChecked(); break;
case 1: scaleVideo.setChecked(); break;
case 2: stretchVideo.setChecked(); break;
}
aspectCorrection.setChecked(config->video.aspectCorrection);
maskOverscan.setChecked(config->video.maskOverscan);
synchronizeVideo.setChecked(config->video.synchronize);
synchronizeAudio.setChecked(config->audio.synchronize);
muteAudio.setChecked(config->audio.mute);
if(application->active == nullptr) {
toolsMenu.setVisible(false);
} else {
toolsMenu.setVisible(true);
saveStateMenu.setVisible(system().information.capability.states);
loadStateMenu.setVisible(system().information.capability.states);
stateMenuSeparator.setVisible(system().information.capability.states);
resizeWindow.setVisible(config->video.scaleMode != 2);
stateManager.setVisible(system().information.capability.states);
cheatEditor.setVisible(system().information.capability.cheats);
synchronizeTime.setVisible(system().rtc());
}
}
void Presentation::setSystemName(const string &name) {
if(active) active->menu.setText(name);
}
Presentation::Presentation() : active(nullptr) {
bootstrap();
loadShaders();
setGeometry({256, 256, 720, 480});
windowManager->append(this, "Presentation");
setTitle({::Emulator::Name, " v", ::Emulator::Version});
setBackgroundColor({0, 0, 0});
setMenuVisible();
setStatusVisible();
loadMenu.setText("Library");
loadImport.setText("Import Game ...");
settingsMenu.setText("Settings");
videoMenu.setText("Video");
centerVideo.setText("Center");
scaleVideo.setText("Scale");
stretchVideo.setText("Stretch");
RadioItem::group(centerVideo, scaleVideo, stretchVideo);
aspectCorrection.setText("Aspect Correction");
maskOverscan.setText("Mask Overscan");
shaderMenu.setText("Shader");
shaderNone.setText("None");
shaderBlur.setText("Blur");
synchronizeVideo.setText("Synchronize Video");
synchronizeAudio.setText("Synchronize Audio");
muteAudio.setText("Mute Audio");
configurationSettings.setText("Configuration ...");
toolsMenu.setText("Tools");
saveStateMenu.setText("Save State");
for(unsigned n = 0; n < 5; n++) saveStateItem[n].setText({"Slot ", 1 + n});
loadStateMenu.setText("Load State");
for(unsigned n = 0; n < 5; n++) loadStateItem[n].setText({"Slot ", 1 + n});
resizeWindow.setText("Resize Window");
stateManager.setText("State Manager");
cheatEditor.setText("Cheat Editor");
synchronizeTime.setText("Synchronize Time");
append(loadMenu);
for(auto &item : loadListSystem) loadMenu.append(*item);
if(application->ananke.opened()) {
loadMenu.append(loadSeparator);
loadMenu.append(loadImport);
}
for(auto &systemItem : emulatorList) append(systemItem->menu);
append(settingsMenu);
settingsMenu.append(videoMenu);
videoMenu.append(centerVideo, scaleVideo, stretchVideo, *new Separator, aspectCorrection, maskOverscan);
settingsMenu.append(shaderMenu);
shaderMenu.append(shaderNone, shaderBlur);
if(shaderList.size() > 0) shaderMenu.append(*new Separator);
for(auto &shader : shaderList) shaderMenu.append(*shader);
settingsMenu.append(*new Separator);
settingsMenu.append(synchronizeVideo, synchronizeAudio, muteAudio);
settingsMenu.append(*new Separator);
settingsMenu.append(configurationSettings);
append(toolsMenu);
toolsMenu.append(saveStateMenu);
for(unsigned n = 0; n < 5; n++) saveStateMenu.append(saveStateItem[n]);
toolsMenu.append(loadStateMenu);
for(unsigned n = 0; n < 5; n++) loadStateMenu.append(loadStateItem[n]);
toolsMenu.append(stateMenuSeparator);
toolsMenu.append(resizeWindow, stateManager, cheatEditor, synchronizeTime);
append(layout);
layout.append(viewport, {0, 0, 720, 480});
onSize = [&] { utility->resize(); };
onClose = [&] { application->quit = true; };
loadImport.onActivate = [&] {
if(application->ananke.opened() == false) return;
function<string ()> browse = application->ananke.sym("ananke_browse");
if(browse == false) return;
string pathname = browse();
if(pathname.empty()) return;
utility->loadMedia(pathname);
};
shaderNone.onActivate = [&] { config->video.shader = "None"; utility->updateShader(); };
shaderBlur.onActivate = [&] { config->video.shader = "Blur"; utility->updateShader(); };
centerVideo.onActivate = [&] { config->video.scaleMode = 0; utility->resize(); };
scaleVideo.onActivate = [&] { config->video.scaleMode = 1; utility->resize(); };
stretchVideo.onActivate = [&] { config->video.scaleMode = 2; utility->resize(); };
aspectCorrection.onToggle = [&] { config->video.aspectCorrection = aspectCorrection.checked(); utility->resize(); };
maskOverscan.onToggle = [&] { config->video.maskOverscan = maskOverscan.checked(); };
synchronizeVideo.onToggle = [&] { config->video.synchronize = synchronizeVideo.checked(); utility->synchronizeRuby(); };
synchronizeAudio.onToggle = [&] { config->audio.synchronize = synchronizeAudio.checked(); utility->synchronizeRuby(); };
muteAudio.onToggle = [&] { config->audio.mute = muteAudio.checked(); utility->synchronizeRuby(); };
configurationSettings.onActivate = [&] { settings->setVisible(); settings->panelList.setFocused(); };
for(unsigned n = 0; n < 5; n++) saveStateItem[n].onActivate = [=] { utility->saveState(1 + n); };
for(unsigned n = 0; n < 5; n++) loadStateItem[n].onActivate = [=] { utility->loadState(1 + n); };
resizeWindow.onActivate = [&] { utility->resize(true); };
stateManager.onActivate = [&] { ::stateManager->setVisible(); };
cheatEditor.onActivate = [&] { ::cheatEditor->setVisible(); };
synchronizeTime.onActivate = [&] { system().rtcsync(); };
synchronize();
}
void Presentation::bootstrap() {
for(auto &emulator : application->emulator) {
auto iEmulator = new Emulator;
iEmulator->interface = emulator;
for(auto &media : emulator->media) {
if(media.bootable == false) continue; //do not add sub-cartridge slot entries to menu
Item *item = new Item;
item->onActivate = [=, &media] {
utility->loadMedia(iEmulator->interface, media);
};
item->setText({media.name, " ..."});
loadListSystem.append(item);
}
iEmulator->menu.setText(emulator->information.name);
iEmulator->power.setText("Power");
iEmulator->reset.setText("Reset");
iEmulator->unload.setText("Unload");
for(auto &port : emulator->port) {
auto iPort = new Emulator::Port;
iPort->menu.setText(port.name);
iEmulator->port.append(iPort);
for(auto &device : port.device) {
auto iDevice = new RadioItem;
iDevice->setText(device.name);
iDevice->onActivate = [=] { utility->connect(port.id, device.id); };
iPort->group.append(*iDevice);
iPort->device.append(iDevice);
}
RadioItem::group(iPort->group);
}
iEmulator->menu.append(iEmulator->power);
if(emulator->information.resettable)
iEmulator->menu.append(iEmulator->reset);
iEmulator->menu.append(*new Separator);
unsigned visiblePorts = 0;
for(auto &iPort : iEmulator->port) {
iEmulator->menu.append(iPort->menu);
if(iPort->device.size() <= 1) iPort->menu.setVisible(false);
else visiblePorts++;
for(auto &iDevice : iPort->device) {
iPort->menu.append(*iDevice);
}
}
iEmulator->menu.append(iEmulator->controllerSeparator);
if(visiblePorts == 0) iEmulator->controllerSeparator.setVisible(false);
iEmulator->menu.append(iEmulator->unload);
iEmulator->power.onActivate = {&Utility::power, utility};
iEmulator->reset.onActivate = {&Utility::reset, utility};
iEmulator->unload.onActivate = {&Utility::unload, utility};
emulatorList.append(iEmulator);
}
}
void Presentation::loadShaders() {
string pathname = application->path("Video Shaders/");
lstring files = directory::files(pathname);
for(auto &filename : files) {
auto shader = new RadioItem;
string name = filename;
if(auto position = name.position(".")) name[position()] = 0;
shader->setText(name);
shader->onActivate = [=] {
config->video.shader = {pathname, filename};
utility->updateShader();
};
shaderList.append(shader);
}
set<RadioItem&> group;
group.append(shaderNone);
group.append(shaderBlur);
for(auto &shader : shaderList) group.append(*shader);
RadioItem::group(group);
}