Peppermint-Classic-Build-Files/PeppermintOS-Classic-i386/config/includes.chroot/usr/bin/ice

858 lines
30 KiB
Plaintext
Raw Normal View History

#!/usr/bin/env python3
#
# by Kendall Weaver <kendall@peppermintos.com>
# for Peppermint OS
# modified by Mark Greaves (PCNetSpec) <mark@peppermintos.com>
# with much appreciated code contributions by rhein
# internationalization (i18n)/gettext support by Kiyohito AOKI
#
# Ice is a simple Site Specific Browser (SSB) manager for Chromium and
# Chrome specifically intended to integrate with the LXDE menu system.
# Unlike the built-in functions in the browsers, Ice boasts the ability
# to remove SSBs, validate addresses, and prevent overwriting existing
# SSBs. Special thanks to Matt Phillips <labratmatt@gmail.com> for the
# excellent pyfav library that is integrated into this application.
# ADDENDUM: Added support for Firefox (via "ice-firefox") and Vivaldi.
import os
import sys
import requests
import urllib.request
import urllib.parse
import urllib.error
import os.path
import string
import gi ## added by MG ##
gi.require_version('Gtk','3.0') ## added by MG ##
from gi.repository import Gtk
from gi.repository.GdkPixbuf import Pixbuf
from urllib.parse import urlparse, urlunparse
from bs4 import BeautifulSoup
import gettext
import locale
_HOME = os.getenv("HOME")
_ICE_DIR = "{0}/.local/share/ice".format(_HOME)
_APPS_DIR = "{0}/.local/share/applications".format(_HOME)
_PROFILES_DIR = "{0}/profiles".format(_ICE_DIR)
_FF_PROFILES_DIR = "{0}/firefox".format(_ICE_DIR)
_ICE_ICON = "/usr/share/pixmaps/ice.png"
_CHROME_BIN = "/usr/bin/google-chrome"
_CHROMIUM_BIN = "/usr/bin/chromium-browser"
_VIVALDI_BIN = "/usr/bin/vivaldi"
_FIREFOX_BIN = "/usr/bin/firefox"
gettext.bindtextdomain('messages', os.path.dirname(__file__)+ '/../share/ice/locale/')
gettext.textdomain('messages')
_ = gettext.gettext
# Requisite dirs
for directory in [ _ICE_DIR, _APPS_DIR, _PROFILES_DIR, _FF_PROFILES_DIR ]:
if not os.path.exists(directory):
os.system("mkdir -p {0}".format(directory))
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:64.0) Gecko/20100101 Firefox/64.0',
#'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/33.0.1750.152 Safari/537.36'
}
def get_details(app):
a = open(app, 'r', errors='ignore')
nameline = ""
iconline = ""
profile = ""
is_ice = False
is_firefox = False
is_isolated = False
for line in a:
if "Name=" in line:
array = line.replace("=", " ").split()
array.pop(0)
for word in array:
nameline = nameline + word + " "
elif "Icon=" in line:
array = line.replace("=", " ").split()
array.pop(0)
for word in array:
iconline = iconline + word
try:
pixbuf = Pixbuf.new_from_file_at_size(iconline, 16, 16)
except:
pixbuf = Pixbuf.new_from_file_at_size(_ICE_ICON, 16, 16)
elif "StartupWMClass=Chromium" in line:
# for legacy apps
is_ice = True
elif "StartupWMClass=ICE-SSB" in line:
is_ice = True
elif "IceFirefox=" in line:
is_firefox = True
profile = str.replace(line, 'IceFirefox=', '').strip()
elif "X-ICE-SSB-Profile=" in line:
is_isolated = True
profile = str.replace(line, 'X-ICE-SSB-Profile=', '').strip()
if nameline != "" and iconline != "" and is_ice is True:
details = {
'nameline' : nameline,
'profile' : profile,
'is_firefox' : is_firefox,
'is_isolated' : is_isolated,
'pixbuf': pixbuf
}
return details
return None
def normalize(url):
(scheme, netloc, path, _, _, frag) = urlparse(url, "http")
if not netloc and path:
return urlunparse((scheme, path, "", "", "", ""))
return urlunparse((scheme, netloc, path, "", "", ""))
def errortest(url):
try:
urllib.request.urlopen(url)
return True
except (urllib.request.HTTPError, urllib.request.URLError):
return False
def download_favicon(url, file_prefix='', target_dir='/tmp'):
parsed_site_uri = urlparse(url)
if not parsed_site_uri.scheme:
url = 'http://{0}'.format(url)
parsed_site_uri = urlparse(url)
if not parsed_site_uri.scheme or not parsed_site_uri.netloc:
raise Exception(_("Unable to parse URL, {0}").format(url))
favicon_url = get_favicon_url(url)
if not favicon_url:
raise Exception(_("Unable to find favicon for, {0}").format(url))
response = requests.get(favicon_url, headers=headers)
if response.status_code == requests.codes.ok:
parsed_uri = urlparse(favicon_url)
favicon_filepath = parsed_uri.path
favicon_path, favicon_filename = os.path.split(favicon_filepath)
valid_chars = "-_.() %s%s" % (string.ascii_letters, string.digits)
sanitized_filename = "".join([x if valid_chars else "" for x in favicon_filename])
sanitized_filename = os.path.join(target_dir, file_prefix + sanitized_filename)
with open(sanitized_filename, 'wb') as f:
for chunk in response.iter_content(chunk_size=1024):
if chunk: # filter out keep-alive new chunks
f.write(chunk)
f.flush()
return sanitized_filename
def parse_markup_for_favicon(markup, parsed_site_uri):
soup = BeautifulSoup(markup, "lxml")
icon_link = soup.find('link', rel='icon')
if icon_link and icon_link.has_attr('href'):
favicon_url = icon_link['href']
if favicon_url.startswith('//'):
parsed_uri = urlparse(url)
favicon_url = "{0}:{1}".format(parsed_uri.scheme, favicon_url)
elif favicon_url.startswith('/'):
favicon_url = "{0}://{1}{2}".format(parsed_site_uri.scheme, parsed_site_uri.netloc, favicon_url)
elif not favicon_url.startswith('http'):
path, filename = os.path.split(parsed_site_uri.path)
favicon_url = "{0}://{1}/{2}".format(parsed_site_uri.scheme, parsed_site_uri.netloc,
os.path.join(path, favicon_url))
return favicon_url
return None
def get_favicon_url(url):
parsed_site_uri = urlparse(url)
try:
response = requests.get(url, headers=headers)
except:
raise Exception(_("Unable to find URL. Is it valid? {0}").format(url))
if response.status_code == requests.codes.ok:
favicon_url = parse_markup_for_favicon(response.content, parsed_site_uri)
if favicon_url:
return favicon_url
favicon_url = '{uri.scheme}://{uri.netloc}/favicon.ico'.format(uri=parsed_site_uri)
response = requests.get(favicon_url, headers=headers)
if response.status_code == requests.codes.ok:
return favicon_url
return None
def applicate():
title = name.get_text()
address = normalize(url.get_text())
semiformatted = ""
array = filter(str.isalpha, title)
for obj in array:
semiformatted = semiformatted + obj
formatted = semiformatted.lower()
loc = where.get_active_text()
if loc == _("Accessories"):
location = "Utility;"
elif loc == _("Games"):
location = "Game;"
elif loc == _("Graphics"):
location = "Graphics;"
elif loc == _("Internet"):
location = "Network;"
elif loc == _("Office"):
location = "Office;"
elif loc == _("Programming"):
location = "Development;"
elif loc == _("Multimedia"):
location = "AudioVideo;"
elif loc == _("System"):
location = "System;"
global iconpath
iconname = iconpath.replace("/", " ").split()[-1]
iconext = iconname.replace(".", " ").split()[-1]
if os.path.exists("{0}/{1}.desktop".format(_APPS_DIR, formatted)):
DuplicateError(title, formatted, address, iconext, location)
elif len(title) == 0:
EmptyNameError()
else:
writefile(title, formatted, address, iconext, location)
def writefile(title, formatted, address, iconext, location):
global iconpath
os.system("cp --force {0} {1}/{2}.{3}".format(iconpath, _ICE_DIR, formatted, iconext))
appfile = os.path.expanduser("{0}/{1}.desktop".format(_APPS_DIR, formatted))
os.system("touch {0}".format(appfile))
if chrome.get_active() == True:
browser = "google-chrome"
elif chromium.get_active() == True:
browser = "chromium-browser"
elif vivaldi.get_active() == True:
browser = "vivaldi"
elif firefox.get_active() == True:
browser = "firefox"
else:
print(_("ERROR: An unknown browser selection error has occurred."))
sys.exit(1)
with open(appfile, 'w') as appfile1:
global isolate_profile
appfile1.truncate()
appfile1.write("[Desktop Entry]\n")
appfile1.write("Version=1.0\n")
appfile1.write("Name={0}\n".format(title))
appfile1.write("Comment={0} (Ice SSB)\n".format(title))
if (browser == "firefox"):
firefox_profile_path = "{0}/{1}".format(_FF_PROFILES_DIR, formatted)
appfile1.write("Exec={0} --class ICE-SSB-{2} --profile {3} --no-remote {1}\n".format(browser, address, formatted, firefox_profile_path))
appfile1.write("IceFirefox={0}\n".format(formatted))
init_firefox_profile(firefox_profile_path)
else:
if isolate_profile == True:
profile_path = "{0}/{1}".format(_PROFILES_DIR, formatted)
appfile1.write("Exec={0} --app={1} --class=ICE-SSB-{2} --user-data-dir={3}\n".format(browser, address, formatted, profile_path))
appfile1.write("X-ICE-SSB-Profile={0}\n".format(formatted))
else:
appfile1.write("Exec={0} --app={1} --class=ICE-SSB-{2}\n".format(browser, address, formatted))
appfile1.write("Terminal=false\n")
appfile1.write("X-MultipleArgs=false\n")
appfile1.write("Type=Application\n")
appfile1.write("Icon={0}/{1}.{2}\n".format(_ICE_DIR, formatted, iconext))
appfile1.write("Categories=GTK;{0}\n".format(location))
appfile1.write("MimeType=text/html;text/xml;application/xhtml_xml;\n")
appfile1.write("StartupWMClass=ICE-SSB-{0}\n".format(formatted))
appfile1.write("StartupNotify=true\n")
name.set_text("")
url.set_text("")
iconpath = _ICE_ICON
new_icon = Pixbuf.new_from_file_at_size(iconpath, 32, 32)
icon.set_from_pixbuf(new_icon)
details = get_details(appfile)
if details is not None:
liststore.prepend([ details['pixbuf'], details['nameline'] ])
def init_firefox_profile(path):
chromepath = "{0}/chrome".format(path)
settingsfile = "{0}/user.js".format(path)
cssfile = "{0}/userChrome.css".format(chromepath)
os.system('mkdir -p ' + chromepath)
os.system('cp -n /usr/lib/peppermint/ice/search.json.mozlz4 ' + path + '/search.json.mozlz4')
os.system('cp -n /usr/lib/peppermint/ice/places.sqlite ' + path + '/places.sqlite')
os.system("touch {0}".format(cssfile))
with open(cssfile, 'w') as cfile:
cfile.write("#nav-bar, #identity-box, #tabbrowser-tabs, #TabsToolbar { visibility: collapse !important; }")
os.system("touch {0}".format(settingsfile))
with open(settingsfile, 'w') as sfile:
sfile.write('user_pref("browser.cache.disk.enable", false);')
sfile.write('user_pref("browser.cache.disk.capacity", 0);')
sfile.write('user_pref("browser.cache.disk.filesystem_reported", 1);')
sfile.write('user_pref("browser.cache.disk.smart_size.enabled", false);')
sfile.write('user_pref("browser.cache.disk.smart_size.first_run", false);')
sfile.write('user_pref("browser.cache.disk.smart_size.use_old_max", false);')
sfile.write('user_pref("browser.ctrlTab.previews", true);')
sfile.write('user_pref("browser.tabs.warnOnClose", false);')
sfile.write('user_pref("plugin.state.flash", 2);')
sfile.write('user_pref("toolkit.legacyUserProfileCustomizations.stylesheets", true);')
# rhein: do we really need this?
#os.system('rm -rf ' + chromepath + '/cache2')
def delete(button):
a = iconview.get_selected_items()
b = liststore.get_iter(a[0])
c = liststore.get_value(b, 1)
liststore.remove(b)
semiformatted = ""
array = filter(str.isalpha, c)
for obj in array:
semiformatted = semiformatted + obj
formatted = semiformatted.lower()
appfile = "{0}/{1}.desktop".format(_APPS_DIR, formatted)
appfileopen = open(appfile, 'r')
appfilelines = appfileopen.readlines()
appfileopen.close()
for line in appfilelines:
if "IceFirefox=" in line:
profile = str.replace(line, 'IceFirefox=', '')
os.system("rm -rf {0}/{1}".format(_FF_PROFILES_DIR, profile))
if "X-ICE-SSB-Profile=" in line:
profile = str.replace(line, 'X-ICE-SSB-Profile=', '')
os.system("rm -rf {0}/{1}".format(_PROFILES_DIR, profile))
os.system("rm {0}".format(appfile))
def clean_orphaned_profiles(known_apps):
known_profiles = []
for app in known_apps:
a = "{0}/{1}".format(_FF_PROFILES_DIR, app['profile'])
if app['profile'] != "":
# make sure firefox apps have profiles available
if app['is_firefox'] is True and not os.path.isdir(a):
init_firefox_profile(a)
known_profiles.append(app['profile'])
for p_type in ['profiles','firefox']:
for fl in os.listdir("{0}/{1}/".format(_ICE_DIR, p_type)):
a = "{0}/{1}/{2}".format(_ICE_DIR, p_type, fl)
if not os.path.isdir(a) or fl not in known_profiles:
os.system("rm -rf {0}".format(a))
class IconSel(Gtk.FileChooserDialog):
def __init__(self):
def update_image(dialog):
filename = dialog.get_preview_filename()
try:
pixbuf = Pixbuf.new_from_file(filename)
preview.set_from_pixbuf(pixbuf)
valid_preview = True
except:
valid_preview = False
dialog.set_preview_widget_active(valid_preview)
filew = Gtk.FileChooserDialog(
_("Please choose an icon."),
None,
Gtk.FileChooserAction.OPEN,
(Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL, Gtk.STOCK_OPEN, Gtk.ResponseType.OK))
filew.set_filename(_ICE_ICON)
filter1 = Gtk.FileFilter()
filter1.set_name("Icons")
filter1.add_mime_type("image/png")
filter1.add_mime_type("image/jpeg")
filter1.add_mime_type("image/gif")
filter1.add_pattern("*.png")
filter1.add_pattern("*.jpg")
filter1.add_pattern("*.gif")
filter1.add_pattern("*.xpm")
filter1.add_pattern("*.svg")
filew.add_filter(filter1)
preview = Gtk.Image()
filew.set_preview_widget(preview)
filew.connect("update-preview", update_image)
response = filew.run()
if response == Gtk.ResponseType.OK:
global iconpath
iconpath = filew.get_filename()
new_icon = Pixbuf.new_from_file_at_size(iconpath, 32, 32)
icon.set_from_pixbuf(new_icon)
filew.destroy()
elif response == Gtk.ResponseType.CANCEL:
filew.destroy()
class NoBrowserError(Gtk.Window):
def destroy(self, button):
self.close()
def __init__(self):
Gtk.Window.__init__(self, title=_("Browser Error"))
self.set_size_request(250, 130)
self.set_icon_from_file(_ICE_ICON)
print(_("test"))
main_lab = Gtk.Label()
main_lab.set_markup(_("<b>Warning: No Suitable Browser Detected</b>"))
text_lab = Gtk.Label(_("The name of the SSB will cause an existing SSB to\nbe overwritten. To prevent this, change a letter in\nthe name. Continue anyway?"))
text_lab = Gtk.Label(_("Ice requires a system installation of either Google\nChrome or Chromium in order to function. Please\ninstall at least one in order to create SSBs."))
close = Gtk.Button(label=_("Close"))
close.connect("clicked", self.destroy)
void = Gtk.Label()
box = Gtk.HBox()
box.pack_start(void, True, True, 0)
box.pack_start(close, False, False, 0)
main_vbox = Gtk.VBox()
main_vbox.pack_start(main_lab, False, False, 10)
main_vbox.pack_start(text_lab, False, False, 0)
main_vbox.pack_start(box, False, False, 10)
main_hbox = Gtk.HBox()
main_hbox.pack_start(main_vbox, True, True, 10)
self.add(main_hbox)
self.show_all()
class DuplicateError(Gtk.Window):
def destroy(self, button):
self.close()
def okay_clicked(self, button, title, formatted, address, iconext, location):
for item in liststore:
itemiter = item.iter
semiformatted = ""
array = filter(str.isalpha, item[1])
for obj in array:
semiformatted = semiformatted + obj
forma = semiformatted.lower()
if forma == formatted:
liststore.remove(itemiter)
writefile(title, formatted, address, iconext, location)
self.close()
def __init__(self, title, formatted, address, iconext, location):
Gtk.Window.__init__(self, title=_("Duplication Error"))
self.set_size_request(250, 130)
self.set_icon_from_file(_ICE_ICON)
main_lab = Gtk.Label()
main_lab.set_markup(_("<b>Warning: File Duplication Error</b>"))
text_lab = Gtk.Label(_("The name of the SSB will cause an existing SSB to\nbe overwritten. To prevent this, change a letter in\nthe name. Continue anyway?"))
okay = Gtk.Button(label=_("OK"))
okay.connect("clicked", self.okay_clicked, title, formatted, address, iconext, location)
cancel = Gtk.Button(label=_("Cancel"))
cancel.connect("clicked", self.destroy)
void = Gtk.Label()
box = Gtk.HBox()
box.pack_start(void, True, True, 0)
box.pack_start(okay, False, False, 10)
box.pack_start(cancel, False, False, 0)
main_vbox = Gtk.VBox()
main_vbox.pack_start(main_lab, False, False, 10)
main_vbox.pack_start(text_lab, False, False, 0)
main_vbox.pack_start(box, False, False, 10)
main_hbox = Gtk.HBox()
main_hbox.pack_start(main_vbox, True, True, 10)
self.add(main_hbox)
self.show_all()
class AddressError(Gtk.Window):
def destroy(self, button):
self.close()
def okay_clicked(self, button):
applicate()
self.close()
def __init__(self):
Gtk.Window.__init__(self, title=_("Address Error"))
self.set_size_request(250, 130)
self.set_icon_from_file(_ICE_ICON)
main_lab = Gtk.Label()
main_lab.set_markup(_("<b>Warning: HTTP or URL Error</b>"))
text_lab = Gtk.Label(_("An error with the web address has been detected.\nThis is possibly the site being down or unavailable\nright now. Continue anyway?"))
okay = Gtk.Button(label=_("OK"))
okay.connect("clicked", self.okay_clicked)
cancel = Gtk.Button(label=_("Cancel"))
cancel.connect("clicked", self.destroy)
void = Gtk.Label()
box = Gtk.HBox()
box.pack_start(void, True, True, 0)
box.pack_start(okay, False, False, 10)
box.pack_start(cancel, False, False, 0)
main_vbox = Gtk.VBox()
main_vbox.pack_start(main_lab, False, False, 10)
main_vbox.pack_start(text_lab, False, False, 0)
main_vbox.pack_start(box, False, False, 10)
main_hbox = Gtk.HBox()
main_hbox.pack_start(main_vbox, True, True, 10)
self.add(main_hbox)
self.show_all()
class EmptyNameError(Gtk.Window):
def destroy(self, button):
self.close()
def okay_clicked(self, button):
applicate()
self.close()
def __init__(self):
Gtk.Window.__init__(self, title=_("Name Error"))
self.set_size_request(250, 130)
self.set_icon_from_file(_ICE_ICON)
main_lab = Gtk.Label()
main_lab.set_markup(_("<b>Error: No Application Name Entered.</b>"))
text_lab = Gtk.Label(_("Please enter an application name to continue."))
close = Gtk.Button(label=_("Close"))
close.connect("clicked", self.destroy)
void = Gtk.Label()
box = Gtk.HBox()
box.pack_start(void, True, True, 0)
box.pack_start(close, False, False, 0)
main_vbox = Gtk.VBox()
main_vbox.pack_start(main_lab, False, False, 10)
main_vbox.pack_start(text_lab, False, False, 0)
main_vbox.pack_start(box, False, False, 10)
main_hbox = Gtk.HBox()
main_hbox.pack_start(main_vbox, True, True, 10)
self.add(main_hbox)
self.show_all()
class Ice(Gtk.Window):
def destroy(self, button):
Gtk.main_quit()
def icon_select(self, button):
IconSel()
def apply_clicked(self, button):
if errortest(normalize(url.get_text())) is True:
applicate()
elif errortest(normalize(url.get_text())) is False:
AddressError()
elif errortest(normalize(url.get_text())) is None:
print(_("ERROR: An address error has occurred."))
sys.exit(1)
else:
print(_("ERROR: An unknown error has occurred."))
sys.exit(1)
def icon_download(self, button):
appurl = normalize(url.get_text())
global iconpath
try:
download_favicon(appurl)
addr0 = get_favicon_url(appurl)
addr1 = addr0.replace('/', ' ')
addr2 = addr1.split()[-1]
iconpath = "/tmp/{0}".format(addr2)
new_icon = Pixbuf.new_from_file_at_size(iconpath, 32, 32)
icon.set_from_pixbuf(new_icon)
except:
iconpath = _ICE_ICON
new_icon = Pixbuf.new_from_file_at_size(iconpath, 32, 32)
icon.set_from_pixbuf(new_icon)
def isolate_clicked(self, button):
global isolate_profile
isolate_profile=False
if button.get_active() == True:
isolate_profile = True
def __init__(self):
Gtk.Window.__init__(self, title="Ice")
self.current_directory = os.path.realpath(_APPS_DIR)
self.set_size_request(460, 350)
self.set_icon_from_file(_ICE_ICON)
######################
# 'Create' page. #
######################
welcome = Gtk.Label()
welcome.set_markup(_("<b>Welcome to Ice, a simple SSB manager.</b>"))
global name
name = Gtk.Entry()
name.set_placeholder_text(_("Name the application"))
global url
url = Gtk.Entry()
url.set_placeholder_text(_("Enter web address"))
where_store = [_("Accessories"), _("Games"), _("Graphics"), _("Internet"),
_("Office"), _("Programming"), _("Multimedia"), _("System")]
where_lab = Gtk.Label(label=_("Where in the menu?"))
global where
where = Gtk.ComboBoxText()
where.set_entry_text_column(0)
for entry in where_store:
where.append_text(entry)
where.set_active(3)
where_box = Gtk.HBox()
where_void = Gtk.Label()
where_box.pack_start(where_lab, False, False, 0)
where_box.pack_start(where_void, False, False, 10)
where_box.pack_start(where, True, True, 0)
global iconpath
iconpath = _ICE_ICON
icon_pixbuf = Pixbuf.new_from_file_at_size(iconpath, 32, 32)
global icon
icon = Gtk.Image()
icon.set_from_pixbuf(icon_pixbuf)
icon_void = Gtk.Label()
icon_box = Gtk.HBox()
icon_box.pack_start(icon, False, False, 10)
icon_box.pack_start(icon_void, False, False, 10)
choose_icon = Gtk.Button(label=_("Select an icon"))
choose_icon.connect("clicked", self.icon_select)
download_icon = Gtk.Button(label=_("Use site favicon"))
download_icon.connect("clicked", self.icon_download)
icon_vbox = Gtk.VBox()
icon_vbox.pack_start(choose_icon, True, True, 5)
icon_vbox.pack_start(download_icon, True, True, 5)
icon_hbox = Gtk.HBox()
icon_hbox.pack_start(icon_box, False, False, 10)
icon_hbox.pack_start(icon_vbox, True, True, 0)
global firefox
firefox = Gtk.RadioButton.new_with_label_from_widget(None, " Firefox")
if not os.path.exists(_FIREFOX_BIN):
firefox.set_sensitive(False)
if not os.path.exists(_CHROMIUM_BIN) and not \
os.path.exists(_CHROME_BIN) and not \
os.path.exists(_VIVALDI_BIN) and \
os.path.exists(_FIREFOX_BIN):
firefox.set_active(True)
global chrome
chrome = Gtk.RadioButton.new_from_widget(firefox)
chrome.set_label(" Chrome")
if not os.path.exists(_CHROME_BIN):
chrome.set_sensitive(False)
if not os.path.exists(_CHROMIUM_BIN) and not \
os.path.exists(_FIREFOX_BIN) and not \
os.path.exists(_VIVALDI_BIN) and \
os.path.exists(_CHROME_BIN):
chrome.set_active(True)
global vivaldi
vivaldi = Gtk.RadioButton.new_from_widget(chrome)
vivaldi.set_label(" Vivaldi")
if not os.path.exists(_VIVALDI_BIN):
vivaldi.set_sensitive(False)
if not os.path.exists(_CHROMIUM_BIN) and not \
os.path.exists(_FIREFOX_BIN) and not \
os.path.exists(_CHROME_BIN) and \
os.path.exists(_VIVALDI_BIN):
vivaldi.set_active(True)
global chromium
chromium = Gtk.RadioButton.new_from_widget(chrome)
chromium.set_label(" Chromium")
if not os.path.exists(_CHROMIUM_BIN):
chromium.set_sensitive(False)
if not os.path.exists(_CHROME_BIN) and not \
os.path.exists(_FIREFOX_BIN) and not \
os.path.exists(_VIVALDI_BIN) and \
os.path.exists(_CHROMIUM_BIN):
chromium.set_active(True)
global isolate_profile
isolate_profile=False
isolate_box = Gtk.VBox()
isolate_button = Gtk.CheckButton(label=_(" Create the SSB with an isolated browser profile (Note: Firefox SSB's are always isolated)"))
isolate_button.connect("toggled", self.isolate_clicked)
isolate_box.add(isolate_button)
apply_button = Gtk.Button(label=_("Apply"))
apply_button.connect("clicked", self.apply_clicked)
close_button = Gtk.Button(label=_("Close"))
close_button.connect("clicked", self.destroy)
button_void = Gtk.Label()
button_box = Gtk.HBox()
button_box.pack_start(chrome, False, False, 10)
button_box.pack_start(chromium, False, False, 0)
button_box.pack_start(vivaldi, False, False, 10)
button_box.pack_start(firefox, False, False, 0)
button_box.pack_start(button_void, True, True, 0)
button_box.pack_start(close_button, False, False, 20)
button_box.pack_start(apply_button, False, False, 0)
create_vbox = Gtk.VBox()
create_vbox.pack_start(welcome, False, False, 15)
create_vbox.pack_start(name, False, False, 0)
create_vbox.pack_start(url, False, False, 10)
create_vbox.pack_start(where_box, False, False, 10)
create_vbox.pack_start(icon_hbox, False, False, 10)
create_vbox.pack_start(isolate_box, False, False, 10)
create_vbox.pack_start(button_box, False, False, 0)
create_hbox = Gtk.HBox()
create_hbox.pack_start(create_vbox, True, True, 20)
create_lab = Gtk.Label(label=_("Create"))
######################
# 'Remove' page. #
######################
global liststore
known_profiles = []
liststore = Gtk.ListStore(Pixbuf, str)
for fl in os.listdir(_APPS_DIR):
a = "{0}/{1}".format(_APPS_DIR, fl)
if not os.path.isdir(a):
details = get_details(a)
if details is not None:
liststore.append([ details['pixbuf'], details['nameline'] ])
known_profiles.append(details)
clean_orphaned_profiles(known_profiles)
global iconview
iconview = Gtk.IconView()
iconview.set_model(liststore)
iconview.set_pixbuf_column(0)
iconview.set_text_column(1)
iconview.set_selection_mode(1)
scroll = Gtk.ScrolledWindow()
scroll.add(iconview)
remove = Gtk.Button(label=_("Remove"))
remove.connect("clicked", delete)
close = Gtk.Button(label=_("Close"))
close.connect("clicked", self.destroy)
void = Gtk.Label()
buttons = Gtk.HBox()
buttons.pack_start(void, True, True, 0)
buttons.pack_start(close, False, False, 20)
buttons.pack_start(remove, False, False, 0)
remove_vbox = Gtk.VBox()
remove_vbox.pack_start(scroll, True, True, 10)
remove_vbox.pack_start(buttons, False, False, 0)
remove_hbox = Gtk.HBox()
remove_hbox.pack_start(remove_vbox, True, True, 20)
remove_lab = Gtk.Label(label=_("Remove"))
##########################
# Main window stuff. #
##########################
notebook = Gtk.Notebook()
notebook.append_page(create_hbox, create_lab)
notebook.append_page(remove_hbox, remove_lab)
main_vbox = Gtk.VBox()
main_vbox.pack_start(notebook, True, True, 10)
main_hbox = Gtk.HBox()
main_hbox.pack_start(main_vbox, True, True, 10)
self.add(main_hbox)
self.show_all()
if not os.path.exists(_CHROME_BIN) and not \
os.path.exists(_CHROMIUM_BIN) and not \
os.path.exists(_VIVALDI_BIN) and not \
os.path.exists(_FIREFOX_BIN):
apply_button.set_sensitive(False)
NoBrowserError()
if __name__ == '__main__':
window = Ice()
window.connect("delete-event", Gtk.main_quit)
Gtk.main()