17
17
You should have received a copy of the GNU General Public
18
18
License along with this program; if not, write to the
19
Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20
Boston, MA 02111-1307, USA.
19
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20
Boston, MA 02110-1301 USA
22
23
from __future__ import absolute_import
24
from __future__ import division
27
gobject.threads_init()
31
41
from pango import FontDescription
35
from xdg.DesktopEntry import DesktopEntry
41
42
from thread import start_new_thread
42
43
from time import sleep
44
from urllib import quote_plus
44
45
from urllib import url2pathname
45
46
from urlparse import urlsplit
47
from xdg.DesktopEntry import DesktopEntry
48
from xml.sax.saxutils import escape as xml_escape
47
50
import guake.globalhotkeys
48
from guake.simplegladeapp import SimpleGladeApp, bindtextdomain
49
from guake.prefs import PrefsDialog, LKEY, GKEY
50
from guake.dbusiface import DbusManager, DBUS_NAME, DBUS_PATH
51
from guake.common import test_gconf, pixmapfile, gladefile, ShowableError, _
53
from guake.common import ShowableError
54
from guake.common import _
55
from guake.common import clamp
56
from guake.common import gladefile
57
from guake.common import pixmapfile
52
58
from guake.common import shell_quote
53
from guake.globals import NAME, VERSION, LOCALE_DIR, KEY, GCONF_PATH, \
54
TERMINAL_MATCH_EXPRS, TERMINAL_MATCH_TAGS, \
55
ALIGN_LEFT, ALIGN_RIGHT, ALIGN_CENTER
59
from guake.common import test_gconf
60
from guake.dbusiface import DBUS_NAME
61
from guake.dbusiface import DBUS_PATH
62
from guake.dbusiface import DbusManager
63
from guake.globals import ALIGN_BOTTOM
64
from guake.globals import ALIGN_CENTER
65
from guake.globals import ALIGN_LEFT
66
from guake.globals import ALIGN_RIGHT
67
from guake.globals import ALWAYS_ON_PRIMARY
68
from guake.globals import GCONF_PATH
69
from guake.globals import KEY
70
from guake.globals import LOCALE_DIR
71
from guake.globals import NAME
72
from guake.globals import QUICK_OPEN_MATCHERS
73
from guake.globals import TERMINAL_MATCH_EXPRS
74
from guake.globals import TERMINAL_MATCH_TAGS
75
from guake.globals import VERSION
76
from guake.prefs import GKEY
77
from guake.prefs import LKEY
78
from guake.prefs import PrefsDialog
79
from guake.simplegladeapp import SimpleGladeApp
80
from guake.simplegladeapp import bindtextdomain
57
pynotify.init('Guake!')
59
83
GNOME_FONT_PATH = '/desktop/gnome/interface/monospace_font_name'
86
gobject.threads_init()
61
88
# Loading translation
62
89
bindtextdomain(NAME, LOCALE_DIR)
120
147
notify_add = client.notify_add
122
149
# these keys does not need to be watched.
123
#notify_add(KEY('/general/default_shell'), self.shell_changed)
124
#notify_add(KEY('/general/use_login_shell'), self.login_shell_toggled)
125
#notify_add(KEY('/general/use_popup'), self.popup_toggled)
126
#notify_add(KEY('/general/window_losefocus'), self.losefocus_toggled)
150
# notify_add(KEY('/general/default_shell'), self.shell_changed)
151
# notify_add(KEY('/general/use_login_shell'), self.login_shell_toggled)
152
# notify_add(KEY('/general/use_popup'), self.popup_toggled)
153
# notify_add(KEY('/general/window_losefocus'), self.losefocus_toggled)
154
# notify_add(KEY('/general/use_vte_titles'), self.use_vte_titles_changed)
155
# notify_add(KEY('/general/quick_open_enable'), self.on_quick_open_enable_changed)
157
# Notification is not required for mouse_display/display_n because
158
# get_final_window_rect polls gconf and is called whenever Guake is
128
161
notify_add(KEY('/general/show_resizer'), self.show_resizer_toggled)
196
237
self.guake.window.resize(window_rect.width, window_rect.height)
197
238
self.guake.window.move(window_rect.x, window_rect.y)
240
def cursor_blink_mode_changed(self, client, connection_id, entry, data):
241
"""Called when cursor blink mode settings has been changed
243
for term in self.guake.term_list:
244
term.set_property("cursor-blink-mode", entry.value.get_int())
246
def cursor_shape_changed(self, client, connection_id, entry, data):
247
"""Called when the cursor shape settings has been changed
249
for term in self.guake.term_list:
250
term.set_property("cursor-shape", entry.value.get_int())
199
252
def scrollbar_toggled(self, client, connection_id, entry, data):
200
253
"""If the gconf var use_scrollbar be changed, this method will
201
254
be called and will show/hide scrollbars of all terminals open.
203
for i in self.guake.term_list:
256
for term in self.guake.term_list:
204
257
# There is an hbox in each tab of the main notebook and it
205
258
# contains a Terminal and a Scrollbar. Since only have the
206
259
# Terminal here, we're going to use this to get the
207
260
# scrollbar and hide/show it.
208
hbox = i.get_parent()
261
hbox = term.get_parent()
209
262
terminal, scrollbar = hbox.get_children()
210
263
if entry.value.get_bool():
301
354
will set the transparent flag to false if an image is set in
302
355
all terminals open.
304
image = entry.value.get_string()
305
for i in self.guake.term_list:
306
if image and os.path.exists(image):
307
i.set_background_image_file(image)
308
i.set_background_transparent(False)
310
"""We need to clear the image if it's not set but there is
311
a bug in vte python bidnings which doesn't allow None to be
312
passed to set_background_image (C GTK function expects NULL).
313
The user will need to restart Guake after clearing the image.
314
i.set_background_image(None)
316
if self.guake.has_argb:
317
i.set_background_transparent(False)
319
i.set_background_transparent(True)
357
self.guake.set_background_image(entry.value.get_string())
321
359
def bgtransparency_changed(self, client, connection_id, entry, data):
322
360
"""If the gconf var style/background/transparency be changed, this
323
361
method will be called and will set the saturation and transparency
324
362
properties in all terminals open.
326
transparency = entry.value.get_int()
327
for i in self.guake.term_list:
328
i.set_background_saturation(transparency / 100.0)
329
if self.guake.has_argb:
330
i.set_opacity(int((100 - transparency) / 100.0 * 65535))
364
self.guake.set_background_transparency(entry.value.get_int())
332
366
def backspace_changed(self, client, connection_id, entry, data):
333
367
"""If the gconf var compat_backspace be changed, this method
354
388
to be used in internal methods.
356
390
self.guake = guake
357
self.accel_group = None # see reload_accelerators
391
self.accel_group = None # see reload_accelerators
358
392
self.client = gconf.client_get_default()
360
394
notify_add = self.client.notify_add
361
395
notify_add(GKEY('show_hide'), self.reload_globals)
363
keys = ['toggle_fullscreen', 'new_tab', 'close_tab', 'rename_tab',
397
keys = ['toggle_fullscreen', 'new_tab', 'close_tab', 'rename_current_tab',
364
398
'previous_tab', 'next_tab', 'clipboard_copy', 'clipboard_paste',
399
'quit', 'zoom_in', 'zoom_out', 'increase_height', 'decrease_height', "search_on_web",
400
'switch_tab1', 'switch_tab2', 'switch_tab3', 'switch_tab4', 'switch_tab5',
401
'switch_tab6', 'switch_tab7', 'switch_tab8', 'switch_tab9', 'switch_tab10'
368
404
notify_add(LKEY(key), self.reload_accelerators)
442
478
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
443
479
self.guake.accel_toggle_fullscreen)
481
key, mask = gtk.accelerator_parse(gets('zoom_in'))
483
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
484
self.guake.accel_zoom_in)
486
key, mask = gtk.accelerator_parse(gets('zoom_in_alt'))
488
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
489
self.guake.accel_zoom_in)
491
key, mask = gtk.accelerator_parse(gets('zoom_out'))
493
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
494
self.guake.accel_zoom_out)
496
key, mask = gtk.accelerator_parse(gets('increase_height'))
498
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
499
self.guake.accel_increase_height)
501
key, mask = gtk.accelerator_parse(gets('decrease_height'))
503
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
504
self.guake.accel_decrease_height)
506
for tab in xrange(1, 11):
507
key, mask = gtk.accelerator_parse(gets('switch_tab%d' % tab))
509
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
510
self.guake.gen_accel_switch_tabN(tab - 1))
513
key, mask = gtk.accelerator_parse(gets('search_on_web'))
515
self.accel_group.connect_group(key, mask, gtk.ACCEL_VISIBLE,
516
self.guake.search_on_web)
517
except Exception as e:
518
print "Exception occured: %s" % (str(e,))
445
521
class GuakeTerminal(vte.Terminal):
446
522
"""Just a vte.Terminal with some properties already set.
448
525
def __init__(self):
449
526
super(GuakeTerminal, self).__init__()
450
527
self.configure_terminal()
451
528
self.add_matches()
452
529
self.connect('button-press-event', self.button_press)
453
530
self.matched_value = ''
531
self.font_scale_index = 0
533
self.custom_bgcolor = None
534
self.custom_fgcolor = None
455
536
def configure_terminal(self):
456
537
"""Sets all customized properties on the terminal
483
580
int(event.x / self.get_char_width()),
484
581
int(event.y / self.get_char_height()))
486
if event.button == 1 \
487
and event.get_state() & gtk.gdk.CONTROL_MASK \
583
if (event.button == 1
584
and event.get_state() & gtk.gdk.CONTROL_MASK
489
586
value, tag = matched_string
491
if TERMINAL_MATCH_TAGS[tag] == 'schema':
492
# value here should not be changed, it is right and
495
elif TERMINAL_MATCH_TAGS[tag] == 'http':
496
value = 'http://%s' % value
497
elif TERMINAL_MATCH_TAGS[tag] == 'email':
498
value = 'mailto:%s' % value
500
gtk.show_uri(self.window.get_screen(), value,
501
gtk.gdk.x11_get_server_time(self.window))
587
# First searching in additional matchers
589
client = gconf.client_get_default()
590
use_quick_open = client.get_bool(KEY("/general/quick_open_enable"))
591
cmdline = client.get_string(KEY("/general/quick_open_command_line"))
593
for _useless, _otheruseless, extractor in QUICK_OPEN_MATCHERS:
594
g = re.compile(extractor).match(value)
595
if g and len(g.groups()) == 2:
596
filename = g.group(1)
597
line_number = g.group(2)
599
curdir = self.get_current_directory()
600
filepath = os.path.join(curdir, filename)
601
if not os.path.exists(filepath):
602
logging.info("Cannot open file %s, it doesn't exists (current dir: %s)", filepath,
605
logging.debug("Opening file %s at line %s", filepath, line_number)
606
resolved_cmdline = cmdline % {"file_path": filepath, "line_number": line_number}
607
logging.debug("Command line: %s", resolved_cmdline)
608
subprocess.call(resolved_cmdline, shell=True)
612
if TERMINAL_MATCH_TAGS[tag] == 'schema':
613
# value here should not be changed, it is right and
616
elif TERMINAL_MATCH_TAGS[tag] == 'http':
617
value = 'http://%s' % value
618
elif TERMINAL_MATCH_TAGS[tag] == 'email':
619
value = 'mailto:%s' % value
621
gtk.show_uri(self.window.get_screen(), value,
622
gtk.gdk.x11_get_server_time(self.window))
502
623
elif event.button == 3 and matched_string:
503
624
self.matched_value = matched_string[0]
626
def set_font(self, font):
628
self.set_font_scale_index(0)
630
def set_font_scale_index(self, scale_index):
631
self.font_scale_index = clamp(scale_index, -6, 12)
633
font = FontDescription(self.font.to_string())
634
scale_factor = 2 ** (self.font_scale_index / 6)
635
new_size = int(scale_factor * font.get_size())
637
if font.get_size_is_absolute():
638
font.set_absolute_size(new_size)
640
font.set_size(new_size)
642
super(GuakeTerminal, self).set_font(font)
644
font_scale = property(
645
fset=set_font_scale_index,
646
fget=lambda self: self.font_scale_index
649
def increase_font_size(self):
652
def decrease_font_size(self):
505
656
class GuakeTerminalBox(gtk.HBox):
506
657
"""A box to group the terminal and a scrollbar.
536
687
# setting global hotkey and showing a pretty notification =)
537
688
guake.globalhotkeys.init()
690
# Cannot use "getattr(gtk.Window().get_style(), "base")[int(gtk.STATE_SELECTED)]"
691
# since theme has not been applied before first show_all
692
self.selected_color = None
694
self.isPromptQuitDialogOpened = False
540
img = pixmapfile('guake-tray.png')
541
self.tray_icon = gtk.status_icon_new_from_file(img)
542
self.tray_icon.set_tooltip(_('Guake Terminal'))
543
self.tray_icon.connect('popup-menu', self.show_menu)
544
self.tray_icon.connect('activate', self.show_hide)
700
img = pixmapfile('guake-tray.png')
701
self.tray_icon = gtk.status_icon_new_from_file(img)
702
self.tray_icon.set_tooltip(_('Guake Terminal'))
703
self.tray_icon.connect('popup-menu', self.show_menu)
704
self.tray_icon.connect('activate', self.show_hide)
706
self.tray_icon = appindicator.Indicator(_("guake-indicator"), _("guake-tray"), appindicator.CATEGORY_OTHER)
707
self.tray_icon.set_icon("guake-tray")
708
self.tray_icon.set_status(appindicator.STATUS_ACTIVE)
709
menu = self.get_widget('tray-menu')
710
show = gtk.MenuItem(_('Show'))
711
show.set_sensitive(True)
712
show.connect('activate', self.show_hide)
715
self.tray_icon.set_menu(menu)
546
717
# adding images from a different path.
547
718
ipath = pixmapfile('guake.png')
639
830
filename = pixmapfile('guake-notification.png')
641
832
if self.client.get_bool(KEY('/general/start_fullscreen')):
644
835
if not self.hotkeys.bind(key, self.show_hide):
645
notification = pynotify.Notification(
836
guake.notifier.show_message(
647
838
_('A problem happened when binding <b>%s</b> key.\n'
648
839
'Please use Guake Preferences dialog to choose another '
649
'key (The trayicon was enabled)') % label, filename)
840
'key') % xml_escape(label), filename)
650
841
self.client.set_bool(KEY('/general/use_trayicon'), True)
653
843
elif self.client.get_bool(KEY('/general/use_popup')):
654
844
# Pop-up that shows that guake is working properly (if not
655
845
# unset in the preferences windows)
656
notification = pynotify.Notification(
846
guake.notifier.show_message(
658
848
_('Guake is now running,\n'
659
'press <b>%s</b> to use it.') % label, filename)
849
'press <b>%s</b> to use it.') % xml_escape(label), filename)
851
def set_background_transparency(self, transparency):
852
for i in self.term_list:
853
i.set_background_saturation(transparency / 100.0)
855
i.set_opacity(int((100 - transparency) / 100.0 * 65535))
857
def set_background_image(self, image):
858
for i in self.term_list:
859
if image and os.path.exists(image):
860
i.set_background_image_file(image)
861
i.set_background_transparent(False)
863
"""We need to clear the image if it's not set but there is
864
a bug in vte python bindings which doesn't allow None to be
865
passed to set_background_image (C GTK function expects NULL).
866
The user will need to restart Guake after clearing the image.
867
i.set_background_image(None)
870
i.set_background_transparent(False)
872
i.set_background_transparent(True)
874
def set_bgcolor(self, bgcolor, tab=None):
875
"""Set the background color of `tab' or the current tab to `bgcolor'."""
876
if not self.term_list:
878
index = tab or self.notebook.get_current_page()
879
self.term_list[index].custom_bgcolor = gtk.gdk.color_parse(bgcolor)
881
def set_fgcolor(self, fgcolor, tab=None):
882
"""Set the foreground color of `tab' or the current tab to `fgcolor'."""
883
if not self.term_list:
885
index = tab or self.notebook.get_current_page()
886
self.term_list[index].custom_fgcolor = gtk.gdk.color_parse(fgcolor)
662
888
def execute_command(self, command, tab=None):
663
889
"""Execute the `command' in the `tab'. If tab is None, the
726
959
self.get_widget('context_paste').set_sensitive(False)
728
961
self.get_widget('context_paste').set_sensitive(True)
963
current_selection = ''
964
current_term = self.term_list[self.notebook.get_current_page()]
965
if current_term.get_has_selection():
966
current_term.copy_clipboard()
967
guake_clipboard = gtk.clipboard_get()
968
current_selection = guake_clipboard.wait_for_text().rstrip()
970
if len(current_selection) > 20:
971
current_selection = current_selection[:17] + "..."
973
if current_selection:
974
self.get_widget('context_search_on_web').set_label(_("Search on Web: '%s'") % current_selection)
975
self.get_widget('context_search_on_web').set_sensitive(True)
977
self.get_widget('context_search_on_web').set_label(_("Search on Web (no selection)"))
978
self.get_widget('context_search_on_web').set_sensitive(False)
729
980
context_menu = self.get_widget('context-menu')
730
981
context_menu.popup(None, None, None, 3, gtk.get_current_event_time())
733
def show_rename_dialog(self, target, event):
984
def show_rename_current_tab_dialog(self, target, event):
734
985
"""On double-click over a tab, show the rename dialog.
736
987
if event.button == 1:
737
988
if event.type == gtk.gdk._2BUTTON_PRESS:
989
self.accel_rename_current_tab()
739
990
self.set_terminal_focus()
740
991
self.selected_tab.pressed()
814
1091
"""Hides the main window of the terminal and sets the visible
817
self.window.hide() # Don't use hide_all here!
1094
self.window.set_keep_below(True)
1095
self.window.hide() # Don't use hide_all here!
1097
def get_final_window_monitor(self):
1098
"""Gets the final screen number for the main window of guake.
1101
screen = self.window.get_screen()
1104
use_mouse = self.client.get_bool(KEY('/general/mouse_display'))
1105
dest_screen = self.client.get_int(KEY('/general/display_n'))
1108
x, y, _ = screen.get_root_window().get_pointer()
1109
dest_screen = screen.get_monitor_at_point(x, y)
1111
# If Guake is configured to use a screen that is not currently attached,
1112
# default to 'primary display' option.
1113
n_screens = screen.get_n_monitors()
1114
if dest_screen > n_screens - 1:
1115
self.client.set_bool(KEY('/general/mouse_display'), False)
1116
self.client.set_int(KEY('/general/display_n'), dest_screen)
1117
dest_screen = screen.get_primary_monitor()
1119
# Use primary display if configured
1120
if dest_screen == ALWAYS_ON_PRIMARY:
1121
dest_screen = screen.get_primary_monitor()
819
1125
def get_final_window_rect(self):
820
1126
"""Gets the final size of the main window of guake. The height
821
1127
is the window_height property, width is window_width and the
822
1128
horizontal alignment is given by window_alignment.
824
screen = self.window.get_screen()
825
height = self.client.get_int(KEY('/general/window_height'))
1133
height_percents = self.client.get_float(KEY('/general/window_height'))
1135
height_percents = self.client.get_int(KEY('/general/window_height'))
1137
width_percents = self.client.get_float(KEY('/general/window_width'))
1139
width_percents = self.client.get_int(KEY('/general/window_width'))
827
1140
halignment = self.client.get_int(KEY('/general/window_halignment'))
829
# get the rectangle just from the first/default monitor in the
830
# future we might create a field to select which monitor you
832
window_rect = screen.get_monitor_geometry(0)
1141
valignment = self.client.get_int(KEY('/general/window_valignment'))
1143
# get the rectangle just from the destination monitor
1144
screen = self.window.get_screen()
1145
monitor = self.get_final_window_monitor()
1146
window_rect = screen.get_monitor_geometry(monitor)
1148
if os.environ.get('DESKTOP_SESSION') == "ubuntu":
1149
unity_hide = self.client.get_int(KEY('/apps/compiz-1/plugins/'
1150
'unityshell/screen0/options/launcher_hide_mode'))
1151
# launcher_hide_mode = 1 => autohide
1153
# Size of the icons for Unity in Ubuntu <= 12.04
1154
# TODO Ubuntu 12.10 use dconf :
1155
# /org/compiz/profiles/unity/plugins/unityshell/icon-size
1156
unity_icon_size = self.client.get_int(KEY('/apps/compiz-1/'
1157
'plugins/unityshell/screen0/options/icon_size'))
1158
unity_dock = unity_icon_size + 17
1159
window_rect.width = window_rect.width - unity_dock
833
1161
total_width = window_rect.width
834
window_rect.height = window_rect.height * height / 100
835
window_rect.width = window_rect.width * width / 100
837
if width < total_width:
1162
total_height = window_rect.height
1164
window_rect.height = window_rect.height * height_percents / 100
1165
window_rect.width = window_rect.width * width_percents / 100
1167
if window_rect.width < total_width:
838
1168
if halignment == ALIGN_CENTER:
839
window_rect.x = (total_width - window_rect.width) / 2
1169
window_rect.x += (total_width - window_rect.width) / 2
840
1170
elif halignment == ALIGN_LEFT:
842
1172
elif halignment == ALIGN_RIGHT:
843
window_rect.x = total_width - window_rect.width
1173
window_rect.x += total_width - window_rect.width
1174
if window_rect.height < total_height:
1175
if valignment == ALIGN_BOTTOM:
1176
window_rect.y += (total_height - window_rect.height)
845
1178
return window_rect
847
1180
def get_running_fg_processes(self):
1243
def accel_zoom_in(self, *args):
1244
"""Callback to zoom in.
1246
for term in self.term_list:
1247
term.increase_font_size()
1250
def accel_zoom_out(self, *args):
1251
"""Callback to zoom out.
1253
for term in self.term_list:
1254
term.decrease_font_size()
1257
def accel_increase_height(self, *args):
1258
"""Callback to increase height.
1261
height = self.client.get_float(KEY('/general/window_height'))
1263
height = self.client.get_int(KEY('/general/window_height'))
1265
self.client.set_int(KEY('/general/window_height'), int(height) + 2)
1268
def accel_decrease_height(self, *args):
1269
"""Callback to decrease height.
1272
height = self.client.get_float(KEY('/general/window_height'))
1274
height = self.client.get_int(KEY('/general/window_height'))
1276
self.client.set_int(KEY('/general/window_height'), int(height) - 2)
902
1279
def accel_add(self, *args):
903
1280
"""Callback to add a new tab. Called by the accel key.
917
1294
def accel_next(self, *args):
918
1295
"""Callback to go to the next tab. Called by the accel key.
920
if self.notebook.get_current_page()+1 == self.notebook.get_n_pages():
1297
if self.notebook.get_current_page() + 1 == self.notebook.get_n_pages():
921
1298
self.notebook.set_current_page(0)
923
1300
self.notebook.next_page()
926
def accel_rename(self, *args):
1303
def gen_accel_switch_tabN(self, N):
1304
"""Generates callback (which called by accel key) to go to the Nth tab.
1306
def callback(*args):
1307
if N >= 0 and N < self.notebook.get_n_pages():
1308
self.notebook.set_current_page(N)
1313
def accel_rename_current_tab(self, *args):
927
1314
"""Callback to show the rename tab dialog. Called by the accel
930
1317
pagepos = self.notebook.get_current_page()
931
1318
self.selected_tab = self.tabs.get_children()[pagepos]
932
self.on_rename_activate()
1319
self.on_rename_current_tab_activate()
935
1322
def accel_copy_clipboard(self, *args):
1220
1648
bnt.set_property('can-focus', False)
1221
1649
bnt.set_property('draw-indicator', False)
1222
1650
bnt.connect('button-press-event', self.show_tab_menu)
1223
bnt.connect('button-press-event', self.show_rename_dialog)
1651
bnt.connect('button-press-event', self.show_rename_current_tab_dialog)
1224
1652
bnt.connect('clicked',
1225
1653
lambda *x: self.notebook.set_current_page(
1226
1654
self.notebook.page_num(box)
1656
if self.selected_color is not None:
1657
bnt.modify_bg(gtk.STATE_ACTIVE, gtk.gdk.Color(str(self.selected_color)))
1658
drag_drop_type = ("text/plain", gtk.TARGET_SAME_APP, 80)
1659
bnt.drag_dest_set(gtk.DEST_DEFAULT_ALL, [drag_drop_type], gtk.gdk.ACTION_MOVE)
1660
bnt.connect("drag_data_received", self.on_drop_tab)
1661
bnt.drag_source_set(gtk.gdk.BUTTON1_MASK, [drag_drop_type], gtk.gdk.ACTION_MOVE)
1662
bnt.connect("drag_data_get", self.on_drag_tab)
1230
1665
self.tabs.pack_start(bnt, expand=False, padding=1)
1234
1669
box.terminal.grab_focus()
1235
1670
self.load_config()
1672
if self.is_fullscreen:
1675
def on_drag_tab(self, widget, context, selection, targetType, eventTime):
1676
tab_pos = self.tabs.get_children().index(widget)
1677
selection.set(selection.target, 32, str(tab_pos))
1679
def on_drop_tab(self, widget, context, x, y, selection, targetType, data):
1680
old_tab_pos = int(selection.get_text())
1681
new_tab_pos = self.tabs.get_children().index(widget)
1682
self.move_tab(old_tab_pos, new_tab_pos)
1684
def move_tab(self, old_tab_pos, new_tab_pos):
1685
self.notebook.reorder_child(self.notebook.get_nth_page(old_tab_pos), new_tab_pos)
1686
self.pid_list.insert(new_tab_pos, self.pid_list.pop(old_tab_pos))
1687
self.term_list.insert(new_tab_pos, self.term_list.pop(old_tab_pos))
1688
self.tabs.reorder_child(self.tabs.get_children()[old_tab_pos], new_tab_pos)
1237
1690
def delete_tab(self, pagepos, kill=True):
1238
1691
"""This function will destroy the notebook page, terminal and
1239
1692
tab widgets and will call the function to kill interpreter
1321
1794
from optparse import OptionParser
1322
1795
parser = OptionParser()
1323
1796
parser.add_option('-f', '--fullscreen', dest='fullscreen',
1324
action='store_true', default=False,
1325
help=_('Put Guake in fullscreen mode'))
1797
action='store_true', default=False,
1798
help=_('Put Guake in fullscreen mode'))
1327
1800
parser.add_option('-t', '--toggle-visibility', dest='show_hide',
1328
action='store_true', default=False,
1329
help=_('Toggles the visibility of the terminal window'))
1801
action='store_true', default=False,
1802
help=_('Toggles the visibility of the terminal window'))
1804
parser.add_option('--show', dest="show",
1805
action='store_true', default=False,
1806
help=_('Shows Guake main window'))
1808
parser.add_option('--hide', dest='hide',
1809
action='store_true', default=False,
1810
help=_('Hides Guake main window'))
1331
1812
parser.add_option('-p', '--preferences', dest='show_preferences',
1332
action='store_true', default=False,
1333
help=_('Shows Guake preference window'))
1813
action='store_true', default=False,
1814
help=_('Shows Guake preference window'))
1335
1816
parser.add_option('-a', '--about', dest='show_about',
1336
action='store_true', default=False,
1337
help=_('Shows Guake\'s about info'))
1817
action='store_true', default=False,
1818
help=_('Shows Guake\'s about info'))
1339
1820
parser.add_option('-n', '--new-tab', dest='new_tab',
1340
action='store', default='',
1341
help=_('Add a new tab'))
1821
action='store', default='',
1822
help=_('Add a new tab (with current directory set to NEW_TAB)'))
1343
1824
parser.add_option('-s', '--select-tab', dest='select_tab',
1344
action='store', default='',
1345
help=_('Select a tab'))
1825
action='store', default='',
1826
help=_('Select a tab (SELECT_TAB is the index of the tab)'))
1347
1828
parser.add_option('-g', '--selected-tab', dest='selected_tab',
1348
action='store_true', default=False,
1349
help=_('Return the selectd tab index.'))
1829
action='store_true', default=False,
1830
help=_('Return the selected tab index.'))
1351
1832
parser.add_option('-e', '--execute-command', dest='command',
1352
action='store', default='',
1353
help=_('Execute an arbitrary command in the selected tab.'))
1355
parser.add_option('-r', '--rename-tab', dest='rename_tab',
1356
action='store', default='',
1357
help=_('Rename the selected tab.'))
1833
action='store', default='',
1834
help=_('Execute an arbitrary command in the selected tab.'))
1836
parser.add_option('-i', '--tab-index', dest='tab_index',
1837
action='store', default='0',
1838
help=_('Specify the tab to rename. Default is 0.'))
1840
parser.add_option('--bgcolor', dest='bgcolor',
1841
action='store', default='',
1842
help=_('Set the hexadecimal (#rrggbb) background color of the selected tab.'))
1844
parser.add_option('--fgcolor', dest='fgcolor',
1845
action='store', default='',
1846
help=_('Set the hexadecimal (#rrggbb) foreground color of the selected tab.'))
1848
parser.add_option('--rename-tab', dest='rename_tab',
1850
action='store', default='',
1851
help=_('Rename the specified tab. Reset to default if TITLE is a single dash "-".'))
1853
parser.add_option('-r', '--rename-current-tab', dest='rename_current_tab',
1855
action='store', default='',
1856
help=_('Rename the current tab. Reset to default if TITLE is a single dash "-".'))
1359
1858
parser.add_option('-q', '--quit', dest='quit',
1360
action='store_true', default=False,
1361
help=_('Says to Guake go away =('))
1859
action='store_true', default=False,
1860
help=_('Says to Guake go away =('))
1363
1862
options = parser.parse_args()[0]