Snippets » History » Version 38
Version 37 (Anonymous, 11/06/2011 07:47 PM) → Version 38/46 (François-Xavier LdM, 04/14/2012 09:36 PM)
h1. Snippets\015\012\015\012This page shows small snippets that might be useful. Without further instructions they just need to be copied into the config of [[subtle]].\015\012\015\012{{>toc}}\015\012\015\012h2. Alt-Tab\015\012\015\012This cycles through windows of view\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012grab "A-Tab" do\015\012    clients = Subtlext::Client.visible\015\012\015\012    clients.last.instance_eval do\015\012      focus\015\012      raise\015\012    end\015\012end\015\012\015\012grab "A-S-Tab" do \015\012clients = Subtlext::Client.visible\015\012\015\012    clients.first.instance_eval do                                                   \015\012      lower                                                                          \015\012    end\015\012    clients.first.instance_eval do\015\012      focus\015\012    end                                                                              \015\012end\015\012</code></pre>\015\012\015\012h2. Extend view\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012require "subtle/subtlext"\015\012\015\012STORE ||= {}\015\012\015\012module Subtlext\015\012    class View\015\012      def method_missing(meth, *args)\015\012        STORE[self.name] = { } unless(STORE.has_key?(self.name))\015\012\015\012        if meth.to_s.end_with?("=")\015\012          meth = meth.to_s.chop.to_sym\015\012\015\012          STORE[self.name][meth] = args[0]\015\012        else\015\012          STORE[self.name][meth]\015\012        end\015\012      end\015\012    end\015\012end\015\012</code></pre>\015\012\015\012Finally make some use of this like following hook:\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012on :view_jump do |v|\015\012    v.visits += 1 rescue v.visits = 1\015\012    puts "View %s, %d visits" % [ v.name, v.visits ]\015\012end\015\012</code></pre>\015\012\015\012h2. Focus gravities\015\012\015\012Focus window a specific gravities on view.\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012{\015\012    "KP_7" => :top_left,      "KP_8" => :top,      "KP_9" => :top_right,\015\012    "KP_4" => :left,          "KP_5" => :center, "KP_6" => :right,\015\012    "KP_1" => :bottom_left, "KP_2" => :bottom, "KP_3" => :bottom_right\015\012}.each do |k, v|\015\012    grab "A-C-" + k, lambda {\015\012      c = Subtlext::View.current.clients.select { |c|\015\012        c.gravity.name.to_sym == v\015\012      }\015\012    \015\012      c.first.focus unless(c.empty?)\015\012    }\015\012end\015\012</code></pre>\015\012\015\012h2. Move windows\015\012\015\012This snippet adds nine [[grabs]] to move windows on the fly to nine defined views. It uses [[tagging]] for this, creates [[tags]] based on the view names and applies them when needed.\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012on :start do\015\012    # Create missing tags\015\012    views = Subtlext::View.all.map { |v| v.name }\015\012    tags    = Subtlext::Tag.all.map { |t| t.name }\015\012\015\012    views.each do |v|\015\012      unless tags.include?(v)\015\012        t = Subtlext::Tag.new(v)\015\012        t.save\015\012      end\015\012    end\015\012end\015\012\015\012# Add nine C-< number> grabs\015\012(1..9).each do |i|\015\012 grab "C-%d" % [ i ] do |c|\015\012     views = Subtlext::View.all\015\012     names = views.map { |v| v.name }\015\012\015\012     # Sanity check\015\012     if i <= views.size\015\012       # Tag client\015\012       tags = c.tags.reject { |t| names.include?(t.name) or "default" == t.name }\015\012       tags << names[i - 1]\015\012\015\012       c.tags = tags\015\012\015\012       # Tag view\015\012       views[i - 1].tag(names[i - 1])\015\012     end\015\012 end\015\012end\015\012</code></pre>\015\012\015\012h2. Current view\015\012\015\012This snippet works similar to the previous, it adds tags based on the view names. When there is an untagged window (a window with the default tag only) it adds the name of the current view as tag, which effectively moves the window to the current view.\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012on :start do\015\012    # Create missing tags\015\012    views = Subtlext::View.all.map { |v| v.name }\015\012    tags    = Subtlext::Tag.all.map { |t| t.name }\015\012\015\012    views.each do |v|\015\012      unless tags.include?(v)\015\012        t = Subtlext::Tag.new(v)\015\012        t.save\015\012      end\015\012    end\015\012end\015\012\015\012# Assign tags to clients\015\012on :client_create do |c|\015\012    view = Subtlext::View.current\015\012    tags = c.tags.map { |t| t.name }\015\012\015\012    # Add tag to view\015\012    view.tag(view.name) unless(view.tags.include?(view.name))\015\012\015\012    # Exclusive for clients with default tag only\015\012    if tags.include?("default") and 1 == tags.size\015\012      c.tags = [ view.name ]\015\012    end\015\012end\015\012</code></pre>\015\012\015\012h2. Scratchpad\015\012\015\012The scratchpad snippet is just a small hack of the tagging. Normally [[subtle]] doesn't allow to create a window without tags, so that it's never visible. This grab just creates a "urxvt":http://software.schmorp.de/pkg/rxvt-unicode.html, strips all [[tagging|tags]] and sets sticky. On the next press it just toggles sticky and blends the window in and out, like a scratchpad.\015\012\015\012<pre>{{hide}}<code class="ruby">grab "A-b" do\015\012    if (c = Subtlext::Client.first("scratch"))\015\012      c.toggle_stick\015\012      c.focus\015\012    elsif (c = Subtlext::Subtle.spawn("urxvt -name scratch"))\015\012      c.tags    = [] \015\012      c.flags = [ :stick ]\015\012    end\015\012end\015\012</code></pre>\015\012\015\012h2. Check config\015\012\015\012In case you keep forgetting to run @subtle -k@ after changing the config this might be handy for you. It checks the config, displays a message via xmessage or just reloads the config.\015\012\015\012<pre>{{hide}}<code class="ruby"># Make xmessage stick and urgent\015\012tag "xmessage" do\015\012    match    "xmessage"\015\012    float    true\015\012    stick    true\015\012    urgent true\015\012end\015\012\015\012# The actual grab\015\012grab "A-C-r", <<SCRIPT\015\012subtle -k &>/dev/null\015\012reload=$?\015\012\015\012if [ $reload -eq 1 ] ; then\015\012    xmessage 'Syntax error, reload anyway?' -center -buttons NO:1,YES:0\015\012    reload=$?\015\012fi\015\012\015\012[ $reload -eq 0 ] && subtler -r\015\012SCRIPT\015\012</code></pre>\015\012\015\012h2. :ViewNext :ViewPrev skipping hidden views\015\012\015\012Allow you to go to the next non-empty view. very useful when you don't want :ViewNext to go into hidden views (Mostly with dynamic views)\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012require "subtle/subtlext"\015\012grab "W-Right" do\015\012    vArr = Subtlext::View[:all];\015\012    cindx = vArr.index(Subtlext::View.current);\015\012\015\012    for i in 1..vArr.size do\015\012      cV = vArr[(i + cindx) % vArr.size];\015\012      if (!cV.clients.empty? && Subtlext::View.visible.index(cV) == nil) then\015\012        cV.jump;\015\012        break;\015\012      end\015\012    end\015\012end\015\012\015\012grab "W-Left" do\015\012    vArr = Subtlext::View[:all].reverse;\015\012    cindx = vArr.index(Subtlext::View.current);\015\012\015\012    for i in 1..vArr.size do\015\012      cV = vArr[(i + cindx) % vArr.size];\015\012      if (!cV.clients.empty? && Subtlext::View.visible.index(cV) == nil) then\015\012        cV.jump;\015\012        break;\015\012      end\015\012    end\015\012end\015\012\015\012</code></pre>\015\012\015\012h2. Go to new client\015\012\015\012When a client is created, go to the view where it is.\015\012\015\012<pre>{{hide}}<code class="ruby">\015\012on :client_create do |c|\015\012    v = c.views;\015\012    if !v.empty? then\015\012      v[0].jump;\015\012    end\015\012end\015\012</code</pre> -r\015\012SCRIPT\015\012</code></pre>