Associating a file type to my program?
-
I have a multi tab text editor program and I want to associate a file type to it, so when we double click on the file, my program will open it in a new tab.
From my understanding, I'll need to first register the file type and shell command in registry to:
HKEY_CURRENT_USER\SOFTWARE\Classes\.myextension
HKEY_CURRENT_USER\SOFTWARE\Classes\.myextension\Shell\Open\Command = "C:\my_program.exe" "%1"
.And then I can retrieve the file path in
main(int argc, char *argv[])
in my c++ file withargv[0]
.But how do I keep my program at only one instance? Right now if I double click the file type, it will open a new instance of my program.
-
@lansing said in Associating a file type to my program?:
But how do I keep my program at only one instance?
See this thread: https://forum.qt.io/topic/98417/how-to-create-singleinstance-application/13
-
@lansing
clone into your project source [https://github.com/KDAB/KDSingleApplication] and include the .pri file in your .pro file -
@lansing
Glancing through that link, you will have to implement what is in the Secondary Instances sub-section. Have you done so?Here is an example of how you would start a Secondary Instance send a message with the command line arguments to the primary instance and then shut down.
That is what you want, isn't it?
-
Yes, so I got the secondary instance sending message to the first instance now. But it was sending a joined
QByteArray
and I don't know how to split it back in the slot.if( app.isSecondary() ) { app.sendMessage( app.arguments().join(' ').toUtf8() ); return 0; } else { QObject::connect( &app, &SingleApplication::receivedMessage, mainwindow, MainWindow::slotReceivedMessage ); }
The QByteArray I received is
"my_program.exe D:\myfile.txt"
, how do I get themyfile.txt
string? -
Hi,
You can split your string however why to just send the relevant arguments rather than just all of them ?
-
@lansing
WellQString::split()
will be the simplest to handle"my_program.exe D:\myfile.txt"
. Though you might want to test with a space in the filename passed in, that might be more tricky, don't know if you can use theQString::split(const QRegularExpression &re)
overload for that. -
@SGaist said in Associating a file type to my program?:
Hi,
You can split your string however why to just send the relevant arguments rather than just all of them ?
Oh yes you're right, I can just send
app.sendMessage( argv[1] )
. A new problem I see is that my file path that was sent will get shrink if it's too long. Like this
C:\Users\Me\Desktop\MYFILE~1.TXT
. Is this normal? -
I've been trying for 2 days but I couldn't get it to work:
main.cpp
int main(int argc, char *argv[]) { SingleApplication application( argc, argv, true); mainWindow = new MainWindow(); if (application.isSecondary()) { if (application.arguments().count() == 2) { application.sendMessage( argv[1] ); } return 0; } else { QObject::connect(&application, &SingleApplication::receivedMessage, mainWindow , &MainWindow::slotReceivedMessage); }
mainwindow.cpp
namespace Win32 { #include "Windows.h" } #define BUFSIZE 4096 void MainWindow::slotReceivedMessage(int instanceId, QByteArray message) { Win32::DWORD retval=0; Win32::BOOL success; Win32::TCHAR buffer[BUFSIZE]; Win32::TCHAR buf[BUFSIZE]; Win32::TCHAR** lppPart={NULL}; // convert char * to wchar_t * const size_t WCHARBUF = 100; wchar_t message_t[WCHARBUF]; Win32::MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, message, -1, message_t, WCHARBUF); // get full filename from short filename retval = Win32::GetFullPathName(message_t, BUFSIZE, buffer, lppPart); QString filePath = QString::fromWCharArray(buffer); qDebug() << message; qDebug() << filePath; }
Since
GetFullPathName
needs a wchar_t as input, I have to first convert the char to wchar_t, then convert it to full path name.But when printing out with debug, both the input(
message
) and output(filePath
) are still the same. TheGetFullPathName
wasn't doing anything. What am I doing wrong?