46
extern "C" EXPORT int GetPluginInterfaceVersion()
48
return PLUGIN_INTERFACE_VERSION;
51
QMakePlugin::QMakePlugin(IManager *manager)
75
extern "C" EXPORT int GetPluginInterfaceVersion() { return PLUGIN_INTERFACE_VERSION; }
77
BEGIN_EVENT_TABLE(QMakePlugin, wxEvtHandler)
78
EVT_COMMAND(wxID_ANY, wxEVT_PROC_DATA_READ, QMakePlugin::OnQmakeOutput)
79
EVT_COMMAND(wxID_ANY, wxEVT_PROC_TERMINATED, QMakePlugin::OnQmakeTerminated)
82
QMakePlugin::QMakePlugin(IManager* manager)
84
, m_qmakeProcess(NULL)
54
86
m_longName = _("Qt's QMake integration with CodeLite");
55
87
m_shortName = wxT("QMakePlugin");
57
m_conf = new QmakeConf(clStandardPaths::Get().GetUserDataDir() + wxFileName::GetPathSeparator() + wxT("config/qmake.ini"));
60
EventNotifier::Get()->Connect(wxEVT_CMD_PROJ_SETTINGS_SAVED, wxCommandEventHandler(QMakePlugin::OnSaveConfig ), NULL, this);
61
EventNotifier::Get()->Connect(wxEVT_BUILD_STARTING, clBuildEventHandler(QMakePlugin::OnBuildStarting ), NULL, this);
62
EventNotifier::Get()->Connect(wxEVT_GET_PROJECT_BUILD_CMD, clBuildEventHandler(QMakePlugin::OnGetBuildCommand), NULL, this);
63
EventNotifier::Get()->Connect(wxEVT_GET_PROJECT_CLEAN_CMD, clBuildEventHandler(QMakePlugin::OnGetCleanCommand), NULL, this);
64
EventNotifier::Get()->Connect(wxEVT_GET_IS_PLUGIN_MAKEFILE, clBuildEventHandler(QMakePlugin::OnGetIsPluginMakefile), NULL, this);
65
EventNotifier::Get()->Connect(wxEVT_TREE_ITEM_FILE_ACTIVATED, wxCommandEventHandler(QMakePlugin::OnOpenFile), NULL, this);
66
EventNotifier::Get()->Connect(wxEVT_PLUGIN_EXPORT_MAKEFILE, clBuildEventHandler(QMakePlugin::OnExportMakefile), NULL, this);
69
QMakePlugin::~QMakePlugin()
74
clToolBar *QMakePlugin::CreateToolBar(wxWindow *parent)
89
m_conf = new QmakeConf(clStandardPaths::Get().GetUserDataDir() + wxFileName::GetPathSeparator() +
90
wxT("config/qmake.ini"));
93
EventNotifier::Get()->Connect(
94
wxEVT_CMD_PROJ_SETTINGS_SAVED, wxCommandEventHandler(QMakePlugin::OnSaveConfig), NULL, this);
95
EventNotifier::Get()->Connect(wxEVT_BUILD_STARTING, clBuildEventHandler(QMakePlugin::OnBuildStarting), NULL, this);
96
EventNotifier::Get()->Connect(
97
wxEVT_GET_PROJECT_BUILD_CMD, clBuildEventHandler(QMakePlugin::OnGetBuildCommand), NULL, this);
98
EventNotifier::Get()->Connect(
99
wxEVT_GET_PROJECT_CLEAN_CMD, clBuildEventHandler(QMakePlugin::OnGetCleanCommand), NULL, this);
100
EventNotifier::Get()->Connect(
101
wxEVT_GET_IS_PLUGIN_MAKEFILE, clBuildEventHandler(QMakePlugin::OnGetIsPluginMakefile), NULL, this);
102
EventNotifier::Get()->Connect(
103
wxEVT_TREE_ITEM_FILE_ACTIVATED, wxCommandEventHandler(QMakePlugin::OnOpenFile), NULL, this);
106
QMakePlugin::~QMakePlugin() { delete m_conf; }
108
clToolBar* QMakePlugin::CreateToolBar(wxWindow* parent)
76
110
// Create the toolbar to be used by the plugin
79
113
// You can use the below code a snippet:
80
114
// First, check that CodeLite allows plugin to register plugins
81
if (m_mgr->AllowToolbar()) {
115
if(m_mgr->AllowToolbar()) {
82
116
// Support both toolbars icon size
83
117
int size = m_mgr->GetToolbarIconSize();
89
123
tb->SetToolBitmapSize(wxSize(size, size));
91
125
// Add tools to the plugins toolbar. You must provide 2 sets of icons: 24x24 and 16x16
93
tb->AddTool(XRCID("qmake_settings"), _("Configure qmake"), LoadBitmapFile(wxT("qt24_preferences.png")), _("Configure qmake"));
94
tb->AddTool(XRCID("new_qmake_project"), _("Create new qmake based project"), LoadBitmapFile(wxT("qt24_new.png")), _("Create new qmake based project"));
127
tb->AddTool(XRCID("qmake_settings"),
128
_("Configure qmake"),
129
LoadBitmapFile(wxT("qt24_preferences.png")),
130
_("Configure qmake"));
131
tb->AddTool(XRCID("new_qmake_project"),
132
_("Create new qmake based project"),
133
LoadBitmapFile(wxT("qt24_new.png")),
134
_("Create new qmake based project"));
96
tb->AddTool(XRCID("qmake_settings"), _("Configure qmake"), LoadBitmapFile(wxT("qt16_preferences.png")), _("Configure qmake"));
97
tb->AddTool(XRCID("new_qmake_project"), _("Create new qmake based project"), LoadBitmapFile(wxT("qt16_new.png")), _("Create new qmake based project"));
136
tb->AddTool(XRCID("qmake_settings"),
137
_("Configure qmake"),
138
LoadBitmapFile(wxT("qt16_preferences.png")),
139
_("Configure qmake"));
140
tb->AddTool(XRCID("new_qmake_project"),
141
_("Create new qmake based project"),
142
LoadBitmapFile(wxT("qt16_new.png")),
143
_("Create new qmake based project"));
99
145
// And finally, we must call 'Realize()'
120
167
pluginsMenu->Append(wxID_ANY, wxT("QMake"), menu);
122
m_mgr->GetTheApp()->Connect(XRCID("new_qmake_project"), wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(QMakePlugin::OnNewQmakeBasedProject), NULL, (wxEvtHandler*)this);
123
m_mgr->GetTheApp()->Connect(XRCID("qmake_settings"), wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(QMakePlugin::OnSettings), NULL, (wxEvtHandler*)this);
169
wxTheApp->Connect(XRCID("new_qmake_project"),
170
wxEVT_COMMAND_MENU_SELECTED,
171
wxCommandEventHandler(QMakePlugin::OnNewQmakeBasedProject),
173
(wxEvtHandler*)this);
174
wxTheApp->Connect(XRCID("qmake_settings"),
175
wxEVT_COMMAND_MENU_SELECTED,
176
wxCommandEventHandler(QMakePlugin::OnSettings),
178
(wxEvtHandler*)this);
179
wxTheApp->Connect(XRCID("qmake_run_qmake"),
180
wxEVT_COMMAND_MENU_SELECTED,
181
wxCommandEventHandler(QMakePlugin::OnExportMakefile),
126
void QMakePlugin::HookPopupMenu(wxMenu *menu, MenuType type)
186
void QMakePlugin::HookPopupMenu(wxMenu* menu, MenuType type)
188
if(type == MenuTypeFileView_Project) {
189
if(!menu->FindItem(XRCID("qmake_run_qmake"))) {
190
menu->PrependSeparator();
191
menu->Prepend(XRCID("qmake_run_qmake"), _("Run qmake..."), _("Run qmake..."));
132
196
void QMakePlugin::UnPlug()
134
EventNotifier::Get()->Disconnect(wxEVT_CMD_PROJ_SETTINGS_SAVED, wxCommandEventHandler(QMakePlugin::OnSaveConfig ), NULL, this);
135
EventNotifier::Get()->Disconnect(wxEVT_BUILD_STARTING, clBuildEventHandler(QMakePlugin::OnBuildStarting ), NULL, this);
136
EventNotifier::Get()->Disconnect(wxEVT_GET_PROJECT_BUILD_CMD, clBuildEventHandler(QMakePlugin::OnGetBuildCommand), NULL, this);
137
EventNotifier::Get()->Disconnect(wxEVT_GET_PROJECT_CLEAN_CMD, clBuildEventHandler(QMakePlugin::OnGetCleanCommand), NULL, this);
138
EventNotifier::Get()->Disconnect(wxEVT_GET_IS_PLUGIN_MAKEFILE, clBuildEventHandler(QMakePlugin::OnGetIsPluginMakefile), NULL, this);
139
EventNotifier::Get()->Disconnect(wxEVT_TREE_ITEM_FILE_ACTIVATED, wxCommandEventHandler(QMakePlugin::OnOpenFile), NULL, this);
140
EventNotifier::Get()->Disconnect(wxEVT_PLUGIN_EXPORT_MAKEFILE, clBuildEventHandler(QMakePlugin::OnExportMakefile), NULL, this);
141
wxTheApp->Disconnect(XRCID("new_qmake_project"), wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(QMakePlugin::OnNewQmakeBasedProject), NULL, (wxEvtHandler*)this);
142
wxTheApp->Disconnect(XRCID("qmake_settings"), wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(QMakePlugin::OnSettings), NULL, (wxEvtHandler*)this);
198
EventNotifier::Get()->Disconnect(
199
wxEVT_CMD_PROJ_SETTINGS_SAVED, wxCommandEventHandler(QMakePlugin::OnSaveConfig), NULL, this);
200
EventNotifier::Get()->Disconnect(
201
wxEVT_BUILD_STARTING, clBuildEventHandler(QMakePlugin::OnBuildStarting), NULL, this);
202
EventNotifier::Get()->Disconnect(
203
wxEVT_GET_PROJECT_BUILD_CMD, clBuildEventHandler(QMakePlugin::OnGetBuildCommand), NULL, this);
204
EventNotifier::Get()->Disconnect(
205
wxEVT_GET_PROJECT_CLEAN_CMD, clBuildEventHandler(QMakePlugin::OnGetCleanCommand), NULL, this);
206
EventNotifier::Get()->Disconnect(
207
wxEVT_GET_IS_PLUGIN_MAKEFILE, clBuildEventHandler(QMakePlugin::OnGetIsPluginMakefile), NULL, this);
208
EventNotifier::Get()->Disconnect(
209
wxEVT_TREE_ITEM_FILE_ACTIVATED, wxCommandEventHandler(QMakePlugin::OnOpenFile), NULL, this);
210
wxTheApp->Disconnect(XRCID("new_qmake_project"),
211
wxEVT_COMMAND_MENU_SELECTED,
212
wxCommandEventHandler(QMakePlugin::OnNewQmakeBasedProject),
214
(wxEvtHandler*)this);
215
wxTheApp->Disconnect(XRCID("qmake_settings"),
216
wxEVT_COMMAND_MENU_SELECTED,
217
wxCommandEventHandler(QMakePlugin::OnSettings),
219
(wxEvtHandler*)this);
220
wxTheApp->Disconnect(XRCID("qmake_run_qmake"),
221
wxEVT_COMMAND_MENU_SELECTED,
222
wxCommandEventHandler(QMakePlugin::OnExportMakefile),
145
void QMakePlugin::HookProjectSettingsTab(wxBookCtrlBase* book, const wxString &projectName, const wxString &configName)
227
void QMakePlugin::HookProjectSettingsTab(wxBookCtrlBase* book, const wxString& projectName, const wxString& configName)
149
232
DoUnHookAllTabs(book);
151
QMakeTab *page = DoGetQmakeTab(configName);
234
QMakeTab* page = DoGetQmakeTab(configName);
153
236
page = new QMakeTab(book, m_conf);
154
237
page->Load(m_mgr, projectName, configName);
155
238
m_pages[configName] = page;
223
307
QmakePluginData::BuildConfPluginData bcpd;
224
wxString project = event.GetProjectName();
225
wxString config = event.GetConfigurationName();
227
if ( !DoGetData(project, config, bcpd) ) {
231
if ( !bcpd.m_enabled ) {
308
wxString project = event.GetProjectName();
309
wxString config = event.GetConfigurationName();
311
if(!DoGetData(project, config, bcpd)) {
315
if(!bcpd.m_enabled) {
319
// OK this is a qmake project
236
323
ProjectPtr p = m_mgr->GetWorkspace()->FindProjectByName(project, errMsg);
240
327
QMakeProFileGenerator generator(m_mgr, project, config);
242
// regenrate the .pro file
243
bool needRegeneration = generator.Generate();
245
wxString qmake_exe = m_conf->Read(wxString::Format(wxT("%s/qmake"), bcpd.m_qmakeConfig.c_str()));
246
wxString qmakespec = m_conf->Read(wxString::Format(wxT("%s/qmakespec"), bcpd.m_qmakeConfig.c_str()));
247
wxString qtdir = m_conf->Read(wxString::Format(wxT("%s/qtdir"), bcpd.m_qmakeConfig.c_str()));
249
// Create qmake comand
250
wxString qmake_exe_line;
251
qmake_exe.Trim().Trim(false);
252
qmakespec.Trim().Trim(false);
258
wxSetWorkingDirectory ( p->GetFileName().GetPath(wxPATH_GET_SEPARATOR|wxPATH_GET_VOLUME) );
259
wxSetEnv(wxT("QTDIR"), qtdir);
260
qmake_exe_line << wxT("\"") << qmake_exe << wxT("\" -spec ") << qmakespec << wxT(" ") << generator.GetProFileName();
262
if ( needRegeneration ) {
263
wxArrayString output;
264
ProcUtils::SafeExecuteCommand(qmake_exe_line, output);
328
if(!wxFileName::Exists(generator.GetProFileName())) {
330
::wxMessageBox(_("Could not locate pro file.\nDid you remember to run qmake? (right click on the project"),
332
wxICON_WARNING | wxCENTER);
270
bool QMakePlugin::DoGetData(const wxString& project, const wxString& conf, QmakePluginData::BuildConfPluginData &bcpd)
339
bool QMakePlugin::DoGetData(const wxString& project, const wxString& conf, QmakePluginData::BuildConfPluginData& bcpd)
273
342
ProjectPtr p = m_mgr->GetWorkspace()->FindProjectByName(project, errMsg);
275
344
wxString rawData = p->GetPluginData(wxT("qmake"));
276
QmakePluginData pd( rawData );
345
QmakePluginData pd(rawData);
277
346
return pd.GetDataForBuildConf(conf, bcpd);
284
353
QmakePluginData::BuildConfPluginData bcpd;
286
wxString project = event.GetProjectName();
287
wxString config = event.GetConfigurationName();
289
if ( !DoGetData(project, config, bcpd) ) {
294
if ( !bcpd.m_enabled ) {
299
event.SetCommand( DoGetBuildCommand(project, config, event.IsProjectOnly()) + wxT(" clean") );
355
wxString project = event.GetProjectName();
356
wxString config = event.GetConfigurationName();
358
if(!DoGetData(project, config, bcpd)) {
363
if(!bcpd.m_enabled) {
368
event.SetCommand(DoGetBuildCommand(project, config, event.IsProjectOnly()) + wxT(" clean"));
302
371
void QMakePlugin::OnGetBuildCommand(clBuildEvent& event)
304
373
QmakePluginData::BuildConfPluginData bcpd;
306
wxString project = event.GetProjectName();
307
wxString config = event.GetConfigurationName();
375
wxString project = event.GetProjectName();
376
wxString config = event.GetConfigurationName();
309
if ( !DoGetData(project, config, bcpd) ) {
378
if(!DoGetData(project, config, bcpd)) {
314
if ( !bcpd.m_enabled ) {
383
if(!bcpd.m_enabled) {
319
388
// we avoid calling event.Skip() to override the default build system by this one
320
event.SetCommand( DoGetBuildCommand(project, config, event.IsProjectOnly()) );
389
event.SetCommand(DoGetBuildCommand(project, config, event.IsProjectOnly()));
323
392
void QMakePlugin::OnGetIsPluginMakefile(clBuildEvent& event)
325
394
QmakePluginData::BuildConfPluginData bcpd;
327
396
wxString project = event.GetProjectName();
328
wxString config = event.GetConfigurationName();
397
wxString config = event.GetConfigurationName();
330
if ( !DoGetData(project, config, bcpd) ) {
399
if(!DoGetData(project, config, bcpd)) {
335
if ( bcpd.m_enabled ) {
336
405
// return without calling event.Skip()
342
wxString QMakePlugin::DoGetBuildCommand(const wxString &project, const wxString &config, bool projectOnly)
411
wxString QMakePlugin::DoGetBuildCommand(const wxString& project, const wxString& config, bool projectOnly)
344
wxUnusedVar ( config );
347
416
ProjectPtr p = m_mgr->GetWorkspace()->FindProjectByName(project, errMsg);
349
418
return wxEmptyString;
352
421
BuildConfigPtr bldConf = WorkspaceST::Get()->GetProjBuildConf(project, config);
357
if ( !projectOnly ) {
425
wxString projectMakefile;
426
projectMakefile << p->GetName() << ".mk";
427
::WrapWithQuotes(projectMakefile);
428
projectMakefile.Replace("\\", "/");
431
// part of a greater makefile, use $(MAKE)
358
432
cmd << wxT("@cd \"") << p->GetFileName().GetPath() << wxT("\" && ");
433
cmd << "$(MAKE) -f " << projectMakefile;
436
cmd = bldConf->GetCompiler()->GetTool("MAKE");
437
if(!cmd.Contains("-f")) {
440
cmd << " " << projectMakefile;
361
// fix: replace all Windows like slashes to POSIX
362
wxString command = bldConf->GetCompiler()->GetTool("MAKE");
363
command.Replace(wxT("\\"), wxT("/"));
365
cmd << command << wxT(" \"") << p->GetName() << wxT(".mk\"");
369
445
void QMakePlugin::OnNewQmakeBasedProject(wxCommandEvent& event)
371
wxUnusedVar ( event );
372
if (m_conf->GetAllConfigurations().IsEmpty()) {
373
wxMessageBox(_("There is no qmake defined, please define one from 'Plugins -> Qmake -> Settings'"), _("CodeLite"), wxOK|wxICON_WARNING|wxCENTER, m_mgr->GetTheApp()->GetTopWindow());
448
if(m_conf->GetAllConfigurations().IsEmpty()) {
449
wxMessageBox(_("There is no qmake defined, please define one from 'Plugins -> Qmake -> Settings'"),
451
wxOK | wxICON_WARNING | wxCENTER,
452
m_mgr->GetTheApp()->GetTopWindow());
377
456
NewQtProjDlg dlg(m_mgr->GetTheApp()->GetTopWindow(), m_conf, m_mgr);
378
if (dlg.ShowModal() == wxID_OK) {
379
wxString kind = dlg.GetProjectKind();
380
wxString name = dlg.GetProjectName();
381
wxString path = dlg.GetProjectPath();
382
wxString configRelease= wxT("0000");
383
wxString config = wxT("0000");
457
if(dlg.ShowModal() == wxID_OK) {
458
wxString kind = dlg.GetProjectKind();
459
wxString name = dlg.GetProjectName();
460
wxString path = dlg.GetProjectPath();
461
wxString configRelease = wxT("0000");
462
wxString config = wxT("0000");
384
463
wxString templateFile = m_mgr->GetStartupDirectory();
385
wxString type = wxEmptyString;
386
wxString qmakeSettings= dlg.GetQmake();
464
wxString type = wxEmptyString;
465
wxString qmakeSettings = dlg.GetQmake();
388
467
wxString content;
390
if ( kind == wxT("Static Library") ) {
469
if(kind == wxT("Static Library")) {
392
471
type = Project::STATIC_LIBRARY;
394
} else if ( kind == wxT("Dynamic Library") ) {
473
} else if(kind == wxT("Dynamic Library")) {
396
475
type = Project::DYNAMIC_LIBRARY;
398
} else if ( kind == wxT("Console") ) {
477
} else if(kind == wxT("Console")) {
400
479
type = Project::EXECUTABLE;
401
480
configRelease = wxT("0017CONFIG += console");
402
config = wxT("0023CONFIG += console debug");
481
config = wxT("0023CONFIG += console debug");
406
485
type = Project::EXECUTABLE;
407
config = wxT("0015CONFIG += debug");
486
config = wxT("0015CONFIG += debug");
408
487
configRelease = wxT("0000");
411
490
wxString filename(m_mgr->GetStartupDirectory() + wxT("/templates/qmake/qmake.project"));
412
if (!ReadFileWithConversion(filename, content)) {
491
if(!ReadFileWithConversion(filename, content)) {
416
495
// prepend the string lenght
417
496
qmake = wxString::Format(wxT("%04d%s"), qmakeSettings.Length(), qmakeSettings.c_str());
420
content.Replace(wxT("$(TYPE)") , type);
421
content.Replace(wxT("$(NAME)") , name);
422
content.Replace(wxT("$(CONFIG)"), config);
498
content.Replace(wxT("$(TYPE)"), type);
499
content.Replace(wxT("$(NAME)"), name);
500
content.Replace(wxT("$(CONFIG)"), config);
423
501
content.Replace(wxT("$(RELEASE_CONFIG)"), configRelease);
424
content.Replace(wxT("$(QMAKE)"), qmake);
502
content.Replace(wxT("$(QMAKE)"), qmake);
426
//save the file to the disk
504
// save the file to the disk
429
if ( !wxSetWorkingDirectory(path) ) {
430
wxMessageBox(_("Invalid project path!"), _("CodeLite"), wxOK|wxCENTER|wxICON_WARNING);
507
if(!wxSetWorkingDirectory(path)) {
508
wxMessageBox(_("Invalid project path!"), _("CodeLite"), wxOK | wxCENTER | wxICON_WARNING);
434
if ( dlg.GetCreateDirectory() ) {
512
if(dlg.GetCreateDirectory()) {
436
514
wxSetWorkingDirectory(name);
439
if ( !WriteFileWithBackup(name + wxT(".project"), content, false) ) {
440
wxMessageBox(wxString::Format(_("Failed to create .project file '%s'"), wxString(name + wxT(".project")).c_str()),
441
_("CodeLite"), wxOK|wxCENTER|wxICON_WARNING);
517
if(!WriteFileWithBackup(name + wxT(".project"), content, false)) {
518
wxMessageBox(wxString::Format(_("Failed to create .project file '%s'"),
519
wxString(name + wxT(".project")).c_str()),
521
wxOK | wxCENTER | wxICON_WARNING);
514
603
ProjectPtr p = m_mgr->GetWorkspace()->FindProjectByName(project, errMsg);
519
wxSetWorkingDirectory ( p->GetFileName().GetPath(wxPATH_GET_SEPARATOR|wxPATH_GET_VOLUME) );
520
wxSetEnv(wxT("QTDIR"), qtdir);
521
qmake_exe_line << wxT("\"") << qmake_exe << wxT("\" -spec ") << qmakespec << wxT(" ") << generator.GetProFileName();
523
wxArrayString output;
524
ProcUtils::SafeExecuteCommand(qmake_exe_line, output);
608
qmake_exe_line << wxT("\"") << qmake_exe << wxT("\" -spec ") << qmakespec << wxT(" ")
609
<< generator.GetProFileName();
611
om.insert(std::make_pair("QTDIR", qtdir));
612
EnvSetter envGuard(NULL, &om, project);
613
m_mgr->ClearOutputTab(kOutputTab_Build);
614
m_mgr->AppendOutputTabText(kOutputTab_Build, wxString() << "-- " << qmake_exe_line << "\n");
616
::CreateAsyncProcess(this, qmake_exe_line, IProcessCreateDefault, p->GetFileName().GetPath());
622
void QMakePlugin::OnQmakeOutput(wxCommandEvent& event)
624
ProcessEventData* ped = static_cast<ProcessEventData*>(event.GetClientData());
625
m_mgr->AppendOutputTabText(kOutputTab_Build, ped->GetData());
629
void QMakePlugin::OnQmakeTerminated(wxCommandEvent& event)
631
ProcessEventData* ped = static_cast<ProcessEventData*>(event.GetClientData());
633
wxDELETE(m_qmakeProcess);
634
m_mgr->AppendOutputTabText(kOutputTab_Build, "-- done\n");