automatic layout for vscode
This commit is contained in:
parent
b6bc571b52
commit
761405e7ce
2
Cargo.lock
generated
2
Cargo.lock
generated
|
@ -653,7 +653,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "sway-flash-indicator"
|
||||
version = "0.2.1"
|
||||
version = "0.3.0"
|
||||
dependencies = [
|
||||
"directories",
|
||||
"futures-util",
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
[package]
|
||||
name = "sway-flash-indicator"
|
||||
version = "0.2.1"
|
||||
version = "0.3.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
# Maintainer: Alex Janka <alex@alexjanka.com>
|
||||
|
||||
pkgname=sway-flash-indicator
|
||||
pkgver=0.2.1
|
||||
pkgver=0.3.0
|
||||
pkgrel=1
|
||||
pkgdesc="flashes sway indicator border rather than always showing it"
|
||||
arch=('x86_64' 'aarch64')
|
||||
|
|
|
@ -12,6 +12,7 @@ pub struct Config {
|
|||
pub flash_colour: Lab,
|
||||
pub autosplit_enabled: bool,
|
||||
pub autosplit_ratio: f64,
|
||||
pub output_blocklist: Vec<String>,
|
||||
}
|
||||
|
||||
pub fn parse_config() -> Res<()> {
|
||||
|
@ -55,6 +56,7 @@ impl Default for Config {
|
|||
},
|
||||
autosplit_enabled: true,
|
||||
autosplit_ratio: 1.0,
|
||||
output_blocklist: Vec::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -14,6 +14,8 @@ pub enum Error {
|
|||
TomlDe(#[from] toml::de::Error),
|
||||
#[error(transparent)]
|
||||
TomlSer(#[from] toml::ser::Error),
|
||||
#[error("node not found")]
|
||||
NodeNotFound,
|
||||
}
|
||||
|
||||
impl<T> From<tokio::sync::SetError<T>> for Error {
|
||||
|
|
94
src/main.rs
94
src/main.rs
|
@ -43,6 +43,7 @@ async fn main() -> Res<()> {
|
|||
.await?;
|
||||
|
||||
let mut fut: Option<tokio::task::JoinHandle<()>> = None;
|
||||
let mut recent_code = None;
|
||||
|
||||
while let Some(event) = events.next().await {
|
||||
if let Ok(event) = event {
|
||||
|
@ -62,9 +63,37 @@ async fn main() -> Res<()> {
|
|||
swayipc_async::Event::Window(window)
|
||||
if window.change != swayipc_async::WindowChange::Mark =>
|
||||
{
|
||||
let node = window.container;
|
||||
|
||||
if window.change == swayipc_async::WindowChange::New
|
||||
&& node.app_id == Some(String::from("code-url-handler"))
|
||||
{
|
||||
recent_code = Some((std::time::Instant::now(), node.id));
|
||||
} else if recent_code.is_some_and(|(t, _)| {
|
||||
std::time::Instant::now().duration_since(t)
|
||||
> std::time::Duration::from_millis(200)
|
||||
}) {
|
||||
recent_code = None;
|
||||
}
|
||||
|
||||
if let Some((_, id)) = recent_code {
|
||||
if id == node.id && window.change == swayipc_async::WindowChange::Focus {
|
||||
recent_code = None;
|
||||
log::info!("focused the window we want with id {id}");
|
||||
if let Err(e) = code_trigger(
|
||||
&mut autosplit_connection,
|
||||
id,
|
||||
&CONFIG.get().unwrap().output_blocklist,
|
||||
)
|
||||
.await
|
||||
{
|
||||
log::error!("error {e:?} fixing vscode window");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: also change on window closed -
|
||||
// the node we're given is the one that closes
|
||||
let node = window.container;
|
||||
if node.node_type == swayipc_async::NodeType::Con {
|
||||
let (width, height) = (node.window_rect.width, node.window_rect.height);
|
||||
if width == 0 || height == 0 {
|
||||
|
@ -90,6 +119,69 @@ async fn main() -> Res<()> {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
async fn code_trigger<T: AsRef<str> + std::cmp::PartialEq<str>>(
|
||||
connection: &mut swayipc_async::Connection,
|
||||
id: i64,
|
||||
output_blocklist: &[T],
|
||||
) -> Res<()> {
|
||||
let tree = connection.get_tree().await?;
|
||||
|
||||
for workspace in connection.get_workspaces().await? {
|
||||
let width = workspace.rect.width;
|
||||
if workspace.focused {
|
||||
let mut workspace = get_with_id(&tree, workspace.id)?;
|
||||
if workspace
|
||||
.output
|
||||
.as_ref()
|
||||
.is_some_and(|output| output_blocklist.iter().any(|s| s == output.as_str()))
|
||||
{
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
while workspace.focus.len() == 1 {
|
||||
workspace = get_with_id(workspace, workspace.focus[0])?;
|
||||
}
|
||||
if workspace.layout == swayipc_async::NodeLayout::SplitH && workspace.focus.len() == 2 {
|
||||
let (code, other) = {
|
||||
let a = get_with_id(&tree, workspace.focus[0])?;
|
||||
let b = get_with_id(&tree, workspace.focus[1])?;
|
||||
if contains_child(a, id) {
|
||||
(a, b)
|
||||
} else {
|
||||
(b, a)
|
||||
}
|
||||
};
|
||||
if code.focus.len() > 1 {
|
||||
log::info!("more than one thing in vscode focus tree");
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
let (code_rect, other_rect) = (code.rect, other.rect);
|
||||
|
||||
if code_rect.x > other_rect.x {
|
||||
log::info!("focused window is to the right");
|
||||
connection
|
||||
.run_command(format!("swap container with con_id {}", other.id))
|
||||
.await?;
|
||||
}
|
||||
|
||||
connection
|
||||
.run_command(format!("resize set width {}px", width - 1220))
|
||||
.await?;
|
||||
}
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn get_with_id(node: &swayipc_async::Node, id: i64) -> Res<&swayipc_async::Node> {
|
||||
node.find_as_ref(|n| n.id == id).ok_or(Error::NodeNotFound)
|
||||
}
|
||||
|
||||
fn contains_child(node: &swayipc_async::Node, id: i64) -> bool {
|
||||
node.find_as_ref(|n| n.id == id).is_some()
|
||||
}
|
||||
|
||||
async fn get_sway_config(connection: &mut swayipc_async::Connection) -> Res<()> {
|
||||
let config = connection.get_config().await?;
|
||||
let default_colours = config
|
||||
|
|
Loading…
Reference in a new issue