You are not logged in.

#1 2009-04-25 11:38:35

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Bare Window Manager (ex-MMWM)

Working at this for a day now.
Basically it's a full screen window manager aimed to those who spend their day cycling through windows instead of having 10 onscreen at a time. It's a dumbed down version of Ratpoison's default behaviour (really dumbed down..I don't expect anyone to use it as a fulltime WM anytime soon).
For people who only use GNU Screen, Firefox  and/or Emacs all day long(like me), it could prove quite useful.
Not sure if this will ever have any type of tiling..I might make it work with some predefined layouts but not sure.
For now I'm concentrating on cleaning it a bit, adding window by number selection(right now you can only cycle through them with MOD+Tab) and I need to get it to ignore DOCK type applications(eg trays and whatnot).
Also a messaging system of some sort is a must.

So far it has keys to:
- pop a new terminal
- kill selected window
- cycle through windows
- pop a launcher menu (using dmenu by default)
- show a list of windows (working, but needs some enhancement)

Configurable options:
- launcher menu to run
- terminal to run
- font
- window list fg/bg color/selected window fg color/
- screen padding(how much space to leave unmanaged on all sides of the screen - you can see a 16 pixel gap on top of the screenie)
- window list position (one of the four corners)
Will post code as soon as I think it deserves sharing, for now here's a little "teaser"
tMWtzZA

Last edited by Wra!th (2009-05-29 05:53:02)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#2 2009-04-25 11:42:40

fogobogo
Member
Registered: 2008-08-24
Posts: 83

Re: Bare Window Manager (ex-MMWM)

do want!

Offline

#3 2009-04-25 12:03:21

mikesd
Member
From: Australia
Registered: 2008-02-01
Posts: 788
Website

Re: Bare Window Manager (ex-MMWM)

Nice!

Perhaps this could be a good WM for netbooks. Looking forward to seeing the code and having a play with it.

Offline

#4 2009-04-25 12:13:44

yasen
Member
From: Bulgaria
Registered: 2009-03-05
Posts: 39

Re: Bare Window Manager (ex-MMWM)

It has been done before. smile

Check out AntiWM. It's like Screen for X Windows - only maximized windows between which you cycle with keybindings.

Offline

#5 2009-04-25 12:16:49

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

yasen wrote:

It has been done before. smile

Check out AntiWM. It's like Screen for X Windows - only maximized windows between which you cycle with keybindings.

Yes it has been done before. But what is your point? smile
Also Antiwm lacks some of the features I have in mine.

Last edited by Wra!th (2009-04-25 12:20:11)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#6 2009-04-25 15:32:05

yasen
Member
From: Bulgaria
Registered: 2009-03-05
Posts: 39

Re: Bare Window Manager (ex-MMWM)

Wra!th wrote:
yasen wrote:

It has been done before. smile

Yes it has been done before. But what is your point? smile

I'm sorry if it came out looking as criticism. I was just mentioning it.

Did you base it  off something or is it written from scratch?

Offline

#7 2009-04-25 16:01:02

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

It's written from scratch (I did reuse some, not a lot, of my old code...but that was written from scratch so shouldn't matter).

edit:
Ok cleaned the code a bit, re-did the whole window management part (listing and all), and added selection by number.
Only problem is that this way I can only select 10 windows (obviouslly), so I need to write some sort of "input mode" (which would be useful anyway if I decide to expand and add commands etc)
Hopefully it's done by tomorrow so I can post code smile

Last edited by Wra!th (2009-04-25 16:21:00)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#8 2009-04-25 16:34:15

haxit
Member
From: /home/haxit
Registered: 2008-03-04
Posts: 1,247
Website

Re: Bare Window Manager (ex-MMWM)

Looks sick. Can I please have your .screenrc?


Archi686 User | Old Screenshots | Old .Configs
Vi veri universum vivus vici.

Offline

#9 2009-04-25 17:08:36

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

haxit wrote:

Looks sick. Can I please have your .screenrc?

sure

escape ^aa 
startup_message off
vbell on
msgwait 2
defscrollback 5000
defutf8 on
shell bash
shelltitle "$ |term"

caption always "%{= y}"
hardstatus alwayslastline '%{= B}[ %{= W}%H%{= B} ] %= %{= w}%?%-Lw%?%{B}( %{W}%n*%f%t%?(%u)%?%{B} )%{w}%?%+Lw%?%?%= %{B}[ %{= W}%C %A%{= B} ]'

screen -t "rtorrent"    0 bash
screen -t "irssi"    1 bash
screen -t "term"    2 bash

MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#10 2009-04-26 09:15:08

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

tMWt5bw

http://omploader.org/vMWt5Zw

Last edited by Wra!th (2009-04-26 09:17:04)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#11 2009-04-26 14:23:11

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

Getting closer to a release
After A LOT of rewriting, I now have:

- removed cycle windows function
- added prev/next window selection
- added window selection by number (a keybinding enters selection mode, where you type the window number and hit enter)
- all keybindings and options are now configurable using conf.h, which looks something like this

#ifndef CONF_H
#define CONF_H

#define MOD_MASK     Mod4Mask /* Modifier key */
#define KEY_WINLIST    'w'       /* key to show window list */
#define KEY_SELECT    's'     /* key to spawn window selection input */
#define KEY_TERMINAL     't' /* key to spawn terminal */
#define KEY_KILL    'q' /* key to kill selected window */
#define KEY_MENU     'm' /* key to spawn menu */
#define KEY_PREV    'p' /* select previous window in list */
#define KEY_NEXT    'n' /* select next window in list */
#define TERMINAL    "urxvt -display :1" /* terminal */
#define MENU        "`dmenu_path | dmenu -fn '-xos4-terminus-*-r-*-*-12-*-*-*-*-*-*-*' -nb '#222222' -nf '#FFFFFF' -sf '#ffffff' -sb '#666666'`"
/* launcher menu to run */
#define FONT        "-xos4-terminus-*-*-*-*-12-*-*-*-*-*-*-*"
/* font to use */
#define FGCOLOR        "Grey90" /* window list and input window foreground color */
#define BGCOLOR        "#191919" /* window list and input window background color */
#define SELFGCOLOR    "#454545" /* window list background for selected window */
#define PADDING_NORTH    0 /* top screen edge unmanaged pixels */
#define PADDING_WEST    0 /* left screen edge unmanaged pixels */
#define PADDING_SOUTH    0 /* bottom screen edge unmanaged pixels */
#define PADDING_EAST    0 /* right screen edge unmanaged pixels */
#define INPUTPADDING    5 /* space around input area in the input window */
#define WLISTPADDING    5 /* left and right space in window list */
#define WLISTPOS    4 /* 0 = NW, 1 = NE, 2 = SE, 3 = SW, 4 = C*/
#define TIMEOUT        1

#endif

Last edited by Wra!th (2009-04-26 14:25:00)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#12 2009-04-26 15:06:31

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

And a first release.
I'm still working hard on this so let me know what bugs you find etc.
I agree this can't compete to any WM's on the "market" but I enjoy working on it, and I use it as I type.
I changed a lot from the first draft so at places I may have forgotten to clean stuff up, working on that now.
Also writing a "normal" window killing routine..right now it's really violent.
keys:
MOD is Mod4 (left windows key) by default
MOD + t - spawn terminal
MOD + w - window list
MOD + s - enter select window by number mode
MOD + q - kill window
MOD + m - spawn dmenu
MOD + p - select previous window
MOD + n - select next window

mmwm.c

#include <stdarg.h>
#include <stdio.h>
#include <string.h>
#include <X11/keysym.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <unistd.h>
#include <errno.h>
#include <stdlib.h>
#include "conf.h"

#define DEBUG 0

Display         * display;
Window             root;
Screen             *screen;
int             SCREEN_WIDTH;
int             SCREEN_HEIGHT;
GC             MMWM_GC, MMWM_SELECTED_GC;
Colormap         MMWM_colormap = None;
XFontStruct  * fontstruct;

Bool input = False;
Window input_window;
static char input_text[256];
#define max_windows 999 
Window windows_container[max_windows];
Window selected;
char window_select_prompt[] = "Jump to window - ";


void main_loop();
GC MMWM_Colors(char *FG, char *BG);
void handle_keypress_event(XEvent *e);
void handle_maprequest_event(XEvent *e);
void handle_configure_event(XEvent *e);
void handle_destroy_event(XEvent *e);
void handle_expose_event(XEvent *e);
int handle_x_error(Display *display, XErrorEvent *e);
void handle_property_event(XEvent *e);
int init_gc();
void spawn(const char *cmd);
ulong name2color(const char *id);
void LOG(const char *text, ...);
void LOG_DEBUG(const char *text, ...);
void list_windows();
int get_free_position();
int free_position(Window window);
int get_position(Window window);
int select_window(int window);
void grab_keyboard();
int get_prev_window();
int get_next_window();

void LOG(const char *text, ...)
{
    va_list vl;
    va_start(vl, text);
    vfprintf(stderr, text, vl);
    va_end(vl);
}

void LOG_DEBUG(const char *text, ...)
{
    if(DEBUG == 1){
        va_list vl;
        va_start(vl, text);
        vfprintf(stderr, text, vl);
        va_end(vl);
    }
}

void spawn(const char *cmd)
{
    if(fork() == 0) {
        if(display) close(ConnectionNumber(display));
        setsid();
        execl("/bin/sh", "/bin/sh", "-c", cmd, (char *)NULL);
    }
}

int TextWidth(XFontStruct *fs, const char *text)
{
    if(strlen(text) >= 1 && text != NULL) {
        return XTextWidth(fs, text, strlen(text));
    } else {
        return 1;
    }
}

int TextHeight(XFontStruct *fs) {
    return fs->ascent + fs->descent;
}

ulong name2color(const char *cid)
{
    XColor tmpcol;

    if(!XParseColor(display, MMWM_colormap, cid, &tmpcol)) {
        LOG("Cannot allocate \"%s\" color. Defaulting to black!\n", cid);
        return BlackPixel(display, XDefaultScreen(display));
    }
    if(!XAllocColor(display, MMWM_colormap, &tmpcol)) {
        LOG("Cannot allocate \"%s\" color. Defaulting to black!\n", cid);
        return BlackPixel(display, XDefaultScreen(display));
    }
    
    return tmpcol.pixel;
}

int init_gc()
{
    XGCValues gcv;
       gcv.font = fontstruct->fid;
       gcv.foreground = name2color(FGCOLOR);
       gcv.background = name2color(BGCOLOR);
       gcv.function = GXcopy;
       gcv.subwindow_mode = IncludeInferiors;
       gcv.line_width = 1;
       MMWM_GC = XCreateGC(display, root, GCForeground | GCBackground | GCFunction | GCLineWidth | GCSubwindowMode | GCFont, &gcv);
       gcv.foreground = name2color(SELFGCOLOR);
       MMWM_SELECTED_GC = XCreateGC(display, root, GCForeground | GCBackground | GCFunction | GCLineWidth | GCSubwindowMode | GCFont, &gcv);
    
    return 0;
}
int get_prev_window()
{
    int x;
    for(x = get_position(selected) - 1; x >= 0; x--)
    {
        if(windows_container[x] != None)
        {
            LOG_DEBUG("Found previous window at: %d\n", x);
            return x;
        }
    }

    return -1;
}
int get_next_window()
{
    int x;
    for(x = get_position(selected) + 1; x < max_windows; x++)
    {
        if(windows_container[x] != None)
        {
            LOG_DEBUG("Found next window at: %d\n", x);
            return x;
        }
    }

    return -1;
}
void grab_keyboard()
{
      XGrabKey(display, XKeysymToKeycode (display, KEY_WINLIST), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
      XGrabKey(display, XKeysymToKeycode (display, KEY_SELECT), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
      XGrabKey(display, XKeysymToKeycode (display, KEY_TERMINAL), MOD_MASK, root, True,GrabModeAsync, GrabModeAsync);
      XGrabKey(display, XKeysymToKeycode (display, KEY_KILL), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
      XGrabKey(display, XKeysymToKeycode (display, KEY_MENU), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
    XGrabKey(display, XKeysymToKeycode (display, KEY_NEXT), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
    XGrabKey(display, XKeysymToKeycode (display, KEY_PREV), MOD_MASK, root, True, GrabModeAsync, GrabModeAsync);
}

void create_input_box()
{
    char tmp[256];
    sprintf(tmp, "%s   ", window_select_prompt);
    input_window = XCreateSimpleWindow(display, root, 0,  0, TextWidth(fontstruct, tmp) + (INPUTPADDING *2), TextHeight(fontstruct) + INPUTPADDING, 0, name2color(FGCOLOR), name2color(BGCOLOR));
    XMapWindow(display, input_window);
    XDrawString(display, input_window, MMWM_GC, INPUTPADDING , 0 + TextHeight(fontstruct) - fontstruct->max_bounds.descent + (INPUTPADDING / 2), window_select_prompt, strlen(window_select_prompt));
    XGrabKey(display, AnyKey, AnyModifier, root, True, GrabModeAsync, GrabModeAsync);
}
void update_input_box()
{
    XClearWindow(display, input_window);
    XDrawString(display, input_window, MMWM_GC, INPUTPADDING , 0 + TextHeight(fontstruct) - fontstruct->max_bounds.descent + (INPUTPADDING / 2), window_select_prompt, strlen(window_select_prompt));
    XDrawString(display, input_window, MMWM_GC, INPUTPADDING + TextWidth(fontstruct, window_select_prompt), 0 + TextHeight(fontstruct) - fontstruct->max_bounds.descent + (INPUTPADDING / 2), input_text, strlen(input_text));
}
void handle_keypress_event(XEvent * e)
{
    XKeyEvent keyevent = e->xkey;
    KeySym key = XKeycodeToKeysym(display, keyevent.keycode, 0);
    KeySym ksym;
    char tmp[32];
    int count, input_length;

    if(!input)
    {
        switch (XLookupKeysym(&keyevent, 0))
        {
        case KEY_SELECT:
            input = True;
            create_input_box();
            break;
        case KEY_TERMINAL:
            spawn(TERMINAL);
            break;
        case KEY_MENU:
            spawn(MENU);
            break;
        case KEY_WINLIST:
            if(TIMEOUT > 0)
            {
                list_windows();
            }            
            break;
        case KEY_KILL:
            XDestroyWindow(display, selected);
            break;
        case KEY_PREV:
            select_window(get_prev_window());
            break;
        case KEY_NEXT:
            select_window(get_next_window());
            break;
        }
    } else {
        if(key == XK_Return || key == XK_KP_Enter)
        {
            if(atoi(input_text) || atoi(input_text) == 0) select_window(atoi(input_text));
            input = False;
            input_text[0] = 0;
            XDestroyWindow(display, input_window);
            XUngrabKey(display, AnyKey, AnyModifier, root);
            grab_keyboard();
            return;
        }
        input_length = strlen(input_text);
        if(key != XK_BackSpace && key != XK_Delete && key != XK_KP_Delete)
        {
            if(input_length < 3)
            {
                tmp[0] = 0;
                count = XLookupString(&e->xkey, tmp, sizeof(tmp), &ksym, NULL);
                tmp[count] = 0;
                strncpy(input_text + input_length, tmp, sizeof(input_text) - input_length);
                update_input_box();
            }
        } else {
            if(input_length > 0)
            {
                input_text[strlen(input_text) - 1] = 0;
                update_input_box();
            }    
        }
    }
}

void list_windows()
{
    int th,ypos;
        th = TextHeight(fontstruct);
    ypos = 0 + th - fontstruct->max_bounds.descent;
    Window WINDOW_LIST_WINDOW = None;
    char *tmp;
    char title[256];
    int x;
    int number = 0;
    int max_title = 0;
    XWindowAttributes winattr;
    Window root_return;
    int char_width = TextWidth(fontstruct, " ");
     for (x = 0; x< max_windows; x++)
    {
        if(windows_container[x] != None)
        {
            if(!XGetWindowAttributes(display, windows_container[x], &winattr) || winattr.override_redirect || XGetTransientForHint(display, windows_container[x], &root_return)) continue;
                if(winattr.map_state == IsViewable)
                {
                    if(XFetchName(display, windows_container[x], &tmp))
                    {
                        number++;
                        if(windows_container[x] == selected)
                        {    
                            sprintf(title, "%d - %s", get_position(windows_container[x]), tmp);
                        } else {
                            sprintf(title, "%d - %s", get_position(windows_container[x]), tmp);
                        }
                        if(strlen(title) > max_title) max_title = strlen(title);
                        title[0] = 0;    
                    }
                }
            }
        }
        int win_width = max_title * char_width + WLISTPADDING*2;
        switch(WLISTPOS)
        {
            case 0:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, PADDING_WEST,  PADDING_NORTH, win_width, number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
            case 1:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, 0 + SCREEN_WIDTH - PADDING_EAST - win_width,  PADDING_NORTH, win_width, number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
            case 2:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, 0 + SCREEN_WIDTH - PADDING_EAST - win_width,  0 + SCREEN_HEIGHT - PADDING_SOUTH - (number * th),win_width,number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
            case 3:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, PADDING_WEST,  0 + SCREEN_HEIGHT - PADDING_SOUTH - (number * th),win_width,number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
            case 4:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, (SCREEN_WIDTH / 2) - (win_width / 2),  (SCREEN_HEIGHT / 2) - ((number * th) / 2),win_width,number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
            default:
                WINDOW_LIST_WINDOW = XCreateSimpleWindow(display, root, PADDING_WEST,  PADDING_NORTH, win_width, number * th, 0, name2color(FGCOLOR), name2color(BGCOLOR));
                break;
        }
        XMapRaised(display, WINDOW_LIST_WINDOW);

        for (x = 0; x< max_windows; x++)
        {
            if(windows_container[x] != None)
            {
                if(!XGetWindowAttributes(display, windows_container[x], &winattr) || winattr.override_redirect || XGetTransientForHint(display, windows_container[x], &root_return)) continue;
                    if(winattr.map_state == IsViewable)
                    {
                        if(XFetchName(display, windows_container[x], &tmp))
                        {
                            if(windows_container[x] == selected)
                            {
                                sprintf(title, "%d - %s", get_position(windows_container[x]), tmp);
                                XFillRectangle(display, WINDOW_LIST_WINDOW, MMWM_SELECTED_GC, 0, ypos - th  + fontstruct->max_bounds.descent, win_width, th);
                                XDrawString(display, WINDOW_LIST_WINDOW, MMWM_GC, WLISTPADDING, ypos, title, strlen(title));
                                ypos+=th;
                            } else {
                                sprintf(title, "%d - %s", get_position(windows_container[x]), tmp);
                                XDrawString(display, WINDOW_LIST_WINDOW, MMWM_GC, WLISTPADDING, ypos, title, strlen(title));
                                ypos+=th;
                            }
                            title[0] = 0;
                        }
                    }

            }
        }
        XFlush(display);
        sleep(TIMEOUT);
        XFlush(display);
        if(WINDOW_LIST_WINDOW)
        {
            XDestroyWindow(display, WINDOW_LIST_WINDOW);
        }
}
int select_window(int window)
{
    if(windows_container[window] != None)
    {
        LOG_DEBUG("Selecting window at position: %d\n", window);
        XRaiseWindow(display, windows_container[window]);
        XSetInputFocus(display, windows_container[window], RevertToParent, CurrentTime);
        selected = windows_container[window];
        return 0;
    } else {
        return -1;
    }
}

int get_free_position()
{
    int x;
    for(x = 0; x < max_windows; x++)
    {
        if(windows_container[x] == None)
        {
            LOG_DEBUG("Asigning position: %d\n", x);
            return x;
        }
    }
    return -1;
}
int get_position(Window window)
{
    int x;
    for(x = 0; x < max_windows; x++)
    {
        if(windows_container[x] == window)
        {
            LOG_DEBUG("Window has position: %d\n", x);
            return x;
        }
    }
    return -1;
}

int free_position(Window window)
{
    int x;
    for(x = 0; x < max_windows; x++)
    {
        if(windows_container[x] == window)
        {
            LOG_DEBUG("Freeing position: %d\n", x);
            windows_container[x] = None;
        }
    }
    return 1;
}

void handle_maprequest_event(XEvent *e)
{
    XMapWindow(display, e->xmaprequest.window);
    XMoveResizeWindow(display, e->xmaprequest.window, PADDING_WEST, PADDING_NORTH, SCREEN_WIDTH - PADDING_WEST - PADDING_EAST, SCREEN_HEIGHT - PADDING_NORTH - PADDING_SOUTH);
    XRaiseWindow(display, e->xmaprequest.window);
    XSetInputFocus(display, e->xmaprequest.window,RevertToParent, CurrentTime);
    selected = e->xmaprequest.window;
    windows_container[get_free_position()] = selected;
}

void handle_destroy_event(XEvent *e)
{
    free_position(e->xdestroywindow.window);
    XDestroyWindow(display, e->xdestroywindow.window);
}


void handle_configure_event(XEvent *e)
{
      e->xconfigurerequest.type = ConfigureNotify;
      e->xconfigurerequest.x = 0;
      e->xconfigurerequest.y = 0;
      e->xconfigurerequest.width = SCREEN_WIDTH;
      e->xconfigurerequest.height = SCREEN_HEIGHT;
      e->xconfigurerequest.window = e->xconfigure.window;
      e->xconfigurerequest.border_width = 0;      
      e->xconfigurerequest.above = None;
      XSendEvent(display, e->xconfigurerequest.window, False, StructureNotifyMask, (XEvent*)&e->xconfigurerequest);
}

void handle_expose_event(XEvent *e)
{
    // Redraw stuff in here...window title etc
    // Not handled yet but I'ma add it here for future dev
}

void handle_property_event(XEvent *e)
{
    // In case properties like name etc change ... handle them in here
    // Not handled yet but I'ma add it here for future dev
}

int handle_x_error(Display *display, XErrorEvent *e)
{
    LOG_DEBUG("Xevent error: %d\n", e->error_code);
    LOG_DEBUG("Operation: %d\n", e->request_code);
    LOG_DEBUG("Resource: %lu (0x%lx)\n", e->resourceid, e->resourceid);
    return 0;
}

void main_loop()
{
    XEvent event;
    XSetErrorHandler(handle_x_error); //Ignore X errors otherwise the WM would crash every other minute :)
    while(1){
               XNextEvent(display, &event);
               switch(event.type){
        case KeyPress:
            handle_keypress_event(&event);
            break;
        case MapRequest:
            handle_maprequest_event(&event);
            break;
        case DestroyNotify: 
            handle_destroy_event(&event);
            break;
        case ConfigureNotify: 
            handle_configure_event(&event);
            break;
        case Expose: 
            handle_expose_event(&event);
            break;
        case PropertyNotify:
            handle_property_event(&event);
            break;
        default:
            LOG_DEBUG("Received an unhandled event:  %d\n", event.type);
            break;
            }
    }
}

int main(int argc, char *argv[])
{
    if(!(display = XOpenDisplay(DISPLAY))){
        LOG("MMWM: cannot open display! Ending session.\n");
        return -1;
    }

    if((root = DefaultRootWindow(display)))
    {
        XSetWindowBackground(display, root, BlackPixel(display, XDefaultScreen(display)));
        XClearWindow(display, root);
    } else {
        LOG("MMWM: cannot get root window! Ending session.\n");
        return -1;
    }
    if((screen = DefaultScreenOfDisplay(display)))
    {
        SCREEN_WIDTH     = XWidthOfScreen(screen);
        SCREEN_HEIGHT     = XHeightOfScreen(screen);
        LOG("Screen: %d x %d\n", SCREEN_WIDTH, SCREEN_HEIGHT);
    } else {
        LOG("MMWM: cannot get screen! Ending session.\n");
        return -1;    
    }
    fontstruct = XLoadQueryFont(display, FONT);
    if (!fontstruct) {
        LOG("Couldn't find font \"%s\", loading default\n", FONT);
        fontstruct = XLoadQueryFont(display, "-*-fixed-medium-r-*-*-12-*-*-*-*-*-iso8859-1");
        if (!fontstruct) {
            LOG("Couldn't load default fixed font. Something is seriouslly wrong. Ending session.\n");
            return -1;        
        }

    }
    grab_keyboard();    
    XSelectInput(display, root, SubstructureNotifyMask | SubstructureRedirectMask ); 

    MMWM_colormap = DefaultColormap(display, 0);
    init_gc();
    main_loop();

    XFree(MMWM_GC);
    XFree(MMWM_SELECTED_GC);
    XCloseDisplay(display);
    return 0;
}

conf.h

#ifndef CONF_H
#define CONF_H
#define DISPLAY        ":0"
#define MOD_MASK     Mod4Mask /* Modifier key */
#define KEY_WINLIST    'w'       /* key to show window list */
#define KEY_SELECT    's'     /* key to spawn window selection input */
#define KEY_TERMINAL     't' /* key to spawn terminal */
#define KEY_KILL    'q' /* key to kill selected window */
#define KEY_MENU     'm' /* key to spawn menu */
#define KEY_PREV    'p' /* select previous window in list */
#define KEY_NEXT    'n' /* select next window in list */
#define TERMINAL    "urxvt" /* terminal */
#define MENU        "`dmenu_path | dmenu -fn '-xos4-terminus-*-r-*-*-12-*-*-*-*-*-*-*' -nb '#222222' -nf '#FFFFFF' -sf '#ffffff' -sb '#666666'`"
/* launcher menu to run */
#define FONT        "-xos4-terminus-*-*-*-*-12-*-*-*-*-*-*-*"
/* font to use */
#define FGCOLOR        "Grey90" /* window list and input window foreground color */
#define BGCOLOR        "#191919" /* window list and input window background color */
#define SELFGCOLOR    "#454545" /* window list background for selected window */
#define PADDING_NORTH    0 /* top screen edge unmanaged pixels */
#define PADDING_WEST    0 /* left screen edge unmanaged pixels */
#define PADDING_SOUTH    0 /* bottom screen edge unmanaged pixels */
#define PADDING_EAST    0 /* right screen edge unmanaged pixels */
#define INPUTPADDING    5 /* space around input area in the input window */
#define WLISTPADDING    5 /* left and right space in window list */
#define WLISTPOS    1 /* 0 = NW, 1 = NE, 2 = SE, 3 = SW, 4 = C */
#define TIMEOUT        1

#endif

Makefile

PREFIX?=/usr
CFLAGS?=-Os -Wall

all:
    $(CC) $(CFLAGS) -I$(PREFIX)/include -L$(PREFIX)/lib -lX11 -o mmwm mmwm.c
install: mmwm
    install -s mmwm $(PREFIX)/bin
clean:
    rm -f mmwm

Last edited by Wra!th (2009-04-26 15:23:33)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#13 2009-04-26 15:20:17

XFire
Member
From: UK
Registered: 2008-05-11
Posts: 192

Re: Bare Window Manager (ex-MMWM)

From the posted files, do I have to recompile the window manager if I modify the config file?


There is a difference between bleeding [edge] and haemorrhaging. - Allan

Offline

#14 2009-04-26 15:23:50

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

XFire wrote:

From the posted files, do I have to recompile the window manager if I modify the config file?

Yes. The source includes the config at compile time, so you do need to recompile for the changes to take effect (same as dwm, evilwm and a bunch of others)

Last edited by Wra!th (2009-04-26 15:24:48)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#15 2009-04-26 15:24:40

leo2501
Member
From: Buenos Aires, Argentina
Registered: 2007-07-07
Posts: 658

Re: Bare Window Manager (ex-MMWM)

i feel this nice project is something in between dwm and antiwm, isn't it? i like it, when im done trying antiwm i will try this smile


Perfection is achieved, not when there is nothing more to add, but when there is nothing left to take away.
-- Antoine de Saint-Exupery

Offline

#16 2009-04-26 15:25:27

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

leo2501 wrote:

i feel this nice project is something in between dwm and antiwm, isn't it? i like it, when im done trying antiwm i will try this smile

It's actually something like an AntiWM with a bunch of extra features


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#17 2009-04-26 16:21:22

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

Cleaned the window list routine and added a border option
tMWwwbA


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#18 2009-04-26 16:59:51

haxit
Member
From: /home/haxit
Registered: 2008-03-04
Posts: 1,247
Website

Re: Bare Window Manager (ex-MMWM)

Wra!th wrote:
haxit wrote:

Looks sick. Can I please have your .screenrc?

sure

escape ^aa 
startup_message off
vbell on
msgwait 2
defscrollback 5000
defutf8 on
shell bash
shelltitle "$ |term"

caption always "%{= y}"
hardstatus alwayslastline '%{= B}[ %{= W}%H%{= B} ] %= %{= w}%?%-Lw%?%{B}( %{W}%n*%f%t%?(%u)%?%{B} )%{w}%?%+Lw%?%?%= %{B}[ %{= W}%C %A%{= B} ]'

screen -t "rtorrent"    0 bash
screen -t "irssi"    1 bash
screen -t "term"    2 bash

Thanks, its perfect!

Also, its looking awesome. Will you be putting this into git?

Last edited by haxit (2009-04-26 17:01:10)


Archi686 User | Old Screenshots | Old .Configs
Vi veri universum vivus vici.

Offline

#19 2009-04-26 17:04:43

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

haxit wrote:

Thanks, its perfect!

Also, its looking awesome. Will you be putting this into git?

Not sure I wanna mess with that git stuff.


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#20 2009-04-26 21:47:18

leo2501
Member
From: Buenos Aires, Argentina
Registered: 2007-07-07
Posts: 658

Re: Bare Window Manager (ex-MMWM)

Well i try antiwm but it's just to bare to fit my needs, so i wanna try mmwm now smile but what about an AUR PKGBUILD? smile


Perfection is achieved, not when there is nothing more to add, but when there is nothing left to take away.
-- Antoine de Saint-Exupery

Offline

#21 2009-04-27 13:47:53

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

Ok..just so we don't have any more problems with tab conversions and whatnot, latest version is (temporarely) hosted as a tar.gz (thanks to rpaisley of #ratpoison).
http://pub.rpaisley.com/mmwm/mmwm-0.1.tar.gz
Working on an AUR package and will be done as soon as I figure out how to make one(will be my first one). Also pending approval from sourceforge.
This one contains improvements from the first(and last) posted source so grab this one, not the above source.

Last edited by Wra!th (2009-04-27 15:20:58)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#22 2009-04-27 19:13:29

haxit
Member
From: /home/haxit
Registered: 2008-03-04
Posts: 1,247
Website

Re: Bare Window Manager (ex-MMWM)

Wra!th wrote:

Ok..just so we don't have any more problems with tab conversions and whatnot, latest version is (temporarely) hosted as a tar.gz (thanks to rpaisley of #ratpoison).
http://pub.rpaisley.com/mmwm/mmwm-0.1.tar.gz
Working on an AUR package and will be done as soon as I figure out how to make one(will be my first one). Also pending approval from sourceforge.
This one contains improvements from the first(and last) posted source so grab this one, not the above source.

When you make the AUR package, if you don't mind, tell me. I will host it on my repo big_smile Also if you make an AUR for uzbl (dieter guy...), I will host that also.

Last edited by haxit (2009-04-28 19:11:24)


Archi686 User | Old Screenshots | Old .Configs
Vi veri universum vivus vici.

Offline

#23 2009-04-28 14:14:29

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

Changelog:
1. First and most important change: MMWM is now modal (MOD + t enters command mode where you issue the defined bindings)
2. Removed the input to select windows bit, and instead you have 0...9 (in command mode) to select windows 0 through 9 (use next/prev bindings to go beyond 9)
3. Added a messaging system (acceps formatted strings e.g. message("Key \"%c\" is unbound", (char)key); ). Messaging system respects the WLIST variables (positioning, padding, timeout)
4. Added some error checking using the new messaging system (lets you know when you've reached last/first window when using the next/prev bindings). It also lets you know when you try to display the windows list but no open windows (this is only useful if I ever implement window hiding, since at this stage you can tell for yourself if you have an open window or not)

TODO:
1. First thing that comes to mind is to handle the timeout better. Sleep() freezes the wm, so some threading is needed. Not a big issue now but it would be if the timeout is set to like 5 seconds.
2. Window killing...XDestroyWindow is brutal. Need to send client quit events and whatnot

NEWS:
1. Project got approved on sourceforge.net smile. Uploading project there and will provide a link, then create a working PKGBUILD.
2. Project changes name to Bare WM smile

tMWxjOQ
tMWxjYQ

http://pub.rpaisley.com/barewm/barewm-0.2.tar.gz
Link until I set the sourceforge page

Last edited by Wra!th (2009-04-28 15:02:05)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

#24 2009-04-28 19:29:35

HashBox
Member
Registered: 2009-01-22
Posts: 271

Re: Bare Window Manager (ex-MMWM)

Nice work Wra!th, I remember using XDestroyWindow in my toy WM I think, and if you try to close urxvtd/urxvtc it closes all the windows at once if I remember correctly tongue

Offline

#25 2009-04-28 19:52:12

Wra!th
Member
Registered: 2009-03-31
Posts: 342

Re: Bare Window Manager (ex-MMWM)

HashBox wrote:

Nice work Wra!th, I remember using XDestroyWindow in my toy WM I think, and if you try to close urxvtd/urxvtc it closes all the windows at once if I remember correctly tongue

Well it kills everything that was ran from that urxvt, but not other windows. (for example if I have 3 open urxvt's, it just kills the selected one, but it's just too brutal)

edit: and we is on github smile

Last edited by Wra!th (2009-04-28 20:12:46)


MacGregor DESPITE THEM!
7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00

Offline

Board footer

Powered by FluxBB