Implement per-tag primary_count and primary_ratio
By default, each tag mask will use the default count and ratio. If the mask gets modified by any of the commands, it gets added to a hash map. When changing tag masks, the current count and ratio are stored, and they're used again later if you switch back to that mask. This commit also adds primary_count and primary_ratio to the general settings for the config, so users can set a default count/ratio to use.
This commit is contained in:
parent
8e93395360
commit
1df6820b1d
5 changed files with 75 additions and 7 deletions
|
|
@ -22,6 +22,12 @@ All configuration is applied top down, so later options will overwrite earlier o
|
||||||
// Whether new windows should go to the top or bottom of the window stack
|
// Whether new windows should go to the top or bottom of the window stack
|
||||||
attach_mode "top"
|
attach_mode "top"
|
||||||
|
|
||||||
|
// Number of windows in the primary stack
|
||||||
|
primary_count 1
|
||||||
|
|
||||||
|
// Proportion of output width taken by the primary stack
|
||||||
|
primary_ratio 0.55
|
||||||
|
|
||||||
// Whether mousing over a new window should move focus
|
// Whether mousing over a new window should move focus
|
||||||
focus_follows_pointer #true
|
focus_follows_pointer #true
|
||||||
|
|
||||||
|
|
@ -37,6 +43,8 @@ wallpaper_image_path "~/Pictures/wallpaper.png"
|
||||||
| Setting | Type | Default | Description |
|
| Setting | Type | Default | Description |
|
||||||
|------------------------------|--------|---------|-----------------------------------------------------|
|
|------------------------------|--------|---------|-----------------------------------------------------|
|
||||||
| `attach_mode` | enum | `top` | Where new windows go in the stack (`top` or `bottom`) |
|
| `attach_mode` | enum | `top` | Where new windows go in the stack (`top` or `bottom`) |
|
||||||
|
| `primary_count` | u8 | `1` | Number of windows in the primary stack (0+) |
|
||||||
|
| `primary_ratio` | float | `0.55` | Proportion of output width for the primary stack (0.10–0.90) |
|
||||||
| `focus_follows_pointer` | bool | `#true` | Focus follows the pointer between windows |
|
| `focus_follows_pointer` | bool | `#true` | Focus follows the pointer between windows |
|
||||||
| `pointer_warp_on_focus_change` | bool | `#true` | Warp pointer to center of newly-focused windows |
|
| `pointer_warp_on_focus_change` | bool | `#true` | Warp pointer to center of newly-focused windows |
|
||||||
| `wallpaper_image_path` | string | none | Path to wallpaper image |
|
| `wallpaper_image_path` | string | none | Path to wallpaper image |
|
||||||
|
|
|
||||||
|
|
@ -2,8 +2,6 @@
|
||||||
|
|
||||||
These are in rough order of my priority, though no promises I do them in this order.
|
These are in rough order of my priority, though no promises I do them in this order.
|
||||||
|
|
||||||
- [ ] Implement primary count/ratio per tagmask
|
|
||||||
- [ ] Add primary_count and primary_ratio to Config
|
|
||||||
- [ ] Implement a river-tag-overlay clone
|
- [ ] Implement a river-tag-overlay clone
|
||||||
- [ ] Implement an optional clock bar
|
- [ ] Implement an optional clock bar
|
||||||
- [ ] Support window rules (float/tags/SSD by app-id/title)
|
- [ ] Support window rules (float/tags/SSD by app-id/title)
|
||||||
|
|
@ -26,3 +24,5 @@ These are in rough order of my priority, though no promises I do them in this or
|
||||||
- [x] Add input configuration, i.e. pointer acceleration and that type of thing
|
- [x] Add input configuration, i.e. pointer acceleration and that type of thing
|
||||||
- [x] Support `None` modifier for keybinds (needed for media/brightness keys)
|
- [x] Support `None` modifier for keybinds (needed for media/brightness keys)
|
||||||
- [x] Support per-host config using properties
|
- [x] Support per-host config using properties
|
||||||
|
- [x] Implement primary count/ratio per tagmask
|
||||||
|
- [x] Add primary_count and primary_ratio to Config
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,9 @@
|
||||||
// Whether new windows should go to the top or bottom of the window stack
|
// Whether new windows should go to the top or bottom of the window stack
|
||||||
attach_mode top
|
attach_mode top
|
||||||
|
// Number of windows in the primary stack
|
||||||
|
primary_count 1
|
||||||
|
// Proportion of output width taken by the primary stack
|
||||||
|
primary_ratio 0.55
|
||||||
// Whether mousing over a new window should move focus
|
// Whether mousing over a new window should move focus
|
||||||
focus_follows_pointer #true
|
focus_follows_pointer #true
|
||||||
// Whether the focus should warp to the center of newly-focused windows
|
// Whether the focus should warp to the center of newly-focused windows
|
||||||
|
|
|
||||||
|
|
@ -13,6 +13,13 @@ border_color_focused: RiverColor = utils.parseRgbaComptime("0x89b4fa"),
|
||||||
/// Color of unfocused windows' borders in 0xRRGGBBAA or 0xRRGGBB form
|
/// Color of unfocused windows' borders in 0xRRGGBBAA or 0xRRGGBB form
|
||||||
border_color_unfocused: RiverColor = utils.parseRgbaComptime("0x1e1e2e"),
|
border_color_unfocused: RiverColor = utils.parseRgbaComptime("0x1e1e2e"),
|
||||||
|
|
||||||
|
/// Number of windows in the primary stack
|
||||||
|
/// This is a global default, but each tagmask can have its own value
|
||||||
|
primary_count: u8 = 1,
|
||||||
|
/// Proportion of output width taken by the primary stack
|
||||||
|
/// This is a global default, but each tagmask can have its own value
|
||||||
|
primary_ratio: f32 = 0.55,
|
||||||
|
|
||||||
/// Where a new window should attach, top or bottom of the stack
|
/// Where a new window should attach, top or bottom of the stack
|
||||||
attach_mode: AttachMode = .top,
|
attach_mode: AttachMode = .top,
|
||||||
/// Should focus change when the cursor moves onto a new window
|
/// Should focus change when the cursor moves onto a new window
|
||||||
|
|
@ -80,6 +87,8 @@ pub const AttachMode = enum {
|
||||||
|
|
||||||
const NodeName = enum {
|
const NodeName = enum {
|
||||||
attach_mode,
|
attach_mode,
|
||||||
|
primary_count,
|
||||||
|
primary_ratio,
|
||||||
focus_follows_pointer,
|
focus_follows_pointer,
|
||||||
pointer_warp_on_focus_change,
|
pointer_warp_on_focus_change,
|
||||||
wallpaper_image_path,
|
wallpaper_image_path,
|
||||||
|
|
@ -229,6 +238,24 @@ fn load(config: *Config, reader: *Io.Reader) !void {
|
||||||
}
|
}
|
||||||
// Next, we have to check the specifics for the NodeName
|
// Next, we have to check the specifics for the NodeName
|
||||||
switch (name) {
|
switch (name) {
|
||||||
|
.primary_count => {
|
||||||
|
const count_str = utils.stripQuotes(node.arg(&parser, 0) orelse "");
|
||||||
|
// Use @max to ensure a minimum of 1
|
||||||
|
config.primary_count = @max(1, fmt.parseInt(u8, count_str, 10) catch {
|
||||||
|
logWarnInvalidNodeArg(name, count_str);
|
||||||
|
continue;
|
||||||
|
});
|
||||||
|
logDebugSettingNode(name, count_str);
|
||||||
|
},
|
||||||
|
.primary_ratio => {
|
||||||
|
const ratio_str = utils.stripQuotes(node.arg(&parser, 0) orelse "");
|
||||||
|
const ratio = fmt.parseFloat(f32, ratio_str) catch {
|
||||||
|
logWarnInvalidNodeArg(name, ratio_str);
|
||||||
|
continue;
|
||||||
|
};
|
||||||
|
config.primary_ratio = std.math.clamp(ratio, 0.10, 0.90);
|
||||||
|
logDebugSettingNode(name, ratio_str);
|
||||||
|
},
|
||||||
.attach_mode => {
|
.attach_mode => {
|
||||||
const attach_mode_str = utils.stripQuotes(node.arg(&parser, 0) orelse "");
|
const attach_mode_str = utils.stripQuotes(node.arg(&parser, 0) orelse "");
|
||||||
if (std.meta.stringToEnum(AttachMode, attach_mode_str)) |mode| {
|
if (std.meta.stringToEnum(AttachMode, attach_mode_str)) |mode| {
|
||||||
|
|
|
||||||
|
|
@ -25,10 +25,15 @@ wl_surface: ?*wl.Surface = null,
|
||||||
layer_surface: ?*zwlr.LayerSurfaceV1 = null,
|
layer_surface: ?*zwlr.LayerSurfaceV1 = null,
|
||||||
|
|
||||||
/// Proportion of output width taken by the primary stack
|
/// Proportion of output width taken by the primary stack
|
||||||
primary_ratio: f32 = 0.55,
|
primary_ratio: f32,
|
||||||
|
|
||||||
/// Number of windows in the primary stack
|
/// Number of windows in the primary stack
|
||||||
primary_count: u8 = 1,
|
primary_count: u8,
|
||||||
|
|
||||||
|
/// Per-tagmask layout overrides
|
||||||
|
/// These only get added when the user modifies primary count or ratio
|
||||||
|
/// Any tagmask NOT in this map keeps using the defaults from Config
|
||||||
|
tag_layout_overrides: std.AutoHashMapUnmanaged(u32, TagLayoutOverride) = .{},
|
||||||
|
|
||||||
/// Tags are 32-bit bitfield. A window can be active on one(?) or more tags.
|
/// Tags are 32-bit bitfield. A window can be active on one(?) or more tags.
|
||||||
tags: u32 = 0x0001,
|
tags: u32 = 0x0001,
|
||||||
|
|
@ -46,6 +51,12 @@ windows: wl.list.Head(Window, .link),
|
||||||
|
|
||||||
link: wl.list.Link,
|
link: wl.list.Link,
|
||||||
|
|
||||||
|
/// Struct used for tagmask-specific count/ratio overrides
|
||||||
|
pub const TagLayoutOverride = struct {
|
||||||
|
primary_count: u8,
|
||||||
|
primary_ratio: f32,
|
||||||
|
};
|
||||||
|
|
||||||
pub const PendingManage = struct {
|
pub const PendingManage = struct {
|
||||||
width: ?u31 = null,
|
width: ?u31 = null,
|
||||||
height: ?u31 = null,
|
height: ?u31 = null,
|
||||||
|
|
@ -64,6 +75,8 @@ pub fn create(context: *Context, river_output_v1: *river.OutputV1) !*Output {
|
||||||
output.* = .{
|
output.* = .{
|
||||||
.context = context,
|
.context = context,
|
||||||
.river_output_v1 = river_output_v1,
|
.river_output_v1 = river_output_v1,
|
||||||
|
.primary_count = context.config.primary_count,
|
||||||
|
.primary_ratio = context.config.primary_ratio,
|
||||||
.windows = undefined, // we will initialize this shortly
|
.windows = undefined, // we will initialize this shortly
|
||||||
.link = undefined, // Handled by the wl.list
|
.link = undefined, // Handled by the wl.list
|
||||||
};
|
};
|
||||||
|
|
@ -82,6 +95,7 @@ pub fn destroy(output: *Output) void {
|
||||||
window.destroy();
|
window.destroy();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
output.tag_layout_overrides.deinit(utils.allocator);
|
||||||
output.deinitWallpaperLayerSurface();
|
output.deinitWallpaperLayerSurface();
|
||||||
output.river_output_v1.destroy();
|
output.river_output_v1.destroy();
|
||||||
utils.allocator.destroy(output);
|
utils.allocator.destroy(output);
|
||||||
|
|
@ -425,9 +439,6 @@ pub fn manage(output: *Output) void {
|
||||||
output.y = y;
|
output.y = y;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (output.pending_manage.tags) |tags| {
|
|
||||||
output.tags = tags;
|
|
||||||
}
|
|
||||||
if (output.pending_manage.primary_ratio) |primary_ratio| {
|
if (output.pending_manage.primary_ratio) |primary_ratio| {
|
||||||
// Ratios outside of this range could cause crashes (when doing the layout calculation)
|
// Ratios outside of this range could cause crashes (when doing the layout calculation)
|
||||||
output.primary_ratio = std.math.clamp(primary_ratio, 0.10, 0.90);
|
output.primary_ratio = std.math.clamp(primary_ratio, 0.10, 0.90);
|
||||||
|
|
@ -436,6 +447,24 @@ pub fn manage(output: *Output) void {
|
||||||
// Don't allow less than 1 primary
|
// Don't allow less than 1 primary
|
||||||
output.primary_count = @max(1, primary_count);
|
output.primary_count = @max(1, primary_count);
|
||||||
}
|
}
|
||||||
|
if (output.pending_manage.tags) |new_tags| {
|
||||||
|
// Save current layout for the old tagmask
|
||||||
|
output.tag_layout_overrides.put(utils.allocator, output.tags, .{
|
||||||
|
.primary_count = output.primary_count,
|
||||||
|
.primary_ratio = output.primary_ratio,
|
||||||
|
}) catch @panic("Out of memory");
|
||||||
|
|
||||||
|
// Restore layout for the new tagmask, or fall back to config defaults
|
||||||
|
if (output.tag_layout_overrides.get(new_tags)) |tag_layout_override| {
|
||||||
|
output.primary_count = tag_layout_override.primary_count;
|
||||||
|
output.primary_ratio = tag_layout_override.primary_ratio;
|
||||||
|
} else {
|
||||||
|
output.primary_count = output.context.config.primary_count;
|
||||||
|
output.primary_ratio = output.context.config.primary_ratio;
|
||||||
|
}
|
||||||
|
|
||||||
|
output.tags = new_tags;
|
||||||
|
}
|
||||||
|
|
||||||
// Calculate layout before managing windows
|
// Calculate layout before managing windows
|
||||||
output.calculatePrimaryStackLayout();
|
output.calculatePrimaryStackLayout();
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue