Merge changes from trunk - diverged
This commit is contained in:
commit
183914c7dc
17
ChangeLog
17
ChangeLog
@ -1,9 +1,24 @@
|
|||||||
terminator 0.97:
|
terminator 1.0:
|
||||||
* Allow font dimming in inactive terminals
|
* Allow font dimming in inactive terminals
|
||||||
* Allow URL handler plugins to override label text for URL context
|
* Allow URL handler plugins to override label text for URL context
|
||||||
menus
|
menus
|
||||||
* When copying a URL, run it through the URL handler first so the
|
* When copying a URL, run it through the URL handler first so the
|
||||||
resulting URL is copied, rather than the original text
|
resulting URL is copied, rather than the original text
|
||||||
|
* Allow users to configure a custom URL handler, since the
|
||||||
|
default GTK library option is failing a lot of users in non-GNOME
|
||||||
|
environments.
|
||||||
|
* Allow rotation of a group of terminals (Andre Hilsendeger)
|
||||||
|
* Add a keyboard shortcut to insert a terminal's number (Stephen J
|
||||||
|
Boddy)
|
||||||
|
* Add a keyboard shortcut to edit the window title (Stephen J Boddy)
|
||||||
|
* Add an easy way to balance terminals by double clicking on their
|
||||||
|
separator (Stephen J Boddy)
|
||||||
|
* Add a plugin by Sinan Nalkaya to log the contents of terminals.
|
||||||
|
* Support configuration of TERM and COLORTERM, via a patch from
|
||||||
|
John Feuerstein
|
||||||
|
* Support reading configuration from alternate files, via a patch
|
||||||
|
from Pavel Khlebovich
|
||||||
|
* Bug fixes
|
||||||
|
|
||||||
terminator 0.96:
|
terminator 0.96:
|
||||||
* Unity support for opening new windows (Lucian Adrian Grijincu)
|
* Unity support for opening new windows (Lucian Adrian Grijincu)
|
||||||
|
6
debian/changelog
vendored
6
debian/changelog
vendored
@ -1,3 +1,9 @@
|
|||||||
|
terminator (1.0) precise; urgency=low
|
||||||
|
|
||||||
|
* New upstream release of 1.0
|
||||||
|
|
||||||
|
-- Chris Jones <cmsj@tenshu.net> Fri, 19 Oct 2012 12:57:42 -0700
|
||||||
|
|
||||||
terminator (0.96ppa6) oneiric; urgency=low
|
terminator (0.96ppa6) oneiric; urgency=low
|
||||||
|
|
||||||
* No-change rebuild for oneiric PPA
|
* No-change rebuild for oneiric PPA
|
||||||
|
@ -115,6 +115,11 @@ Controls how much to reduce the colour values of fonts in terminals that do not
|
|||||||
factor. A font colour that was RGB(200,200,200) with an inactive_color_offset of 0.5 would set inactive terminals to
|
factor. A font colour that was RGB(200,200,200) with an inactive_color_offset of 0.5 would set inactive terminals to
|
||||||
RGB(100,100,100).
|
RGB(100,100,100).
|
||||||
.TP
|
.TP
|
||||||
|
.B always_split_with_profile
|
||||||
|
Controls whether splits/tabs will continue to use the profile of their peer terminal. If set to False, they will always use
|
||||||
|
the default profile.
|
||||||
|
Default value: \fBFalse\fR
|
||||||
|
.TP
|
||||||
.B enabled_plugins
|
.B enabled_plugins
|
||||||
A list of plugins which should be loaded by default. All other plugin classes will be ignored. The default value includes two
|
A list of plugins which should be loaded by default. All other plugin classes will be ignored. The default value includes two
|
||||||
plugins related to Launchpad, which are enabled by default to provide continuity with earlier releases where these were the
|
plugins related to Launchpad, which are enabled by default to provide continuity with earlier releases where these were the
|
||||||
@ -377,6 +382,14 @@ Default value: \fBblock\fR
|
|||||||
Sets what type of terminal should be emulated.
|
Sets what type of terminal should be emulated.
|
||||||
Default value: \fBxterm\fR
|
Default value: \fBxterm\fR
|
||||||
.TP
|
.TP
|
||||||
|
.B xterm
|
||||||
|
This translates into the value that will be set for TERM in the environment of your terminals.
|
||||||
|
Default value: \fBxterm\fR
|
||||||
|
.TP
|
||||||
|
.B colorterm
|
||||||
|
This translates into the value that will be set for COLORTERM in the environment of your terminals.
|
||||||
|
Default value: \fBgnome-terminal\fR
|
||||||
|
.TP
|
||||||
.B use_system_font
|
.B use_system_font
|
||||||
Whether or not to use the GNOME default monospace font for terminals.
|
Whether or not to use the GNOME default monospace font for terminals.
|
||||||
Default value: \fBTrue\fR
|
Default value: \fBTrue\fR
|
||||||
@ -423,7 +436,7 @@ Default value: \fBFalse\fR
|
|||||||
.TP
|
.TP
|
||||||
.B focus_on_close
|
.B focus_on_close
|
||||||
Sets which terminal should get the focus when another terminal is closed. Values can be "prev", "next" or "auto".
|
Sets which terminal should get the focus when another terminal is closed. Values can be "prev", "next" or "auto".
|
||||||
Using "auto", if the closed terminal is within a splitted window, the focus will be on the sibling terminal rather than another tab.
|
Using "auto", if the closed terminal is within a split window, the focus will be on the sibling terminal rather than another tab.
|
||||||
Default value: \fBauto\fR
|
Default value: \fBauto\fR
|
||||||
.TP
|
.TP
|
||||||
.B exit_action
|
.B exit_action
|
||||||
|
10
po/es.po
10
po/es.po
@ -8,14 +8,14 @@ msgstr ""
|
|||||||
"Project-Id-Version: PACKAGE VERSION\n"
|
"Project-Id-Version: PACKAGE VERSION\n"
|
||||||
"Report-Msgid-Bugs-To: \n"
|
"Report-Msgid-Bugs-To: \n"
|
||||||
"POT-Creation-Date: 2011-08-21 01:31+0100\n"
|
"POT-Creation-Date: 2011-08-21 01:31+0100\n"
|
||||||
"PO-Revision-Date: 2012-05-04 22:28+0000\n"
|
"PO-Revision-Date: 2012-10-05 03:56+0000\n"
|
||||||
"Last-Translator: Juan Pablo <Unknown>\n"
|
"Last-Translator: Paco Molinero <paco@byasl.com>\n"
|
||||||
"Language-Team: LANGUAGE <LL@li.org>\n"
|
"Language-Team: LANGUAGE <LL@li.org>\n"
|
||||||
"MIME-Version: 1.0\n"
|
"MIME-Version: 1.0\n"
|
||||||
"Content-Type: text/plain; charset=utf-8\n"
|
"Content-Type: text/plain; charset=utf-8\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
"X-Launchpad-Export-Date: 2012-05-24 10:30+0000\n"
|
"X-Launchpad-Export-Date: 2012-10-06 04:33+0000\n"
|
||||||
"X-Generator: Launchpad (build 15288)\n"
|
"X-Generator: Launchpad (build 16061)\n"
|
||||||
|
|
||||||
#: ../data/terminator.desktop.in.h:1
|
#: ../data/terminator.desktop.in.h:1
|
||||||
msgid "Multiple terminals in one window"
|
msgid "Multiple terminals in one window"
|
||||||
@ -333,7 +333,7 @@ msgstr "Captura de terminal"
|
|||||||
|
|
||||||
#: ../terminatorlib/prefseditor.py:942 ../terminatorlib/prefseditor.py:947
|
#: ../terminatorlib/prefseditor.py:942 ../terminatorlib/prefseditor.py:947
|
||||||
msgid "New Profile"
|
msgid "New Profile"
|
||||||
msgstr "Nuevo Perfil"
|
msgstr "Perfil nuevo"
|
||||||
|
|
||||||
#: ../terminatorlib/prefseditor.py:987 ../terminatorlib/prefseditor.py:992
|
#: ../terminatorlib/prefseditor.py:987 ../terminatorlib/prefseditor.py:992
|
||||||
msgid "New Layout"
|
msgid "New Layout"
|
||||||
|
@ -24,7 +24,7 @@ import sys
|
|||||||
from terminatorlib.util import dbg, err
|
from terminatorlib.util import dbg, err
|
||||||
try:
|
try:
|
||||||
from terminatorlib import ipc
|
from terminatorlib import ipc
|
||||||
except ImportErrror:
|
except ImportError:
|
||||||
err('Unable to initialise Terminator remote library. This probably means dbus is not available')
|
err('Unable to initialise Terminator remote library. This probably means dbus is not available')
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
@ -35,6 +35,8 @@ COMMANDS={
|
|||||||
'hsplit': ['terminal_hsplit', 'Split the current terminal horizontally'],
|
'hsplit': ['terminal_hsplit', 'Split the current terminal horizontally'],
|
||||||
'vsplit': ['terminal_vsplit', 'Split the current terminal vertically'],
|
'vsplit': ['terminal_vsplit', 'Split the current terminal vertically'],
|
||||||
'terminals': ['get_terminals', 'Get a list of all terminals'],
|
'terminals': ['get_terminals', 'Get a list of all terminals'],
|
||||||
|
'terminal_tab': ['get_terminal_tab', 'Get the UUID of a parent tab'],
|
||||||
|
'terminal_tab_title': ['get_terminal_tab_title', 'Get the title of a parent tab'],
|
||||||
}
|
}
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
|
14
terminator
14
terminator
@ -62,11 +62,23 @@ if __name__ == '__main__':
|
|||||||
dbg('dbus disabled by command line')
|
dbg('dbus disabled by command line')
|
||||||
raise ImportError
|
raise ImportError
|
||||||
from terminatorlib import ipc
|
from terminatorlib import ipc
|
||||||
|
import dbus
|
||||||
try:
|
try:
|
||||||
dbus_service = ipc.DBusService()
|
dbus_service = ipc.DBusService()
|
||||||
except ipc.DBusException:
|
except ipc.DBusException:
|
||||||
dbg('Unable to become master process, requesting a new window')
|
dbg('Unable to become master process, requesting a new window')
|
||||||
ipc.new_window(OPTIONS.layout)
|
# get rid of the None and True types so dbus can handle them (empty
|
||||||
|
# and 'True' strings are used instead), also arrays are joined
|
||||||
|
# (the -x argument for example)
|
||||||
|
optionslist = {}
|
||||||
|
for opt, val in OPTIONS.__dict__.items():
|
||||||
|
if type(val) == type([]):
|
||||||
|
val = ' '.join(val)
|
||||||
|
if val == True:
|
||||||
|
val = 'True'
|
||||||
|
optionslist[opt] = val and '%s'%val or ''
|
||||||
|
optionslist = dbus.Dictionary(optionslist, signature='ss')
|
||||||
|
ipc.new_window(optionslist)
|
||||||
sys.exit()
|
sys.exit()
|
||||||
except ImportError:
|
except ImportError:
|
||||||
dbg('dbus not imported')
|
dbg('dbus not imported')
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
%{!?python_sitelib: %define python_sitelib %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib()")}
|
%{!?python_sitelib: %define python_sitelib %(%{__python} -c "from distutils.sysconfig import get_python_lib; print get_python_lib()")}
|
||||||
|
|
||||||
Name: terminator
|
Name: terminator
|
||||||
Version: 0.96
|
Version: 1.0
|
||||||
Release: 1%{?dist}
|
Release: 1%{?dist}
|
||||||
Summary: Store and run multiple GNOME terminals in one window
|
Summary: Store and run multiple GNOME terminals in one window
|
||||||
|
|
||||||
|
@ -105,6 +105,7 @@ DEFAULTS = {
|
|||||||
'LaunchpadCodeURLHandler',
|
'LaunchpadCodeURLHandler',
|
||||||
'APTURLHandler'],
|
'APTURLHandler'],
|
||||||
'suppress_multiple_term_dialog': False,
|
'suppress_multiple_term_dialog': False,
|
||||||
|
'always_split_with_profile': False,
|
||||||
},
|
},
|
||||||
'keybindings': {
|
'keybindings': {
|
||||||
'zoom_in' : '<Control>plus',
|
'zoom_in' : '<Control>plus',
|
||||||
@ -185,6 +186,8 @@ DEFAULTS = {
|
|||||||
'cursor_shape' : 'block',
|
'cursor_shape' : 'block',
|
||||||
'cursor_color' : '#aaaaaa',
|
'cursor_color' : '#aaaaaa',
|
||||||
'emulation' : 'xterm',
|
'emulation' : 'xterm',
|
||||||
|
'term' : 'xterm',
|
||||||
|
'colorterm' : 'gnome-terminal',
|
||||||
'font' : 'Mono 10',
|
'font' : 'Mono 10',
|
||||||
'foreground_color' : '#aaaaaa',
|
'foreground_color' : '#aaaaaa',
|
||||||
'show_titlebar' : True,
|
'show_titlebar' : True,
|
||||||
@ -351,6 +354,7 @@ class Config(object):
|
|||||||
self.gconf = gconf.client_get_default()
|
self.gconf = gconf.client_get_default()
|
||||||
|
|
||||||
value = self.gconf.get('/apps/metacity/general/focus_mode')
|
value = self.gconf.get('/apps/metacity/general/focus_mode')
|
||||||
|
if value:
|
||||||
self.system_focus = value.get_string()
|
self.system_focus = value.get_string()
|
||||||
self.gconf.notify_add('/apps/metacity/general/focus_mode',
|
self.gconf.notify_add('/apps/metacity/general/focus_mode',
|
||||||
self.on_gconf_notify)
|
self.on_gconf_notify)
|
||||||
@ -427,6 +431,8 @@ class ConfigBase(Borg):
|
|||||||
Borg.__init__(self, self.__class__.__name__)
|
Borg.__init__(self, self.__class__.__name__)
|
||||||
|
|
||||||
self.prepare_attributes()
|
self.prepare_attributes()
|
||||||
|
import optionparse
|
||||||
|
self.command_line_options = optionparse.options
|
||||||
self.load()
|
self.load()
|
||||||
|
|
||||||
def prepare_attributes(self):
|
def prepare_attributes(self):
|
||||||
@ -474,6 +480,9 @@ class ConfigBase(Borg):
|
|||||||
|
|
||||||
keytype = '%s(default=%s)' % (keytype, value)
|
keytype = '%s(default=%s)' % (keytype, value)
|
||||||
|
|
||||||
|
if key == 'custom_url_handler':
|
||||||
|
keytype = 'string(default="")'
|
||||||
|
|
||||||
section[key] = keytype
|
section[key] = keytype
|
||||||
configspecdata['global_config'] = section
|
configspecdata['global_config'] = section
|
||||||
|
|
||||||
@ -528,7 +537,10 @@ class ConfigBase(Borg):
|
|||||||
dbg('ConfigBase::load: config already loaded')
|
dbg('ConfigBase::load: config already loaded')
|
||||||
return
|
return
|
||||||
|
|
||||||
filename = os.path.join(get_config_dir(), 'config')
|
if not self.command_line_options.config:
|
||||||
|
self.command_line_options.config = os.path.join(get_config_dir(), 'config')
|
||||||
|
filename = self.command_line_options.config
|
||||||
|
|
||||||
dbg('looking for config file: %s' % filename)
|
dbg('looking for config file: %s' % filename)
|
||||||
try:
|
try:
|
||||||
configfile = open(filename, 'r')
|
configfile = open(filename, 'r')
|
||||||
@ -624,7 +636,7 @@ class ConfigBase(Borg):
|
|||||||
if not os.path.isdir(config_dir):
|
if not os.path.isdir(config_dir):
|
||||||
os.makedirs(config_dir)
|
os.makedirs(config_dir)
|
||||||
try:
|
try:
|
||||||
parser.write(open(os.path.join(config_dir, 'config'), 'w'))
|
parser.write(open(self.command_line_options.config, 'w'))
|
||||||
except Exception, ex:
|
except Exception, ex:
|
||||||
err('ConfigBase::save: Unable to save config: %s' % ex)
|
err('ConfigBase::save: Unable to save config: %s' % ex)
|
||||||
|
|
||||||
|
@ -20,7 +20,7 @@ True
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
from borg import Borg
|
from borg import Borg
|
||||||
from util import dbg, err
|
from util import dbg, err, inject_uuid
|
||||||
|
|
||||||
# pylint: disable-msg=R0201
|
# pylint: disable-msg=R0201
|
||||||
# pylint: disable-msg=W0613
|
# pylint: disable-msg=W0613
|
||||||
@ -91,7 +91,9 @@ class Factory(Borg):
|
|||||||
return(None)
|
return(None)
|
||||||
|
|
||||||
dbg('Factory::make: created a %s' % product)
|
dbg('Factory::make: created a %s' % product)
|
||||||
return(func(**kwargs))
|
output = func(**kwargs)
|
||||||
|
inject_uuid(output)
|
||||||
|
return(output)
|
||||||
|
|
||||||
def make_window(self, **kwargs):
|
def make_window(self, **kwargs):
|
||||||
"""Make a Window"""
|
"""Make a Window"""
|
||||||
|
@ -10,6 +10,7 @@ import dbus.glib
|
|||||||
from borg import Borg
|
from borg import Borg
|
||||||
from terminator import Terminator
|
from terminator import Terminator
|
||||||
from config import Config
|
from config import Config
|
||||||
|
from factory import Factory
|
||||||
from util import dbg
|
from util import dbg
|
||||||
|
|
||||||
CONFIG = Config()
|
CONFIG = Config()
|
||||||
@ -58,13 +59,17 @@ class DBusService(Borg, dbus.service.Object):
|
|||||||
if not self.terminator:
|
if not self.terminator:
|
||||||
self.terminator = Terminator()
|
self.terminator = Terminator()
|
||||||
|
|
||||||
@dbus.service.method(BUS_NAME)
|
@dbus.service.method(BUS_NAME, in_signature='a{ss}')
|
||||||
def new_window(self, layout='default'):
|
def new_window(self, options=dbus.Dictionary()):
|
||||||
"""Create a new Window"""
|
"""Create a new Window"""
|
||||||
dbg('dbus method called: new_window')
|
dbg('dbus method called: new_window with parameters %s'%(options))
|
||||||
self.terminator.create_layout(layout)
|
oldopts = self.terminator.config.options_get()
|
||||||
|
oldopts.__dict__ = options
|
||||||
|
self.terminator.config.options_set(oldopts)
|
||||||
|
self.terminator.create_layout(oldopts.layout)
|
||||||
self.terminator.layout_done()
|
self.terminator.layout_done()
|
||||||
|
|
||||||
|
|
||||||
@dbus.service.method(BUS_NAME)
|
@dbus.service.method(BUS_NAME)
|
||||||
def terminal_hsplit(self, uuid=None):
|
def terminal_hsplit(self, uuid=None):
|
||||||
"""Split a terminal horizontally, by UUID"""
|
"""Split a terminal horizontally, by UUID"""
|
||||||
@ -93,6 +98,26 @@ class DBusService(Borg, dbus.service.Object):
|
|||||||
"""Return a list of all the terminals"""
|
"""Return a list of all the terminals"""
|
||||||
return [x.uuid.urn for x in self.terminator.terminals]
|
return [x.uuid.urn for x in self.terminator.terminals]
|
||||||
|
|
||||||
|
@dbus.service.method(BUS_NAME)
|
||||||
|
def get_terminal_tab(self, uuid):
|
||||||
|
"""Return the UUID of the parent tab of a given terminal"""
|
||||||
|
maker = Factory()
|
||||||
|
terminal = self.terminator.find_terminal_by_uuid(uuid)
|
||||||
|
window = terminal.get_toplevel()
|
||||||
|
root_widget = window.get_children()[0]
|
||||||
|
if maker.isinstance(root_widget, 'Notebook'):
|
||||||
|
return root_widget.uuid.urn
|
||||||
|
|
||||||
|
@dbus.service.method(BUS_NAME)
|
||||||
|
def get_terminal_tab_title(self, uuid):
|
||||||
|
"""Return the title of a parent tab of a given terminal"""
|
||||||
|
maker = Factory()
|
||||||
|
terminal = self.terminator.find_terminal_by_uuid(uuid)
|
||||||
|
window = terminal.get_toplevel()
|
||||||
|
root_widget = window.get_children()[0]
|
||||||
|
if maker.isinstance(root_widget, "Notebook"):
|
||||||
|
return root_widget.get_tab_label(terminal).get_label()
|
||||||
|
|
||||||
def with_proxy(func):
|
def with_proxy(func):
|
||||||
"""Decorator function to connect to the session dbus bus"""
|
"""Decorator function to connect to the session dbus bus"""
|
||||||
dbg('dbus client call: %s' % func.func_name)
|
dbg('dbus client call: %s' % func.func_name)
|
||||||
@ -103,9 +128,9 @@ def with_proxy(func):
|
|||||||
return _exec
|
return _exec
|
||||||
|
|
||||||
@with_proxy
|
@with_proxy
|
||||||
def new_window(session, layout='default'):
|
def new_window(session, options):
|
||||||
"""Call the dbus method to open a new window"""
|
"""Call the dbus method to open a new window"""
|
||||||
session.new_window(layout)
|
session.new_window(options)
|
||||||
|
|
||||||
@with_proxy
|
@with_proxy
|
||||||
def terminal_hsplit(session, uuid):
|
def terminal_hsplit(session, uuid):
|
||||||
@ -122,3 +147,13 @@ def get_terminals(session, uuid):
|
|||||||
"""Call the dbus method to return a list of all terminals"""
|
"""Call the dbus method to return a list of all terminals"""
|
||||||
print '\n'.join(session.get_terminals(uuid))
|
print '\n'.join(session.get_terminals(uuid))
|
||||||
|
|
||||||
|
@with_proxy
|
||||||
|
def get_terminal_tab(session, uuid):
|
||||||
|
"""Call the dbus method to return the toplevel tab for a terminal"""
|
||||||
|
print session.get_terminal_tab(uuid)
|
||||||
|
|
||||||
|
@with_proxy
|
||||||
|
def get_terminal_tab_title(session, uuid):
|
||||||
|
"""Call the dbus method to return the title of a tab"""
|
||||||
|
print session.get_terminal_tab_title(uuid)
|
||||||
|
|
||||||
|
@ -136,6 +136,10 @@ class Notebook(Container, gtk.Notebook):
|
|||||||
sibling = maker.make('terminal')
|
sibling = maker.make('terminal')
|
||||||
sibling.set_cwd(cwd)
|
sibling.set_cwd(cwd)
|
||||||
sibling.spawn_child()
|
sibling.spawn_child()
|
||||||
|
if widget.group and self.config['split_to_group']:
|
||||||
|
sibling.set_group(None, widget.group)
|
||||||
|
if self.config['always_split_with_profile']:
|
||||||
|
sibling.force_set_profile(None, widget.get_profile())
|
||||||
|
|
||||||
self.insert_page(container, None, page_num)
|
self.insert_page(container, None, page_num)
|
||||||
self.set_tab_reorderable(container, True)
|
self.set_tab_reorderable(container, True)
|
||||||
@ -195,7 +199,7 @@ class Notebook(Container, gtk.Notebook):
|
|||||||
children.append(self.get_nth_page(page))
|
children.append(self.get_nth_page(page))
|
||||||
return(children)
|
return(children)
|
||||||
|
|
||||||
def newtab(self, debugtab=False, widget=None, cwd=None, metadata=None):
|
def newtab(self, debugtab=False, widget=None, cwd=None, metadata=None, profile=None):
|
||||||
"""Add a new tab, optionally supplying a child widget"""
|
"""Add a new tab, optionally supplying a child widget"""
|
||||||
dbg('making a new tab')
|
dbg('making a new tab')
|
||||||
maker = Factory()
|
maker = Factory()
|
||||||
@ -206,6 +210,8 @@ class Notebook(Container, gtk.Notebook):
|
|||||||
if cwd:
|
if cwd:
|
||||||
widget.set_cwd(cwd)
|
widget.set_cwd(cwd)
|
||||||
widget.spawn_child(debugserver=debugtab)
|
widget.spawn_child(debugserver=debugtab)
|
||||||
|
if profile and self.config['always_split_with_profile']:
|
||||||
|
widget.force_set_profile(None, profile)
|
||||||
|
|
||||||
signals = {'close-term': self.wrapcloseterm,
|
signals = {'close-term': self.wrapcloseterm,
|
||||||
'split-horiz': self.split_horiz,
|
'split-horiz': self.split_horiz,
|
||||||
@ -472,6 +478,8 @@ class TabLabel(gtk.HBox):
|
|||||||
self.set_orientation(gtk.ORIENTATION_VERTICAL)
|
self.set_orientation(gtk.ORIENTATION_VERTICAL)
|
||||||
self.label.set_angle(90)
|
self.label.set_angle(90)
|
||||||
elif position == gtk.POS_RIGHT:
|
elif position == gtk.POS_RIGHT:
|
||||||
|
if hasattr(self, 'set_orientation'):
|
||||||
|
self.set_orientation(gtk.ORIENTATION_VERTICAL)
|
||||||
self.label.set_angle(270)
|
self.label.set_angle(270)
|
||||||
else:
|
else:
|
||||||
if hasattr(self, 'set_orientation'):
|
if hasattr(self, 'set_orientation'):
|
||||||
|
@ -26,6 +26,8 @@ import config
|
|||||||
import version
|
import version
|
||||||
from translation import _
|
from translation import _
|
||||||
|
|
||||||
|
options = None
|
||||||
|
|
||||||
def execute_cb(option, opt, value, lparser):
|
def execute_cb(option, opt, value, lparser):
|
||||||
"""Callback for use in parsing execute options"""
|
"""Callback for use in parsing execute options"""
|
||||||
assert value is None
|
assert value is None
|
||||||
@ -40,7 +42,6 @@ def parse_options():
|
|||||||
"""Parse the command line options"""
|
"""Parse the command line options"""
|
||||||
usage = "usage: %prog [options]"
|
usage = "usage: %prog [options]"
|
||||||
|
|
||||||
configobj = config.Config()
|
|
||||||
parser = OptionParser(usage)
|
parser = OptionParser(usage)
|
||||||
|
|
||||||
parser.add_option('-v', '--version', action='store_true', dest='version',
|
parser.add_option('-v', '--version', action='store_true', dest='version',
|
||||||
@ -53,26 +54,31 @@ def parse_options():
|
|||||||
dest='borderless', help=_('Disable window borders'))
|
dest='borderless', help=_('Disable window borders'))
|
||||||
parser.add_option('-H', '--hidden', action='store_true', dest='hidden',
|
parser.add_option('-H', '--hidden', action='store_true', dest='hidden',
|
||||||
help=_('Hide the window at startup'))
|
help=_('Hide the window at startup'))
|
||||||
parser.add_option('-T', '--title', dest='forcedtitle', help=_('Specify a \
|
parser.add_option('-T', '--title', dest='forcedtitle',
|
||||||
title for the window'))
|
help=_('Specify a title for the window'))
|
||||||
parser.add_option('--geometry', dest='geometry', type='string', help=_('Set \
|
parser.add_option('--geometry', dest='geometry', type='string',
|
||||||
the preferred size and position of the window (see X man page)'))
|
help=_('Set the preferred size and position of the window'
|
||||||
parser.add_option('-e', '--command', dest='command', help=_('Specify a \
|
'(see X man page)'))
|
||||||
command to execute inside the terminal'))
|
parser.add_option('-e', '--command', dest='command',
|
||||||
|
help=_('Specify a command to execute inside the terminal'))
|
||||||
|
parser.add_option('-g', '--config', dest='config',
|
||||||
|
help=_('Specify a config file'))
|
||||||
parser.add_option('-x', '--execute', dest='execute', action='callback',
|
parser.add_option('-x', '--execute', dest='execute', action='callback',
|
||||||
callback=execute_cb, help=_('Use the rest of the command line as a \
|
callback=execute_cb,
|
||||||
command to execute inside the terminal, and its arguments'))
|
help=_('Use the rest of the command line as a command to execute'
|
||||||
|
'nside the terminal, and its arguments'))
|
||||||
parser.add_option('--working-directory', metavar='DIR',
|
parser.add_option('--working-directory', metavar='DIR',
|
||||||
dest='working_directory', help=_('Set the working directory'))
|
dest='working_directory', help=_('Set the working directory'))
|
||||||
parser.add_option('-r', '--role', dest='role', help=_('Set a custom \
|
|
||||||
WM_WINDOW_ROLE property on the window'))
|
|
||||||
parser.add_option('-c', '--classname', dest='classname', help=_('Set a \
|
parser.add_option('-c', '--classname', dest='classname', help=_('Set a \
|
||||||
custom name (WM_CLASS) property on the window'))
|
custom name (WM_CLASS) property on the window'))
|
||||||
parser.add_option('-l', '--layout', dest='layout', help=_('Select a layout'))
|
|
||||||
parser.add_option('-p', '--profile', dest='profile', help=_('Use a \
|
|
||||||
different profile as the default'))
|
|
||||||
parser.add_option('-i', '--icon', dest='forcedicon', help=_('Set a custom \
|
parser.add_option('-i', '--icon', dest='forcedicon', help=_('Set a custom \
|
||||||
icon for the window (by file or name)'))
|
icon for the window (by file or name)'))
|
||||||
|
parser.add_option('-r', '--role', dest='role',
|
||||||
|
help=_('Set a custom WM_WINDOW_ROLE property on the window'))
|
||||||
|
parser.add_option('-l', '--layout', dest='layout',
|
||||||
|
help=_('Select a layout'))
|
||||||
|
parser.add_option('-p', '--profile', dest='profile',
|
||||||
|
help=_('Use a different profile as the default'))
|
||||||
parser.add_option('-u', '--no-dbus', action='store_true', dest='nodbus',
|
parser.add_option('-u', '--no-dbus', action='store_true', dest='nodbus',
|
||||||
help=_('Disable DBus'))
|
help=_('Disable DBus'))
|
||||||
parser.add_option('-d', '--debug', action='count', dest='debug',
|
parser.add_option('-d', '--debug', action='count', dest='debug',
|
||||||
@ -86,6 +92,7 @@ icon for the window (by file or name)'))
|
|||||||
parser.add_option(item, dest='dummy', action='store',
|
parser.add_option(item, dest='dummy', action='store',
|
||||||
help=SUPPRESS_HELP)
|
help=SUPPRESS_HELP)
|
||||||
|
|
||||||
|
global options
|
||||||
(options, args) = parser.parse_args()
|
(options, args) = parser.parse_args()
|
||||||
if len(args) != 0:
|
if len(args) != 0:
|
||||||
parser.error('Additional unexpected arguments found: %s' % args)
|
parser.error('Additional unexpected arguments found: %s' % args)
|
||||||
@ -122,6 +129,7 @@ icon for the window (by file or name)'))
|
|||||||
if options.layout is None:
|
if options.layout is None:
|
||||||
options.layout = 'default'
|
options.layout = 'default'
|
||||||
|
|
||||||
|
configobj = config.Config()
|
||||||
if options.profile and options.profile not in configobj.list_profiles():
|
if options.profile and options.profile not in configobj.list_profiles():
|
||||||
options.profile = None
|
options.profile = None
|
||||||
|
|
||||||
|
@ -50,6 +50,10 @@ class Paned(Container):
|
|||||||
sibling = self.maker.make('terminal')
|
sibling = self.maker.make('terminal')
|
||||||
sibling.set_cwd(cwd)
|
sibling.set_cwd(cwd)
|
||||||
sibling.spawn_child()
|
sibling.spawn_child()
|
||||||
|
if widget.group and self.config['split_to_group']:
|
||||||
|
sibling.set_group(None, widget.group)
|
||||||
|
if self.config['always_split_with_profile']:
|
||||||
|
sibling.force_set_profile(None, widget.get_profile())
|
||||||
|
|
||||||
self.add(container)
|
self.add(container)
|
||||||
self.show_all()
|
self.show_all()
|
||||||
@ -111,6 +115,9 @@ class Paned(Container):
|
|||||||
handler = handler[0]
|
handler = handler[0]
|
||||||
self.connect_child(widget, signal, handler, *args)
|
self.connect_child(widget, signal, handler, *args)
|
||||||
|
|
||||||
|
if metadata and \
|
||||||
|
metadata.has_key('had_focus') and \
|
||||||
|
metadata['had_focus'] == True:
|
||||||
widget.grab_focus()
|
widget.grab_focus()
|
||||||
|
|
||||||
elif isinstance(widget, gtk.Paned):
|
elif isinstance(widget, gtk.Paned):
|
||||||
@ -220,9 +227,15 @@ class Paned(Container):
|
|||||||
children.append(self.get_child2())
|
children.append(self.get_child2())
|
||||||
return(children)
|
return(children)
|
||||||
|
|
||||||
|
def get_child_metadata(self, widget):
|
||||||
|
"""Return metadata about a child"""
|
||||||
|
metadata = {}
|
||||||
|
metadata['had_focus'] = widget.has_focus()
|
||||||
|
|
||||||
def wrapcloseterm(self, widget):
|
def wrapcloseterm(self, widget):
|
||||||
"""A child terminal has closed, so this container must die"""
|
"""A child terminal has closed, so this container must die"""
|
||||||
dbg('Paned::wrapcloseterm: Called on %s' % widget)
|
dbg('Paned::wrapcloseterm: Called on %s' % widget)
|
||||||
|
|
||||||
if self.closeterm(widget):
|
if self.closeterm(widget):
|
||||||
# At this point we only have one child, which is the surviving term
|
# At this point we only have one child, which is the surviving term
|
||||||
sibling = self.children[0]
|
sibling = self.children[0]
|
||||||
@ -235,7 +248,6 @@ class Paned(Container):
|
|||||||
parent.remove(self)
|
parent.remove(self)
|
||||||
self.cnxids.remove_all()
|
self.cnxids.remove_all()
|
||||||
parent.add(sibling, metadata)
|
parent.add(sibling, metadata)
|
||||||
sibling.grab_focus()
|
|
||||||
del(self)
|
del(self)
|
||||||
else:
|
else:
|
||||||
dbg("Paned::wrapcloseterm: self.closeterm failed")
|
dbg("Paned::wrapcloseterm: self.closeterm failed")
|
||||||
|
108
terminatorlib/plugins/logger.py
Normal file
108
terminatorlib/plugins/logger.py
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
#!/usr/bin/python
|
||||||
|
|
||||||
|
# Plugin by Sinan Nalkaya <sardok@gmail.com>
|
||||||
|
# See LICENSE of Terminator package.
|
||||||
|
|
||||||
|
""" logger.py - Terminator Plugin to log 'content' of individual
|
||||||
|
terminals """
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
import gtk
|
||||||
|
import terminatorlib.plugin as plugin
|
||||||
|
from terminatorlib.translation import _
|
||||||
|
|
||||||
|
AVAILABLE = ['Logger']
|
||||||
|
|
||||||
|
class Logger(plugin.MenuItem):
|
||||||
|
""" Add custom command to the terminal menu"""
|
||||||
|
capabilities = ['terminal_menu']
|
||||||
|
loggers = None
|
||||||
|
dialog_action = gtk.FILE_CHOOSER_ACTION_SAVE
|
||||||
|
dialog_buttons = (gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
|
||||||
|
gtk.STOCK_SAVE, gtk.RESPONSE_OK)
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
plugin.MenuItem.__init__(self)
|
||||||
|
if not self.loggers:
|
||||||
|
self.loggers = {}
|
||||||
|
|
||||||
|
def callback(self, menuitems, menu, terminal):
|
||||||
|
""" Add save menu item to the menu"""
|
||||||
|
vte_terminal = terminal.get_vte()
|
||||||
|
if not self.loggers.has_key(vte_terminal):
|
||||||
|
item = gtk.MenuItem(_('Start Logger'))
|
||||||
|
item.connect("activate", self.start_logger, terminal)
|
||||||
|
else:
|
||||||
|
item = gtk.MenuItem(_('Stop Logger'))
|
||||||
|
item.connect("activate", self.stop_logger, terminal)
|
||||||
|
item.set_has_tooltip(True)
|
||||||
|
item.set_tooltip_text("Saving at '" + self.loggers[vte_terminal]["filepath"] + "'")
|
||||||
|
menuitems.append(item)
|
||||||
|
|
||||||
|
def write_content(self, terminal, row_start, col_start, row_end, col_end):
|
||||||
|
""" Final function to write a file """
|
||||||
|
content = terminal.get_text_range(row_start, col_start, row_end, col_end,
|
||||||
|
lambda *a: True)
|
||||||
|
fd = self.loggers[terminal]["fd"]
|
||||||
|
# Don't write the last char which is always '\n'
|
||||||
|
fd.write(content[:-1])
|
||||||
|
self.loggers[terminal]["col"] = col_end
|
||||||
|
self.loggers[terminal]["row"] = row_end
|
||||||
|
|
||||||
|
def save(self, terminal):
|
||||||
|
""" 'contents-changed' callback """
|
||||||
|
last_saved_col = self.loggers[terminal]["col"]
|
||||||
|
last_saved_row = self.loggers[terminal]["row"]
|
||||||
|
(col, row) = terminal.get_cursor_position()
|
||||||
|
# Save only when buffer is nearly full,
|
||||||
|
# for the sake of efficiency
|
||||||
|
if row - last_saved_row < terminal.get_row_count():
|
||||||
|
return
|
||||||
|
self.write_content(terminal, last_saved_row, last_saved_col, row, col)
|
||||||
|
|
||||||
|
def start_logger(self, _widget, Terminal):
|
||||||
|
""" Handle menu item callback by saving text to a file"""
|
||||||
|
savedialog = gtk.FileChooserDialog(title="Save Log File As",
|
||||||
|
action=self.dialog_action,
|
||||||
|
buttons=self.dialog_buttons)
|
||||||
|
savedialog.set_do_overwrite_confirmation(True)
|
||||||
|
savedialog.set_local_only(True)
|
||||||
|
savedialog.show_all()
|
||||||
|
response = savedialog.run()
|
||||||
|
if response == gtk.RESPONSE_OK:
|
||||||
|
try:
|
||||||
|
logfile = os.path.join(savedialog.get_current_folder(),
|
||||||
|
savedialog.get_filename())
|
||||||
|
fd = open(logfile, 'w+')
|
||||||
|
# Save log file path,
|
||||||
|
# associated file descriptor, signal handler id
|
||||||
|
# and last saved col,row positions respectively.
|
||||||
|
vte_terminal = Terminal.get_vte()
|
||||||
|
(col, row) = vte_terminal.get_cursor_position()
|
||||||
|
|
||||||
|
self.loggers[vte_terminal] = {"filepath":logfile,
|
||||||
|
"handler_id":0, "fd":fd,
|
||||||
|
"col":col, "row":row}
|
||||||
|
# Add contents-changed callback
|
||||||
|
self.loggers[vte_terminal]["handler_id"] = vte_terminal.connect('contents-changed', self.save)
|
||||||
|
except:
|
||||||
|
e = sys.exc_info()[1]
|
||||||
|
error = gtk.MessageDialog(None, gtk.DIALOG_MODAL, gtk.MESSAGE_ERROR,
|
||||||
|
gtk.BUTTONS_OK, e.strerror)
|
||||||
|
error.run()
|
||||||
|
error.destroy()
|
||||||
|
savedialog.destroy()
|
||||||
|
|
||||||
|
def stop_logger(self, _widget, terminal):
|
||||||
|
vte_terminal = terminal.get_vte()
|
||||||
|
last_saved_col = self.loggers[vte_terminal]["col"]
|
||||||
|
last_saved_row = self.loggers[vte_terminal]["row"]
|
||||||
|
(col, row) = vte_terminal.get_cursor_position()
|
||||||
|
if last_saved_col != col or last_saved_row != row:
|
||||||
|
# Save unwritten bufer to the file
|
||||||
|
self.write_content(vte_terminal, last_saved_row, last_saved_col, row, col)
|
||||||
|
fd = self.loggers[vte_terminal]["fd"]
|
||||||
|
fd.close()
|
||||||
|
vte_terminal.disconnect(self.loggers[vte_terminal]["handler_id"])
|
||||||
|
del(self.loggers[vte_terminal])
|
@ -382,7 +382,7 @@
|
|||||||
<object class="GtkTable" id="global_config_table">
|
<object class="GtkTable" id="global_config_table">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="n_rows">15</property>
|
<property name="n_rows">16</property>
|
||||||
<property name="n_columns">2</property>
|
<property name="n_columns">2</property>
|
||||||
<property name="column_spacing">6</property>
|
<property name="column_spacing">6</property>
|
||||||
<child>
|
<child>
|
||||||
@ -857,6 +857,36 @@
|
|||||||
<property name="bottom_attach">15</property>
|
<property name="bottom_attach">15</property>
|
||||||
</packing>
|
</packing>
|
||||||
</child>
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkLabel" id="label34">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Re-use profiles for new terminals</property>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="top_attach">15</property>
|
||||||
|
<property name="bottom_attach">16</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkCheckButton" id="always_split_with_profile">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="receives_default">False</property>
|
||||||
|
<property name="use_action_appearance">False</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
<property name="draw_indicator">True</property>
|
||||||
|
<signal name="toggled" handler="on_always_split_with_profile_toggled" swapped="no"/>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">1</property>
|
||||||
|
<property name="right_attach">2</property>
|
||||||
|
<property name="top_attach">15</property>
|
||||||
|
<property name="bottom_attach">16</property>
|
||||||
|
<property name="x_options">GTK_EXPAND</property>
|
||||||
|
<property name="y_options">GTK_EXPAND</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="expand">True</property>
|
<property name="expand">True</property>
|
||||||
|
@ -238,6 +238,9 @@ class PrefsEditor:
|
|||||||
#Hide size text from the title bar
|
#Hide size text from the title bar
|
||||||
widget = guiget('title_hide_sizetextcheck')
|
widget = guiget('title_hide_sizetextcheck')
|
||||||
widget.set_active(self.config['title_hide_sizetext'])
|
widget.set_active(self.config['title_hide_sizetext'])
|
||||||
|
#Always split with profile
|
||||||
|
widget = guiget('always_split_with_profile')
|
||||||
|
widget.set_active(self.config['always_split_with_profile'])
|
||||||
|
|
||||||
## Profile tab
|
## Profile tab
|
||||||
# Populate the profile list
|
# Populate the profile list
|
||||||
@ -610,6 +613,11 @@ class PrefsEditor:
|
|||||||
self.config['title_hide_sizetext'] = widget.get_active()
|
self.config['title_hide_sizetext'] = widget.get_active()
|
||||||
self.config.save()
|
self.config.save()
|
||||||
|
|
||||||
|
def on_always_split_with_profile_toggled(self, widget):
|
||||||
|
"""Always split with profile setting changed"""
|
||||||
|
self.config['always_split_with_profile'] = widget.get_active()
|
||||||
|
self.config.save()
|
||||||
|
|
||||||
def on_allow_bold_checkbutton_toggled(self, widget):
|
def on_allow_bold_checkbutton_toggled(self, widget):
|
||||||
"""Allow bold setting changed"""
|
"""Allow bold setting changed"""
|
||||||
self.config['allow_bold'] = widget.get_active()
|
self.config['allow_bold'] = widget.get_active()
|
||||||
|
@ -14,7 +14,6 @@ import gobject
|
|||||||
import pango
|
import pango
|
||||||
import subprocess
|
import subprocess
|
||||||
import urllib
|
import urllib
|
||||||
import uuid
|
|
||||||
|
|
||||||
from util import dbg, err, gerr
|
from util import dbg, err, gerr
|
||||||
import util
|
import util
|
||||||
@ -89,7 +88,6 @@ class Terminal(gtk.VBox):
|
|||||||
command = None
|
command = None
|
||||||
clipboard = None
|
clipboard = None
|
||||||
pid = None
|
pid = None
|
||||||
uuid = None
|
|
||||||
|
|
||||||
matches = None
|
matches = None
|
||||||
config = None
|
config = None
|
||||||
@ -107,6 +105,7 @@ class Terminal(gtk.VBox):
|
|||||||
composite_support = None
|
composite_support = None
|
||||||
|
|
||||||
cnxids = None
|
cnxids = None
|
||||||
|
targets_for_new_group = None
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
"""Class initialiser"""
|
"""Class initialiser"""
|
||||||
@ -119,6 +118,7 @@ class Terminal(gtk.VBox):
|
|||||||
# FIXME: Surely these should happen in Terminator::register_terminal()?
|
# FIXME: Surely these should happen in Terminator::register_terminal()?
|
||||||
self.connect('enumerate', self.terminator.do_enumerate)
|
self.connect('enumerate', self.terminator.do_enumerate)
|
||||||
self.connect('focus-in', self.terminator.focus_changed)
|
self.connect('focus-in', self.terminator.focus_changed)
|
||||||
|
self.connect('focus-out', self.terminator.focus_left)
|
||||||
|
|
||||||
self.matches = {}
|
self.matches = {}
|
||||||
self.cnxids = Signalman()
|
self.cnxids = Signalman()
|
||||||
@ -131,9 +131,6 @@ class Terminal(gtk.VBox):
|
|||||||
|
|
||||||
self.pending_on_vte_size_allocate = False
|
self.pending_on_vte_size_allocate = False
|
||||||
|
|
||||||
self.uuid = uuid.uuid4()
|
|
||||||
dbg('assigning Terminal a TERMINATOR_UUID of: %s' % self.uuid.urn)
|
|
||||||
|
|
||||||
self.vte = vte.Terminal()
|
self.vte = vte.Terminal()
|
||||||
self.vte._expose_data = None
|
self.vte._expose_data = None
|
||||||
if not hasattr(self.vte, "set_opacity") or \
|
if not hasattr(self.vte, "set_opacity") or \
|
||||||
@ -167,8 +164,8 @@ class Terminal(gtk.VBox):
|
|||||||
|
|
||||||
self.connect_signals()
|
self.connect_signals()
|
||||||
|
|
||||||
os.putenv('TERM', 'xterm')
|
os.putenv('TERM', self.config['term'])
|
||||||
os.putenv('COLORTERM', 'gnome-terminal')
|
os.putenv('COLORTERM', self.config['colorterm'])
|
||||||
|
|
||||||
env_proxy = os.getenv('http_proxy')
|
env_proxy = os.getenv('http_proxy')
|
||||||
if not env_proxy:
|
if not env_proxy:
|
||||||
@ -770,7 +767,40 @@ class Terminal(gtk.VBox):
|
|||||||
def on_group_button_press(self, widget, event):
|
def on_group_button_press(self, widget, event):
|
||||||
"""Handler for the group button"""
|
"""Handler for the group button"""
|
||||||
if event.button == 1:
|
if event.button == 1:
|
||||||
|
if event.type == gtk.gdk._2BUTTON_PRESS or \
|
||||||
|
event.type == gtk.gdk._3BUTTON_PRESS:
|
||||||
|
# Ignore these, or they make the interaction bad
|
||||||
|
return False
|
||||||
|
# Super key applies interaction to all terms in group
|
||||||
|
include_siblings=event.state & gtk.gdk.MOD4_MASK == gtk.gdk.MOD4_MASK
|
||||||
|
if include_siblings:
|
||||||
|
targets=self.terminator.get_sibling_terms(self)
|
||||||
|
else:
|
||||||
|
targets=[self]
|
||||||
|
if event.state & gtk.gdk.CONTROL_MASK == gtk.gdk.CONTROL_MASK:
|
||||||
|
dbg('on_group_button_press: toggle terminal to focused terminals group')
|
||||||
|
focused=self.get_toplevel().get_focussed_terminal()
|
||||||
|
if focused in targets: targets.remove(focused)
|
||||||
|
if self != focused:
|
||||||
|
if self.group==focused.group:
|
||||||
|
new_group=None
|
||||||
|
else:
|
||||||
|
new_group=focused.group
|
||||||
|
[term.set_group(None, new_group) for term in targets]
|
||||||
|
[term.titlebar.update(focused) for term in targets]
|
||||||
|
return True
|
||||||
|
elif event.state & gtk.gdk.SHIFT_MASK == gtk.gdk.SHIFT_MASK:
|
||||||
|
dbg('on_group_button_press: rename of terminals group')
|
||||||
|
self.targets_for_new_group = targets
|
||||||
|
self.titlebar.create_group()
|
||||||
|
return True
|
||||||
|
elif event.type == gtk.gdk.BUTTON_PRESS:
|
||||||
|
# Single Click gives popup
|
||||||
|
dbg('on_group_button_press: group menu popup')
|
||||||
self.create_popup_group_menu(widget, event)
|
self.create_popup_group_menu(widget, event)
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
dbg('on_group_button_press: unknown group button interaction')
|
||||||
return(False)
|
return(False)
|
||||||
|
|
||||||
def on_keypress(self, widget, event):
|
def on_keypress(self, widget, event):
|
||||||
@ -947,9 +977,10 @@ class Terminal(gtk.VBox):
|
|||||||
if gtk.targets_include_text(drag_context.targets) or \
|
if gtk.targets_include_text(drag_context.targets) or \
|
||||||
gtk.targets_include_uri(drag_context.targets):
|
gtk.targets_include_uri(drag_context.targets):
|
||||||
# copy text to destination
|
# copy text to destination
|
||||||
txt = selection_data.data.strip()
|
txt = selection_data.data.strip(' ')
|
||||||
if txt[0:7] == 'file://':
|
if txt[0:7] == 'file://':
|
||||||
txt = "'%s'" % urllib.unquote(txt[7:])
|
txt = "'%s'" % urllib.unquote(txt[7:])
|
||||||
|
txt = selection_data.data.strip('\n')
|
||||||
for term in self.terminator.get_target_terms(self):
|
for term in self.terminator.get_target_terms(self):
|
||||||
term.feed(txt)
|
term.feed(txt)
|
||||||
return
|
return
|
||||||
@ -1247,6 +1278,8 @@ class Terminal(gtk.VBox):
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
envv = []
|
envv = []
|
||||||
|
envv.append('TERM=%s' % self.config['term'])
|
||||||
|
envv.append('COLORTERM=%s' % self.config['colorterm'])
|
||||||
envv.append('TERMINATOR_UUID=%s' % self.uuid.urn)
|
envv.append('TERMINATOR_UUID=%s' % self.uuid.urn)
|
||||||
if self.terminator.dbus_name:
|
if self.terminator.dbus_name:
|
||||||
envv.append('TERMINATOR_DBUS_NAME=%s' % self.terminator.dbus_name)
|
envv.append('TERMINATOR_DBUS_NAME=%s' % self.terminator.dbus_name)
|
||||||
|
@ -349,18 +349,20 @@ class Terminator(Borg):
|
|||||||
idx = terminals.index(term)
|
idx = terminals.index(term)
|
||||||
term.feed(numstr % (idx + 1))
|
term.feed(numstr % (idx + 1))
|
||||||
|
|
||||||
|
def get_sibling_terms(self, widget):
|
||||||
|
termset = []
|
||||||
|
for term in self.terminals:
|
||||||
|
if term.group == widget.group:
|
||||||
|
termset.append(term)
|
||||||
|
return(termset)
|
||||||
|
|
||||||
def get_target_terms(self, widget):
|
def get_target_terms(self, widget):
|
||||||
"""Get the terminals we should currently be broadcasting to"""
|
"""Get the terminals we should currently be broadcasting to"""
|
||||||
if self.groupsend == self.groupsend_type['all']:
|
if self.groupsend == self.groupsend_type['all']:
|
||||||
return(self.terminals)
|
return(self.terminals)
|
||||||
elif self.groupsend == self.groupsend_type['group']:
|
elif self.groupsend == self.groupsend_type['group']:
|
||||||
termset = []
|
if widget.group != None:
|
||||||
for term in self.terminals:
|
return(self.get_sibling_terms(widget))
|
||||||
if term == widget or (term.group != None and term.group ==
|
|
||||||
widget.group):
|
|
||||||
termset.append(term)
|
|
||||||
return(termset)
|
|
||||||
else:
|
|
||||||
return([widget])
|
return([widget])
|
||||||
|
|
||||||
def get_focussed_terminal(self):
|
def get_focussed_terminal(self):
|
||||||
@ -376,6 +378,9 @@ class Terminator(Borg):
|
|||||||
terminal.titlebar.update(widget)
|
terminal.titlebar.update(widget)
|
||||||
return
|
return
|
||||||
|
|
||||||
|
def focus_left(self, widget):
|
||||||
|
self.last_focused_term=widget
|
||||||
|
|
||||||
def describe_layout(self):
|
def describe_layout(self):
|
||||||
"""Describe our current layout"""
|
"""Describe our current layout"""
|
||||||
layout = {}
|
layout = {}
|
||||||
|
@ -94,7 +94,7 @@ class Titlebar(gtk.EventBox):
|
|||||||
|
|
||||||
def connect_icon(self, func):
|
def connect_icon(self, func):
|
||||||
"""Connect the supplied function to clicking on the group icon"""
|
"""Connect the supplied function to clicking on the group icon"""
|
||||||
self.ebox.connect('button-release-event', func)
|
self.ebox.connect('button-press-event', func)
|
||||||
|
|
||||||
def update(self, other=None):
|
def update(self, other=None):
|
||||||
"""Update our contents"""
|
"""Update our contents"""
|
||||||
@ -247,6 +247,7 @@ class Titlebar(gtk.EventBox):
|
|||||||
if self.groupentry.get_text()=='' and freegroups:
|
if self.groupentry.get_text()=='' and freegroups:
|
||||||
self.groupentry.set_text(freegroups.pop())
|
self.groupentry.set_text(freegroups.pop())
|
||||||
self.groupentry.show()
|
self.groupentry.show()
|
||||||
|
self.grouplabel.hide()
|
||||||
self.groupentry.grab_focus()
|
self.groupentry.grab_focus()
|
||||||
self.update_visibility()
|
self.update_visibility()
|
||||||
|
|
||||||
@ -254,6 +255,7 @@ class Titlebar(gtk.EventBox):
|
|||||||
"""Hide the group name entry"""
|
"""Hide the group name entry"""
|
||||||
self.groupentry.set_text('')
|
self.groupentry.set_text('')
|
||||||
self.groupentry.hide()
|
self.groupentry.hide()
|
||||||
|
self.grouplabel.show()
|
||||||
self.get_parent().grab_focus()
|
self.get_parent().grab_focus()
|
||||||
|
|
||||||
def groupentry_activate(self, widget):
|
def groupentry_activate(self, widget):
|
||||||
@ -261,7 +263,14 @@ class Titlebar(gtk.EventBox):
|
|||||||
groupname = self.groupentry.get_text()
|
groupname = self.groupentry.get_text()
|
||||||
dbg('Titlebar::groupentry_activate: creating group: %s' % groupname)
|
dbg('Titlebar::groupentry_activate: creating group: %s' % groupname)
|
||||||
self.groupentry_cancel(None, None)
|
self.groupentry_cancel(None, None)
|
||||||
|
last_focused_term=self.terminator.last_focused_term
|
||||||
|
if self.terminal.targets_for_new_group:
|
||||||
|
[term.titlebar.emit('create-group', groupname) for term in self.terminal.targets_for_new_group]
|
||||||
|
self.terminal.targets_for_new_group = None
|
||||||
|
else:
|
||||||
self.emit('create-group', groupname)
|
self.emit('create-group', groupname)
|
||||||
|
last_focused_term.grab_focus()
|
||||||
|
self.terminator.focus_changed(last_focused_term)
|
||||||
|
|
||||||
def groupentry_keypress(self, widget, event):
|
def groupentry_keypress(self, widget, event):
|
||||||
"""Handle keypresses on the entry widget"""
|
"""Handle keypresses on the entry widget"""
|
||||||
|
@ -28,6 +28,7 @@ import gtk
|
|||||||
import os
|
import os
|
||||||
import pwd
|
import pwd
|
||||||
import inspect
|
import inspect
|
||||||
|
import uuid
|
||||||
|
|
||||||
# set this to true to enable debugging output
|
# set this to true to enable debugging output
|
||||||
DEBUG = False
|
DEBUG = False
|
||||||
@ -276,3 +277,16 @@ def enumerate_descendants(parent):
|
|||||||
len(terminals), parent))
|
len(terminals), parent))
|
||||||
return(containers, terminals)
|
return(containers, terminals)
|
||||||
|
|
||||||
|
def make_uuid():
|
||||||
|
"""Generate a UUID for an object"""
|
||||||
|
return uuid.uuid4()
|
||||||
|
|
||||||
|
def inject_uuid(target):
|
||||||
|
"""Inject a UUID into an existing object"""
|
||||||
|
uuid = make_uuid()
|
||||||
|
if not hasattr(target, "uuid") or target.uuid == None:
|
||||||
|
dbg("Injecting UUID %s into: %s" % (uuid, target))
|
||||||
|
target.uuid = uuid
|
||||||
|
else:
|
||||||
|
dbg("Object already has a UUID: %s" % target)
|
||||||
|
|
||||||
|
@ -21,4 +21,4 @@ TerminatorVersion supplies our version number.
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
APP_NAME = 'terminator'
|
APP_NAME = 'terminator'
|
||||||
APP_VERSION = '0.96'
|
APP_VERSION = '1.0'
|
||||||
|
@ -71,10 +71,10 @@ class Window(Container, gtk.Window):
|
|||||||
|
|
||||||
options = self.config.options_get()
|
options = self.config.options_get()
|
||||||
if options:
|
if options:
|
||||||
if options.forcedtitle is not None:
|
if options.forcedtitle:
|
||||||
self.title.force_title(options.forcedtitle)
|
self.title.force_title(options.forcedtitle)
|
||||||
|
|
||||||
if options.role is not None:
|
if options.role:
|
||||||
self.set_role(options.role)
|
self.set_role(options.role)
|
||||||
|
|
||||||
if options.classname is not None:
|
if options.classname is not None:
|
||||||
@ -83,7 +83,7 @@ class Window(Container, gtk.Window):
|
|||||||
if options.forcedicon is not None:
|
if options.forcedicon is not None:
|
||||||
icon_to_apply = options.forcedicon
|
icon_to_apply = options.forcedicon
|
||||||
|
|
||||||
if options.geometry is not None:
|
if options.geometry:
|
||||||
if not self.parse_geometry(options.geometry):
|
if not self.parse_geometry(options.geometry):
|
||||||
err('Window::__init__: Unable to parse geometry: %s' %
|
err('Window::__init__: Unable to parse geometry: %s' %
|
||||||
options.geometry)
|
options.geometry)
|
||||||
@ -248,6 +248,7 @@ class Window(Container, gtk.Window):
|
|||||||
def tab_new(self, widget=None, debugtab=False, _param1=None, _param2=None):
|
def tab_new(self, widget=None, debugtab=False, _param1=None, _param2=None):
|
||||||
"""Make a new tab"""
|
"""Make a new tab"""
|
||||||
cwd = None
|
cwd = None
|
||||||
|
profile = None
|
||||||
|
|
||||||
if self.get_property('term_zoomed') == True:
|
if self.get_property('term_zoomed') == True:
|
||||||
err("You can't create a tab while a terminal is maximised/zoomed")
|
err("You can't create a tab while a terminal is maximised/zoomed")
|
||||||
@ -255,11 +256,13 @@ class Window(Container, gtk.Window):
|
|||||||
|
|
||||||
if widget:
|
if widget:
|
||||||
cwd = widget.get_cwd()
|
cwd = widget.get_cwd()
|
||||||
|
profile = widget.get_profile()
|
||||||
|
|
||||||
maker = Factory()
|
maker = Factory()
|
||||||
if not self.is_child_notebook():
|
if not self.is_child_notebook():
|
||||||
dbg('Making a new Notebook')
|
dbg('Making a new Notebook')
|
||||||
notebook = maker.make('Notebook', window=self)
|
notebook = maker.make('Notebook', window=self)
|
||||||
self.get_child().newtab(debugtab, cwd=cwd)
|
self.get_child().newtab(debugtab, cwd=cwd, profile=profile)
|
||||||
|
|
||||||
def on_delete_event(self, window, event, data=None):
|
def on_delete_event(self, window, event, data=None):
|
||||||
"""Handle a window close request"""
|
"""Handle a window close request"""
|
||||||
@ -373,8 +376,10 @@ class Window(Container, gtk.Window):
|
|||||||
|
|
||||||
def show(self, startup=False):
|
def show(self, startup=False):
|
||||||
"""Undo the startup show request if started in hidden mode"""
|
"""Undo the startup show request if started in hidden mode"""
|
||||||
gtk.Window.show(self)
|
#Present is necessary to grab focus when window is hidden from taskbar.
|
||||||
#Present is necessary to grab focus when window is hidden from taskbar
|
#It is important to call present() before show(), otherwise the window
|
||||||
|
#won't be brought to front if an another application has the focus.
|
||||||
|
#Last note: present() will implicitly call gtk.Window.show()
|
||||||
self.present()
|
self.present()
|
||||||
|
|
||||||
#Window must be shown, then hidden for the hotkeys to be registered
|
#Window must be shown, then hidden for the hotkeys to be registered
|
||||||
@ -454,6 +459,11 @@ class Window(Container, gtk.Window):
|
|||||||
sibling = maker.make('Terminal')
|
sibling = maker.make('Terminal')
|
||||||
sibling.set_cwd(cwd)
|
sibling.set_cwd(cwd)
|
||||||
sibling.spawn_child()
|
sibling.spawn_child()
|
||||||
|
if widget.group and self.config['split_to_group']:
|
||||||
|
sibling.set_group(None, widget.group)
|
||||||
|
if self.config['always_split_with_profile']:
|
||||||
|
sibling.force_set_profile(None, widget.get_profile())
|
||||||
|
|
||||||
self.add(container)
|
self.add(container)
|
||||||
container.show_all()
|
container.show_all()
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user