Re: window list snapshot?



* Daniel M German <dmg uvic ca> wrote:
> I would recommend dumpina all info in every line. Then you can 
> sort by using the sort command. No need for more lisp.

Yeah, that's a good idea.  I've changed it to do this.

And my python wrapper for it has grown less trivial, so I'm 
attaching it too.  The code for both is messy, but it works.  The 
output is something like this:

2008-07-22 14:27:54
147 windows, 17 active desktops (8.65 per)
...
(1,2) (10 windows)
	(5 windows)	(1177x380+0+14)
		Dillo: 
		Dillo: Forer effect - Wikipedia, the free encyclopedia
		Dillo: Search results for horrible - Mininova
		XChat: ToyKeeper @ DircFreenode / #sawfish
		btclient.sh
	chi : ~/ [scott]	(484x316+698+136)
	(2 windows)	(544x368+148+416)
		umutt 
		umutt 
	(2 windows)	(484x316+699+468)
		newmail | less
		silc
...



-- Scott
#!/bin/sh
exec rep "$0" "$@"
!#

; TODO: sort windows by position and stacking order

(require 'sawfish.client)

(define (exit n) (throw 'quit n))

(defun print-windows (windows ws-name)
  (mapcar (lambda (w) (apply print-window ws-name w)) windows))

(defun print-window (ws-name name wid hgt x y)
  (format standard-output "%s\t%s\t(%sx%s+%s+%s)\n" ws-name name wid hgt x y))

(defun dump-windows (windows)
  (mapcar dump-window windows))

(defun dump-window (w)
  (let* (
         (name (sawfish-client-eval 
                 `(window-full-name (get-window-by-id ',w))))
         (size (sawfish-client-eval 
                 `(window-dimensions (get-window-by-id ',w))))
         (wid (car size))
         (hgt (cdr size))
         (pos (sawfish-client-eval 
                 `(window-position (get-window-by-id ',w))))
         (x (car pos))
         (y (cdr pos))
         )
    (list name wid hgt x y)
    )
  )

(defun dump-workspace (ws)
  (let* (
         (per-column (sawfish-client-eval `pager-workspaces-per-column))
         (x (1+ (quotient ws per-column)))
         (y (1+ (remainder ws per-column)))
         (ws-name (format nil "(%s,%s)" x y))
         (windows (dump-windows (sawfish-client-eval `(mapcar window-id (workspace-windows ',ws))) ))
         )
    (print-windows windows ws-name)
    )
  )

(defun dump-workspaces (workspaces)
  (mapcar dump-workspace workspaces))

(defun dump-all-windows ()
  (dump-workspaces (sort (sawfish-client-eval `(all-workspaces)))))

(dump-all-windows)
(exit 0)
#!/usr/bin/env python

"""Keep a current list of open windows in a file.
"""

import os
outfile = "~/.open/open.otl"
jl_path = '%s/.sawfish/bin/list-all-windows.jl' % (os.environ["HOME"])
delay = 30
repl = ( # rewrite some window titles...  fill this in yourself
        (r' search', 'replace'),
        (r'Mozilla Firefox', 'Firefox'),
        )

def main(args):
    import os
    import re
    import time
    reps = [(re.compile(s), r) for s,r in repl]
    ws_re = re.compile('\((\d+),(\d+)\)')
    geom_re = re.compile('(\d+)x(\d+)\+(-?\d+)\+(-?\d+)')

    global outfile
    outfile = outfile.replace('~', os.environ['HOME'])

    oldlines = []
    while 1:
        lines = os.popen(jl_path).readlines()
        if lines != oldlines:
            desktops = {}
            # parse data into a more usable structure
            for line in lines:
                line = line.rstrip()
                parts = line.split('\t')
                ws, title, geom = parts[0], " ".join(parts[1:-1]), parts[-1]
                # x y
                ws = tuple([int(x) for x in ws_re.search(ws).groups()])
                for s,r in reps:
                    title = s.sub(r, title)
                # w h x y
                geom = tuple([int(x) for x in geom_re.search(geom).groups()])
                if ws not in desktops: desktops[ws] = []
                desktops[ws].append((title, geom))

            # detect tab groups
            for ws, windows in desktops.items():
                tmp = [(w[1][3], w[1][2], w[0], w) for w in windows]
                tmp.sort()
                windows = [x[-1] for x in tmp]
                prev_geom = ()
                groups = []
                for title, geom in windows:
                    if geom != prev_geom:
                        groups.append([])
                        prev_geom = geom
                    groups[-1].append((title, geom))
                desktops[ws] = groups

            # build our output text
            out = []
            out.append(time.strftime("%Y-%m-%d %H:%M:%S"))
            num_windows, num_desktops = (len(lines), len(desktops))
            avg_per = float(num_windows) / num_desktops
            out.append("%s windows, %s active desktops (%.2f per)" % \
                    (num_windows, num_desktops, avg_per))
            keys = desktops.keys()
            keys.sort()
            for ws in keys:
                groups = desktops[ws]
                ws_windows = sum([len(g) for g in groups])
                out.append('(%s,%s) (%s windows)' % (ws[0], ws[1], ws_windows))
                for group in groups:
                    geom = group[0][1]
                    geom_text = '(%sx%s+%s+%s)' % geom
                    if len(group) == 1:
                        title = group[0][0]
                        out.append('\t%s\t%s' % (title, geom_text))
                    else:
                        out.append('\t(%s windows)\t%s' % (len(group), geom_text))
                        for title, geom in group:
                            out.append('\t\t%s' % (title))
            write_out(out)

        oldlines = lines
        time.sleep(delay)

def write_out(lines):
    text = '\n'.join(lines)
    rotate()
    fp = open(outfile, 'wb')
    fp.write(text)
    fp.write('\n')
    fp.close()

def rotate():
    import os
    base = os.path.basename(outfile)
    rotated = '%s/.open/%s' % (os.environ['HOME'], base)
    for n in range(9,0,-1):
        path1 = '%s.%s' % (rotated, n-1)
        path2 = '%s.%s' % (rotated, n)
        if os.path.exists(path1):
            os.rename(path1, path2)
    if os.path.exists(outfile):
        os.rename(outfile, path1)

if __name__ == "__main__":
    import sys
    main(sys.argv[1:])



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]