Merge branch 'master' of git+ssh://dev.laptop.org/git/sugar

This commit is contained in:
Morgan Collett 2007-07-11 10:42:27 +02:00
commit 8fab49b64e
23 changed files with 216 additions and 199 deletions

23
NEWS
View File

@ -1,3 +1,26 @@
* #1984 Fix removing items from the clipboard. (tomeu)
Snapshot b83a9ec27d
* Fix font size on the XO. (marco)
* Make developer console work again. (marco)
* #2020 Use the new activity-stop icon. (marco)
* #2002 Tooltips for the zoom levels. (marco)
* #2018 Rename Save to Keep. (marco)
* #2020 Rename Close to Stop. (marco)
Snapshot 42f0bcc48d
* Fix broken import which was preventing startup. (marco)
Snapshot 757b2b8ce6
* #2031: Do not die if battery properties are unavailable. (marco)
* #1953: Retrieve friends' nicks from the profile. (tomeu)
* #1720: Show the owner's buddy menu in the Groups view. (tomeu)
Snapshot aa6a024368
* #1825: Fix tab label padding. (marco)
* #1823: Margin at the toolbar tabs bottom. (marco)
* #1872, #1934: Hide palettes when closing activities or switching views. (tomeu)

View File

@ -3,6 +3,9 @@ import sys
from sugar.activity.bundle import Bundle
from dbus.mainloop.glib import DBusGMainLoop
DBusGMainLoop(set_as_default=True)
bundle = Bundle(sys.argv[1])
bundle.install()

View File

@ -83,8 +83,8 @@ def cmd_build_snapshot():
sugar_news += '%s - %s - %s\n\n' % (name, version, alphatag)
f = open('NEWS', 'r')
for line in f.readline():
if len(line) > 0:
for line in f.readlines():
if len(line.strip()) > 0:
sugar_news += line
else:
break

View File

@ -7,4 +7,5 @@ shell/view/Shell.py
shell/view/clipboardicon.py
shell/view/home/HomeBox.py
shell/view/home/MeshBox.py
shell/view/devices/battery.py
sugar/activity/activity.py

View File

@ -141,7 +141,7 @@ class Format:
def get_data(self):
return self._data
def _set_data(self, data):
def set_data(self, data):
self._data = data
def is_on_disk(self):

View File

@ -17,10 +17,16 @@
import logging
import os
import shutil
import urlparse
import tempfile
import dbus
import dbus.service
from sugar import env
from sugar import util
from sugar.objects import mime
from clipboardobject import ClipboardObject, Format
NAME_KEY = 'NAME'
@ -52,34 +58,6 @@ class ClipboardService(dbus.service.Object):
self._next_id += 1
return self._next_id
def _handle_file_completed(self, cb_object):
"""If the object is an on-disk file, and it's at 100%, and we care about
it's file type, copy that file to $HOME and upate the clipboard object's
data to point to the new location"""
formats = cb_object.get_formats()
if not len(formats) or len(formats) > 1:
return
format = formats.values()[0]
if not format.is_on_disk():
return
if not len(cb_object.get_activity()):
# no activity to handle this, don't autosave it
return
# copy to homedir
src = format.get_data()
if not os.path.exists(src):
logging.debug("File %s doesn't appear to exist" % src)
return
dst = os.path.join(os.path.expanduser("~"), os.path.basename(src))
try:
shutil.move(src, dst)
format._set_data(dst)
except IOError, e:
logging.debug("Couldn't move file %s to %s: %s" % (src, dst, e))
# dbus methods
@dbus.service.method(_CLIPBOARD_DBUS_INTERFACE,
in_signature="s", out_signature="o")
@ -96,11 +74,13 @@ class ClipboardService(dbus.service.Object):
def add_object_format(self, object_path, format_type, data, on_disk):
logging.debug('ClipboardService.add_object_format')
cb_object = self._objects[str(object_path)]
cb_object.add_format(Format(format_type, data, on_disk))
if on_disk:
logging.debug('Added format of type ' + format_type + ' with path at ' + data)
if on_disk and cb_object.get_percent() == 100:
new_uri = self._copy_file(data)
cb_object.add_format(Format(format_type, new_uri, on_disk))
logging.debug('Added format of type ' + format_type + ' with path at ' + new_uri)
else:
cb_object.add_format(Format(format_type, data, on_disk))
logging.debug('Added in-memory format of type ' + format_type + '.')
self.object_state_changed(object_path, {NAME_KEY: cb_object.get_name(),
@ -132,7 +112,10 @@ class ClipboardService(dbus.service.Object):
cb_object.set_percent(percent)
if percent == 100:
self._handle_file_completed(cb_object)
for format_name, format in cb_object.get_formats().iteritems():
if format.is_on_disk():
new_uri = self._copy_file(format.get_data())
format.set_data(new_uri)
self.object_state_changed(object_path, {NAME_KEY: cb_object.get_name(),
PERCENT_KEY: percent,
@ -183,6 +166,21 @@ class ClipboardService(dbus.service.Object):
def object_state_changed(self, object_path, values):
pass
def _copy_file(self, original_uri):
uri = urlparse.urlparse(original_uri)
path, file_name = os.path.split(uri.path)
root, ext = os.path.splitext(file_name)
if not ext or ext == '.':
mime_type = mime.get_for_file(uri.path)
ext = '.' + mime.get_primary_extension(mime_type)
f, new_file_path = tempfile.mkstemp(ext, root)
del f
shutil.copyfile(uri.path, new_file_path)
return 'file://' + new_file_path
_instance = None
def get_instance():

View File

@ -4,5 +4,4 @@ sugar_PYTHON = \
xo.py \
cpu.py \
system.py \
battery.py \
nandflash.py

View File

@ -1,99 +0,0 @@
# Copyright (C) 2007, Eduardo Silva (edsiper@gmail.com).
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
import gtk
import gobject
from label import Label
from graphics.box import BoxGraphic
class XO_Battery(gtk.Fixed):
def __init__(self):
gtk.Fixed.__init__(self)
self._frame_text = 'Battery Status'
self.frame = gtk.Frame(self._frame_text)
self.set_border_width(10)
self._battery_charge = self._get_battery_status()
self._battery_box = BoxGraphic()
self._battery_box.set_size_request(70, 150)
self._battery_box.set_capacity(self._battery_charge)
fixed = gtk.Fixed();
fixed.set_border_width(10)
fixed.add(self._battery_box)
hbox = gtk.HBox(False, 0)
hbox.pack_start(fixed, False, False, 4)
# Battery info
table = gtk.Table(2, 2)
table.set_border_width(5)
table.set_col_spacings(7)
table.set_row_spacings(7)
label_charge = Label('Charge: ' , Label.DESCRIPTION)
self.label_charge_value = Label(str(self._battery_charge) + '%', Label.DESCRIPTION)
table.attach(label_charge, 0, 1, 0, 1)
table.attach(self.label_charge_value, 1,2, 0,1)
# Charging
"""
hbox_charging = gtk.HBox(False, 2)
l_charging = gtk.Label('Charging: ')
l_charging.set_justify(gtk.JUSTIFY_LEFT)
hbox_charging.pack_start(l_charging, False, False, 0)
self._label_charging = gtk.Label('No')
self._label_charging.set_justify(gtk.JUSTIFY_LEFT)
hbox_charging.pack_start(self._label_charging, False, False, 0)
"""
alignment = gtk.Alignment(0,0,0,0)
alignment.add(table)
hbox.pack_start(alignment, False, False, 0)
self.frame.add(hbox)
self.add(self.frame)
self.show_all()
def update_status(self):
new_charge = self._get_battery_status()
frame_label = str(self._battery_charge) + '%'
if new_charge != self._battery_charge:
self._battery_charge = self._get_battery_status()
self.label_charge_value.set_text(frame_label)
self._battery_box.set_capacity(self._battery_charge)
def _get_battery_status(self):
battery_class_path = '/sys/class/battery/psu_0/'
capacity_path = battery_class_path + 'capacity_percentage'
try:
f = open(capacity_path, 'r')
val = f.read().split('\n')
capacity = int(val[0])
f.close()
except:
capacity = 0
return capacity

View File

@ -23,7 +23,6 @@ import string
from cpu import XO_CPU
from system import XO_System
from battery import XO_Battery
from nandflash import XO_NandFlash
class Interface:
@ -40,11 +39,9 @@ class Interface:
self.vbox.pack_start(xo_cpu, False, False, 0)
# Graphics: Battery Status, NandFlash
self._xo_battery = XO_Battery()
self._xo_nandflash = XO_NandFlash()
hbox = gtk.HBox(False, 2)
hbox.pack_start(self._xo_battery, False, False, 0)
hbox.pack_start(self._xo_nandflash, False, False, 0)
self.vbox.pack_start(hbox, False, False, 0)
@ -54,7 +51,6 @@ class Interface:
gobject.timeout_add(5000, self._update_components)
def _update_components(self):
self._xo_battery.update_status()
self._xo_nandflash.update_status()
return True

View File

@ -36,7 +36,7 @@ class BuddyModel(gobject.GObject):
([gobject.TYPE_PYOBJECT]))
}
def __init__(self, key=None, buddy=None):
def __init__(self, key=None, buddy=None, nick=None):
if (key and buddy) or (not key and not buddy):
raise RuntimeError("Must specify only _one_ of key or buddy.")
@ -51,7 +51,6 @@ class BuddyModel(gobject.GObject):
self._pservice = presenceservice.get_instance()
self._buddy = None
self._nick = None
# If given just a key, try to get the buddy from the PS first
if not buddy:
@ -72,7 +71,7 @@ class BuddyModel(gobject.GObject):
self._key = key
# Set color to 'inactive'/'disconnected'
self._set_color_from_string(_NOT_PRESENT_COLOR)
self._name = "Unknown buddy"
self._nick = nick
def _set_color_from_string(self, color_string):
self._color = XoColor(color_string)

View File

@ -69,7 +69,7 @@ class Friends(gobject.GObject):
# HACK: don't screw up on old friends files
if len(key) < 20:
continue
buddy = BuddyModel(key=key)
buddy = BuddyModel(key=key, nick=cp.get(key, 'nick'))
self.add_friend(buddy)
except Exception, exc:
logging.error("Error parsing friends file: %s" % exc)

View File

@ -14,6 +14,8 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
import logging
import gobject
import dbus
@ -45,9 +47,30 @@ class Device(device.Device):
'org.freedesktop.Hal',
udi)
self._level = self._battery.GetProperty(_LEVEL_PROP)
self._charging = self._battery.GetProperty(_CHARGING_PROP)
self._discharging = self._battery.GetProperty(_DISCHARGING_PROP)
self._level = self._get_level()
self._charging = self._get_charging()
self._discharging = self._get_discharging()
def _get_level(self):
try:
return self._battery.GetProperty(_LEVEL_PROP)
except dbus.DBusException:
logging.error('Cannot access %s' % _LEVEL_PROP)
return 0
def _get_charging(self):
try:
return self._battery.GetProperty(_CHARGING_PROP)
except dbus.DBusException:
logging.error('Cannot access %s' % _CHARGING_PROP)
return False
def _get_discharging(self):
try:
return self._battery.GetProperty(_DISCHARGING_PROP)
except dbus.DBusException:
logging.error('Cannot access %s' % _DISCHARGING_PROP)
return False
def do_get_property(self, pspec):
if pspec.name == 'level':
@ -63,11 +86,11 @@ class Device(device.Device):
def _battery_changed(self, num_changes, changes_list):
for change in changes_list:
if change[0] == _LEVEL_PROP:
self._level = self._battery.GetProperty(_LEVEL_PROP)
self._level = self._get_level()
self.notify('level')
elif change[0] == _CHARGING_PROP:
self._charging = self._battery.GetProperty(_CHARGING_PROP)
self._charging = self._get_charging()
self.notify('charging')
elif change[0] == _DISCHARGING_PROP:
self._discharging = self._battery.GetProperty(_DISCHARGING_PROP)
self._discharging = self._get_discharging()
self.notify('discharging')

View File

@ -56,6 +56,9 @@ class ShellService(dbus.service.Object):
self._home_model.connect('active-activity-changed',
self._cur_activity_changed_cb)
bundle_registry = bundleregistry.get_registry()
bundle_registry.connect('bundle-added', self._bundle_added_cb)
bus = dbus.SessionBus()
bus_name = dbus.service.BusName(_DBUS_SERVICE, bus=bus)
dbus.service.Object.__init__(self, bus_name, _DBUS_PATH)
@ -121,6 +124,10 @@ class ShellService(dbus.service.Object):
return result
@dbus.service.signal(_DBUS_ACTIVITY_REGISTRY_IFACE, signature="a{sv}")
def ActivityAdded(self, activity_info):
pass
@dbus.service.signal(_DBUS_OWNER_IFACE, signature="s")
def ColorChanged(self, color):
pass
@ -158,3 +165,7 @@ class ShellService(dbus.service.Object):
'icon': bundle.get_icon(),
'service_name': bundle.get_service_name(),
'path': bundle.get_path()}
def _bundle_added_cb(self, bundle_registry, bundle):
self.ActivityAdded(self._bundle_to_dict(bundle))

View File

@ -8,6 +8,6 @@ sugar_PYTHON = \
FriendsBox.py \
eventarea.py \
frame.py \
ZoomBox.py \
overlaybox.py \
framewindow.py
framewindow.py \
zoombox.py

View File

@ -13,16 +13,14 @@
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
import shutil
import os
import logging
import urlparse
import hippo
import gtk
from sugar import util
from sugar.objects import mime
from view.clipboardicon import ClipboardIcon
from sugar.clipboard import clipboardservice
@ -101,21 +99,10 @@ class ClipboardBox(hippo.CanvasBox):
uris = selection.data.split('\n')
if len(uris) > 1:
raise NotImplementedError('Multiple uris in text/uri-list still not supported.')
uri = urlparse.urlparse(uris[0])
path, file_name = os.path.split(uri.path)
root, ext = os.path.splitext(file_name)
if not ext or ext == '.':
mime_type = mime.get_for_file(uri.path)
file_name = root + '.' + mime.get_primary_extension(mime_type)
# Copy the file, as it will be deleted when the dnd operation finishes.
new_file_path = os.path.join(path, 'cb' + file_name)
shutil.copyfile(uri.path, new_file_path)
cb_service.add_object_format(object_id,
selection.type,
"file://" + new_file_path,
uris[0],
on_disk=True)
else:
cb_service.add_object_format(object_id,

View File

@ -27,7 +27,7 @@ from sugar.clipboard import clipboardservice
from view.frame.eventarea import EventArea
from view.frame.ActivitiesBox import ActivitiesBox
from view.frame.ZoomBox import ZoomBox
from view.frame.zoombox import ZoomBox
from view.frame.overlaybox import OverlayBox
from view.frame.FriendsBox import FriendsBox
from view.frame.framewindow import FrameWindow

View File

@ -14,10 +14,14 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
from gettext import gettext as _
import hippo
from sugar.graphics import color
from sugar.graphics.palette import Palette
from sugar.graphics.iconbutton import IconButton
from frameinvoker import FrameCanvasInvoker
from model.shellmodel import ShellModel
@ -35,6 +39,11 @@ class ZoomBox(hippo.CanvasBox):
ShellModel.ZOOM_MESH)
self.append(icon)
palette = Palette(_('Neighborhood'))
palette.props.invoker = FrameCanvasInvoker(icon)
palette.set_group_id('frame')
icon.set_palette(palette)
icon = IconButton(icon_name='theme:stock-zoom-friends',
stroke_color=color.BLACK,
fill_color=color.WHITE)
@ -43,6 +52,11 @@ class ZoomBox(hippo.CanvasBox):
ShellModel.ZOOM_FRIENDS)
self.append(icon)
palette = Palette(_('Group'))
palette.props.invoker = FrameCanvasInvoker(icon)
palette.set_group_id('frame')
icon.set_palette(palette)
icon = IconButton(icon_name='theme:stock-zoom-home',
stroke_color=color.BLACK,
fill_color=color.WHITE)
@ -51,6 +65,11 @@ class ZoomBox(hippo.CanvasBox):
ShellModel.ZOOM_HOME)
self.append(icon)
palette = Palette(_('Home'))
palette.props.invoker = FrameCanvasInvoker(icon)
palette.set_group_id('frame')
icon.set_palette(palette)
icon = IconButton(icon_name='theme:stock-zoom-activity',
stroke_color=color.BLACK,
fill_color=color.WHITE)
@ -59,5 +78,10 @@ class ZoomBox(hippo.CanvasBox):
ShellModel.ZOOM_ACTIVITY)
self.append(icon)
palette = Palette(_('Activity'))
palette.props.invoker = FrameCanvasInvoker(icon)
palette.set_group_id('frame')
icon.set_palette(palette)
def _level_clicked_cb(self, item, level):
self._shell.set_zoom_level(level)

View File

@ -19,9 +19,12 @@ import random
import hippo
import gobject
from sugar import profile
from sugar.graphics.spreadlayout import SpreadLayout
from sugar.graphics import units
from view.home.MyIcon import MyIcon
from model.BuddyModel import BuddyModel
from view.BuddyIcon import BuddyIcon
from view.home.FriendView import FriendView
class FriendsBox(hippo.CanvasBox):
@ -35,8 +38,10 @@ class FriendsBox(hippo.CanvasBox):
self._layout = SpreadLayout()
self.set_layout(self._layout)
self._my_icon = MyIcon(units.LARGE_ICON_SCALE)
self._layout.add_center(self._my_icon)
buddy_model = BuddyModel(key=profile.get_pubkey())
self._owner_icon = BuddyIcon(shell, buddy_model)
self._owner_icon.props.scale = units.LARGE_ICON_SCALE
self._layout.add_center(self._owner_icon)
friends = self._shell.get_model().get_friends()

View File

@ -64,11 +64,11 @@ class ActivityToolbar(gtk.Toolbar):
self.insert(separator, -1)
separator.show()
self.save = ToolButton('document-save')
self.save.set_tooltip(_('Save'))
self.save.connect('clicked', self._save_clicked_cb)
self.insert(self.save, -1)
self.save.show()
self.keep = ToolButton('document-save')
self.keep.set_tooltip(_('Keep'))
self.keep.connect('clicked', self._keep_clicked_cb)
self.insert(self.keep, -1)
self.keep.show()
self.share = ToolButton('stock-share-mesh')
self.share.set_tooltip(_('Share'))
@ -83,21 +83,21 @@ class ActivityToolbar(gtk.Toolbar):
self.insert(separator, -1)
separator.show()
self.close = ToolButton('window-close')
self.close.set_tooltip(_('Close'))
self.close.connect('clicked', self._close_clicked_cb)
self.insert(self.close, -1)
self.close.show()
self.stop = ToolButton('activity-stop')
self.stop.set_tooltip(_('Stop'))
self.stop.connect('clicked', self._stop_clicked_cb)
self.insert(self.stop, -1)
self.stop.show()
self._update_title_sid = None
def _share_clicked_cb(self, button):
self._activity.share()
def _save_clicked_cb(self, button):
def _keep_clicked_cb(self, button):
self._activity.save()
def _close_clicked_cb(self, button):
def _stop_clicked_cb(self, button):
self._activity.close()
self._activity.destroy()

View File

@ -50,26 +50,22 @@ class _DefaultFileList(list):
self.append(os.path.join('activity', name))
self.append('activity/activity.info')
self.append('setup.py')
if os.path.isfile(_get_source_path('NEWS')):
self.append('NEWS')
class _ManifestFileList(list):
def __init__(self, manifest=None):
class _ManifestFileList(_DefaultFileList):
def __init__(self, manifest):
_DefaultFileList.__init__(self)
self.append(manifest)
f = open(manifest,'r')
for line in f.readlines():
stripped_line = line.strip()
if stripped_line:
if stripped_line and not stripped_line in self:
self.append(stripped_line)
f.close()
defaults = _DefaultFileList()
for path in defaults:
self.append(path)
def _extract_bundle(source_file, dest_dir):
if not os.path.exists(dest_dir):
os.mkdir(dest_dir)
@ -270,8 +266,8 @@ def cmd_release(bundle_name, manifest):
sugar_news += '%s - %d\n\n' % (bundle_name, version)
f = open(news_path,'r')
for line in f.readline():
if len(line) > 0:
for line in f.readlines():
if len(line.strip()) > 0:
sugar_news += line
else:
break

View File

@ -15,6 +15,8 @@
# Free Software Foundation, Inc., 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
import logging
import dbus
_SHELL_SERVICE = "org.laptop.Shell"
@ -39,6 +41,11 @@ class ActivityRegistry(object):
bus = dbus.SessionBus()
bus_object = bus.get_object(_SHELL_SERVICE, _SHELL_PATH)
self._registry = dbus.Interface(bus_object, _REGISTRY_IFACE)
self._registry.connect_to_signal('ActivityAdded', self._activity_added_cb)
# Two caches fo saving some travel across dbus.
self._service_name_to_activity_info = {}
self._mime_type_to_activities = {}
def _convert_info_list(self, info_list):
result = []
@ -49,16 +56,33 @@ class ActivityRegistry(object):
return result
def get_activity(self, service_name):
if self._service_name_to_activity_info.has_key(service_name):
return self._service_name_to_activity_info[service_name]
info_dict = self._registry.GetActivity(service_name)
return _activity_info_from_dict(info_dict)
activity_info = _activity_info_from_dict(info_dict)
self._service_name_to_activity_info[service_name] = activity_info
return activity_info
def find_activity(self, name):
info_list = self._registry.FindActivity(name)
return self._convert_info_list(info_list)
def get_activities_for_type(self, mime_type):
if self._mime_type_to_activities.has_key(mime_type):
return self._mime_type_to_activities[mime_type]
info_list = self._registry.GetActivitiesForType(mime_type)
return self._convert_info_list(info_list)
activities = self._convert_info_list(info_list)
self._mime_type_to_activities[mime_type] = activities
return activities
def _activity_added_cb(self, bundle):
logging.debug('ActivityRegistry._activity_added_cb: flushing caches')
self._service_name_to_activity_info.clear()
self._mime_type_to_activities.clear()
_registry = None

View File

@ -18,6 +18,10 @@
import gtk
import pango
def _get_screen_dpi():
xft_dpi = gtk.settings_get_default().get_property('gtk-xft-dpi')
return float(xft_dpi / 1024)
def _compute_zoom_factor():
return gtk.gdk.screen_width() / 1200.0
@ -43,17 +47,21 @@ class Font(object):
def get_pango_desc(self):
return pango.FontDescription(self._desc)
_XO_DPI = 200.0
_FOCUS_LINE_WIDTH = 2
_TAB_CURVATURE = 1
ZOOM_FACTOR = _compute_zoom_factor()
FONT_SIZE = _zoom(7 * 200 / 72.0)
FONT_SIZE = _zoom(7 * _XO_DPI / _get_screen_dpi())
FONT_NORMAL = Font('Bitstream Vera Sans %d' % FONT_SIZE)
FONT_BOLD = Font('Bitstream Vera Sans bold %d' % FONT_SIZE)
FONT_NORMAL_H = _compute_font_height(FONT_NORMAL)
FONT_BOLD_H = _compute_font_height(FONT_BOLD)
TOOLBOX_SEPARATOR_HEIGHT = _zoom(9)
TOOLBOX_HORIZONTAL_PADDING = _zoom(75)
TOOLBOX_TAB_VBORDER = int((_zoom(36) - FONT_SIZE - _FOCUS_LINE_WIDTH) / 2)
TOOLBOX_TAB_VBORDER = int((_zoom(36) - FONT_NORMAL_H - _FOCUS_LINE_WIDTH) / 2)
TOOLBOX_TAB_HBORDER = _zoom(15) - _FOCUS_LINE_WIDTH - _TAB_CURVATURE
TOOLBOX_TAB_LABEL_WIDTH = _zoom(150 - 15 * 2)

View File

@ -36,20 +36,39 @@ class ObjectType(object):
self.name = name
self.icon = icon
self.mime_types = mime_types
self._type_id_to_type = {}
self._mime_type_to_type = {}
class ObjectTypeRegistry(object):
def __init__(self):
bus = dbus.SessionBus()
bus_object = bus.get_object(_SERVICE, _PATH)
self._registry = dbus.Interface(bus_object, _IFACE)
# Two caches fo saving some travel across dbus.
self._type_id_to_type = {}
self._mime_type_to_type = {}
def get_type(self, type_id):
if self._type_id_to_type.has_key(type_id):
return self._type_id_to_type[type_id]
type_dict = self._registry.GetType(type_id)
return _object_type_from_dict(type_dict)
object_type = _object_type_from_dict(type_dict)
self._type_id_to_type[type_id] = object_type
return object_type
def get_type_for_mime(self, mime_type):
if self._mime_type_to_type.has_key(mime_type):
return self._mime_type_to_type[mime_type]
type_dict = self._registry.GetTypeForMIME(mime_type)
return _object_type_from_dict(type_dict)
object_type = _object_type_from_dict(type_dict)
self._mime_type_to_type[mime_type] = object_type
return object_type
_registry = None