【问题标题】:Bottom edge of a rectangle is not straight in SDL2矩形的底边在 SDL2 中不是直的
【发布时间】:2021-05-06 18:19:04
【问题描述】:

我正在使用这个简单的函数制作矩形:

int render_cell(SDL_Renderer *renderer, int x, int y, const SDL_Color *color) {
    SDL_Rect rect;
    rect.x = x * CELL_WIDTH;
    rect.y = y * CELL_HEIGHT + 30;
    rect.w = CELL_HEIGHT;
    rect.h = CELL_WIDTH;

    SDL_SetRenderDrawColor(renderer, color->r, color->g, color->b, 255);
    SDL_RenderDrawRect(renderer, &rect);
    SDL_RenderFillRect(renderer, &rect);
}

结果,我得到了底部有“断”边的矩形:

我已经尝试避免与其他物体发生碰撞,但这没有任何区别。

此外,如您所见,线条是直的,矩形的其他边也是如此。

这是下载我的项目的谷歌驱动器链接:您需要导航到构建并在终端中输入“make”,然后输入“./game”,它就会运行。如果您有 CMake,这将起作用 https://drive.google.com/file/d/1txmb2IKEYcJOcFSUBVSZyqWyCZQDp2uR/view?usp=sharing

【问题讨论】:

  • 猜测,这看起来像是帧间“撕裂”。也就是说,绘图代码正在与显示器齐平。因此,代码正在绘制到试图显示的框架中。您的(例如)SDL_RenderPresent 在哪里刷新以前对屏幕的更改?通常是这样的:start new frame, draw, draw, draw, flush frame to display, sleep 重复。你是双缓冲吗?也就是说,绘制到一个表面,刷新那个,绘制到另一个表面,刷新那个,然后翻转缓冲区?
  • 您的程序看起来足够小,可以编辑您的问题并发布完整的 MRE,我们可以下载、编译和运行。
  • minimal reproducible example作为文本编辑到问题中;示例见this answer末尾的程序:single-file & self-contained。
  • 在您的系统上创建一个 single .c 文件,该文件通过编辑和/或剪切和粘贴仅具有 #include 的标准代码来包含您的所有代码,例如stdio.hSDL.h。您可能必须重新排序,以便(例如)如果funcB 调用funcA,则funcA 被定义之前 funcB。它应该使用(例如)干净地编译:cc -o single single.c `pkg-config --cflags --libs sdl2` 然后可以将single.c 发布在问题底部的代码块中。使用{} 图标创建另一个代码块。或者,将文本用 ``` 换行。
  • @AndreiMikhov:断边是调用函数render_grid还是调用函数render_board造成的?请提供minimal reproducible example,其中仅包含重现问题所需的代码。

标签: c rendering sdl-2


【解决方案1】:

看起来像库中的一个已知错误: https://github.com/libsdl-org/SDL/issues/4001 仅影响 openGL。

我在矩形上也看到了同样的虚线。我正在 Fedora 34 上开发。下面是一个显示问题的最小示例:

#include <SDL2/SDL.h>
#include <iostream>
#include <string>

int main(int argc, char** argv)
{
    SDL_Init(SDL_INIT_VIDEO);
    SDL_Window* window = SDL_CreateWindow("Test", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, 800, 480, 0);
    SDL_Renderer* renderer = SDL_CreateRenderer( window, -1, SDL_RENDERER_ACCELERATED);
    SDL_SetRenderDrawColor(renderer, 0xff, 0xff, 0xff, 0xff );
    SDL_Rect r = { 10, 10, 100, 100 };
    SDL_RenderDrawRect(renderer, &r);
    SDL_RenderPresent(renderer);

    // Type any text and enter to continue
    std::string dummy;
    std::cin >> dummy;

    SDL_DestroyRenderer(renderer);
    SDL_Quit();
}

我正在编译上面的内容:

g++ example.cpp -o example -lSDL2

通过以上,我得到一个带有单个白色矩形的窗口,但底线并不像 OP 在他们的屏幕截图中那样是直的。看起来右侧底角比左侧高一个像素。

【讨论】:

    【解决方案2】:

    警告:这是我的顶级 cmets 的序言。

    我无法重现您的问题。

    但是,我会详细说明我所做的事情,并就如何进行操作提出一些建议。

    我从 Google 云端硬盘下载了您的源代码 .zip。我提取了.zip 文件并将所有文件放在(例如)/home/me/cw2

    /home/me/cw2/build 目录中,我做了:

    1. rm -f CMakeCache.txt
    2. cmake /home/me/cw2
    3. make clean
    4. make
    5. ./game

    输出窗口如下。

    换句话说,我做了一个完整的重建。

    我还将文件复制到另一个目录,进行了清理并重新排列了文件,以与我在个人构建环境中构建 SDL2 程序的方式兼容。我得到了同样的结果。

    以上是在fedora 29系统上完成的。

    我也在我拥有的 ubuntu 18.04.5 系统上试过这个

    我只能建议:

    1. 进行完全重建(包括make clean
    2. 查看 pkg-config 的输出,正如我在顶级 cmets 中概述的那样
    3. 在不同的系统上重建。

    如果您使用的是 ubuntu,我过去在使用预构建的 SDL2 库包时遇到过问题。因此,在 my ubuntu 系统上,我从源代码包中重建了 SDL2。请参阅:Compile an SDL project using gcc? 考虑这是最后的手段。


    这是你的程序在我的系统上的输出。

    1. 很干净,没有半线重叠。
    2. 而且,没有左上角的“黑色区域”:

    【讨论】:

    • 为什么是DV?这太大了,无法仅发表评论。 DV 的答案是针对严重错误的答案 [根据 SO 指南]。
    • 我没有DV,但如果你不能repro,你可以投票关闭作为没有repro。
    • @HolyBlackCat l 由于 OP 的形象而没有投票关闭。因为我想详细说明可能的补救措施。我在过去遇到过cmake 进入时髦状态的问题。还有libsdl2 [可能在 nVidia Jetson 上] 的问题。如果 OP 可以确认完全重建工作或提供更多详细信息,我会相应地跟进
    猜你喜欢
    • 1970-01-01
    • 2016-07-28
    • 2015-01-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-10-31
    • 2015-12-31
    • 2014-03-20
    相关资源
    最近更新 更多