4

你可能知道 Mac OS X 内置了一个非常棒的屏幕缩放功能,可以在 System Preferences => Universal Access 中启用。

现在我试图以编程方式触发这个屏幕缩放。我可以通过发送键盘快捷键来做到这一点,但它不像它应该的那样流畅。所以我对系统如何做到这一点进行了一些研究。

似乎有一些私有核心图形方法可以做我想做的事情,但我无法找到它们采用的参数。

这些是我发现的功能:

  • CGSZoomPoint
  • CGSU缩放点
  • CGSGetZoomParameters
  • CGSSetZoomParameters
  • CGSI 放大

有些人已经对核心图形框架的一些私有方法进行了逆向工程,并为它们创建了标头。(参见例如http://pwproject.googlecode.com/svn/trunk/Mac%20OS%20X/Vector%20Grab/)不幸的是,我似乎需要的方法丢失了。(CGSIsZoomed,其实是包含

CG_EXTERN CGError CGSIsZoomed(CGSConnectionID cid, bool *outIsZoomed); 

)

我还发现了一个似乎可以缩放屏幕的应用程序,这似乎是相关的反汇编,但我对汇编不太了解,因此我无法阅读它;-(

0000000100015c21    callq   0x10002c212 ; symbol stub for: _CGEventCreate
0000000100015c26    movq    %rax,%rbx
0000000100015c29    movq    %rbx,%rdi
0000000100015c2c    callq   0x10002c22a ; symbol stub for: _CGEventGetLocation
0000000100015c31    movsd   %xmm0,0xffffff48(%rbp)
0000000100015c39    movsd   %xmm1,0xffffff58(%rbp)
0000000100015c41    movsd   %xmm0,0xa8(%rbp)
0000000100015c46    movsd   %xmm1,0xb0(%rbp)
0000000100015c4b    movq    %rbx,%rdi
0000000100015c4e    callq   0x10002c362 ; symbol stub for: _CFRelease
0000000100015c5a    jle 0x100015d01
0000000100015c60    movq    0x00098a71(%rip),%rax
0000000100015c67    movq    0x18(%rax),%rcx
0000000100015c6b    movq    %rcx,0x18(%rsp)
0000000100015c70    movq    0x10(%rax),%rcx
0000000100015c74    movq    %rcx,0x10(%rsp)
0000000100015c79    movq    (%rax),%rcx
0000000100015c7c    movq    0x08(%rax),%rax
0000000100015c80    movq    %rax,0x08(%rsp)
0000000100015c85    movq    %rcx,(%rsp)
0000000100015c89    movsd   0xffffff48(%rbp),%xmm0
0000000100015c91    movsd   0xffffff58(%rbp),%xmm1
0000000100015c99    callq   0x10002c266 ; symbol stub for: _CGRectContainsPoint
0000000100015c9e    cmpl    $0x02,0x00098a43(%rip)
0000000100015ca5    jl  0x100015d01
0000000100015ca7    movl    $0x    00000001,%r15d
0000000100015cad    movl    $0x00000020,%ebx
0000000100015cb2    movsd   0xa8(%rbp),%xmm0
0000000100015cb7    movsd   0xb0(%rbp),%xmm1
0000000100015cbc    movq    0x00098a15(%rip),%rax
0000000100015cc3    movq    0x18(%rax,%rbx),%rcx
0000000100015cc8    movq    %rcx,0x18(%rsp)
0000000100015ccd    movq    0x10(%rax,%rbx),%rcx
0000000100015cd2    movq    %rcx,0x10(%rsp)
0000000100015cd7    movq    (%rax,%rbx),%rcx
0000000100015cdb    movq    0x08(%rax,%rbx),%rax
0000000100015ce0    movq    %rax,0x08(%rsp)
0000000100015ce5    movq    %rcx,(%rsp)
0000000100015ce9    callq   0x10002c266 ; symbol stub for: _CGRectContainsPoint
0000000100015cee    addq    $0x20,%rbx
0000000100015cf2    incq    %r15
0000000100015cf5    movslq  0x000989ec(%rip),%rax
0000000100015cfc    cmpq    %rax,%r15
0000000100015cff    jl  0x100015cb2
0000000100015d01    movsd   0xc0(%rbp),%xmm0
0000000100015d06    movsd   %xmm0,0xffffff58(%rbp)
0000000100015d0e    leaq    0xa8(%rbp),%rsi
0000000100015d12    leaq    0x98(%rbp),%rdx
0000000100015d16    movl    %r14d,%edi
0000000100015d19    callq   0x10002c296 ; symbol stub for: _CGSZoomPoint
0000000100015d1e    movsd   0xffffff58(%rbp),%xmm2
0000000100015d26    testl   %eax,%eax
0000000100015d28    jne 0x100015d99
0000000100015d2a    movapd  %xmm2,%xmm0
0000000100015d2e    mulsd   0xffffff60(%rbp),%xmm0
0000000100015d36    addsd   0x98(%rbp),%xmm0
0000000100015d3b    movsd   0x00017255(%rip),%xmm1
0000000100015d43    ucomisd %xmm0,%xmm1
0000000100015d47    ja  0x100015d78
0000000100015d49    ucomisd 0x0001749f(%rip),%xmm0
0000000100015d51    ja  0x100015d78
0000000100015d53    mulsd   0xffffff50(%rbp),%xmm2
0000000100015d5b    addsd   0xa0(%rbp),%xmm2
0000000100015d60    movsd   0x00017230(%rip),%xmm0
0000000100015d68    ucomisd %xmm2,%xmm0
0000000100015d6c    ja  0x100015d78
0000000100015d6e    ucomisd 0x00017482(%rip),%xmm2
0000000100015d76    jbe 0x100015d99
0000000100015d78    movzbl  0xbf(%rbp),%edx
0000000100015d7c    andl    $0x01,%edx
0000000100015d7f    movsd   0xc0(%rbp),%xmm0
0000000100015d84    leaq    0xc8(%rbp),%rsi
0000000100015d88    movl    %r14d,%edi
0000000100015d8b    movl    $0x    00000001,%ecx
0000000100015d90    xorpd   %xmm1,%xmm1
0000000100015d94    callq   0x10002c290 ; symbol stub for: _CGSSetZoomParameters
0000000100015d99    movsd   0xffffff70(%rbp),%xmm1
0000000100015da1    addsd   0xffffff50(%rbp),%xmm1
0000000100015da9    movsd   0xffffff68(%rbp),%xmm0
0000000100015db1    addsd   0xffffff60(%rbp),%xmm0
0000000100015db9    movb    0x000988f1(%rip),%al
0000000100015dbf    xorl    %edi,%edi
0000000100015dc1    cmpb    $0x01,%al
0000000100015dc3    jne 0x100015dde
0000000100015dc5    movl    $0x    00000006,%esi
0000000100015dca    xorl    %edx,%edx

如果有人知道如何使用这些私人功能,你会让我的一周:-)

最好的,托马斯

4

1 回答 1

0

好吧,这个问题已经很久没有答案了,但碰巧我只是想出了如何使用CGSGetZoomParametersCGSSetZoomParameters我自己的工作,它们都可以用来控制和检索有关屏幕缩放状态的信息。函数定义如下:

CG_EXTERN CGError CGSGetZoomParameters(CGSConnectionID cid, CGPoint *origin, double * zoomFactor, int8_t *smoothed);
CG_EXTERN CGError CGSSetZoomParameters(CGSConnectionID cid, CGPoint *origin, double zoomFactor, int8_t smoothed);

whereorigin确定使用以下方法缩放屏幕的哪个部分:

要尽可能向左缩放区域,请设置origin.x为:(desktopWidth / 2) / zoomFactor

要尽可能向右缩放区域,请设置origin.x为:desktopWidth - ((desktopWidth / 2) / zoomFactor)

要尽可能放大区域,请设置origin.y为:(desktopHeight / 2) / zoomFactor

要尽可能向右缩放区域,请设置origin.y为:desktopHeight - ((desktopHeight / 2) / zoomFactor)

FordesktopWidthdesktopHeight是当前桌面边界矩形的总宽度/高度,包括当前排列的所有显示器。因此,如果您有两个完全水平排列的 1080p 显示器,那么桌面的总宽度和高度为 3840x1080。

要缩放中间区域,请使用origin介于两个极值之间的值。数学计算出来,因此它们之间的整数点数完全对应于任何给定的缩放屏幕可以具有的位置数zoomFactor

这些功能是低级的,会干扰标准的 macOS 无障碍缩放功能。例如,如果您的屏幕未缩放,您可以使用 将其放大CGSSetZoomParameters,然后使用辅助功能之一,例如按住 Control 并滚动鼠标滚轮来更改缩放,它们将像屏幕未缩放一样工作。此外,当屏幕缩放时,无论如何配置辅助功能缩放功能,都无法使用鼠标进行平移,所以要小心!您可能会导致屏幕放大并让用户无法再次缩小。

我不确定如何使用CGSZoomPointCGSUnzoomPoint使用 - 我无法让它们产生任何效果。但如前所述,屏幕缩放的低级控制可以通过其他两个功能来完成。

于 2017-07-18T22:11:42.250 回答