baskerville / bspwm

A tiling window manager based on binary space partitioning
BSD 2-Clause "Simplified" License
7.73k stars 414 forks source link

bspc rules ignored after starting winit window #1440

Open bolshoytoster opened 1 year ago

bolshoytoster commented 1 year ago

I like to have ffplay windows floating, which looks to be the default, and works perfectly fine most of the time.

Unfortunately, I've found that after starting a winit window (or even firefox in some cases), ffplay windows will open tiled instead, andd I'll have to restart bspwm.

You could reproduce this (with an empty bspwmrc) if you have cargo installed:

$ ffplay '~/something.mp4' # It's floating
^C
$ cargo new winit_test
     Created binary (application) `winit_test` package
$ cd winit_test
$ cargo add winit
    Updating crates.io index
      Adding winit v0.28.1 to dependencies.
             Features:
                         + mio
                         + percent-encoding
                         + sctk
                         + sctk-adwaita
                         + wayland
                         + wayland-client
                         + wayland-commons
                         + wayland-csd-adwaita
                         + wayland-dlopen
                         + wayland-protocols
                         + x11
                         + x11-dl
                         - android-game-activity
                         - android-native-activity
                         - mint
                         - serde
                         - wayland-csd-adwaita-crossfont
                         - wayland-csd-adwaita-notitle
$ # Example from winit's README.md:
$ echo "use winit::{
     event::{Event, WindowEvent},
     event_loop::{ControlFlow, EventLoop},
     window::WindowBuilder,

};

 fn main() {
     let event_loop = EventLoop::new();
     let window = WindowBuilder::new().build(&event_loop).unwrap();

     event_loop.run(move |event, _, control_flow| {
         *control_flow = ControlFlow::Wait;

         match event {
             Event::WindowEvent {
                 event: WindowEvent::CloseRequested,
                 window_id,
             } if window_id == window.id() => *control_flow = ControlFlow::Exit,
             _ => (),
         }
     });
}" > src/main.rs
$ cargo run
   Downloaded wayland-cursor v0.29.5
   Downloaded nom v7.1.3
   Downloaded arrayref v0.3.6
   Downloaded dlib v0.5.0
   Downloaded scoped-tls v1.0.1
   Downloaded sctk-adwaita v0.5.3
   Downloaded memmap2 v0.5.10
   Downloaded wayland-commons v0.29.5
   Downloaded xcursor v0.3.4
   Downloaded strict-num v0.1.0
   Downloaded tiny-skia v0.8.3
   Downloaded tiny-skia-path v0.8.3
   Downloaded wayland-sys v0.29.5
   Downloaded wayland-client v0.29.5
   Downloaded smithay-client-toolkit v0.16.0
   Downloaded wayland-protocols v0.29.5
   Downloaded calloop v0.10.5
   Downloaded minimal-lexical v0.2.1
   Downloaded 18 crates (991.0 KB) in 2.40s
   Compiling proc-macro2 v1.0.51
   Compiling cfg-if v1.0.0
   Compiling quote v1.0.23
   Compiling unicode-ident v1.0.6
   Compiling libc v0.2.139
   Compiling pkg-config v0.3.26
   Compiling autocfg v1.1.0
   Compiling xml-rs v0.8.4
   Compiling bitflags v1.3.2
   Compiling libloading v0.7.4
   Compiling once_cell v1.17.1
   Compiling dlib v0.5.0
   Compiling lazy_static v1.4.0
   Compiling syn v1.0.109
   Compiling memoffset v0.6.5
   Compiling memchr v2.5.0
   Compiling log v0.4.17
   Compiling wayland-sys v0.29.5
   Compiling crc32fast v1.3.2
   Compiling smallvec v1.10.0
   Compiling version_check v0.9.4
   Compiling wayland-scanner v0.29.5
   Compiling thiserror v1.0.38
   Compiling adler v1.0.2
   Compiling slotmap v1.0.6
   Compiling downcast-rs v1.2.0
   Compiling minimal-lexical v0.2.1
   Compiling scoped-tls v1.0.1
   Compiling miniz_oxide v0.6.2
   Compiling nom v7.1.3
   Compiling nix v0.24.3
   Compiling nix v0.25.1
   Compiling flate2 v1.0.25
   Compiling wayland-client v0.29.5
   Compiling wayland-protocols v0.29.5
   Compiling smithay-client-toolkit v0.16.0
   Compiling vec_map v0.8.2
   Compiling bytemuck v1.13.0
   Compiling arrayref v0.3.6
   Compiling ttf-parser v0.18.1
   Compiling strict-num v0.1.0
   Compiling tiny-skia-path v0.8.3
   Compiling wayland-commons v0.29.5
   Compiling xcursor v0.3.4
   Compiling png v0.17.7
   Compiling memmap2 v0.5.10
   Compiling thiserror-impl v1.0.38
   Compiling x11-dl v2.21.0
   Compiling arrayvec v0.7.2
   Compiling cfg_aliases v0.1.1
   Compiling ab_glyph_rasterizer v0.1.8
   Compiling tiny-skia v0.8.3
   Compiling winit v0.28.1
   Compiling cty v0.2.2
   Compiling raw-window-handle v0.5.0
   Compiling owned_ttf_parser v0.18.1
   Compiling wayland-cursor v0.29.5
   Compiling ab_glyph v0.2.20
   Compiling mio v0.8.6
   Compiling calloop v0.10.5
   Compiling instant v0.1.12
   Compiling percent-encoding v2.2.0
   Compiling sctk-adwaita v0.5.3
   Compiling winit_test v0.1.0 (/home/a/projects/winit_test)
    Finished dev [unoptimized + debuginfo] target(s) in 18.85s
     Running `target/debug/winit_test`
^C
$ ffplay ~/something.mp4 # It's tiled now

I've also been able to reproduce this occasionally by running firefox.

matt-mich commented 1 year ago

I can confirm that I'm experiencing the same issue seemingly at random while using Firefox version 110.0

ortango commented 1 year ago

probably a good idea to include the versions of ffplay and bspwm for people trying to reproduce this issue (which i cannot do). also, are you playing the same file before and after running the winit test?

seems curious that you say ffplay should float by default - that is not really the case. you can cause sdl2 to create a fixed size window by starting ffplay with -noborder. might be useful to include the xprop output of the ffplay windows in both states.

bolshoytoster commented 1 year ago

@ortango

probably a good idea to include the versions of ffplay and bspwm for people trying to reproduce this issue

$ ffplay -version
ffplay version 4.4.2-0ubuntu0.22.04.1 Copyright (c) 2003-2021 the FFmpeg developers
built with gcc 11 (Ubuntu 11.2.0-19ubuntu1)
configuration: --prefix=/usr --extra-version=0ubuntu0.22.04.1 --toolchain=hardened --libdir=/usr/lib/x86_64-linux-gnu --incdir=/usr/include/x86_64-linux-gnu --arch=amd64 --enable-gpl --disable-stripping --enable-gnutls --enable-ladspa --enable-libaom --enable-libass --enable-libbluray --enable-libbs2b --enable-libcaca --enable-libcdio --enable-libcodec2 --enable-libdav1d --enable-libflite --enable-libfontconfig --enable-libfreetype --enable-libfribidi --enable-libgme --enable-libgsm --enable-libjack --enable-libmp3lame --enable-libmysofa --enable-libopenjpeg --enable-libopenmpt --enable-libopus --enable-libpulse --enable-librabbitmq --enable-librubberband --enable-libshine --enable-libsnappy --enable-libsoxr --enable-libspeex --enable-libsrt --enable-libssh --enable-libtheora --enable-libtwolame --enable-libvidstab --enable-libvorbis --enable-libvpx --enable-libwebp --enable-libx265 --enable-libxml2 --enable-libxvid --enable-libzimg --enable-libzmq --enable-libzvbi --enable-lv2 --enable-omx --enable-openal --enable-opencl --enable-opengl --enable-sdl2 --enable-pocketsphinx --enable-librsvg --enable-libmfx --enable-libdc1394 --enable-libdrm --enable-libiec61883 --enable-chromaprint --enable-frei0r --enable-libx264 --enable-shared
libavutil      56. 70.100 / 56. 70.100
libavcodec     58.134.100 / 58.134.100
libavformat    58. 76.100 / 58. 76.100
libavdevice    58. 13.100 / 58. 13.100
libavfilter     7.110.100 /  7.110.100
libswscale      5.  9.100 /  5.  9.100
libswresample   3.  9.100 /  3.  9.100
libpostproc    55.  9.100 / 55.  9.100
$ bspwm -v
0.9.10

also, are you playing the same file before and after running the winit test?

Yes, but this occurs with any file for me.

seems curious that you say ffplay should float by default - that is not really the case.

That might be the issue. After running bspc rule -a ffplay state=floating, the window spawns floating.

I still think it's odd that it spawns floating on boot but stops after opening certain windows.

might be useful to include the xprop output of the ffplay windows in both states.

Before (floating):

_NET_WM_USER_TIME(CARDINAL) = 481780
_VARIABLE_REFRESH(CARDINAL) = 1
_NET_WM_DESKTOP(CARDINAL) = 0
WM_STATE(WM_STATE):
                window state: Normal
                icon window: 0x0
XdndAware(ATOM) = BITMAP
_NET_WM_NAME(UTF8_STRING) = "something - something.mp4"
WM_NAME(STRING) = "something - something.mp4"
WM_PROTOCOLS(ATOM): protocols  WM_DELETE_WINDOW, WM_TAKE_FOCUS, _NET_WM_PING
_NET_WM_BYPASS_COMPOSITOR(CARDINAL) = 1
_NET_WM_WINDOW_TYPE(ATOM) = _NET_WM_WINDOW_TYPE_NORMAL
_NET_WM_PID(CARDINAL) = 2593
WM_LOCALE_NAME(STRING) = "C"
WM_CLASS(STRING) = "ffplay", "ffplay"
WM_HINTS(WM_HINTS):
                Client accepts input or input focus: True
                window id # of group leader: 0x243667f1
WM_NORMAL_HINTS(WM_SIZE_HINTS):
                user specified location: 640, 300
WM_CLIENT_MACHINE(STRING) = "0"
WM_TRANSIENT_FOR(WINDOW): window id # 0x79e

After (tiled):

_VARIABLE_REFRESH(CARDINAL) = 1
_NET_WM_DESKTOP(CARDINAL) = 0
WM_STATE(WM_STATE):
                window state: Normal
                icon window: 0x0
XdndAware(ATOM) = BITMAP
_NET_WM_NAME(UTF8_STRING) = "something - something.mp4"
WM_NAME(STRING) = "something - something.mp4"
WM_PROTOCOLS(ATOM): protocols  WM_DELETE_WINDOW, WM_TAKE_FOCUS, _NET_WM_PING
_NET_WM_BYPASS_COMPOSITOR(CARDINAL) = 1
_NET_WM_WINDOW_TYPE(ATOM) = _NET_WM_WINDOW_TYPE_NORMAL
_NET_WM_PID(CARDINAL) = 3205
WM_LOCALE_NAME(STRING) = "C"
WM_CLASS(STRING) = "ffplay", "ffplay"
WM_HINTS(WM_HINTS):
                Client accepts input or input focus: True
                window id # of group leader: 0x5384f155
WM_NORMAL_HINTS(WM_SIZE_HINTS):
                user specified location: 640, 300
WM_CLIENT_MACHINE(STRING) = "0"
_MOTIF_WM_HINTS(_MOTIF_WM_HINTS) = 0x2, 0x0, 0x1, 0x0, 0x0

Diff:

1d0
< _NET_WM_USER_TIME(CARDINAL) = 481780
13c12
< _NET_WM_PID(CARDINAL) = 2593
---
> _NET_WM_PID(CARDINAL) = 3205
18c17
<                 window id # of group leader: 0x243667f1
---
>                 window id # of group leader: 0x5384f155
22c21
< WM_TRANSIENT_FOR(WINDOW): window id # 0x79e
---
> _MOTIF_WM_HINTS(_MOTIF_WM_HINTS) = 0x2, 0x0, 0x1, 0x0, 0x0
ortango commented 1 year ago

_NET_WM_USER_TIME

i believe that sdl will update that property on button and key events (should be unset until the first event), so maybe that is a red herring - you can double check just to make sure.


peeking at sdl's source some more, it looks like motif hints and transient for are tied together (SetWindowBordered()). i wonder if transientfor is getting set and then unset by the time you check it with xprop? you can use external_rules_script to check xprop of a window before bspwm maps it - you might catch it there.


apologies for a third edit.

not sure how i missed

WM_TRANSIENT_FOR(WINDOW): window id # 0x79e

that explains it. check the above second edit, the sdl function i refer too, and rule.c's _apply_transient() function.


refs

  1. https://github.com/baskerville/bspwm/blob/master/src/rule.c#L275-L282
  2. https://github.com/libsdl-org/SDL/blob/main/src/video/x11/SDL_x11window.c#L342-L370
  3. https://github.com/libsdl-org/SDL/blob/fde78d12f247a776b52b007479e5274d4bd4e3fe/src/video/x11/SDL_x11sym.h#L88
  4. https://tronche.com/gui/x/xlib/window-information/XInternAtom.html
  5. just for ref on what is supposed to happen according to sdl : https://wiki.libsdl.org/SDL2/SDL_SetWindowBordered