触摸适配、高 DPI 缩放、音频桥接、平台能力查询与后端切换。
XGE 跨平台适配关键领域:
• 触摸:移动端多点触摸替代鼠标,控件需支持 Touch 事件
• 高 DPI:Retina/4K 屏幕逻辑坐标 vs 物理像素
• 音频:不同平台音频后端(WASAPI/OpenSL/CoreAudio)
• 后端切换:xgePlatformBackendSet / xgeGraphicsBackendSet
• 能力查询:xgePlatformCapsGet 运行时检测平台特性
| 领域 | API / 策略 |
|---|---|
触摸 | xgeTouchGetCount/Get/Find → XUI DispatchEvent |
高 DPI | xgeGetWidth/Height(逻辑)vs 物理像素比 |
音频 | xgeAudioInit 自动选择平台后端 |
图形后端 | xgeGraphicsBackendSet(OpenGL/Vulkan/Metal) |
平台能力 | xgePlatformCapsGet(触摸/手柄/IME 支持) |
IME | xgeImeSetEnabled(移动端软键盘) |
gcc -O2 -I. -o ch209.exe ch209_main.c src\xui_*.c build\xge.lib -lm -lws2_32 -liphlpapi -lgdi32 -luser32 -lshell32 -lopengl32 -lole32 -lwinmm -lavrt
.\ch209.exe
// 查询平台能力
xge_platform_caps_t tCaps;
xgePlatformCapsGet(&tCaps);
// 高 DPI 缩放
float fDPI = tCaps.fDisplayScale; // 1.0 / 2.0 / 3.0
xuiSetVirtualDpi(pCtx, fDPI);
// 触摸 → XUI 事件
void OnFrame(void) {
int iCount = xgeTouchGetCount();
for (int i = 0; i < iCount; i++) {
xge_touch_point_t tTouch;
xgeTouchGet(i, &tTouch);
xui_event_t ev = { 0 };
ev.fX = tTouch.fX;
ev.fY = tTouch.fY;
ev.iId = tTouch.iId;
if (tTouch.iPhase == XGE_TOUCH_BEGIN)
ev.iType = XUI_EVENT_POINTER_DOWN;
else if (tTouch.iPhase == XGE_TOUCH_END)
ev.iType = XUI_EVENT_POINTER_UP;
else
ev.iType = XUI_EVENT_POINTER_MOVE;
xuiDispatchEvent(pCtx, &ev);
}
}将以下代码保存为 ch209_main.c,编译后运行即可看到平台能力查询与 DPI 适配效果:
#include "xge.h"
#include "xui.h"
#include <stdio.h>
static xui_context g_pCtx;
static int onFrame(void* pUser) {
(void)pUser;
xgeClear(0x1a1a2e);
xui_vec2_t pos;
xgeMouseGet(&pos.x, &pos.y);
xuiInputPointerMove(g_pCtx, pos.x, pos.y);
if (xgeMouseDown(XGE_MOUSE_LEFT))
xuiInputPointerDown(g_pCtx, pos.x, pos.y, 0);
else
xuiInputPointerUp(g_pCtx, pos.x, pos.y, 0);
xuiUpdate(g_pCtx, xgeGetDelta());
xuiLayout(g_pCtx);
xuiRender(g_pCtx, NULL, NULL, 0);
return XGE_OK;
}
int main(void) {
xge_desc_t d = {0};
d.iWidth = 640; d.iHeight = 480;
d.sTitle = "ch209 - Platform Adapt";
d.iFlags = XGE_INIT_VSYNC;
xgeInit(&d);
xuiCreate(&g_pCtx);
extern const xui_proxy_t tXgeProxy;
xui_proxy_t tXgeProxy = xuiProxyXge();
xuiSetProxy(g_pCtx, &tXgeProxy);
xuiSetViewportSize(g_pCtx, 640, 480);
/* 查询平台能力 */
xge_platform_caps_t tCaps;
xgePlatformCapsGet(&tCaps);
xui_widget pRoot;
xuiPanelCreate(g_pCtx, &pRoot, NULL);
xuiWidgetSetRect(pRoot, (xui_rect_t){0, 0, 640, 480});
char buf[128];
sprintf(buf, "DPI Scale: %.1f", tCaps.fDisplayScale);
xui_widget pLbl;
xuiLabelCreate(g_pCtx, &pLbl, NULL);
xuiWidgetAddChild(pRoot, pLbl);
xuiLabelSetText(pLbl, buf);
xuiWidgetSetRect(pLbl, (xui_rect_t){220, 200, 200, 32});
xuiWidgetSetRect(pLbl, (xui_rect_t){0, 0, 200, 32});
xgeRun(onFrame, NULL);
xuiDestroy(g_pCtx);
xgeUnit();
return 0;
}