summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFrederic Back <fredericback@gmail.com>2006-09-27 17:19:35 +0000
committerFrederic Back <fredericback@gmail.com>2006-09-27 17:19:35 +0000
commite39436576c68e70ac70d4ee108860d411b52d0bb (patch)
treee9b63c2e8374b99639694d67afd3349041cb893a
parent5bcf37b8944759e09fe45c341a555757b53a6e20 (diff)
* added gnomevfs support
* added menu entry to choose walking method * merged back from trunk * UI now uses gnomevfs everywhere git-svn-id: file:///home/lennart/svn/public/fring/branches/c_walker@33 d0d2c35f-0a1e-0410-abeb-dabff30a67ee
-rw-r--r--src/fringlib/fringrenderer.py51
-rw-r--r--src/fringlib/fringui.py50
-rw-r--r--src/fringlib/fringutil.py12
-rw-r--r--src/fringlib/fringwalker.py109
-rwxr-xr-xsrc/fringlib/launch.py7
5 files changed, 175 insertions, 54 deletions
diff --git a/src/fringlib/fringrenderer.py b/src/fringlib/fringrenderer.py
index f69a0a2..0f71f8a 100644
--- a/src/fringlib/fringrenderer.py
+++ b/src/fringlib/fringrenderer.py
@@ -1,10 +1,8 @@
import cairo
import pango
from math import *
-#from fringwalker import sum_list
from fringutil import *
import os
-from fringwalker import print_tree
class Hotspot:
@@ -55,8 +53,8 @@ class FringRenderer:
if data is None: return
dataname = data[0]
- datadata = data[1]
- datathe_sum = data[2]
+ datacontents = data[1]
+ datasize = data[2]
if ring == 0:
self.lookup_data = []
@@ -68,27 +66,24 @@ class FringRenderer:
CENTERX, CENTERY = self.WIDTH/2, self.HEIGHT/2
ctx.move_to(CENTERX, CENTERY)
- if ring == 0:
- self._draw_centered_text(ctx, pretty_size(datathe_sum))
-
- n = len(datadata)
+ n = len(datacontents)
i = 0
accumulated = 0
last = start_angle
- if datadata is None: return
- for fn, contents, d in datadata:
+ if datacontents is None: return
+ for fn, contents, d in datacontents:
+
if contents == None: hasContents = False
else: hasContents = True
start = last
-
value = d # third tuple element now *always* contains the size
-
accumulated += value
-
- end = start_angle+(end_angle - start_angle)*1.0*accumulated/datathe_sum
+
+ if datasize == 0: continue
+ end = start_angle+(end_angle - start_angle)*1.0*accumulated/datasize
if end-start >= .01:
@@ -159,17 +154,27 @@ class FringRenderer:
width *= -1
self.__register_side_link(hasContents,p,value,end-start,x,y+(height/2),x+(width),y-(height/2))
-
- if ring <= self.LABEL_UNTIL_RING:
+
+ # write disk usage on segments
+ if self.RING_RADIUS >= ctx.text_extents("55%")[3]:
ctx.move_to(*middle)
ctx.set_source_rgb(0, 0, 0)
+ percent = (end-start)*100
+ if percent >= 8:
+ #self._draw_centered_text2(ctx, "%.0f%%" % ((end-start)*100), pretty_size(value))
+ self._draw_centered_text(ctx, "%.0f%%" %percent)
- # write relative and absolute disk usage
- self._draw_centered_text2(ctx, "%.0f%%" % ((end-start)*100), pretty_size(value))
-
last = end
i += 1
+ if ring == 0:
+ ctx.set_source_rgb(.3,.3,.3)
+ i = format_disk_space(datasize)
+ ctx.move_to(CENTERX, CENTERY)
+ width,height = self._draw_centered_text(ctx, i[0], .5, 1 )
+ ctx.move_to(CENTERX, CENTERY+height)
+ self._draw_centered_text(ctx, i[1], .5, 1 )
+
def get_hotspot_at(self,x,y):
for h in self.side_links:
if x >= h.minx and x <= h.maxx and \
@@ -202,7 +207,9 @@ class FringRenderer:
p = int(maxidx*v) # Initial estimation
while True:
- d = data[p]
+
+ try: d = data[p]
+ except IndexError: return None
if v <= d.start:
maxidx = p-1
@@ -244,10 +251,6 @@ class FringRenderer:
(t,p,v),
(v,p,q))[int(h)]
- def _list_value(self,l):
- if isinstance(l, sum_list):
- return l.the_sum
- return l
def _choose_color(self,v, ring):
color = self.hsv2rgb(v, .61, 1-ring*0.1)
diff --git a/src/fringlib/fringui.py b/src/fringlib/fringui.py
index 5236af6..ffe624c 100644
--- a/src/fringlib/fringui.py
+++ b/src/fringlib/fringui.py
@@ -3,7 +3,7 @@ import cairo
import sys
import os
-from fringwalker import FringWalker
+from fringwalker import *
from fringrenderer import FringRenderer
from fringutil import *
@@ -37,6 +37,14 @@ ui = """
<separator />
<menuitem action="Quit"/>
</menu>
+
+ <menu action="TreeWalker">
+ <menuitem action="Python"/>
+ <menuitem action="Python gnomevfs"/>
+ <menuitem action="c++"/>
+ </menu>
+
+
<menu action="View">
<menuitem action="Show Hidden Files"/>
<separator />
@@ -56,7 +64,7 @@ ui = """
class UI( gtk.Window ):
- def __init__(self, path):
+ def __init__(self, uri):
self.busy_cursor = 0
self.backgroundColour = (1,1,1)
self.data = None
@@ -67,14 +75,15 @@ class UI( gtk.Window ):
# create gui
gtk.Window.__init__(self)
self.set_title("fring");
- self.__init_gui(path)
+ self.__init_gui()
# walk directory
self.walker.connect("list-changed",self.__list_changed)
self.walker.connect("finished", self.__walker_finished)
- self.open_folder(path)
+ self.walker.connect("manually-stopped", lambda w: self.__show_busy_cursor(-1))
+ self.open_folder(uri)
- def __init_gui(self, path):
+ def __init_gui(self):
# create menubar
uimanager = gtk.UIManager()
@@ -82,6 +91,7 @@ class UI( gtk.Window ):
self.add_accel_group(accelgroup)
ag_global = gtk.ActionGroup('ag_global')
ag_global.add_actions([
+ ('TreeWalker', None, "TreeWalker"),
('FRing', None, "_Folder"),
('View', None, "_View"),
('Help', None, "_Help"),
@@ -95,8 +105,18 @@ class UI( gtk.Window ):
('About', gtk.STOCK_ABOUT, "_About", None, "About", self.about_dialog),
])
action = gtk.ToggleAction("Show Hidden Files", "Show Hidden Files", None, None)
+ action.set_active(True)
action.connect("toggled",self.__hidden_files_toggled)
ag_global.add_action(action)
+
+ # add a menu with radio buttons to choose the walking method
+ ag_global.add_radio_actions([
+ ('Python', None, "Python", None, None, WALKER_CLASSIC),
+ ('Python gnomevfs', None, "Python gnomevfs", None, None, WALKER_GNOMEVFS),
+ ('c++', None, "c++", None, None, WALKER_CPP),
+ ], 0)
+ self.methodaction = ag_global.get_action("c++")
+
uimanager.insert_action_group(ag_global, 0)
uimanager.add_ui_from_string(ui)
menubar = uimanager.get_widget('/MenuBar')
@@ -113,7 +133,8 @@ class UI( gtk.Window ):
b = gtk.FileChooserButton('Select a Folder')
b.set_action(gtk.FILE_CHOOSER_ACTION_SELECT_FOLDER)
- b.connect("current-folder-changed", lambda w: self.__set_path(w.get_current_folder()))
+
+ b.connect("current-folder-changed", lambda w: self.__set_path(w.get_uri()))
toolbar.pack_start( b, True )
self.filechooserbutton = b
@@ -155,12 +176,9 @@ class UI( gtk.Window ):
self.eventbox.connect("size-allocate",self.__on_resize)
self.connect("delete_event", self.close)
-
-
- def open_folder(self,path):
- print "open",path
+ def open_folder(self,uri):
# change folder by changing the chooser button
- self.filechooserbutton.set_current_folder(path)
+ self.filechooserbutton.set_current_folder_uri(uri)
def about_dialog(self,widget):
d = gtk.AboutDialog()
@@ -197,15 +215,11 @@ class UI( gtk.Window ):
if not self.data: return
self.renderer.WIDTH = self.width
self.renderer.HEIGHT = self.height
- self.renderer.INNER_RADIUS = self.height/15
+ self.renderer.INNER_RADIUS = self.height/12
self.renderer.RING_RADIUS = self.height/10
#self.renderer.INNER_RADIUS *= self.zoomfactor
self.renderer.RING_RADIUS *= self.zoomfactor
self.renderer.RINGS_MAX = 3
-
- self.renderer.LABEL_UNTIL_RING = int(self.zoomfactor - 0.4)
- if self.zoomfactor < 0.8: self.renderer.LABEL_UNTIL_RING = -1
-
self.renderer.draw_segment(self.ctx, 0, 0, 1, 0, 1, self.data, self.path)
self.image.queue_draw()
self.__show_busy_cursor(-1)
@@ -234,7 +248,7 @@ class UI( gtk.Window ):
self.path = path
self.walker.stop()
if path is None: return
- self.walker.walk(path);
+ self.walker.walk(path,self.methodaction.get_current_value())
self.__show_busy_cursor(1)
def __selectfolder(self,widget):
@@ -242,7 +256,7 @@ class UI( gtk.Window ):
d = gtk.FileChooserDialog(None, self,
gtk.FILE_CHOOSER_ACTION_SELECT_FOLDER,
(gtk.STOCK_CANCEL,0,gtk.STOCK_OK,1))
- if d.run() == 1: self.open_folder(d.get_current_folder())
+ if d.run() == 1: self.open_folder(d.get_uri())
d.destroy()
def __hidden_files_toggled(self,widget):
diff --git a/src/fringlib/fringutil.py b/src/fringlib/fringutil.py
index e174d66..4bfa5d7 100644
--- a/src/fringlib/fringutil.py
+++ b/src/fringlib/fringutil.py
@@ -10,3 +10,15 @@ def pretty_size(size):
return "%u B" % size
+def format_disk_space(size):
+ """ Convert bytes to a human readable format.
+ Returns a tuple, for example (20,"MiB") """
+
+ if size >= 1024*1024*1024:
+ return ("%.1f"%round(size/1024/1024/1024.0),"GiB")
+ elif size >= 1024*1024:
+ return ("%.1f"%round(size/1024/1024.0),"MiB")
+ elif size >= 1024:
+ return ("%.1f"%round(size/1024.0),"KiB")
+ else:
+ return ("%u"%size,"B")
diff --git a/src/fringlib/fringwalker.py b/src/fringlib/fringwalker.py
index 99eaeff..364b997 100644
--- a/src/fringlib/fringwalker.py
+++ b/src/fringlib/fringwalker.py
@@ -1,12 +1,21 @@
import os, os.path, stat, sys
-import gobject, gtk
-from threading import Thread
+import threading
+import posixpath # instead of os.path for gnomevfs operations
import time
+
+import gobject, gtk
+from gnomevfs import *
+
import fringtools
+WALKER_CLASSIC = 0
+WALKER_GNOMEVFS = 1
+WALKER_CPP = 2
+
def print_tree( treearray, tab=0 ):
""" An utility function to print out a tree array """
+
fn, data, size = treearray
print " "*tab,"%s (%i)"%(fn,size)
if not data: return
@@ -55,13 +64,17 @@ class FringWalker( gobject.GObject ):
self.thread = None
self.showhidden = False
- def walk(self,path):
+ def walk(self,uri,method=WALKER_GNOMEVFS):
self.stop()
- self.thread = WalkThread(self,path,self.showhidden)
+
+ print "walkwalk",uri
+
+ self.thread = WalkThread(self,uri,self.showhidden,method)
self.thread.start()
def stop(self):
if self.thread:
+ self.emit("manually-stopped")
self.thread.stopsignal = True
self.thread = None
@@ -78,23 +91,90 @@ class FringWalker( gobject.GObject ):
gtk.gdk.threads_enter()
self.emit("finished", r)
gtk.gdk.threads_leave()
+ self.thread = None
-class WalkThread( Thread ):
+class WalkThread( threading.Thread ):
""" A separate class for the thread. """
- def __init__(self, master, path, showhidden):
+
+ def __init__(self, master, uri, showhidden, method=WALKER_CLASSIC):
""" Parameters: A FringWalker instance, a string with the path and a bool """
- Thread.__init__(self)
+ threading.Thread.__init__(self)
self.stopsignal = False
self.master = master
- self.path = path
+ self.uri = uri
self.showhidden = showhidden
+ self.method = method
+
+ print "open",uri
+ self.path = get_local_path_from_uri( str(uri) )
+ print "local",self.path
+
+
+ def build_tree_python(self, path, showhidden):
+ l = []
+ total = 0
+ for fn in os.listdir(path):
+ if self.stopsignal: return (None,None,0)
+ if not showhidden and fn[0] == ".": continue
+ try: p = os.path.join(path, fn)
+ except: continue
+ s = os.lstat(p)
+ if stat.S_ISDIR(s.st_mode):
+ sub = self.build_tree_python(p,showhidden)
+ l.append( sub )
+ total += sub[2]
+ elif stat.S_ISREG(s.st_mode):
+ l.append( (fn, None, s.st_size) )
+ total += s.st_size
+ return (os.path.split(path)[-1], l, total)
+
+ def __uri_tail(self, uri):
+ """ Return the filename in a gnomevfs uri """
+ f = format_uri_for_display(str(uri))
+ f = posixpath.split( f )[-1]
+ return f
+
+ def build_tree_gnomevfs(self, uri, showhidden):
+
+ try: h = DirectoryHandle(uri)
+ except InvalidURIError:
+ print uri,"is not a valid uri, skipped"
+ return (str(uri), None, 0)
+ except NotFoundError:
+ print uri,"not found, skipped"
+ return (str(uri), None, 0)
+
+ l = []
+ total = 0
+ d = h.next()
+ try:
+ while True:
+ if self.stopsignal: return (None,None,0)
+ d = h.next()
+ if not showhidden and d.name[0] == ".": continue
+
+ if d.type == 2: # directory
+ sub = self.build_tree_gnomevfs(uri.append_path(d.name),showhidden)
+ l.append( sub )
+ total += sub[2]
+ else:
+ l.append( (d.name, None, d.size) )
+ total += d.size
+
+ except StopIteration: pass
+ return (self.__uri_tail(uri), l, total)
+
def run(self):
""" Parse the root directory """
- print "start walking",self.path
+ starttime = time.time()
+ print "start walking",self.path,
+ if self.method == WALKER_CPP: print "(using c++ extension)"
+ elif self.method == WALKER_GNOMEVFS: print "(using python and gnomevfs)"
+ else: print "(using classic python)"
l = []
i = 0
@@ -136,7 +216,13 @@ class WalkThread( Thread ):
for fn, p in subdirectories:
c += 1
- sub = fringtools.build_tree(p, self.showhidden)
+ if self.method == WALKER_CPP:
+ sub = fringtools.build_tree(p, self.showhidden)
+ elif self.method == WALKER_GNOMEVFS:
+ sub = self.build_tree_gnomevfs(URI("file://"+p), self.showhidden)
+ else:
+ sub = self.build_tree_python(p, self.showhidden)
+
if self.stopsignal: return None
total += sub[2]
@@ -154,4 +240,5 @@ class WalkThread( Thread ):
# emit final signal
self.master._finished_fn(self,(os.path.split(self.path)[-1], l, total))
- print "finished walking",self.path
+ print "finished walking",self.path,"(time=%s)"%round(time.time()-starttime,2)
+
diff --git a/src/fringlib/launch.py b/src/fringlib/launch.py
index 8e3b107..f420768 100755
--- a/src/fringlib/launch.py
+++ b/src/fringlib/launch.py
@@ -17,11 +17,12 @@
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
# USA.
-# Copyright Lennart Poettering, 2006
+# Copyright Lennart Poettering, Frederic Back 2006
import sys, os
import gtk
import fringui
+import gnomevfs
if __name__ == "__main__":
@@ -30,6 +31,10 @@ if __name__ == "__main__":
else:
tree_path = os.path.expanduser("~")
+ # first parameter can be a gnomevfs uri or a local path
+ #try: uri = URI(tree_path)
+ #except: uri = get_uri_from_local_path(tree_path)
+
ui = fringui.UI(tree_path)
gtk.gdk.threads_init()