Hacking » History » Version 62
Version 61 (Anonymous, 10/17/2009 07:35 PM) → Version 62/100 (Anonymous, 05/22/2010 01:26 AM)
h1. Hacking\015\012\015\012The Development\015\012\015\012The following information is for people who are interested in [[subtle]]'s internals and/or like to play around and extend [[subtle]].\015\012\015\012{{>toc}}\015\012\015\012h1. RDoc documentation\015\012\015\012The latest "rdoc":http://rdoc.sourceforge.net documention can either be found "here":http://unexist.scrapping.cc/rdoc/index.html or be generated with *rake rdoc* in the source tree.\015\012\015\012h1. Unit testing\015\012\015\012[[Subtle]] is shipped with a bunch of unit tests that can be run easily via "rake":http://rake.rubyforge.org/ tasks:\015\012\015\012bq. rake test\015\012rake test sublet=clock.rb\015\012\015\012_They can be found in the test folder._\015\012\015\012Following tests are included:\015\012\015\012h2. [[Subtlext]]\015\012\015\012<pre><code class="ruby">\015\012% rake test \015\012(in /home/unexist/projects/subtle)\015\012LD subtle\015\012LD subtler\015\012LD subtlext\015\012Loaded suite /usr/bin/rake\015\012Started\015\012......\015\012Finished in 0.047792 seconds.\015\012\015\0126 tests, 84 assertions, 0 failures, 0 errors\015\012</code></pre>\015\012\015\012h2. [[Sublets]]\015\012\015\012<pre><code class="ruby">\015\012% rake test sublet=clock.rb\015\012(in /home/unexist/projects/subtle)\015\012LD subtle\015\012LD subtler\015\012LD subtlext\015\012Loaded suite /usr/bin/rake\015\012Started\015\012.\015\012Finished in 0.000561 seconds.\015\012\015\0121 tests, 2 assertions, 0 failures, 0 errors\015\012</code></pre>\015\012\015\012h1. EWMH/ICCCM specifications\015\012\015\012Here are all "EWMH/NetWM":http://standards.freedesktop.org/wm-spec atoms listed that are supported by [[subtle]], [[subtler]] and [[subtlext]].\015\012\015\012h2. Default\015\012\015\012h3. _NET_NUMBER_OF_DESKTOPS\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_DESKTOP_NAMES\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_VIRTUAL_ROOTS\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_CURRENT_DESKTOP\015\012\015\012Change current desktop\015\012<pre><code class="ruby">\015\012data.l[0] = <View id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_RESTACK_WINDOW\015\012\015\012Change stacking of window\015\012<pre><code class="ruby">\015\012data.l[0] = <Ignored>\015\012data.l[1] = <Client id>\015\012data.l[2] = <Detail>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012*Detail*: 0 = Above (raise), 1 = Below (lower)\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_MOVERESIZE_WINDOW\015\012\015\012Resize window\015\012<pre><code class="ruby">\015\012data.l[0] = <Ignored>\015\012data.l[1] = <x>\015\012data.l[2] = <y>\015\012data.l[3] = <width>\015\012data.l[4] = <height>\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_CLOSE_WINDOW\015\012\015\012Close client window\015\012<pre><code class="ruby">\015\012data.l[0] = <Timestamp>\015\012data.l[1] = <Ignored>\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h2. WM State\015\012\015\012Normally there are three types of actions: +remove+ (0), +add+ (1) and +toggle+ (2), but we _always_ toggle the states independent of the supplied action. The second property will be ignored.\015\012\015\012h3. _NET_WM_STATE_FULLSCREEN\015\012\015\012Toggle client fullscreen\015\012<pre><code class="ruby">\015\012data.l[0] = <Action>\015\012data.l[1] = _NET_WM_STATE_FULLSCREEN\015\012data.l[2] = <Ignored>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_WM_STATE_ABOVE\015\012\015\012Toggle client float\015\012<pre><code class="ruby">\015\012data.l[0] = <Action>\015\012data.l[1] = _NET_WM_STATE_ABOVE\015\012data.l[2] = <Ignored>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_WM_STATE_STICKY\015\012\015\012Toggle client urgent\015\012<pre><code class="ruby">\015\012data.l[0] = <Action>\015\012data.l[1] = _NET_WM_STATE_STICKY\015\012data.l[2] = <Ignored>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h2. XEmbed\015\012\015\012h3. MANAGER\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_SYSTEM_TRAY_OPCODE \015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_SYSTEM_TRAY_MESSAGE_DATA \015\012\015\012[[Development#1|top]]\015\012\015\012h3. _NET_SYSTEM_TRAY_S\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _XEMBED\015\012\015\012[[Development#1|top]]\015\012\015\012h3. _XEMBED_INFO\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_EMBEDDED_NOTIFY\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_WINDOW_ACTIVATE\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_WINDOW_DEACTIVATE\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_REQUEST_FOCUS\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_FOCUS_IN\015\012\015\012[[Development#1|top]]\015\012\015\012h3. XEMBED_FOCUS_OUT\015\012\015\012[[Development#1|top]]\015\012\015\012h2. Extension\015\012\015\012h3. SUBTLE_WINDOW_TAG\015\012\015\012Add a tag to window (Client or View)\015\012<pre><code class="ruby">\015\012data.l[0] = <Client id>\015\012data.l[1] = <Tag id>\015\012data.l[2] = <Type>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012*Type*: 0 = Client, 1 = View\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_WINDOW_UNTAG\015\012\015\012Remove a tag from window (Client or [[Views|View]])\015\012<pre><code class="ruby">\015\012data.l[0] = <Client id>\015\012data.l[1] = <Tag id>\015\012data.l[2] = <Type>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012*Type*: 0 = Client, 1 = View\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_WINDOW_TAGS\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_WINDOW_GRAVITY\015\012\015\012Set client window [[gravity]]\015\012<pre><code class="ruby">\015\012data.l[0] = <Client id>\015\012data.l[1] = <Gravity type>\015\012data.l[2] = <Gravity mode>\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_WINDOW_SCREEN\015\012\015\012Set client window [[screens|screen]]\015\012<pre><code class="ruby">\015\012data.l[0] = <Client id>\015\012data.l[1] = <Screen id>\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_WINDOW_FLAGS\015\012\015\012Set client flags\015\012<pre><code class="ruby">\015\012data.l[0] = <Client id>\015\012data.l[1] = <Flags>\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012The bits in *flags* have the following meaning:\015\012\015\012| Bit | Description |\015\012| 1 | Fullscreen | \015\012| 2 | Floating |\015\012| 3 | Sticky |\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_GRAVITY_NEW\015\012\015\012Create a new [[gravity]] mode\015\012<pre><code class="ruby">\015\012data.l[0] = <Gravity id>\015\012data.l[1] = <x>\015\012data.l[2] = <y>\015\012data.l[3] = <width>\015\012data.l[4] = <height>\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_GRAVITY_LIST\015\012\015\012Get a [[gravity]] mode list\015\012<pre><code class="ruby">\015\012data.l[0] = 0\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_GRAVITY_KILL\015\012\015\012Kill a tag\015\012<pre><code class="ruby">\015\012data.l[0] = <Tag id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_TAG_NEW\015\012\015\012Create a new [[tags|tag]]\015\012<pre><code class="ruby">\015\012data.b[0-20] = <Tag name>\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_TAG_LIST\015\012\015\012Get a [[tags|tag]] list\015\012<pre><code class="ruby">\015\012data.l[0] = 0\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_TAG_KILL\015\012\015\012Kill a [[tags|tag]]\015\012<pre><code class="ruby">\015\012data.l[0] = <Tag id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_VIEW_NEW\015\012\015\012Create a new [[views|view]]\015\012<pre><code class="ruby">\015\012data.b[0-20] = <View name>\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_VIEW_LIST\015\012\015\012Get a [[views|view]] list\015\012<pre><code class="ruby">\015\012data.l[0] = 0\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_VIEW_KILL\015\012\015\012Kill a [[views|view]]\015\012<pre><code class="ruby">\015\012data.l[0] = <View id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_SUBLET_NEW\015\012\015\012Load a [[sublets|sublet]] from _$XDG_DATA_HOME/subtle/sublets_\015\012<pre><code class="ruby">\015\012data.b[0-20] = <Sublet filename>\015\012</code></pre>\015\012\015\012h3. SUBTLE_SUBLET_DATA\015\012\015\012Set data field of [[sublets|sublet]]\015\012<pre><code class="ruby">\015\012data.b[0] = <Sublet id>\015\012data.b[1-20] = <data>\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_SUBLET_UPDATE\015\012\015\012Force update of a [[sublets|sublet]]\015\012<pre><code class="ruby">\015\012data.l[0] = <Sublet id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_SUBLET_LIST\015\012\015\012Get [[sublets|sublet]] list\015\012<pre><code class="ruby">\015\012data.l[0] = 0\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012\015\012h3. SUBTLE_SUBLET_KILL\015\012\015\012Kill a [[sublets|sublet]]\015\012<pre><code class="ruby">\015\012data.l[0] = <Sublet id>\015\012data.l[1] = 0\015\012data.l[2] = 0\015\012data.l[3] = 0\015\012data.l[4] = 0\015\012</code></pre>\015\012\015\012[[Development#1|top]]\015\012