RomInfoWidget auto detects controllers and displays results

This commit is contained in:
thrust26 2019-02-15 22:19:19 +01:00
parent ccee7e4dc6
commit 9fba356d8b
7 changed files with 72 additions and 37 deletions

View File

@ -562,7 +562,6 @@ void Console::changePhosphor(int direction)
{
int blend = atoi(myProperties.get(Display_PPBlend).c_str());
if(direction == +1) // increase blend
{
if(blend >= 100)
@ -848,19 +847,24 @@ void Console::setControllers(const string& rommd5)
string right = myProperties.get(Controller_Right);
uInt32 size = 0;
const uInt8* image = myCart->getImage(size);
const bool swappedPorts = myProperties.get(Console_SwapPorts) != "NO";
// try to detect controllers
if(image != nullptr || size != 0)
{
left = ControllerDetector::detect(image, size, left, Controller::Left, myOSystem.settings());
right = ControllerDetector::detect(image, size, right, Controller::Right, myOSystem.settings());
left = ControllerDetector::detect(image, size, left,
!swappedPorts ? Controller::Left : Controller::Right,
myOSystem.settings());
right = ControllerDetector::detect(image, size, right,
!swappedPorts ? Controller::Right : Controller::Left,
myOSystem.settings());
}
unique_ptr<Controller> leftC = getControllerPort(rommd5, left, Controller::Left),
rightC = getControllerPort(rommd5, right, Controller::Right);
// Swap the ports if necessary
if(myProperties.get(Console_SwapPorts) == "NO")
if(!swappedPorts)
{
myLeftControl = std::move(leftC);
myRightControl = std::move(rightC);

View File

@ -393,7 +393,7 @@ bool ControllerDetector::usesPaddle(const uInt8* image, uInt32 size,
if(port == Controller::Left)
{
// check for INPT0 access
const int NUM_SIGS_0 = 13;
const int NUM_SIGS_0 = 12;
const int SIG_SIZE_0 = 3;
uInt8 signature_0[NUM_SIGS_0][SIG_SIZE_0] = {
//{ 0x24, 0x08, 0x10 }, // bit INPT0; bpl (many joystick games too!)
@ -409,7 +409,6 @@ bool ControllerDetector::usesPaddle(const uInt8* image, uInt32 size,
{ 0xb5, 0x38, 0x10 }, // lda INPT0|$30,x; bpl (Circus Atari, old code!)
{ 0xb5, 0x38, 0x30 }, // lda INPT0|$30,x; bmi (no joystick games)
{ 0x68, 0x48, 0x10 }, // pla; pha; bpl (i.a. Bachelor Party)
{ 0xa5, 0x3b, 0x30 }, // lda INPT3|$30; bmi (only Tac Scan, ports and paddles swapped)
{ 0xa5, 0x08, 0x4c }, // lda INPT0; jmp (only Backgammon)
{ 0xa4, 0x38, 0x30 }, // ldy INPT0; bmi (no joystick games)
};
@ -444,7 +443,7 @@ bool ControllerDetector::usesPaddle(const uInt8* image, uInt32 size,
else if(port == Controller::Right)
{
// check for INPT2 and indexed INPT0 access
const int NUM_SIGS_0 = 17;
const int NUM_SIGS_0 = 18;
const int SIG_SIZE_0 = 3;
uInt8 signature_0[NUM_SIGS_0][SIG_SIZE_0] = {
{ 0x24, 0x0a, 0x10 }, // bit INPT2; bpl (no joystick games)
@ -464,6 +463,7 @@ bool ControllerDetector::usesPaddle(const uInt8* image, uInt32 size,
{ 0xb5, 0x38, 0x10 }, // lda INPT0|$30,x; bpl (Circus Atari, old code!)
{ 0xb5, 0x38, 0x30 }, // lda INPT0|$30,x; bmi (no joystick games)
{ 0xa4, 0x3a, 0x30 }, // ldy INPT2|$30; bmi (no joystick games)
{ 0xa5, 0x3b, 0x30 }, // lda INPT3|$30; bmi (only Tac Scan, ports and paddles swapped)
};
const int NUM_SIGS_1 = 1;
const int SIG_SIZE_1 = 4;

View File

@ -282,6 +282,20 @@ class OSystem
*/
const FilesystemNode& romFile() const { return myRomFile; }
/**
Open the given ROM and return an array containing its contents.
Also, the properties database is updated with a valid ROM name
for this ROM (if necessary).
@param rom The file node of the ROM to open (contains path)
@param md5 The md5 calculated from the ROM file
(will be recalculated if necessary)
@param size The amount of data read into the image array
@return Unique pointer to the array
*/
BytePtr openROM(const FilesystemNode& rom, string& md5, uInt32& size);
/**
Creates a new game console from the specified romfile, and correctly
initializes the system state to start emulation of the Console.
@ -541,20 +555,6 @@ class OSystem
*/
void closeConsole();
/**
Open the given ROM and return an array containing its contents.
Also, the properties database is updated with a valid ROM name
for this ROM (if necessary).
@param rom The file node of the ROM to open (contains path)
@param md5 The md5 calculated from the ROM file
(will be recalculated if necessary)
@param size The amount of data read into the image array
@return Unique pointer to the array
*/
BytePtr openROM(const FilesystemNode& rom, string& md5, uInt32& size);
/**
Gets all possible info about the given console.

View File

@ -414,10 +414,15 @@ void GameInfoDialog::loadConsoleProperties(const Properties& props)
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void GameInfoDialog::loadControllerProperties(const Properties& props)
{
bool swapPorts = props.get(Console_SwapPorts) == "YES";
myLeftPort->setSelected(props.get(Controller_Left), "AUTO");
if(instance().hasConsole() && myLeftPort->getSelectedTag().toString() == "AUTO")
{
myLeftPortDetected->setLabel(instance().console().leftController().name() + " detected");
myLeftPortDetected->setLabel((!swapPorts
? instance().console().leftController().name()
: instance().console().rightController().name())
+ " detected");
}
else
myLeftPortDetected->setLabel("");
@ -425,7 +430,10 @@ void GameInfoDialog::loadControllerProperties(const Properties& props)
myRightPort->setSelected(props.get(Controller_Right), "AUTO");
if(instance().hasConsole() && myRightPort->getSelectedTag().toString() == "AUTO")
{
myRightPortDetected->setLabel(instance().console().rightController().name() + " detected");
myRightPortDetected->setLabel((!swapPorts
? instance().console().rightController().name()
: instance().console().leftController().name())
+ " detected");
}
else
myRightPortDetected->setLabel("");

View File

@ -249,7 +249,13 @@ void LauncherDialog::loadConfig()
Dialog::setFocus(getFocusList()[mySelectedItem]);
if(myRomInfoWidget)
myRomInfoWidget->loadConfig();
{
int item = myList->getSelected();
if(item < 0) return;
const FilesystemNode node(myGameList->path(item));
myRomInfoWidget->loadConfig(node);
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -339,7 +345,7 @@ void LauncherDialog::loadRomInfo()
Properties props;
instance().propSet().getMD5WithInsert(node, myGameList->md5(item), props);
myRomInfoWidget->setProperties(props);
myRomInfoWidget->setProperties(props, node);
}
else
myRomInfoWidget->clearProperties();

View File

@ -21,7 +21,7 @@
#include "FBSurface.hxx"
#include "Font.hxx"
#include "OSystem.hxx"
#include "Settings.hxx"
#include "ControllerDetector.hxx"
#include "Props.hxx"
#include "PNGLibrary.hxx"
#include "Rect.hxx"
@ -44,24 +44,24 @@ RomInfoWidget::RomInfoWidget(GuiObject* boss, const GUI::Font& font,
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void RomInfoWidget::loadConfig()
void RomInfoWidget::loadConfig(const FilesystemNode& node)
{
// The ROM may have changed since we were last in the browser, either
// by saving a different image or through a change in video renderer,
// so we reload the properties
if(myHaveProperties)
parseProperties();
parseProperties(node);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void RomInfoWidget::setProperties(const Properties& props)
void RomInfoWidget::setProperties(const Properties& props, const FilesystemNode& node)
{
myHaveProperties = true;
myProperties = props;
// Decide whether the information should be shown immediately
if(instance().eventHandler().state() == EventHandlerState::LAUNCHER)
parseProperties();
parseProperties(node);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -77,7 +77,7 @@ void RomInfoWidget::clearProperties()
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void RomInfoWidget::parseProperties()
void RomInfoWidget::parseProperties(const FilesystemNode& node)
{
// Check if a surface has ever been created; if so, we use it
// The surface will always be the maximum size, but sometimes we'll
@ -125,9 +125,26 @@ void RomInfoWidget::parseProperties()
myRomInfo.push_back("Rarity: " + myProperties.get(Cartridge_Rarity));
myRomInfo.push_back("Note: " + myProperties.get(Cartridge_Note));
bool swappedPorts = myProperties.get(Console_SwapPorts) == "YES";
myRomInfo.push_back("Controllers: " + (!swappedPorts
? myProperties.get(Controller_Left) + " (left), " + myProperties.get(Controller_Right) + " (right)"
: myProperties.get(Controller_Right) + " (left), " + myProperties.get(Controller_Left) + " (right)"));
string left = myProperties.get(Controller_Left);
string right = myProperties.get(Controller_Right);
// load the image for auto detection
BytePtr image;
string md5 = myProperties.get(Cartridge_MD5);
uInt32 size = 0;
if(node.exists() && !node.isDirectory() && (image = instance().openROM(node, md5, size)) != nullptr)
{
left = ControllerDetector::detect(image.get(), size, left,
!swappedPorts ? Controller::Jack::Left : Controller::Jack::Right,
instance().settings());
right = ControllerDetector::detect(image.get(), size, right,
!swappedPorts ? Controller::Jack::Right : Controller::Jack::Left,
instance().settings());
}
myRomInfo.push_back("Controllers: " + (left + " (left), " + right + " (right)"));
#if 0
myRomInfo.push_back("YStart/Height: " + myProperties.get(Display_YStart) +
" " + myProperties.get(Display_Height));

View File

@ -34,15 +34,15 @@ class RomInfoWidget : public Widget
int x, int y, int w, int h);
virtual ~RomInfoWidget() = default;
void setProperties(const Properties& props);
void setProperties(const Properties& props, const FilesystemNode& node);
void clearProperties();
void loadConfig() override;
void loadConfig(const FilesystemNode& node);
protected:
void drawWidget(bool hilite) override;
private:
void parseProperties();
void parseProperties(const FilesystemNode& node);
private:
// Surface pointer holding the PNG image