CVideoHandler.h 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288
  1. #pragma once
  2. struct SDL_Surface;
  3. class IVideoPlayer
  4. {
  5. public:
  6. virtual bool open(std::string name)=0; //true - succes
  7. virtual void close()=0;
  8. virtual bool nextFrame()=0;
  9. virtual void show(int x, int y, SDL_Surface *dst, bool update = true)=0;
  10. virtual void redraw(int x, int y, SDL_Surface *dst, bool update = true)=0; //reblits buffer
  11. virtual bool wait()=0;
  12. virtual int curFrame() const =0;
  13. virtual int frameCount() const =0;
  14. };
  15. class IMainVideoPlayer : public IVideoPlayer
  16. {
  17. public:
  18. std::string fname; //name of current video file (empty if idle)
  19. virtual void update(int x, int y, SDL_Surface *dst, bool forceRedraw, bool update = true){}
  20. virtual bool openAndPlayVideo(std::string name, int x, int y, SDL_Surface *dst, bool stopOnKey = false)
  21. {
  22. return false;
  23. }
  24. };
  25. class CEmptyVideoPlayer : public IMainVideoPlayer
  26. {
  27. public:
  28. virtual int curFrame() const {return -1;};
  29. virtual int frameCount() const {return -1;};
  30. virtual void redraw( int x, int y, SDL_Surface *dst, bool update = true ) {};
  31. virtual void show( int x, int y, SDL_Surface *dst, bool update = true ) {};
  32. virtual bool nextFrame() {return false;};
  33. virtual void close() {};
  34. virtual bool wait() {return false;};
  35. virtual bool open( std::string name ) {return false;};
  36. };
  37. #if defined(_WIN32) && (_MSC_VER < 1800 || !defined(USE_FFMPEG))
  38. #define WIN32_LEAN_AND_MEAN //excludes rarely used stuff from windows headers - delete this line if something is missing
  39. #include <windows.h>
  40. #pragma pack(push,1)
  41. struct BINK_STRUCT
  42. {
  43. si32 width;
  44. si32 height;
  45. si32 frameCount;
  46. si32 currentFrame;
  47. si32 lastFrame;
  48. si32 FPSMul;
  49. si32 FPSDiv;
  50. si32 unknown0;
  51. ui8 flags;
  52. ui8 unknown1[260];
  53. si32 CurPlane; // current plane
  54. void *plane0; // posi32er to plane 0
  55. void *plane1; // posi32er to plane 1
  56. si32 unknown2;
  57. si32 unknown3;
  58. si32 yWidth; // Y plane width
  59. si32 yHeight; // Y plane height
  60. si32 uvWidth; // U&V plane width
  61. si32 uvHeight; // U&V plane height
  62. };
  63. #pragma pack(pop)
  64. typedef BINK_STRUCT* HBINK;
  65. class DLLHandler
  66. {
  67. public:
  68. std::string name;
  69. HINSTANCE dll;
  70. void Instantiate(const char *filename);
  71. const char *GetLibExtension();
  72. void *FindAddress(const char *symbol);
  73. DLLHandler();
  74. virtual ~DLLHandler(); //d-tor
  75. };
  76. typedef void*(__stdcall* BinkSetSoundSystem)(void * soundfun, void*);
  77. typedef HBINK(__stdcall* BinkOpen)(HANDLE bikfile, int flags);
  78. typedef void(__stdcall* BinkClose)(HBINK);
  79. //typedef si32(__stdcall* BinkGetPalette)(HBINK);
  80. typedef void(__stdcall* BinkNextFrame)(HBINK);
  81. typedef void(__stdcall* BinkDoFrame)(HBINK);
  82. typedef ui8(__stdcall* BinkWait)(HBINK);
  83. typedef si32(__stdcall* BinkCopyToBuffer)(HBINK, void* buffer, int stride, int height, int x, int y, int mode);
  84. class CBIKHandler : public DLLHandler, public IVideoPlayer
  85. {
  86. void allocBuffer(int Bpp = 0);
  87. void freeBuffer();
  88. public:
  89. HANDLE hBinkFile;
  90. HBINK hBink;
  91. char * buffer;
  92. int bufferSize;
  93. BinkSetSoundSystem binkSetSoundSystem;
  94. BinkOpen binkOpen;
  95. //BinkGetPalette getPalette;
  96. BinkNextFrame binkNextFrame;
  97. BinkDoFrame binkDoFrame;
  98. BinkCopyToBuffer binkCopyToBuffer;
  99. BinkWait binkWait;
  100. BinkClose binkClose;
  101. CBIKHandler();
  102. bool open(std::string name);
  103. void close();
  104. bool nextFrame();
  105. void show(int x, int y, SDL_Surface *dst, bool update = true);
  106. void redraw(int x, int y, SDL_Surface *dst, bool update = true); //reblits buffer
  107. bool wait();
  108. int curFrame() const;
  109. int frameCount() const;
  110. };
  111. //////////SMK Player ///////////////////////////////////////////////////////
  112. struct SmackStruct
  113. {
  114. si32 version;
  115. si32 width;
  116. si32 height;
  117. si32 frameCount;
  118. si32 mspf;
  119. ui8 unk1[88];
  120. ui8 palette[776];
  121. si32 currentFrame; // Starting with 0
  122. ui8 unk[56];
  123. ui32 fileHandle; // exact type is HANDLE in windows.h
  124. };
  125. // defines function pointer types
  126. typedef SmackStruct* (__stdcall* SmackOpen)(void* , ui32, si32 );
  127. typedef int (__stdcall* SmackDoFrame)( SmackStruct * );
  128. typedef void (__stdcall * SmackGoto )(SmackStruct *, int frameNumber);
  129. typedef void (__stdcall* SmackNextFrame)(SmackStruct*);
  130. typedef void (__stdcall* SmackClose)(SmackStruct*);
  131. typedef void (__stdcall* SmackToBuffer) (SmackStruct*, int, int, int, int, char *, ui32);
  132. typedef bool (__stdcall* SmackWait)(SmackStruct*);
  133. typedef void (__stdcall* SmackSoundOnOff) (SmackStruct*, bool);
  134. typedef int (__stdcall* SmackVolumePan)(SmackStruct *, int SmackTrack, int volume, int pan);
  135. class CSmackPlayer: public DLLHandler, public IVideoPlayer
  136. {
  137. public:
  138. SmackOpen ptrSmackOpen;
  139. SmackDoFrame ptrSmackDoFrame;
  140. SmackToBuffer ptrSmackToBuffer;
  141. SmackNextFrame ptrSmackNextFrame;
  142. SmackWait ptrSmackWait;
  143. SmackSoundOnOff ptrSmackSoundOnOff;
  144. SmackClose ptrSmackClose;
  145. SmackVolumePan ptrVolumePan;
  146. char *buffer, *buf;
  147. SmackStruct* data;
  148. CSmackPlayer();
  149. ~CSmackPlayer();
  150. bool open(std::string name);
  151. void close();
  152. bool nextFrame();
  153. void show(int x, int y, SDL_Surface *dst, bool update = true);
  154. void redraw(int x, int y, SDL_Surface *dst, bool update = true); //reblits buffer
  155. bool wait();
  156. int curFrame() const;
  157. int frameCount() const;
  158. };
  159. class CVidHandler;
  160. class CVideoPlayer : public IMainVideoPlayer
  161. {
  162. private:
  163. CSmackPlayer smkPlayer; //for .SMK
  164. CBIKHandler bikPlayer; //for .BIK
  165. IVideoPlayer *current; //points to bik or smk player, appropriate to type of currently played video
  166. bool first; //are we about to display the first frame (blocks update)
  167. public:
  168. CVideoPlayer(); //c-tor
  169. ~CVideoPlayer(); //d-tor
  170. bool open(std::string name);
  171. void close();
  172. bool nextFrame(); //move animation to the next frame
  173. void show(int x, int y, SDL_Surface *dst, bool update = true); //blit current frame
  174. void redraw(int x, int y, SDL_Surface *dst, bool update = true); //reblits buffer
  175. void update(int x, int y, SDL_Surface *dst, bool forceRedraw, bool update = true); //moves to next frame if appropriate, and blits it or blits only if redraw paremeter is set true
  176. bool wait(); //true if we should wait before displaying next frame (for keeping FPS)
  177. int curFrame() const; //current frame number <1, framecount>
  178. int frameCount() const;
  179. bool openAndPlayVideo(std::string name, int x, int y, SDL_Surface *dst, bool stopOnKey = false); //opens video, calls playVideo, closes video; returns playVideo result (if whole video has been played)
  180. bool playVideo(int x, int y, SDL_Surface *dst, bool stopOnKey = false); //plays whole opened video; returns: true when whole video has been shown, false when it has been interrupted
  181. };
  182. #else
  183. #ifndef DISABLE_VIDEO
  184. #include "../lib/filesystem/CInputStream.h"
  185. #include <SDL.h>
  186. #include <SDL_video.h>
  187. #if SDL_VERSION_ATLEAST(1,3,0) && !SDL_VERSION_ATLEAST(2,0,0)
  188. #include <SDL_compat.h>
  189. #endif
  190. extern "C" {
  191. #include <libavformat/avformat.h>
  192. #include <libswscale/swscale.h>
  193. }
  194. class CVideoPlayer : public IMainVideoPlayer
  195. {
  196. int stream; // stream index in video
  197. AVFormatContext *format;
  198. AVCodecContext *codecContext; // codec context for stream
  199. AVCodec *codec;
  200. AVFrame *frame;
  201. struct SwsContext *sws;
  202. AVIOContext * context;
  203. // Destination. Either overlay or dest.
  204. #ifdef VCMI_SDL1
  205. SDL_Overlay * overlay;
  206. #else
  207. SDL_Texture *texture;
  208. #endif
  209. SDL_Surface *dest;
  210. SDL_Rect destRect; // valid when dest is used
  211. SDL_Rect pos; // destination on screen
  212. int refreshWait; // Wait several refresh before updating the image
  213. int refreshCount;
  214. bool doLoop; // loop through video
  215. bool playVideo(int x, int y, SDL_Surface *dst, bool stopOnKey);
  216. bool open(std::string fname, bool loop, bool useOverlay = false);
  217. public:
  218. CVideoPlayer();
  219. ~CVideoPlayer();
  220. bool init();
  221. bool open(std::string fname);
  222. void close();
  223. bool nextFrame(); // display next frame
  224. void show(int x, int y, SDL_Surface *dst, bool update = true); //blit current frame
  225. void redraw(int x, int y, SDL_Surface *dst, bool update = true); //reblits buffer
  226. void update(int x, int y, SDL_Surface *dst, bool forceRedraw, bool update = true); //moves to next frame if appropriate, and blits it or blits only if redraw parameter is set true
  227. // Opens video, calls playVideo, closes video; returns playVideo result (if whole video has been played)
  228. bool openAndPlayVideo(std::string name, int x, int y, SDL_Surface *dst, bool stopOnKey = false);
  229. //TODO:
  230. bool wait(){return false;};
  231. int curFrame() const {return -1;};
  232. int frameCount() const {return -1;};
  233. // public to allow access from ffmpeg IO functions
  234. std::unique_ptr<CInputStream> data;
  235. };
  236. #endif
  237. #endif