gpt4 book ai didi

c++ - WinAPI - 获取用于绘图的可滚动框架

转载 作者:行者123 更新时间:2023-11-28 04:15:02 28 4
gpt4 key购买 nike

作为一项暑期工作,我正在编写一种算法,通过较冷的物体计算序列。算法本身已经完成,我开始研究使用 C++ 制作一个简单的 GUI,您可以在其中为特定的冷却器组合创建序列,并且能够预先查看它。这不是我以前做过的任何事。

我有一些相当简单的工作,现在我直接在主窗口上绘制序列的外观。将它绘制到同一个主窗口中的可滚动“框架”中会不会有什么困难?现在,更大的组合太大而无法显示在同一屏幕上,仅仅让窗口变大是不够的。感谢您的帮助!

我尝试使用样式“WS_VSCROLL”制作一个静态文件并使用“hdc = GetDC(hWndNewStatic)”,我用它处理了一小段时间的绘图,然后它又不起作用了。滚动条不工作。

example program pic

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
LPSTR lpCmdLine, int nCmdShow)
{

WNDCLASSEX wcex = {};
wcex.cbClsExtra = 0;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.cbWndExtra = 0;
wcex.hbrBackground = (HBRUSH)(COLOR_BTNFACE + 1);
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE (IDI_ICON));
wcex.hIconSm = LoadIcon(hInstance, MAKEINTRESOURCE (IDI_ICON));
wcex.hInstance = hInstance;
wcex.lpfnWndProc = WndProc;
wcex.lpszClassName = TEXT("WinApp");
wcex.lpszMenuName = NULL;
wcex.style = CS_HREDRAW | CS_VREDRAW;

if (!RegisterClassEx(&wcex))
{
MessageBox(NULL, TEXT("RegisterClassEx Failed!"), TEXT("Error"), MB_ICONERROR);
return EXIT_FAILURE;
}

HWND hWnd = CreateWindow(
TEXT("WinApp"), TEXT("SeqGen"),
WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX | WS_MAXIMIZEBOX,
CW_USEDEFAULT, CW_USEDEFAULT, WINDOW_WIDTH, WINDOW_HEIGHT,
NULL, NULL, hInstance, NULL
);

if (!hWnd)
{
MessageBox(NULL, TEXT("CreateWindow Failed!"), TEXT("Error"), MB_ICONERROR);
return EXIT_FAILURE;
}

ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);

hdc = GetDC(hWnd);

// Messages
MSG msg;

while (GetMessage(&msg, NULL, 0, 0))
{
if (IsDialogMessage(hWnd, &msg))
{}
else
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return EXIT_SUCCESS;
}

LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{

LPCSTR moduleValue;
static int index {};
static unsigned module {0};
static bool draw {false};

switch (msg)
{
case WM_CREATE:
hWndStatic = CreateWindow(
TEXT("Static"), TEXT("Tube rows"),
WS_CHILD | WS_VISIBLE,
30, 20, 100, 24,
hWnd, NULL, NULL, NULL
);

hWndStatic = CreateWindow(
TEXT("Static"), TEXT("Water passes"),
WS_CHILD | WS_VISIBLE,
130, 20, 100, 24,
hWnd, NULL, NULL, NULL
);

hWndStatic = CreateWindow(
TEXT("Static"), TEXT("Multiples"),
WS_CHILD | WS_VISIBLE,
230, 20, 100, 24,
hWnd, NULL, NULL, NULL
);

hWndrr = CreateWindowEx(
WS_EX_CLIENTEDGE, TEXT("Edit"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_TABSTOP,
30, 50, 50, 24,
hWnd, NULL, NULL, NULL
);

hWndvv = CreateWindowEx(
WS_EX_CLIENTEDGE, TEXT("Edit"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_TABSTOP,
130, 50, 50, 24,
hWnd, NULL, NULL, NULL
);

hWndN = CreateWindowEx(
WS_EX_CLIENTEDGE, TEXT("Edit"), TEXT("0"),
WS_CHILD | WS_VISIBLE | WS_TABSTOP,
230, 50, 50, 24,
hWnd, NULL, NULL, NULL
);

hWndList = CreateWindow(
TEXT("ListBox"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_VSCROLL | ES_AUTOVSCROLL | WS_BORDER | LBS_NOTIFY,
20, 150, TEXTBOX_WIDTH, TEXTBOX_HEIGHT,
hWnd, (HMENU) LST_RESULT, NULL, NULL
);


hWndCreateall = CreateWindow(
TEXT("Button"), TEXT("Create all DIR"),
WS_CHILD | WS_VISIBLE,
50, 90, 100, 24,
hWnd, (HMENU) BTN_CREATEALL, NULL, NULL
);

hWndButton = CreateWindow(
TEXT("Button"), TEXT("Create DIR"),
WS_CHILD | WS_VISIBLE | WS_TABSTOP,
200, 90, 100, 24,
hWnd, (HMENU) BTN_CREATE, NULL, NULL
);

break;

case WM_COMMAND:
switch (HIWORD(wParam))
{
case LBN_SELCHANGE:
if (LOWORD(wParam) == LST_RESULT)
{
index = SendMessage(hWndList, LB_GETCURSEL, 0, 0);

if (index >= 0)
{
module = 0;
moduleValue = (to_string(module).c_str());
SetWindowText(hWndStaticModule, moduleValue);
draw = true;
RedrawWindow(hWnd, 0, 0, RDW_INVALIDATE);
}
}
break;

case BN_CLICKED:
switch (LOWORD(wParam))
{
case BTN_CREATE:
--stuff for creating combination--

break;

case BTN_CREATEALL:
--stuff for creating all possible combination--

break;
}

break;

default:
break;
}
break;

case WM_PAINT:
if (draw)
{
--function for drawing stuff on main window--

draw = false;
}
UpdateWindow(hWnd);

break;

case WM_DESTROY:
PostQuitMessage(EXIT_SUCCESS);

default:
return DefWindowProc(hWnd, msg, wParam, lParam);
}
return FALSE;
}

最佳答案

你需要大量的代码来实现你所需要的,我只能对你需要的组件进行理论上的解释。

  1. 面板类。一个面板需要它自己的窗口类和它自己的 windowproc。 Panel proc 应该处理 WM_VSCROLL,也许还有 WM_HSCROLL手动使用 SetScrollPos 设置新的滚动值并将其存储在一些状态变量。您的 WM_*SCROLL 处理程序现在有两个选项:
    • 调用InvalidateRect,让WM_PAINT刷新整个面板。
    • 调用 ScrollWindow 移动实际图形,然后调用 UpdateWindow 刷新未覆盖区域。
  2. 面板的绘制算法。您应该像往常一样对 WM_PAINT 绘制您的模型使用react,但是 y 坐标必须通过滚动状态变量进行移动。你有几个选择:
    • 重绘整个窗口。
    • 在屏幕外的 HDC 上绘制新窗口内容,然后在整个窗口上进行 bitblit。
    • 重绘未覆盖区域(参见上一点关于ScrollWindow)
  3. 主窗口上的面板实例。主 win 将像您为其他控件所做的那样将面板分配为子窗口,还指定 WS_VSCROLL(和 WS_HSCROLL?)并使用 SetScrollInfo 配置滚动大小,根据文件大小。 Main win 还需要对 WM_SIZE 使用react,以调整面板的大小(MoveWindow),给它一个新的大小。新尺寸的计算方法是从主胜利的客户区中减去您喜欢的填充。

每一小点最终都需要进一步谷歌搜索并在 SO 上发布。

您还可以考虑使用 OpenGL、DirectX 或仅使用 GDI+ 进行绘图(这反过来可能会引发很多其他问题)。

关于c++ - WinAPI - 获取用于绘图的可滚动框架,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56865771/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com