/****************************************************************************
KHotKeys
Copyright ( C ) 1999 - 2001 Lubos Lunak < l . lunak @ kde . org >
Distributed under the terms of the GNU General Public License version 2.
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
# define _ACTIONS_CPP_
# ifdef HAVE_CONFIG_H
# include <config.h>
# endif
# include "actions.h"
# include <krun.h>
# include <tdeconfig.h>
# include <kdebug.h>
# include <kurifilter.h>
# include <tdeglobal.h>
# include <kstandarddirs.h>
# include <tdeapplication.h>
# include <dcopclient.h>
# include <kdesktopfile.h>
# include <tdelocale.h>
# include <tdeaccel.h>
# include <kservice.h>
# include <kprocess.h>
# include <tdemessagebox.h>
# include "windows.h"
# include "action_data.h"
# include <X11/X.h>
namespace KHotKeys
{
// Action
Action * Action : : create_cfg_read ( TDEConfig & cfg_P , Action_data * data_P )
{
TQString type = cfg_P . readEntry ( " Type " ) ;
if ( type = = " COMMAND_URL " )
return new Command_url_action ( cfg_P , data_P ) ;
if ( type = = " MENUENTRY " )
return new Menuentry_action ( cfg_P , data_P ) ;
if ( type = = " DCOP " )
return new Dcop_action ( cfg_P , data_P ) ;
if ( type = = " KEYBOARD_INPUT " )
return new Keyboard_input_action ( cfg_P , data_P ) ;
if ( type = = " ACTIVATE_WINDOW " )
return new Activate_window_action ( cfg_P , data_P ) ;
if ( type = = " WAITING " )
return new Waiting_action ( cfg_P , data_P ) ;
kdWarning ( 1217 ) < < " Unknown Action type read from cfg file: " < < type < < endl ;
return NULL ;
}
void Action : : cfg_write ( TDEConfig & cfg_P ) const
{
cfg_P . writeEntry ( " Type " , " ERROR " ) ; // derived classes should call with their type
}
// Action_list
Action_list : : Action_list ( TDEConfig & cfg_P , Action_data * data_P )
: TQPtrList < Action > ( )
{
setAutoDelete ( true ) ;
TQString save_cfg_group = cfg_P . group ( ) ;
int cnt = cfg_P . readNumEntry ( " ActionsCount " , 0 ) ;
for ( int i = 0 ;
i < cnt ;
+ + i )
{
cfg_P . setGroup ( save_cfg_group + TQString : : number ( i ) ) ;
Action * action = Action : : create_cfg_read ( cfg_P , data_P ) ;
if ( action )
append ( action ) ;
}
cfg_P . setGroup ( save_cfg_group ) ;
}
void Action_list : : cfg_write ( TDEConfig & cfg_P ) const
{
TQString save_cfg_group = cfg_P . group ( ) ;
int i = 0 ;
for ( Iterator it ( * this ) ;
it ;
+ + it , + + i )
{
cfg_P . setGroup ( save_cfg_group + TQString : : number ( i ) ) ;
it . current ( ) - > cfg_write ( cfg_P ) ;
}
cfg_P . setGroup ( save_cfg_group ) ;
cfg_P . writeEntry ( " ActionsCount " , i ) ;
}
// Command_url_action
Command_url_action : : Command_url_action ( TDEConfig & cfg_P , Action_data * data_P )
: Action ( cfg_P , data_P )
{
_command_url = cfg_P . readEntry ( " CommandURL " ) ;
}
void Command_url_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " CommandURL " , command_url ( ) ) ;
cfg_P . writeEntry ( " Type " , " COMMAND_URL " ) ; // overwrites value set in base::cfg_write()
}
void Command_url_action : : execute ( )
{
if ( command_url ( ) . isEmpty ( ) )
return ;
KURIFilterData uri ;
TQString cmd = command_url ( ) ;
static bool sm_ready = false ;
if ( ! sm_ready )
{
kapp - > propagateSessionManager ( ) ;
sm_ready = true ;
}
// int space_pos = command_url().find( ' ' );
// if( command_url()[ 0 ] != '\'' && command_url()[ 0 ] != '"' && space_pos > -1
// && command_url()[ space_pos - 1 ] != '\\' )
// cmd = command_url().left( space_pos ); // get first 'word'
uri . setData ( cmd ) ;
KURIFilter : : self ( ) - > filterURI ( uri ) ;
if ( uri . uri ( ) . isLocalFile ( ) & & ! uri . uri ( ) . hasRef ( ) )
cmd = uri . uri ( ) . path ( ) ;
else
cmd = uri . uri ( ) . url ( ) ;
switch ( uri . uriType ( ) )
{
case KURIFilterData : : LOCAL_FILE :
case KURIFilterData : : LOCAL_DIR :
case KURIFilterData : : NET_PROTOCOL :
case KURIFilterData : : HELP :
{
( void ) new KRun ( uri . uri ( ) ) ;
break ;
}
case KURIFilterData : : EXECUTABLE :
{
if ( ! kapp - > authorize ( " shell_access " ) )
return ;
if ( ! uri . hasArgsAndOptions ( ) )
{
KService : : Ptr service = KService : : serviceByDesktopName ( cmd ) ;
if ( service ! = NULL )
{
if ( ! KRun : : run ( * service , KURL : : List ( ) ) )
{
KMessageBox : : sorry ( 0 , " <qt> " + i18n ( " KHotKeys was unable to execute " ) + " ' " + cmd + " '<p> " + i18n ( " Please verify existence of the service " ) + " </qt> " , i18n ( " Unable to launch service! " ) ) ;
}
break ;
}
}
// fall though
}
case KURIFilterData : : SHELL :
{
if ( ! kapp - > authorize ( " shell_access " ) )
return ;
if ( ! KRun : : runCommand (
cmd + ( uri . hasArgsAndOptions ( ) ? uri . argsAndOptions ( ) : " " ) ,
cmd , uri . iconName ( ) ) ) {
KMessageBox : : sorry ( 0 , " <qt> " + i18n ( " KHotKeys was unable to execute " ) + " ' " + cmd + " '<p> " + i18n ( " Please verify existence and permissions of the executable file " ) + " </qt> " , i18n ( " Unable to launch program " ) ) ;
}
break ;
}
default : // error
KMessageBox : : sorry ( 0 , " <qt> " + i18n ( " KHotKeys was unable to execute " ) + " ' " + cmd + " '<p> " + i18n ( " Please verify existence and permissions of the executable file " ) + " </qt> " , i18n ( " Unable to launch program " ) ) ;
return ;
}
timeout . start ( 1000 , true ) ; // 1sec timeout
}
TQString Command_url_action : : description ( ) const
{
return i18n ( " Command/URL : " ) + command_url ( ) ;
}
Action * Command_url_action : : copy ( Action_data * data_P ) const
{
return new Command_url_action ( data_P , command_url ( ) ) ;
}
// Menuentry_action
void Menuentry_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " Type " , " MENUENTRY " ) ; // overwrites value set in base::cfg_write()
}
KService : : Ptr Menuentry_action : : service ( ) const
{
if ( ! _service )
{
const_cast < Menuentry_action * > ( this ) - > _service = KService : : serviceByStorageId ( command_url ( ) ) ;
}
return _service ;
}
void Menuentry_action : : execute ( )
{
( void ) service ( ) ;
if ( ! _service )
return ;
KRun : : run ( * _service , KURL : : List ( ) ) ;
timeout . start ( 1000 , true ) ; // 1sec timeout
}
TQString Menuentry_action : : description ( ) const
{
( void ) service ( ) ;
return i18n ( " Menuentry : " ) + ( _service ? _service - > name ( ) : TQString : : null ) ;
}
Action * Menuentry_action : : copy ( Action_data * data_P ) const
{
return new Menuentry_action ( data_P , command_url ( ) ) ;
}
// Dcop_action
Dcop_action : : Dcop_action ( TDEConfig & cfg_P , Action_data * data_P )
: Action ( cfg_P , data_P )
{
app = cfg_P . readEntry ( " RemoteApp " ) ;
obj = cfg_P . readEntry ( " RemoteObj " ) ;
call = cfg_P . readEntry ( " Call " ) ;
args = cfg_P . readEntry ( " Arguments " ) ;
}
void Dcop_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " Type " , " DCOP " ) ; // overwrites value set in base::cfg_write()
cfg_P . writeEntry ( " RemoteApp " , app ) ;
cfg_P . writeEntry ( " RemoteObj " , obj ) ;
cfg_P . writeEntry ( " Call " , call ) ;
cfg_P . writeEntry ( " Arguments " , args ) ;
}
void Dcop_action : : execute ( )
{
if ( app . isEmpty ( ) | | obj . isEmpty ( ) | | call . isEmpty ( ) )
return ;
TQStringList args_list ;
TQString args_str = args ;
while ( ! args_str . isEmpty ( ) )
{
unsigned int pos = 0 ;
while ( args_str [ pos ] = = ' ' )
+ + pos ;
if ( args_str [ pos ] = = ' \" ' | | args_str [ pos ] = = ' \' ' )
{
TQString val = " " ;
TQChar sep = args_str [ pos ] ;
bool skip = false ;
+ + pos ;
for ( ;
pos < args_str . length ( ) ;
+ + pos )
{
if ( args_str [ pos ] = = ' \\ ' )
{
skip = true ;
continue ;
}
if ( ! skip & & args_str [ pos ] = = sep )
break ;
skip = false ;
val + = args_str [ pos ] ;
}
if ( pos > = args_str . length ( ) )
return ;
+ + pos ;
args_str = args_str . mid ( pos ) ;
args_list . append ( val ) ;
}
else
{
// one word
if ( pos ! = 0 )
args_str = args_str . mid ( pos ) ;
int nxt_pos = args_str . find ( ' ' ) ;
args_list . append ( args_str . left ( nxt_pos ) ) ; // should be ok if nxt_pos is -1
args_str = nxt_pos > = 0 ? args_str . mid ( nxt_pos ) : " " ;
}
}
kdDebug ( 1217 ) < < " DCOP call: " < < app < < " : " < < obj < < " : " < < call < < " : " < < args_list < < endl ;
TDEProcess proc ;
proc < < " dcop " < < app < < obj < < call < < args_list ;
proc . start ( TDEProcess : : DontCare ) ;
}
TQString Dcop_action : : description ( ) const
{
return i18n ( " DCOP : " ) + remote_application ( ) + " :: " + remote_object ( ) + " :: "
+ called_function ( ) ;
}
Action * Dcop_action : : copy ( Action_data * data_P ) const
{
return new Dcop_action ( data_P , remote_application ( ) , remote_object ( ) ,
called_function ( ) , arguments ( ) ) ;
}
// Keyboard_input_action
Keyboard_input_action : : Keyboard_input_action ( TDEConfig & cfg_P , Action_data * data_P )
: Action ( cfg_P , data_P )
{
_input = cfg_P . readEntry ( " Input " ) ;
if ( cfg_P . readBoolEntry ( " IsDestinationWindow " ) )
{
TQString save_cfg_group = cfg_P . group ( ) ;
cfg_P . setGroup ( save_cfg_group + " DestinationWindow " ) ;
_dest_window = new Windowdef_list ( cfg_P ) ;
_active_window = false ; // ignored with _dest_window set anyway
cfg_P . setGroup ( save_cfg_group ) ;
}
else
{
_dest_window = NULL ;
_active_window = cfg_P . readBoolEntry ( " ActiveWindow " ) ;
}
}
Keyboard_input_action : : ~ Keyboard_input_action ( )
{
delete _dest_window ;
}
void Keyboard_input_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " Type " , " KEYBOARD_INPUT " ) ; // overwrites value set in base::cfg_write()
cfg_P . writeEntry ( " Input " , input ( ) ) ;
if ( dest_window ( ) ! = NULL )
{
cfg_P . writeEntry ( " IsDestinationWindow " , true ) ;
TQString save_cfg_group = cfg_P . group ( ) ;
cfg_P . setGroup ( save_cfg_group + " DestinationWindow " ) ;
dest_window ( ) - > cfg_write ( cfg_P ) ;
cfg_P . setGroup ( save_cfg_group ) ;
}
else
cfg_P . writeEntry ( " IsDestinationWindow " , false ) ;
cfg_P . writeEntry ( " ActiveWindow " , _active_window ) ;
}
void Keyboard_input_action : : execute ( )
{
if ( input ( ) . isEmpty ( ) )
return ;
Window w = InputFocus ;
if ( dest_window ( ) ! = NULL )
{
w = windows_handler - > find_window ( dest_window ( ) ) ;
if ( w = = None )
w = InputFocus ;
}
else
{
if ( ! _active_window )
w = windows_handler - > action_window ( ) ;
if ( w = = None )
w = InputFocus ;
}
int last_index = - 1 , start = 0 ;
while ( ( last_index = input ( ) . find ( ' : ' , last_index + 1 ) ) ! = - 1 ) // find next ';'
{
TQString key = input ( ) . mid ( start , last_index - start ) . stripWhiteSpace ( ) ;
if ( key = = " Enter " & & KKey ( key ) . keyCodeQt ( ) = = 0 )
key = " Return " ; // CHECKE hack
keyboard_handler - > send_macro_key ( KKey ( key ) , w ) ;
start = last_index + 1 ;
}
// and the last one
TQString key = input ( ) . mid ( start , input ( ) . length ( ) ) . stripWhiteSpace ( ) ;
if ( key = = " Enter " & & KKey ( key ) . keyCodeQt ( ) = = 0 )
key = " Return " ;
keyboard_handler - > send_macro_key ( KKey ( key ) , w ) ; // the rest
XFlush ( tqt_xdisplay ( ) ) ;
}
TQString Keyboard_input_action : : description ( ) const
{
TQString tmp = input ( ) ;
tmp . replace ( ' \n ' , ' ' ) ;
tmp . truncate ( 30 ) ;
return i18n ( " Keyboard input : " ) + tmp ;
}
Action * Keyboard_input_action : : copy ( Action_data * data_P ) const
{
return new Keyboard_input_action ( data_P , input ( ) ,
dest_window ( ) ? dest_window ( ) - > copy ( ) : NULL , _active_window ) ;
}
// Activate_window_action
Activate_window_action : : Activate_window_action ( TDEConfig & cfg_P , Action_data * data_P )
: Action ( cfg_P , data_P )
{
TQString save_cfg_group = cfg_P . group ( ) ;
cfg_P . setGroup ( save_cfg_group + " Window " ) ;
_window = new Windowdef_list ( cfg_P ) ;
cfg_P . setGroup ( save_cfg_group ) ;
}
Activate_window_action : : ~ Activate_window_action ( )
{
delete _window ;
}
void Activate_window_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " Type " , " ACTIVATE_WINDOW " ) ; // overwrites value set in base::cfg_write()
TQString save_cfg_group = cfg_P . group ( ) ;
cfg_P . setGroup ( save_cfg_group + " Window " ) ;
window ( ) - > cfg_write ( cfg_P ) ;
cfg_P . setGroup ( save_cfg_group ) ;
}
void Activate_window_action : : execute ( )
{
if ( window ( ) - > match ( windows_handler - > active_window ( ) ) )
return ; // is already active
WId win_id = windows_handler - > find_window ( window ( ) ) ;
if ( win_id ! = None )
windows_handler - > activate_window ( win_id ) ;
}
TQString Activate_window_action : : description ( ) const
{
return i18n ( " Activate window : " ) + window ( ) - > comment ( ) ;
}
Action * Activate_window_action : : copy ( Action_data * data_P ) const
{
return new Activate_window_action ( data_P , window ( ) - > copy ( ) ) ;
}
// Waiting_action
Waiting_action : : Waiting_action ( TDEConfig & cfg_P , Action_data * data_P )
: Action ( cfg_P , data_P )
{
_waiting_time = cfg_P . readNumEntry ( " Time " ) ;
}
void Waiting_action : : cfg_write ( TDEConfig & cfg_P ) const
{
base : : cfg_write ( cfg_P ) ;
cfg_P . writeEntry ( " Type " , " WAITING " ) ; // overwrites value set in base::cfg_write()
cfg_P . writeEntry ( " Time " , _waiting_time ) ;
}
void Waiting_action : : execute ( )
{
usleep ( _waiting_time * 1000 ) ;
}
TQString Waiting_action : : description ( ) const
{
return i18n ( " Waiting %1 ms " ) . arg ( _waiting_time ) ;
}
Action * Waiting_action : : copy ( Action_data * data_P ) const
{
return new Waiting_action ( data_P , _waiting_time ) ;
}
} // namespace KHotKeys