xul:面板在多个显示器上的位置
xul:panel position on multiple monitors
我的火狐扩展上有一个xul:panel。我给出与屏幕宽度和屏幕高度一致的显示位置。当我有多个显示器并在第一台显示器上启动浏览器时,我的问题会出现在第二台显示器上,并且根据第二台显示器上的第一个屏幕的分辨率绘制 xul:panel。是否有根据第二个屏幕的分辨率绘制的解决方案?
背景:
当我开发一个基于XULRunner的多监视器应用程序时,我发现你无法预测窗口管理器会在主应用程序/浏览器窗口首次启动后启动窗口的位置。
XULRunner确实正确地给了我:
- 用于完整多显示器显示的几何形状(宽度、高度)
- 多显示器显示器上给定窗口的窗口位置
- 给定窗口的窗口状态(最大化、最小化、两者都不是)
- (取消)最大化窗口的能力
特定监视器上时,它没有正确遵循多显示器几何形状(相反,窗口管理器将新窗口放置在任何它喜欢的地方)。
这让我不得不以某种方式执行以下操作:
- 相对于
- 多显示器显示定位窗口,以及
(因为移动窗口有时会失去窗口焦点) - 聚焦窗口。
我能够在js-ctypes加载/使用的外部DLL的帮助下实现这两个目标。
Win32 的示例:
以下是将外部 DLL 绑定到 JavaScript 的基础知识。这个例子只涵盖了Win32,但我也为Linux和MacOSX做了这个(与Win32相比,它们分别更容易和更难)。
共有 3 个部分:
- 用于加载/绑定 Win32 API 的特权 JavaScript 代码
- 外部 DLL 的 CPP 头文件
- 外部 DLL 的 CPP 源文件
我用后面的两个文件构建一个简单的GUI DLL项目,并根据msvcr100.dll
编译wmctrl.dll
,并使用Dependency Walker来查找DLL导出的"纯C"符号供js-ctypes使用。
我还围绕 API 构建了一个 JavaScript 库,它允许在应用程序的多次运行中操作、跟踪和持久化多个窗口的窗口状态/几何形状,但这与这个简单示例并不真正相关。
在特权 JavaScript 代码中:
// get js-ctypes, you do this part a bit differently from browser chrome
const {Cc,Ci,Cu} = require("chrome");
var file=null, lib=null, ctypes = {};
Cu.import("resource://gre/modules/ctypes.jsm", ctypes);
var ctypes = ctypes.ctypes;
// build platform specific library path
var filename = ctypes.libraryName("wmctrl");
var comp = "@mozilla.org/file/directory_service;1";
var file = Cc[comp].getService(Ci.nsIProperties).get("CurProcD", Ci.nsIFile);
file.append("browser_code");
file.append(filename);
// get the JavaScript library interface (load the library)
var lib = ctypes.open(file.path);
// wmctrl_find_window: returing unsigned 32bit (long) "window handle"
// takes string "window title".
var find_window = lib.declare("?wmctrl_find_window@@YAKPAD@Z",
ctypes.stdcall_abi, ctypes.uint32_t,
ctypes.char.ptr);
// wmctrl_window_focus: takes unsigned 32bit (long) "window handle".
var window_focus = lib.declare("?wmctrl_window_focus@@YAXK@Z",
ctypes.stdcall_abi, ctypes.void_t,
ctypes.uint32_t);
// wmctrl_window_move: takes unsigned 32bit (long) "window handle",
// and two (x & y) signed 32bit ints.
var window_move = lib.declare("?wmctrl_window_move@@YAXKHH@Z",
ctypes.stdcall_abi, ctypes.void_t,
ctypes.uint32_t, ctypes.int32_t, ctypes.int32_t);
wmctrldll.h
#ifdef WMCTRLDLL_EXPORTS
#define WMCTRLDLL_API __declspec(dllexport)
#else
#define WMCTRLDLL_API __declspec(dllimport)
#endif
WMCTRLDLL_API void wmctrl_window_focus (unsigned long wid);
WMCTRLDLL_API void wmctrl_window_move (unsigned long wid, int x, int y);
WMCTRLDLL_API unsigned long wmctrl_find_window(char* find_title);
wmctrldll.cpp
#include "stdafx.h"
#include "wmctrldll.h"
typedef struct {
HWND hWnd;
char title[255];
} myWinSpec;
BOOL CALLBACK EnumWindowsProc(HWND hWnd, LPARAM lParam) {
char String[255];
myWinSpec* to_find = (myWinSpec*) lParam;
// not a window
if (!hWnd) return TRUE;
// not visible
if (!IsWindowVisible(hWnd)) return TRUE;
// no window title
if (!GetWindowTextA(hWnd, (LPSTR)String, 255)) return TRUE;
// no title match
if (strcmp(String, to_find->title) != 0) return TRUE;
to_find->hWnd = hWnd;
return FALSE;
}
WMCTRLDLL_API void wmctrl_window_focus(unsigned long wid) {
SetForegroundWindow((HWND) wid);
}
WMCTRLDLL_API unsigned long wmctrl_find_window(char* find_title) {
myWinSpec to_find;
sprintf_s(to_find.title, sizeof(to_find.title), "%s", find_title);
to_find.hWnd = 0;
EnumWindows(EnumWindowsProc, (LPARAM)&to_find);
return (unsigned long) to_find.hWnd;
}
WMCTRLDLL_API void wmctrl_window_move(unsigned long wid, int x, int y) {
UINT flags = SWP_SHOWWINDOW | SWP_NOSIZE;
SetForegroundWindow((HWND) wid);
SetWindowPos((HWND) wid, HWND_NOTOPMOST, x, y, NULL, NULL, flags);
}
相关文章:
- jquery试图按名称获取按钮位置
- 我可以获得相对于被点击元素的确切点击位置吗
- 谷歌地图固定位置覆盖
- 在单击任何位置时隐藏元素,而不检查每次DOM单击
- 循环比赛位置算法
- es6 相当于下划线查找位置
- jQuery循环在特定位置暂停
- 引导程序:在导航栏中,显示悬停在单个位置的基于Li Link的不同内容
- 自定义函数中的光标位置
- 安卓平台上的QWebView HTML5地理位置
- DIV并排,位置不正确
- 使用jQuery更改元素的顶部位置
- 在谷歌地图上绘制位置数据库
- 跟踪jqplot垂直折线图的鼠标位置
- 设置画布渲染器的x和y位置
- 固定位置菜单时滚动,直到它击中一个相对容器的底部
- 根据页面的位置突出显示文本中的字符
- 传单缩放控制位置错误
- 如何将返回的值应用于多个不同位置的多个选择器
- xul:面板在多个显示器上的位置