Return-Path: Received: from mail.dulug.duke.edu (annapurna.dulug.duke.edu [152.3.183.71]) by swamp.nerdfest.org (8.12.8/8.12.8) with ESMTP id h9O1Y29Z017488 for ; Fri, 24 Oct 2003 02:34:03 +0100 Received: from ligo.mit.edu (LIGO.MIT.EDU [18.120.0.82]) by mail.dulug.duke.edu (Postfix) with ESMTP id 6400E2C121 for ; Thu, 23 Oct 2003 21:31:01 -0400 (EDT) Received: from ligo (ligo [18.120.0.82]) by ligo.mit.edu (8.11.6+Sun/8.11.6) with ESMTP id h9O1Wpp27313 for ; Thu, 23 Oct 2003 21:32:51 -0400 (EDT) Date: Thu, 23 Oct 2003 21:32:51 -0400 (EDT) From: Pradeep Sarin X-X-Sender: sarin@ligo To: zed@linuxpower.org Subject: patch to add APM status display on fspanel Message-ID: MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII Status: O Hi I really like fspanel, and have been using it for the past couple of years on my laptop. A while ago, I added in some simple code to read /proc/apm and display the battery level on the panel right next to the clock. I am submitting the relevant patch to fspanel.c (version 0.7) below. Hopefully someone else may find it useful. The APM display can be turned off by commenting out the #define PROCAPM line near the top of the file. The display shows battery percentage as black text on gray if the AC line is plugged in, white on black otherwise. In addition, the desk-switching icons on left of the panel have been removed (I use Ctrl-RghtArrow, Ctrl-LeftArrow key bindings), and width of the panel is a fixed 1024 - to workaround problems I was having with a multi-headed display. Cheers - Pradeep Sarin Postdoctoral Associate MIT LIGO Laboratory, Cambridge MA 02139 --- fspanel.c.orig 2001-06-11 03:59:48.000000000 -0400 +++ fspanel.c 2003-10-23 21:18:56.000000000 -0400 @@ -6,6 +6,7 @@ ********************************************************/ #include +#include #include #include #include @@ -21,6 +22,14 @@ #include "icon.xpm" #endif +/* Comment out this line, if you don't want APM display */ +#define PROCAPM "/proc/apm" +#ifdef PROCAPM +#define apm_width (20) +#else +#define apm_width (0) +#endif + #include "fspanel.h" /* you can edit these */ @@ -28,7 +37,7 @@ #define ICONWIDTH 16 #define ICONHEIGHT 16 #define WINHEIGHT 24 -#define WINWIDTH (scr_width) +#define WINWIDTH 1024 #define FONT_NAME "-*-lucida*-m*-r-*-*-12-*-*" /* don't edit these */ @@ -47,7 +56,8 @@ int scr_width; int scr_height; int text_y; -/*int time_width;*/ + +#define time_width (35) unsigned short cols[] = { 0xd75c, 0xd75c, 0xd75c, /* 0. light gray */ @@ -145,7 +155,7 @@ mk = XCreatePixmap (dd, tk->win, ICONWIDTH, ICONHEIGHT, 1); gcv.subwindow_mode = IncludeInferiors; gcv.graphics_exposures = False; - mgc = XCreateGC (dd, mk, GCGraphicsExposures | GCSubwindowMode, &gcv); + mgc = XCreateGC (dd, mk, GCGraphicsExposures|GCSubwindowMode, &gcv); } set_foreground (3); @@ -337,20 +347,19 @@ att.background_pixel = palette[0]; att.event_mask = ButtonPressMask | ExposureMask; - win = XCreateWindow ( - /* display */ dd, - /* parent */ root_win, - /* x */ 0, - /* y */ scr_height - WINHEIGHT, - /* width */ WINWIDTH, - /* height */ WINHEIGHT, - /* border */ 0, - /* depth */ CopyFromParent, - /* class */ InputOutput, - /* visual */ CopyFromParent, - /*value mask*/ CWBackPixel | CWEventMask, - /* attribs */ &att); - + win = XCreateWindow (/* display */ dd, + /* parent */ root_win, + /* x */ 0, + /* y */ scr_height - WINHEIGHT, + /* width */ WINWIDTH, + /* height */ WINHEIGHT, + /* border */ 0, + /* depth */ CopyFromParent, + /* class */ InputOutput, + /* visual */ CopyFromParent, + /*value mask*/ CWBackPixel | CWEventMask, + /* attribs */ &att); + /* don't let any windows cover fspanel */ set_prop (win, atom__WIN_LAYER, 10); /* WIN_LAYER_ABOVE_DOCK */ @@ -422,8 +431,6 @@ } while (!xfs); - /*time_width = XTextWidth (xfs, "88:88", 5); */ -#define time_width (35) text_y = xfs->ascent + ((WINHEIGHT - xfs->ascent) / 2); gcv.font = xfs->fid; @@ -539,7 +546,6 @@ gui_draw_vline (tb, x); x += TEXTPAD; -/*set_foreground (3); *//* white *//* it's already 3 from gui_draw_vline() */ draw_line (tb, x + 1, WINHEIGHT - 2, old_x + width - TEXTPAD, WINHEIGHT - 2); draw_line (tb, old_x + width - TEXTPAD, 2, old_x + width - TEXTPAD, @@ -557,6 +563,71 @@ time_str, 5); } +#ifdef PROCAPM +int +read_apm(int *blevel, int *bac, int *btime) +{ + FILE *battery; + int i, ret; + char b[20]; + + ret = 1; + battery = fopen (PROCAPM, "r"); + if (battery == NULL) + ret = 0; + else + { + fscanf(battery, "%s %s %s %x %s %x %d%% %d %s", + b, b, b, bac, b, &i, blevel, btime, b); + /* 1.16 1.2 0x03 0x01 0x00 0x01 99% 123 min */ + fclose (battery); + + /* + * Bit 7 is set if we have a battery (laptop). If it isn't set, + * (desktop) then we don't want to display the battery. + */ + if ((i & 0x80) != 0) + ret = 0; + } + return ret; +} + +void +gui_draw_apm (taskbar * tb) +{ + char apm_str[3]; + int blevel=0, bac=0, btime=0; + int width, old_x, x = WINWIDTH - time_width - apm_width - (TEXTPAD * 8); + + if( read_apm( &blevel, &bac, &btime) ) + { + sprintf(apm_str,"%02d%%",blevel); + + old_x = x; + width = WINWIDTH - x - time_width - apm_width - 2; + + gui_draw_vline (tb, x); + x += TEXTPAD; + + draw_line (tb, x + 1, WINHEIGHT - 2, old_x + width - TEXTPAD, + WINHEIGHT - 2); + draw_line (tb, old_x + width - TEXTPAD, 2, old_x + width - TEXTPAD, + WINHEIGHT - 2); + + set_foreground (bac ? 1 : 5); /* mid gray if on AC, pale red if OFF */ + fill_rect (tb, x + 1, 2, width - (TEXTPAD * 2) - 1, WINHEIGHT - 4); + + set_foreground (4); /* dark gray */ + draw_line (tb, x, 2, x + width - (TEXTPAD * 2) - 1, 2); + draw_line (tb, x, 2, x, WINHEIGHT - 2); + + set_foreground (bac ? 5 : 1); + XDrawString (dd, tb->win, fore_gc, x + TEXTPAD - 1, text_y, + apm_str, 3); + } +} +#endif + void draw_dot (Window win, int x, int y) { @@ -578,23 +649,6 @@ } } -void -draw_up_triangle (taskbar *tb) -{ - fill_rect (tb, left_arrow_x + 2, (WINHEIGHT - 4) / 2 + 1, 3, 3); - draw_line (tb, left_arrow_x, (WINHEIGHT - 4) / 2 + 3, left_arrow_x + 3, (WINHEIGHT - 4) / 2); - draw_line (tb, left_arrow_x + 3, (WINHEIGHT - 4) / 2, left_arrow_x + 6, (WINHEIGHT - 4) / 2 + 3); - draw_line (tb, left_arrow_x + 1, (WINHEIGHT - 4) / 2 + 3, left_arrow_x + 5, (WINHEIGHT - 4) / 2 + 3); -} - -void -draw_down_triangle (taskbar *tb) -{ - draw_line (tb, right_arrow_x, (WINHEIGHT - 4) / 2, right_arrow_x + 3, (WINHEIGHT - 4) / 2 + 3); - draw_line (tb, right_arrow_x, (WINHEIGHT - 4) / 2, right_arrow_x + 4, (WINHEIGHT - 4) / 2 + 2); - draw_line (tb, right_arrow_x, (WINHEIGHT - 4) / 2, right_arrow_x + 5, (WINHEIGHT - 4) / 2 + 1); - draw_line (tb, right_arrow_x, (WINHEIGHT - 4) / 2, right_arrow_x + 6, (WINHEIGHT - 4) / 2); -} void gui_draw_taskbar (taskbar * tb) @@ -604,11 +658,9 @@ int under = 0; set_foreground (5); /* black */ - draw_up_triangle (tb); - draw_down_triangle (tb); - width = WINWIDTH - 80 - time_width - (TEXTPAD * 4); - x = 80; + width = WINWIDTH - time_width - apm_width - (TEXTPAD * 8); + x = 0; if (tb->num_tasks == 0) goto clear; @@ -639,11 +691,10 @@ } gui_draw_clock (tb); + #ifdef PROCAPM + gui_draw_apm (tb); + #endif - gui_draw_vline (tb, 8); - gui_draw_vline (tb, 74); - - draw_grill (tb->win, 2); draw_grill (tb->win, WINWIDTH - 6); } @@ -990,7 +1041,12 @@ FD_ZERO (&fd); FD_SET (xfd, &fd); if (select (xfd + 1, &fd, 0, 0, &tv) == 0) - gui_draw_clock (tb); + { + gui_draw_clock (tb); + #ifdef PROCAPM + gui_draw_apm (tb); + #endif + } while (XPending (dd)) {