sminez / penrose

A library for writing an X11 tiling window manager
https://sminez.github.io/penrose/
MIT License
1.24k stars 87 forks source link

Windows not drawing at correct location when using borders #246

Closed epicgamer256705 closed 1 year ago

epicgamer256705 commented 1 year ago

Describe the bug

When you have borders around the windows, it draws the window a couple of pixels down and to the right. For example, if you have 5px gaps and a 2px border with one window opened it will not be centered.

Expected behavior

It should correct the window position so that the border will not make it in the wrong position.

Versions & OS Details

arch linux git commit: 37d0fbdcff39eed2a7f7bcff7c16bb5013cae26c

Additional context

Example main.rs:

//! penrose :: minimal configuration
//!
//! This file will give you a functional if incredibly minimal window manager that
//! has multiple workspaces and simple client / workspace movement.
use penrose::{
    builtin::{
        actions::{exit, modify_with, send_layout_message, spawn},
        layout::messages::{ExpandMain, IncMain, ShrinkMain},
    },
    core::{
        bindings::{parse_keybindings_with_xmodmap, KeyEventHandler},
        Config, WindowManager,
    },
    map,
    x11rb::RustConn,
    Result,
};
use std::collections::HashMap;

fn raw_key_bindings() -> HashMap<String, Box<dyn KeyEventHandler<RustConn>>> {
    let mut raw_bindings = map! {
        map_keys: |k: &str| k.to_string();

        "M-j" => modify_with(|cs| cs.focus_down()),
        "M-k" => modify_with(|cs| cs.focus_up()),
        "M-S-j" => modify_with(|cs| cs.swap_down()),
        "M-S-k" => modify_with(|cs| cs.swap_up()),
        "M-S-q" => modify_with(|cs| cs.kill_focused()),
        "M-Tab" => modify_with(|cs| cs.toggle_tag()),
        "M-bracketright" => modify_with(|cs| cs.next_screen()),
        "M-bracketleft" => modify_with(|cs| cs.previous_screen()),
        "M-grave" => modify_with(|cs| cs.next_layout()),
        "M-S-grave" => modify_with(|cs| cs.previous_layout()),
        "M-S-Up" => send_layout_message(|| IncMain(1)),
        "M-S-Down" => send_layout_message(|| IncMain(-1)),
        "M-S-Right" => send_layout_message(|| ExpandMain),
        "M-S-Left" => send_layout_message(|| ShrinkMain),
        "M-semicolon" => spawn("dmenu_run"),
        "M-Return" => spawn("st"),
        "M-A-Escape" => exit(),
    };

    for tag in &["1", "2", "3", "4", "5", "6", "7", "8", "9"] {
        raw_bindings.extend([
            (
                format!("M-{tag}"),
                modify_with(move |client_set| client_set.focus_tag(tag)),
            ),
            (
                format!("M-S-{tag}"),
                modify_with(move |client_set| client_set.move_focused_to_tag(tag)),
            ),
        ]);
    }

    raw_bindings
}

fn main() -> Result<()> {
    let config = Config {
        border_width: 5,
        ..Config::default()
    };

    let conn = RustConn::new()?;
    let key_bindings = parse_keybindings_with_xmodmap(raw_key_bindings())?;
    let wm = WindowManager::new(config, key_bindings, HashMap::new(), conn)?;

    wm.run()
}
sminez commented 1 year ago

The config you have provided only specifies a 5px border and no gaps, unlike your bug description (5px gap and 2px border). You're definitely going to get some odd behaviour if you tile windows directly against one another and set a border of 5px I think.

Are you able to provide a screenshot of the problem please? I'm not sure I understand but it sounds like I would expect: gaps offset the window down and to the right and then the border is applied around the window. Are you saying that the border is displaced from the window itself?

sminez commented 1 year ago

ah ok, I've run the example you provided now and I can see the issue: the size of windows wasn't being shrunk to account for the border frame being drawn. That should be fixed now following the commit shown above.