Merge 98abef4de5
into 272010b612
This commit is contained in:
commit
0b8ef08d4b
|
@ -2009,6 +2009,11 @@ elseif(APPLE)
|
|||
set(HAVE_SDL_FILE TRUE)
|
||||
endif()
|
||||
|
||||
if(IOS OR TVOS OR MACOSX OR DARWIN)
|
||||
file(GLOB SDL_VIDEO_CAPTURE_SOURCES ${SDL3_SOURCE_DIR}/src/video/SDL_video_capture_apple.m)
|
||||
list(APPEND SOURCE_FILES ${SDL_VIDEO_CAPTURE_SOURCES})
|
||||
endif()
|
||||
|
||||
if(SDL_MISC)
|
||||
if(IOS OR TVOS)
|
||||
file(GLOB MISC_SOURCES ${SDL3_SOURCE_DIR}/src/misc/ios/*.m)
|
||||
|
@ -2201,6 +2206,11 @@ elseif(APPLE)
|
|||
|
||||
# Actually load the frameworks at the end so we don't duplicate include.
|
||||
if(SDL_FRAMEWORK_COREVIDEO)
|
||||
find_library(COREMEDIA CoreMedia)
|
||||
if(COREMEDIA)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DHAVE_COREMEDIA=1")
|
||||
list(APPEND SDL_EXTRA_LDFLAGS "-Wl,-weak_framework,CoreMedia")
|
||||
endif()
|
||||
list(APPEND SDL_EXTRA_LDFLAGS "-Wl,-framework,CoreVideo")
|
||||
endif()
|
||||
if(SDL_FRAMEWORK_COCOA)
|
||||
|
|
|
@ -487,6 +487,7 @@
|
|||
<ClCompile Include="..\src\video\SDL_stretch.c" />
|
||||
<ClCompile Include="..\src\video\SDL_surface.c" />
|
||||
<ClCompile Include="..\src\video\SDL_video.c" />
|
||||
<ClCompile Include="..\src\video\SDL_video_capture.c" />
|
||||
<ClCompile Include="..\src\video\SDL_yuv.c" />
|
||||
<ClCompile Include="..\src\video\winrt\SDL_winrtevents.cpp">
|
||||
<CompileAsWinRT>true</CompileAsWinRT>
|
||||
|
|
|
@ -756,6 +756,9 @@
|
|||
<ClCompile Include="..\src\video\SDL_video.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\video\SDL_video_capture.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\video\winrt\SDL_winrtevents.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
|
|
|
@ -630,6 +630,7 @@
|
|||
<ClCompile Include="..\..\src\video\SDL_stretch.c" />
|
||||
<ClCompile Include="..\..\src\video\SDL_surface.c" />
|
||||
<ClCompile Include="..\..\src\video\SDL_video.c" />
|
||||
<ClCompile Include="..\..\src\video\SDL_video_capture.c" />
|
||||
<ClCompile Include="..\..\src\video\SDL_vulkan_utils.c" />
|
||||
<ClCompile Include="..\..\src\video\SDL_yuv.c" />
|
||||
<ClCompile Include="..\..\src\video\windows\SDL_windowsclipboard.c" />
|
||||
|
|
|
@ -1144,6 +1144,9 @@
|
|||
<ClCompile Include="..\..\src\video\SDL_video.c">
|
||||
<Filter>video</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\src\video\SDL_video_capture.c">
|
||||
<Filter>video</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\..\src\video\SDL_yuv.c">
|
||||
<Filter>video</Filter>
|
||||
</ClCompile>
|
||||
|
|
|
@ -130,6 +130,54 @@
|
|||
A1626A582617008D003F1973 /* SDL_triangle.h in Headers */ = {isa = PBXBuildFile; fileRef = A1626A512617008C003F1973 /* SDL_triangle.h */; };
|
||||
A1626A592617008D003F1973 /* SDL_triangle.h in Headers */ = {isa = PBXBuildFile; fileRef = A1626A512617008C003F1973 /* SDL_triangle.h */; };
|
||||
A1626A5A2617008D003F1973 /* SDL_triangle.h in Headers */ = {isa = PBXBuildFile; fileRef = A1626A512617008C003F1973 /* SDL_triangle.h */; };
|
||||
A16680C229967B6900318FE2 /* SDL_video_capture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C129967B6900318FE2 /* SDL_video_capture.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
A16680C329967B6900318FE2 /* SDL_video_capture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C129967B6900318FE2 /* SDL_video_capture.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
A16680C429967B6900318FE2 /* SDL_video_capture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C129967B6900318FE2 /* SDL_video_capture.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
A16680CA29967BD100318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680CB29967BD100318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680CC29967BD100318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680CD29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680CE29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680CF29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680D029967BD100318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680D129967BD100318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680D229967BD100318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680D329967BD100318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680D429967BD100318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680D529967BD100318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680D629967BD100318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680D729967BD100318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680D829967BD100318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680D929967BEE00318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DA29967BEE00318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DB29967BEF00318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DC29967BEF00318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DD29967BF000318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DE29967BF000318FE2 /* SDL_sysvideocapture.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */; };
|
||||
A16680DF29967C0A00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680E029967C0A00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680E129967C0A00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680E229967C0A00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680E329967C0A00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680E429967C0A00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680E529967C0B00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680E629967C0B00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680E729967C0B00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680E829967C0B00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680E929967C0B00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680EA29967C0B00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680EB29967C0C00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680EC29967C0C00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680ED29967C0C00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680EE29967C0C00318FE2 /* SDL_video_capture.c in Sources */ = {isa = PBXBuildFile; fileRef = A16680C529967BD000318FE2 /* SDL_video_capture.c */; };
|
||||
A16680EF29967C0C00318FE2 /* SDL_video_capture_apple.m in Sources */ = {isa = PBXBuildFile; fileRef = A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */; };
|
||||
A16680F029967C0C00318FE2 /* SDL_video_capture_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C929967BD100318FE2 /* SDL_video_capture_c.h */; };
|
||||
A16680F129967C1B00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680F229967C1C00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680F329967C1C00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680F429967C1C00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680F529967C1D00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A16680F629967C1D00318FE2 /* SDL_video_c.h in Headers */ = {isa = PBXBuildFile; fileRef = A16680C729967BD100318FE2 /* SDL_video_c.h */; };
|
||||
A1BB8B6327F6CF330057CFA8 /* SDL_list.c in Sources */ = {isa = PBXBuildFile; fileRef = A1BB8B6127F6CF320057CFA8 /* SDL_list.c */; };
|
||||
A1BB8B6427F6CF330057CFA8 /* SDL_list.c in Sources */ = {isa = PBXBuildFile; fileRef = A1BB8B6127F6CF320057CFA8 /* SDL_list.c */; };
|
||||
A1BB8B6527F6CF330057CFA8 /* SDL_list.c in Sources */ = {isa = PBXBuildFile; fileRef = A1BB8B6127F6CF320057CFA8 /* SDL_list.c */; };
|
||||
|
@ -3490,6 +3538,12 @@
|
|||
9846B07B287A9020000C35C8 /* SDL_hidapi_shield.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = SDL_hidapi_shield.c; sourceTree = "<group>"; };
|
||||
A1626A3D2617006A003F1973 /* SDL_triangle.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = SDL_triangle.c; sourceTree = "<group>"; };
|
||||
A1626A512617008C003F1973 /* SDL_triangle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SDL_triangle.h; sourceTree = "<group>"; };
|
||||
A16680C129967B6900318FE2 /* SDL_video_capture.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = SDL_video_capture.h; path = SDL3/SDL_video_capture.h; sourceTree = "<group>"; };
|
||||
A16680C529967BD000318FE2 /* SDL_video_capture.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = SDL_video_capture.c; sourceTree = "<group>"; };
|
||||
A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SDL_sysvideocapture.h; sourceTree = "<group>"; };
|
||||
A16680C729967BD100318FE2 /* SDL_video_c.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SDL_video_c.h; sourceTree = "<group>"; };
|
||||
A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SDL_video_capture_apple.m; sourceTree = "<group>"; };
|
||||
A16680C929967BD100318FE2 /* SDL_video_capture_c.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SDL_video_capture_c.h; sourceTree = "<group>"; };
|
||||
A1BB8B6127F6CF320057CFA8 /* SDL_list.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = SDL_list.c; sourceTree = "<group>"; };
|
||||
A1BB8B6227F6CF330057CFA8 /* SDL_list.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SDL_list.h; sourceTree = "<group>"; };
|
||||
A7381E931D8B69C300B177DD /* AudioToolbox.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AudioToolbox.framework; path = System/Library/Frameworks/AudioToolbox.framework; sourceTree = SDKROOT; };
|
||||
|
@ -4160,6 +4214,7 @@
|
|||
F3F7D8AF2933074900816151 /* SDL_touch.h */,
|
||||
F3F7D8E42933074D00816151 /* SDL_version.h */,
|
||||
F3F7D8C52933074B00816151 /* SDL_video.h */,
|
||||
A16680C129967B6900318FE2 /* SDL_video_capture.h */,
|
||||
F3F7D8D42933074C00816151 /* SDL_vulkan.h */,
|
||||
);
|
||||
name = "Public Headers";
|
||||
|
@ -4493,7 +4548,12 @@
|
|||
A7D8A60323E2513D00DCD162 /* SDL_stretch.c */,
|
||||
A7D8A61423E2513D00DCD162 /* SDL_surface.c */,
|
||||
A7D8A61723E2513D00DCD162 /* SDL_sysvideo.h */,
|
||||
A16680C629967BD000318FE2 /* SDL_sysvideocapture.h */,
|
||||
A7D8A60E23E2513D00DCD162 /* SDL_video.c */,
|
||||
A16680C729967BD100318FE2 /* SDL_video_c.h */,
|
||||
A16680C829967BD100318FE2 /* SDL_video_capture_apple.m */,
|
||||
A16680C929967BD100318FE2 /* SDL_video_capture_c.h */,
|
||||
A16680C529967BD000318FE2 /* SDL_video_capture.c */,
|
||||
A7D8A63E23E2513D00DCD162 /* SDL_vulkan_internal.h */,
|
||||
A7D8A64023E2513D00DCD162 /* SDL_vulkan_utils.c */,
|
||||
A7D8A76A23E2513E00DCD162 /* SDL_yuv_c.h */,
|
||||
|
@ -5190,6 +5250,7 @@
|
|||
A75FCDD623E25AB700529352 /* SDL_dynapi_procs.h in Headers */,
|
||||
A75FCD1F23E25AB700529352 /* SDL_egl_c.h in Headers */,
|
||||
A75FCD1923E25AB700529352 /* SDL_error_c.h in Headers */,
|
||||
A16680DD29967BF000318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A75FCD7923E25AB700529352 /* SDL_events_c.h in Headers */,
|
||||
A75FCD8B23E25AB700529352 /* SDL_gamepad_db.h in Headers */,
|
||||
A75FCDDB23E25AB700529352 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -5204,6 +5265,7 @@
|
|||
A75FCDC823E25AB700529352 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B7327F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6EE2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680ED29967C0C00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1C12569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A75FCDCC23E25AB700529352 /* SDL_mouse_c.h in Headers */,
|
||||
A75FCD8523E25AB700529352 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -5221,6 +5283,7 @@
|
|||
A75FCDBE23E25AB700529352 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A75FCD9623E25AB700529352 /* SDL_sensor_c.h in Headers */,
|
||||
A75FCD4623E25AB700529352 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F529967C1D00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A75FCD8023E25AB700529352 /* SDL_shaders_gles2.h in Headers */,
|
||||
A75FCD0C23E25AB700529352 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A75FCD0B23E25AB700529352 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -5355,6 +5418,7 @@
|
|||
A75FCF8F23E25AC700529352 /* SDL_dynapi_procs.h in Headers */,
|
||||
A75FCED823E25AC700529352 /* SDL_egl_c.h in Headers */,
|
||||
A75FCED223E25AC700529352 /* SDL_error_c.h in Headers */,
|
||||
A16680DE29967BF000318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A75FCF3223E25AC700529352 /* SDL_events_c.h in Headers */,
|
||||
A75FCF4423E25AC700529352 /* SDL_gamepad_db.h in Headers */,
|
||||
A75FCF9423E25AC700529352 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -5369,6 +5433,7 @@
|
|||
A75FCF8123E25AC700529352 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B7427F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6EF2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680F029967C0C00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1C22569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A75FCF8523E25AC700529352 /* SDL_mouse_c.h in Headers */,
|
||||
A75FCF3E23E25AC700529352 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -5386,6 +5451,7 @@
|
|||
A75FCF7723E25AC700529352 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A75FCF4F23E25AC700529352 /* SDL_sensor_c.h in Headers */,
|
||||
A75FCEFF23E25AC700529352 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F629967C1D00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A75FCF3923E25AC700529352 /* SDL_shaders_gles2.h in Headers */,
|
||||
A75FCEC523E25AC700529352 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A75FCEC423E25AC700529352 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -5520,6 +5586,7 @@
|
|||
A769B15D23E259AE00872273 /* SDL_dynapi_procs.h in Headers */,
|
||||
A769B0A623E259AE00872273 /* SDL_egl_c.h in Headers */,
|
||||
A769B0A023E259AE00872273 /* SDL_error_c.h in Headers */,
|
||||
A16680DB29967BEF00318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A769B10123E259AE00872273 /* SDL_events_c.h in Headers */,
|
||||
A769B11123E259AE00872273 /* SDL_gamepad_db.h in Headers */,
|
||||
A769B16323E259AE00872273 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -5534,6 +5601,7 @@
|
|||
A769B14F23E259AE00872273 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B7127F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6EC2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680E729967C0B00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1BF2569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A769B15323E259AE00872273 /* SDL_mouse_c.h in Headers */,
|
||||
A769B10C23E259AE00872273 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -5551,6 +5619,7 @@
|
|||
A769B14523E259AE00872273 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A769B11E23E259AE00872273 /* SDL_sensor_c.h in Headers */,
|
||||
A769B0CC23E259AE00872273 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F329967C1C00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A769B10723E259AE00872273 /* SDL_shaders_gles2.h in Headers */,
|
||||
A769B09323E259AE00872273 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A769B09223E259AE00872273 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -5678,6 +5747,7 @@
|
|||
A7D8AEE923E2514100DCD162 /* SDL_cocoavulkan.h in Headers */,
|
||||
A7D8AEFB23E2514100DCD162 /* SDL_cocoawindow.h in Headers */,
|
||||
F3F7D9D22933074E00816151 /* SDL_copying.h in Headers */,
|
||||
A16680D129967BD100318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8B8CD23E2514400DCD162 /* SDL_coreaudio.h in Headers */,
|
||||
A7D8A97023E2514000DCD162 /* SDL_coremotionsensor.h in Headers */,
|
||||
F3F7D9BA2933074E00816151 /* SDL_cpuinfo.h in Headers */,
|
||||
|
@ -5693,6 +5763,7 @@
|
|||
A7D8A96423E2514000DCD162 /* SDL_dummysensor.h in Headers */,
|
||||
A7D8AB0B23E2514100DCD162 /* SDL_dynapi.h in Headers */,
|
||||
A7D8AB1123E2514100DCD162 /* SDL_dynapi_overrides.h in Headers */,
|
||||
A16680C329967B6900318FE2 /* SDL_video_capture.h in Headers */,
|
||||
A7D8AB1D23E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
F3F7D9262933074E00816151 /* SDL_egl.h in Headers */,
|
||||
A7D8ABDA23E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
|
@ -5765,6 +5836,7 @@
|
|||
A7D8AC0423E2514100DCD162 /* SDL_rect_c.h in Headers */,
|
||||
F3F7D9BE2933074E00816151 /* SDL_render.h in Headers */,
|
||||
A7D8B9FC23E2514400DCD162 /* SDL_render_sw_c.h in Headers */,
|
||||
A16680CE29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
F3F7D9162933074E00816151 /* SDL_revision.h in Headers */,
|
||||
A7D8BA3223E2514400DCD162 /* SDL_rotate.h in Headers */,
|
||||
F3F7D9662933074E00816151 /* SDL_rwops.h in Headers */,
|
||||
|
@ -5777,6 +5849,7 @@
|
|||
A7D8B98D23E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B99C23E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
A7D8B9A223E2514400DCD162 /* SDL_shaders_metal_tvos.h in Headers */,
|
||||
A16680D729967BD100318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F3F7D92E2933074E00816151 /* SDL_shape.h in Headers */,
|
||||
A7D8AC0A23E2514100DCD162 /* SDL_shape_internals.h in Headers */,
|
||||
F3F7D8F62933074E00816151 /* SDL_stdinc.h in Headers */,
|
||||
|
@ -5911,6 +5984,7 @@
|
|||
A7D8AEEA23E2514100DCD162 /* SDL_cocoavulkan.h in Headers */,
|
||||
A7D8AEFC23E2514100DCD162 /* SDL_cocoawindow.h in Headers */,
|
||||
F3F7D9D32933074E00816151 /* SDL_copying.h in Headers */,
|
||||
A16680D229967BD100318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8B8CE23E2514400DCD162 /* SDL_coreaudio.h in Headers */,
|
||||
A7D8A97123E2514000DCD162 /* SDL_coremotionsensor.h in Headers */,
|
||||
F3F7D9BB2933074E00816151 /* SDL_cpuinfo.h in Headers */,
|
||||
|
@ -5926,6 +6000,7 @@
|
|||
A7D8A96523E2514000DCD162 /* SDL_dummysensor.h in Headers */,
|
||||
A7D8AB0C23E2514100DCD162 /* SDL_dynapi.h in Headers */,
|
||||
A7D8AB1223E2514100DCD162 /* SDL_dynapi_overrides.h in Headers */,
|
||||
A16680C429967B6900318FE2 /* SDL_video_capture.h in Headers */,
|
||||
A7D8AB1E23E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
F3F7D9272933074E00816151 /* SDL_egl.h in Headers */,
|
||||
A7D8ABDB23E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
|
@ -5998,6 +6073,7 @@
|
|||
A7D8AC0523E2514100DCD162 /* SDL_rect_c.h in Headers */,
|
||||
F3F7D9BF2933074E00816151 /* SDL_render.h in Headers */,
|
||||
A7D8B9FD23E2514400DCD162 /* SDL_render_sw_c.h in Headers */,
|
||||
A16680CF29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
F3F7D9172933074E00816151 /* SDL_revision.h in Headers */,
|
||||
A7D8BA3323E2514400DCD162 /* SDL_rotate.h in Headers */,
|
||||
F3F7D9672933074E00816151 /* SDL_rwops.h in Headers */,
|
||||
|
@ -6010,6 +6086,7 @@
|
|||
A7D8B98E23E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B99D23E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
A7D8B9A323E2514400DCD162 /* SDL_shaders_metal_tvos.h in Headers */,
|
||||
A16680D829967BD100318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F3F7D92F2933074E00816151 /* SDL_shape.h in Headers */,
|
||||
A7D8AC0B23E2514100DCD162 /* SDL_shape_internals.h in Headers */,
|
||||
F3F7D8F72933074E00816151 /* SDL_stdinc.h in Headers */,
|
||||
|
@ -6151,6 +6228,7 @@
|
|||
A7D8AB2023E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
A7D8ABDD23E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
A7D8A96123E2514000DCD162 /* SDL_error_c.h in Headers */,
|
||||
A16680DA29967BEE00318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A7D8BBA923E2514500DCD162 /* SDL_events_c.h in Headers */,
|
||||
A7D8B4B023E2514300DCD162 /* SDL_gamepad_db.h in Headers */,
|
||||
A7D8BA5923E2514400DCD162 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -6165,6 +6243,7 @@
|
|||
A7D8BB8B23E2514500DCD162 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B7027F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6EB2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680E429967C0A00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1BE2569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A7D8BB1F23E2514500DCD162 /* SDL_mouse_c.h in Headers */,
|
||||
A7D8AC0123E2514100DCD162 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -6182,6 +6261,7 @@
|
|||
A7D8B5C723E2514300DCD162 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A7D8A99123E2514000DCD162 /* SDL_sensor_c.h in Headers */,
|
||||
A7D8BA7723E2514400DCD162 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F229967C1C00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8BA5323E2514400DCD162 /* SDL_shaders_gles2.h in Headers */,
|
||||
A7D8B99023E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B99F23E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -6309,6 +6389,7 @@
|
|||
A7D8AEE823E2514100DCD162 /* SDL_cocoavulkan.h in Headers */,
|
||||
A7D8AEFA23E2514100DCD162 /* SDL_cocoawindow.h in Headers */,
|
||||
F3F7D9D12933074E00816151 /* SDL_copying.h in Headers */,
|
||||
A16680D029967BD100318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8B8CC23E2514400DCD162 /* SDL_coreaudio.h in Headers */,
|
||||
A7D8A96F23E2514000DCD162 /* SDL_coremotionsensor.h in Headers */,
|
||||
F3F7D9B92933074E00816151 /* SDL_cpuinfo.h in Headers */,
|
||||
|
@ -6324,6 +6405,7 @@
|
|||
A7D8A96323E2514000DCD162 /* SDL_dummysensor.h in Headers */,
|
||||
A7D8AB0A23E2514100DCD162 /* SDL_dynapi.h in Headers */,
|
||||
A7D8AB1023E2514100DCD162 /* SDL_dynapi_overrides.h in Headers */,
|
||||
A16680C229967B6900318FE2 /* SDL_video_capture.h in Headers */,
|
||||
A7D8AB1C23E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
F3F7D9252933074E00816151 /* SDL_egl.h in Headers */,
|
||||
A7D8ABD923E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
|
@ -6396,6 +6478,7 @@
|
|||
A7D8AC0323E2514100DCD162 /* SDL_rect_c.h in Headers */,
|
||||
F3F7D9BD2933074E00816151 /* SDL_render.h in Headers */,
|
||||
A7D8B9FB23E2514400DCD162 /* SDL_render_sw_c.h in Headers */,
|
||||
A16680CD29967BD100318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
F3F7D9152933074E00816151 /* SDL_revision.h in Headers */,
|
||||
A7D8BA3123E2514400DCD162 /* SDL_rotate.h in Headers */,
|
||||
F3F7D9652933074E00816151 /* SDL_rwops.h in Headers */,
|
||||
|
@ -6408,6 +6491,7 @@
|
|||
A7D8B98C23E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B99B23E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
A7D8B9A123E2514400DCD162 /* SDL_shaders_metal_tvos.h in Headers */,
|
||||
A16680D629967BD100318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F3F7D92D2933074E00816151 /* SDL_shape.h in Headers */,
|
||||
A7D8AC0923E2514100DCD162 /* SDL_shape_internals.h in Headers */,
|
||||
F3F7D8F52933074E00816151 /* SDL_stdinc.h in Headers */,
|
||||
|
@ -6549,6 +6633,7 @@
|
|||
A7D8AB1F23E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
A7D8ABDC23E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
A7D8A96023E2514000DCD162 /* SDL_error_c.h in Headers */,
|
||||
A16680D929967BEE00318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A7D8BBA823E2514500DCD162 /* SDL_events_c.h in Headers */,
|
||||
A7D8B4AF23E2514300DCD162 /* SDL_gamepad_db.h in Headers */,
|
||||
A7D8BA5823E2514400DCD162 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -6563,6 +6648,7 @@
|
|||
A7D8BB8A23E2514500DCD162 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B6F27F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6EA2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680E129967C0A00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1BD2569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A7D8BB1E23E2514500DCD162 /* SDL_mouse_c.h in Headers */,
|
||||
A7D8AC0023E2514100DCD162 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -6580,6 +6666,7 @@
|
|||
A7D8B5C623E2514300DCD162 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A7D8A99023E2514000DCD162 /* SDL_sensor_c.h in Headers */,
|
||||
A7D8BA7623E2514400DCD162 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F129967C1B00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8BA5223E2514400DCD162 /* SDL_shaders_gles2.h in Headers */,
|
||||
A7D8B98F23E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B99E23E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -6714,6 +6801,7 @@
|
|||
A7D8AB2123E2514100DCD162 /* SDL_dynapi_procs.h in Headers */,
|
||||
A7D8ABDE23E2514100DCD162 /* SDL_egl_c.h in Headers */,
|
||||
A7D8A96223E2514000DCD162 /* SDL_error_c.h in Headers */,
|
||||
A16680DC29967BEF00318FE2 /* SDL_sysvideocapture.h in Headers */,
|
||||
A7D8BBAA23E2514500DCD162 /* SDL_events_c.h in Headers */,
|
||||
A7D8B4B123E2514300DCD162 /* SDL_gamepad_db.h in Headers */,
|
||||
A7D8BA5A23E2514400DCD162 /* SDL_gles2funcs.h in Headers */,
|
||||
|
@ -6728,6 +6816,7 @@
|
|||
A7D8BB8C23E2514500DCD162 /* SDL_keyboard_c.h in Headers */,
|
||||
A1BB8B7227F6CF330057CFA8 /* SDL_list.h in Headers */,
|
||||
F386F6ED2884663E001840AA /* SDL_log_c.h in Headers */,
|
||||
A16680EA29967C0B00318FE2 /* SDL_video_capture_c.h in Headers */,
|
||||
F395C1C02569C6A000942BFF /* SDL_mfijoystick_c.h in Headers */,
|
||||
A7D8BB2023E2514500DCD162 /* SDL_mouse_c.h in Headers */,
|
||||
A7D8AC0223E2514100DCD162 /* SDL_nullevents_c.h in Headers */,
|
||||
|
@ -6745,6 +6834,7 @@
|
|||
A7D8B5C823E2514300DCD162 /* SDL_rwopsbundlesupport.h in Headers */,
|
||||
A7D8A99223E2514000DCD162 /* SDL_sensor_c.h in Headers */,
|
||||
A7D8BA7823E2514400DCD162 /* SDL_shaders_gl.h in Headers */,
|
||||
A16680F429967C1C00318FE2 /* SDL_video_c.h in Headers */,
|
||||
A7D8BA5423E2514400DCD162 /* SDL_shaders_gles2.h in Headers */,
|
||||
A7D8B99123E2514400DCD162 /* SDL_shaders_metal_ios.h in Headers */,
|
||||
A7D8B9A023E2514400DCD162 /* SDL_shaders_metal_macos.h in Headers */,
|
||||
|
@ -7301,6 +7391,7 @@
|
|||
A75FCE4B23E25AB700529352 /* SDL_render.c in Sources */,
|
||||
A75FCE4C23E25AB700529352 /* SDL_stretch.c in Sources */,
|
||||
A75FCE4D23E25AB700529352 /* s_floor.c in Sources */,
|
||||
A16680EC29967C0C00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A75FCE4E23E25AB700529352 /* SDL_blit_copy.c in Sources */,
|
||||
A75FCE4F23E25AB700529352 /* e_fmod.c in Sources */,
|
||||
A75FCE5023E25AB700529352 /* SDL_syspower.m in Sources */,
|
||||
|
@ -7335,6 +7426,7 @@
|
|||
A75FCE6F23E25AB700529352 /* SDL_surface.c in Sources */,
|
||||
A75FCE7023E25AB700529352 /* SDL_hidapi_xboxone.c in Sources */,
|
||||
A75FCE7123E25AB700529352 /* SDL_blit_auto.c in Sources */,
|
||||
A16680EB29967C0C00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A75FCE7323E25AB700529352 /* SDL_keyboard.c in Sources */,
|
||||
A75FCE7523E25AB700529352 /* SDL_rect.c in Sources */,
|
||||
A75FCE7623E25AB700529352 /* SDL_cocoaopengles.m in Sources */,
|
||||
|
@ -7496,6 +7588,7 @@
|
|||
A75FD00423E25AC700529352 /* SDL_render.c in Sources */,
|
||||
A75FD00523E25AC700529352 /* SDL_stretch.c in Sources */,
|
||||
A75FD00623E25AC700529352 /* s_floor.c in Sources */,
|
||||
A16680EF29967C0C00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A75FD00723E25AC700529352 /* SDL_blit_copy.c in Sources */,
|
||||
A75FD00823E25AC700529352 /* e_fmod.c in Sources */,
|
||||
A75FD00923E25AC700529352 /* SDL_syspower.m in Sources */,
|
||||
|
@ -7530,6 +7623,7 @@
|
|||
A75FD02823E25AC700529352 /* SDL_surface.c in Sources */,
|
||||
A75FD02923E25AC700529352 /* SDL_hidapi_xboxone.c in Sources */,
|
||||
A75FD02A23E25AC700529352 /* SDL_blit_auto.c in Sources */,
|
||||
A16680EE29967C0C00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A75FD02C23E25AC700529352 /* SDL_keyboard.c in Sources */,
|
||||
A75FD02E23E25AC700529352 /* SDL_rect.c in Sources */,
|
||||
A75FD02F23E25AC700529352 /* SDL_cocoaopengles.m in Sources */,
|
||||
|
@ -7691,6 +7785,7 @@
|
|||
A769B1DF23E259AE00872273 /* SDL_blit_0.c in Sources */,
|
||||
F36C7AD7294BA009004D61C3 /* SDL_runapp.c in Sources */,
|
||||
A769B1E023E259AE00872273 /* k_tan.c in Sources */,
|
||||
A16680E629967C0B00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A769B1E223E259AE00872273 /* SDL_diskaudio.c in Sources */,
|
||||
A769B1E423E259AE00872273 /* SDL_egl.c in Sources */,
|
||||
A769B1E523E259AE00872273 /* SDL_RLEaccel.c in Sources */,
|
||||
|
@ -7725,6 +7820,7 @@
|
|||
A769B20323E259AE00872273 /* SDL_qsort.c in Sources */,
|
||||
A769B20423E259AE00872273 /* SDL_hidapi_switch.c in Sources */,
|
||||
F3984CD525BCC92900374F43 /* SDL_hidapi_stadia.c in Sources */,
|
||||
A16680E529967C0B00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A769B20523E259AE00872273 /* SDL_strtokr.c in Sources */,
|
||||
5605720B2473687A00B46B66 /* SDL_syslocale.m in Sources */,
|
||||
F3820718284F3609004DD584 /* controller_type.c in Sources */,
|
||||
|
@ -7886,6 +7982,7 @@
|
|||
A7D8BAFE23E2514500DCD162 /* s_floor.c in Sources */,
|
||||
A7D8AC3A23E2514100DCD162 /* SDL_blit_copy.c in Sources */,
|
||||
A7D8BAE023E2514500DCD162 /* e_fmod.c in Sources */,
|
||||
A16680D429967BD100318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8B5D023E2514300DCD162 /* SDL_syspower.m in Sources */,
|
||||
A7D8BAEC23E2514500DCD162 /* e_log10.c in Sources */,
|
||||
A7D8AC7023E2514100DCD162 /* SDL_uikitopenglview.m in Sources */,
|
||||
|
@ -7920,6 +8017,7 @@
|
|||
A7D8AD2423E2514100DCD162 /* SDL_blit_auto.c in Sources */,
|
||||
A7D8BB6A23E2514500DCD162 /* SDL_keyboard.c in Sources */,
|
||||
A7D8ACE823E2514100DCD162 /* SDL_rect.c in Sources */,
|
||||
A16680CB29967BD100318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8AE9B23E2514100DCD162 /* SDL_cocoaopengles.m in Sources */,
|
||||
A7D8B96923E2514400DCD162 /* SDL_qsort.c in Sources */,
|
||||
A7D8B55223E2514300DCD162 /* SDL_hidapi_switch.c in Sources */,
|
||||
|
@ -8081,6 +8179,7 @@
|
|||
A7D8BAFF23E2514500DCD162 /* s_floor.c in Sources */,
|
||||
A7D8AC3B23E2514100DCD162 /* SDL_blit_copy.c in Sources */,
|
||||
A7D8BAE123E2514500DCD162 /* e_fmod.c in Sources */,
|
||||
A16680D529967BD100318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8B5D123E2514300DCD162 /* SDL_syspower.m in Sources */,
|
||||
A7D8BAED23E2514500DCD162 /* e_log10.c in Sources */,
|
||||
A7D8AC7123E2514100DCD162 /* SDL_uikitopenglview.m in Sources */,
|
||||
|
@ -8115,6 +8214,7 @@
|
|||
A7D8AD2523E2514100DCD162 /* SDL_blit_auto.c in Sources */,
|
||||
A7D8BB6B23E2514500DCD162 /* SDL_keyboard.c in Sources */,
|
||||
A7D8ACE923E2514100DCD162 /* SDL_rect.c in Sources */,
|
||||
A16680CC29967BD100318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8AE9C23E2514100DCD162 /* SDL_cocoaopengles.m in Sources */,
|
||||
A7D8B96A23E2514400DCD162 /* SDL_qsort.c in Sources */,
|
||||
A7D8B55323E2514300DCD162 /* SDL_hidapi_switch.c in Sources */,
|
||||
|
@ -8276,6 +8376,7 @@
|
|||
A7D8ADEA23E2514100DCD162 /* SDL_blit_0.c in Sources */,
|
||||
F36C7AD6294BA009004D61C3 /* SDL_runapp.c in Sources */,
|
||||
A7D8BB0D23E2514500DCD162 /* k_tan.c in Sources */,
|
||||
A16680E329967C0A00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8B8AC23E2514400DCD162 /* SDL_diskaudio.c in Sources */,
|
||||
A7D8AFC423E2514200DCD162 /* SDL_egl.c in Sources */,
|
||||
A7D8AC3723E2514100DCD162 /* SDL_RLEaccel.c in Sources */,
|
||||
|
@ -8310,6 +8411,7 @@
|
|||
A7D8B96C23E2514400DCD162 /* SDL_qsort.c in Sources */,
|
||||
A7D8B55523E2514300DCD162 /* SDL_hidapi_switch.c in Sources */,
|
||||
F3984CD425BCC92900374F43 /* SDL_hidapi_stadia.c in Sources */,
|
||||
A16680E229967C0A00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8B96623E2514400DCD162 /* SDL_strtokr.c in Sources */,
|
||||
560572092473687900B46B66 /* SDL_syslocale.m in Sources */,
|
||||
F3820717284F3609004DD584 /* controller_type.c in Sources */,
|
||||
|
@ -8418,6 +8520,7 @@
|
|||
75E0915A241EA924004729E1 /* SDL_virtualjoystick.c in Sources */,
|
||||
A7D8ABEB23E2514100DCD162 /* SDL_nullvideo.c in Sources */,
|
||||
A7D8AB6723E2514100DCD162 /* SDL_offscreenevents.c in Sources */,
|
||||
A16680CA29967BD100318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8ABF123E2514100DCD162 /* SDL_nullevents.c in Sources */,
|
||||
A7D8B81823E2514400DCD162 /* SDL_audiodev.c in Sources */,
|
||||
A7D8AF0C23E2514100DCD162 /* SDL_cocoaclipboard.m in Sources */,
|
||||
|
@ -8440,6 +8543,7 @@
|
|||
A7D8AED623E2514100DCD162 /* SDL_cocoakeyboard.m in Sources */,
|
||||
A7D8AB1623E2514100DCD162 /* SDL_dynapi.c in Sources */,
|
||||
A7D8BA8523E2514400DCD162 /* SDL_shaders_gl.c in Sources */,
|
||||
A16680D329967BD100318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8BAF123E2514500DCD162 /* e_log.c in Sources */,
|
||||
A7D8AED023E2514100DCD162 /* SDL_cocoamessagebox.m in Sources */,
|
||||
F376F6552559B4E300CFC0BC /* SDL_hidapi.c in Sources */,
|
||||
|
@ -8612,6 +8716,7 @@
|
|||
A7D8BA3A23E2514400DCD162 /* SDL_d3dmath.c in Sources */,
|
||||
A7D8ABEE23E2514100DCD162 /* SDL_nullvideo.c in Sources */,
|
||||
A7D8AB6A23E2514100DCD162 /* SDL_offscreenevents.c in Sources */,
|
||||
A16680DF29967C0A00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8ABF423E2514100DCD162 /* SDL_nullevents.c in Sources */,
|
||||
A7D8B81B23E2514400DCD162 /* SDL_audiodev.c in Sources */,
|
||||
A7D8AF0F23E2514100DCD162 /* SDL_cocoaclipboard.m in Sources */,
|
||||
|
@ -8634,6 +8739,7 @@
|
|||
A7D8BAF423E2514500DCD162 /* e_log.c in Sources */,
|
||||
A7D8AED323E2514100DCD162 /* SDL_cocoamessagebox.m in Sources */,
|
||||
A7D8BA2E23E2514400DCD162 /* SDL_blendfillrect.c in Sources */,
|
||||
A16680E029967C0A00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8AEE523E2514100DCD162 /* SDL_cocoashape.m in Sources */,
|
||||
A7D8AEBB23E2514100DCD162 /* SDL_cocoamouse.m in Sources */,
|
||||
F376F6762559B4E500CFC0BC /* SDL_hidapi.c in Sources */,
|
||||
|
@ -8806,6 +8912,7 @@
|
|||
A7D8AB6C23E2514100DCD162 /* SDL_offscreenevents.c in Sources */,
|
||||
A7D8ACAA23E2514100DCD162 /* SDL_uikitview.m in Sources */,
|
||||
A7D8ABF623E2514100DCD162 /* SDL_nullevents.c in Sources */,
|
||||
A16680E829967C0B00318FE2 /* SDL_video_capture.c in Sources */,
|
||||
A7D8B81D23E2514400DCD162 /* SDL_audiodev.c in Sources */,
|
||||
A7D8AF1123E2514100DCD162 /* SDL_cocoaclipboard.m in Sources */,
|
||||
A7D8ABD223E2514100DCD162 /* SDL_blit_slow.c in Sources */,
|
||||
|
@ -8828,6 +8935,7 @@
|
|||
A7D8BA8A23E2514400DCD162 /* SDL_shaders_gl.c in Sources */,
|
||||
A7D8BAF623E2514500DCD162 /* e_log.c in Sources */,
|
||||
A7D8AED523E2514100DCD162 /* SDL_cocoamessagebox.m in Sources */,
|
||||
A16680E929967C0B00318FE2 /* SDL_video_capture_apple.m in Sources */,
|
||||
A7D8BA3023E2514400DCD162 /* SDL_blendfillrect.c in Sources */,
|
||||
A7D8ACE023E2514100DCD162 /* SDL_uikitvideo.m in Sources */,
|
||||
F376F68D2559B4E900CFC0BC /* SDL_hidapi.c in Sources */,
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
#include <SDL3/SDL_touch.h>
|
||||
#include <SDL3/SDL_version.h>
|
||||
#include <SDL3/SDL_video.h>
|
||||
#include "SDL3/SDL_video_capture.h"
|
||||
#include <SDL3/SDL_oldnames.h>
|
||||
|
||||
#endif /* SDL_h_ */
|
||||
|
|
302
include/SDL3/SDL_video_capture.h
Normal file
302
include/SDL3/SDL_video_capture.h
Normal file
|
@ -0,0 +1,302 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it
|
||||
freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not
|
||||
claim that you wrote the original software. If you use this software
|
||||
in a product, an acknowledgment in the product documentation would be
|
||||
appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
/**
|
||||
* \file SDL_video_capture.h
|
||||
*
|
||||
* Video Capture for the SDL library.
|
||||
*/
|
||||
|
||||
#ifndef SDL_video_capture_h_
|
||||
#define SDL_video_capture_h_
|
||||
|
||||
#include "SDL3/SDL_video.h"
|
||||
|
||||
#include <SDL3/SDL_begin_code.h>
|
||||
/* Set up for C function definitions, even when using C++ */
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
* SDL VideoCapture Device IDs.
|
||||
*/
|
||||
typedef Sint32 SDL_VideoCaptureDeviceID;
|
||||
#define SDL_VIDEO_CAPTURE_INVALID -1
|
||||
|
||||
#define SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE 1
|
||||
|
||||
/**
|
||||
* SDL_VideoCaptureSpec structure
|
||||
*
|
||||
* Only those field can be 'desired' when configuring the device:
|
||||
* - format
|
||||
* - width
|
||||
* - height
|
||||
*
|
||||
* \sa SDL_GetVideoCaptureFormat
|
||||
* \sa SDL_GetVideoCaptureFrameSize
|
||||
*
|
||||
*/
|
||||
typedef struct SDL_VideoCaptureSpec
|
||||
{
|
||||
Uint32 format; /**< Video data format */
|
||||
Uint32 width; /**< Width */
|
||||
Uint32 height; /**< Height */
|
||||
} SDL_VideoCaptureSpec;
|
||||
|
||||
/**
|
||||
* SDL Video Capture Status
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
SDL_VIDEO_CAPTURE_INIT = 0, /**< Init, spec hasn't been set */
|
||||
SDL_VIDEO_CAPTURE_STOPPED, /**< Stopped */
|
||||
SDL_VIDEO_CAPTURE_PLAYING /**< Playing */
|
||||
} SDL_VideoCaptureStatus;
|
||||
|
||||
/**
|
||||
* SDL Video Capture Status
|
||||
*/
|
||||
typedef struct SDL_VideoCaptureFrame
|
||||
{
|
||||
int num_planes; /**< Number of planes */
|
||||
Uint8 *data[3]; /**< Pointer to data of i-th plane */
|
||||
int row_stride[3]; /**< Row stride of i-th plane */
|
||||
int fd; /**< DMABUF file descriptor if available (-1 if not) */
|
||||
void *clientbuffer; /**< Android clientbuffer if available (NULL if not) */
|
||||
void *internal; /**< Private field */
|
||||
} SDL_VideoCaptureFrame;
|
||||
|
||||
/**
|
||||
* Open a Video Capture device
|
||||
*
|
||||
* \param device_name device name to open. Can be NULL.
|
||||
*
|
||||
* \returns device id, or SDL_VIDEO_CAPTURE_INVALID on error
|
||||
*
|
||||
* \sa SDL_GetVideoCaptureDeviceName
|
||||
* \sa SDL_GetNumVideoCaptureDevices
|
||||
*/
|
||||
extern DECLSPEC SDL_VideoCaptureDeviceID SDLCALL SDL_OpenVideoCapture(const char *device_name);
|
||||
|
||||
/**
|
||||
* Set specification
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param desired desired video capture spec
|
||||
* \param obtained obtained video capture spec
|
||||
* \param allowed_changes allow changes or not
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_SetVideoCaptureSpec(SDL_VideoCaptureDeviceID id,
|
||||
const SDL_VideoCaptureSpec *desired,
|
||||
SDL_VideoCaptureSpec *obtained,
|
||||
int allowed_changes);
|
||||
|
||||
/**
|
||||
* Open a Video Capture device and set specification
|
||||
*
|
||||
* \param device_name device name to open. Can be NULL.
|
||||
* \param desired desired video capture spec
|
||||
* \param obtained obtained video capture spec
|
||||
* \param allowed_changes allow changes or not
|
||||
*
|
||||
* \returns device id, or SDL_VIDEO_CAPTURE_INVALID on error
|
||||
*/
|
||||
extern DECLSPEC SDL_VideoCaptureDeviceID SDLCALL SDL_OpenVideoCaptureWithSpec(
|
||||
const char *device_name,
|
||||
const SDL_VideoCaptureSpec *desired,
|
||||
SDL_VideoCaptureSpec *obtained,
|
||||
int allowed_changes);
|
||||
/**
|
||||
* Get device name
|
||||
*
|
||||
* \param index device index between 0 and num -1
|
||||
*
|
||||
* \returns device name, shouldn't be freed
|
||||
*
|
||||
* \sa SDL_GetNumVideoCaptureDevices
|
||||
*/
|
||||
extern DECLSPEC const char * SDLCALL SDL_GetVideoCaptureDeviceName(int index);
|
||||
|
||||
/**
|
||||
* Use this function to get the number of video capture devices.
|
||||
*
|
||||
* \returns the number of video capture devices
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetNumVideoCaptureDevices(void);
|
||||
|
||||
/**
|
||||
* Get the obtained video capture spec
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param spec The SDL_VideoCaptureSpec to be initialized by this function.
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetVideoCaptureSpec(SDL_VideoCaptureDeviceID id, SDL_VideoCaptureSpec *spec);
|
||||
|
||||
|
||||
#define SDL_VIDEO_CAPTURE_TYPE_COMPRESSED 1
|
||||
#define SDL_VIDEO_CAPTURE_TYPE_EMULATED 2
|
||||
/**
|
||||
* Get frame format of video capture device.
|
||||
* The value can be used to fill SDL_VideoCaptureSpec structure.
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param index format between 0 and num -1
|
||||
* \param format pointer output format (SDL_PixelFormatEnum)
|
||||
* \param type pointer output type
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_GetNumVideoCaptureFormats
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetVideoCaptureFormat(SDL_VideoCaptureDeviceID id, int index, Uint32 *format, Uint32 *type);
|
||||
|
||||
/**
|
||||
* Number of available formats for the device
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
*
|
||||
* \returns number of formats, negative value on error
|
||||
*
|
||||
* \sa SDL_GetVideoCaptureFormat
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetNumVideoCaptureFormats(SDL_VideoCaptureDeviceID id);
|
||||
|
||||
/**
|
||||
* Get frame sizes of the device and the specified input format.
|
||||
* The value can be used to fill SDL_VideoCaptureSpec structure.
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param format a format that can be used by the device (SDL_PixelFormatEnum)
|
||||
* \param index framesize between 0 and num -1
|
||||
* \param width output width
|
||||
* \param height output height
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_GetNumVideoCaptureFrameSizes
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetVideoCaptureFrameSize(SDL_VideoCaptureDeviceID id, Uint32 format, int index, Uint32 *width, Uint32 *height);
|
||||
|
||||
/**
|
||||
* Number of different framesizes available for the device and pixel format.
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param format frame pixel format (SDL_PixelFormatEnum)
|
||||
*
|
||||
* \returns number of framesize, negative value on error
|
||||
*
|
||||
* \sa SDL_GetVideoCaptureFrameSize
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_GetNumVideoCaptureFrameSizes(SDL_VideoCaptureDeviceID id, Uint32 format);
|
||||
|
||||
|
||||
/**
|
||||
* Get video capture status
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_VideoCaptureStatus
|
||||
*/
|
||||
extern DECLSPEC SDL_VideoCaptureStatus SDLCALL SDL_GetVideoCaptureStatus(SDL_VideoCaptureDeviceID id);
|
||||
|
||||
/**
|
||||
* Start video capture
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_StopVideoCapture
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_StartVideoCapture(SDL_VideoCaptureDeviceID id);
|
||||
|
||||
/**
|
||||
* Acquire a frame.
|
||||
* The frame is a memory pointer to the image data, whose size and format
|
||||
* are given by the the obtained spec.
|
||||
*
|
||||
* Non blocking API. If there is a frame available, frame->num_planes is non 0.
|
||||
* If frame->num_planes is 0 and returned code is 0, there is no frame at that time.
|
||||
*
|
||||
* After used, the frame should be released with SDL_VideoCaptureReleaseFrame
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param frame pointer to get the frame
|
||||
* \param ticks pointer to get the ticks when this was read from driver
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_VideoCaptureReleaseFrame
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_VideoCaptureAcquireFrame(SDL_VideoCaptureDeviceID id, SDL_VideoCaptureFrame *frame, Uint64 *ticks);
|
||||
|
||||
/**
|
||||
* Release a frame. Let the back-end re-use the internal buffer for video capture.
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
* \param frame frame pointer.
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_VideoCaptureAcquireFrame
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_VideoCaptureReleaseFrame(SDL_VideoCaptureDeviceID id, SDL_VideoCaptureFrame *frame);
|
||||
|
||||
/**
|
||||
* Stop Video Capture
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
*
|
||||
* \returns 0 on success, negative value on error
|
||||
*
|
||||
* \sa SDL_StartVideoCapture
|
||||
*/
|
||||
extern DECLSPEC int SDLCALL SDL_StopVideoCapture(SDL_VideoCaptureDeviceID id);
|
||||
|
||||
/**
|
||||
* Use this function to shut down video_capture processing and close the video_capture device.
|
||||
*
|
||||
* The device ID is invalid as soon as the device is closed, and is eligible
|
||||
* for reuse in a new SDL_OpenVideoCaptureWithSpec() call immediately.
|
||||
*
|
||||
* \param id video capture opened device id
|
||||
*
|
||||
* \sa SDL_OpenVideoCaptureWithSpec
|
||||
* \sa SDL_OpenVideoCapture
|
||||
*/
|
||||
extern DECLSPEC void SDLCALL SDL_CloseVideoCapture(SDL_VideoCaptureDeviceID id);
|
||||
|
||||
/* Ends C function definitions when using C++ */
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#include <SDL3/SDL_close_code.h>
|
||||
|
||||
#endif /* SDL_video_capture_h_ */
|
|
@ -199,6 +199,8 @@
|
|||
#define SDL_VIDEO_METAL 1
|
||||
#endif
|
||||
|
||||
#define HAVE_COREMEDIA 1
|
||||
|
||||
/* Enable system power support */
|
||||
#define SDL_POWER_UIKIT 1
|
||||
|
||||
|
|
|
@ -260,6 +260,8 @@
|
|||
#endif
|
||||
#endif
|
||||
|
||||
#define HAVE_COREMEDIA 1
|
||||
|
||||
/* Enable system power support */
|
||||
#define SDL_POWER_MACOSX 1
|
||||
|
||||
|
|
91
src/video/SDL_sysvideocapture.h
Normal file
91
src/video/SDL_sysvideocapture.h
Normal file
|
@ -0,0 +1,91 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it
|
||||
freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not
|
||||
claim that you wrote the original software. If you use this software
|
||||
in a product, an acknowledgment in the product documentation would be
|
||||
appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#include "../SDL_internal.h"
|
||||
|
||||
#ifndef SDL_sysvideocapture_h_
|
||||
#define SDL_sysvideocapture_h_
|
||||
|
||||
#include "../SDL_list.h"
|
||||
|
||||
#define _THIS SDL_VideoCaptureDevice *_this
|
||||
|
||||
/* The SDL video_capture driver */
|
||||
typedef struct SDL_VideoCaptureDevice SDL_VideoCaptureDevice;
|
||||
|
||||
/* Define the SDL video_capture driver structure */
|
||||
struct SDL_VideoCaptureDevice
|
||||
{
|
||||
/* * * */
|
||||
/* Data common to all devices */
|
||||
SDL_VideoCaptureDeviceID id;
|
||||
|
||||
/* The device's current video_capture specification */
|
||||
SDL_VideoCaptureSpec spec;
|
||||
|
||||
/* Device name */
|
||||
char *dev_name;
|
||||
|
||||
/* Current state flags */
|
||||
SDL_atomic_t shutdown;
|
||||
SDL_atomic_t enabled;
|
||||
SDL_bool is_spec_set;
|
||||
|
||||
/* A mutex for locking the queue buffers */
|
||||
SDL_mutex *device_lock;
|
||||
SDL_mutex *acquiring_lock;
|
||||
|
||||
/* A thread to feed the video_capture device */
|
||||
SDL_Thread *thread;
|
||||
SDL_threadID threadid;
|
||||
|
||||
/* Queued buffers (if app not using callback). */
|
||||
SDL_ListNode *buffer_queue;
|
||||
|
||||
/* * * */
|
||||
/* Data private to this driver */
|
||||
struct SDL_PrivateVideoCaptureData *hidden;
|
||||
};
|
||||
|
||||
extern int OpenDevice(_THIS);
|
||||
extern void CloseDevice(_THIS);
|
||||
|
||||
extern int InitDevice(_THIS);
|
||||
|
||||
extern int GetDeviceSpec(_THIS, SDL_VideoCaptureSpec *spec);
|
||||
|
||||
extern int StartCapture(_THIS);
|
||||
extern int StopCapture(_THIS);
|
||||
|
||||
extern int AcquireFrame(_THIS, SDL_VideoCaptureFrame *frame, Uint64 *ticks);
|
||||
extern int ReleaseFrame(_THIS, SDL_VideoCaptureFrame *frame);
|
||||
|
||||
extern int GetNumFormats(_THIS);
|
||||
extern int GetFormat(_THIS, int index, Uint32 *format, Uint32 *type);
|
||||
|
||||
extern int GetNumFrameSizes(_THIS, Uint32 format);
|
||||
extern int GetFrameSize(_THIS, Uint32 format, int index, Uint32 *width, Uint32 *height);
|
||||
|
||||
extern int GetDeviceName(int index, char *buf, int size);
|
||||
extern int GetNumDevices(void);
|
||||
|
||||
|
||||
|
||||
#endif /* SDL_sysvideocapture_h_ */
|
|
@ -30,6 +30,7 @@
|
|||
#include "SDL_video_c.h"
|
||||
#include "../events/SDL_events_c.h"
|
||||
#include "../timer/SDL_timer_c.h"
|
||||
#include "SDL_video_capture_c.h"
|
||||
|
||||
#include <SDL3/SDL_syswm.h>
|
||||
|
||||
|
@ -420,6 +421,7 @@ int SDL_VideoInit(const char *driver_name)
|
|||
SDL_bool init_keyboard = SDL_FALSE;
|
||||
SDL_bool init_mouse = SDL_FALSE;
|
||||
SDL_bool init_touch = SDL_FALSE;
|
||||
SDL_bool init_video_capture = SDL_FALSE;
|
||||
int i = 0;
|
||||
|
||||
/* Check to make sure we don't overwrite '_this' */
|
||||
|
@ -448,6 +450,10 @@ int SDL_VideoInit(const char *driver_name)
|
|||
goto pre_driver_error;
|
||||
}
|
||||
init_touch = SDL_TRUE;
|
||||
if (SDL_VideoCaptureInit() < 0) {
|
||||
goto pre_driver_error;
|
||||
}
|
||||
init_video_capture = SDL_TRUE;
|
||||
|
||||
/* Select the proper video driver */
|
||||
video = NULL;
|
||||
|
@ -541,6 +547,9 @@ int SDL_VideoInit(const char *driver_name)
|
|||
|
||||
pre_driver_error:
|
||||
SDL_assert(_this == NULL);
|
||||
if (init_video_capture) {
|
||||
SDL_QuitVideoCapture();
|
||||
}
|
||||
if (init_touch) {
|
||||
SDL_QuitTouch();
|
||||
}
|
||||
|
@ -3283,6 +3292,7 @@ void SDL_VideoQuit(void)
|
|||
}
|
||||
|
||||
/* Halt event processing before doing anything else */
|
||||
SDL_QuitVideoCapture();
|
||||
SDL_QuitTouch();
|
||||
SDL_QuitMouse();
|
||||
SDL_QuitKeyboard();
|
||||
|
|
2491
src/video/SDL_video_capture.c
Normal file
2491
src/video/SDL_video_capture.c
Normal file
File diff suppressed because it is too large
Load diff
578
src/video/SDL_video_capture_apple.m
Normal file
578
src/video/SDL_video_capture_apple.m
Normal file
|
@ -0,0 +1,578 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 2021 Valve Corporation
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it
|
||||
freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not
|
||||
claim that you wrote the original software. If you use this software
|
||||
in a product, an acknowledgment in the product documentation would be
|
||||
appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#include "../SDL_internal.h"
|
||||
|
||||
#include "SDL3/SDL.h"
|
||||
#include "SDL3/SDL_video_capture.h"
|
||||
#include "SDL_sysvideocapture.h"
|
||||
#include "SDL_video_capture_c.h"
|
||||
#include "../thread/SDL_systhread.h"
|
||||
|
||||
#if defined(__MACOS__) && (__MAC_OS_X_VERSION_MAX_ALLOWED < 101500)
|
||||
/* AVCaptureDeviceTypeBuiltInWideAngleCamera requires macOS SDK 10.15 */
|
||||
#undef HAVE_COREMEDIA
|
||||
#endif
|
||||
|
||||
#if TARGET_OS_TV
|
||||
#undef HAVE_COREMEDIA
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_COREMEDIA
|
||||
int InitDevice(_THIS) {
|
||||
return -1;
|
||||
}
|
||||
int OpenDevice(_THIS) {
|
||||
return -1;
|
||||
}
|
||||
int AcquireFrame(_THIS, SDL_VideoCaptureFrame *frame, Uint64 *ticks) {
|
||||
return -1;
|
||||
}
|
||||
void CloseDevice(_THIS) {
|
||||
}
|
||||
int GetDeviceName(int index, char *buf, int size) {
|
||||
return -1;
|
||||
}
|
||||
int GetDeviceSpec(_THIS, SDL_VideoCaptureSpec *spec) {
|
||||
return -1;
|
||||
}
|
||||
int GetFormat(_THIS, int index, Uint32 *format, Uint32 *type) {
|
||||
return -1;
|
||||
}
|
||||
int GetFrameSize(_THIS, Uint32 format, int index, Uint32 *width, Uint32 *height) {
|
||||
return -1;
|
||||
}
|
||||
int GetNumDevices(void) {
|
||||
return 0;
|
||||
}
|
||||
int GetNumFormats(_THIS) {
|
||||
return 0;
|
||||
}
|
||||
int GetNumFrameSizes(_THIS, Uint32 format) {
|
||||
return 0;
|
||||
}
|
||||
int ReleaseFrame(_THIS, SDL_VideoCaptureFrame *frame) {
|
||||
return 0;
|
||||
}
|
||||
int StartCapture(_THIS) {
|
||||
return 0;
|
||||
}
|
||||
int StopCapture(_THIS) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
#import <AVFoundation/AVFoundation.h>
|
||||
#import <CoreMedia/CoreMedia.h>
|
||||
|
||||
/*
|
||||
* Need to link with:: CoreMedia CoreVideo
|
||||
*
|
||||
* Add in pInfo.list:
|
||||
* <key>NSCameraUsageDescription</key> <string>Access camera</string>
|
||||
*
|
||||
*
|
||||
* MACOSX:
|
||||
* Add to the Code Sign Entitlement file:
|
||||
* <key>com.apple.security.device.camera</key> <true/>
|
||||
*
|
||||
*/
|
||||
|
||||
@class MySampleBufferDelegate;
|
||||
|
||||
struct SDL_PrivateVideoCaptureData
|
||||
{
|
||||
dispatch_queue_t queue;
|
||||
MySampleBufferDelegate *delegate;
|
||||
AVCaptureSession *session;
|
||||
CMSimpleQueueRef frame_queue;
|
||||
};
|
||||
|
||||
static NSString *
|
||||
fourcc_to_nstring(Uint32 code)
|
||||
{
|
||||
Uint8 buf[4];
|
||||
*(Uint32 *)buf = code;
|
||||
return [NSString stringWithFormat:@"%c%c%c%c", buf[3], buf[2], buf[1], buf[0]];
|
||||
}
|
||||
|
||||
static NSArray<AVCaptureDevice *> *
|
||||
discover_devices()
|
||||
{
|
||||
NSArray *deviceType = @[AVCaptureDeviceTypeBuiltInWideAngleCamera];
|
||||
|
||||
AVCaptureDeviceDiscoverySession *discoverySession = [AVCaptureDeviceDiscoverySession
|
||||
discoverySessionWithDeviceTypes:deviceType
|
||||
mediaType:AVMediaTypeVideo
|
||||
position:AVCaptureDevicePositionUnspecified];
|
||||
|
||||
NSArray<AVCaptureDevice *> *devices = discoverySession.devices;
|
||||
|
||||
if ([devices count] > 0) {
|
||||
return devices;
|
||||
} else {
|
||||
AVCaptureDevice *captureDevice = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
|
||||
if (captureDevice == nil) {
|
||||
return devices;
|
||||
} else {
|
||||
NSArray<AVCaptureDevice *> *default_device = @[ captureDevice ];
|
||||
return default_device;
|
||||
}
|
||||
}
|
||||
|
||||
return devices;
|
||||
}
|
||||
|
||||
static AVCaptureDevice *
|
||||
get_device_by_name(const char *dev_name)
|
||||
{
|
||||
NSArray<AVCaptureDevice *> *devices = discover_devices();
|
||||
|
||||
for (AVCaptureDevice *device in devices) {
|
||||
char buf[1024];
|
||||
NSString *cameraID = [device localizedName];
|
||||
const char *str = [cameraID UTF8String];
|
||||
SDL_snprintf(buf, sizeof (buf) - 1, "%s", str);
|
||||
if (SDL_strcmp(buf, dev_name) == 0) {
|
||||
return device;
|
||||
}
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
static Uint32
|
||||
nsfourcc_to_sdlformat(NSString *nsfourcc)
|
||||
{
|
||||
const char *str = [nsfourcc UTF8String];
|
||||
|
||||
if (SDL_strcmp("420v", str) == 0) return SDL_PIXELFORMAT_NV12;
|
||||
if (SDL_strcmp("yuvs", str) == 0) return SDL_PIXELFORMAT_UYVY;
|
||||
if (SDL_strcmp("420f", str) == 0) return SDL_PIXELFORMAT_UNKNOWN;
|
||||
|
||||
SDL_Log("Unknown format '%s'", str);
|
||||
|
||||
return SDL_PIXELFORMAT_UNKNOWN;
|
||||
}
|
||||
|
||||
static NSString *
|
||||
sdlformat_to_nsfourcc(Uint32 fmt)
|
||||
{
|
||||
const char *str = "";
|
||||
|
||||
if (fmt == SDL_PIXELFORMAT_NV12) str = "420v";
|
||||
if (fmt == SDL_PIXELFORMAT_UYVY) str = "yuvs";
|
||||
|
||||
NSString *result = [[NSString alloc] initWithUTF8String: str];
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
@interface MySampleBufferDelegate : NSObject<AVCaptureVideoDataOutputSampleBufferDelegate>
|
||||
@property struct SDL_PrivateVideoCaptureData *hidden;
|
||||
- (void) set: (struct SDL_PrivateVideoCaptureData *) val;
|
||||
@end
|
||||
|
||||
@implementation MySampleBufferDelegate
|
||||
|
||||
- (void) set: (struct SDL_PrivateVideoCaptureData *) val {
|
||||
_hidden = val;
|
||||
}
|
||||
|
||||
- (void) captureOutput:(AVCaptureOutput *)output
|
||||
didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer
|
||||
fromConnection:(AVCaptureConnection *) connection {
|
||||
CFRetain(sampleBuffer);
|
||||
CMSimpleQueueEnqueue(_hidden->frame_queue, sampleBuffer);
|
||||
}
|
||||
|
||||
- (void)captureOutput:(AVCaptureOutput *)output
|
||||
didDropSampleBuffer:(CMSampleBufferRef)sampleBuffer
|
||||
fromConnection:(AVCaptureConnection *)connection {
|
||||
SDL_Log("Drop frame..");
|
||||
}
|
||||
@end
|
||||
|
||||
int
|
||||
OpenDevice(_THIS)
|
||||
{
|
||||
_this->hidden = (struct SDL_PrivateVideoCaptureData *) SDL_calloc(1, sizeof (struct SDL_PrivateVideoCaptureData));
|
||||
if (_this->hidden == NULL) {
|
||||
SDL_OutOfMemory();
|
||||
goto error;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
return -1;
|
||||
}
|
||||
|
||||
void
|
||||
CloseDevice(_THIS)
|
||||
{
|
||||
if (!_this) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (_this->hidden) {
|
||||
AVCaptureSession *session = _this->hidden->session;
|
||||
|
||||
if (session) {
|
||||
AVCaptureInput *input = [session.inputs objectAtIndex:0];
|
||||
[session removeInput:input];
|
||||
AVCaptureVideoDataOutput *output = (AVCaptureVideoDataOutput*)[session.outputs objectAtIndex:0];
|
||||
[session removeOutput:output];
|
||||
// TODO clenaupp
|
||||
}
|
||||
|
||||
if (_this->hidden->frame_queue) {
|
||||
CFRelease(_this->hidden->frame_queue);
|
||||
}
|
||||
|
||||
SDL_free(_this->hidden);
|
||||
_this->hidden = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
InitDevice(_THIS)
|
||||
{
|
||||
NSString *fmt = sdlformat_to_nsfourcc(_this->spec.format);
|
||||
int w = _this->spec.width;
|
||||
int h = _this->spec.height;
|
||||
|
||||
NSError *error = nil;
|
||||
AVCaptureDevice *device = nil;
|
||||
AVCaptureDeviceInput *input = nil;
|
||||
AVCaptureVideoDataOutput *output = nil;
|
||||
|
||||
AVCaptureDeviceFormat *spec_format = nil;
|
||||
|
||||
#ifdef __MACOS__
|
||||
if (@available(macOS 10.15, *)) {
|
||||
/* good. */
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
|
||||
device = get_device_by_name(_this->dev_name);
|
||||
if (!device) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
_this->hidden->session = [[AVCaptureSession alloc] init];
|
||||
if (_this->hidden->session == nil) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
[_this->hidden->session setSessionPreset:AVCaptureSessionPresetHigh];
|
||||
|
||||
// Pick format that matches the spec
|
||||
{
|
||||
NSArray<AVCaptureDeviceFormat *> *formats = [device formats];
|
||||
for (AVCaptureDeviceFormat *format in formats) {
|
||||
CMFormatDescriptionRef formatDescription = [format formatDescription];
|
||||
FourCharCode mediaSubType = CMFormatDescriptionGetMediaSubType(formatDescription);
|
||||
NSString *str = fourcc_to_nstring(mediaSubType);
|
||||
if (str == fmt) {
|
||||
CMVideoDimensions dim = CMVideoFormatDescriptionGetDimensions(formatDescription);
|
||||
if (dim.width == w && dim.height == h) {
|
||||
spec_format = format;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (spec_format == nil) {
|
||||
SDL_SetError("format not found");
|
||||
goto error;
|
||||
}
|
||||
|
||||
// Set format
|
||||
if ([device lockForConfiguration:NULL] == YES) {
|
||||
device.activeFormat = spec_format;
|
||||
[device unlockForConfiguration];
|
||||
} else {
|
||||
SDL_SetError("Cannot lockForConfiguration");
|
||||
goto error;
|
||||
}
|
||||
|
||||
// Input
|
||||
input = [AVCaptureDeviceInput deviceInputWithDevice:device error:&error];
|
||||
if (!input) {
|
||||
SDL_SetError("Cannot create AVCaptureDeviceInput");
|
||||
goto error;
|
||||
}
|
||||
|
||||
// Output
|
||||
output = [[AVCaptureVideoDataOutput alloc] init];
|
||||
|
||||
// Specify the pixel format
|
||||
output.videoSettings =
|
||||
[NSDictionary dictionaryWithObject:
|
||||
[NSNumber numberWithInt:kCVPixelFormatType_422YpCbCr8]
|
||||
forKey:(id)kCVPixelBufferPixelFormatTypeKey];
|
||||
|
||||
_this->hidden->delegate = [[MySampleBufferDelegate alloc] init];
|
||||
[_this->hidden->delegate set:_this->hidden];
|
||||
|
||||
|
||||
CMSimpleQueueCreate(kCFAllocatorDefault, 30 /* buffers */, &_this->hidden->frame_queue);
|
||||
if (_this->hidden->frame_queue == nil) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
_this->hidden->queue = dispatch_queue_create("my_queue", NULL);
|
||||
[output setSampleBufferDelegate:_this->hidden->delegate queue:_this->hidden->queue];
|
||||
|
||||
|
||||
if ([_this->hidden->session canAddInput:input] ){
|
||||
[_this->hidden->session addInput:input];
|
||||
} else {
|
||||
SDL_SetError("Cannot add AVCaptureDeviceInput");
|
||||
goto error;
|
||||
}
|
||||
|
||||
if ([_this->hidden->session canAddOutput:output] ){
|
||||
[_this->hidden->session addOutput:output];
|
||||
} else {
|
||||
SDL_SetError("Cannot add AVCaptureVideoDataOutput");
|
||||
goto error;
|
||||
}
|
||||
|
||||
[_this->hidden->session commitConfiguration];
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
GetDeviceSpec(_THIS, SDL_VideoCaptureSpec *spec)
|
||||
{
|
||||
if (spec) {
|
||||
*spec = _this->spec;
|
||||
return 0;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
StartCapture(_THIS)
|
||||
{
|
||||
[_this->hidden->session startRunning];
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
StopCapture(_THIS)
|
||||
{
|
||||
[_this->hidden->session stopRunning];
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
AcquireFrame(_THIS, SDL_VideoCaptureFrame *frame, Uint64 *ticks)
|
||||
{
|
||||
if (CMSimpleQueueGetCount(_this->hidden->frame_queue) > 0) {
|
||||
CMSampleBufferRef sampleBuffer = (CMSampleBufferRef)CMSimpleQueueDequeue(_this->hidden->frame_queue);
|
||||
frame->internal = (void *) sampleBuffer;
|
||||
*ticks = SDL_GetTicks();
|
||||
|
||||
int i = 0;
|
||||
CVImageBufferRef image = CMSampleBufferGetImageBuffer(sampleBuffer);
|
||||
int numPlanes = CVPixelBufferGetPlaneCount(image);
|
||||
int planar = CVPixelBufferIsPlanar(image);
|
||||
|
||||
#if 0
|
||||
int w = CVPixelBufferGetWidth(image);
|
||||
int h = CVPixelBufferGetHeight(image);
|
||||
int sz = CVPixelBufferGetDataSize(image);
|
||||
int pitch = CVPixelBufferGetBytesPerRow(image);
|
||||
SDL_Log("buffer planar=%d count:%d %d x %d sz=%d pitch=%d", planar, numPlanes, w, h, sz, pitch);
|
||||
#endif
|
||||
|
||||
CVPixelBufferLockBaseAddress(image, 0);
|
||||
|
||||
if (planar == 0 && numPlanes == 0) {
|
||||
frame->row_stride[0] = CVPixelBufferGetBytesPerRow(image);
|
||||
frame->data[0] = CVPixelBufferGetBaseAddress(image);
|
||||
frame->num_planes = 1;
|
||||
} else {
|
||||
for (i = 0; i < numPlanes && i < 3; i++) {
|
||||
int rowStride = 0;
|
||||
uint8_t *data = NULL;
|
||||
frame->num_planes += 1;
|
||||
|
||||
rowStride = CVPixelBufferGetBytesPerRowOfPlane(image, i);
|
||||
data = CVPixelBufferGetBaseAddressOfPlane(image, i);
|
||||
frame->data[i] = data;
|
||||
frame->row_stride[i] = rowStride;
|
||||
}
|
||||
}
|
||||
|
||||
/* Unlocked when frame is released */
|
||||
|
||||
} else {
|
||||
// no frame
|
||||
SDL_Delay(20); // TODO fix some delay
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
ReleaseFrame(_THIS, SDL_VideoCaptureFrame *frame)
|
||||
{
|
||||
if (frame->internal){
|
||||
CMSampleBufferRef sampleBuffer = (CMSampleBufferRef) frame->internal;
|
||||
|
||||
CVImageBufferRef image = CMSampleBufferGetImageBuffer(sampleBuffer);
|
||||
CVPixelBufferUnlockBaseAddress(image, 0);
|
||||
|
||||
CFRelease(sampleBuffer);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
GetNumFormats(_THIS)
|
||||
{
|
||||
AVCaptureDevice *device = get_device_by_name(_this->dev_name);
|
||||
if (device) {
|
||||
// LIST FORMATS
|
||||
NSMutableOrderedSet<NSString *> *array_formats = [NSMutableOrderedSet new];
|
||||
NSArray<AVCaptureDeviceFormat *> *formats = [device formats];
|
||||
for (AVCaptureDeviceFormat *format in formats) {
|
||||
// NSLog(@"%@", formats);
|
||||
CMFormatDescriptionRef formatDescription = [format formatDescription];
|
||||
//NSLog(@"%@", formatDescription);
|
||||
FourCharCode mediaSubType = CMFormatDescriptionGetMediaSubType(formatDescription);
|
||||
NSString *str = fourcc_to_nstring(mediaSubType);
|
||||
[array_formats addObject:str];
|
||||
}
|
||||
return [array_formats count];
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
GetFormat(_THIS, int index, Uint32 *format, Uint32 *type)
|
||||
{
|
||||
AVCaptureDevice *device = get_device_by_name(_this->dev_name);
|
||||
if (device) {
|
||||
// LIST FORMATS
|
||||
NSMutableOrderedSet<NSString *> *array_formats = [NSMutableOrderedSet new];
|
||||
NSArray<AVCaptureDeviceFormat *> *formats = [device formats];
|
||||
for (AVCaptureDeviceFormat *f in formats) {
|
||||
CMFormatDescriptionRef formatDescription = [f formatDescription];
|
||||
FourCharCode mediaSubType = CMFormatDescriptionGetMediaSubType(formatDescription);
|
||||
NSString *str = fourcc_to_nstring(mediaSubType);
|
||||
[array_formats addObject:str];
|
||||
}
|
||||
|
||||
NSString *str = array_formats[index];
|
||||
*format = nsfourcc_to_sdlformat(str);
|
||||
|
||||
return 0;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
GetNumFrameSizes(_THIS, Uint32 format)
|
||||
{
|
||||
AVCaptureDevice *device = get_device_by_name(_this->dev_name);
|
||||
if (device) {
|
||||
NSString *fmt = sdlformat_to_nsfourcc(format);
|
||||
int count = 0;
|
||||
|
||||
NSArray<AVCaptureDeviceFormat *> *formats = [device formats];
|
||||
for (AVCaptureDeviceFormat *f in formats) {
|
||||
CMFormatDescriptionRef formatDescription = [f formatDescription];
|
||||
FourCharCode mediaSubType = CMFormatDescriptionGetMediaSubType(formatDescription);
|
||||
NSString *str = fourcc_to_nstring(mediaSubType);
|
||||
|
||||
if (str == fmt) {
|
||||
count += 1;
|
||||
}
|
||||
}
|
||||
return count;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
GetFrameSize(_THIS, Uint32 format, int index, Uint32 *width, Uint32 *height)
|
||||
{
|
||||
AVCaptureDevice *device = get_device_by_name(_this->dev_name);
|
||||
if (device) {
|
||||
NSString *fmt = sdlformat_to_nsfourcc(format);
|
||||
int count = 0;
|
||||
|
||||
NSArray<AVCaptureDeviceFormat *> *formats = [device formats];
|
||||
for (AVCaptureDeviceFormat *f in formats) {
|
||||
CMFormatDescriptionRef formatDescription = [f formatDescription];
|
||||
FourCharCode mediaSubType = CMFormatDescriptionGetMediaSubType(formatDescription);
|
||||
NSString *str = fourcc_to_nstring(mediaSubType);
|
||||
|
||||
if (str == fmt) {
|
||||
if (index == count) {
|
||||
CMVideoDimensions dim = CMVideoFormatDescriptionGetDimensions(formatDescription);
|
||||
*width = dim.width;
|
||||
*height = dim.height;
|
||||
return 0;
|
||||
}
|
||||
count += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
GetDeviceName(int index, char *buf, int size)
|
||||
{
|
||||
NSArray<AVCaptureDevice *> *devices = discover_devices();
|
||||
if (index < [devices count]) {
|
||||
AVCaptureDevice *device = devices[index];
|
||||
NSString *cameraID = [device localizedName];
|
||||
const char *str = [cameraID UTF8String];
|
||||
SDL_snprintf(buf, size, "%s", str);
|
||||
return 0;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
GetNumDevices(void)
|
||||
{
|
||||
NSArray<AVCaptureDevice *> *devices = discover_devices();
|
||||
return [devices count];
|
||||
}
|
||||
|
||||
#endif /* HAVE_COREMEDIA */
|
||||
|
||||
/* vi: set ts=4 sw=4 expandtab: */
|
||||
|
33
src/video/SDL_video_capture_c.h
Normal file
33
src/video/SDL_video_capture_c.h
Normal file
|
@ -0,0 +1,33 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it
|
||||
freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not
|
||||
claim that you wrote the original software. If you use this software
|
||||
in a product, an acknowledgment in the product documentation would be
|
||||
appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#include "../SDL_internal.h"
|
||||
#include "../../include/SDL3/SDL_video_capture.h"
|
||||
|
||||
#ifndef SDL_video_capture_c_h_
|
||||
#define SDL_video_capture_c_h_
|
||||
|
||||
/* Initialize the video_capture subsystem */
|
||||
int SDL_VideoCaptureInit(void);
|
||||
|
||||
/* Shutdown the video_capture subsystem */
|
||||
void SDL_QuitVideoCapture(void);
|
||||
|
||||
#endif /* SDL_video_capture_c_h_ */
|
|
@ -190,6 +190,7 @@ add_sdl_test_executable(teststreaming NEEDS_RESOURCES TESTUTILS teststreaming.c)
|
|||
add_sdl_test_executable(testtimer NONINTERACTIVE testtimer.c)
|
||||
add_sdl_test_executable(testurl testurl.c)
|
||||
add_sdl_test_executable(testver NONINTERACTIVE testver.c)
|
||||
add_sdl_test_executable(testvideocapture testvideocapture.c)
|
||||
add_sdl_test_executable(testviewport NEEDS_RESOURCES TESTUTILS testviewport.c)
|
||||
add_sdl_test_executable(testwm testwm.c)
|
||||
add_sdl_test_executable(testyuv NEEDS_RESOURCES testyuv.c testyuv_cvt.c)
|
||||
|
|
787
test/testvideocapture.c
Normal file
787
test/testvideocapture.c
Normal file
|
@ -0,0 +1,787 @@
|
|||
/*
|
||||
Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it
|
||||
freely.
|
||||
*/
|
||||
#include "SDL3/SDL.h"
|
||||
#include "SDL3/SDL_video_capture.h"
|
||||
#include <stdio.h>
|
||||
|
||||
/* Enable DMABUF to compile (linux + v4l2) */
|
||||
#define USE_DMABUF 0
|
||||
|
||||
#if USE_DMABUF
|
||||
# include "SDL_egl.h"
|
||||
# include "SDL_opengles2.h"
|
||||
# include "drm/drm_fourcc.h"
|
||||
#endif
|
||||
|
||||
#ifdef __EMSCRIPTEN__
|
||||
#include <emscripten/emscripten.h>
|
||||
#endif
|
||||
|
||||
static const char *usage = "\
|
||||
\n\
|
||||
=========================================================================\n\
|
||||
\n\
|
||||
Use keyboards:\n\
|
||||
o: open first video capture device. (close previously opened)\n\
|
||||
l: list video capture devices\n\
|
||||
i: information about status (Init, Playing, Stopped)\n\
|
||||
f: formats and resolutions available\n\
|
||||
s: start / stop capture\n\
|
||||
h: display help\n\
|
||||
esc: exit \n\
|
||||
\n\
|
||||
=========================================================================\n\
|
||||
\n\
|
||||
";
|
||||
|
||||
typedef struct {
|
||||
Uint64 next_check;
|
||||
int frame_counter;
|
||||
int check_delay;
|
||||
double last_fps;
|
||||
} measure_fps_t;
|
||||
|
||||
static void
|
||||
update_fps(measure_fps_t *m, const char *str)
|
||||
{
|
||||
Uint64 now = SDL_GetTicks();
|
||||
Uint64 deadline;
|
||||
m->frame_counter++;
|
||||
if (m->check_delay == 0) {
|
||||
m->check_delay = 1500;
|
||||
}
|
||||
if (str == NULL) {
|
||||
str = "";
|
||||
}
|
||||
deadline = m->next_check;
|
||||
if (now >= deadline) {
|
||||
/* Print out some timing information */
|
||||
const Uint64 then = m->next_check - m->check_delay;
|
||||
m->last_fps = ((double) m->frame_counter * 1000) / (now - then);
|
||||
|
||||
SDL_Log("%s %2.2f frames per second\n", str, m->last_fps);
|
||||
m->next_check = now + m->check_delay;
|
||||
m->frame_counter = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
+--1--+
|
||||
| |
|
||||
4 6
|
||||
|--2--|
|
||||
5 7
|
||||
| |
|
||||
+--3--+
|
||||
*/
|
||||
static const
|
||||
SDL_FPoint segments[9][2] = {
|
||||
{ {0, 0}, {10, 1} }, /* 1 */
|
||||
{ {0, 10}, {10, 11} }, /* 2 */
|
||||
{ {0, 20}, {10, 21} }, /* 3 */
|
||||
|
||||
{ {0, 0}, {1, 11} }, /* 4 */
|
||||
{ {0, 10}, {1, 21} }, /* 5 */
|
||||
|
||||
{ {9, 0}, {10, 11} }, /* 6 */
|
||||
{ {9, 10}, {10, 21} }, /* 7 */
|
||||
{ {3, 18}, {5, 21} }, /* . */
|
||||
{ {4, 0}, {5, 21} } /* | */
|
||||
};
|
||||
|
||||
static void
|
||||
draw_string(SDL_Renderer *renderer, const char *c, float x0, float y0)
|
||||
{
|
||||
while (*c) {
|
||||
int seg = 0;
|
||||
int val = *c;
|
||||
if (val >= 'A' && val <= 'Z') {
|
||||
val = 'a' + val - 'A';
|
||||
}
|
||||
switch (val) {
|
||||
case '0': seg = 167345; break;
|
||||
case '1': seg = 67; break;
|
||||
case '2': seg = 16253; break;
|
||||
case '3': seg = 16732; break;
|
||||
case '4': seg = 4267; break;
|
||||
case '5': seg = 14273; break;
|
||||
case '6': seg = 145372; break;
|
||||
case '7': seg = 167; break;
|
||||
case '8': seg = 1234567; break;
|
||||
case '9': seg = 123467; break;
|
||||
case '.': seg = 8; break;
|
||||
case '-': seg = 2; break;
|
||||
case '_': seg = 3; break;
|
||||
case '+': seg = 29; break;
|
||||
case '|': seg = 9; break;
|
||||
case '[': seg = 1453; break;
|
||||
case ']': seg = 1673; break;
|
||||
case 'a': seg = 124567; break;
|
||||
case 'b': seg = 1234567; break;
|
||||
case 'c': seg = 1453; break;
|
||||
case 'd': seg = 167345; break;
|
||||
case 'e': seg = 12345; break;
|
||||
case 'f': seg = 1425; break;
|
||||
case 'g': seg = 123457; break;
|
||||
case 'h': seg = 24567; break;
|
||||
case 'i': seg = 9; break;
|
||||
case 'j': seg = 6735; break;
|
||||
case 'k': seg = 24567; break;
|
||||
case 'l': seg = 453; break;
|
||||
case 'm': seg = 145679; break;
|
||||
case 'n': seg = 14567; break;
|
||||
case 'o': seg = 134567; break;
|
||||
case 'p': seg = 14256; break;
|
||||
case 'q': seg = 134567; break;
|
||||
case 'r': seg = 145; break;
|
||||
case 's': seg = 14273; break;
|
||||
case 't': seg = 19; break;
|
||||
case 'u': seg = 45367; break;
|
||||
case 'v': seg = 45367; break;
|
||||
case 'w': seg = 345679; break;
|
||||
case 'x': seg = 24567; break;
|
||||
case 'y': seg = 23467; break;
|
||||
case 'z': seg = 16253; break;
|
||||
}
|
||||
while (seg) {
|
||||
SDL_FRect r;
|
||||
SDL_FPoint p1, p2;
|
||||
int s = seg - 10 * (seg/10);
|
||||
p1 = segments[s - 1][0];
|
||||
p2 = segments[s - 1][1];
|
||||
r.x = p1.x + x0;
|
||||
r.y = p1.y + y0;
|
||||
r.w = p2.x - p1.x;
|
||||
r.h = p2.y - p1.y;
|
||||
SDL_RenderRect(renderer, &r);
|
||||
seg /= 10;
|
||||
}
|
||||
x0 += 12;
|
||||
c++;
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(__linux__) && !defined(__ANDROID__)
|
||||
static void load_average(float *val)
|
||||
{
|
||||
FILE *fp = 0;
|
||||
char line[1024];
|
||||
fp = fopen("/proc/loadavg", "rt");
|
||||
if (fp) {
|
||||
char *s = fgets(line, sizeof(line), fp);
|
||||
if (s) {
|
||||
SDL_sscanf(s, "%f", val);
|
||||
}
|
||||
fclose(fp);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
SDL_Window *window = NULL;
|
||||
SDL_Renderer *renderer = NULL;
|
||||
SDL_Texture *texture = NULL;
|
||||
int texture_updated = 0;
|
||||
SDL_Event evt;
|
||||
int quit = 1;
|
||||
|
||||
SDL_VideoCaptureDeviceID id = 0;
|
||||
SDL_VideoCaptureSpec obtained;
|
||||
|
||||
SDL_FRect r_playstop = { 50, 50, 120, 50 };
|
||||
SDL_FRect r_close = { 50 + (120 + 50) * 1, 50, 120, 50 };
|
||||
|
||||
SDL_FRect r_open0 = { 50 + (120 + 50) * 2, 50, 120, 50 };
|
||||
SDL_FRect r_open1 = { 50 + (120 + 50) * 2, 150, 120, 50 };
|
||||
|
||||
SDL_FRect r_format = { 50 + (120 + 50) * 3, 50, 120, 50 };
|
||||
SDL_FRect r_listdev = { 50 + (120 + 50) * 4, 50, 120, 50 };
|
||||
|
||||
int start = 1;
|
||||
SDL_VideoCaptureFrame frame_current;
|
||||
|
||||
#if USE_DMABUF
|
||||
EGLDisplay display;
|
||||
|
||||
typedef EGLDisplay (*eglGetCurrentDisplay_t)();
|
||||
typedef EGLImageKHR (*eglCreateImageKHR_t)(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLint *attrib_list);
|
||||
typedef EGLBoolean (*eglDestroyImageKHR_t)(EGLDisplay dpy, EGLImageKHR image);
|
||||
typedef void (*glActiveTexture_t)(GLenum texture);
|
||||
typedef void (*glEGLImageTargetTexture2DOES_t)(GLenum target, GLeglImageOES image);
|
||||
typedef EGLint (*eglGetError_t)(void);
|
||||
|
||||
eglGetCurrentDisplay_t eglGetCurrentDisplay;
|
||||
eglCreateImageKHR_t eglCreateImageKHR;
|
||||
eglDestroyImageKHR_t eglDestroyImageKHR;
|
||||
glActiveTexture_t glActiveTexture;
|
||||
glEGLImageTargetTexture2DOES_t glEGLImageTargetTexture2DOES;
|
||||
eglGetError_t eglGetError;
|
||||
|
||||
#endif
|
||||
|
||||
measure_fps_t fps_main;
|
||||
measure_fps_t fps_capture;
|
||||
|
||||
SDL_zero(fps_main);
|
||||
SDL_zero(fps_capture);
|
||||
SDL_zero(frame_current);
|
||||
|
||||
SDL_Log("%s", usage);
|
||||
|
||||
/* Enable standard application logging */
|
||||
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
|
||||
|
||||
#if USE_DMABUF
|
||||
SDL_SetHint("SDL_RENDER_OPENGL_NV12_RG_SHADER", "1");
|
||||
SDL_SetHint("SDL_VIDEO_X11_FORCE_EGL", "1"); /* Don't use GLX */
|
||||
SDL_SetHint(SDL_HINT_RENDER_DRIVER, "opengles2");
|
||||
#endif
|
||||
|
||||
/* Load the SDL library */
|
||||
if (SDL_Init(SDL_INIT_VIDEO) < 0) {
|
||||
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't initialize SDL: %s", SDL_GetError());
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!(window = SDL_CreateWindow("Local Video", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1000, 800, 0))) {
|
||||
SDL_Log("Couldn't create window: %s", SDL_GetError());
|
||||
return 1;
|
||||
}
|
||||
|
||||
SDL_LogSetAllPriority(SDL_LOG_PRIORITY_VERBOSE);
|
||||
|
||||
renderer = SDL_CreateRenderer(window, NULL, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC);
|
||||
if (renderer == NULL) {
|
||||
SDL_Log("Couldn't create renderer: %s", SDL_GetError());
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if USE_DMABUF
|
||||
|
||||
#define LOAL_FUNC(f) \
|
||||
f = (f ##_t)SDL_GL_GetProcAddress(#f); \
|
||||
if (f == NULL) { \
|
||||
SDL_Log("Cannot load function: " #f ); \
|
||||
return 0; \
|
||||
} \
|
||||
|
||||
LOAL_FUNC(eglGetError)
|
||||
LOAL_FUNC(eglGetCurrentDisplay)
|
||||
LOAL_FUNC(eglCreateImageKHR)
|
||||
LOAL_FUNC(eglDestroyImageKHR)
|
||||
LOAL_FUNC(glActiveTexture)
|
||||
LOAL_FUNC(glEGLImageTargetTexture2DOES)
|
||||
|
||||
display = eglGetCurrentDisplay();
|
||||
if (display == EGL_NO_DISPLAY) {
|
||||
SDL_Log("no dispay");
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
SDL_LogSetAllPriority(SDL_LOG_PRIORITY_VERBOSE);
|
||||
|
||||
id = SDL_OpenVideoCapture(NULL);
|
||||
|
||||
if (id == SDL_VIDEO_CAPTURE_INVALID) {
|
||||
SDL_Log("Error SDL_OpenVideoCapture: %s", SDL_GetError());
|
||||
}
|
||||
|
||||
{
|
||||
/* List formats */
|
||||
int i, num = SDL_GetNumVideoCaptureFormats(id);
|
||||
for (i = 0; i < num; i++) {
|
||||
Uint32 format, type;
|
||||
SDL_GetVideoCaptureFormat(id, i, &format, &type);
|
||||
SDL_Log("format %d/%d type=%08" SDL_PRIx32 ": %s", i, num, type, SDL_GetPixelFormatName(format));
|
||||
{
|
||||
Uint32 w, h;
|
||||
int j, num2 = SDL_GetNumVideoCaptureFrameSizes(id, format);
|
||||
for (j = 0; j < num2; j++) {
|
||||
SDL_GetVideoCaptureFrameSize(id, format, j, &w, &h);
|
||||
SDL_Log(" framesizes %d/%d : %" SDL_PRIu32 " x %" SDL_PRIu32 "", j, num2, w, h);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Set Spec */
|
||||
{
|
||||
int ret;
|
||||
/* forced_format */
|
||||
SDL_VideoCaptureSpec desired;
|
||||
SDL_zero(desired);
|
||||
desired.width = 640 * 2;
|
||||
desired.height = 360 * 2;
|
||||
ret = SDL_SetVideoCaptureSpec(id, &desired, &obtained, SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE);
|
||||
|
||||
if (ret < 0) {
|
||||
SDL_SetVideoCaptureSpec(id, NULL, &obtained, 0);
|
||||
}
|
||||
}
|
||||
|
||||
SDL_Log("Open capture video device. Obtained spec: size=%" SDL_PRIu32 "x%" SDL_PRIu32 " format=%s",
|
||||
obtained.width, obtained.height, SDL_GetPixelFormatName(obtained.format));
|
||||
|
||||
{
|
||||
SDL_VideoCaptureSpec spec;
|
||||
if (SDL_GetVideoCaptureSpec(id, &spec) == 0) {
|
||||
SDL_Log("Read spec: size=%" SDL_PRIu32 "x%" SDL_PRIu32 " format=%s",
|
||||
spec.width, spec.height, SDL_GetPixelFormatName(spec.format));
|
||||
} else {
|
||||
SDL_Log("Error read spec: %s", SDL_GetError());
|
||||
}
|
||||
}
|
||||
|
||||
if (SDL_StartVideoCapture(id) < 0) {
|
||||
SDL_Log("error SDL_StartVideoCapture(): %s", SDL_GetError());
|
||||
}
|
||||
|
||||
while (quit) {
|
||||
|
||||
SDL_SetRenderDrawColor(renderer, 0x99, 0x99, 0x99, 255);
|
||||
SDL_RenderClear(renderer);
|
||||
|
||||
SDL_SetRenderDrawColor(renderer, 0x33, 0x33, 0x33, 255);
|
||||
|
||||
SDL_RenderFillRect(renderer, &r_playstop);
|
||||
SDL_RenderFillRect(renderer, &r_close);
|
||||
SDL_RenderFillRect(renderer, &r_open0);
|
||||
SDL_RenderFillRect(renderer, &r_open1);
|
||||
SDL_RenderFillRect(renderer, &r_format);
|
||||
SDL_RenderFillRect(renderer, &r_listdev);
|
||||
|
||||
SDL_SetRenderDrawColor(renderer, 0xcc, 0xcc, 0xcc, 255);
|
||||
|
||||
draw_string(renderer, "play stop", r_playstop.x + 5, r_playstop.y + 5);
|
||||
draw_string(renderer, "close", r_close.x + 5, r_close.y + 5);
|
||||
draw_string(renderer, "open dev0", r_open0.x + 5, r_open0.y + 5);
|
||||
draw_string(renderer, "open dev1", r_open1.x + 5, r_open1.y + 5);
|
||||
draw_string(renderer, "formats", r_format.x + 5, r_format.y + 5);
|
||||
draw_string(renderer, "devices", r_listdev.x + 5, r_listdev.y + 5);
|
||||
|
||||
|
||||
|
||||
while (SDL_PollEvent(&evt) == 1) {
|
||||
int sym = 0;
|
||||
int opendev = 0;
|
||||
switch (evt.type)
|
||||
{
|
||||
case SDL_EVENT_KEY_DOWN:
|
||||
{
|
||||
sym = evt.key.keysym.sym;
|
||||
break;
|
||||
}
|
||||
case SDL_EVENT_QUIT:
|
||||
{
|
||||
quit = 0;
|
||||
SDL_Log("Ctlr+C : Quit!");
|
||||
}
|
||||
break;
|
||||
|
||||
case SDL_EVENT_MOUSE_BUTTON_DOWN:
|
||||
{
|
||||
SDL_FRect *r = NULL;
|
||||
SDL_FPoint pt;
|
||||
pt.x = evt.button.x;
|
||||
pt.y = evt.button.y;
|
||||
if (SDL_PointInRectFloat(&pt, &r_playstop)) {
|
||||
r = &r_playstop;
|
||||
sym = SDLK_s;
|
||||
}
|
||||
if (SDL_PointInRectFloat(&pt, &r_close)) {
|
||||
r = &r_close;
|
||||
sym = SDLK_c;
|
||||
}
|
||||
if (SDL_PointInRectFloat(&pt, &r_open0)) {
|
||||
r = &r_open0;
|
||||
sym = SDLK_o;
|
||||
opendev = 0;
|
||||
}
|
||||
|
||||
if (SDL_PointInRectFloat(&pt, &r_open1)) {
|
||||
r = &r_open1;
|
||||
sym = SDLK_o;
|
||||
opendev = 1;
|
||||
}
|
||||
|
||||
if (SDL_PointInRectFloat(&pt, &r_format)) {
|
||||
r = &r_format;
|
||||
sym = SDLK_f;
|
||||
}
|
||||
if (SDL_PointInRectFloat(&pt, &r_listdev)) {
|
||||
r = &r_listdev;
|
||||
sym = SDLK_l;
|
||||
}
|
||||
|
||||
|
||||
if (r) {
|
||||
SDL_SetRenderDrawColor(renderer, 0x33, 0, 0, 255);
|
||||
SDL_RenderFillRect(renderer, r);
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
if (sym == SDLK_c) {
|
||||
if (frame_current.num_planes) {
|
||||
SDL_VideoCaptureReleaseFrame(id, &frame_current);
|
||||
}
|
||||
SDL_CloseVideoCapture(id);
|
||||
id = SDL_VIDEO_CAPTURE_INVALID;
|
||||
SDL_Log("Close");
|
||||
}
|
||||
|
||||
if (sym == SDLK_o) {
|
||||
if (id != SDL_VIDEO_CAPTURE_INVALID) {
|
||||
SDL_Log("Close previous ..");
|
||||
if (frame_current.num_planes) {
|
||||
SDL_VideoCaptureReleaseFrame(id, &frame_current);
|
||||
}
|
||||
SDL_CloseVideoCapture(id);
|
||||
}
|
||||
|
||||
texture_updated = 0;
|
||||
|
||||
SDL_ClearError();
|
||||
|
||||
if (opendev == 0) {
|
||||
id = SDL_OpenVideoCaptureWithSpec(NULL, &obtained, &obtained, SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE);
|
||||
} else {
|
||||
SDL_Log("Try to open:%s", SDL_GetVideoCaptureDeviceName(opendev));
|
||||
id = SDL_OpenVideoCaptureWithSpec(SDL_GetVideoCaptureDeviceName(opendev), &obtained, &obtained, SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE);
|
||||
}
|
||||
|
||||
/* spec may have changed because of re-open */
|
||||
if (texture) {
|
||||
SDL_DestroyTexture(texture);
|
||||
texture = NULL;
|
||||
}
|
||||
|
||||
SDL_Log("Open id:%" SDL_PRIu32 " %s", id, SDL_GetError());
|
||||
start = 0;
|
||||
}
|
||||
|
||||
if (sym == SDLK_l) {
|
||||
int num = SDL_GetNumVideoCaptureDevices();
|
||||
int i;
|
||||
SDL_Log("Num devices : %d", num);
|
||||
for (i = 0; i < num; i++) {
|
||||
SDL_Log("Device %d/%d : %s", i, num, SDL_GetVideoCaptureDeviceName(i));
|
||||
}
|
||||
}
|
||||
|
||||
if (sym == SDLK_i) {
|
||||
SDL_VideoCaptureStatus status = SDL_GetVideoCaptureStatus(id);
|
||||
if (status == SDL_VIDEO_CAPTURE_STOPPED) SDL_Log("STOPPED");
|
||||
if (status == SDL_VIDEO_CAPTURE_PLAYING) SDL_Log("PLAYING");
|
||||
if (status == SDL_VIDEO_CAPTURE_INIT) SDL_Log("INIT");
|
||||
}
|
||||
|
||||
if (sym == SDLK_s) {
|
||||
start = !start;
|
||||
|
||||
if (start) {
|
||||
SDL_Log("Start");
|
||||
SDL_StartVideoCapture(id);
|
||||
} else {
|
||||
SDL_Log("Stop");
|
||||
SDL_StopVideoCapture(id);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (sym == SDLK_f) {
|
||||
SDL_Log("List formats");
|
||||
|
||||
if (id == SDL_VIDEO_CAPTURE_INVALID) {
|
||||
id = SDL_OpenVideoCapture(NULL);
|
||||
}
|
||||
|
||||
/* List formats */
|
||||
{
|
||||
int i, num = SDL_GetNumVideoCaptureFormats(id);
|
||||
for (i = 0; i < num; i++) {
|
||||
Uint32 format, type;
|
||||
SDL_GetVideoCaptureFormat(id, i, &format, &type);
|
||||
SDL_Log("format %d/%d type=%08" SDL_PRIx32 ": %s", i, num, type, SDL_GetPixelFormatName(format));
|
||||
{
|
||||
Uint32 w, h;
|
||||
int j, num2 = SDL_GetNumVideoCaptureFrameSizes(id, format);
|
||||
for (j = 0; j < num2; j++) {
|
||||
SDL_GetVideoCaptureFrameSize(id, format, j, &w, &h);
|
||||
SDL_Log(" framesizes %d/%d : %" SDL_PRIu32 " x %" SDL_PRIu32 "", j, num2, w, h);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (sym == SDLK_ESCAPE || sym == SDLK_AC_BACK) {
|
||||
quit = 0;
|
||||
SDL_Log("Key : Escape!");
|
||||
}
|
||||
|
||||
if (sym == SDLK_h || sym == SDLK_F1) {
|
||||
SDL_Log("%s", usage);
|
||||
}
|
||||
}
|
||||
|
||||
if (id == SDL_VIDEO_CAPTURE_INVALID) {
|
||||
/* device has been closed */
|
||||
frame_current.num_planes = 0;
|
||||
texture_updated = 0;
|
||||
} else {
|
||||
Uint64 ticks;
|
||||
int ret;
|
||||
SDL_VideoCaptureFrame frame_next;
|
||||
SDL_zero(frame_next);
|
||||
|
||||
ret = SDL_VideoCaptureAcquireFrame(id, &frame_next, &ticks);
|
||||
if (ret < 0) {
|
||||
SDL_Log("err SDL_VideoCaptureAcquireFrame: %s", SDL_GetError());
|
||||
}
|
||||
#if 1
|
||||
if (frame_next.num_planes) {
|
||||
SDL_Log("frame: %p at %" SDL_PRIu64, (void*)frame_next.data[0], ticks);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (frame_next.num_planes) {
|
||||
|
||||
update_fps(&fps_capture, "Capture");
|
||||
|
||||
if (frame_current.num_planes) {
|
||||
ret = SDL_VideoCaptureReleaseFrame(id, &frame_current);
|
||||
if (ret < 0) {
|
||||
SDL_Log("err SDL_VideoCaptureReleaseFrame: %s", SDL_GetError());
|
||||
}
|
||||
}
|
||||
frame_current = frame_next;
|
||||
texture_updated = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* Moving square */
|
||||
SDL_SetRenderDrawColor(renderer, 0, 0xff, 0, 255);
|
||||
{
|
||||
SDL_FRect r;
|
||||
static float x = 0;
|
||||
x += 10;
|
||||
if (x > 1000) {
|
||||
x = 0;
|
||||
}
|
||||
r.x = x;
|
||||
r.y = 100;
|
||||
r.w = r.h = 10;
|
||||
SDL_RenderFillRect(renderer, &r);
|
||||
}
|
||||
|
||||
SDL_SetRenderDrawColor(renderer, 0x33, 0x33, 0x33, 255);
|
||||
|
||||
/* Update SDL_Texture with last video frame (only once per new frame) */
|
||||
if (frame_current.num_planes && texture_updated == 0) {
|
||||
#if USE_DMABUF
|
||||
int use_sw = 0;
|
||||
#else
|
||||
int use_sw = 1;
|
||||
#endif
|
||||
|
||||
/* Create texture with appropriate format (for DMABUF or not) */
|
||||
if (texture == NULL) {
|
||||
Uint32 format = obtained.format;
|
||||
#if USE_DMABUF
|
||||
if ((frame_current.fd == -1 && frame_current.clientbuffer == NULL) || use_sw) {
|
||||
/* keep format */
|
||||
} else {
|
||||
format = SDL_PIXELFORMAT_EXTERNAL_OES;
|
||||
}
|
||||
#endif
|
||||
texture = SDL_CreateTexture(renderer, format, SDL_TEXTUREACCESS_STATIC, obtained.width, obtained.height);
|
||||
if (texture == NULL) {
|
||||
SDL_Log("Couldn't create texture: %s", SDL_GetError());
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
if ((frame_current.fd == -1 && frame_current.clientbuffer == NULL) || use_sw) {
|
||||
/* Use software data */
|
||||
if (frame_current.num_planes == 1) {
|
||||
SDL_UpdateTexture(texture, NULL,
|
||||
frame_current.data[0], frame_current.row_stride[0]);
|
||||
} else if (frame_current.num_planes == 2) {
|
||||
SDL_UpdateNVTexture(texture, NULL,
|
||||
frame_current.data[0], frame_current.row_stride[0],
|
||||
frame_current.data[1], frame_current.row_stride[1]);
|
||||
} else if (frame_current.num_planes == 3) {
|
||||
SDL_UpdateYUVTexture(texture, NULL, frame_current.data[0], frame_current.row_stride[0],
|
||||
frame_current.data[1], frame_current.row_stride[1],
|
||||
frame_current.data[2], frame_current.row_stride[2]);
|
||||
}
|
||||
texture_updated = 1;
|
||||
} else {
|
||||
/* Use DMABUF */
|
||||
#if USE_DMABUF
|
||||
int j = 0;
|
||||
EGLImage image;
|
||||
EGLint img_attr[64];
|
||||
|
||||
#if __ANDROID__
|
||||
img_attr[j] = EGL_NONE;
|
||||
image = eglCreateImageKHR(display, EGL_NO_CONTEXT, EGL_NATIVE_BUFFER_ANDROID, frame_current.clientbuffer, img_attr);
|
||||
#else
|
||||
/* V4L2_PIX_FMT_YUYV / SDL_PIXELFORMAT_EXTERNAL_OES */
|
||||
img_attr[j++] = EGL_WIDTH;
|
||||
img_attr[j++] = obtained.width;
|
||||
|
||||
img_attr[j++] = EGL_HEIGHT;
|
||||
img_attr[j++] = obtained.height;
|
||||
|
||||
img_attr[j++] = EGL_LINUX_DRM_FOURCC_EXT;
|
||||
img_attr[j++] = DRM_FORMAT_YUYV;
|
||||
|
||||
img_attr[j++] = EGL_DMA_BUF_PLANE0_FD_EXT;
|
||||
img_attr[j++] = frame_current.fd;
|
||||
img_attr[j++] = EGL_DMA_BUF_PLANE0_OFFSET_EXT;
|
||||
img_attr[j++] = 0;
|
||||
img_attr[j++] = EGL_DMA_BUF_PLANE0_PITCH_EXT;
|
||||
img_attr[j++] = frame_current.row_stride[0];
|
||||
|
||||
img_attr[j++] = EGL_NONE;
|
||||
|
||||
image = eglCreateImageKHR(display, EGL_NO_CONTEXT, EGL_LINUX_DMA_BUF_EXT, NULL, img_attr);
|
||||
#endif
|
||||
|
||||
if (image == EGL_NO_IMAGE_KHR) {
|
||||
SDL_Log("error eglCreateImageKHR : eglGetError: %08" SDL_PRIx32 "", eglGetError());
|
||||
} else {
|
||||
SDL_Log("ImageKHR: %p fd: %" SDL_PRIu32 "", image, frame_current.fd);
|
||||
|
||||
SDL_GL_BindTexture(texture, NULL, NULL);
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glEGLImageTargetTexture2DOES(GL_TEXTURE_EXTERNAL_OES, image);
|
||||
SDL_GL_UnbindTexture(texture);
|
||||
|
||||
eglDestroyImageKHR(display, image);
|
||||
texture_updated = 1;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
/* RenderCopy the SDL_Texture */
|
||||
if (texture_updated == 1) {
|
||||
#if 0
|
||||
SDL_Rect dst;
|
||||
dst.x = 10;
|
||||
dst.y = 120;
|
||||
dst.w = obtained.width;
|
||||
dst.h = obtained.height;
|
||||
|
||||
SDL_RenderCopy(renderer, texture, NULL, &dst);
|
||||
#else
|
||||
{ /* Scale texture to fit the screen */
|
||||
int w, h;
|
||||
int tw, th;
|
||||
SDL_FRect d;
|
||||
SDL_GetWindowSize(window, &w, &h);
|
||||
SDL_QueryTexture(texture, NULL, NULL, &tw, &th);
|
||||
|
||||
if (tw > w - 20) {
|
||||
float scale = (float) (w - 20) / (float) tw;
|
||||
tw = w - 20;
|
||||
th = (int)((float) th * scale);
|
||||
}
|
||||
d.x = 10;
|
||||
d.y = (float)(h - th);
|
||||
d.w = (float)tw;
|
||||
d.h = (float)(th - 10);
|
||||
SDL_RenderTexture(renderer, texture, NULL, &d);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/* display FPS */
|
||||
{
|
||||
char buf[128];
|
||||
SDL_snprintf(buf, sizeof(buf), "%2.2f fps", fps_capture.last_fps);
|
||||
draw_string(renderer, buf, 10, 10);
|
||||
}
|
||||
|
||||
/* display status */
|
||||
{
|
||||
const char *status = "no status";
|
||||
if (id != SDL_VIDEO_CAPTURE_INVALID) {
|
||||
SDL_VideoCaptureStatus s = SDL_GetVideoCaptureStatus(id);
|
||||
if (s == SDL_VIDEO_CAPTURE_INIT) {
|
||||
status = "init";
|
||||
} else if (s == SDL_VIDEO_CAPTURE_PLAYING) {
|
||||
status = "playing";
|
||||
} else if (s == SDL_VIDEO_CAPTURE_STOPPED) {
|
||||
status = "stopped";
|
||||
}
|
||||
}
|
||||
draw_string(renderer, status, 200, 10);
|
||||
}
|
||||
|
||||
/* display last error */
|
||||
{
|
||||
draw_string(renderer, SDL_GetError(), 400, 10);
|
||||
}
|
||||
|
||||
/* display spec */
|
||||
{
|
||||
char buf[128];
|
||||
SDL_snprintf(buf, sizeof(buf), "%" SDL_PRIu32 " x %" SDL_PRIu32 " %s", obtained.width, obtained.height, SDL_GetPixelFormatName(obtained.format));
|
||||
draw_string(renderer, buf, 10, 200);
|
||||
}
|
||||
|
||||
/* display load average */
|
||||
#if defined(__linux__) && !defined(__ANDROID__)
|
||||
{
|
||||
float val = 0.0f;
|
||||
char buf[128];
|
||||
load_average(&val);
|
||||
if (val != 0.0f) {
|
||||
SDL_snprintf(buf, sizeof(buf), "load avg %2.2f percent", val);
|
||||
draw_string(renderer, buf, 800, 10);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
SDL_RenderPresent(renderer);
|
||||
|
||||
update_fps(&fps_main, "Main");
|
||||
|
||||
}
|
||||
|
||||
if (SDL_StopVideoCapture(id) < 0) {
|
||||
SDL_Log("error SDL_StopVideoCapture(): %s", SDL_GetError());
|
||||
}
|
||||
|
||||
if (frame_current.num_planes) {
|
||||
SDL_VideoCaptureReleaseFrame(id, &frame_current);
|
||||
}
|
||||
|
||||
SDL_CloseVideoCapture(id);
|
||||
|
||||
if (texture) SDL_DestroyTexture(texture);
|
||||
SDL_DestroyRenderer(renderer);
|
||||
SDL_DestroyWindow(window);
|
||||
|
||||
SDL_Quit();
|
||||
|
||||
return 0;
|
||||
}
|
Loading…
Reference in a new issue