Уменьшение индикатора прогресса статического изображения по горизонтали в SDL - PullRequest
0 голосов
/ 28 июня 2018

В моем проекте у меня на дисплее отображается PNG-изображение с индикатором уменьшения таймера. Это изображение и его фон можно найти по ссылке ниже: https://s3.eksiup.com/df7dd38f781.png Моя цель - уменьшить полосу, начиная с верхней зеленой стороны до нижней красной. Мой код для этого следующий:

    void EntityTimer::OnRender(SDL_Renderer *ren)
    {
        SDL_Rect currRect,dstRect;
        double rem=0.0;

        memcpy(&currRect,&origRect,sizeof (SDL_Rect));
        memcpy(&dstRect,&origRect,sizeof (SDL_Rect));
        if (timerObjPtr->remainingDuration>timerObjPtr->durationInMilisec)
            timerObjPtr->durationInMilisec=timerObjPtr->remainingDuration;
        rem=((double)timerObjPtr->remainingDuration/timerObjPtr->durationInMilisec);

        currRect.h=(origRect.h)*rem;
        currRect.h = currRect.h;
        dstRect.x=0;
        dstRect.y=0;
        dstRect.h=currRect.h;
        SDL_RenderCopy(ren,timerTexture,&dstRect,&currRect);
    }

Так как это изображение статично, я попытался сделать это, манипулируя параметром высоты этой текстуры с помощью "currRect.h = (origRect.h) * rem;" линия. Но это заставляет индикатор выполнения уменьшаться от красной стороны к зеленой стороне (противоположность того, что я хочу).

Я пытался исправить это, но ухудшил его, отразив изображение PNG в области индикатора выполнения и снова уменьшив его снизу вверх.

Любая помощь приветствуется, так что полоса уменьшается сверху вниз (зеленым), снизу (красным).

1 Ответ

0 голосов
/ 28 июня 2018

Что ж, это довольно ожидаемо, поскольку вы рисуете из той же точки (x = 0, y = 0), но используете меньший размер. Вам необходимо обновить позицию назначения:

dstRect.y = origRect.h - origRect.h * rem;

РЕДАКТИРОВАТЬ: Это было наоборот

dstRect.y = origRect.h * rem

(при условии, что rem изменяется от 0 до 1)

Вот пример того, что вы хотите, вы можете использовать это изображение для проверки https://i.imgur.com/faKKShU.png

#include <SDL2/SDL.h>                                                        
#include <SDL2/SDL_image.h>                                                  
#include <iostream>                                                          
#include <thread>                                                            

#define HEIGHT 600                                                           
#define WIDTH  800                                                           

using namespace std;                                                         

int main() {                                                                 
    SDL_Init(SDL_INIT_VIDEO);                                                

    SDL_Window *window = SDL_CreateWindow("Red", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, WIDTH, HEIGHT, SDL_WINDOW_SHOWN);

    SDL_Renderer *renderer = SDL_CreateRenderer(window, 0, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC);

    bool quit = false;                                                       
    SDL_Event event;                                                         

    SDL_Texture *red_part = IMG_LoadTexture(renderer, "red_image.png");      

    float multiplier = 0;                                                    

    while (!quit) {                                                          
        while (SDL_PollEvent(&event)) {                                      
            if (event.type == SDL_QUIT) {                                    
                quit = true;                                                 
            }                                                                
        }                                                                    

        int y_pos = HEIGHT * multiplier;                                     
        SDL_RenderClear(renderer);                                           
        SDL_Rect copy_rect{0, y_pos, 800, 600};                              
        SDL_RenderCopy(renderer, red_part, nullptr, &copy_rect);             

        SDL_RenderPresent(renderer);                                         

        multiplier += 0.01;                                                  
        if (multiplier >= 1.)                                                
            multiplier = 1.;                                                 
        std::this_thread::sleep_for(std::chrono::milliseconds{33});          
    }                                                                        

    SDL_DestroyWindow(window);                                               
    SDL_DestroyRenderer(renderer);                                           
    SDL_Quit();                                                              

    return 0;                                                                
}
...