Added Single Instantiation mode, which makes starting a second copy of FCEUX with a path to a game make it load the file into the first, then exit. To enable, set SingleInstanceOnly 1 in the config file. If someone else wants to edit things to make this easy on the user, go for it. If started with nothing in the command line, it will simply start a second copy.
This commit is contained in:
parent
bca41a8c4b
commit
b68d9a91b8
|
@ -1,3 +1,4 @@
|
|||
19-may-2010 - ugetab - Win32 - Added single-instance mode, which makes starting a second copy of FCEUX load the file into the first, then exit.
|
||||
18-may-2010 - adelikat - Movie + loadstate errors are handled more gracefully now, more informative error messages and the movie doesn't have to stop
|
||||
18-may-2010 - adelikat - Implemented a "full savestate-movie load" mode similar to the implementation in VBA-rr & SNES9x-rr. In this mode loading a savestate in read+write doesn't truncate the movie to its frame count immediately. Instead it waits until input is recording into the movie (next frame). For win32 this feature is togglable in movie options and the context menu. For SDL this is off by default and a toggle will need to be added.
|
||||
17-may-2010 - adelikat - Made gamepad 2 off by default.
|
||||
|
|
|
@ -63,6 +63,7 @@ extern int CurrentState;
|
|||
extern bool pauseWhileActive; //adelikat: Cheats dialog
|
||||
extern bool AVIdisableMovieMessages;
|
||||
extern bool replaceP2StartWithMicrophone;
|
||||
extern bool SingleInstanceOnly;
|
||||
extern bool oldInputDisplay;
|
||||
extern bool fullSaveStateLoads;
|
||||
|
||||
|
@ -313,6 +314,7 @@ static CFGSTRUCT fceuconfig[] = {
|
|||
AC(pauseWhileActive),
|
||||
AC(AVIdisableMovieMessages),
|
||||
AC(replaceP2StartWithMicrophone),
|
||||
AC(SingleInstanceOnly),
|
||||
|
||||
ENDCFGSTRUCT
|
||||
};
|
||||
|
|
|
@ -185,11 +185,15 @@ int erendlinep = 239;
|
|||
//mbg 6/30/06 - indicates that the main loop should close the game as soon as it can
|
||||
bool closeGame = false;
|
||||
|
||||
|
||||
// Counts the number of frames that have not been displayed.
|
||||
// Used for the bot, to skip frames (makes things faster).
|
||||
int BotFramesSkipped = 0;
|
||||
|
||||
// Instantiated FCEUX stuff:
|
||||
bool SingleInstanceOnly=false; // Enable/disable option
|
||||
bool DoInstantiatedExit=false;
|
||||
HWND DoInstantiatedExitWindow;
|
||||
|
||||
// Internal functions
|
||||
void SetDirs()
|
||||
{
|
||||
|
@ -580,6 +584,48 @@ void initDirectories()
|
|||
}
|
||||
}
|
||||
*/
|
||||
|
||||
static BOOL CALLBACK EnumCallbackFCEUXInstantiated(HWND hWnd, LPARAM lParam)
|
||||
{
|
||||
//LPSTR lpClassName = '\0';
|
||||
std::string TempString;
|
||||
char buf[512];
|
||||
bool PassedTest=true;
|
||||
|
||||
GetClassName(hWnd, buf, 511);
|
||||
//Console.WriteLine(lpClassName.ToString());
|
||||
|
||||
TempString = buf;
|
||||
|
||||
if (TempString != "FCEUXWindowClass")
|
||||
return true;
|
||||
|
||||
//memset(buf, 0, 512 * sizeof(char));
|
||||
GetWindowText(hWnd, buf, 512 * sizeof(char));
|
||||
|
||||
if (hWnd != hAppWnd) {
|
||||
PassedTest = (PassedTest & (buf[0] == 'F'));
|
||||
PassedTest = (PassedTest & (buf[1] == 'C'));
|
||||
PassedTest = (PassedTest & (buf[2] == 'E'));
|
||||
PassedTest = (PassedTest & (buf[3] == 'U'));
|
||||
PassedTest = (PassedTest & (buf[4] == 'X'));
|
||||
PassedTest = (PassedTest & (buf[5] == ' '));
|
||||
PassedTest = (PassedTest & ((buf[6] >= '2') & (buf[6] <= '9')));
|
||||
PassedTest = (PassedTest & (buf[7] == '.'));
|
||||
PassedTest = (PassedTest & ((buf[8] >= '1') & (buf[8] <= '9')));
|
||||
PassedTest = (PassedTest & (buf[9] == '.'));
|
||||
PassedTest = (PassedTest & ((buf[10] >= '4') & (buf[10] <= '9')));
|
||||
|
||||
if (PassedTest) {
|
||||
DoInstantiatedExit=true;
|
||||
DoInstantiatedExitWindow = hWnd;
|
||||
}
|
||||
}
|
||||
|
||||
//printf("[%03i] Found '%s'\n", ++WinCount, buf);
|
||||
return true;
|
||||
}
|
||||
|
||||
#include "x6502.h"
|
||||
int main(int argc,char *argv[])
|
||||
{
|
||||
|
@ -624,8 +670,6 @@ int main(int argc,char *argv[])
|
|||
sprintf(TempArray,"%s\\%s",BaseDirectory.c_str(),cfgFile.c_str());
|
||||
LoadConfig(TempArray);
|
||||
|
||||
|
||||
|
||||
//Bleh, need to find a better place for this.
|
||||
{
|
||||
pal_emulation = !!pal_emulation;
|
||||
|
@ -675,6 +719,33 @@ int main(int argc,char *argv[])
|
|||
|
||||
CreateMainWindow();
|
||||
|
||||
// Do single instance coding, since we now know if the user wants it,
|
||||
// and we have a source window to send from
|
||||
// http://wiki.github.com/ffi/ffi/windows-examples
|
||||
if (SingleInstanceOnly) {
|
||||
// Checks window names / hWnds, decides if there's going to be a conflict.
|
||||
EnumDesktopWindows(NULL, EnumCallbackFCEUXInstantiated, (LPARAM)0);
|
||||
|
||||
if (DoInstantiatedExit) {
|
||||
|
||||
if(t)
|
||||
{
|
||||
COPYDATASTRUCT cData;
|
||||
DATA tData;
|
||||
|
||||
sprintf(tData.strFilePath,"%s",t);
|
||||
|
||||
cData.dwData = 1;
|
||||
cData.cbData = sizeof ( tData );
|
||||
cData.lpData = &tData;
|
||||
|
||||
SendMessage(DoInstantiatedExitWindow,WM_COPYDATA,(WPARAM)(HWND)hAppWnd, (LPARAM)(LPVOID) &cData);
|
||||
do_exit();
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(!InitDInput())
|
||||
{
|
||||
do_exit();
|
||||
|
|
|
@ -23,6 +23,13 @@
|
|||
#define GOO_CONFIRMEXIT 2 /* Confirmation before exiting. */
|
||||
#define GOO_POWERRESET 4 /* Confirm on power/reset. */
|
||||
|
||||
//For single instance mode, transfers with WM_COPYDATA
|
||||
//http://www.go4expert.com/forums/showthread.php?t=19730
|
||||
typedef struct WMCopyStruct
|
||||
{
|
||||
char strFilePath[2048];
|
||||
} DATA;
|
||||
|
||||
extern int maxconbskip;
|
||||
extern int ffbskip;
|
||||
extern void LoadNewGamey(HWND hParent, const char *initialdir);
|
||||
|
|
|
@ -1223,9 +1223,23 @@ LRESULT FAR PASCAL AppWndProc(HWND hWnd,UINT msg,WPARAM wParam,LPARAM lParam)
|
|||
int x = 0;
|
||||
|
||||
char TempArray[2048];
|
||||
PCOPYDATASTRUCT pcData;
|
||||
|
||||
switch(msg)
|
||||
{
|
||||
case WM_COPYDATA:
|
||||
|
||||
pcData = (PCOPYDATASTRUCT) lParam;
|
||||
|
||||
switch ( pcData->dwData )
|
||||
{
|
||||
case 1: //cData.dwData = 1; (can use for other types as well)
|
||||
if (!ALoad((LPSTR) ( (DATA *) (pcData->lpData) )-> strFilePath))
|
||||
MessageBox(hWnd,"File from second instance failed to open", "Failed to open file", MB_OK);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_LBUTTONDOWN:
|
||||
case WM_LBUTTONUP:
|
||||
case WM_RBUTTONDOWN:
|
||||
|
@ -2360,7 +2374,7 @@ int CreateMainWindow()
|
|||
winclass.hIconSm = LoadIcon(fceu_hInstance, "ICON_1");
|
||||
winclass.hCursor = LoadCursor(NULL, IDC_ARROW);
|
||||
winclass.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH); //mbg merge 7/17/06 added cast
|
||||
winclass.lpszClassName = "FCEULTRA";
|
||||
winclass.lpszClassName = "FCEUXWindowClass";
|
||||
|
||||
if(!RegisterClassEx(&winclass))
|
||||
{
|
||||
|
@ -2386,7 +2400,7 @@ int CreateMainWindow()
|
|||
if (MainWindow_wndy==-32000) MainWindow_wndy=0;
|
||||
hAppWnd = CreateWindowEx(
|
||||
0,
|
||||
"FCEULTRA",
|
||||
"FCEUXWindowClass",
|
||||
FCEU_NAME_AND_VERSION,
|
||||
WS_OVERLAPPEDWINDOW | WS_CLIPSIBLINGS, /* Style */
|
||||
MainWindow_wndx,
|
||||
|
|
Loading…
Reference in New Issue