You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Delphi中编写PHYSICAL_MONITOR数组以调用WinAPI函数?

Delphi调用GetPhysicalMonitorsFromHMONITOR的数据结构设置方法

首先你当前的结构体命名存在混淆,WinAPI原生的PHYSICAL_MONITOR结构体被你命名成了LPPHYSICAL_MONITOR,这容易和指针类型搞混,先修正类型定义:

type
  PHYSICAL_MONITOR = record
    hPhysicalMonitor: THandle;
    szPhysicalMonitorDescription: array[0..127] of WideChar; // 对应WinAPI的WCHAR数组,长度128(含终止符)
  end;
  PPHYSICAL_MONITOR = ^PHYSICAL_MONITOR;
  TPhysicalMonitorArray = array of PHYSICAL_MONITOR;

你的函数声明基本没问题,只需确保参数类型和WinAPI匹配,这里可以保留你的声明:

function GetPhysicalMonitorsFromHMONITOR(hMonitor: HMONITOR;
  dwPhysicalMonitorArraySize: DWORD;
  pPhysicalMonitorArray: PPHYSICAL_MONITOR): BOOL; stdcall; external 'Dxva2.dll';

接下来处理函数需要的数组需求:该函数接收的是指向PHYSICAL_MONITOR结构体数组的指针,你可以通过两种方式实现:

方式一:使用动态数组(推荐)

先调用GetNumberOfPhysicalMonitorsFromHMONITOR获取当前显示器对应的物理监视器数量,再动态分配数组:

var
  hMonitor: HMONITOR;
  MonitorCount: DWORD;
  PhysicalMonitors: TPhysicalMonitorArray;
  i: Integer;
begin
  // 先获取目标HMONITOR(可通过EnumDisplayMonitors等方式获取)
  hMonitor := ...;
  
  // 获取物理监视器数量
  if not GetNumberOfPhysicalMonitorsFromHMONITOR(hMonitor, MonitorCount) then Exit;
  
  // 动态分配数组
  SetLength(PhysicalMonitors, MonitorCount);
  
  // 调用函数,传入数组首地址
  if GetPhysicalMonitorsFromHMONITOR(hMonitor, MonitorCount, @PhysicalMonitors[0]) then
  begin
    // 遍历访问每个物理监视器
    for i := 0 to MonitorCount - 1 do
    begin
      // 使用结构体中的句柄和描述信息
      ShowMessage(WideString(PhysicalMonitors[i].szPhysicalMonitorDescription));
    end;
    
    // 用完后必须关闭物理监视器句柄,避免资源泄漏
    for i := 0 to MonitorCount - 1 do
      DestroyPhysicalMonitor(PhysicalMonitors[i].hPhysicalMonitor);
  end;
end;

方式二:手动分配内存+指针偏移

如果不想用动态数组,也可以手动分配内存,通过指针偏移访问每个元素:

var
  hMonitor: HMONITOR;
  MonitorCount: DWORD;
  pMonitors: PPHYSICAL_MONITOR;
  i: Integer;
begin
  hMonitor := ...;
  if not GetNumberOfPhysicalMonitorsFromHMONITOR(hMonitor, MonitorCount) then Exit;
  
  // 分配对应大小的内存
  pMonitors := AllocMem(MonitorCount * SizeOf(PHYSICAL_MONITOR));
  try
    if GetPhysicalMonitorsFromHMONITOR(hMonitor, MonitorCount, pMonitors) then
    begin
      for i := 0 to MonitorCount - 1 do
      begin
        // 通过指针偏移访问第i个元素
        ShowMessage(WideString((pMonitors + i)^.szPhysicalMonitorDescription));
      end;
      
      // 关闭句柄
      for i := 0 to MonitorCount - 1 do
        DestroyPhysicalMonitor((pMonitors + i)^.hPhysicalMonitor);
    end;
  finally
    // 释放手动分配的内存
    FreeMem(pMonitors);
  end;
end;

注意事项

  • 获取到的hPhysicalMonitor句柄必须调用DestroyPhysicalMonitor释放,否则会造成资源泄漏
  • szPhysicalMonitorDescription是宽字符数组,转换成Delphi的WideString即可正常显示
  • 确保已引入Windows单元,它提供了THandle、DWORD、stdcall等必要定义

内容的提问来源于stack exchange,提问作者dexamenos

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 21:23:10