1 // Copyright 2019 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef CAST_STANDALONE_RECEIVER_SDL_GLUE_H_ 6 #define CAST_STANDALONE_RECEIVER_SDL_GLUE_H_ 7 8 #include <stdint.h> 9 10 #include <functional> 11 #include <memory> 12 13 #pragma GCC diagnostic push 14 #pragma GCC diagnostic ignored "-Wimplicit-fallthrough" 15 #include <SDL2/SDL.h> 16 #pragma GCC diagnostic pop 17 18 #include "util/alarm.h" 19 20 namespace openscreen { 21 22 class TaskRunner; 23 24 namespace cast { 25 26 template <uint32_t subsystem> 27 class ScopedSDLSubSystem { 28 public: ScopedSDLSubSystem()29 ScopedSDLSubSystem() { SDL_InitSubSystem(subsystem); } ~ScopedSDLSubSystem()30 ~ScopedSDLSubSystem() { SDL_QuitSubSystem(subsystem); } 31 }; 32 33 // Macro that, for an SDL_Foo, generates code for: 34 // 35 // using SDLFooUniquePtr = std::unique_ptr<SDL_Foo, SDLFooDestroyer>; 36 // SDLFooUniquePtr MakeUniqueSDLFoo(...args...); 37 #define DEFINE_SDL_UNIQUE_PTR(name) \ 38 struct SDL##name##Destroyer { \ 39 void operator()(SDL_##name* obj) const { \ 40 if (obj) { \ 41 SDL_Destroy##name(obj); \ 42 } \ 43 } \ 44 }; \ 45 using SDL##name##UniquePtr = \ 46 std::unique_ptr<SDL_##name, SDL##name##Destroyer>; \ 47 template <typename... Args> \ 48 SDL##name##UniquePtr MakeUniqueSDL##name(Args&&... args) { \ 49 return SDL##name##UniquePtr( \ 50 SDL_Create##name(std::forward<Args>(args)...)); \ 51 } 52 53 DEFINE_SDL_UNIQUE_PTR(Window); 54 DEFINE_SDL_UNIQUE_PTR(Renderer); 55 DEFINE_SDL_UNIQUE_PTR(Texture); 56 57 #undef DEFINE_SDL_UNIQUE_PTR 58 59 // A looping mechanism that runs the SDL event loop by scheduling periodic tasks 60 // to the given TaskRunner. Looping continues indefinitely, until the instance 61 // is destroyed. A client-provided quit callback is invoked whenever a SDL_QUIT 62 // event is received. 63 class SDLEventLoopProcessor { 64 public: 65 SDLEventLoopProcessor(TaskRunner* task_runner, 66 std::function<void()> quit_callback); 67 ~SDLEventLoopProcessor(); 68 69 private: 70 void ProcessPendingEvents(); 71 72 Alarm alarm_; 73 std::function<void()> quit_callback_; 74 }; 75 76 } // namespace cast 77 } // namespace openscreen 78 79 #endif // CAST_STANDALONE_RECEIVER_SDL_GLUE_H_ 80