有没有类似 "awful.client.focus.global_byidx()" 的东西?

Is there something like "awful.client.focus.global_byidx()"?

我有两个显示器,我想通过快捷方式更改客户端焦点。现在我有 awful.client.focus.byidx(1) 但它只会更改一台显示器上的客户端。我知道有 awful.client.focus.global_bydirection("right") 可以在多个屏幕上工作,但它只会向一个方向移动,并且在到达最后一个客户端时停止工作。我喜欢 awful.client.focus.byidx(1) 遍历所有客户端的行为,因此从最后一个客户端转到第一个客户端。

我想在两者之间使用混合:像 awful.client.focus.byidx(1) 那样通过客户端,但像 awful.client.focus.global_bydirection("right") 一样在所有 monitors/screens 上。是否有具有该行为的函数以便我可以使用它?如果没有,你知道我怎样才能实现那个目标吗?

首先,让我们看看awful.client.focus.byidx是如何实现的。

函数本身调用 awful.client.next 然后聚焦 returned 客户端,如果找到的话:

https://github.com/awesomeWM/awesome/blob/9781f14b105ee700c5bca339bf49bb52d2cca4b5/lib/awful/client/focus.lua#L65-L71

awful.client.next 在这里实现:https://github.com/awesomeWM/awesome/blob/9781f14b105ee700c5bca339bf49bb52d2cca4b5/lib/awful/client.lua#L262-L284

它执行以下操作:

  • 第263行:获取当前关注的客户端
  • 第267行:获取可见客户端屏幕上的所有可见客户端
  • 第 270-274 行:从列表中过滤掉无法聚焦的客户
  • 第 277 - 278 行:在结果列表中找到重点客户
  • 第 280 行:在想要的偏移处获取客户端并return它

因此,您的请求听起来像是您只需要更改此处的一个步骤:获取所有可见客户端的列表,而不仅仅是当前聚焦屏幕上的那些。 要获取该列表,您需要使用 nil 而不是特定屏幕来调用 awful.client.visible

未经测试的代码:

function next_global(i, sel, stacked)
  sel = sel or client.focus
  if not sel then return end
  local cls = awful.client.visible(nil, stacked)
  local fcls = {}
  for _, c in ipairs(cls) do
    if awful.client.focus.filter(c) or c == sel then
      table.insert(fcls, c)
    end
  end
  cls = fcls
  for idx, c in ipairs(cls) do
    if c == sel then
      return cls[gears.math.cycle(#cls, idx + i)]
    end
  end
end
function focus_byidx_global(i, c)
  local target = next_global(i, c)
  if target then
    target:emit_signal("request::activate", "client.focus.byidx", {raise=true})
  end
end

我不知道您使用的是哪个版本的 AwesomeWM。如有疑问,请查看 /usr/share/awesome/lib/ 中已安装的文件并从那里复制代码,然后进行更改。

(更难看的解决方案如下所示,尽管它需要更少的代码;我把它作为练习留给 reader 来弄清楚它的作用,但请注意这个 "breaks stuff" 以防发生 Lua 错误并且猴子修补成为永久性的)

function focus_byidx_global(i, c)
  local old = awful.client.visible
  awful.client.visible = function(_, s) return old(nil, s) end
  awful.client.focus.byidx(i, c)
  awful.client.visible = old
end