Проблемы с производительностью SetConsoleCursorPosition и рендеринга консоли в реальном времени на C++.C++

Программы на C++. Форум разработчиков
Ответить
Anonymous
 Проблемы с производительностью SetConsoleCursorPosition и рендеринга консоли в реальном времени на C++.

Сообщение Anonymous »

Описание проблемы:
Я разрабатываю игру в консоли Windows с использованием C++ и столкнулся с проблемами производительности при рендеринге. Конвейер рендеринга включает в себя несколько вызовов SetConsoleCursorPosition и std::cout для отображения предварительно вычисленного буфера. Однако время рендеринга кадров непостоянно:
  • Генерация буфера происходит относительно быстро, занимая ~2000 микросекунд на кадр.
  • Перемещение курсора с помощью SetConsoleCursorPosition является узким местом, иногда занимающим до 20–25 миллисекунд.
  • Вывод буфера с помощью std::cout достаточно эффективен, но все же способствует задержки при сочетании с другими шагами.
Пример кода:
Вот мой текущий код итерации рендеринга:

Код: Выделить всё

void Renderer::render() {
auto frameStart = std::chrono::steady_clock::now();
auto frameEnd = std::chrono::steady_clock::now();

// Frame generation
frameStart = std::chrono::steady_clock::now();
for (int invY = 0; invY < RENDERER_HEIGHT; invY++) {
for (int x = 0; x < RENDERER_WIDTH; x++) {
buffer[(invY) * (2 * RENDERER_WIDTH + 1) + 2 * x] = ' ';
for (auto& renderable : toRender) {
if (renderable->render(x, RENDERER_HEIGHT - invY - 1) != ' ') {
buffer[(invY) * (2 * RENDERER_WIDTH + 1) + 2 * x] = renderable->render(x, RENDERER_HEIGHT - invY - 1);
}
}
buffer[(invY) * (2 * RENDERER_WIDTH + 1) + 2 * x + 1] = ' ';
}
buffer[(invY) * (2 * RENDERER_WIDTH + 1) + 2 * RENDERER_WIDTH] = '\n';
}
buffer[(2 * RENDERER_WIDTH + 1) * RENDERER_HEIGHT] = '\0';
frameEnd = std::chrono::steady_clock::now();
Logger::get()->log("Renderer frame generation time: " +
std::to_string(std::chrono::duration_cast(frameEnd - frameStart).count()));

// Cursor repositioning
frameStart = std::chrono::steady_clock::now();
SetConsoleCursorPosition(hConsole, {0, 0});
frameEnd = std::chrono::steady_clock::now();
Logger::get()->log("SetConsoleCursorPosition time: " +
std::to_string(std::chrono::duration_cast(frameEnd - frameStart).count()));

// Buffer output
frameStart = std::chrono::steady_clock::now();
std::cout , который в целом эффективно, но не устраняет задержки, вызванные изменением положения курсора.

[*]Общее время кадра меняется непредсказуемо, что влияет на рендеринг в реальном времени.< /p>

[/list]

Попытки решения проблемы:
[list]
[*]Уменьшено количество вызовов изменения положения курсора на их объединение.

[*]Использован метод двойной буферизации для минимизации мерцания.

[*]Изучены альтернативы, такие как WriteConsoleOutput, для прямого управления буфером экрана консоли.

[/list]

Вопросы:
[list]
[*]Существуют ли более быстрые альтернативы SetConsoleCursorPosition для перемещения курсора?

[*]
Подходит ли WriteConsoleOutput или аналогичный метод для повышения производительности рендеринга консоли?

[*]Какие общие методы можно использовать для оптимизации рендеринга? консольные приложения реального времени на C++?

[/list]

Спасибо за помощь! Мы будем очень признательны за любые советы и идеи. 

Подробнее здесь: [url]https://stackoverflow.com/questions/79256376/performance-issues-with-setconsolecursorposition-and-real-time-console-rendering[/url]
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «C++»