0

私は3つのことをレンダリングしようとしています:

  • gfxPrimitives を使用した幾何学的形状 (この例では円)
  • 画像/テクスチャ (オプション)
  • AntTewakBar を使用した GUI (ここから OS X 上の SDL2 用にコンパイル)

これらはそれぞれ単独では問題なく動作しますが、それらを組み合わせると、組み合わせによっては AntTweakBar が何らかの形で壊れます。

  1. AntTweakBar のみ: すべてを適切にレンダリングします 円とテクスチャがなくても問題なく動作します
  2. AntTweakBar + Texture : TestBar でテキスト以外のすべてが消えました。マウスは以前と同じ位置にありますが、「幅」が強調表示されておらず、すべての「アイコン」が欠落しています。どういうわけか、「ヘルプとショートカット」バーの背景は生き残った。テクスチャを再度削除しても何も変わりません。円を追加すると、ケース3につながります しかし、これをファック
  3. AntTweakBar + Circle (+Texture) : テキスト以外のすべてがレンダリングされ、テキストがボックスに変わります。テクスチャを追加したり、円を再度削除したりしても何も変わりませんが、最初に円を削除してからテクスチャを追加すると、ケース2につながります。 そしてそれ

これは、このテスト アプリケーションの (乱雑な) ソース コードです。ここres_path.hここcleanup.hで見つけることができます(ただし、問題ではありません)。

#include <iostream>
#include <SDL2/SDL.h>
#include "res_path.h"
#include "cleanup.h"
#include "SDL2/SDL2_gfxPrimitives.h"
#include <AntTweakBar.h>

const int SCREEN_WIDTH  = 640;
const int SCREEN_HEIGHT = 480;

bool quit = false;
bool tex = false;
bool circ = false;

//-----------------------------------------------------------------------

/**
 * Log an SDL error with some error message to the output stream of our choice
 * @param os The output stream to write the message to
 * @param msg The error message to write, format will be msg error: SDL_GetError()
 */
void logSDLError(std::ostream &os, const std::string &msg)
{
    os << msg << " error: " << SDL_GetError() << std::endl;
}

/**
 * Loads a BMP image into a texture on the rendering device
 * @param file The BMP image file to load
 * @param ren The renderer to load the texture onto
 * @return the loaded texture, or nullptr if something went wrong.
 */
SDL_Texture* loadTexture(const std::string &file, SDL_Renderer *ren)
{
    //Initialize to nullptr to avoid dangling pointer issues
    SDL_Texture *texture = nullptr;
    //Load the image
    SDL_Surface *loadedImage = SDL_LoadBMP(file.c_str());
    //If the loading went ok, convert to texture and return the texture
    if (loadedImage != nullptr){
        texture = SDL_CreateTextureFromSurface(ren, loadedImage);
        SDL_FreeSurface(loadedImage);
        //Make sure converting went ok too
        if (texture == nullptr){
            logSDLError(std::cout, "CreateTextureFromSurface");
        }
    }
    else {
        logSDLError(std::cout, "LoadBMP");
    }
    return texture;
}


/**
 * Draw an SDL_Texture to an SDL_Renderer at position x, y, preserving
 * the texture's width and height
 * @param tex The source texture we want to draw
 * @param ren The renderer we want to draw to
 * @param x The x coordinate to draw to
 * @param y The y coordinate to draw to
 */
void renderTexture(SDL_Texture *tex, SDL_Renderer *ren, int x, int y)
{
    //Setup the destination rectangle to be at the position we want
    SDL_Rect dst;
    dst.x = x;
    dst.y = y;
    //Query the texture to get its width and height to use
    SDL_QueryTexture(tex, NULL, NULL, &dst.w, &dst.h);
    SDL_RenderCopy(ren, tex, NULL, &dst);
}

void TW_CALL RunCA(void * /*clientData*/)
{
    std::cout << "button 1 clicked" << std::endl;
    tex = !tex;
}
void TW_CALL RunCB(void * /*clientData*/)
{
    std::cout << "button 2 clicked" << std::endl;
    circ = !circ;
}

//---------------------------------------

int main()
{

    int size=10;
    int alpha=100;

    std::cout << "Resource path is: " << getResourcePath() << std::endl;

    if (SDL_Init(SDL_INIT_EVERYTHING) != 0){
        logSDLError(std::cout, "SDL_Init");
        return 1;
    }

    SDL_Window *window = SDL_CreateWindow("Lesson 2", SDL_WINDOWPOS_CENTERED,
        SDL_WINDOWPOS_CENTERED, SCREEN_WIDTH,SCREEN_HEIGHT, SDL_WINDOW_SHOWN);
    if (window == nullptr){
        logSDLError(std::cout, "CreateWindow");
        SDL_Quit();
        return 1;
    }
    SDL_Renderer *renderer = SDL_CreateRenderer(window, -1,
            SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE);
    if (renderer == nullptr){
        logSDLError(std::cout, "CreateRenderer");
        cleanup(window);
        SDL_Quit();
        return 1;
    }


    const std::string resPath = getResourcePath();
    SDL_Texture *image = loadTexture(resPath + "image.bmp", renderer);
    if (image == nullptr){
        cleanup(image, renderer, window);
        SDL_Quit();
        return 1;
    }


    TwInit(TW_OPENGL, NULL);
    TwWindowSize(SCREEN_WIDTH, SCREEN_HEIGHT);

    TwBar *myBar;
    myBar = TwNewBar("TestBar");
    TwDefine(" GLOBAL help='example help' "); // Message added to the help bar.

    TwAddButton(myBar, "Switch Texture", RunCA, NULL, " label='texture' ");
    TwAddButton(myBar, "Switch Circle", RunCB, NULL, " label='circle' ");

    TwAddVarRW(myBar, "width", TW_TYPE_INT32, &size, " keyIncr=w, keyDecr=s ");
    TwAddVarRW(myBar, "alpha", TW_TYPE_INT32, &alpha, " ");
    // Add 'quit' to 'bar': this is a modifiable (RW) variable of type TW_TYPE_BOOL32
    // (a boolean stored in a 32 bits integer). Its shortcut is [ESC].
    TwAddVarRW(myBar, "Quit", TW_TYPE_BOOL32, &quit,
        " label='Quit?' true='+' false='-' key='ESC' help='Quit program.' ");

    // main loop
    while( !quit )
    {
        SDL_Event event;
        int handled=1;

        SDL_SetRenderDrawColor(renderer, 255, 0, 0, 255);
        SDL_RenderClear(renderer);

        if(tex)
        renderTexture(image, renderer, 50, 50);

        if(circ)
        filledCircleRGBA(renderer,
                100, 100,
                size,
                0, 255, 0, alpha);


        TwDraw();  // draw the tweak bar(s)


        SDL_RenderPresent(renderer);

        while(SDL_PollEvent(&event))
        {
            handled = TwEventSDL(&event, SDL_MAJOR_VERSION, SDL_MINOR_VERSION);
            if( !handled )
            {
                //If user closes the window
                if (event.type == SDL_QUIT){
                    std::cout << "window closed" << std::endl;
                    quit = true;
                }
                //If user presses any key
                if (event.type == SDL_KEYDOWN){
                    std::cout << "key down" << std::endl;
                }
                //If user clicks the mouse
                if (event.type == SDL_MOUSEBUTTONDOWN){
                    std::cout << "mouse clicked" << std::endl;
                }
            }    
        }

    //      SDL_Delay(10);


    } // end of main loop


//cleanup
cleanup(image, renderer, window);
// Terminate AntTweakBar
TwTerminate();
SDL_Quit();
return 0;
}

何が起こっているのか、これを修正または回避する方法を知っている人はいますか? そうでない場合は、SDL2/C++ で単純な幾何学的形状と GUI (いくつかのパラメーターを構成するため) をそれほど労力をかけずにレンダリングするための別のアプローチを誰かが推奨できるかもしれません。

4

1 に答える 1

0

開発環境を OSX (10.11.1) から Linux (Ubuntu 14.04-3) に変更することで回避しました。もちろん、これは「本当の」解決策ではありませんが、この情報は誰かの役に立つかもしれません。

于 2015-11-23T15:44:30.507 に答える