[c5c522c] | 1 | LCDproc client/server protocol |
---|
| 2 | --------------------------------------------- |
---|
| 3 | |
---|
| 4 | |
---|
| 5 | QUICKSTART |
---|
| 6 | ---------- |
---|
| 7 | - Open a socket to the LCDproc port (usually 13666). |
---|
| 8 | - say "hello" |
---|
| 9 | - the server will notify you of a good connection, and some info |
---|
| 10 | on the type of display available. |
---|
| 11 | - Identify yourself. "client_set name some_sort_of_name" |
---|
| 12 | - Add a new screen. "screen_add my_screen" |
---|
| 13 | - Put a widget on the screen. |
---|
| 14 | "widget_add my_screen my_widget string" |
---|
| 15 | - Now, update the widget whenever your status info changes... |
---|
| 16 | "widget_set my_screen my_widget 1 1 Booger!" |
---|
| 17 | |
---|
| 18 | - When you're done, just close the socket. |
---|
| 19 | - You probably want to read on for more information, once you've |
---|
| 20 | gotten the LCDproc server to display something. :) |
---|
| 21 | |
---|
| 22 | |
---|
| 23 | |
---|
| 24 | DETAILS |
---|
| 25 | ------- |
---|
| 26 | |
---|
| 27 | There are two parts to the spec: |
---|
| 28 | A language for client/server to interact with. |
---|
| 29 | A protocol guiding interactions. |
---|
| 30 | |
---|
| 31 | =================== The protocol ================================== |
---|
| 32 | |
---|
| 33 | The protocol is context-free. So, no commands require responses; and |
---|
| 34 | responses are simply commands. |
---|
| 35 | |
---|
| 36 | The client may send updated info at any time, and the server decides |
---|
| 37 | whether to display it. An ideal communication may flow like this: |
---|
| 38 | client->server server->client |
---|
| 39 | ------------------ ------------------- |
---|
| 40 | (idle) (nothing) |
---|
| 41 | (idle) "I'm listening" |
---|
| 42 | new stats... (nothing; displays updated stats) |
---|
| 43 | new stats... (nothing...) |
---|
| 44 | new stats... (nothing...) |
---|
| 45 | new stats... "Okay, be quiet" |
---|
| 46 | (idle) (nothing; displays new screen) |
---|
| 47 | ... ... |
---|
| 48 | (idle) "Your slider moved up" |
---|
| 49 | Set slider value: 43 (nothing; displays updated slider) |
---|
| 50 | (idle) (nothing) |
---|
| 51 | ... ... |
---|
| 52 | But the client could safely continue to send new stats, knowing that |
---|
| 53 | the server isn't listening and won't display it. Also, the client could |
---|
| 54 | ignore the slider change, and the slider onscreen simply wouldn't move. |
---|
| 55 | |
---|
| 56 | |
---|
| 57 | =================== The syntax ================================== |
---|
| 58 | |
---|
| 59 | The language is ascii-based, so a human can telnet to a port and talk |
---|
| 60 | to the server. This helps with development and debugging. |
---|
| 61 | |
---|
| 62 | With that in mind, a commandline-like syntax seems good: |
---|
| 63 | |
---|
| 64 | function arg1 arg2 arg3 ... |
---|
| 65 | |
---|
| 66 | The syntax dictates that the first word is a function name, and the |
---|
| 67 | rest of the line is passed to that function as an argument. |
---|
| 68 | String-type arguments should always come last. So, for example: |
---|
| 69 | |
---|
| 70 | set_label 23 3 2 Hey, booger. What's up? |
---|
| 71 | |
---|
| 72 | The first argument is a label id number, the 2nd and 3rd are x,y |
---|
| 73 | coordinates onscreen, and the rest of the line is a string. |
---|
| 74 | |
---|
| 75 | |
---|
| 76 | =================== The command set ================================== |
---|
| 77 | |
---|
| 78 | The naming convention dictates that function names are lower-case, |
---|
| 79 | with underscores ("_"'s) between words. |
---|
| 80 | |
---|
| 81 | The naming convention also requires that function-name words go in |
---|
| 82 | descending order. So, "screen_set_priority" would be okay, but |
---|
| 83 | "set_screen_priority" would not. |
---|
| 84 | |
---|
| 85 | Id's are strings. (the "#id" things) |
---|
| 86 | |
---|
| 87 | In general, we're trying to keep the command set small. Especially the |
---|
| 88 | server->client functions, so that clients won't have to handle a lot of |
---|
| 89 | different types of input. |
---|
| 90 | |
---|
| 91 | Now, the function list: |
---|
| 92 | |
---|
| 93 | client->server functions |
---|
| 94 | ------------------------- |
---|
| 95 | hello |
---|
| 96 | Client init. You must send this before the server will pay |
---|
| 97 | any attention to you. You'll get some info about the server |
---|
| 98 | in return... (a "connect" string) |
---|
| 99 | |
---|
| 100 | |
---|
| 101 | client_set [name #id] |
---|
| 102 | Set client's name and other info |
---|
| 103 | |
---|
| 104 | client_add_key #id |
---|
| 105 | Tells the server the client can handle keypresses of type #id. |
---|
| 106 | #id is probably just "A", "B", and so on... |
---|
| 107 | All keypresses are disabled by default, so you'll have to tell |
---|
| 108 | the server which ones you want to accept... |
---|
| 109 | |
---|
| 110 | client_del_key #id |
---|
| 111 | Tells the server to never send that keypress. |
---|
| 112 | All keypresses are disabled by default. |
---|
| 113 | |
---|
| 114 | |
---|
| 115 | screen_add #id |
---|
| 116 | Add a new screen |
---|
| 117 | |
---|
| 118 | screen_del #id |
---|
| 119 | Remove a screen |
---|
| 120 | |
---|
| 121 | screen_set #id [priority integer] [name "my_name"] [duration integer] |
---|
| 122 | [wid width] [hgt height] |
---|
| 123 | Initialize a screen, or reset its data. |
---|
| 124 | Priority values are as follows: |
---|
| 125 | 0 You feel like getting kicked off the server, don't you? |
---|
| 126 | 1 The world is about to explode |
---|
| 127 | 16 Emergency priority |
---|
| 128 | 32 Very high priority (important) |
---|
| 129 | 64 High priority (normal) |
---|
| 130 | 128 Normal (recommended) |
---|
| 131 | 192 Low priority (normal) |
---|
| 132 | 224 Very low priority (very unimportant) |
---|
| 133 | 240 Boring as hell |
---|
| 134 | 255 This screen won't show up very much even if there are |
---|
| 135 | no other screens queued... |
---|
| 136 | An example of using priorities is as follows. |
---|
| 137 | |
---|
| 138 | Imagine you're making an mp3 player for LCDproc. When the |
---|
| 139 | song changes, it's nice to display the new name immediately. |
---|
| 140 | So, you could set your screen's priority to 64, wait for |
---|
| 141 | the server to display (or ignore) your screen, then set the |
---|
| 142 | screen back to 128. This would cause the mp3 screen to |
---|
| 143 | show up as soon as the one onscreen was finished, then |
---|
| 144 | return to normal priority afterward. |
---|
| 145 | |
---|
| 146 | Or, let's say your client monitors the health of hospital |
---|
| 147 | patients. If one of the patients has a heart attack, you |
---|
| 148 | could set the screen priority to 16 (emergency), and it |
---|
| 149 | would be displayed immediately. It wouldn't even wait for |
---|
| 150 | the previous screen to finish. ... And it would stay there |
---|
| 151 | most of the time until the user did something about it. |
---|
| 152 | |
---|
| 153 | A priority of 1 would stay onscreen permanently, with |
---|
| 154 | flashing lights and other visual cues if possible. |
---|
| 155 | ... Please *don't* use this priority. :) |
---|
| 156 | |
---|
| 157 | The duration can be either a positive number, or -1. A |
---|
| 158 | positive number indicates how many display frames the screen |
---|
| 159 | should last for. A 0 or -1 means that the server should use |
---|
| 160 | "auto" duration, which is probably a good idea. This will be |
---|
| 161 | whatever the user wants. It defaults to 4 seconds (32 |
---|
| 162 | frames), or will be calculated for things such as scrollers. |
---|
| 163 | |
---|
| 164 | widget_add #screen #id type [-in #id] |
---|
| 165 | Add something onscreen |
---|
| 166 | Widget types can be any of the following: "string", "hbar", |
---|
| 167 | "vbar", "title", "icon", "scroller", "frame", ... more later? |
---|
| 168 | Widgets are drawn in the order you create them. |
---|
| 169 | |
---|
| 170 | You can put a widget inside a frame by adding "-in #id", where |
---|
| 171 | #id is the name of a frame. |
---|
| 172 | |
---|
| 173 | widget_del #screen #id |
---|
| 174 | Kill something onscreen |
---|
| 175 | |
---|
| 176 | widget_set #screen #id data |
---|
| 177 | Set (reset) widget's data |
---|
| 178 | Note that the "string" type should be used for frame buffers. |
---|
| 179 | Strings should not be bigger than the screen. |
---|
| 180 | The widgets take these arguments for data: |
---|
| 181 | |
---|
| 182 | string x y text |
---|
| 183 | |
---|
| 184 | hbar x y length_in_pixels |
---|
| 185 | |
---|
| 186 | vbar x y length_in_pixels |
---|
| 187 | |
---|
| 188 | icon x y binary_data |
---|
| 189 | |
---|
| 190 | title text |
---|
| 191 | |
---|
| 192 | scroller left top right bottom direction speed text |
---|
| 193 | |
---|
| 194 | A scroller is a string which scrolls. |
---|
| 195 | This is useful for things such as the disk |
---|
| 196 | usage screen, which may be very tall. |
---|
| 197 | The speed is how many display frames to delay |
---|
| 198 | between scrolling. Each display frame is |
---|
| 199 | 1/8th of a second, by default. |
---|
| 200 | Direction must be "h" or "v". |
---|
| 201 | Positive speeds indicate frames per movement. |
---|
| 202 | Negative speeds indicate movements per frame. |
---|
| 203 | |
---|
| 204 | frame left top right bottom wid hgt dir speed |
---|
| 205 | |
---|
| 206 | Frames occupy the area (left, top)-(right,bottom) |
---|
| 207 | onscreen, and the inside area is wid x hgt. |
---|
| 208 | The inside may be bigger than the actual size, |
---|
| 209 | so that the frame will scroll. |
---|
| 210 | |
---|
| 211 | |
---|
| 212 | server->client functions |
---|
| 213 | ------------------------- |
---|
| 214 | connect args |
---|
| 215 | Verifies connection; gives info about the LCD, etc... |
---|
| 216 | |
---|
| 217 | bye |
---|
| 218 | Notifies the client of a server shutdown. |
---|
| 219 | |
---|
| 220 | huh? [info] |
---|
| 221 | Notifies the client of a request error. |
---|
| 222 | |
---|
| 223 | listen [#screen [#widget [#widgets...]]] |
---|
| 224 | Notifies client that "server is listening for data". |
---|
| 225 | |
---|
| 226 | ignore [#screen [#widget [#widgets...]]] |
---|
| 227 | Tells the client "shut up". |
---|
| 228 | |
---|
| 229 | key #id |
---|
| 230 | Sends a keypress to the client. |
---|
| 231 | |
---|
| 232 | |
---|
| 233 | |
---|
| 234 | |
---|
| 235 | --- Not implemented yet --- |
---|
| 236 | The functions below are planned but not completed. |
---|
| 237 | |
---|
| 238 | |
---|
| 239 | client->server functions |
---|
| 240 | ------------------------- |
---|
| 241 | menu_add #id |
---|
| 242 | Add a new menu. |
---|
| 243 | |
---|
| 244 | menu_del #id |
---|
| 245 | Get rid of a menu. |
---|
| 246 | |
---|
| 247 | menu_set [top] [name my_menu_name] |
---|
| 248 | if (top) Gets added to "Client Menus". |
---|
| 249 | else Client must insert it into its own menu heirarchy. |
---|
| 250 | |
---|
| 251 | menu_item_add #menu #id |
---|
| 252 | Add a new, blank menu item. |
---|
| 253 | |
---|
| 254 | menu_item_del #menu #id |
---|
| 255 | Delete a menu item. |
---|
| 256 | |
---|
| 257 | menu_item_set #menu #id type [value] text |
---|
| 258 | (re)Set the menu item's data. |
---|
| 259 | If type is "checkbox" or "slider" or "menu", [value] should |
---|
| 260 | contain appropriate info. (like true, 43, or #menuid) |
---|
| 261 | |
---|
| 262 | |
---|
| 263 | backlight [on] [off] [blink] [flash] [toggle] |
---|
| 264 | Requests that the backlight be toggled... The backlight |
---|
| 265 | command will likely be ignored, but users can enable it if |
---|
| 266 | desired. |
---|
| 267 | |
---|
| 268 | The LCDproc server has [will have] several backlight modes: |
---|
| 269 | On Stays on all the time |
---|
| 270 | Off Stays off all the time |
---|
| 271 | Load? Turns off when the load average is low |
---|
| 272 | Shell? Controlled by a user-supplied shell script |
---|
| 273 | Open Can be controlled by all clients |
---|
| 274 | Vis Controlled by the currently visible client |
---|
| 275 | |
---|
| 276 | |
---|
| 277 | driver_add #id? type args |
---|
| 278 | Start up a new output driver. |
---|
| 279 | Nice if you want to check on your machine remotely with the |
---|
| 280 | curses driver. |
---|
| 281 | |
---|
| 282 | driver_del #id? (or type) |
---|
| 283 | Stop a running output driver. |
---|
| 284 | Good for reclaiming your joystick when you want to play games... |
---|
| 285 | |
---|
| 286 | |
---|
| 287 | |
---|
| 288 | |
---|
| 289 | server->client functions |
---|
| 290 | ------------------------- |
---|
| 291 | menu #menu #item #action |
---|
| 292 | Tells the client that a menu item was selected/used/etc... |
---|
| 293 | The action can be "click", "up", or "down". The client should |
---|
| 294 | handle this according to what type of menu item has been |
---|
| 295 | activated, and should probably send the server a new item |
---|
| 296 | definition if the item was a checkbox or slider. |
---|
| 297 | |
---|
| 298 | |
---|