mirror of
https://github.com/KDE/konsole.git
synced 2026-05-01 19:25:46 -04:00
If this information is put anywhere it should be in a single file instead of duplicated for each file. In fact, it shouldn't be needed at all since we have the same rules on tabs and tab sizes as most other parts of kdebase svn path=/trunk/KDE/kdebase/apps/konsole/; revision=946369
324 lines
9.5 KiB
C++
324 lines
9.5 KiB
C++
/*
|
|
Copyright 2006-2008 by Robert Knight <robertknight@gmail.com>
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; either version 2 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; if not, write to the Free Software
|
|
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
|
02110-1301 USA.
|
|
*/
|
|
|
|
// Own
|
|
#include "Application.h"
|
|
|
|
// std
|
|
#include <iostream>
|
|
|
|
#include "kdebug.h"
|
|
|
|
// Qt
|
|
#include <QHashIterator>
|
|
#include <QFileInfo>
|
|
|
|
// KDE
|
|
#include <KAction>
|
|
#include <KCmdLineArgs>
|
|
#include <KDebug>
|
|
#include <KWindowSystem>
|
|
|
|
// Konsole
|
|
#include "ColorScheme.h"
|
|
#include "ProfileList.h"
|
|
#include "SessionManager.h"
|
|
#include "KeyboardTranslator.h"
|
|
#include "MainWindow.h"
|
|
#include "Session.h"
|
|
#include "TerminalDisplay.h"
|
|
#include "ViewManager.h"
|
|
|
|
using namespace Konsole;
|
|
|
|
#ifdef Q_WS_X11
|
|
Application::Application(Display* display , Qt::HANDLE visual, Qt::HANDLE colormap)
|
|
: KUniqueApplication(display,visual,colormap)
|
|
{
|
|
init();
|
|
}
|
|
#endif
|
|
|
|
Application::Application() : KUniqueApplication()
|
|
{
|
|
init();
|
|
}
|
|
|
|
void Application::init()
|
|
{
|
|
_sessionList = 0;
|
|
_backgroundInstance = 0;
|
|
|
|
// check for compositing functionality
|
|
TerminalDisplay::setTransparencyEnabled( KWindowSystem::compositingActive() );
|
|
}
|
|
|
|
Application* Application::self()
|
|
{
|
|
return (Application*)KApp;
|
|
}
|
|
|
|
MainWindow* Application::newMainWindow()
|
|
{
|
|
MainWindow* window = new MainWindow();
|
|
window->setSessionList( new ProfileList(true,window) );
|
|
|
|
connect( window , SIGNAL(newSessionRequest(Profile::Ptr,const QString&,ViewManager*)),
|
|
this , SLOT(createSession(Profile::Ptr,const QString&,ViewManager*)));
|
|
connect( window , SIGNAL(newWindowRequest(Profile::Ptr,const QString&)),
|
|
this , SLOT(createWindow(Profile::Ptr,const QString&)) );
|
|
connect( window->viewManager() , SIGNAL(viewDetached(Session*)) , this , SLOT(detachView(Session*)) );
|
|
|
|
return window;
|
|
}
|
|
|
|
void Application::listAvailableProfiles()
|
|
{
|
|
QList<QString> paths = SessionManager::instance()->availableProfilePaths();
|
|
QListIterator<QString> iter(paths);
|
|
|
|
while ( iter.hasNext() )
|
|
{
|
|
QFileInfo info(iter.next());
|
|
std::cout << info.baseName().toLocal8Bit().data() << std::endl;
|
|
}
|
|
}
|
|
|
|
int Application::newInstance()
|
|
{
|
|
KCmdLineArgs* args = KCmdLineArgs::parsedArgs();
|
|
static bool firstInstance = true;
|
|
|
|
// handle session management
|
|
if ((args->count() != 0) || !firstInstance || !isSessionRestored())
|
|
{
|
|
// check for arguments to print help or other information to the terminal,
|
|
// quit if such an argument was found
|
|
if ( processHelpArgs(args) )
|
|
return 0;
|
|
|
|
// create a new window or use an existing one
|
|
MainWindow* window = processWindowArgs(args);
|
|
|
|
// select profile to use
|
|
processProfileSelectArgs(args,window);
|
|
|
|
// process various command-line options which cause a property of the
|
|
// default profile to be changed
|
|
processProfileChangeArgs(args,window);
|
|
|
|
// create new session
|
|
Session* session = createSession( window->defaultProfile() , QString() , window->viewManager() );
|
|
if ( !args->isSet("close") )
|
|
session->setAutoClose(false);
|
|
|
|
// if the background-mode argument is supplied, start the background session
|
|
// ( or bring to the front if it already exists )
|
|
if ( args->isSet("background-mode") )
|
|
startBackgroundMode(window);
|
|
else
|
|
{
|
|
// Qt constrains top-level windows which have not been manually resized
|
|
// (via QWidget::resize()) to a maximum of 2/3rds of the screen size.
|
|
//
|
|
// This means that the terminal display might not get the width/height
|
|
// it asks for. To work around this, the widget must be manually resized
|
|
// to its sizeHint().
|
|
//
|
|
// This problem only affects the first time the application is run. After
|
|
// that KMainWindow will have manually resized the window to its saved size
|
|
// at this point (so the Qt::WA_Resized attribute will be set)
|
|
if (!window->testAttribute(Qt::WA_Resized))
|
|
window->resize(window->sizeHint());
|
|
|
|
window->show();
|
|
}
|
|
}
|
|
|
|
firstInstance = false;
|
|
args->clear();
|
|
return 0;
|
|
}
|
|
|
|
MainWindow* Application::processWindowArgs(KCmdLineArgs* args)
|
|
{
|
|
MainWindow* window = 0;
|
|
if ( args->isSet("new-tab") )
|
|
{
|
|
QListIterator<QWidget*> iter(topLevelWidgets());
|
|
iter.toBack();
|
|
while ( iter.hasPrevious() )
|
|
{
|
|
window = qobject_cast<MainWindow*>(iter.previous());
|
|
if ( window != 0 )
|
|
break;
|
|
}
|
|
}
|
|
|
|
if ( window == 0 )
|
|
{
|
|
window = newMainWindow();
|
|
}
|
|
return window;
|
|
}
|
|
|
|
void Application::processProfileSelectArgs(KCmdLineArgs* args,MainWindow* window)
|
|
{
|
|
if ( args->isSet("profile") )
|
|
{
|
|
Profile::Ptr profile = SessionManager::instance()->loadProfile(args->getOption("profile"));
|
|
if (!profile)
|
|
profile = SessionManager::instance()->defaultProfile();
|
|
|
|
window->setDefaultProfile(profile);
|
|
}
|
|
}
|
|
|
|
bool Application::processHelpArgs(KCmdLineArgs* args)
|
|
{
|
|
if ( args->isSet("list-profiles") )
|
|
{
|
|
listAvailableProfiles();
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
void Application::processProfileChangeArgs(KCmdLineArgs* args,MainWindow* window)
|
|
{
|
|
Profile::Ptr defaultProfile = window->defaultProfile();
|
|
if (!defaultProfile)
|
|
defaultProfile = SessionManager::instance()->defaultProfile();
|
|
Profile::Ptr newProfile = Profile::Ptr(new Profile(defaultProfile));
|
|
newProfile->setHidden(true);
|
|
// run a custom command
|
|
if ( args->isSet("e") )
|
|
{
|
|
QStringList arguments;
|
|
arguments << args->getOption("e");
|
|
for ( int i = 0 ; i < args->count() ; i++ )
|
|
arguments << args->arg(i);
|
|
|
|
newProfile->setProperty(Profile::Command,args->getOption("e"));
|
|
newProfile->setProperty(Profile::Arguments,arguments);
|
|
}
|
|
|
|
// change the initial working directory
|
|
if( args->isSet("workdir") )
|
|
{
|
|
newProfile->setProperty(Profile::Directory,args->getOption("workdir"));
|
|
}
|
|
|
|
// temporary changes to profile options specified on the command line
|
|
foreach( const QString &value , args->getOptionList("p") )
|
|
{
|
|
ProfileCommandParser parser;
|
|
|
|
QHashIterator<Profile::Property,QVariant> iter(parser.parse(value));
|
|
while ( iter.hasNext() )
|
|
{
|
|
iter.next();
|
|
newProfile->setProperty(iter.key(),iter.value());
|
|
}
|
|
}
|
|
|
|
if (!newProfile->isEmpty())
|
|
{
|
|
window->setDefaultProfile(newProfile);
|
|
}
|
|
}
|
|
|
|
void Application::startBackgroundMode(MainWindow* window)
|
|
{
|
|
if ( _backgroundInstance )
|
|
{
|
|
return;
|
|
}
|
|
|
|
KAction* action = new KAction(window);
|
|
KShortcut shortcut = action->shortcut();
|
|
action->setObjectName("Konsole Background Mode");
|
|
//TODO - Customisable key sequence for this
|
|
action->setGlobalShortcut( KShortcut(QKeySequence(Qt::Key_F12)) );
|
|
|
|
_backgroundInstance = window;
|
|
|
|
connect( action , SIGNAL(triggered()) , this , SLOT(toggleBackgroundInstance()) );
|
|
}
|
|
|
|
void Application::toggleBackgroundInstance()
|
|
{
|
|
Q_ASSERT( _backgroundInstance );
|
|
|
|
if ( !_backgroundInstance->isVisible() )
|
|
{
|
|
_backgroundInstance->show();
|
|
// ensure that the active terminal display has the focus.
|
|
// without this, an odd problem occurred where the focus widgetwould change
|
|
// each time the background instance was shown
|
|
_backgroundInstance->viewManager()->activeView()->setFocus();
|
|
}
|
|
else
|
|
{
|
|
_backgroundInstance->hide();
|
|
}
|
|
}
|
|
|
|
Application::~Application()
|
|
{
|
|
SessionManager::instance()->closeAll();
|
|
SessionManager::instance()->saveState();
|
|
}
|
|
|
|
void Application::detachView(Session* session)
|
|
{
|
|
MainWindow* window = newMainWindow();
|
|
window->viewManager()->createView(session);
|
|
window->show();
|
|
}
|
|
|
|
void Application::createWindow(Profile::Ptr profile , const QString& directory)
|
|
{
|
|
MainWindow* window = newMainWindow();
|
|
window->setDefaultProfile(profile);
|
|
createSession(profile,directory,window->viewManager());
|
|
window->show();
|
|
}
|
|
|
|
Session* Application::createSession(Profile::Ptr profile, const QString& directory , ViewManager* view)
|
|
{
|
|
if (!profile)
|
|
profile = SessionManager::instance()->defaultProfile();
|
|
|
|
Session* session = SessionManager::instance()->createSession(profile);
|
|
|
|
if (!directory.isEmpty() && profile->property<bool>(Profile::StartInCurrentSessionDir))
|
|
session->setInitialWorkingDirectory(directory);
|
|
|
|
// create view before starting the session process so that the session doesn't suffer
|
|
// a change in terminal size right after the session starts. some applications such as GNU Screen
|
|
// and Midnight Commander don't like this happening
|
|
view->createView(session);
|
|
session->run();
|
|
|
|
return session;
|
|
}
|
|
|
|
#include "Application.moc"
|
|
|