commit 35b69241970185b21bffa31d955d08cbd79a63ea
parent 533b07a1e498b1f6a045b1bcfa4e9dc48964a284
Author: Suraj N. Kurapati <sunaku@gmail.com>
Date: Thu, 26 Apr 2007 11:39:30 -0700
incorporate John-Galt's and borior's mini DSL for easier config
Diffstat:
wmiirc | | | 1 | + |
wmiirc-config.rb | | | 924 | ++++++++++++++++++++++++++++++++++++++++--------------------------------------- |
2 files changed, 469 insertions(+), 456 deletions(-)
diff --git a/wmiirc b/wmiirc
@@ -23,6 +23,7 @@ class << LOG
alias write <<
end
+
LOG.info "birth"
# terminate existing instances of this program
diff --git a/wmiirc-config.rb b/wmiirc-config.rb
@@ -3,153 +3,241 @@
# Copyright 2006-2007 Suraj N. Kurapati
# See the file named LICENSE for details.
+
+# load the wmii-irb library
$: << File.join(File.dirname(__FILE__), 'wmii-irb')
require 'wm'
include Wmii
+
+################################################################################
+# Miniature DSL to ease configuration.
+# Adapted from Kris Maglione and borior.
+################################################################################
+
+class HandlerHash < Hash
+ def handle aKey, *aArgs, &aBlock
+ if block_given?
+ self[aKey] = aBlock
+ elsif key? aKey
+ self[aKey].call(*aArgs)
+ end
+ end
+end
+
+EVENTS = HandlerHash.new
+ACTIONS = HandlerHash.new
+SHORTCUTS = HandlerHash.new
+
+def event *a, &b
+ EVENTS.handle(*a, &b)
+end
+
+def action *a, &b
+ ACTIONS.handle(*a, &b)
+end
+
+def shortcut *a, &b
+ SHORTCUTS.handle(*a, &b)
+end
+
+
+################################################################################
+# Utility functions
+################################################################################
+
+# Shows a menu with the given items and returns the chosen item.
+# If nothing was chosen, then *nil* is returned.
+def show_menu aChoices, aPrompt = nil
+ cmd = "dmenu -b -fn #{WMII_FONT.inspect} " <<
+ %w[-nf -nb -sf -sb].zip(
+ Color::NORMAL.split[0,2] + Color::FOCUSED.split[0,2]
+ ).flatten!.map! {|s| s.inspect}.join(' ')
+
+ cmd << " -p #{aPrompt.to_s.inspect}" if aPrompt
+
+ IO.popen cmd, 'r+' do |menu|
+ menu.puts aChoices
+ menu.close_write
+
+ choice = menu.read
+ choice unless choice.empty?
+ end
+end
+
+
require 'find'
+# Returns the names of programs present in the given directories.
+def find_programs aDirs
+ aDirs = aDirs.map {|p| File.expand_path p}
+ names = []
-############################################################################
-# CONFIGURATION VARIABLES
-############################################################################
-
-MODKEY = 'Mod1'
-UP_KEY = 't'
-DOWN_KEY = 'n'
-LEFT_KEY = 'h'
-RIGHT_KEY = 's'
-
-MOD_PREFIX = MODKEY + '-Control-'
-MOD_FOCUS = MOD_PREFIX
-MOD_SEND = MOD_PREFIX + 'm,'
-MOD_SWAP = MOD_PREFIX + 'w,'
-MOD_ARRANGE = MOD_PREFIX + 'z,'
-MOD_GROUP = MOD_PREFIX + 'g,'
-MOD_MENU = MOD_PREFIX
-MOD_EXEC = MOD_PREFIX
-
-PRIMARY_CLICK = 1
-MIDDLE_CLICK = 2
-SECONDARY_CLICK = 3
-
-# Tag used for wmii-2 style client detaching.
-DETACHED_TAG = '|'
-
-# Colors tuples are "<text> <background> <border>"
-WMII_NORMCOLORS = '#e0e0e0 #0a0a0a #202020'
-WMII_FOCUSCOLORS = '#ffffff #285577 #4c7899'
-WMII_BACKGROUND = '#333333'
-WMII_FONT = '-*-fixed-medium-r-normal-*-18-*-*-*-*-*-*-*'
-
-WMII_MENU = "dmenu -b -fn #{WMII_FONT.inspect} #{
- %w[-nf -nb -sf -sb].zip(
- WMII_NORMCOLORS.split[0,2] +
- WMII_FOCUSCOLORS.split[0,2]
- ).flatten!.map! {|s| s.inspect}.join(' ')
- }"
-WMII_TERM = 'gnome-terminal'
-
-# export WMII_* constants as environment variables
- k = self.class
- k.constants.grep(/^WMII_/).each do |c|
- ENV[c] = k.const_get c
+ Find.find(*aDirs) do |f|
+ if File.file? f and File.executable? f
+ names << File.basename(f)
+ end
end
+ names.uniq!
+ names.sort!
+ names
+end
+
-############################################################################
-# WM CONFIGURATION
-############################################################################
+################################################################################
+# GENERAL CONFIGURATION
+################################################################################
+
+module Key
+ MOD = 'Mod1'
+ UP = 't'
+ DOWN = 'n'
+ LEFT = 'h'
+ RIGHT = 's'
+
+ PREFIX = MOD + '-Control-'
+ FOCUS = PREFIX
+ SEND = PREFIX + 'm,'
+ SWAP = PREFIX + 'w,'
+ ARRANGE = PREFIX + 'z,'
+ GROUP = PREFIX + 'g,'
+ VIEW = PREFIX + 'v,'
+ MENU = PREFIX
+ EXECUTE = PREFIX
+end
+
+module Mouse
+ FIRST_CLICK = 1
+ MIDDLE_CLICK = 2
+ SECOND_CLICK = 3
+ SCROLL_UP = 4
+ SCROLL_DOWN = 5
+end
+module Color
+ { # Color tuples are "<text> <background> <border>"
+ :NORMCOLORS => NORMAL = '#e0e0e0 #0a0a0a #202020',
+ :FOCUSCOLORS => FOCUSED = '#ffffff #285577 #4c7899',
+ :BACKGROUND => BACKGROUND = '#333333',
+ }.each_pair do |k, v|
+ ENV["WMII_#{k}"] = v
+ end
+end
+
+WMII_FONT = '*-fixed-medium-r-normal-*-18-*-*-*-*-*-*-*'
+
+
+################################################################################
+# DETAILED CONFIGURATION
+################################################################################
+
+# WM Configuration
fs.ctl = <<EOF
+grabmod #{Key::MOD}
+border 2
font #{WMII_FONT}
-focuscolors #{WMII_FOCUSCOLORS}
-normcolors #{WMII_NORMCOLORS}
-grabmod #{MODKEY}
-border 1
+focuscolors #{Color::FOCUSED}
+normcolors #{Color::NORMAL}
EOF
-
-############################################################################
-# COLUMN RULES
-############################################################################
-
+# Column Rules
fs.colrules = <<EOF
-/.*/ -> 58+42
+/./ -> 60+40
EOF
-
-############################################################################
-# TAGGING RULES
-############################################################################
-
+# Tagging Rules
fs.tagrules = <<EOF
/Buddy List.*/ -> chat
/XChat.*/ -> chat
/.*thunderbird.*/ -> mail
+/Gimp.*/ -> gimp
/xconsole.*/ -> ~
/alsamixer.*/ -> ~
/QEMU.*/ -> ~
/XMMS.*/ -> ~
-/Gimp.*/ -> gimp
/MPlayer.*/ -> ~
/.*/ -> !
/.*/ -> 1
EOF
-############################################################################
-# FUNCTIONS
-############################################################################
+# Events
-# Shows a menu with the given items and returns the chosen item.
-# If nothing was chosen, then *nil* is returned.
-def show_menu aChoices, aPrompt = nil
- cmd = WMII_MENU
- cmd += ' -p ' << aPrompt.to_s.inspect if aPrompt
+ event :Start do |arg|
+ exit if arg == 'wmiirc'
+ end
- IO.popen cmd, 'r+' do |menu|
- menu.puts aChoices
- menu.close_write
+ event :Key do |*args|
+ shortcut(*args)
+ end
- choice = menu.read
- choice unless choice.empty?
+ event :CreateTag do |tag|
+ bar = fs.lbar[tag]
+ bar.create
+ bar.write "#{Color::NORMAL} #{tag}"
end
-end
-# Returns the names of programs present in the given directories.
-def find_programs *aPaths
- aPaths.flatten!
- aPaths.map! {|p| File.expand_path p}
- list = []
+ event :DestroyTag do |tag|
+ fs.lbar[tag].remove
+ end
- Find.find(*aPaths) do |f|
- if File.file? f and File.executable? f
- list << File.basename(f)
+ event :FocusTag do |tag|
+ fs.lbar[tag] << "#{Color::FOCUSED} #{tag}"
+ end
+
+ event :UnfocusTag do |tag|
+ fs.lbar[tag] << "#{Color::NORMAL} #{tag}"
+ end
+
+ event :UrgentTag do |tag|
+ fs.lbar[tag] << "*#{tag}"
+ end
+
+ event :NotUrgentTag do |tag|
+ fs.lbar[tag] << tag
+ end
+
+ event :LeftBarClick do |button, viewId|
+ case button.to_i
+ when Mouse::FIRST_CLICK
+ focus_view viewId
+
+ when Mouse::MIDDLE_CLICK
+ # add the grouping onto the clicked view
+ grouped_clients.each do |c|
+ c.tag viewId
+ end
+
+ when Mouse::SECOND_CLICK
+ # remove the grouping from the clicked view
+ grouped_clients.each do |c|
+ c.untag viewId
+ end
end
end
- list.uniq!
- list.sort!
- list
-end
+ event :ClientClick do |clientId, button|
+ case button.to_i
+ when Mouse::SECOND_CLICK
+ # toggle the clicked client's grouping
+ Client.toggle_grouping clientId
+ end
+ end
-############################################################################
-# INTERNAL ACTIONS
-############################################################################
+# Actions
-ACTIONS = {
- :rehash => lambda do
- @programMenu = find_programs(ENV['PATH'].squeeze(':').split(':'))
- @actionMenu = find_programs(File.dirname(__FILE__))
- end,
+ action :rehash do
+ @programMenu = find_programs ENV['PATH'].squeeze(':').split(':')
+ @actionMenu = find_programs File.dirname(__FILE__)
+ end
- :quit => lambda do
+ action :quit do
Wmii.fs.ctl = 'quit'
- end,
+ end
- :status => lambda do
+ action :status do
if defined? @status
@status.kill
end
@@ -164,7 +252,7 @@ ACTIONS = {
5.times do
bar.write [
- WMII_NORMCOLORS,
+ Color::NORMAL,
Time.now,
cpuLoad,
diskSpace,
@@ -174,220 +262,164 @@ ACTIONS = {
end
end
end
- end,
-}
-
-ACTIONS[:rehash].call
-ACTIONS[:status].call
-
-
-############################################################################
-# KEY BINDINGS
-############################################################################
-
-SHORTCUTS = {
-
- ##########################################################################
- ## focusing / showing
- ##########################################################################
-
- # focus client at left
- MOD_FOCUS + LEFT_KEY => lambda do
- current_view.ctl = 'select left'
- end,
-
- # focus client at right
- MOD_FOCUS + RIGHT_KEY => lambda do
- current_view.ctl = 'select right'
- end,
+ end
- # focus client below
- MOD_FOCUS + DOWN_KEY => lambda do
- current_view.ctl = 'select down'
- end,
- # focus client above
- MOD_FOCUS + UP_KEY => lambda do
- current_view.ctl = 'select up'
- end,
+# Shortcuts
- # toggle focus between floating area and the columns
- MOD_FOCUS + 'space' => lambda do
- current_view.ctl = 'select toggle'
- end,
+ # focusing / showing
- # apply equal-spacing layout to current column
- MOD_ARRANGE + 'w' => lambda do
- if a = current_area
- a.layout = :default
+ # focus client at left
+ shortcut Key::FOCUS + Key::LEFT do
+ current_view.ctl = 'select left'
end
- end,
- # apply equal-spacing layout to all columns
- MOD_ARRANGE + 'Shift-w' => lambda do
- current_view.columns.each do |a|
- a.layout = :default
+ # focus client at right
+ shortcut Key::FOCUS + Key::RIGHT do
+ current_view.ctl = 'select right'
end
- end,
- # apply stacked layout to currently focused column
- MOD_ARRANGE + 'v' => lambda do
- if a = current_area
- a.layout = :stack
+ # focus client below
+ shortcut Key::FOCUS + Key::DOWN do
+ current_view.ctl = 'select down'
end
- end,
- # apply stacked layout to all columns in current view
- MOD_ARRANGE + 'Shift-v' => lambda do
- current_view.columns.each do |a|
- a.layout = :stack
+ # focus client above
+ shortcut Key::FOCUS + Key::UP do
+ current_view.ctl = 'select up'
end
- end,
- # apply maximized layout to currently focused column
- MOD_ARRANGE + 'm' => lambda do
- if a = current_area
- a.layout = :max
+ # toggle focus between floating area and the columns
+ shortcut Key::FOCUS + 'space' do
+ current_view.ctl = 'select toggle'
end
- end,
- # apply maximized layout to all columns in current view
- MOD_ARRANGE + 'Shift-m' => lambda do
- current_view.columns.each do |a|
- a.layout = :max
+ # apply equal-spacing layout to current column
+ shortcut Key::ARRANGE + 'w' do
+ if a = current_area
+ a.layout = :default
+ end
end
- end,
- # focus the previous view
- MOD_FOCUS + 'comma' => lambda do
- if v = prev_view
- v.focus
+ # apply equal-spacing layout to all columns
+ shortcut Key::ARRANGE + 'Shift-w' do
+ current_view.columns.each do |a|
+ a.layout = :default
+ end
end
- end,
- # focus the next view
- MOD_FOCUS + 'period' => lambda do
- if v = next_view
- v.focus
+ # apply stacked layout to currently focused column
+ shortcut Key::ARRANGE + 'v' do
+ if a = current_area
+ a.layout = :stack
+ end
end
- end,
-
-
- ##########################################################################
- ## interactive menu
- ##########################################################################
- # launch an internal action by choosing from a menu
- MOD_MENU + 'i' => lambda do
- if choice = show_menu(@actionMenu + ACTIONS.keys, 'run action:')
- if action = ACTIONS[choice.to_sym]
- action.call
- else
- system choice << '&'
+ # apply stacked layout to all columns in current view
+ shortcut Key::ARRANGE + 'Shift-v' do
+ current_view.columns.each do |a|
+ a.layout = :stack
end
end
- end,
- # launch an external program by choosing from a menu
- MOD_MENU + 'e' => lambda do
- if choice = show_menu(@programMenu, 'run program:')
- system choice << '&'
+ # apply maximized layout to currently focused column
+ shortcut Key::ARRANGE + 'm' do
+ if a = current_area
+ a.layout = :max
+ end
end
- end,
- # focus any view by choosing from a menu
- MOD_MENU + 'u' => lambda do
- if choice = show_menu(tags, 'show view:')
- focus_view choice
+ # apply maximized layout to all columns in current view
+ shortcut Key::ARRANGE + 'Shift-m' do
+ current_view.columns.each do |a|
+ a.layout = :max
+ end
end
- end,
-
- # focus any client by choosing from a menu
- MOD_MENU + 'a' => lambda do
- list = Wmii.clients
- i = -1
- choices = list.map do |c|
- i += 1
- format "%d. [%s] %s", i, c[:tags].read, c[:props].read.downcase
+ # focus the previous view
+ shortcut Key::FOCUS + 'comma' do
+ if v = prev_view
+ v.focus
+ end
end
- if target = show_menu(choices, 'show client:')
- pos = target.scan(/\d+/).first.to_i
- list[pos].focus
+ # focus the next view
+ shortcut Key::FOCUS + 'period' do
+ if v = next_view
+ v.focus
+ end
end
- end,
- ##########################################################################
- ## sending / moving
- ##########################################################################
+ # sending / moving
- MOD_SEND + LEFT_KEY => lambda do
- grouped_clients.each do |c|
- c.send :left
+ shortcut Key::SEND + Key::LEFT do
+ grouped_clients.each do |c|
+ c.send :left
+ end
end
- end,
- MOD_SEND + RIGHT_KEY => lambda do
- grouped_clients.each do |c|
- c.send :right
+ shortcut Key::SEND + Key::RIGHT do
+ grouped_clients.each do |c|
+ c.send :right
+ end
end
- end,
- MOD_SEND + DOWN_KEY => lambda do
- grouped_clients.each do |c|
- c.send :down
+ shortcut Key::SEND + Key::DOWN do
+ grouped_clients.each do |c|
+ c.send :down
+ end
end
- end,
- MOD_SEND + UP_KEY => lambda do
- grouped_clients.each do |c|
- c.send :up
+ shortcut Key::SEND + Key::UP do
+ grouped_clients.each do |c|
+ c.send :up
+ end
end
- end,
- MOD_SEND + 'space' => lambda do
- grouped_clients.each do |c|
- c.send :toggle
+ # send all grouped clients from managed to floating area (or vice versa)
+ shortcut Key::SEND + 'space' do
+ grouped_clients.each do |c|
+ c.send :toggle
+ end
end
- end,
- MOD_SEND + 'Delete' => lambda do
- grouped_clients.each do |c|
- c.ctl = 'kill'
+ # close all grouped clients
+ shortcut Key::SEND + 'Delete' do
+ grouped_clients.each do |c|
+ c.ctl = 'kill'
+ end
end
- end,
- # swap the currently focused client with the one to its left
- MOD_SWAP + LEFT_KEY => lambda do
- current_client.swap :left
- end,
+ # swap the currently focused client with the one to its left
+ shortcut Key::SWAP + Key::LEFT do
+ current_client.swap :left
+ end
- # swap the currently focused client with the one to its right
- MOD_SWAP + RIGHT_KEY => lambda do
- current_client.swap :right
- end,
+ # swap the currently focused client with the one to its right
+ shortcut Key::SWAP + Key::RIGHT do
+ current_client.swap :right
+ end
- # swap the currently focused client with the one below it
- MOD_SWAP + DOWN_KEY => lambda do
- current_client.swap :down
- end,
+ # swap the currently focused client with the one below it
+ shortcut Key::SWAP + Key::DOWN do
+ current_client.swap :down
+ end
- # swap the currently focused client with the one above it
- MOD_SWAP + UP_KEY => lambda do
- current_client.swap :up
- end,
+ # swap the currently focused client with the one above it
+ shortcut Key::SWAP + Key::UP do
+ current_client.swap :up
+ end
- # Changes the tag (according to a menu choice) of each grouped client and
- # returns the chosen tag. The +tag -tag idea is from Jonas Pfenniger:
- # <http://zimbatm.oree.ch/articles/2006/06/15/wmii-3-and-ruby>
- MOD_SEND + 't' => lambda do
- choices = tags.map {|t| [t, "+#{t}", "-#{t}"]}.flatten
+ # Changes the tag (according to a menu choice) of each grouped client and
+ # returns the chosen tag. The +tag -tag idea is from Jonas Pfenniger:
+ # <http://zimbatm.oree.ch/articles/2006/06/15/wmii-3-and-ruby>
+ shortcut Key::SEND + 't' do
+ choices = tags.map {|t| [t, "+#{t}", "-#{t}"]}.flatten
- if target = show_menu(choices, 'tag as:')
- grouped_clients.each do |c|
- case target
+ if target = show_menu(choices, 'tag as:')
+ grouped_clients.each do |c|
+ case target
when /^\+/
c.tag $'
@@ -396,268 +428,248 @@ SHORTCUTS = {
else
c.tags = target
+ end
end
- end
- target
+ target
+ end
end
- end,
-
- ##########################################################################
- ## visual arrangement
- ##########################################################################
- MOD_ARRANGE + 't' => lambda do
- current_view.arrange_as_larswm
- end,
+ # zooming / sizing
- MOD_ARRANGE + 'g' => lambda do
- current_view.arrange_in_grid
- end,
-
- MOD_ARRANGE + 'd' => lambda do
- current_view.arrange_in_diamond
- end,
+ # Sends grouped clients to temporary view.
+ shortcut Key::PREFIX + 'b' do
+ src = current_tag
+ dst = src + '~'
+ grouped_clients.each do |c|
+ c.tag dst
+ end
- ##########################################################################
- ## client grouping
- ##########################################################################
+ v = View.new dst
+ v.focus
+ v.arrange_in_grid
+ end
- # include/exclude the currently focused client from the grouping
- MOD_GROUP + 'g' => lambda do
- current_client.toggle_grouping
- end,
+ # Sends grouped clients back to their original view.
+ shortcut Key::PREFIX + 'Shift-b' do
+ t = current_tag
- # include all clients in the currently focused view in the grouping
- MOD_GROUP + 'v' => lambda do
- current_view.group
- end,
+ if t =~ /~$/
+ grouped_clients.each do |c|
+ c.with_tags do
+ delete t
+ push $` if empty?
+ end
+ end
- # exclude all clients in the currently focused view from the grouping
- MOD_GROUP + 'Shift-v' => lambda do
- current_view.ungroup
- end,
+ focus_view $`
+ end
+ end
- # include all clients in the currently focused column in the grouping
- MOD_GROUP + 'c' => lambda do
- current_area.group
- end,
- # exclude all clients in the currently focused column from the grouping
- MOD_GROUP + 'Shift-c' => lambda do
- current_area.ungroup
- end,
+ # client grouping
- # invert the grouping in the currently focused view
- MOD_GROUP + 'i' => lambda do
- current_view.toggle_grouping
- end,
+ # include/exclude the currently focused client from the grouping
+ shortcut Key::GROUP + 'g' do
+ current_client.toggle_grouping
+ end
- # exclude all clients everywhere from the grouping
- MOD_GROUP + 'n' => lambda do
- ungroup_all
- end,
+ # include all clients in the currently focused view in the grouping
+ shortcut Key::GROUP + 'v' do
+ current_view.group
+ end
+ # exclude all clients in the currently focused view from the grouping
+ shortcut Key::GROUP + 'Shift-v' do
+ current_view.ungroup
+ end
- ##########################################################################
- ## external programs
- ##########################################################################
+ # include all clients in the currently focused column in the grouping
+ shortcut Key::GROUP + 'c' do
+ current_area.group
+ end
- MOD_EXEC + 'x' => lambda do
- system WMII_TERM + ' &'
- end,
+ # exclude all clients in the currently focused column from the grouping
+ shortcut Key::GROUP + 'Shift-c' do
+ current_area.ungroup
+ end
- MOD_EXEC + 'k' => lambda do
- system 'firefox &'
- end,
+ # invert the grouping in the currently focused view
+ shortcut Key::GROUP + 'i' do
+ current_view.toggle_grouping
+ end
- MOD_EXEC + 'j' => lambda do
- system 'nautilus --no-desktop &'
- end,
+ # exclude all clients everywhere from the grouping
+ shortcut Key::GROUP + 'n' do
+ ungroup_all
+ end
- ##########################################################################
- ## detaching (wmii-2 style)
- ##########################################################################
+ # visual arrangement
- # Detach the current grouping to a separate tag.
- MOD_PREFIX + 'd' => lambda do
- grouped_clients.each do |c|
- c.tags = DETACHED_TAG
+ shortcut Key::ARRANGE + 't' do
+ current_view.arrange_as_larswm
end
- end,
- # Attach the most recently detached client.
- MOD_PREFIX + 'Shift-d' => lambda do
- v = View.new DETACHED_TAG
+ shortcut Key::ARRANGE + 'g' do
+ current_view.arrange_in_grid
+ end
- if v.exist? and c = v.clients.last
- c.tags = current_tag
+ shortcut Key::ARRANGE + 'd' do
+ current_view.arrange_in_diamond
end
- end,
- ##########################################################################
- ## zooming / sizing
- ##########################################################################
+ # interactive menu
- # Sends grouped clients to temporary view.
- MOD_PREFIX + 'b' => lambda do
- src = current_tag
- dst = src + '~' + Time.now.to_i.to_s
+ # launch an internal action by choosing from a menu
+ shortcut Key::MENU + 'i' do
+ if choice = show_menu(@actionMenu + ACTIONS.keys, 'run action:')
+ unless action choice.to_sym
+ system choice << '&'
+ end
+ end
+ end
- grouped_clients.each do |c|
- c.tag dst
+ # launch an external program by choosing from a menu
+ shortcut Key::MENU + 'e' do
+ if choice = show_menu(@programMenu, 'run program:')
+ system choice << '&'
+ end
end
- v = View.new dst
- v.focus
- v.arrange_in_grid
- end,
+ # focus any view by choosing from a menu
+ shortcut Key::MENU + 'u' do
+ if choice = show_menu(tags, 'show view:')
+ focus_view choice
+ end
+ end
- # Sends grouped clients back to their original view.
- MOD_PREFIX + 'Shift-b' => lambda do
- t = current_tag
+ # focus any client by choosing from a menu
+ shortcut Key::MENU + 'a' do
+ list = Wmii.clients
- if t =~ /~\d+$/
- grouped_clients.each do |c|
- c.with_tags do
- delete t
- push $` if empty?
- end
+ i = -1
+ choices = list.map do |c|
+ i += 1
+ format "%d. [%s] %s", i, c[:tags].read, c[:props].read.downcase
end
- focus_view $`
+ if target = show_menu(choices, 'show client:')
+ pos = target.scan(/\d+/).first.to_i
+ list[pos].focus
+ end
end
- end,
-}
- ##########################################################################
- ## number keys
- ##########################################################################
- 10.times do |i|
- # focus {i}'th view
- SHORTCUTS[MOD_FOCUS + i.to_s] = lambda do
- focus_view tags[i - 1] || i
- end
+ # external programs
- # send current grouping to {i}'th view
- SHORTCUTS[MOD_SEND + i.to_s] = lambda do
- grouped_clients.each do |c|
- c.tags = tags[i - 1] || i
- end
+ shortcut Key::EXECUTE + 'x' do
+ system 'gnome-terminal &'
end
- # apply grid layout with {i} clients per column
- SHORTCUTS[MOD_ARRANGE + i.to_s] = lambda do
- current_view.arrange_in_grid i
+ shortcut Key::EXECUTE + 'k' do
+ system 'firefox &'
end
- end
-
- ##########################################################################
- ## alphabet keys
- ##########################################################################
- # focus the view whose name begins with an alphabet key
- ('a'..'z').each do |key|
- SHORTCUTS[MOD_FOCUS + 'v,' + key] = lambda do
- if t = tags.grep(/^#{key}/i).first
- focus_view t
- end
+ shortcut Key::EXECUTE + 'j' do
+ system 'nautilus --no-desktop &'
end
- end
-
-fs.keys = SHORTCUTS.keys.join("\n")
-############################################################################
-# START UP
-############################################################################
+ # wmii-2 style client detaching
-system 'xsetroot -solid $WMII_BACKGROUND &'
+ DETACHED_TAG = '|'
-# initialize the tag bar
- fs.lbar.clear
+ # Detach the current grouping from the current view.
+ shortcut Key::PREFIX + 'd' do
+ grouped_clients.each do |c|
+ c.with_tags do
+ c.tags = DETACHED_TAG
+ end
+ end
+ end
- sel = current_tag
- tags.each do |tag|
- bar = fs.lbar[tag]
- bar.create
+ # Attach the most recently detached client onto the current view.
+ shortcut Key::PREFIX + 'Shift-d' do
+ v = View.new DETACHED_TAG
- color = if tag == sel
- WMII_FOCUSCOLORS
- else
- WMII_NORMCOLORS
+ if v.exist? and c = v.clients.last
+ c.with_tags do
+ c.tags = current_tag
+ end
+ end
end
- bar.write "#{color} #{tag}"
- end
+ # number keys
-############################################################################
-# EVENT LOOP
-############################################################################
+ 10.times do |i|
+ # focus the {i}'th view
+ shortcut Key::FOCUS + i.to_s do
+ focus_view tags[i - 1] || i
+ end
-fs.event.open do |bus|
- loop do
- bus.read.split("\n").each do |event|
- type, parms = event.split(' ', 2)
+ # send current grouping to {i}'th view
+ shortcut Key::SEND, i.to_s do
+ grouped_clients.each do |c|
+ c.tags = tags[i - 1] || i
+ end
+ end
- case type.to_sym
- when :Start
- exit if parms == 'wmiirc'
+ # apply grid layout with {i} clients per column
+ shortcut Key::ARRANGE, i.to_s do
+ current_view.arrange_in_grid i
+ end
+ end
- when :CreateTag
- bar = fs.lbar[parms]
- bar.create
- bar.write "#{WMII_NORMCOLORS} #{parms}"
- when :DestroyTag
- fs.lbar[parms].remove
+ # alphabet keys
- when :FocusTag
- fs.lbar[parms] << "#{WMII_FOCUSCOLORS} #{parms}"
+ # focus the view whose name begins with an alphabet key
+ ('a'..'z').each do |k|
+ shortcut Key::VIEW + k do
+ if t = tags.grep(/^#{k}/i).first
+ focus_view t
+ end
+ end
+ end
- when :UnfocusTag
- fs.lbar[parms] << "#{WMII_NORMCOLORS} #{parms}"
- when :UrgentTag
- fs.lbar[parms] << "*#{parms}"
+################################################################################
+# START UP
+################################################################################
- when :NotUrgentTag
- fs.lbar[parms] << parms
+system "xsetroot -solid #{Color::BACKGROUND.inspect} &"
- when :LeftBarClick
- button, viewId = parms.split
+# Misc Setup
+action :status
+action :rehash
- case button.to_i
- when PRIMARY_CLICK
- focus_view viewId
+# Tag Bar Setup
+fs.lbar.clear
- when MIDDLE_CLICK
- grouped_clients.each do |c|
- c.tag viewId
- end
+tags.each do |tag|
+ color = (tag == current_tag) ? Color::FOCUSED : Color::NORMAL
- when SECONDARY_CLICK
- grouped_clients.each do |c|
- c.untag viewId
- end
- end
+ bar = fs.lbar[tag]
+ bar.create
+ bar.write "#{color} #{tag}"
+end
- when :ClientClick
- clientId, button = parms.split
+# Keygrab Setup
+fs.keys = SHORTCUTS.keys.join("\n")
- if button.to_i == SECONDARY_CLICK
- Client.toggle_grouping clientId
- end
+# Event Loop
+fs.event.open do |bus|
+ loop do
+ bus.read.split("\n").each do |event|
+ type, parms = event.split(' ', 2)
- when :Key
- SHORTCUTS[parms].call
- end
+ args = parms.split(' ') rescue []
+ event type.to_sym, *args
end
end
end