2017-10-29 16 views
-2

SDL_Rectで奇妙なエラーが発生しました。私はこの長方形とSDL_RenderFillRect、呼び出すたび:SDL_Rectが指定より大きい

SDL_Rect rect = {100, 100, 100, 100}; 

を私は常に全体の800 x 600の画面をカバーする長方形で終わります。ここで

は私のプログラムです:

#include "SDL.h" 
#include <iostream> 
#include <cstdlib> 
#include <ctime> 
#include <thread> 
#include <string> 

class Window 
{ 
public: 
    Window(std::string title, int width, int height); 
    void runEvents(SDL_Event event); 
    void drawRect(int x, int y, int h, int w); 
    bool closed = false; 
    SDL_Renderer *_renderer; 
    SDL_Window *_window; 

private: 
    int colour = 0; 
}; 

Window::Window(std::string title, int width, int height) 
{ 
    _window = SDL_CreateWindow(title.c_str(), SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, width, height, 0); 
    _renderer = SDL_CreateRenderer(_window, -1, 0); 
} 

// this function deals with rects (it's supposed to draw a rect when the mouse button is down): 
void Window::runEvents(SDL_Event event) 
{ 
    SDL_Rect rect = { 100, 100, 100, 100 }; 
    switch(event.type) 
    { 
    case SDL_QUIT: 
     closed = true; 
     break; 
    case SDL_KEYDOWN: 
     switch(event.key.keysym.sym) 
     { 
     case SDLK_ESCAPE: 
      closed = true; 
      break; 
     case SDLK_KP_1: 
      // set colour to blue 
      SDL_SetRenderDrawColor(_renderer, 0, 51, 204, 255); 
      std::cout << "Colour set to blue!" << std::endl; 
      colour = 1; 
      break; 
     case SDLK_KP_2: 
      // set colour to red 
      SDL_SetRenderDrawColor(_renderer, 255, 0, 0, 255); 
      std::cout << "Colour set to red!" << std::endl; 
      colour = 2; 
      break; 
     case SDLK_KP_3: 
      // set colour to green 
      SDL_SetRenderDrawColor(_renderer, 51, 204, 51, 255); 
      std::cout << "Colour set to green!" << std::endl; 
      colour = 3; 
      break; 
     case SDLK_KP_4: 
      SDL_SetRenderDrawColor(_renderer, 153, 0, 153, 255); 
      std::cout << "Colour set to purple!" << std::endl; 
      colour = 4; 
      break; 
     case SDLK_KP_0: 
      SDL_SetRenderDrawColor(_renderer, 255, 255, 255, 255); 
      std::cout << "Colour set to white!" << std::endl; 
      colour = 0; 
      break; 
     } 
     break; 
     //this draws the rectangle: 
    case SDL_MOUSEBUTTONDOWN: 
     SDL_SetRenderDrawColor(_renderer, 255, 0, 0, 255); 
     drawRect(rect.h, rect.y, rect.h, rect.w); 
     break; 
     //this removes it 
    case SDL_MOUSEBUTTONUP: 
     switch(colour) 
     { 
     case 1: 
      SDL_SetRenderDrawColor(_renderer, 0, 51, 204, 255); 
      break; 
     case 2: 
      SDL_SetRenderDrawColor(_renderer, 255, 0, 0, 255); 
      break; 
     case 3: 
      SDL_SetRenderDrawColor(_renderer, 51, 204, 51, 255); 
      break; 
     case 4: 
      SDL_SetRenderDrawColor(_renderer, 153, 0, 153, 255); 
      break; 
     case 0: 
      SDL_SetRenderDrawColor(_renderer, 255, 255, 255, 255); 
      break; 
     } 
     drawRect(rect.h, rect.y, rect.h, rect.w); 
     break; 
    } 
} 

//this function is supposed to draw the rect 
void Window::drawRect(int x, int y, int h, int w) 
{ 
    SDL_Rect rect = { x, y, w, h }; 
    SDL_RenderFillRect(_renderer, &rect); 
} 

bool running = true; 

void mouseCheck() 
{ 
    while(running) 
    { 
     int x; 
     int y; 
     SDL_GetMouseState(&x, &y); 
     printf("Mouse is at x: %i and y: %i\n", x, y); 
     SDL_Delay(5000); 
    } 
} 

int main(int argc, char *argv[]) 
{ 
    SDL_Init(SDL_INIT_EVERYTHING); 

    Window window("Hello World", 800, 600); 
    SDL_Event event; 

    SDL_SetRenderDrawColor(window._renderer, 255, 255, 255, 255); 

    std::thread mousePosition(mouseCheck); 
    mousePosition.detach(); 

    while(!window.closed) 
    { 
     SDL_RenderClear(window._renderer); 
     SDL_RenderPresent(window._renderer); 
     if(SDL_PollEvent(&event)) 
     { 
      window.runEvents(event); 

     } 
    } 
    return 0; 
} 

答えて

1

複数の問題:

  • 今、あなたのメインドローループがある:あなたが欲しい

    1. Draw 
    2. Clear 
    3. Present 
    

    1. (re)Set clear color 
    2. Clear 
    3. Draw 
    4. Present 
    
  • そのmouseCheck()スレッドで何をしようとしているのかは不明ですが、他のスレッドからGUI関連のSDL関数を呼び出すことは避けてください。他のスレッドでその情報が必要な場合は、スレッドセーフなアトミック/キュー/メッセージを使用して通信します。

  • あなたが代わりにrect.xの最初のパラメータとしてrect.hを持つ2つの場所でdrawRect()を呼んでいます。

  • runEvents()のように入力処理とレンダリングをインターリーブすることをお勧めします。イベントキュー(while(SDL_PollEvent()))を排出している間にシステム状態(shouldDrawRect & colour)を更新し、新しい状態(Window::drawScene())のフレームを描画します。

  • 1つのフレームにつき1つのイベントしか処理していません。各フレームをwhile(SDL_PollEvent())経由で排除して、イベントをバックアップおよび廃棄しないようにします。すべて一緒に

は:

#include "SDL.h" 
#include <iostream> 
#include <cstdlib> 
#include <ctime> 
#include <thread> 
#include <string> 

class Window 
{ 
public: 
    Window(std::string title, int width, int height); 
    void runEvents(SDL_Event event); 
    void drawScene(); 
    void drawRect(int x, int y, int h, int w); 
    bool closed = false; 
    SDL_Renderer *_renderer; 
    SDL_Window *_window; 

private: 
    bool shouldDrawRect; 
    int colour = 0; 
}; 

Window::Window(std::string title, int width, int height) 
{ 
    _window = SDL_CreateWindow(title.c_str(), SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, width, height, 0); 
    _renderer = SDL_CreateRenderer(_window, -1, 0); 
    shouldDrawRect = false; 
} 

void Window::drawScene() 
{ 
    if(shouldDrawRect) 
    { 
     switch(colour) 
     { 
     case 0: 
      SDL_SetRenderDrawColor(_renderer, 255, 0, 0, 255); 
      break; 
     case 1: 
      SDL_SetRenderDrawColor(_renderer, 0, 51, 204, 255); 
      break; 
     case 2: 
      SDL_SetRenderDrawColor(_renderer, 255, 0, 0, 255); 
      break; 
     case 3: 
      SDL_SetRenderDrawColor(_renderer, 51, 204, 51, 255); 
      break; 
     case 4: 
      SDL_SetRenderDrawColor(_renderer, 153, 0, 153, 255); 
      break; 
     } 

     SDL_Rect rect = { 100, 100, 100, 100 }; 
     drawRect(rect.x, rect.y, rect.h, rect.w); 
    } 
} 

//this function deals with rects (it's supposed to draw a rect when the mouse button is down): 
void Window::runEvents(SDL_Event event) 
{ 
    switch(event.type) 
    { 
    case SDL_QUIT: 
     closed = true; 
     break; 
    case SDL_KEYDOWN: 
     switch(event.key.keysym.sym) 
     { 
     case SDLK_ESCAPE: 
      closed = true; 
      break; 
     case SDLK_KP_1: 
      // set colour to blue 
      std::cout << "Colour set to blue!" << std::endl; 
      colour = 1; 
      break; 
     case SDLK_KP_2: 
      // set colour to red 
      std::cout << "Colour set to red!" << std::endl; 
      colour = 2; 
      break; 
     case SDLK_KP_3: 
      // set colour to green 
      std::cout << "Colour set to green!" << std::endl; 
      colour = 3; 
      break; 
     case SDLK_KP_4: 
      std::cout << "Colour set to purple!" << std::endl; 
      colour = 4; 
      break; 
     case SDLK_KP_0: 
      std::cout << "Colour set to white!" << std::endl; 
      colour = 0; 
      break; 
     } 
     break; 
     //this draws the rectangle: 
    case SDL_MOUSEBUTTONDOWN: 
     shouldDrawRect = true; 
     break; 
     //this removes it 
    case SDL_MOUSEBUTTONUP: 
     shouldDrawRect = false; 
     break; 
    } 
} 

//this function is supposed to draw the rect 
void Window::drawRect(int x, int y, int h, int w) 
{ 
    SDL_Rect rect = { x, y, w, h }; 
    SDL_RenderFillRect(_renderer, &rect); 
} 

bool running = true; 

int main(int argc, char *argv[]) 
{ 
    SDL_Init(SDL_INIT_EVERYTHING); 

    Window window("Hello World", 800, 600); 
    SDL_Event event; 

    while(!window.closed) 
    { 
     SDL_SetRenderDrawColor(window._renderer, 255, 255, 255, 255); 
     SDL_RenderClear(window._renderer); 

     while(SDL_PollEvent(&event)) 
     { 
      window.runEvents(event); 
     } 
     window.drawScene(); 

     SDL_RenderPresent(window._renderer); 
    } 
    return 0; 
} 
+0

これは見事に動作します!どうもありがとうございました。 –

関連する問題