sdl (master post 3.1 preview) Merge commit 'e4f454091a943345938608570b104400f62fd625'

This commit is contained in:
2024-03-28 16:27:42 +01:00
862 changed files with 204894 additions and 45662 deletions

View File

@ -2,7 +2,12 @@
# CMake script for building the SDL tests
#
list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}/../cmake")
include(CheckIncludeFile)
include(CheckStructHasMember)
include(CMakePushCheckState)
include(sdlcompilers)
if(SDL_TESTS_LINK_SHARED)
set(sdl_name_component SDL3-shared)
@ -220,26 +225,29 @@ if(HAVE_LIBUDEV_H)
endif()
set(FFmpeg_FIND_COMPONENTS AVCODEC AVFORMAT AVUTIL SWSCALE)
include("${SDL3_SOURCE_DIR}/cmake/FindFFmpeg.cmake")
include("${CMAKE_CURRENT_LIST_DIR}/../cmake/FindFFmpeg.cmake")
if(FFmpeg_FOUND)
cmake_push_check_state()
list(APPEND CMAKE_REQUIRED_INCLUDES "${FFmpeg_AVUTIL_INCLUDE_DIRS}")
list(APPEND CMAKE_REQUIRED_INCLUDES "${SDL3_SOURCE_DIR}/src/video/khronos")
check_struct_has_member("AVFrame" "ch_layout" "libavutil/frame.h" LIBAVUTIL_AVFRAME_HAS_CH_LAYOUT)
check_struct_has_member("AVVulkanFramesContext" "format" "libavutil/hwcontext_vulkan.h" LIBAVUTIL_AVFULKANFRAMESCONTEXT_HAS_FORMAT)
cmake_pop_check_state()
endif()
if(FFmpeg_FOUND AND LIBAVUTIL_AVFRAME_HAS_CH_LAYOUT)
add_sdl_test_executable(testffmpeg NO_C90 SOURCES testffmpeg.c ${icon_bmp_header})
add_sdl_test_executable(testffmpeg NO_C90 SOURCES testffmpeg.c testffmpeg_vulkan.c ${icon_bmp_header})
if(LIBAVUTIL_AVFULKANFRAMESCONTEXT_HAS_FORMAT)
target_compile_definitions(testffmpeg PRIVATE FFMPEG_VULKAN_SUPPORT)
endif()
if(APPLE)
target_sources(testffmpeg PRIVATE testffmpeg_videotoolbox.m)
target_link_options(testffmpeg PRIVATE "-Wl,-framework,CoreFoundation" "-Wl,-framework,CoreVideo" "-Wl,-framework,Metal")
target_link_options(testffmpeg PRIVATE "-Wl,-framework,CoreVideo")
endif()
if(HAVE_OPENGLES_V2)
if(TARGET OpenGL::EGL)
message(DEBUG "Enabling EGL support in testffmpeg")
target_link_libraries(testffmpeg PRIVATE OpenGL::EGL)
target_compile_definitions(testffmpeg PRIVATE HAVE_EGL)
if(TARGET OpenGL::EGL)
target_link_libraries(testffmpeg PRIVATE OpenGL::EGL)
endif()
endif()
target_include_directories(testffmpeg BEFORE PRIVATE ${SDL3_SOURCE_DIR}/src/video/khronos)
target_link_libraries(testffmpeg PRIVATE ${FFMPEG_LIBRARIES})
else()
message(STATUS "Can't find ffmpeg 5.1.3 or newer, skipping testffmpeg")
@ -348,8 +356,10 @@ files2headers(gamepad_image_headers
gamepad_touchpad.bmp
)
files2headers(icon_bmp_header icon.bmp)
files2headers(glass_bmp_header glass.bmp)
add_sdl_test_executable(testaudio MAIN_CALLBACKS NEEDS_RESOURCES TESTUTILS SOURCES testaudio.c)
add_sdl_test_executable(testcolorspace SOURCES testcolorspace.c)
add_sdl_test_executable(testfile NONINTERACTIVE SOURCES testfile.c)
add_sdl_test_executable(testcontroller TESTUTILS SOURCES testcontroller.c gamepadutils.c ${gamepad_image_headers})
add_sdl_test_executable(testgeometry TESTUTILS SOURCES testgeometry.c)
@ -358,8 +368,11 @@ add_sdl_test_executable(testgles SOURCES testgles.c)
if(ANDROID)
target_link_libraries(testgles PRIVATE GLESv1_CM)
endif()
add_sdl_test_executable(testgles2 SOURCES testgles2.c)
add_sdl_test_executable(testgles2_sdf NEEDS_RESOURCES TESTUTILS SOURCES testgles2_sdf.c)
check_include_file("GLES2/gl2platform.h" HAVE_GLES2_GL2PLATFORM_H)
if(HAVE_GLES2_GL2PLATFORM_H OR (TARGET SDL3-static OR SDL3-shared))
add_sdl_test_executable(testgles2 SOURCES testgles2.c)
add_sdl_test_executable(testgles2_sdf NEEDS_RESOURCES TESTUTILS SOURCES testgles2_sdf.c)
endif()
add_sdl_test_executable(testhaptic SOURCES testhaptic.c)
add_sdl_test_executable(testhotplug SOURCES testhotplug.c)
add_sdl_test_executable(testpen SOURCES testpen.c)
@ -386,15 +399,14 @@ add_sdl_test_executable(testscale NEEDS_RESOURCES TESTUTILS SOURCES testscale.c)
add_sdl_test_executable(testsem NONINTERACTIVE NONINTERACTIVE_ARGS 10 NONINTERACTIVE_TIMEOUT 30 SOURCES testsem.c)
add_sdl_test_executable(testsensor SOURCES testsensor.c)
add_sdl_test_executable(testshader NEEDS_RESOURCES TESTUTILS SOURCES testshader.c)
add_sdl_test_executable(testshape NEEDS_RESOURCES SOURCES testshape.c)
add_sdl_test_executable(testshape NEEDS_RESOURCES SOURCES testshape.c ${glass_bmp_header})
add_sdl_test_executable(testsprite MAIN_CALLBACKS NEEDS_RESOURCES TESTUTILS SOURCES testsprite.c)
add_sdl_test_executable(testspriteminimal SOURCES testspriteminimal.c ${icon_bmp_header})
add_sdl_test_executable(teststreaming NEEDS_RESOURCES TESTUTILS SOURCES teststreaming.c)
add_sdl_test_executable(testtimer NONINTERACTIVE NONINTERACTIVE_ARGS --no-interactive NONINTERACTIVE_TIMEOUT 60 SOURCES testtimer.c)
add_sdl_test_executable(testurl SOURCES testurl.c)
add_sdl_test_executable(testver NONINTERACTIVE SOURCES testver.c)
add_sdl_test_executable(testvideocapture SOURCES testvideocapture.c)
add_sdl_test_executable(testvideocaptureminimal SOURCES testvideocaptureminimal.c)
add_sdl_test_executable(testcamera MAIN_CALLBACKS SOURCES testcamera.c)
add_sdl_test_executable(testviewport NEEDS_RESOURCES TESTUTILS SOURCES testviewport.c)
add_sdl_test_executable(testwm SOURCES testwm.c)
add_sdl_test_executable(testyuv NONINTERACTIVE NONINTERACTIVE_ARGS "--automated" NEEDS_RESOURCES TESTUTILS SOURCES testyuv.c testyuv_cvt.c)
@ -408,6 +420,9 @@ add_sdl_test_executable(testcustomcursor SOURCES testcustomcursor.c)
add_sdl_test_executable(testvulkan NO_C90 SOURCES testvulkan.c)
add_sdl_test_executable(testoffscreen SOURCES testoffscreen.c)
add_sdl_test_executable(testpopup SOURCES testpopup.c)
add_sdl_test_executable(testdialog SOURCES testdialog.c)
add_sdl_test_executable(testtime SOURCES testtime.c)
add_sdl_test_executable(testmanymouse SOURCES testmanymouse.c)
if (HAVE_WAYLAND)
# Set the GENERATED property on the protocol file, since it is first created at build time
@ -568,41 +583,52 @@ set(TESTS_ENVIRONMENT
PATH=$<TARGET_FILE_DIR:SDL3::${sdl_name_component}>
)
foreach(TEST ${SDL_TEST_EXECUTABLES})
get_property(noninteractive TARGET ${TEST} PROPERTY SDL_NONINTERACTIVE)
function(add_sdl_test TEST TARGET)
cmake_parse_arguments(ast "INSTALL" "" "" ${ARGN})
get_property(noninteractive TARGET ${TARGET} PROPERTY SDL_NONINTERACTIVE)
if(noninteractive)
set(command ${TEST})
get_property(noninteractive_arguments TARGET ${TEST} PROPERTY SDL_NONINTERACTIVE_ARGUMENTS)
set(command ${TARGET})
get_property(noninteractive_arguments TARGET ${TARGET} PROPERTY SDL_NONINTERACTIVE_ARGUMENTS)
if(noninteractive_arguments)
list(APPEND command ${noninteractive_arguments})
endif()
add_test(
NAME ${TEST}
COMMAND ${command}
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
NAME ${TEST}
COMMAND ${command}
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
)
set_tests_properties(${TEST} PROPERTIES ENVIRONMENT "${TESTS_ENVIRONMENT}")
get_property(noninteractive_timeout TARGET ${TEST} PROPERTY SDL_NONINTERACTIVE_TIMEOUT)
get_property(noninteractive_timeout TARGET ${TARGET} PROPERTY SDL_NONINTERACTIVE_TIMEOUT)
if(NOT noninteractive_timeout)
set(noninteractive_timeout 10)
endif()
math(EXPR noninteractive_timeout "${noninteractive_timeout}*${SDL_TESTS_TIMEOUT_MULTIPLIER}")
set_tests_properties(${TEST} PROPERTIES TIMEOUT "${noninteractive_timeout}")
if(SDL_INSTALL_TESTS)
set(exe ${TEST})
if(ast_INSTALL AND SDL_INSTALL_TESTS)
set(exe ${TARGET})
set(installedtestsdir "${CMAKE_INSTALL_FULL_LIBEXECDIR}/installed-tests/SDL3")
configure_file(template.test.in "${exe}.test" @ONLY)
install(
FILES "${CMAKE_CURRENT_BINARY_DIR}/${exe}.test"
DESTINATION ${CMAKE_INSTALL_DATADIR}/installed-tests/SDL3
FILES "${CMAKE_CURRENT_BINARY_DIR}/${exe}.test"
DESTINATION ${CMAKE_INSTALL_DATADIR}/installed-tests/SDL3
)
endif()
if(TARGET pretest AND NOT "${TEST}" MATCHES "pretest")
if(TARGET pretest AND NOT "${TARGET}" MATCHES "pretest")
set_property(TEST ${TEST} APPEND PROPERTY DEPENDS pretest)
endif()
endif()
endfunction()
foreach(TARGET ${SDL_TEST_EXECUTABLES})
add_sdl_test(${TARGET} ${TARGET} INSTALL)
endforeach()
add_sdl_test(testautomation-no-simd testautomation)
set_property(TEST testautomation-no-simd APPEND PROPERTY ENVIRONMENT "SDL_CPU_FEATURE_MASK=-all")
add_sdl_test(testplatform-no-simd testplatform)
set_property(TEST testplatform-no-simd APPEND PROPERTY ENVIRONMENT "SDL_CPU_FEATURE_MASK=-all")
if(SDL_INSTALL_TESTS)
if(RISCOS)
install(

View File

@ -6,7 +6,7 @@ These are test programs for the SDL library:
testsurround Audio test -- play test tone on each audio channel
testaudioinfo Lists audio device capabilities
testerror Tests multi-threaded error handling
testfile Tests RWops layer
testfile Tests SDL_IOStream layer
testgl A very simple example of using OpenGL with SDL
testiconv Tests international string conversion
testkeys List the available keyboard keys

View File

@ -15,14 +15,14 @@
pump the event loop and catch keystrokes.
*/
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
static SDLTest_CommonState *state;
static SDLTest_TextWindow *textwin;
static int done;
@ -228,7 +228,7 @@ static void loop(void)
/* Slow down framerate */
SDL_Delay(100);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -266,7 +266,7 @@ int main(int argc, char *argv[])
SDL_GetWindowSize(state->windows[0], &w, &h);
textwin = SDLTest_TextWindowCreate(0.f, 0.f, (float)w, (float)h);
#ifdef __IOS__
#ifdef SDL_PLATFORM_IOS
{
int i;
/* Creating the context creates the view, which we need to show keyboard */
@ -285,7 +285,7 @@ int main(int argc, char *argv[])
/* Watch keystrokes */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -15,17 +15,17 @@
pump the event loop and catch keystrokes.
*/
#include <stdio.h>
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdio.h>
#include <stdlib.h>
static int done;
/* Call this instead of exit(), so we can clean up SDL: atexit() is evil. */
@ -214,7 +214,7 @@ static void loop(void)
}
(void)fprintf(stderr, "exiting event loop\n");
(void)fflush(stderr);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -279,7 +279,7 @@ int main(int argc, char *argv[])
renderer = SDL_CreateRenderer(window, NULL, 0);
SDL_RenderPresent(renderer);
#ifdef __IOS__
#ifdef SDL_PLATFORM_IOS
/* Creating the context creates the view, which we need to show keyboard */
SDL_GL_CreateContext(window);
#endif
@ -295,7 +295,7 @@ int main(int argc, char *argv[])
thread = SDL_CreateThread(ping_thread, "PingThread", NULL);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -135,9 +135,9 @@ static SDL_Texture *CreateTexture(SDL_Renderer *renderer, unsigned char *data, u
{
SDL_Texture *texture = NULL;
SDL_Surface *surface;
SDL_RWops *src = SDL_RWFromConstMem(data, len);
SDL_IOStream *src = SDL_IOFromConstMem(data, len);
if (src) {
surface = SDL_LoadBMP_RW(src, SDL_TRUE);
surface = SDL_LoadBMP_IO(src, SDL_TRUE);
if (surface) {
texture = SDL_CreateTextureFromSurface(renderer, surface);
SDL_DestroySurface(surface);
@ -649,6 +649,11 @@ static const char *gamepad_button_names[] = {
"Right Paddle 2",
"Left Paddle 2",
"Touchpad",
"Misc2",
"Misc3",
"Misc4",
"Misc5",
"Misc6",
};
SDL_COMPILE_TIME_ASSERT(gamepad_button_names, SDL_arraysize(gamepad_button_names) == SDL_GAMEPAD_BUTTON_MAX);

BIN
external/sdl/SDL/test/glass.bmp vendored Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 MiB

128148
external/sdl/SDL/test/glass.h vendored Normal file

File diff suppressed because it is too large Load Diff

View File

@ -42,7 +42,7 @@ static int fillerup(void)
return 0;
}
int SDL_AppInit(int argc, char *argv[])
int SDL_AppInit(void **appstate, int argc, char *argv[])
{
int i;
char *filename = NULL;
@ -119,17 +119,17 @@ int SDL_AppInit(int argc, char *argv[])
return 0;
}
int SDL_AppEvent(const SDL_Event *event)
int SDL_AppEvent(void *appstate, const SDL_Event *event)
{
return (event->type == SDL_EVENT_QUIT) ? 1 : 0;
}
int SDL_AppIterate(void)
int SDL_AppIterate(void *appstate)
{
return fillerup();
}
void SDL_AppQuit(void)
void SDL_AppQuit(void *appstate)
{
SDL_DestroyAudioStream(stream);
SDL_free(wave.sound);

View File

@ -42,9 +42,9 @@ static void RunBasicTest(void)
SDL_Log("\nspin lock---------------------------------------\n\n");
SDL_AtomicLock(&lock);
SDL_LockSpinlock(&lock);
SDL_Log("AtomicLock lock=%d\n", lock);
SDL_AtomicUnlock(&lock);
SDL_UnlockSpinlock(&lock);
SDL_Log("AtomicUnlock lock=%d\n", lock);
SDL_Log("\natomic -----------------------------------------\n\n");
@ -68,10 +68,10 @@ static void RunBasicTest(void)
SDL_Log("AtomicDecRef() tfret=%s val=%d\n", tf(tfret), SDL_AtomicGet(&v));
SDL_AtomicSet(&v, 10);
tfret = (SDL_AtomicCAS(&v, 0, 20) == SDL_FALSE);
tfret = (SDL_AtomicCompareAndSwap(&v, 0, 20) == SDL_FALSE);
SDL_Log("AtomicCAS() tfret=%s val=%d\n", tf(tfret), SDL_AtomicGet(&v));
value = SDL_AtomicGet(&v);
tfret = (SDL_AtomicCAS(&v, value, 20) == SDL_TRUE);
tfret = (SDL_AtomicCompareAndSwap(&v, value, 20) == SDL_TRUE);
SDL_Log("AtomicCAS() tfret=%s val=%d\n", tf(tfret), SDL_AtomicGet(&v));
}
@ -179,12 +179,12 @@ static void RunEpicTest(void)
SDL_Log("Test compare and exchange\n");
b = SDL_AtomicCAS(&good, 500, 43);
b = SDL_AtomicCompareAndSwap(&good, 500, 43);
SDL_assert(!b); /* no swap since CountTo!=500 */
v = SDL_AtomicGet(&good);
SDL_assert(v == CountTo); /* ensure no swap */
b = SDL_AtomicCAS(&good, CountTo, 44);
b = SDL_AtomicCompareAndSwap(&good, CountTo, 44);
SDL_assert(!!b); /* will swap */
v = SDL_AtomicGet(&good);
SDL_assert(v == 44);
@ -317,10 +317,10 @@ static SDL_bool EnqueueEvent_LockFree(SDL_EventQueue *queue, const SDL_Event *ev
#ifdef TEST_SPINLOCK_FIFO
/* This is a gate so an external thread can lock the queue */
SDL_AtomicLock(&queue->lock);
SDL_LockSpinlock(&queue->lock);
SDL_assert(SDL_AtomicGet(&queue->watcher) == 0);
SDL_AtomicIncRef(&queue->rwcount);
SDL_AtomicUnlock(&queue->lock);
SDL_UnlockSpinlock(&queue->lock);
#endif
queue_pos = (unsigned)SDL_AtomicGet(&queue->enqueue_pos);
@ -331,7 +331,7 @@ static SDL_bool EnqueueEvent_LockFree(SDL_EventQueue *queue, const SDL_Event *ev
delta = (int)(entry_seq - queue_pos);
if (delta == 0) {
/* The entry and the queue position match, try to increment the queue position */
if (SDL_AtomicCAS(&queue->enqueue_pos, (int)queue_pos, (int)(queue_pos + 1))) {
if (SDL_AtomicCompareAndSwap(&queue->enqueue_pos, (int)queue_pos, (int)(queue_pos + 1))) {
/* We own the object, fill it! */
entry->event = *event;
SDL_AtomicSet(&entry->sequence, (int)(queue_pos + 1));
@ -364,10 +364,10 @@ static SDL_bool DequeueEvent_LockFree(SDL_EventQueue *queue, SDL_Event *event)
#ifdef TEST_SPINLOCK_FIFO
/* This is a gate so an external thread can lock the queue */
SDL_AtomicLock(&queue->lock);
SDL_LockSpinlock(&queue->lock);
SDL_assert(SDL_AtomicGet(&queue->watcher) == 0);
SDL_AtomicIncRef(&queue->rwcount);
SDL_AtomicUnlock(&queue->lock);
SDL_UnlockSpinlock(&queue->lock);
#endif
queue_pos = (unsigned)SDL_AtomicGet(&queue->dequeue_pos);
@ -378,7 +378,7 @@ static SDL_bool DequeueEvent_LockFree(SDL_EventQueue *queue, SDL_Event *event)
delta = (int)(entry_seq - (queue_pos + 1));
if (delta == 0) {
/* The entry and the queue position match, try to increment the queue position */
if (SDL_AtomicCAS(&queue->dequeue_pos, (int)queue_pos, (int)(queue_pos + 1))) {
if (SDL_AtomicCompareAndSwap(&queue->dequeue_pos, (int)queue_pos, (int)(queue_pos + 1))) {
/* We own the object, fill it! */
*event = entry->event;
SDL_AtomicSet(&entry->sequence, (int)(queue_pos + MAX_ENTRIES));
@ -564,14 +564,14 @@ static int SDLCALL FIFO_Watcher(void *_data)
SDL_EventQueue *queue = (SDL_EventQueue *)_data;
while (SDL_AtomicGet(&queue->active)) {
SDL_AtomicLock(&queue->lock);
SDL_LockSpinlock(&queue->lock);
SDL_AtomicIncRef(&queue->watcher);
while (SDL_AtomicGet(&queue->rwcount) > 0) {
SDL_Delay(0);
}
/* Do queue manipulation here... */
(void)SDL_AtomicDecRef(&queue->watcher);
SDL_AtomicUnlock(&queue->lock);
SDL_UnlockSpinlock(&queue->lock);
/* Wait a bit... */
SDL_Delay(1);

View File

@ -644,7 +644,7 @@ static Thing *LoadWavThing(const char *fname, float x, float y)
static const ThingType can_be_dropped_onto[] = { THING_TRASHCAN, THING_NULL };
char *titlebar = NULL;
const char *nodirs = SDL_strrchr(fname, '/');
#ifdef __WINDOWS__
#ifdef SDL_PLATFORM_WINDOWS
const char *nodirs2 = SDL_strrchr(nodirs ? nodirs : fname, '\\');
if (nodirs2) {
nodirs = nodirs2;
@ -1036,7 +1036,7 @@ static void WindowResized(const int newwinw, const int newwinh)
state->window_h = newwinh;
}
int SDL_AppInit(int argc, char *argv[])
int SDL_AppInit(void **appstate, int argc, char *argv[])
{
int i;
@ -1094,7 +1094,7 @@ int SDL_AppInit(int argc, char *argv[])
static SDL_bool saw_event = SDL_FALSE;
int SDL_AppEvent(const SDL_Event *event)
int SDL_AppEvent(void *appstate, const SDL_Event *event)
{
Thing *thing = NULL;
@ -1168,7 +1168,7 @@ int SDL_AppEvent(const SDL_Event *event)
break;
case SDL_EVENT_MOUSE_WHEEL:
UpdateMouseOver(event->wheel.mouseX, event->wheel.mouseY);
UpdateMouseOver(event->wheel.mouse_x, event->wheel.mouse_y);
break;
case SDL_EVENT_KEY_DOWN:
@ -1214,7 +1214,7 @@ int SDL_AppEvent(const SDL_Event *event)
return SDLTest_CommonEventMainCallbacks(state, event);
}
int SDL_AppIterate(void)
int SDL_AppIterate(void *appstate)
{
if (app_ready_ticks == 0) {
app_ready_ticks = SDL_GetTicks();
@ -1232,7 +1232,7 @@ int SDL_AppIterate(void)
return 0; /* keep going. */
}
void SDL_AppQuit(void)
void SDL_AppQuit(void *appstate)
{
while (things) {
DestroyThing(things); /* make sure all the audio devices are closed, etc. */

View File

@ -21,7 +21,7 @@ static SDL_AudioStream *stream_in = NULL;
static SDL_AudioStream *stream_out = NULL;
static SDLTest_CommonState *state = NULL;
int SDL_AppInit(int argc, char **argv)
int SDL_AppInit(void **appstate, int argc, char **argv)
{
SDL_AudioDeviceID *devices;
SDL_AudioSpec outspec;
@ -145,7 +145,7 @@ int SDL_AppInit(int argc, char **argv)
return 0;
}
int SDL_AppEvent(const SDL_Event *event)
int SDL_AppEvent(void *appstate, const SDL_Event *event)
{
if (event->type == SDL_EVENT_QUIT) {
return 1; /* terminate as success. */
@ -169,7 +169,7 @@ int SDL_AppEvent(const SDL_Event *event)
return 0; /* keep going. */
}
int SDL_AppIterate(void)
int SDL_AppIterate(void *appstate)
{
if (!SDL_AudioDevicePaused(SDL_GetAudioStreamDevice(stream_in))) {
SDL_SetRenderDrawColor(renderer, 0, 255, 0, 255);
@ -195,7 +195,7 @@ int SDL_AppIterate(void)
return 0; /* keep app going. */
}
void SDL_AppQuit(void)
void SDL_AppQuit(void *appstate)
{
SDL_Log("Shutting down.\n");
const SDL_AudioDeviceID devid_in = SDL_GetAudioStreamDevice(stream_in);

View File

@ -12,21 +12,21 @@
/* Program to test hotplugging of audio devices */
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#ifdef HAVE_SIGNAL_H
#include <signal.h>
#endif
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include "testutils.h"
static SDL_AudioSpec spec;
static Uint8 *sound = NULL; /* Pointer to wave data */
static Uint32 soundlen = 0; /* Length of wave data */
@ -101,7 +101,7 @@ static void iteration(void)
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
static void loop(void)
{
if (done)
@ -194,7 +194,7 @@ int main(int argc, char *argv[])
SDL_Log("Select a driver with the SDL_AUDIO_DRIVER environment variable.\n");
SDL_Log("Using audio driver: %s\n", SDL_GetCurrentAudioDriver());
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -17,7 +17,7 @@
#include <SDL3/SDL_test.h>
#include "testutils.h"
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
@ -219,7 +219,7 @@ static void loop(void)
while (SDL_PollEvent(&e)) {
SDLTest_CommonEvent(state, &e, &done);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -432,7 +432,7 @@ int main(int argc, char *argv[])
SDL_BindAudioStream(state->audio_id, stream);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -30,6 +30,7 @@ static SDLTest_TestSuiteReference *testSuites[] = {
&intrinsicsTestSuite,
&joystickTestSuite,
&keyboardTestSuite,
&logTestSuite,
&mainTestSuite,
&mathTestSuite,
&mouseTestSuite,
@ -39,10 +40,11 @@ static SDLTest_TestSuiteReference *testSuites[] = {
&propertiesTestSuite,
&rectTestSuite,
&renderTestSuite,
&rwopsTestSuite,
&iostrmTestSuite,
&sdltestTestSuite,
&stdlibTestSuite,
&surfaceTestSuite,
&timeTestSuite,
&timerTestSuite,
&videoTestSuite,
&subsystemsTestSuite, /* run last, not interfere with other test enviroment */

View File

@ -54,7 +54,7 @@ static void SDLCALL audio_testCallback(void *userdata, Uint8 *stream, int len)
}
#endif
static SDL_AudioDeviceID g_audio_id = -1;
static SDL_AudioDeviceID g_audio_id = 0;
/* Test case functions */
@ -188,6 +188,7 @@ static int audio_initOpenCloseQuitAudio(void *arg)
desired.freq = 22050;
desired.format = SDL_AUDIO_S16;
desired.channels = 2;
break;
case 1:
/* Set custom desired spec */

View File

@ -117,7 +117,7 @@ TestGuidToString(void *arg)
/* Serialise to limited-length buffers */
for (size = 0; size <= 36; ++size) {
const Uint8 fill_char = size + 0xa0;
const Uint8 fill_char = (Uint8)(size + 0xa0);
Uint32 expected_prefix;
Uint32 actual_prefix;
int written_size;

View File

@ -7,18 +7,14 @@
#include "testautomation_suites.h"
static const char *HintsEnum[] = {
SDL_HINT_ACCELEROMETER_AS_JOYSTICK,
SDL_HINT_FRAMEBUFFER_ACCELERATION,
SDL_HINT_GAMECONTROLLERCONFIG,
SDL_HINT_GRAB_KEYBOARD,
SDL_HINT_JOYSTICK_ALLOW_BACKGROUND_EVENTS,
SDL_HINT_MAC_CTRL_CLICK_EMULATE_RIGHT_CLICK,
SDL_HINT_MOUSE_RELATIVE_MODE_WARP,
SDL_HINT_ORIENTATIONS,
SDL_HINT_RENDER_DIRECT3D_THREADSAFE,
SDL_HINT_RENDER_DRIVER,
SDL_HINT_RENDER_OPENGL_SHADERS,
SDL_HINT_RENDER_SCALE_QUALITY,
SDL_HINT_RENDER_VSYNC,
SDL_HINT_TIMER_RESOLUTION,
SDL_HINT_VIDEO_ALLOW_SCREENSAVER,
@ -29,18 +25,14 @@ static const char *HintsEnum[] = {
SDL_HINT_XINPUT_ENABLED,
};
static const char *HintsVerbose[] = {
"SDL_ACCELEROMETER_AS_JOYSTICK",
"SDL_FRAMEBUFFER_ACCELERATION",
"SDL_GAMECONTROLLERCONFIG",
"SDL_GRAB_KEYBOARD",
"SDL_JOYSTICK_ALLOW_BACKGROUND_EVENTS",
"SDL_MAC_CTRL_CLICK_EMULATE_RIGHT_CLICK",
"SDL_MOUSE_RELATIVE_MODE_WARP",
"SDL_ORIENTATIONS",
"SDL_RENDER_DIRECT3D_THREADSAFE",
"SDL_RENDER_DRIVER",
"SDL_RENDER_OPENGL_SHADERS",
"SDL_RENDER_SCALE_QUALITY",
"SDL_RENDER_VSYNC",
"SDL_TIMER_RESOLUTION",
"SDL_VIDEO_ALLOW_SCREENSAVER",

View File

@ -2,8 +2,10 @@
* Intrinsics test suite
*/
#ifndef NO_BUILD_CONFIG
/* Disable intrinsics that are unsupported by the current compiler */
#include <build_config/SDL_build_config.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_intrin.h>
@ -95,7 +97,7 @@ static void verify_ints_addition(const Sint32 *dest, const Sint32 *a, const Sint
for (i = 0; i < size; ++i) {
Sint32 expected = a[i] + b[i];
if (dest[i] != expected) {
SDLTest_AssertCheck(SDL_FALSE, "%"SDL_PRIs32" + %"SDL_PRIs32" = %"SDL_PRIs32", expected %"SDL_PRIs32" ([%"SDL_PRIu32"/%"SDL_PRIu32"] %s)",
SDLTest_AssertCheck(SDL_FALSE, "%" SDL_PRIs32 " + %" SDL_PRIs32 " = %" SDL_PRIs32 ", expected %" SDL_PRIs32 " ([%" SDL_PRIu32 "/%" SDL_PRIu32 "] %s)",
a[i], b[i], dest[i], expected, (Uint32)i, (Uint32)size, desc);
all_good = 0;
}
@ -115,7 +117,7 @@ static void verify_ints_multiplication(const Sint32 *dest, const Sint32 *a, cons
for (i = 0; i < size; ++i) {
Sint32 expected = a[i] * b[i];
if (dest[i] != expected) {
SDLTest_AssertCheck(SDL_FALSE, "%"SDL_PRIs32" * %"SDL_PRIs32" = %"SDL_PRIs32", expected %"SDL_PRIs32" ([%"SDL_PRIu32"/%"SDL_PRIu32"] %s)",
SDLTest_AssertCheck(SDL_FALSE, "%" SDL_PRIs32 " * %" SDL_PRIs32 " = %" SDL_PRIs32 ", expected %" SDL_PRIs32 " ([%" SDL_PRIu32 "/%" SDL_PRIu32 "] %s)",
a[i], b[i], dest[i], expected, (Uint32)i, (Uint32)size, desc);
all_good = 0;
}
@ -136,7 +138,7 @@ static void verify_floats_addition(const float *dest, const float *a, const floa
float expected = a[i] + b[i];
float abs_error = SDL_fabsf(dest[i] - expected);
if (abs_error > 1.0e-5f) {
SDLTest_AssertCheck(SDL_FALSE, "%g + %g = %g, expected %g (error = %g) ([%"SDL_PRIu32"/%"SDL_PRIu32"] %s)",
SDLTest_AssertCheck(SDL_FALSE, "%g + %g = %g, expected %g (error = %g) ([%" SDL_PRIu32 "/%" SDL_PRIu32 "] %s)",
a[i], b[i], dest[i], expected, abs_error, (Uint32) i, (Uint32) size, desc);
all_good = 0;
}
@ -157,7 +159,7 @@ static void verify_doubles_addition(const double *dest, const double *a, const d
double expected = a[i] + b[i];
double abs_error = SDL_fabs(dest[i] - expected);
if (abs_error > 1.0e-5) {
SDLTest_AssertCheck(abs_error < 1.0e-5f, "%g + %g = %g, expected %g (error = %g) ([%"SDL_PRIu32"/%"SDL_PRIu32"] %s)",
SDLTest_AssertCheck(abs_error < 1.0e-5f, "%g + %g = %g, expected %g (error = %g) ([%" SDL_PRIu32 "/%" SDL_PRIu32 "] %s)",
a[i], b[i], dest[i], expected, abs_error, (Uint32) i, (Uint32) size, desc);
all_good = SDL_FALSE;
}
@ -251,7 +253,7 @@ SDL_TARGETING("sse4.1") static void kernel_ints_mul_sse4_1(Sint32 *dest, const S
#ifdef SDL_SSE4_2_INTRINSICS
SDL_TARGETING("sse4.2") static Uint32 calculate_crc32c_sse4_2(const char *text) {
Uint32 crc32c = ~0;
Uint32 crc32c = ~0u;
size_t len = SDL_strlen(text);
#if defined(__x86_64__) || defined(_M_X64)

View File

@ -0,0 +1,701 @@
/**
* Automated SDL_IOStream test.
*
* Original code written by Edgar Simo "bobbens"
* Ported by Markus Kauppila (markus.kauppila@gmail.com)
* Updated and extended for SDL_test by aschiffler at ferzkopp dot net
*
* Released under Public Domain.
*/
/* quiet windows compiler warnings */
#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS)
#define _CRT_SECURE_NO_WARNINGS
#endif
#include <stdio.h>
#include <SDL3/SDL.h>
#include <SDL3/SDL_test.h>
#include "testautomation_suites.h"
/* ================= Test Case Implementation ================== */
static const char *IOStreamReadTestFilename = "iostrm_read";
static const char *IOStreamWriteTestFilename = "iostrm_write";
static const char *IOStreamAlphabetFilename = "iostrm_alphabet";
static const char IOStreamHelloWorldTestString[] = "Hello World!";
static const char IOStreamHelloWorldCompString[] = "Hello World!";
static const char IOStreamAlphabetString[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
/* Fixture */
static void IOStreamSetUp(void *arg)
{
size_t fileLen;
FILE *handle;
size_t writtenLen;
int result;
/* Clean up from previous runs (if any); ignore errors */
(void)remove(IOStreamReadTestFilename);
(void)remove(IOStreamWriteTestFilename);
(void)remove(IOStreamAlphabetFilename);
/* Create a test file */
handle = fopen(IOStreamReadTestFilename, "w");
SDLTest_AssertCheck(handle != NULL, "Verify creation of file '%s' returned non NULL handle", IOStreamReadTestFilename);
if (handle == NULL) {
return;
}
/* Write some known text into it */
fileLen = SDL_strlen(IOStreamHelloWorldTestString);
writtenLen = fwrite(IOStreamHelloWorldTestString, 1, fileLen, handle);
SDLTest_AssertCheck(fileLen == writtenLen, "Verify number of written bytes, expected %i, got %i", (int)fileLen, (int)writtenLen);
result = fclose(handle);
SDLTest_AssertCheck(result == 0, "Verify result from fclose, expected 0, got %i", result);
/* Create a second test file */
handle = fopen(IOStreamAlphabetFilename, "w");
SDLTest_AssertCheck(handle != NULL, "Verify creation of file '%s' returned non NULL handle", IOStreamAlphabetFilename);
if (handle == NULL) {
return;
}
/* Write alphabet text into it */
fileLen = SDL_strlen(IOStreamAlphabetString);
writtenLen = fwrite(IOStreamAlphabetString, 1, fileLen, handle);
SDLTest_AssertCheck(fileLen == writtenLen, "Verify number of written bytes, expected %i, got %i", (int)fileLen, (int)writtenLen);
result = fclose(handle);
SDLTest_AssertCheck(result == 0, "Verify result from fclose, expected 0, got %i", result);
SDLTest_AssertPass("Creation of test file completed");
}
static void IOStreamTearDown(void *arg)
{
int result;
/* Remove the created files to clean up; ignore errors for write filename */
result = remove(IOStreamReadTestFilename);
SDLTest_AssertCheck(result == 0, "Verify result from remove(%s), expected 0, got %i", IOStreamReadTestFilename, result);
(void)remove(IOStreamWriteTestFilename);
result = remove(IOStreamAlphabetFilename);
SDLTest_AssertCheck(result == 0, "Verify result from remove(%s), expected 0, got %i", IOStreamAlphabetFilename, result);
SDLTest_AssertPass("Cleanup of test files completed");
}
/**
* Makes sure parameters work properly. Local helper function.
*
* \sa SDL_SeekIO
* \sa SDL_ReadIO
*/
static void testGenericIOStreamValidations(SDL_IOStream *rw, SDL_bool write)
{
char buf[sizeof(IOStreamHelloWorldTestString)];
Sint64 i;
size_t s;
int seekPos = SDLTest_RandomIntegerInRange(4, 8);
/* Clear buffer */
SDL_zeroa(buf);
/* Set to start. */
i = SDL_SeekIO(rw, 0, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_SeekIO (SDL_IO_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test write */
s = SDL_WriteIO(rw, IOStreamHelloWorldTestString, sizeof(IOStreamHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_WriteIO succeeded");
if (write) {
SDLTest_AssertCheck(s == sizeof(IOStreamHelloWorldTestString) - 1, "Verify result of writing with SDL_WriteIO, expected %i, got %i", (int)sizeof(IOStreamHelloWorldTestString) - 1, (int)s);
} else {
SDLTest_AssertCheck(s == 0, "Verify result of writing with SDL_WriteIO, expected: 0, got %i", (int)s);
}
/* Test seek to random position */
i = SDL_SeekIO(rw, seekPos, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(i == (Sint64)seekPos, "Verify seek to %i with SDL_SeekIO (SDL_IO_SEEK_SET), expected %i, got %" SDL_PRIs64, seekPos, seekPos, i);
/* Test seek back to start */
i = SDL_SeekIO(rw, 0, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_SeekIO (SDL_IO_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test read */
s = SDL_ReadIO(rw, buf, sizeof(IOStreamHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_ReadIO succeeded");
SDLTest_AssertCheck(
s == (sizeof(IOStreamHelloWorldTestString) - 1),
"Verify result from SDL_ReadIO, expected %i, got %i",
(int)(sizeof(IOStreamHelloWorldTestString) - 1),
(int)s);
SDLTest_AssertCheck(
SDL_memcmp(buf, IOStreamHelloWorldTestString, sizeof(IOStreamHelloWorldTestString) - 1) == 0,
"Verify read bytes match expected string, expected '%s', got '%s'", IOStreamHelloWorldTestString, buf);
/* Test seek back to start */
i = SDL_SeekIO(rw, 0, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_SeekIO (SDL_IO_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test printf */
s = SDL_IOprintf(rw, "%s", IOStreamHelloWorldTestString);
SDLTest_AssertPass("Call to SDL_IOprintf succeeded");
if (write) {
SDLTest_AssertCheck(s == sizeof(IOStreamHelloWorldTestString) - 1, "Verify result of writing with SDL_IOprintf, expected %i, got %i", (int)sizeof(IOStreamHelloWorldTestString) - 1, (int)s);
} else {
SDLTest_AssertCheck(s == 0, "Verify result of writing with SDL_WriteIO, expected: 0, got %i", (int)s);
}
/* Test seek back to start */
i = SDL_SeekIO(rw, 0, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_SeekIO (SDL_IO_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test read */
s = SDL_ReadIO(rw, buf, sizeof(IOStreamHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_ReadIO succeeded");
SDLTest_AssertCheck(
s == (sizeof(IOStreamHelloWorldTestString) - 1),
"Verify result from SDL_ReadIO, expected %i, got %i",
(int)(sizeof(IOStreamHelloWorldTestString) - 1),
(int)s);
SDLTest_AssertCheck(
SDL_memcmp(buf, IOStreamHelloWorldTestString, sizeof(IOStreamHelloWorldTestString) - 1) == 0,
"Verify read bytes match expected string, expected '%s', got '%s'", IOStreamHelloWorldTestString, buf);
/* More seek tests. */
i = SDL_SeekIO(rw, -4, SDL_IO_SEEK_CUR);
SDLTest_AssertPass("Call to SDL_SeekIO(...,-4,SDL_IO_SEEK_CUR) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(sizeof(IOStreamHelloWorldTestString) - 5),
"Verify seek to -4 with SDL_SeekIO (SDL_IO_SEEK_CUR), expected %i, got %i",
(int)(sizeof(IOStreamHelloWorldTestString) - 5),
(int)i);
i = SDL_SeekIO(rw, -1, SDL_IO_SEEK_END);
SDLTest_AssertPass("Call to SDL_SeekIO(...,-1,SDL_IO_SEEK_END) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(sizeof(IOStreamHelloWorldTestString) - 2),
"Verify seek to -1 with SDL_SeekIO (SDL_IO_SEEK_END), expected %i, got %i",
(int)(sizeof(IOStreamHelloWorldTestString) - 2),
(int)i);
/* Invalid whence seek */
i = SDL_SeekIO(rw, 0, 999);
SDLTest_AssertPass("Call to SDL_SeekIO(...,0,invalid_whence) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(-1),
"Verify seek with SDL_SeekIO (invalid_whence); expected: -1, got %i",
(int)i);
}
/**
* Negative test for SDL_IOFromFile parameters
*
* \sa SDL_IOFromFile
*
*/
static int iostrm_testParamNegative(void *arg)
{
SDL_IOStream *iostrm;
/* These should all fail. */
iostrm = SDL_IOFromFile(NULL, NULL);
SDLTest_AssertPass("Call to SDL_IOFromFile(NULL, NULL) succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromFile(NULL, NULL) returns NULL");
iostrm = SDL_IOFromFile(NULL, "ab+");
SDLTest_AssertPass("Call to SDL_IOFromFile(NULL, \"ab+\") succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromFile(NULL, \"ab+\") returns NULL");
iostrm = SDL_IOFromFile(NULL, "sldfkjsldkfj");
SDLTest_AssertPass("Call to SDL_IOFromFile(NULL, \"sldfkjsldkfj\") succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromFile(NULL, \"sldfkjsldkfj\") returns NULL");
iostrm = SDL_IOFromFile("something", "");
SDLTest_AssertPass("Call to SDL_IOFromFile(\"something\", \"\") succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromFile(\"something\", \"\") returns NULL");
iostrm = SDL_IOFromFile("something", NULL);
SDLTest_AssertPass("Call to SDL_IOFromFile(\"something\", NULL) succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromFile(\"something\", NULL) returns NULL");
iostrm = SDL_IOFromMem(NULL, 10);
SDLTest_AssertPass("Call to SDL_IOFromMem(NULL, 10) succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromMem(NULL, 10) returns NULL");
iostrm = SDL_IOFromMem((void *)IOStreamAlphabetString, 0);
SDLTest_AssertPass("Call to SDL_IOFromMem(data, 0) succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromMem(data, 0) returns NULL");
iostrm = SDL_IOFromConstMem((const void *)IOStreamAlphabetString, 0);
SDLTest_AssertPass("Call to SDL_IOFromConstMem(data, 0) succeeded");
SDLTest_AssertCheck(iostrm == NULL, "Verify SDL_IOFromConstMem(data, 0) returns NULL");
return TEST_COMPLETED;
}
/**
* Tests opening from memory.
*
* \sa SDL_IOFromMem
* \sa SDL_CloseIO
*/
static int iostrm_testMem(void *arg)
{
char mem[sizeof(IOStreamHelloWorldTestString)];
SDL_IOStream *rw;
int result;
/* Clear buffer */
SDL_zeroa(mem);
/* Open */
rw = SDL_IOFromMem(mem, sizeof(IOStreamHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_IOFromMem() succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening memory with SDL_IOFromMem does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Run generic tests */
testGenericIOStreamValidations(rw, SDL_TRUE);
/* Close */
result = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests opening from memory.
*
* \sa SDL_IOFromConstMem
* \sa SDL_CloseIO
*/
static int iostrm_testConstMem(void *arg)
{
SDL_IOStream *rw;
int result;
/* Open handle */
rw = SDL_IOFromConstMem(IOStreamHelloWorldCompString, sizeof(IOStreamHelloWorldCompString) - 1);
SDLTest_AssertPass("Call to SDL_IOFromConstMem() succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening memory with SDL_IOFromConstMem does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Run generic tests */
testGenericIOStreamValidations(rw, SDL_FALSE);
/* Close handle */
result = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests dynamic memory
*
* \sa SDL_IOFromDynamicMem
* \sa SDL_CloseIO
*/
static int iostrm_testDynamicMem(void *arg)
{
SDL_IOStream *rw;
SDL_PropertiesID props;
char *mem;
int result;
/* Open */
rw = SDL_IOFromDynamicMem();
SDLTest_AssertPass("Call to SDL_IOFromDynamicMem() succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening memory with SDL_IOFromDynamicMem does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Set the chunk size to 1 byte */
props = SDL_GetIOProperties(rw);
SDL_SetNumberProperty(props, SDL_PROP_IOSTREAM_DYNAMIC_CHUNKSIZE_NUMBER, 1);
/* Run generic tests */
testGenericIOStreamValidations(rw, SDL_TRUE);
/* Get the dynamic memory and verify it */
mem = (char *)SDL_GetProperty(props, SDL_PROP_IOSTREAM_DYNAMIC_MEMORY_POINTER, NULL);
SDLTest_AssertPass("Call to SDL_GetProperty(props, SDL_PROP_IOSTREAM_DYNAMIC_MEMORY_POINTER, NULL) succeeded");
SDLTest_AssertCheck(mem != NULL, "Verify memory value is not NULL");
mem[SDL_GetIOSize(rw)] = '\0';
SDLTest_AssertCheck(SDL_strcmp(mem, IOStreamHelloWorldTestString) == 0, "Verify memory value is correct");
/* Take the memory and free it ourselves */
SDL_SetProperty(props, SDL_PROP_IOSTREAM_DYNAMIC_MEMORY_POINTER, NULL);
SDL_free(mem);
/* Close */
result = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests reading from file.
*
* \sa SDL_IOFromFile
* \sa SDL_CloseIO
*/
static int iostrm_testFileRead(void *arg)
{
SDL_IOStream *rw;
int result;
/* Read test. */
rw = SDL_IOFromFile(IOStreamReadTestFilename, "r");
SDLTest_AssertPass("Call to SDL_IOFromFile(..,\"r\") succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_IOFromFile in read mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Run generic tests */
testGenericIOStreamValidations(rw, SDL_FALSE);
/* Close handle */
result = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests writing from file.
*
* \sa SDL_IOFromFile
* \sa SDL_CloseIO
*/
static int iostrm_testFileWrite(void *arg)
{
SDL_IOStream *rw;
int result;
/* Write test. */
rw = SDL_IOFromFile(IOStreamWriteTestFilename, "w+");
SDLTest_AssertPass("Call to SDL_IOFromFile(..,\"w+\") succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_IOFromFile in write mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Run generic tests */
testGenericIOStreamValidations(rw, SDL_TRUE);
/* Close handle */
result = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests alloc and free RW context.
*
* \sa SDL_OpenIO
* \sa SDL_CloseIO
*/
static int iostrm_testAllocFree(void *arg)
{
/* Allocate context */
SDL_IOStreamInterface iface;
SDL_IOStream *rw;
SDL_zero(iface);
rw = SDL_OpenIO(&iface, NULL);
SDLTest_AssertPass("Call to SDL_OpenIO() succeeded");
SDLTest_AssertCheck(rw != NULL, "Validate result from SDL_OpenIO() is not NULL");
if (rw == NULL) {
return TEST_ABORTED;
}
/* Free context again */
SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
return TEST_COMPLETED;
}
/**
* Compare memory and file reads
*
* \sa SDL_IOFromMem
* \sa SDL_IOFromFile
*/
static int iostrm_testCompareRWFromMemWithRWFromFile(void *arg)
{
int slen = 26;
char buffer_file[27];
char buffer_mem[27];
size_t rv_file;
size_t rv_mem;
Uint64 sv_file;
Uint64 sv_mem;
SDL_IOStream *iostrm_file;
SDL_IOStream *iostrm_mem;
int size;
int result;
for (size = 5; size < 10; size++) {
/* Terminate buffer */
buffer_file[slen] = 0;
buffer_mem[slen] = 0;
/* Read/seek from memory */
iostrm_mem = SDL_IOFromMem((void *)IOStreamAlphabetString, slen);
SDLTest_AssertPass("Call to SDL_IOFromMem()");
rv_mem = SDL_ReadIO(iostrm_mem, buffer_mem, size * 6);
SDLTest_AssertPass("Call to SDL_ReadIO(mem, size=%d)", size * 6);
sv_mem = SDL_SeekIO(iostrm_mem, 0, SEEK_END);
SDLTest_AssertPass("Call to SDL_SeekIO(mem,SEEK_END)");
result = SDL_CloseIO(iostrm_mem);
SDLTest_AssertPass("Call to SDL_CloseIO(mem)");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
/* Read/see from file */
iostrm_file = SDL_IOFromFile(IOStreamAlphabetFilename, "r");
SDLTest_AssertPass("Call to SDL_IOFromFile()");
rv_file = SDL_ReadIO(iostrm_file, buffer_file, size * 6);
SDLTest_AssertPass("Call to SDL_ReadIO(file, size=%d)", size * 6);
sv_file = SDL_SeekIO(iostrm_file, 0, SEEK_END);
SDLTest_AssertPass("Call to SDL_SeekIO(file,SEEK_END)");
result = SDL_CloseIO(iostrm_file);
SDLTest_AssertPass("Call to SDL_CloseIO(file)");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
/* Compare */
SDLTest_AssertCheck(rv_mem == rv_file, "Verify returned read blocks matches for mem and file reads; got: rv_mem=%d rv_file=%d", (int)rv_mem, (int)rv_file);
SDLTest_AssertCheck(sv_mem == sv_file, "Verify SEEK_END position matches for mem and file seeks; got: sv_mem=%d sv_file=%d", (int)sv_mem, (int)sv_file);
SDLTest_AssertCheck(buffer_mem[slen] == 0, "Verify mem buffer termination; expected: 0, got: %d", buffer_mem[slen]);
SDLTest_AssertCheck(buffer_file[slen] == 0, "Verify file buffer termination; expected: 0, got: %d", buffer_file[slen]);
SDLTest_AssertCheck(
SDL_strncmp(buffer_mem, IOStreamAlphabetString, slen) == 0,
"Verify mem buffer contain alphabet string; expected: %s, got: %s", IOStreamAlphabetString, buffer_mem);
SDLTest_AssertCheck(
SDL_strncmp(buffer_file, IOStreamAlphabetString, slen) == 0,
"Verify file buffer contain alphabet string; expected: %s, got: %s", IOStreamAlphabetString, buffer_file);
}
return TEST_COMPLETED;
}
/**
* Tests writing and reading from file using endian aware functions.
*
* \sa SDL_IOFromFile
* \sa SDL_CloseIO
* \sa SDL_ReadU16BE
* \sa SDL_WriteU16BE
*/
static int iostrm_testFileWriteReadEndian(void *arg)
{
SDL_IOStream *rw;
Sint64 result;
int mode;
Uint16 BE16value;
Uint32 BE32value;
Uint64 BE64value;
Uint16 LE16value;
Uint32 LE32value;
Uint64 LE64value;
Uint16 BE16test;
Uint32 BE32test;
Uint64 BE64test;
Uint16 LE16test;
Uint32 LE32test;
Uint64 LE64test;
SDL_bool bresult;
int cresult;
for (mode = 0; mode < 3; mode++) {
/* Create test data */
switch (mode) {
default:
case 0:
SDLTest_Log("All 0 values");
BE16value = 0;
BE32value = 0;
BE64value = 0;
LE16value = 0;
LE32value = 0;
LE64value = 0;
break;
case 1:
SDLTest_Log("All 1 values");
BE16value = 1;
BE32value = 1;
BE64value = 1;
LE16value = 1;
LE32value = 1;
LE64value = 1;
break;
case 2:
SDLTest_Log("Random values");
BE16value = SDLTest_RandomUint16();
BE32value = SDLTest_RandomUint32();
BE64value = SDLTest_RandomUint64();
LE16value = SDLTest_RandomUint16();
LE32value = SDLTest_RandomUint32();
LE64value = SDLTest_RandomUint64();
break;
}
/* Write test. */
rw = SDL_IOFromFile(IOStreamWriteTestFilename, "w+");
SDLTest_AssertPass("Call to SDL_IOFromFile(..,\"w+\")");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_IOFromFile in write mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Write test data */
bresult = SDL_WriteU16BE(rw, BE16value);
SDLTest_AssertPass("Call to SDL_WriteU16BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU32BE(rw, BE32value);
SDLTest_AssertPass("Call to SDL_WriteU32BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU64BE(rw, BE64value);
SDLTest_AssertPass("Call to SDL_WriteU64BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU16LE(rw, LE16value);
SDLTest_AssertPass("Call to SDL_WriteU16LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU32LE(rw, LE32value);
SDLTest_AssertPass("Call to SDL_WriteU32LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU64LE(rw, LE64value);
SDLTest_AssertPass("Call to SDL_WriteU64LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
/* Test seek to start */
result = SDL_SeekIO(rw, 0, SDL_IO_SEEK_SET);
SDLTest_AssertPass("Call to SDL_SeekIO succeeded");
SDLTest_AssertCheck(result == 0, "Verify result from position 0 with SDL_SeekIO, expected 0, got %i", (int)result);
/* Read test data */
bresult = SDL_ReadU16BE(rw, &BE16test);
SDLTest_AssertPass("Call to SDL_ReadU16BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE16test == BE16value, "Validate object read from SDL_ReadU16BE, expected: %hu, got: %hu", BE16value, BE16test);
bresult = SDL_ReadU32BE(rw, &BE32test);
SDLTest_AssertPass("Call to SDL_ReadU32BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE32test == BE32value, "Validate object read from SDL_ReadU32BE, expected: %" SDL_PRIu32 ", got: %" SDL_PRIu32, BE32value, BE32test);
bresult = SDL_ReadU64BE(rw, &BE64test);
SDLTest_AssertPass("Call to SDL_ReadU64BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE64test == BE64value, "Validate object read from SDL_ReadU64BE, expected: %" SDL_PRIu64 ", got: %" SDL_PRIu64, BE64value, BE64test);
bresult = SDL_ReadU16LE(rw, &LE16test);
SDLTest_AssertPass("Call to SDL_ReadU16LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE16test == LE16value, "Validate object read from SDL_ReadU16LE, expected: %hu, got: %hu", LE16value, LE16test);
bresult = SDL_ReadU32LE(rw, &LE32test);
SDLTest_AssertPass("Call to SDL_ReadU32LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE32test == LE32value, "Validate object read from SDL_ReadU32LE, expected: %" SDL_PRIu32 ", got: %" SDL_PRIu32, LE32value, LE32test);
bresult = SDL_ReadU64LE(rw, &LE64test);
SDLTest_AssertPass("Call to SDL_ReadU64LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE64test == LE64value, "Validate object read from SDL_ReadU64LE, expected: %" SDL_PRIu64 ", got: %" SDL_PRIu64, LE64value, LE64test);
/* Close handle */
cresult = SDL_CloseIO(rw);
SDLTest_AssertPass("Call to SDL_CloseIO() succeeded");
SDLTest_AssertCheck(cresult == 0, "Verify result value is 0; got: %d", cresult);
}
return TEST_COMPLETED;
}
/* ================= Test References ================== */
/* IOStream test cases */
static const SDLTest_TestCaseReference iostrmTest1 = {
(SDLTest_TestCaseFp)iostrm_testParamNegative, "iostrm_testParamNegative", "Negative test for SDL_IOFromFile parameters", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest2 = {
(SDLTest_TestCaseFp)iostrm_testMem, "iostrm_testMem", "Tests opening from memory", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest3 = {
(SDLTest_TestCaseFp)iostrm_testConstMem, "iostrm_testConstMem", "Tests opening from (const) memory", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest4 = {
(SDLTest_TestCaseFp)iostrm_testDynamicMem, "iostrm_testDynamicMem", "Tests opening dynamic memory", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest5 = {
(SDLTest_TestCaseFp)iostrm_testFileRead, "iostrm_testFileRead", "Tests reading from a file", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest6 = {
(SDLTest_TestCaseFp)iostrm_testFileWrite, "iostrm_testFileWrite", "Test writing to a file", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest7 = {
(SDLTest_TestCaseFp)iostrm_testAllocFree, "iostrm_testAllocFree", "Test alloc and free of RW context", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest8 = {
(SDLTest_TestCaseFp)iostrm_testFileWriteReadEndian, "iostrm_testFileWriteReadEndian", "Test writing and reading via the Endian aware functions", TEST_ENABLED
};
static const SDLTest_TestCaseReference iostrmTest9 = {
(SDLTest_TestCaseFp)iostrm_testCompareRWFromMemWithRWFromFile, "iostrm_testCompareRWFromMemWithRWFromFile", "Compare RWFromMem and RWFromFile IOStream for read and seek", TEST_ENABLED
};
/* Sequence of IOStream test cases */
static const SDLTest_TestCaseReference *iostrmTests[] = {
&iostrmTest1, &iostrmTest2, &iostrmTest3, &iostrmTest4, &iostrmTest5, &iostrmTest6,
&iostrmTest7, &iostrmTest8, &iostrmTest9, NULL
};
/* IOStream test suite (global) */
SDLTest_TestSuiteReference iostrmTestSuite = {
"IOStream",
IOStreamSetUp,
iostrmTests,
IOStreamTearDown
};

View File

@ -50,6 +50,7 @@ static int TestVirtualJoystick(void *arg)
SDLTest_AssertCheck(SDL_GetJoystickSerial(joystick) == NULL, "SDL_GetJoystickSerial()");
SDLTest_AssertCheck(SDL_GetJoystickType(joystick) == desc.type, "SDL_GetJoystickType()");
SDLTest_AssertCheck(SDL_GetNumJoystickAxes(joystick) == desc.naxes, "SDL_GetNumJoystickAxes()");
SDLTest_AssertCheck(SDL_GetNumJoystickBalls(joystick) == 0, "SDL_GetNumJoystickBalls()");
SDLTest_AssertCheck(SDL_GetNumJoystickHats(joystick) == desc.nhats, "SDL_GetNumJoystickHats()");
SDLTest_AssertCheck(SDL_GetNumJoystickButtons(joystick) == desc.nbuttons, "SDL_GetNumJoystickButtons()");

View File

@ -0,0 +1,209 @@
/**
* Log test suite
*/
#include <SDL3/SDL.h>
#include <SDL3/SDL_test.h>
#include "testautomation_suites.h"
static SDL_LogOutputFunction original_function;
static void *original_userdata;
static void SDLCALL TestLogOutput(void *userdata, int category, SDL_LogPriority priority, const char *message)
{
int *message_count = (int *)userdata;
++(*message_count);
}
static void EnableTestLog(int *message_count)
{
*message_count = 0;
SDL_GetLogOutputFunction(&original_function, &original_userdata);
SDL_SetLogOutputFunction(TestLogOutput, message_count);
}
static void DisableTestLog()
{
SDL_SetLogOutputFunction(original_function, original_userdata);
}
/* Fixture */
/* Test case functions */
/**
* Check SDL_HINT_LOGGING functionality
*/
static int log_testHint(void *arg)
{
int count;
SDL_SetHint(SDL_HINT_LOGGING, NULL);
SDLTest_AssertPass("SDL_SetHint(SDL_HINT_LOGGING, NULL)");
{
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
}
SDL_SetHint(SDL_HINT_LOGGING, "debug");
SDLTest_AssertPass("SDL_SetHint(SDL_HINT_LOGGING, \"debug\")");
{
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_VERBOSE, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_VERBOSE, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
}
SDL_SetHint(SDL_HINT_LOGGING, "system=debug");
SDLTest_AssertPass("SDL_SetHint(SDL_HINT_LOGGING, \"system=debug\")");
{
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
}
SDL_SetHint(SDL_HINT_LOGGING, "app=warn,system=debug,assert=quiet,*=info");
SDLTest_AssertPass("SDL_SetHint(SDL_HINT_LOGGING, \"app=warn,system=debug,assert=quiet,*=info\")");
{
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_WARN, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_WARN, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_ASSERT, SDL_LOG_PRIORITY_CRITICAL, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_ASSERT, SDL_LOG_PRIORITY_CRITICAL, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_INFO, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_INFO, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
}
SDL_SetHint(SDL_HINT_LOGGING, "0=4,3=2,2=0,*=3");
SDLTest_AssertPass("SDL_SetHint(SDL_HINT_LOGGING, \"0=4,3=2,2=0,*=3\")");
{
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_WARN, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_WARN, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_ASSERT, SDL_LOG_PRIORITY_CRITICAL, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_ASSERT, SDL_LOG_PRIORITY_CRITICAL, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_INFO, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_INFO, \"test\")");
SDLTest_AssertCheck(count == 1, "Check result value, expected: 1, got: %d", count);
EnableTestLog(&count);
SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_DEBUG, "test");
DisableTestLog();
SDLTest_AssertPass("SDL_LogMessage(SDL_LOG_CATEGORY_CUSTOM, SDL_LOG_PRIORITY_DEBUG, \"test\")");
SDLTest_AssertCheck(count == 0, "Check result value, expected: 0, got: %d", count);
}
return TEST_COMPLETED;
}
/* ================= Test References ================== */
/* Log test cases */
static const SDLTest_TestCaseReference logTestHint = {
(SDLTest_TestCaseFp)log_testHint, "log_testHint", "Check SDL_HINT_LOGGING functionality", TEST_ENABLED
};
/* Sequence of Log test cases */
static const SDLTest_TestCaseReference *logTests[] = {
&logTestHint, NULL
};
/* Timer test suite (global) */
SDLTest_TestSuiteReference logTestSuite = {
"Log",
NULL,
logTests,
NULL
};

View File

@ -25,7 +25,7 @@
#define EULER M_E
#endif
#define IS_INFINITY(V) fpclassify(V) == FP_INFINITE
#define IS_INFINITY(V) isinf(V)
/* Square root of 3 (used in atan2) */
#define SQRT3 1.7320508075688771931766041234368458390235900878906250
@ -77,7 +77,7 @@ helper_dtod(const char *func_name, d_to_d_func func,
Uint32 i;
for (i = 0; i < cases_size; i++) {
const double result = func(cases[i].input);
SDLTest_AssertCheck((result - cases[i].expected) < FLT_EPSILON,
SDLTest_AssertCheck(SDL_fabs(result - cases[i].expected) < FLT_EPSILON,
"%s(%f), expected %f, got %f",
func_name,
cases[i].input,
@ -103,13 +103,19 @@ helper_dtod_inexact(const char *func_name, d_to_d_func func,
Uint32 i;
for (i = 0; i < cases_size; i++) {
const double result = func(cases[i].input);
SDLTest_AssertCheck(result >= cases[i].expected - EPSILON &&
result <= cases[i].expected + EPSILON,
"%s(%f), expected [%f,%f], got %f",
double diff = result - cases[i].expected;
double max_err = (cases[i].expected + 1.) * EPSILON;
if (diff < 0) {
diff = -diff;
}
if (max_err < 0) {
max_err = -max_err;
}
SDLTest_AssertCheck(diff <= max_err,
"%s(%f), expected %f +/- %g, got %f",
func_name,
cases[i].input,
cases[i].expected - EPSILON,
cases[i].expected + EPSILON,
cases[i].expected, max_err,
result);
}
@ -158,13 +164,20 @@ helper_ddtod_inexact(const char *func_name, dd_to_d_func func,
Uint32 i;
for (i = 0; i < cases_size; i++) {
const double result = func(cases[i].x_input, cases[i].y_input);
SDLTest_AssertCheck(result >= cases[i].expected - EPSILON &&
result <= cases[i].expected + EPSILON,
"%s(%f,%f), expected [%f,%f], got %f",
double diff = result - cases[i].expected;
double max_err = (cases[i].expected + 1.) * EPSILON;
if (diff < 0) {
diff = -diff;
}
if (max_err < 0) {
max_err = -max_err;
}
SDLTest_AssertCheck(diff <= max_err,
"%s(%f,%f), expected %f +/- %g, got %f",
func_name,
cases[i].x_input, cases[i].y_input,
cases[i].expected - EPSILON,
cases[i].expected + EPSILON,
cases[i].expected, max_err,
result);
}
@ -1092,7 +1105,7 @@ exp_regularCases(void *args)
{ 112.89, 10653788283588960962604279261058893737879589093376.0 },
{ 539.483, 1970107755334319939701129934673541628417235942656909222826926175622435588279443011110464355295725187195188154768877850257012251677751742837992843520967922303961718983154427294786640886286983037548604937796221048661733679844353544028160.0 },
};
return helper_dtod("Exp", SDL_exp, regular_cases, SDL_arraysize(regular_cases));
return helper_dtod_inexact("Exp", SDL_exp, regular_cases, SDL_arraysize(regular_cases));
}
/* SDL_log tests functions */
@ -1139,7 +1152,7 @@ log_baseCases(void *args)
1.0, 0.0, result);
result = SDL_log(EULER);
SDLTest_AssertCheck((result - 1.) < FLT_EPSILON,
SDLTest_AssertCheck(SDL_fabs(result - 1.) < FLT_EPSILON,
"Log(%f), expected %f, got %f",
EULER, 1.0, result);
@ -1665,14 +1678,16 @@ static int
pow_regularCases(void *args)
{
const dd_to_d regular_cases[] = {
#if 0 /* These tests fail when using the Mingw C runtime, we'll disable them for now */
{ -391.25, -2.0, 0.00000653267870448815438463212659780943170062528224661946296691894531250 },
{ -72.3, 12.0, 20401381050275984310272.0 },
#endif
{ -5.0, 3.0, -125.0 },
{ 3.0, 2.5, 15.58845726811989607085706666111946105957031250 },
{ 39.23, -1.5, 0.0040697950366865498147972424192175822099670767784118652343750 },
{ 478.972, 12.125, 315326359630449587856007411793920.0 }
};
return helper_ddtod("Pow", SDL_pow, regular_cases, SDL_arraysize(regular_cases));
return helper_ddtod_inexact("Pow", SDL_pow, regular_cases, SDL_arraysize(regular_cases));
}
/**
@ -2000,24 +2015,24 @@ static int
cos_precisionTest(void *args)
{
const d_to_d precision_cases[] = {
{ SDL_PI_D * 1.0 / 10.0, 0.9510565162 },
{ SDL_PI_D * 2.0 / 10.0, 0.8090169943 },
{ SDL_PI_D * 3.0 / 10.0, 0.5877852522 },
{ SDL_PI_D * 4.0 / 10.0, 0.3090169943 },
{ SDL_PI_D * 1.0 / 10.0, 0.9510565162951535 },
{ SDL_PI_D * 2.0 / 10.0, 0.8090169943749475 },
{ SDL_PI_D * 3.0 / 10.0, 0.5877852522924731 },
{ SDL_PI_D * 4.0 / 10.0, 0.30901699437494745 },
{ SDL_PI_D * 5.0 / 10.0, 0.0 },
{ SDL_PI_D * 6.0 / 10.0, -0.3090169943 },
{ SDL_PI_D * 7.0 / 10.0, -0.5877852522 },
{ SDL_PI_D * 8.0 / 10.0, -0.8090169943 },
{ SDL_PI_D * 9.0 / 10.0, -0.9510565162 },
{ SDL_PI_D * -1.0 / 10.0, 0.9510565162 },
{ SDL_PI_D * -2.0 / 10.0, 0.8090169943 },
{ SDL_PI_D * -3.0 / 10.0, 0.5877852522 },
{ SDL_PI_D * -4.0 / 10.0, 0.3090169943 },
{ SDL_PI_D * 6.0 / 10.0, -0.30901699437494734 },
{ SDL_PI_D * 7.0 / 10.0, -0.587785252292473 },
{ SDL_PI_D * 8.0 / 10.0, -0.8090169943749473 },
{ SDL_PI_D * 9.0 / 10.0, -0.9510565162951535 },
{ SDL_PI_D * -1.0 / 10.0, 0.9510565162951535 },
{ SDL_PI_D * -2.0 / 10.0, 0.8090169943749475 },
{ SDL_PI_D * -3.0 / 10.0, 0.5877852522924731 },
{ SDL_PI_D * -4.0 / 10.0, 0.30901699437494745 },
{ SDL_PI_D * -5.0 / 10.0, 0.0 },
{ SDL_PI_D * -6.0 / 10.0, -0.3090169943 },
{ SDL_PI_D * -7.0 / 10.0, -0.5877852522 },
{ SDL_PI_D * -8.0 / 10.0, -0.8090169943 },
{ SDL_PI_D * -9.0 / 10.0, -0.9510565162 }
{ SDL_PI_D * -6.0 / 10.0, -0.30901699437494734 },
{ SDL_PI_D * -7.0 / 10.0, -0.587785252292473 },
{ SDL_PI_D * -8.0 / 10.0, -0.8090169943749473 },
{ SDL_PI_D * -9.0 / 10.0, -0.9510565162951535 }
};
return helper_dtod_inexact("Cos", SDL_cos, precision_cases, SDL_arraysize(precision_cases));
}
@ -2118,23 +2133,23 @@ static int
sin_precisionTest(void *args)
{
const d_to_d precision_cases[] = {
{ SDL_PI_D * 1.0 / 10.0, 0.3090169943 },
{ SDL_PI_D * 2.0 / 10.0, 0.5877852522 },
{ SDL_PI_D * 3.0 / 10.0, 0.8090169943 },
{ SDL_PI_D * 4.0 / 10.0, 0.9510565162 },
{ SDL_PI_D * 6.0 / 10.0, 0.9510565162 },
{ SDL_PI_D * 7.0 / 10.0, 0.8090169943 },
{ SDL_PI_D * 8.0 / 10.0, 0.5877852522 },
{ SDL_PI_D * 9.0 / 10.0, 0.3090169943 },
{ SDL_PI_D * 1.0 / 10.0, 0.3090169943749474 },
{ SDL_PI_D * 2.0 / 10.0, 0.5877852522924731 },
{ SDL_PI_D * 3.0 / 10.0, 0.8090169943749475 },
{ SDL_PI_D * 4.0 / 10.0, 0.9510565162951535 },
{ SDL_PI_D * 6.0 / 10.0, 0.9510565162951536 },
{ SDL_PI_D * 7.0 / 10.0, 0.8090169943749475 },
{ SDL_PI_D * 8.0 / 10.0, 0.5877852522924732 },
{ SDL_PI_D * 9.0 / 10.0, 0.3090169943749475 },
{ SDL_PI_D, 0.0 },
{ SDL_PI_D * -1.0 / 10.0, -0.3090169943 },
{ SDL_PI_D * -2.0 / 10.0, -0.5877852522 },
{ SDL_PI_D * -3.0 / 10.0, -0.8090169943 },
{ SDL_PI_D * -4.0 / 10.0, -0.9510565162 },
{ SDL_PI_D * -6.0 / 10.0, -0.9510565162 },
{ SDL_PI_D * -7.0 / 10.0, -0.8090169943 },
{ SDL_PI_D * -8.0 / 10.0, -0.5877852522 },
{ SDL_PI_D * -9.0 / 10.0, -0.3090169943 },
{ SDL_PI_D * -1.0 / 10.0, -0.3090169943749474 },
{ SDL_PI_D * -2.0 / 10.0, -0.5877852522924731 },
{ SDL_PI_D * -3.0 / 10.0, -0.8090169943749475 },
{ SDL_PI_D * -4.0 / 10.0, -0.9510565162951535 },
{ SDL_PI_D * -6.0 / 10.0, -0.9510565162951536 },
{ SDL_PI_D * -7.0 / 10.0, -0.8090169943749475 },
{ SDL_PI_D * -8.0 / 10.0, -0.5877852522924732 },
{ SDL_PI_D * -9.0 / 10.0, -0.3090169943749475 },
{ -SDL_PI_D, 0.0 },
};
return helper_dtod_inexact("Sin", SDL_sin, precision_cases, SDL_arraysize(precision_cases));
@ -2234,26 +2249,26 @@ static int
tan_precisionTest(void *args)
{
const d_to_d precision_cases[] = {
{ SDL_PI_D * 1.0 / 11.0, 0.2936264929 },
{ SDL_PI_D * 2.0 / 11.0, 0.6426609771 },
{ SDL_PI_D * 3.0 / 11.0, 1.1540615205 },
{ SDL_PI_D * 4.0 / 11.0, 2.1896945629 },
{ SDL_PI_D * 5.0 / 11.0, 6.9551527717 },
{ SDL_PI_D * 6.0 / 11.0, -6.9551527717 },
{ SDL_PI_D * 7.0 / 11.0, -2.1896945629 },
{ SDL_PI_D * 8.0 / 11.0, -1.1540615205 },
{ SDL_PI_D * 9.0 / 11.0, -0.6426609771 },
{ SDL_PI_D * 10.0 / 11.0, -0.2936264929 },
{ SDL_PI_D * -1.0 / 11.0, -0.2936264929 },
{ SDL_PI_D * -2.0 / 11.0, -0.6426609771 },
{ SDL_PI_D * -3.0 / 11.0, -1.1540615205 },
{ SDL_PI_D * -4.0 / 11.0, -2.1896945629 },
{ SDL_PI_D * -5.0 / 11.0, -6.9551527717 },
{ SDL_PI_D * -6.0 / 11.0, 6.9551527717 },
{ SDL_PI_D * -7.0 / 11.0, 2.1896945629 },
{ SDL_PI_D * -8.0 / 11.0, 1.1540615205 },
{ SDL_PI_D * -9.0 / 11.0, 0.6426609771 },
{ SDL_PI_D * -10.0 / 11.0, 0.2936264929 }
{ SDL_PI_D * 1.0 / 11.0, 0.29362649293836673 },
{ SDL_PI_D * 2.0 / 11.0, 0.642660977168331 },
{ SDL_PI_D * 3.0 / 11.0, 1.1540615205330094 },
{ SDL_PI_D * 4.0 / 11.0, 2.189694562989681 },
{ SDL_PI_D * 5.0 / 11.0, 6.9551527717734745 },
{ SDL_PI_D * 6.0 / 11.0, -6.955152771773481 },
{ SDL_PI_D * 7.0 / 11.0, -2.189694562989682 },
{ SDL_PI_D * 8.0 / 11.0, -1.1540615205330096 },
{ SDL_PI_D * 9.0 / 11.0, -0.6426609771683314 },
{ SDL_PI_D * 10.0 / 11.0, -0.2936264929383667 },
{ SDL_PI_D * -1.0 / 11.0, -0.29362649293836673 },
{ SDL_PI_D * -2.0 / 11.0, -0.642660977168331 },
{ SDL_PI_D * -3.0 / 11.0, -1.1540615205330094 },
{ SDL_PI_D * -4.0 / 11.0, -2.189694562989681 },
{ SDL_PI_D * -5.0 / 11.0, -6.9551527717734745 },
{ SDL_PI_D * -6.0 / 11.0, 6.955152771773481 },
{ SDL_PI_D * -7.0 / 11.0, 2.189694562989682 },
{ SDL_PI_D * -8.0 / 11.0, 1.1540615205330096 },
{ SDL_PI_D * -9.0 / 11.0, 0.6426609771683314 },
{ SDL_PI_D * -10.0 / 11.0, 0.2936264929383667 }
};
return helper_dtod_inexact("Tan", SDL_tan, precision_cases, SDL_arraysize(precision_cases));
}
@ -2418,26 +2433,26 @@ static int
asin_precisionTest(void *args)
{
const d_to_d precision_cases[] = {
{ 0.9, 1.1197695149 },
{ 0.8, 0.9272952180 },
{ 0.7, 0.7753974966 },
{ 0.6, 0.6435011087 },
{ 0.5, 0.5235987755 },
{ 0.4, 0.4115168460 },
{ 0.3, 0.3046926540 },
{ 0.2, 0.2013579207 },
{ 0.1, 0.1001674211 },
{ 0.9, 1.1197695149986342 },
{ 0.8, 0.9272952180016123 },
{ 0.7, 0.775397496610753 },
{ 0.6, 0.6435011087932844 },
{ 0.5, 0.5235987755982989 },
{ 0.4, 0.41151684606748806 },
{ 0.3, 0.3046926540153976 },
{ 0.2, 0.20135792079033074 },
{ 0.1, 0.10016742116155977 },
{ 0.0, 0.0 },
{ -0.0, -0.0 },
{ -0.1, -0.1001674211 },
{ -0.2, -0.2013579207 },
{ -0.3, -0.3046926540 },
{ -0.4, -0.4115168460 },
{ -0.5, -0.5235987755 },
{ -0.6, -0.6435011087 },
{ -0.7, -0.7753974966 },
{ -0.8, -0.9272952180 },
{ -0.9, -1.1197695149 }
{ -0.1, -0.10016742116155977 },
{ -0.2, -0.20135792079033074 },
{ -0.3, -0.3046926540153976 },
{ -0.4, -0.41151684606748806 },
{ -0.5, -0.5235987755982989 },
{ -0.6, -0.6435011087932844 },
{ -0.7, -0.775397496610753 },
{ -0.8, -0.9272952180016123 },
{ -0.9, -1.1197695149986342 }
};
return helper_dtod_inexact("Asin", SDL_asin, precision_cases, SDL_arraysize(precision_cases));
}
@ -2512,24 +2527,24 @@ static int
atan_precisionTest(void *args)
{
const d_to_d precision_cases[] = {
{ 6.313751514675041, 1.4137166941 },
{ 3.0776835371752527, 1.2566370614 },
{ 1.9626105055051504, 1.0995574287 },
{ 1.3763819204711734, 0.9424777960 },
{ 1.0, 0.7853981633 },
{ 0.7265425280053609, 0.6283185307 },
{ 0.5095254494944288, 0.4712388980 },
{ 0.3249196962329063, 0.3141592653 },
{ 0.15838444032453627, 0.1570796326 },
{ -0.15838444032453627, -0.1570796326 },
{ -0.3249196962329063, -0.3141592653 },
{ -0.5095254494944288, -0.4712388980 },
{ -0.7265425280053609, -0.6283185307 },
{ -1.0, -0.7853981633 },
{ -1.3763819204711734, -0.9424777960 },
{ -1.9626105055051504, -1.0995574287 },
{ -3.0776835371752527, -1.2566370614 },
{ -6.313751514675041, -1.4137166941 },
{ 6.313751514675041, 1.413716694115407 },
{ 3.0776835371752527, 1.2566370614359172 },
{ 1.9626105055051504, 1.0995574287564276 },
{ 1.3763819204711734, 0.9424777960769379 },
{ 1.0, 0.7853981633974483 },
{ 0.7265425280053609, 0.6283185307179586 },
{ 0.5095254494944288, 0.47123889803846897 },
{ 0.3249196962329063, 0.3141592653589793 },
{ 0.15838444032453627, 0.15707963267948966 },
{ -0.15838444032453627, -0.15707963267948966 },
{ -0.3249196962329063, -0.3141592653589793 },
{ -0.5095254494944288, -0.47123889803846897 },
{ -0.7265425280053609, -0.6283185307179586 },
{ -1.0, -0.7853981633974483 },
{ -1.3763819204711734, -0.9424777960769379 },
{ -1.9626105055051504, -1.0995574287564276 },
{ -3.0776835371752527, -1.2566370614359172 },
{ -6.313751514675041, -1.413716694115407 },
};
return helper_dtod_inexact("Atan", SDL_atan, precision_cases, SDL_arraysize(precision_cases));
}

View File

@ -19,6 +19,7 @@
3. This notice may not be removed or altered from any source distribution.
*/
#ifndef NO_BUILD_CONFIG
#include <stddef.h>
/**
@ -71,10 +72,10 @@
#define SDL_SetMouseFocus SDL_Mock_SetMouseFocus
/* Mock mouse API */
static int SDL_SendMouseMotion(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, int relative, float x, float y);
static int SDL_SendMouseMotion(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, SDL_bool relative, float x, float y);
static int SDL_SendMouseButton(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, Uint8 state, Uint8 button);
static SDL_Mouse *SDL_GetMouse(void);
static SDL_bool SDL_MousePositionInWindow(SDL_Window *window, SDL_MouseID mouseID, float x, float y);
static SDL_bool SDL_MousePositionInWindow(SDL_Window *window, float x, float y);
static void SDL_SetMouseFocus(SDL_Window *window);
/* Import SUT code with macro-renamed function names */
@ -87,7 +88,7 @@ static void SDL_SetMouseFocus(SDL_Window *window);
/* Mock implementations of Pen -> Mouse calls */
/* Not thread-safe! */
static SDL_bool SDL_MousePositionInWindow(SDL_Window *window, SDL_MouseID mouseID, float x, float y)
static SDL_bool SDL_MousePositionInWindow(SDL_Window *window, float x, float y)
{
return SDL_TRUE;
}
@ -97,7 +98,7 @@ static float _mouseemu_last_x = 0.0f;
static float _mouseemu_last_y = 0.0f;
static int _mouseemu_last_mouseid = 0;
static int _mouseemu_last_button = 0;
static int _mouseemu_last_relative = 0;
static SDL_bool _mouseemu_last_relative = SDL_FALSE;
static int _mouseemu_last_focus = -1;
static int SDL_SendMouseButton(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, Uint8 state, Uint8 button)
@ -110,7 +111,7 @@ static int SDL_SendMouseButton(Uint64 timestamp, SDL_Window *window, SDL_MouseID
return 1;
}
static int SDL_SendMouseMotion(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, int relative, float x, float y)
static int SDL_SendMouseMotion(Uint64 timestamp, SDL_Window *window, SDL_MouseID mouseID, SDL_bool relative, float x, float y)
{
if (mouseID == SDL_PEN_MOUSEID) {
_mouseemu_last_event = SDL_EVENT_MOUSE_MOTION;
@ -126,9 +127,6 @@ static SDL_Mouse *SDL_GetMouse(void)
{
static SDL_Mouse dummy_mouse;
dummy_mouse.focus = NULL;
dummy_mouse.mouseID = 0;
return &dummy_mouse;
}
@ -255,7 +253,7 @@ static void _pen_trackGCSweep(pen_testdata *tracker)
/* Finds a number of unused pen IDs (does not allocate them). Also initialises GUIDs. */
static void _pen_unusedIDs(pen_testdata *tracker, int count)
{
static int guidmod = 0; /* Ensure uniqueness as long as we use no more than 256 test pens */
static Uint8 guidmod = 0; /* Ensure uniqueness as long as we use no more than 256 test pens */
Uint32 synthetic_penid = 1000u;
int index = 0;
@ -270,7 +268,7 @@ static void _pen_unusedIDs(pen_testdata *tracker, int count)
}
tracker->ids[index] = synthetic_penid;
for (k = 0; k < 15; ++k) {
tracker->guids[index].data[k] = (16 * k) + index;
tracker->guids[index].data[k] = (Uint8)((16 * k) + index);
}
tracker->guids[index].data[15] = ++guidmod;
@ -454,7 +452,7 @@ static simulated_pen_action _simpen_event(int type, int pen_index, int index, fl
/* Sanity check-- turned out to be necessary */
if ((type == SIMPEN_ACTION_PRESS || type == SIMPEN_ACTION_RELEASE) && index == 0) {
SDL_Log("Error: SIMPEN_EVENT_BUTTON must have button > 0 (first button has number 1!), in line %d!", line_nr);
SDL_Log("Error: SIMPEN_EVENT_BUTTON must have button > 0 (first button has number 1!), in line %d!", line_nr);
exit(1);
}
return action;
@ -480,7 +478,7 @@ static simulated_pen_action _simpen_event(int type, int pen_index, int index, fl
#define SIMPEN_EVENT_BUTTON(pen_index, push, button) \
STEP _simpen_event((push) ? SIMPEN_ACTION_PRESS : SIMPEN_ACTION_RELEASE, (pen_index), (button), 0.0f, __LINE__)
#define SIMPEN_EVENT_TIP(pen_index, touch, tip) \
#define SIMPEN_EVENT_TIP(pen_index, touch, tip) \
STEP _simpen_event((touch) ? SIMPEN_ACTION_DOWN : SIMPEN_ACTION_UP, (pen_index), tip, 0.0f, __LINE__)
#define SIMPEN_SET_ERASER(pen_index, eraser_mode) \
@ -573,7 +571,7 @@ _pen_simulate(simulated_pen_action *steps, int *step_counter, SDL_Pen *simulated
case SIMPEN_ACTION_PRESS:
mask = (1 << (step.index - 1));
simpen->last.buttons |= mask;
SDLTest_AssertCheck(SDL_SendPenButton(0, simpen->header.id, SDL_PRESSED, step.index),
SDLTest_AssertCheck(SDL_SendPenButton(0, simpen->header.id, SDL_PRESSED, (Uint8)step.index),
"SIMPEN_ACTION_PRESS [pen %d]: button %d (mask %x)", step.pen_index, step.index, mask);
done = SDL_TRUE;
break;
@ -581,7 +579,7 @@ _pen_simulate(simulated_pen_action *steps, int *step_counter, SDL_Pen *simulated
case SIMPEN_ACTION_RELEASE:
mask = ~(1 << (step.index - 1));
simpen->last.buttons &= mask;
SDLTest_AssertCheck(SDL_SendPenButton(0, simpen->header.id, SDL_RELEASED, step.index),
SDLTest_AssertCheck(SDL_SendPenButton(0, simpen->header.id, SDL_RELEASED, (Uint8)step.index),
"SIMPEN_ACTION_RELEASE [pen %d]: button %d (mask %x)", step.pen_index, step.index, mask);
done = SDL_TRUE;
break;
@ -601,22 +599,22 @@ _pen_simulate(simulated_pen_action *steps, int *step_counter, SDL_Pen *simulated
break;
case SIMPEN_ACTION_ERASER_MODE: {
Uint32 pmask;
SDL_Pen *pen = SDL_PenModifyBegin(simpen->header.id);
Uint32 pmask;
SDL_Pen *pen = SDL_PenModifyBegin(simpen->header.id);
if (step.index) {
pmask = SDL_PEN_ERASER_MASK;
} else {
pmask = SDL_PEN_INK_MASK;
}
if (step.index) {
pmask = SDL_PEN_ERASER_MASK;
} else {
pmask = SDL_PEN_INK_MASK;
}
SDL_PenModifyAddCapabilities(pen, pmask);
SDL_PenModifyEnd(pen, SDL_TRUE);
SDL_PenModifyAddCapabilities(pen, pmask);
SDL_PenModifyEnd(pen, SDL_TRUE);
simpen->header.flags &= ~(SDL_PEN_INK_MASK | SDL_PEN_ERASER_MASK);
simpen->header.flags |= pmask;
break;
}
simpen->header.flags &= ~(SDL_PEN_INK_MASK | SDL_PEN_ERASER_MASK);
simpen->header.flags |= pmask;
break;
}
default:
SDLTest_AssertCheck(0,
@ -1046,40 +1044,40 @@ pen_buttonReporting(void *arg)
for (pen_nr = 0; pen_nr < 2; ++pen_nr) {
float *expected_axes = axes + pen_nr;
SDL_bool found_event = SDL_FALSE;
SDL_bool found_event = SDL_FALSE;
Uint16 pen_state = 0x0000 | SDL_PEN_DOWN_MASK;
Uint8 tip = SDL_PEN_TIP_INK;
Uint8 tip = SDL_PEN_TIP_INK;
if (pen_nr == 1) {
pen_state |= SDL_PEN_ERASER_MASK;
tip = SDL_PEN_TIP_ERASER;
tip = SDL_PEN_TIP_ERASER;
}
SDL_SendPenTipEvent(0, ptest.ids[pen_nr], SDL_PRESSED);
SDL_SendPenTipEvent(0, ptest.ids[pen_nr], SDL_PRESSED);
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_DOWN) {
SDLTest_AssertCheck(event.ptip.which == ptest.ids[pen_nr],
"Received SDL_EVENT_PEN_DOWN from correct pen");
SDLTest_AssertCheck(event.ptip.tip == (pen_nr == 0)? SDL_PEN_TIP_INK : SDL_PEN_TIP_ERASER,
"Received SDL_EVENT_PEN_DOWN for correct tip");
SDLTest_AssertCheck(event.ptip.state == SDL_PRESSED,
"Received SDL_EVENT_PEN_DOWN but and marked SDL_PRESSED");
SDLTest_AssertCheck(event.ptip.tip == tip,
"Received tip %x but expected %x", event.ptip.tip, tip);
SDLTest_AssertCheck(event.ptip.pen_state == pen_state,
"Received SDL_EVENT_PEN_DOWN, and state %04x == %04x (expected)",
event.pbutton.pen_state, pen_state);
SDLTest_AssertCheck((event.ptip.x == expected_x[pen_nr]) && (event.ptip.y == expected_y[pen_nr]),
"Received SDL_EVENT_PEN_DOWN event at correct coordinates: (%f, %f) vs (%f, %f) (expected)",
event.pbutton.x, event.pbutton.y, expected_x[pen_nr], expected_y[pen_nr]);
SDLTest_AssertCheck(0 == SDL_memcmp(expected_axes, event.pbutton.axes, sizeof(float) * SDL_PEN_NUM_AXES),
"Received SDL_EVENT_PEN_DOWN event with correct axis values");
found_event = SDL_TRUE;
}
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_DOWN) {
SDLTest_AssertCheck(event.ptip.which == ptest.ids[pen_nr],
"Received SDL_EVENT_PEN_DOWN from correct pen");
SDLTest_AssertCheck(event.ptip.tip == (pen_nr == 0)? SDL_PEN_TIP_INK : SDL_PEN_TIP_ERASER,
"Received SDL_EVENT_PEN_DOWN for correct tip");
SDLTest_AssertCheck(event.ptip.state == SDL_PRESSED,
"Received SDL_EVENT_PEN_DOWN but and marked SDL_PRESSED");
SDLTest_AssertCheck(event.ptip.tip == tip,
"Received tip %x but expected %x", event.ptip.tip, tip);
SDLTest_AssertCheck(event.ptip.pen_state == pen_state,
"Received SDL_EVENT_PEN_DOWN, and state %04x == %04x (expected)",
event.pbutton.pen_state, pen_state);
SDLTest_AssertCheck((event.ptip.x == expected_x[pen_nr]) && (event.ptip.y == expected_y[pen_nr]),
"Received SDL_EVENT_PEN_DOWN event at correct coordinates: (%f, %f) vs (%f, %f) (expected)",
event.pbutton.x, event.pbutton.y, expected_x[pen_nr], expected_y[pen_nr]);
SDLTest_AssertCheck(0 == SDL_memcmp(expected_axes, event.pbutton.axes, sizeof(float) * SDL_PEN_NUM_AXES),
"Received SDL_EVENT_PEN_DOWN event with correct axis values");
found_event = SDL_TRUE;
}
SDLTest_AssertCheck(found_event,
"Received the expected SDL_EVENT_PEN_DOWN event");
}
}
}
SDLTest_AssertPass("Pen and eraser set up for button testing");
@ -1096,7 +1094,7 @@ pen_buttonReporting(void *arg)
SDL_bool found_event = SDL_FALSE;
pen_state |= (1 << (button_nr - 1));
SDL_SendPenButton(0, ptest.ids[pen_nr], SDL_PRESSED, button_nr);
SDL_SendPenButton(0, ptest.ids[pen_nr], SDL_PRESSED, (Uint8)button_nr);
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_BUTTON_DOWN) {
SDLTest_AssertCheck(event.pbutton.which == ptest.ids[pen_nr],
@ -1143,7 +1141,7 @@ pen_buttonReporting(void *arg)
SDL_bool found_event = SDL_FALSE;
pen_state &= ~(1 << (button_nr - 1));
SDL_SendPenButton(0, ptest.ids[pen_nr], SDL_RELEASED, button_nr);
SDL_SendPenButton(0, ptest.ids[pen_nr], SDL_RELEASED, (Uint8)button_nr);
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_BUTTON_UP) {
SDLTest_AssertCheck(event.pbutton.which == ptest.ids[pen_nr],
@ -1173,40 +1171,40 @@ pen_buttonReporting(void *arg)
for (pen_nr = 0; pen_nr < 2; ++pen_nr) {
float *expected_axes = axes + pen_nr;
SDL_bool found_event = SDL_FALSE;
SDL_bool found_event = SDL_FALSE;
Uint16 pen_state = 0x0000;
Uint8 tip = SDL_PEN_TIP_INK;
Uint8 tip = SDL_PEN_TIP_INK;
if (pen_nr == 1) {
pen_state |= SDL_PEN_ERASER_MASK;
tip = SDL_PEN_TIP_ERASER;
tip = SDL_PEN_TIP_ERASER;
}
SDL_SendPenTipEvent(0, ptest.ids[pen_nr], SDL_RELEASED);
SDL_SendPenTipEvent(0, ptest.ids[pen_nr], SDL_RELEASED);
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_UP) {
SDLTest_AssertCheck(event.ptip.which == ptest.ids[pen_nr],
"Received SDL_EVENT_PEN_UP from correct pen");
SDLTest_AssertCheck(event.ptip.tip == (pen_nr == 0)? SDL_PEN_TIP_INK : SDL_PEN_TIP_ERASER,
"Received SDL_EVENT_PEN_UP for correct tip");
SDLTest_AssertCheck(event.ptip.state == SDL_RELEASED,
"Received SDL_EVENT_PEN_UP but and marked SDL_RELEASED");
SDLTest_AssertCheck(event.ptip.tip == tip,
"Received tip %x but expected %x", event.ptip.tip, tip);
SDLTest_AssertCheck((event.ptip.pen_state & 0xff00) == (pen_state & 0xff00),
"Received SDL_EVENT_PEN_UP, and state %04x == %04x (expected)",
event.pbutton.pen_state, pen_state);
SDLTest_AssertCheck((event.ptip.x == expected_x[pen_nr]) && (event.ptip.y == expected_y[pen_nr]),
"Received SDL_EVENT_PEN_UP event at correct coordinates: (%f, %f) vs (%f, %f) (expected)",
event.pbutton.x, event.pbutton.y, expected_x[pen_nr], expected_y[pen_nr]);
SDLTest_AssertCheck(0 == SDL_memcmp(expected_axes, event.pbutton.axes, sizeof(float) * SDL_PEN_NUM_AXES),
"Received SDL_EVENT_PEN_UP event with correct axis values");
found_event = SDL_TRUE;
}
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_PEN_UP) {
SDLTest_AssertCheck(event.ptip.which == ptest.ids[pen_nr],
"Received SDL_EVENT_PEN_UP from correct pen");
SDLTest_AssertCheck(event.ptip.tip == (pen_nr == 0)? SDL_PEN_TIP_INK : SDL_PEN_TIP_ERASER,
"Received SDL_EVENT_PEN_UP for correct tip");
SDLTest_AssertCheck(event.ptip.state == SDL_RELEASED,
"Received SDL_EVENT_PEN_UP but and marked SDL_RELEASED");
SDLTest_AssertCheck(event.ptip.tip == tip,
"Received tip %x but expected %x", event.ptip.tip, tip);
SDLTest_AssertCheck((event.ptip.pen_state & 0xff00) == (pen_state & 0xff00),
"Received SDL_EVENT_PEN_UP, and state %04x == %04x (expected)",
event.pbutton.pen_state, pen_state);
SDLTest_AssertCheck((event.ptip.x == expected_x[pen_nr]) && (event.ptip.y == expected_y[pen_nr]),
"Received SDL_EVENT_PEN_UP event at correct coordinates: (%f, %f) vs (%f, %f) (expected)",
event.pbutton.x, event.pbutton.y, expected_x[pen_nr], expected_y[pen_nr]);
SDLTest_AssertCheck(0 == SDL_memcmp(expected_axes, event.pbutton.axes, sizeof(float) * SDL_PEN_NUM_AXES),
"Received SDL_EVENT_PEN_UP event with correct axis values");
found_event = SDL_TRUE;
}
SDLTest_AssertCheck(found_event,
"Received the expected SDL_EVENT_PEN_UP event");
}
}
}
/* Cleanup */
@ -1342,10 +1340,10 @@ pen_movementAndAxes(void *arg)
_pen_simulate_init(&ptest, simulated_pens, 2);
/* Simulate pen movements */
while ((last_action = _pen_simulate(steps, &sim_pc, &simulated_pens[0], 2))) {
while ((last_action = _pen_simulate(steps, &sim_pc, &simulated_pens[0], 2)) != 0) {
int attempts = 0;
SDL_Pen *simpen = &simulated_pens[last_action->pen_index];
SDL_PenID reported_which = -1;
SDL_PenID reported_which = 0;
float reported_x = -1.0f, reported_y = -1.0f;
float *reported_axes = NULL;
Uint32 reported_pen_state = 0;
@ -1360,8 +1358,8 @@ pen_movementAndAxes(void *arg)
return TEST_ABORTED;
}
} while (event.type != SDL_EVENT_PEN_DOWN
&& event.type != SDL_EVENT_PEN_UP
&& event.type != SDL_EVENT_PEN_MOTION
&& event.type != SDL_EVENT_PEN_UP
&& event.type != SDL_EVENT_PEN_MOTION
&& event.type != SDL_EVENT_PEN_BUTTON_UP
&& event.type != SDL_EVENT_PEN_BUTTON_DOWN); /* skip boring events */
@ -1383,7 +1381,7 @@ pen_movementAndAxes(void *arg)
case SIMPEN_ACTION_PRESS:
SDLTest_AssertCheck(event.type == SDL_EVENT_PEN_BUTTON_DOWN, "Expected PENBUTTONDOWN event (but got 0x%lx)", (unsigned long) event.type);
SDLTest_AssertCheck(event.pbutton.state == SDL_PRESSED, "Expected PRESSED button");
/* Fall through */
SDL_FALLTHROUGH;
case SIMPEN_ACTION_RELEASE:
if (last_action->type == SIMPEN_ACTION_RELEASE) {
SDLTest_AssertCheck(event.type == SDL_EVENT_PEN_BUTTON_UP, "Expected PENBUTTONUP event (but got 0x%lx)", (unsigned long) event.type);
@ -1401,7 +1399,7 @@ pen_movementAndAxes(void *arg)
case SIMPEN_ACTION_DOWN:
SDLTest_AssertCheck(event.type == SDL_EVENT_PEN_DOWN, "Expected PENBUTTONDOWN event (but got 0x%lx)", (unsigned long) event.type);
SDLTest_AssertCheck(event.ptip.state == SDL_PRESSED, "Expected PRESSED button");
/* Fall through */
SDL_FALLTHROUGH;
case SIMPEN_ACTION_UP:
if (last_action->type == SIMPEN_ACTION_UP) {
SDLTest_AssertCheck(event.type == SDL_EVENT_PEN_UP, "Expected PENBUTTONUP event (but got 0x%lx)", (unsigned long) event.type);
@ -1417,7 +1415,7 @@ pen_movementAndAxes(void *arg)
break;
case SIMPEN_ACTION_ERASER_MODE:
break;
break;
default:
SDLTest_AssertCheck(0, "Error in pen simulator: unexpected action %d", last_action->type);
@ -1728,7 +1726,7 @@ pen_mouseEmulation(void *arg)
_penmouse_expect_button(SDL_PRESSED, 1);
for (i = 1; i <= 3; ++i) {
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, (Uint8)i);
_penmouse_expect_button(SDL_PRESSED, i + 1);
}
SDLTest_AssertPass("Button press mouse emulation");
@ -1738,7 +1736,7 @@ pen_mouseEmulation(void *arg)
_penmouse_expect_button(SDL_RELEASED, 1);
for (i = 1; i <= 3; ++i) {
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, (Uint8)i);
_penmouse_expect_button(SDL_RELEASED, i + 1);
}
SDLTest_AssertPass("Button release mouse emulation");
@ -1800,10 +1798,10 @@ pen_mouseEmulationDelayed(void *arg)
/* Test button press reporting */
for (i = 1; i <= 2; ++i) {
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button press suppressed: %d", _mouseemu_last_event);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button release suppressed: %d", _mouseemu_last_event);
}
@ -1816,16 +1814,16 @@ pen_mouseEmulationDelayed(void *arg)
/* Test button press reporting, releasing extra button AFTER lifting pen */
for (i = 1; i <= 2; ++i) {
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button press suppressed (A.1): %d", _mouseemu_last_event);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_PRESSED);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_PRESSED);
_penmouse_expect_button(SDL_PRESSED, i + 1);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_RELEASED);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_RELEASED);
_penmouse_expect_button(SDL_RELEASED, i + 1);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button press suppressed (A.2): %d", _mouseemu_last_event);
}
@ -1833,16 +1831,16 @@ pen_mouseEmulationDelayed(void *arg)
/* Test button press reporting, releasing extra button BEFORE lifting pen */
for (i = 1; i <= 2; ++i) {
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_PRESSED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button press suppressed (B.1): %d", _mouseemu_last_event);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_PRESSED);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_PRESSED);
_penmouse_expect_button(SDL_PRESSED, i + 1);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, i);
SDL_SendPenButton(0, ptest.ids[0], SDL_RELEASED, (Uint8)i);
SDLTest_AssertCheck(0 == _mouseemu_last_event,
"Non-touching button press suppressed (B.2): %d", _mouseemu_last_event);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_RELEASED);
SDL_SendPenTipEvent(0, ptest.ids[0], SDL_RELEASED);
_penmouse_expect_button(SDL_RELEASED, i + 1);
}
SDLTest_AssertPass("Delayed button press mouse emulation, touching and then releasing button");
@ -1860,11 +1858,11 @@ pen_mouseEmulationDelayed(void *arg)
static int
pen_memoryLayout(void *arg)
{
#define LAYOUT_COMPATIBLE(field) \
#define LAYOUT_COMPATIBLE(field) \
SDLTest_AssertCheck(offsetof(SDL_PenTipEvent, field) == offsetof(SDL_PenMotionEvent, field), \
"Memory layout SDL_PenTipEvent and SDL_PenMotionEvent compatibility: '" #field "'"); \
"Memory layout SDL_PenTipEvent and SDL_PenMotionEvent compatibility: '" #field "'"); \
SDLTest_AssertCheck(offsetof(SDL_PenTipEvent, field) == offsetof(SDL_PenButtonEvent, field), \
"Memory layout SDL_PenTipEvent and SDL_PenBUttonEvent compatibility: '" #field "'");
"Memory layout SDL_PenTipEvent and SDL_PenBUttonEvent compatibility: '" #field "'");
LAYOUT_COMPATIBLE(which);
LAYOUT_COMPATIBLE(x);
@ -1874,9 +1872,21 @@ pen_memoryLayout(void *arg)
return TEST_COMPLETED;
}
/* ================= Test Setup and Teardown ================== */
static void
pen_test_setup(void *arg) {
SDL_PenInit();
}
static void
pen_test_teardown(void *arg) {
SDL_PenQuit();
}
/* ================= Test References ================== */
/* Mouse test cases */
/* Pen test cases */
static const SDLTest_TestCaseReference penTest1 = { (SDLTest_TestCaseFp)pen_iteration, "pen_iteration", "Iterate over all pens with SDL_PenIDForIndex", TEST_ENABLED };
static const SDLTest_TestCaseReference penTest2 = { (SDLTest_TestCaseFp)pen_hotplugging, "pen_hotplugging", "Hotplug pens and validate their status, including SDL_PenConnected", TEST_ENABLED };
@ -1895,11 +1905,29 @@ static const SDLTest_TestCaseReference penTest8 = { (SDLTest_TestCaseFp)pen_mous
static const SDLTest_TestCaseReference penTest9 = { (SDLTest_TestCaseFp)pen_memoryLayout, "pen_memoryLayout", "Check that all pen events have compatible layout (required by SDL_pen.c)", TEST_ENABLED };
/* Sequence of Mouse test cases */
/* Sequence of Pen test cases */
static const SDLTest_TestCaseReference *penTests[] = {
&penTest1, &penTest2, &penTest3, &penTest4, &penTest5, &penTest6, &penTest7, &penTest8, &penTest9, NULL
};
/* Pen test suite (global) */
SDLTest_TestSuiteReference penTestSuite = {
"Pen",
(SDLTest_TestCaseSetUpFp)pen_test_setup,
penTests,
(SDLTest_TestCaseTearDownFp)pen_test_teardown
};
#else
#include <SDL3/SDL_test.h>
#include "testautomation_suites.h"
/* Sequence of Mouse test cases */
static const SDLTest_TestCaseReference *penTests[] = {
NULL
};
/* Mouse test suite (global) */
SDLTest_TestSuiteReference penTestSuite = {
"Pen",
@ -1907,3 +1935,5 @@ SDLTest_TestSuiteReference penTestSuite = {
penTests,
NULL
};
#endif

View File

@ -8,7 +8,7 @@
/* Test case functions */
/* Definition of all RGB formats used to test pixel conversions */
static const Uint32 g_AllFormats[] = {
static const SDL_PixelFormatEnum g_AllFormats[] = {
SDL_PIXELFORMAT_INDEX1LSB,
SDL_PIXELFORMAT_INDEX1MSB,
SDL_PIXELFORMAT_INDEX2LSB,
@ -126,22 +126,26 @@ static int pixels_allocFreeFormat(void *arg)
const char *expectedError = "Unknown pixel format";
const char *error;
int i;
Uint32 format;
SDL_PixelFormatEnum format;
Uint32 masks;
SDL_PixelFormat *result;
/* Blank/unknown format */
format = 0;
SDLTest_Log("Pixel Format: %s (%" SDL_PRIu32 ")", unknownFormat, format);
format = SDL_PIXELFORMAT_UNKNOWN;
SDLTest_Log("Pixel Format: %s (%d)", unknownFormat, format);
/* Allocate format */
result = SDL_CreatePixelFormat(format);
SDLTest_AssertPass("Call to SDL_CreatePixelFormat()");
SDLTest_AssertCheck(result != NULL, "Verify result is not NULL");
if (result != NULL) {
SDLTest_AssertCheck(result->format == format, "Verify value of result.format; expected: %" SDL_PRIu32 ", got %" SDL_PRIu32, format, result->format);
SDLTest_AssertCheck(result->BitsPerPixel == 0, "Verify value of result.BitsPerPixel; expected: 0, got %u", result->BitsPerPixel);
SDLTest_AssertCheck(result->BytesPerPixel == 0, "Verify value of result.BytesPerPixel; expected: 0, got %u", result->BytesPerPixel);
SDLTest_AssertCheck(result->format == format, "Verify value of result.format; expected: %d, got %d", format, result->format);
SDLTest_AssertCheck(result->bits_per_pixel == 0,
"Verify value of result.bits_per_pixel; expected: 0, got %u",
result->bits_per_pixel);
SDLTest_AssertCheck(result->bytes_per_pixel == 0,
"Verify value of result.bytes_per_pixel; expected: 0, got %u",
result->bytes_per_pixel);
masks = result->Rmask | result->Gmask | result->Bmask | result->Amask;
SDLTest_AssertCheck(masks == 0, "Verify value of result.[RGBA]mask combined; expected: 0, got %" SDL_PRIu32, masks);
@ -153,17 +157,21 @@ static int pixels_allocFreeFormat(void *arg)
/* RGB formats */
for (i = 0; i < g_numAllFormats; i++) {
format = g_AllFormats[i];
SDLTest_Log("Pixel Format: %s (%" SDL_PRIu32 ")", g_AllFormatsVerbose[i], format);
SDLTest_Log("Pixel Format: %s (%d)", g_AllFormatsVerbose[i], format);
/* Allocate format */
result = SDL_CreatePixelFormat(format);
SDLTest_AssertPass("Call to SDL_CreatePixelFormat()");
SDLTest_AssertCheck(result != NULL, "Verify result is not NULL");
if (result != NULL) {
SDLTest_AssertCheck(result->format == format, "Verify value of result.format; expected: %" SDL_PRIu32 ", got %" SDL_PRIu32, format, result->format);
SDLTest_AssertCheck(result->format == format, "Verify value of result.format; expected: %d, got %d", format, result->format);
if (!SDL_ISPIXELFORMAT_FOURCC(format)) {
SDLTest_AssertCheck(result->BitsPerPixel > 0, "Verify value of result.BitsPerPixel; expected: >0, got %u", result->BitsPerPixel);
SDLTest_AssertCheck(result->BytesPerPixel > 0, "Verify value of result.BytesPerPixel; expected: >0, got %u", result->BytesPerPixel);
SDLTest_AssertCheck(result->bits_per_pixel > 0,
"Verify value of result.bits_per_pixel; expected: >0, got %u",
result->bits_per_pixel);
SDLTest_AssertCheck(result->bytes_per_pixel > 0,
"Verify value of result.bytes_per_pixel; expected: >0, got %u",
result->bytes_per_pixel);
if (!SDL_ISPIXELFORMAT_INDEXED(format)) {
masks = result->Rmask | result->Gmask | result->Bmask | result->Amask;
SDLTest_AssertCheck(masks > 0, "Verify value of result.[RGBA]mask combined; expected: >0, got %" SDL_PRIu32, masks);
@ -184,7 +192,7 @@ static int pixels_allocFreeFormat(void *arg)
SDLTest_AssertPass("Call to SDL_ClearError()");
format = g_invalidPixelFormats[i];
result = SDL_CreatePixelFormat(format);
SDLTest_AssertPass("Call to SDL_CreatePixelFormat(%" SDL_PRIu32 ")", format);
SDLTest_AssertPass("Call to SDL_CreatePixelFormat(%d)", format);
SDLTest_AssertCheck(result == NULL, "Verify result is NULL");
error = SDL_GetError();
SDLTest_AssertPass("Call to SDL_GetError()");
@ -217,12 +225,12 @@ static int pixels_getPixelFormatName(void *arg)
const char *unknownFormat = "SDL_PIXELFORMAT_UNKNOWN";
const char *error;
int i;
Uint32 format;
SDL_PixelFormatEnum format;
const char *result;
/* Blank/undefined format */
format = 0;
SDLTest_Log("RGB Format: %s (%" SDL_PRIu32 ")", unknownFormat, format);
format = SDL_PIXELFORMAT_UNKNOWN;
SDLTest_Log("RGB Format: %s (%d)", unknownFormat, format);
/* Get name of format */
result = SDL_GetPixelFormatName(format);
@ -237,7 +245,7 @@ static int pixels_getPixelFormatName(void *arg)
/* RGB formats */
for (i = 0; i < g_numAllFormats; i++) {
format = g_AllFormats[i];
SDLTest_Log("RGB Format: %s (%" SDL_PRIu32 ")", g_AllFormatsVerbose[i], format);
SDLTest_Log("RGB Format: %s (%d)", g_AllFormatsVerbose[i], format);
/* Get name of format */
result = SDL_GetPixelFormatName(format);
@ -258,7 +266,7 @@ static int pixels_getPixelFormatName(void *arg)
for (i = 0; i < g_numInvalidPixelFormats; i++) {
format = g_invalidPixelFormats[i];
result = SDL_GetPixelFormatName(format);
SDLTest_AssertPass("Call to SDL_GetPixelFormatName(%" SDL_PRIu32 ")", format);
SDLTest_AssertPass("Call to SDL_GetPixelFormatName(%d)", format);
SDLTest_AssertCheck(result != NULL, "Verify result is not NULL");
if (result != NULL) {
SDLTest_AssertCheck(result[0] != '\0',

View File

@ -209,7 +209,7 @@ static int platform_testHasFunctions(void *arg)
*/
static int platform_testGetVersion(void *arg)
{
SDL_version linked;
SDL_Version linked;
int major = SDL_MAJOR_VERSION;
int minor = SDL_MINOR_VERSION;
@ -231,7 +231,7 @@ static int platform_testGetVersion(void *arg)
*/
static int platform_testSDLVersion(void *arg)
{
SDL_version compiled;
SDL_Version compiled;
int major = SDL_MAJOR_VERSION;
int minor = SDL_MINOR_VERSION;
@ -256,12 +256,12 @@ static int platform_testDefaultInit(void *arg)
int ret;
int subsystem;
subsystem = SDL_WasInit(SDL_INIT_EVERYTHING);
subsystem = SDL_WasInit(0);
SDLTest_AssertCheck(subsystem != 0,
"SDL_WasInit(0): returned %i, expected != 0",
subsystem);
ret = SDL_Init(SDL_WasInit(SDL_INIT_EVERYTHING));
ret = SDL_Init(0);
SDLTest_AssertCheck(ret == 0,
"SDL_Init(0): returned %i, expected 0, error: %s",
ret,

View File

@ -38,7 +38,7 @@ static int properties_testBasic(void *arg)
props = SDL_CreateProperties();
SDLTest_AssertPass("Call to SDL_CreateProperties()");
SDLTest_AssertCheck(props != 0,
"Verify props were created, got: %" SDL_PRIu32 "", props);
"Verify props were created, got: %" SDL_PRIu32, props);
for (i = 0; i < 10; ++i) {
SDL_snprintf(key, SDL_arraysize(key), "%c", 'a' + i);
@ -84,7 +84,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected abcd, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 1234);
SDLTest_AssertCheck(value_number == 1234,
"Verify number property, expected 1234, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 1234, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 1234.0f);
SDLTest_AssertCheck(value_float == 1234.0f,
"Verify float property, expected 1234, got: %f", value_float);
@ -106,7 +106,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected NULL, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 0);
SDLTest_AssertCheck(value_number == 0,
"Verify number property, expected 0, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 0, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 0.0f);
SDLTest_AssertCheck(value_float == 0.0f,
"Verify float property, expected 0, got: %f", value_float);
@ -128,7 +128,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected bar, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 0);
SDLTest_AssertCheck(value_number == 0,
"Verify number property, expected 0, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 0, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 0.0f);
SDLTest_AssertCheck(value_float == 0.0f,
"Verify float property, expected 0, got: %f", value_float);
@ -150,7 +150,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected 1, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 0);
SDLTest_AssertCheck(value_number == 1,
"Verify number property, expected 1, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 1, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 0.0f);
SDLTest_AssertCheck(value_float == 1.0f,
"Verify float property, expected 1, got: %f", value_float);
@ -172,7 +172,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected 1.750000, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 0);
SDLTest_AssertCheck(value_number == 2,
"Verify number property, expected 2, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 2, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 0.0f);
SDLTest_AssertCheck(value_float == 1.75f,
"Verify float property, expected 1.75, got: %f", value_float);
@ -194,7 +194,7 @@ static int properties_testBasic(void *arg)
"Verify string property, expected true, got: %s", value_string);
value_number = SDL_GetNumberProperty(props, "foo", 0);
SDLTest_AssertCheck(value_number == 1,
"Verify number property, expected 1, got: %" SDL_PRIu64 "", value_number);
"Verify number property, expected 1, got: %" SDL_PRIu64, value_number);
value_float = SDL_GetFloatProperty(props, "foo", 0.0f);
SDLTest_AssertCheck(value_float == 1.0f,
"Verify float property, expected 1, got: %f", value_float);
@ -213,6 +213,67 @@ static int properties_testBasic(void *arg)
return TEST_COMPLETED;
}
/**
* Test copy functionality
*/
static void SDLCALL copy_cleanup(void *userdata, void *value)
{
}
static int properties_testCopy(void *arg)
{
SDL_PropertiesID a, b;
int num;
const char *string;
void *data;
int result;
a = SDL_CreateProperties();
SDL_SetNumberProperty(a, "num", 1);
SDL_SetStringProperty(a, "string", "foo");
SDL_SetProperty(a, "data", &a);
SDL_SetPropertyWithCleanup(a, "cleanup", &a, copy_cleanup, &a);
b = SDL_CreateProperties();
SDL_SetNumberProperty(b, "num", 2);
SDLTest_AssertPass("Call to SDL_CopyProperties(a, 0)");
result = SDL_CopyProperties(a, 0);
SDLTest_AssertCheck(result == -1,
"SDL_CopyProperties() result, got %d, expected -1", result);
SDLTest_AssertPass("Call to SDL_CopyProperties(0, b)");
result = SDL_CopyProperties(0, b);
SDLTest_AssertCheck(result == -1,
"SDL_CopyProperties() result, got %d, expected -1", result);
SDLTest_AssertPass("Call to SDL_CopyProperties(a, b)");
result = SDL_CopyProperties(a, b);
SDLTest_AssertCheck(result == 0,
"SDL_CopyProperties() result, got %d, expected 0", result);
SDL_DestroyProperties(a);
num = (int)SDL_GetNumberProperty(b, "num", 0);
SDLTest_AssertCheck(num == 1,
"Checking number property, got %d, expected 1", num);
string = SDL_GetStringProperty(b, "string", NULL);
SDLTest_AssertCheck(string && SDL_strcmp(string, "foo") == 0,
"Checking string property, got \"%s\", expected \"foo\"", string);
data = SDL_GetProperty(b, "data", NULL);
SDLTest_AssertCheck(data == &a,
"Checking data property, got %p, expected %p", data, &a);
data = SDL_GetProperty(b, "cleanup", NULL);
SDLTest_AssertCheck(data == NULL,
"Checking cleanup property, got %p, expected NULL", data);
SDL_DestroyProperties(b);
return TEST_COMPLETED;
}
/**
* Test cleanup functionality
*/
@ -324,21 +385,29 @@ static int properties_testLocking(void *arg)
/* ================= Test References ================== */
/* Properties test cases */
static const SDLTest_TestCaseReference propertiesTest1 = {
static const SDLTest_TestCaseReference propertiesTestBasic = {
(SDLTest_TestCaseFp)properties_testBasic, "properties_testBasic", "Test basic property functionality", TEST_ENABLED
};
static const SDLTest_TestCaseReference propertiesTest2 = {
static const SDLTest_TestCaseReference propertiesTestCopy = {
(SDLTest_TestCaseFp)properties_testCopy, "properties_testCopy", "Test property copy functionality", TEST_ENABLED
};
static const SDLTest_TestCaseReference propertiesTestCleanup = {
(SDLTest_TestCaseFp)properties_testCleanup, "properties_testCleanup", "Test property cleanup functionality", TEST_ENABLED
};
static const SDLTest_TestCaseReference propertiesTest3 = {
static const SDLTest_TestCaseReference propertiesTestLocking = {
(SDLTest_TestCaseFp)properties_testLocking, "properties_testLocking", "Test property locking functionality", TEST_ENABLED
};
/* Sequence of Properties test cases */
static const SDLTest_TestCaseReference *propertiesTests[] = {
&propertiesTest1, &propertiesTest2, &propertiesTest3, NULL
&propertiesTestBasic,
&propertiesTestCopy,
&propertiesTestCleanup,
&propertiesTestLocking,
NULL
};
/* Properties test suite (global) */

View File

@ -150,7 +150,7 @@ static int render_testPrimitives(void *arg)
checkFailCount2 = 0;
for (y = 0; y < 3; y++) {
for (x = y % 2; x < TESTRENDER_SCREEN_W; x += 2) {
ret = SDL_SetRenderDrawColor(renderer, x * y, x * y / 2, x * y / 3, SDL_ALPHA_OPAQUE);
ret = SDL_SetRenderDrawColor(renderer, (Uint8)(x * y), (Uint8)(x * y / 2), (Uint8)(x * y / 3), SDL_ALPHA_OPAQUE);
if (ret != 0) {
checkFailCount1++;
}
@ -247,7 +247,7 @@ static int render_testPrimitivesBlend(void *arg)
checkFailCount2 = 0;
checkFailCount3 = 0;
for (i = 0; i < TESTRENDER_SCREEN_W; i += 2) {
ret = SDL_SetRenderDrawColor(renderer, 60 + 2 * i, 240 - 2 * i, 50, 3 * i);
ret = SDL_SetRenderDrawColor(renderer, (Uint8)(60 + 2 * i), (Uint8)(240 - 2 * i), 50, (Uint8)(3 * i));
if (ret != 0) {
checkFailCount1++;
}
@ -271,7 +271,7 @@ static int render_testPrimitivesBlend(void *arg)
checkFailCount2 = 0;
checkFailCount3 = 0;
for (i = 0; i < TESTRENDER_SCREEN_H; i += 2) {
ret = SDL_SetRenderDrawColor(renderer, 60 + 2 * i, 240 - 2 * i, 50, 3 * i);
ret = SDL_SetRenderDrawColor(renderer, (Uint8)(60 + 2 * i), (Uint8)(240 - 2 * i), 50, (Uint8)(3 * i));
if (ret != 0) {
checkFailCount1++;
}
@ -297,7 +297,7 @@ static int render_testPrimitivesBlend(void *arg)
checkFailCount3 = 0;
for (j = 0; j < TESTRENDER_SCREEN_H; j += 3) {
for (i = 0; i < TESTRENDER_SCREEN_W; i += 3) {
ret = SDL_SetRenderDrawColor(renderer, j * 4, i * 3, j * 4, i * 3);
ret = SDL_SetRenderDrawColor(renderer, (Uint8)(j * 4), (Uint8)(i * 3), (Uint8)(j * 4), (Uint8)(i * 3));
if (ret != 0) {
checkFailCount1++;
}
@ -332,6 +332,50 @@ static int render_testPrimitivesBlend(void *arg)
return TEST_COMPLETED;
}
/**
* Tests the SDL primitives for rendering within a viewport.
*
* \sa SDL_SetRenderDrawColor
* \sa SDL_RenderFillRect
* \sa SDL_RenderLine
*
*/
static int render_testPrimitivesWithViewport(void *arg)
{
SDL_Rect viewport;
SDL_Surface *surface;
/* Clear surface. */
clearScreen();
viewport.x = 2;
viewport.y = 2;
viewport.w = 2;
viewport.h = 2;
CHECK_FUNC(SDL_SetRenderViewport, (renderer, &viewport));
CHECK_FUNC(SDL_SetRenderDrawColor, (renderer, 255, 255, 255, SDL_ALPHA_OPAQUE))
CHECK_FUNC(SDL_RenderLine, (renderer, 0.0f, 0.0f, 1.0f, 1.0f));
viewport.x = 3;
viewport.y = 3;
viewport.w = 1;
viewport.h = 1;
CHECK_FUNC(SDL_SetRenderViewport, (renderer, &viewport));
surface = SDL_RenderReadPixels(renderer, NULL);
if (surface) {
Uint8 r, g, b, a;
CHECK_FUNC(SDL_ReadSurfacePixel, (surface, 0, 0, &r, &g, &b, &a));
SDLTest_AssertCheck(r == 0xFF && g == 0xFF && b == 0xFF && a == 0xFF, "Validate diagonal line drawing with viewport, expected 0xFFFFFFFF, got 0x%.2x%.2x%.2x%.2x", r, g, b, a);
SDL_DestroySurface(surface);
} else {
SDLTest_AssertCheck(surface != NULL, "Validate result from SDL_RenderReadPixels, got NULL, %s", SDL_GetError());
}
return TEST_COMPLETED;
}
/**
* Tests some blitting routines.
*
@ -441,7 +485,7 @@ static int render_testBlitColor(void *arg)
for (j = 0; j <= nj; j += 4) {
for (i = 0; i <= ni; i += 4) {
/* Set color mod. */
ret = SDL_SetTextureColorMod(tface, (255 / nj) * j, (255 / ni) * i, (255 / nj) * j);
ret = SDL_SetTextureColorMod(tface, (Uint8)((255 / nj) * j), (Uint8)((255 / ni) * i), (Uint8)((255 / nj) * j));
if (ret != 0) {
checkFailCount1++;
}
@ -518,7 +562,7 @@ static int render_testBlitAlpha(void *arg)
for (j = 0; j <= nj; j += 4) {
for (i = 0; i <= ni; i += 4) {
/* Set alpha mod. */
ret = SDL_SetTextureAlphaMod(tface, (255 / ni) * i);
ret = SDL_SetTextureAlphaMod(tface, (Uint8)((255 / ni) * i));
if (ret != 0) {
checkFailCount1++;
}
@ -701,13 +745,13 @@ static int render_testBlitBlend(void *arg)
for (i = 0; i <= ni; i += 4) {
/* Set color mod. */
ret = SDL_SetTextureColorMod(tface, (255 / nj) * j, (255 / ni) * i, (255 / nj) * j);
ret = SDL_SetTextureColorMod(tface, (Uint8)((255 / nj) * j), (Uint8)((255 / ni) * i), (Uint8)((255 / nj) * j));
if (ret != 0) {
checkFailCount1++;
}
/* Set alpha mod. */
ret = SDL_SetTextureAlphaMod(tface, (100 / ni) * i);
ret = SDL_SetTextureAlphaMod(tface, (Uint8)((100 / ni) * i));
if (ret != 0) {
checkFailCount2++;
}
@ -815,6 +859,63 @@ static int render_testViewport(void *arg)
return TEST_COMPLETED;
}
/**
* Test clip rect
*/
static int render_testClipRect(void *arg)
{
SDL_Surface *referenceSurface;
SDL_Rect cliprect;
cliprect.x = TESTRENDER_SCREEN_W / 3;
cliprect.y = TESTRENDER_SCREEN_H / 3;
cliprect.w = TESTRENDER_SCREEN_W / 2;
cliprect.h = TESTRENDER_SCREEN_H / 2;
/* Create expected result */
referenceSurface = SDL_CreateSurface(TESTRENDER_SCREEN_W, TESTRENDER_SCREEN_H, RENDER_COMPARE_FORMAT);
CHECK_FUNC(SDL_FillSurfaceRect, (referenceSurface, NULL, RENDER_COLOR_CLEAR))
CHECK_FUNC(SDL_FillSurfaceRect, (referenceSurface, &cliprect, RENDER_COLOR_GREEN))
/* Clear surface. */
clearScreen();
/* Set the cliprect and do a fill operation */
CHECK_FUNC(SDL_SetRenderClipRect, (renderer, &cliprect))
CHECK_FUNC(SDL_SetRenderDrawColor, (renderer, 0, 255, 0, SDL_ALPHA_OPAQUE))
CHECK_FUNC(SDL_RenderFillRect, (renderer, NULL))
CHECK_FUNC(SDL_SetRenderClipRect, (renderer, NULL))
/* Check to see if final image matches. */
compare(referenceSurface, ALLOWABLE_ERROR_OPAQUE);
/*
* Verify that clear ignores the cliprect
*/
/* Create expected result */
CHECK_FUNC(SDL_FillSurfaceRect, (referenceSurface, NULL, RENDER_COLOR_GREEN))
/* Clear surface. */
clearScreen();
/* Set the cliprect and do a clear operation */
CHECK_FUNC(SDL_SetRenderClipRect, (renderer, &cliprect))
CHECK_FUNC(SDL_SetRenderDrawColor, (renderer, 0, 255, 0, SDL_ALPHA_OPAQUE))
CHECK_FUNC(SDL_RenderClear, (renderer))
CHECK_FUNC(SDL_SetRenderClipRect, (renderer, NULL))
/* Check to see if final image matches. */
compare(referenceSurface, ALLOWABLE_ERROR_OPAQUE);
/* Make current */
SDL_RenderPresent(renderer);
SDL_DestroySurface(referenceSurface);
return TEST_COMPLETED;
}
/**
* Test logical size
*/
@ -1167,36 +1268,35 @@ hasTexAlpha(void)
static void
compare(SDL_Surface *referenceSurface, int allowable_error)
{
int ret;
SDL_Rect rect;
Uint8 *pixels;
SDL_Surface *testSurface;
int ret;
SDL_Rect rect;
SDL_Surface *surface, *testSurface;
/* Read pixels. */
pixels = (Uint8 *)SDL_malloc(4*TESTRENDER_SCREEN_W*TESTRENDER_SCREEN_H);
SDLTest_AssertCheck(pixels != NULL, "Validate allocated temp pixel buffer");
if (pixels == NULL) {
return;
}
/* Explicitly specify the rect in case the window isn't the expected size... */
rect.x = 0;
rect.y = 0;
rect.w = TESTRENDER_SCREEN_W;
rect.h = TESTRENDER_SCREEN_H;
/* Explicitly specify the rect in case the window isn't the expected size... */
rect.x = 0;
rect.y = 0;
rect.w = TESTRENDER_SCREEN_W;
rect.h = TESTRENDER_SCREEN_H;
CHECK_FUNC(SDL_RenderReadPixels, (renderer, &rect, RENDER_COMPARE_FORMAT, pixels, 80*4 ))
surface = SDL_RenderReadPixels(renderer, &rect);
if (!surface) {
SDLTest_AssertCheck(surface != NULL, "Validate result from SDL_RenderReadPixels, got NULL, %s", SDL_GetError());
return;
}
/* Create surface. */
testSurface = SDL_CreateSurfaceFrom(pixels, TESTRENDER_SCREEN_W, TESTRENDER_SCREEN_H, TESTRENDER_SCREEN_W*4, RENDER_COMPARE_FORMAT);
SDLTest_AssertCheck(testSurface != NULL, "Verify result from SDL_CreateSurfaceFrom is not NULL");
testSurface = SDL_ConvertSurfaceFormat(surface, RENDER_COMPARE_FORMAT);
SDL_DestroySurface(surface);
if (!testSurface) {
SDLTest_AssertCheck(testSurface != NULL, "Validate result from SDL_ConvertSurfaceFormat, got NULL, %s", SDL_GetError());
return;
}
/* Compare surface. */
ret = SDLTest_CompareSurfaces( testSurface, referenceSurface, allowable_error );
SDLTest_AssertCheck(ret == 0, "Validate result from SDLTest_CompareSurfaces, expected: 0, got: %i", ret);
/* Compare surface. */
ret = SDLTest_CompareSurfaces(testSurface, referenceSurface, allowable_error);
SDLTest_AssertCheck(ret == 0, "Validate result from SDLTest_CompareSurfaces, expected: 0, got: %i", ret);
/* Clean up. */
SDL_free(pixels);
SDL_DestroySurface(testSurface);
/* Clean up. */
SDL_DestroySurface(testSurface);
}
/**
@ -1250,28 +1350,36 @@ static const SDLTest_TestCaseReference renderTest3 = {
};
static const SDLTest_TestCaseReference renderTest4 = {
(SDLTest_TestCaseFp)render_testBlit, "render_testBlit", "Tests blitting", TEST_ENABLED
(SDLTest_TestCaseFp)render_testPrimitivesWithViewport, "render_testPrimitivesWithViewport", "Tests rendering primitives within a viewport", TEST_ENABLED
};
static const SDLTest_TestCaseReference renderTest5 = {
(SDLTest_TestCaseFp)render_testBlit, "render_testBlit", "Tests blitting", TEST_ENABLED
};
static const SDLTest_TestCaseReference renderTest6 = {
(SDLTest_TestCaseFp)render_testBlitColor, "render_testBlitColor", "Tests blitting with color", TEST_ENABLED
};
/* TODO: rewrite test case, define new test data and re-enable; current implementation fails */
static const SDLTest_TestCaseReference renderTest6 = {
static const SDLTest_TestCaseReference renderTest7 = {
(SDLTest_TestCaseFp)render_testBlitAlpha, "render_testBlitAlpha", "Tests blitting with alpha", TEST_DISABLED
};
/* TODO: rewrite test case, define new test data and re-enable; current implementation fails */
static const SDLTest_TestCaseReference renderTest7 = {
static const SDLTest_TestCaseReference renderTest8 = {
(SDLTest_TestCaseFp)render_testBlitBlend, "render_testBlitBlend", "Tests blitting with blending", TEST_DISABLED
};
static const SDLTest_TestCaseReference renderTest8 = {
static const SDLTest_TestCaseReference renderTest9 = {
(SDLTest_TestCaseFp)render_testViewport, "render_testViewport", "Tests viewport", TEST_ENABLED
};
static const SDLTest_TestCaseReference renderTest9 = {
static const SDLTest_TestCaseReference renderTest10 = {
(SDLTest_TestCaseFp)render_testClipRect, "render_testClipRect", "Tests clip rect", TEST_ENABLED
};
static const SDLTest_TestCaseReference renderTest11 = {
(SDLTest_TestCaseFp)render_testLogicalSize, "render_testLogicalSize", "Tests logical size", TEST_ENABLED
};
@ -1279,7 +1387,7 @@ static const SDLTest_TestCaseReference renderTest9 = {
static const SDLTest_TestCaseReference *renderTests[] = {
&renderTest1, &renderTest2, &renderTest3, &renderTest4,
&renderTest5, &renderTest6, &renderTest7, &renderTest8,
&renderTest9, NULL
&renderTest9, &renderTest10, &renderTest11, NULL
};
/* Render test suite (global) */

View File

@ -1,685 +0,0 @@
/**
* Automated SDL_RWops test.
*
* Original code written by Edgar Simo "bobbens"
* Ported by Markus Kauppila (markus.kauppila@gmail.com)
* Updated and extended for SDL_test by aschiffler at ferzkopp dot net
*
* Released under Public Domain.
*/
/* quiet windows compiler warnings */
#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS)
#define _CRT_SECURE_NO_WARNINGS
#endif
#include <stdio.h>
#include <SDL3/SDL.h>
#include <SDL3/SDL_test.h>
#include "testautomation_suites.h"
/* ================= Test Case Implementation ================== */
static const char *RWopsReadTestFilename = "rwops_read";
static const char *RWopsWriteTestFilename = "rwops_write";
static const char *RWopsAlphabetFilename = "rwops_alphabet";
static const char RWopsHelloWorldTestString[] = "Hello World!";
static const char RWopsHelloWorldCompString[] = "Hello World!";
static const char RWopsAlphabetString[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
/* Fixture */
static void RWopsSetUp(void *arg)
{
size_t fileLen;
FILE *handle;
size_t writtenLen;
int result;
/* Clean up from previous runs (if any); ignore errors */
(void)remove(RWopsReadTestFilename);
(void)remove(RWopsWriteTestFilename);
(void)remove(RWopsAlphabetFilename);
/* Create a test file */
handle = fopen(RWopsReadTestFilename, "w");
SDLTest_AssertCheck(handle != NULL, "Verify creation of file '%s' returned non NULL handle", RWopsReadTestFilename);
if (handle == NULL) {
return;
}
/* Write some known text into it */
fileLen = SDL_strlen(RWopsHelloWorldTestString);
writtenLen = fwrite(RWopsHelloWorldTestString, 1, fileLen, handle);
SDLTest_AssertCheck(fileLen == writtenLen, "Verify number of written bytes, expected %i, got %i", (int)fileLen, (int)writtenLen);
result = fclose(handle);
SDLTest_AssertCheck(result == 0, "Verify result from fclose, expected 0, got %i", result);
/* Create a second test file */
handle = fopen(RWopsAlphabetFilename, "w");
SDLTest_AssertCheck(handle != NULL, "Verify creation of file '%s' returned non NULL handle", RWopsAlphabetFilename);
if (handle == NULL) {
return;
}
/* Write alphabet text into it */
fileLen = SDL_strlen(RWopsAlphabetString);
writtenLen = fwrite(RWopsAlphabetString, 1, fileLen, handle);
SDLTest_AssertCheck(fileLen == writtenLen, "Verify number of written bytes, expected %i, got %i", (int)fileLen, (int)writtenLen);
result = fclose(handle);
SDLTest_AssertCheck(result == 0, "Verify result from fclose, expected 0, got %i", result);
SDLTest_AssertPass("Creation of test file completed");
}
static void RWopsTearDown(void *arg)
{
int result;
/* Remove the created files to clean up; ignore errors for write filename */
result = remove(RWopsReadTestFilename);
SDLTest_AssertCheck(result == 0, "Verify result from remove(%s), expected 0, got %i", RWopsReadTestFilename, result);
(void)remove(RWopsWriteTestFilename);
result = remove(RWopsAlphabetFilename);
SDLTest_AssertCheck(result == 0, "Verify result from remove(%s), expected 0, got %i", RWopsAlphabetFilename, result);
SDLTest_AssertPass("Cleanup of test files completed");
}
/**
* Makes sure parameters work properly. Local helper function.
*
* \sa SDL_RWseek
* \sa SDL_RWread
*/
static void testGenericRWopsValidations(SDL_RWops *rw, SDL_bool write)
{
char buf[sizeof(RWopsHelloWorldTestString)];
Sint64 i;
size_t s;
int seekPos = SDLTest_RandomIntegerInRange(4, 8);
/* Clear buffer */
SDL_zeroa(buf);
/* Set to start. */
i = SDL_RWseek(rw, 0, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_RWseek (SDL_RW_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test write */
s = SDL_RWwrite(rw, RWopsHelloWorldTestString, sizeof(RWopsHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_RWwrite succeeded");
if (write) {
SDLTest_AssertCheck(s == sizeof(RWopsHelloWorldTestString) - 1, "Verify result of writing with SDL_RWwrite, expected %i, got %i", (int)sizeof(RWopsHelloWorldTestString) - 1, (int)s);
} else {
SDLTest_AssertCheck(s == 0, "Verify result of writing with SDL_RWwrite, expected: 0, got %i", (int)s);
}
/* Test seek to random position */
i = SDL_RWseek(rw, seekPos, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(i == (Sint64)seekPos, "Verify seek to %i with SDL_RWseek (SDL_RW_SEEK_SET), expected %i, got %" SDL_PRIs64, seekPos, seekPos, i);
/* Test seek back to start */
i = SDL_RWseek(rw, 0, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_RWseek (SDL_RW_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test read */
s = SDL_RWread(rw, buf, sizeof(RWopsHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_RWread succeeded");
SDLTest_AssertCheck(
s == (sizeof(RWopsHelloWorldTestString) - 1),
"Verify result from SDL_RWread, expected %i, got %i",
(int)(sizeof(RWopsHelloWorldTestString) - 1),
(int)s);
SDLTest_AssertCheck(
SDL_memcmp(buf, RWopsHelloWorldTestString, sizeof(RWopsHelloWorldTestString) - 1) == 0,
"Verify read bytes match expected string, expected '%s', got '%s'", RWopsHelloWorldTestString, buf);
/* Test seek back to start */
i = SDL_RWseek(rw, 0, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_RWseek (SDL_RW_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test printf */
s = SDL_RWprintf(rw, "%s", RWopsHelloWorldTestString);
SDLTest_AssertPass("Call to SDL_RWprintf succeeded");
if (write) {
SDLTest_AssertCheck(s == sizeof(RWopsHelloWorldTestString) - 1, "Verify result of writing with SDL_RWprintf, expected %i, got %i", (int)sizeof(RWopsHelloWorldTestString) - 1, (int)s);
} else {
SDLTest_AssertCheck(s == 0, "Verify result of writing with SDL_RWwrite, expected: 0, got %i", (int)s);
}
/* Test seek back to start */
i = SDL_RWseek(rw, 0, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(i == (Sint64)0, "Verify seek to 0 with SDL_RWseek (SDL_RW_SEEK_SET), expected 0, got %" SDL_PRIs64, i);
/* Test read */
s = SDL_RWread(rw, buf, sizeof(RWopsHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_RWread succeeded");
SDLTest_AssertCheck(
s == (sizeof(RWopsHelloWorldTestString) - 1),
"Verify result from SDL_RWread, expected %i, got %i",
(int)(sizeof(RWopsHelloWorldTestString) - 1),
(int)s);
SDLTest_AssertCheck(
SDL_memcmp(buf, RWopsHelloWorldTestString, sizeof(RWopsHelloWorldTestString) - 1) == 0,
"Verify read bytes match expected string, expected '%s', got '%s'", RWopsHelloWorldTestString, buf);
/* More seek tests. */
i = SDL_RWseek(rw, -4, SDL_RW_SEEK_CUR);
SDLTest_AssertPass("Call to SDL_RWseek(...,-4,SDL_RW_SEEK_CUR) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(sizeof(RWopsHelloWorldTestString) - 5),
"Verify seek to -4 with SDL_RWseek (SDL_RW_SEEK_CUR), expected %i, got %i",
(int)(sizeof(RWopsHelloWorldTestString) - 5),
(int)i);
i = SDL_RWseek(rw, -1, SDL_RW_SEEK_END);
SDLTest_AssertPass("Call to SDL_RWseek(...,-1,SDL_RW_SEEK_END) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(sizeof(RWopsHelloWorldTestString) - 2),
"Verify seek to -1 with SDL_RWseek (SDL_RW_SEEK_END), expected %i, got %i",
(int)(sizeof(RWopsHelloWorldTestString) - 2),
(int)i);
/* Invalid whence seek */
i = SDL_RWseek(rw, 0, 999);
SDLTest_AssertPass("Call to SDL_RWseek(...,0,invalid_whence) succeeded");
SDLTest_AssertCheck(
i == (Sint64)(-1),
"Verify seek with SDL_RWseek (invalid_whence); expected: -1, got %i",
(int)i);
}
/**
* Negative test for SDL_RWFromFile parameters
*
* \sa SDL_RWFromFile
*
*/
static int rwops_testParamNegative(void *arg)
{
SDL_RWops *rwops;
/* These should all fail. */
rwops = SDL_RWFromFile(NULL, NULL);
SDLTest_AssertPass("Call to SDL_RWFromFile(NULL, NULL) succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromFile(NULL, NULL) returns NULL");
rwops = SDL_RWFromFile(NULL, "ab+");
SDLTest_AssertPass("Call to SDL_RWFromFile(NULL, \"ab+\") succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromFile(NULL, \"ab+\") returns NULL");
rwops = SDL_RWFromFile(NULL, "sldfkjsldkfj");
SDLTest_AssertPass("Call to SDL_RWFromFile(NULL, \"sldfkjsldkfj\") succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromFile(NULL, \"sldfkjsldkfj\") returns NULL");
rwops = SDL_RWFromFile("something", "");
SDLTest_AssertPass("Call to SDL_RWFromFile(\"something\", \"\") succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromFile(\"something\", \"\") returns NULL");
rwops = SDL_RWFromFile("something", NULL);
SDLTest_AssertPass("Call to SDL_RWFromFile(\"something\", NULL) succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromFile(\"something\", NULL) returns NULL");
rwops = SDL_RWFromMem(NULL, 10);
SDLTest_AssertPass("Call to SDL_RWFromMem(NULL, 10) succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromMem(NULL, 10) returns NULL");
rwops = SDL_RWFromMem((void *)RWopsAlphabetString, 0);
SDLTest_AssertPass("Call to SDL_RWFromMem(data, 0) succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromMem(data, 0) returns NULL");
rwops = SDL_RWFromConstMem((const void *)RWopsAlphabetString, 0);
SDLTest_AssertPass("Call to SDL_RWFromConstMem(data, 0) succeeded");
SDLTest_AssertCheck(rwops == NULL, "Verify SDL_RWFromConstMem(data, 0) returns NULL");
return TEST_COMPLETED;
}
/**
* Tests opening from memory.
*
* \sa SDL_RWFromMem
* \sa SDL_RWClose
*/
static int rwops_testMem(void *arg)
{
char mem[sizeof(RWopsHelloWorldTestString)];
SDL_RWops *rw;
int result;
/* Clear buffer */
SDL_zeroa(mem);
/* Open */
rw = SDL_RWFromMem(mem, sizeof(RWopsHelloWorldTestString) - 1);
SDLTest_AssertPass("Call to SDL_RWFromMem() succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening memory with SDL_RWFromMem does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Check type */
SDLTest_AssertCheck(rw->type == SDL_RWOPS_MEMORY, "Verify RWops type is SDL_RWOPS_MEMORY; expected: %d, got: %" SDL_PRIu32, SDL_RWOPS_MEMORY, rw->type);
/* Run generic tests */
testGenericRWopsValidations(rw, SDL_TRUE);
/* Close */
result = SDL_RWclose(rw);
SDLTest_AssertPass("Call to SDL_RWclose() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests opening from memory.
*
* \sa SDL_RWFromConstMem
* \sa SDL_RWClose
*/
static int rwops_testConstMem(void *arg)
{
SDL_RWops *rw;
int result;
/* Open handle */
rw = SDL_RWFromConstMem(RWopsHelloWorldCompString, sizeof(RWopsHelloWorldCompString) - 1);
SDLTest_AssertPass("Call to SDL_RWFromConstMem() succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening memory with SDL_RWFromConstMem does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Check type */
SDLTest_AssertCheck(rw->type == SDL_RWOPS_MEMORY_RO, "Verify RWops type is SDL_RWOPS_MEMORY_RO; expected: %d, got: %" SDL_PRIu32, SDL_RWOPS_MEMORY_RO, rw->type);
/* Run generic tests */
testGenericRWopsValidations(rw, SDL_FALSE);
/* Close handle */
result = SDL_RWclose(rw);
SDLTest_AssertPass("Call to SDL_RWclose() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests reading from file.
*
* \sa SDL_RWFromFile
* \sa SDL_RWClose
*/
static int rwops_testFileRead(void *arg)
{
SDL_RWops *rw;
int result;
/* Read test. */
rw = SDL_RWFromFile(RWopsReadTestFilename, "r");
SDLTest_AssertPass("Call to SDL_RWFromFile(..,\"r\") succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_RWFromFile in read mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Check type */
#ifdef __ANDROID__
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_STDFILE || rw->type == SDL_RWOPS_JNIFILE,
"Verify RWops type is SDL_RWOPS_STDFILE or SDL_RWOPS_JNIFILE; expected: %d|%d, got: %d", SDL_RWOPS_STDFILE, SDL_RWOPS_JNIFILE, rw->type);
#elif defined(__WIN32__)
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_WINFILE,
"Verify RWops type is SDL_RWOPS_WINFILE; expected: %d, got: %d", SDL_RWOPS_WINFILE, rw->type);
#else
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_STDFILE,
"Verify RWops type is SDL_RWOPS_STDFILE; expected: %d, got: %" SDL_PRIu32, SDL_RWOPS_STDFILE, rw->type);
#endif
/* Run generic tests */
testGenericRWopsValidations(rw, SDL_FALSE);
/* Close handle */
result = SDL_RWclose(rw);
SDLTest_AssertPass("Call to SDL_RWclose() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests writing from file.
*
* \sa SDL_RWFromFile
* \sa SDL_RWClose
*/
static int rwops_testFileWrite(void *arg)
{
SDL_RWops *rw;
int result;
/* Write test. */
rw = SDL_RWFromFile(RWopsWriteTestFilename, "w+");
SDLTest_AssertPass("Call to SDL_RWFromFile(..,\"w+\") succeeded");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_RWFromFile in write mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Check type */
#ifdef __ANDROID__
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_STDFILE || rw->type == SDL_RWOPS_JNIFILE,
"Verify RWops type is SDL_RWOPS_STDFILE or SDL_RWOPS_JNIFILE; expected: %d|%d, got: %d", SDL_RWOPS_STDFILE, SDL_RWOPS_JNIFILE, rw->type);
#elif defined(__WIN32__)
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_WINFILE,
"Verify RWops type is SDL_RWOPS_WINFILE; expected: %d, got: %d", SDL_RWOPS_WINFILE, rw->type);
#else
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_STDFILE,
"Verify RWops type is SDL_RWOPS_STDFILE; expected: %d, got: %" SDL_PRIu32, SDL_RWOPS_STDFILE, rw->type);
#endif
/* Run generic tests */
testGenericRWopsValidations(rw, SDL_TRUE);
/* Close handle */
result = SDL_RWclose(rw);
SDLTest_AssertPass("Call to SDL_RWclose() succeeded");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
return TEST_COMPLETED;
}
/**
* Tests alloc and free RW context.
*
* \sa SDL_CreateRW
* \sa SDL_DestroyRW
*/
static int rwops_testAllocFree(void *arg)
{
/* Allocate context */
SDL_RWops *rw = SDL_CreateRW();
SDLTest_AssertPass("Call to SDL_CreateRW() succeeded");
SDLTest_AssertCheck(rw != NULL, "Validate result from SDL_CreateRW() is not NULL");
if (rw == NULL) {
return TEST_ABORTED;
}
/* Check type */
SDLTest_AssertCheck(
rw->type == SDL_RWOPS_UNKNOWN,
"Verify RWops type is SDL_RWOPS_UNKNOWN; expected: %d, got: %" SDL_PRIu32, SDL_RWOPS_UNKNOWN, rw->type);
/* Free context again */
SDL_DestroyRW(rw);
SDLTest_AssertPass("Call to SDL_DestroyRW() succeeded");
return TEST_COMPLETED;
}
/**
* Compare memory and file reads
*
* \sa SDL_RWFromMem
* \sa SDL_RWFromFile
*/
static int rwops_testCompareRWFromMemWithRWFromFile(void *arg)
{
int slen = 26;
char buffer_file[27];
char buffer_mem[27];
size_t rv_file;
size_t rv_mem;
Uint64 sv_file;
Uint64 sv_mem;
SDL_RWops *rwops_file;
SDL_RWops *rwops_mem;
int size;
int result;
for (size = 5; size < 10; size++) {
/* Terminate buffer */
buffer_file[slen] = 0;
buffer_mem[slen] = 0;
/* Read/seek from memory */
rwops_mem = SDL_RWFromMem((void *)RWopsAlphabetString, slen);
SDLTest_AssertPass("Call to SDL_RWFromMem()");
rv_mem = SDL_RWread(rwops_mem, buffer_mem, size * 6);
SDLTest_AssertPass("Call to SDL_RWread(mem, size=%d)", size * 6);
sv_mem = SDL_RWseek(rwops_mem, 0, SEEK_END);
SDLTest_AssertPass("Call to SDL_RWseek(mem,SEEK_END)");
result = SDL_RWclose(rwops_mem);
SDLTest_AssertPass("Call to SDL_RWclose(mem)");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
/* Read/see from file */
rwops_file = SDL_RWFromFile(RWopsAlphabetFilename, "r");
SDLTest_AssertPass("Call to SDL_RWFromFile()");
rv_file = SDL_RWread(rwops_file, buffer_file, size * 6);
SDLTest_AssertPass("Call to SDL_RWread(file, size=%d)", size * 6);
sv_file = SDL_RWseek(rwops_file, 0, SEEK_END);
SDLTest_AssertPass("Call to SDL_RWseek(file,SEEK_END)");
result = SDL_RWclose(rwops_file);
SDLTest_AssertPass("Call to SDL_RWclose(file)");
SDLTest_AssertCheck(result == 0, "Verify result value is 0; got: %d", result);
/* Compare */
SDLTest_AssertCheck(rv_mem == rv_file, "Verify returned read blocks matches for mem and file reads; got: rv_mem=%d rv_file=%d", (int)rv_mem, (int)rv_file);
SDLTest_AssertCheck(sv_mem == sv_file, "Verify SEEK_END position matches for mem and file seeks; got: sv_mem=%d sv_file=%d", (int)sv_mem, (int)sv_file);
SDLTest_AssertCheck(buffer_mem[slen] == 0, "Verify mem buffer termination; expected: 0, got: %d", buffer_mem[slen]);
SDLTest_AssertCheck(buffer_file[slen] == 0, "Verify file buffer termination; expected: 0, got: %d", buffer_file[slen]);
SDLTest_AssertCheck(
SDL_strncmp(buffer_mem, RWopsAlphabetString, slen) == 0,
"Verify mem buffer contain alphabet string; expected: %s, got: %s", RWopsAlphabetString, buffer_mem);
SDLTest_AssertCheck(
SDL_strncmp(buffer_file, RWopsAlphabetString, slen) == 0,
"Verify file buffer contain alphabet string; expected: %s, got: %s", RWopsAlphabetString, buffer_file);
}
return TEST_COMPLETED;
}
/**
* Tests writing and reading from file using endian aware functions.
*
* \sa SDL_RWFromFile
* \sa SDL_RWClose
* \sa SDL_ReadU16BE
* \sa SDL_WriteU16BE
*/
static int rwops_testFileWriteReadEndian(void *arg)
{
SDL_RWops *rw;
Sint64 result;
int mode;
Uint16 BE16value;
Uint32 BE32value;
Uint64 BE64value;
Uint16 LE16value;
Uint32 LE32value;
Uint64 LE64value;
Uint16 BE16test;
Uint32 BE32test;
Uint64 BE64test;
Uint16 LE16test;
Uint32 LE32test;
Uint64 LE64test;
SDL_bool bresult;
int cresult;
for (mode = 0; mode < 3; mode++) {
/* Create test data */
switch (mode) {
default:
case 0:
SDLTest_Log("All 0 values");
BE16value = 0;
BE32value = 0;
BE64value = 0;
LE16value = 0;
LE32value = 0;
LE64value = 0;
break;
case 1:
SDLTest_Log("All 1 values");
BE16value = 1;
BE32value = 1;
BE64value = 1;
LE16value = 1;
LE32value = 1;
LE64value = 1;
break;
case 2:
SDLTest_Log("Random values");
BE16value = SDLTest_RandomUint16();
BE32value = SDLTest_RandomUint32();
BE64value = SDLTest_RandomUint64();
LE16value = SDLTest_RandomUint16();
LE32value = SDLTest_RandomUint32();
LE64value = SDLTest_RandomUint64();
break;
}
/* Write test. */
rw = SDL_RWFromFile(RWopsWriteTestFilename, "w+");
SDLTest_AssertPass("Call to SDL_RWFromFile(..,\"w+\")");
SDLTest_AssertCheck(rw != NULL, "Verify opening file with SDL_RWFromFile in write mode does not return NULL");
/* Bail out if NULL */
if (rw == NULL) {
return TEST_ABORTED;
}
/* Write test data */
bresult = SDL_WriteU16BE(rw, BE16value);
SDLTest_AssertPass("Call to SDL_WriteU16BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU32BE(rw, BE32value);
SDLTest_AssertPass("Call to SDL_WriteU32BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU64BE(rw, BE64value);
SDLTest_AssertPass("Call to SDL_WriteU64BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU16LE(rw, LE16value);
SDLTest_AssertPass("Call to SDL_WriteU16LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU32LE(rw, LE32value);
SDLTest_AssertPass("Call to SDL_WriteU32LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
bresult = SDL_WriteU64LE(rw, LE64value);
SDLTest_AssertPass("Call to SDL_WriteU64LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object written, expected: SDL_TRUE, got: SDL_FALSE");
/* Test seek to start */
result = SDL_RWseek(rw, 0, SDL_RW_SEEK_SET);
SDLTest_AssertPass("Call to SDL_RWseek succeeded");
SDLTest_AssertCheck(result == 0, "Verify result from position 0 with SDL_RWseek, expected 0, got %i", (int)result);
/* Read test data */
bresult = SDL_ReadU16BE(rw, &BE16test);
SDLTest_AssertPass("Call to SDL_ReadU16BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE16test == BE16value, "Validate object read from SDL_ReadU16BE, expected: %hu, got: %hu", BE16value, BE16test);
bresult = SDL_ReadU32BE(rw, &BE32test);
SDLTest_AssertPass("Call to SDL_ReadU32BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE32test == BE32value, "Validate object read from SDL_ReadU32BE, expected: %" SDL_PRIu32 ", got: %" SDL_PRIu32, BE32value, BE32test);
bresult = SDL_ReadU64BE(rw, &BE64test);
SDLTest_AssertPass("Call to SDL_ReadU64BE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(BE64test == BE64value, "Validate object read from SDL_ReadU64BE, expected: %" SDL_PRIu64 ", got: %" SDL_PRIu64, BE64value, BE64test);
bresult = SDL_ReadU16LE(rw, &LE16test);
SDLTest_AssertPass("Call to SDL_ReadU16LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE16test == LE16value, "Validate object read from SDL_ReadU16LE, expected: %hu, got: %hu", LE16value, LE16test);
bresult = SDL_ReadU32LE(rw, &LE32test);
SDLTest_AssertPass("Call to SDL_ReadU32LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE32test == LE32value, "Validate object read from SDL_ReadU32LE, expected: %" SDL_PRIu32 ", got: %" SDL_PRIu32, LE32value, LE32test);
bresult = SDL_ReadU64LE(rw, &LE64test);
SDLTest_AssertPass("Call to SDL_ReadU64LE()");
SDLTest_AssertCheck(bresult == SDL_TRUE, "Validate object read, expected: SDL_TRUE, got: SDL_FALSE");
SDLTest_AssertCheck(LE64test == LE64value, "Validate object read from SDL_ReadU64LE, expected: %" SDL_PRIu64 ", got: %" SDL_PRIu64, LE64value, LE64test);
/* Close handle */
cresult = SDL_RWclose(rw);
SDLTest_AssertPass("Call to SDL_RWclose() succeeded");
SDLTest_AssertCheck(cresult == 0, "Verify result value is 0; got: %d", cresult);
}
return TEST_COMPLETED;
}
/* ================= Test References ================== */
/* RWops test cases */
static const SDLTest_TestCaseReference rwopsTest1 = {
(SDLTest_TestCaseFp)rwops_testParamNegative, "rwops_testParamNegative", "Negative test for SDL_RWFromFile parameters", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest2 = {
(SDLTest_TestCaseFp)rwops_testMem, "rwops_testMem", "Tests opening from memory", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest3 = {
(SDLTest_TestCaseFp)rwops_testConstMem, "rwops_testConstMem", "Tests opening from (const) memory", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest4 = {
(SDLTest_TestCaseFp)rwops_testFileRead, "rwops_testFileRead", "Tests reading from a file", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest5 = {
(SDLTest_TestCaseFp)rwops_testFileWrite, "rwops_testFileWrite", "Test writing to a file", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest6 = {
(SDLTest_TestCaseFp)rwops_testAllocFree, "rwops_testAllocFree", "Test alloc and free of RW context", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest7 = {
(SDLTest_TestCaseFp)rwops_testFileWriteReadEndian, "rwops_testFileWriteReadEndian", "Test writing and reading via the Endian aware functions", TEST_ENABLED
};
static const SDLTest_TestCaseReference rwopsTest8 = {
(SDLTest_TestCaseFp)rwops_testCompareRWFromMemWithRWFromFile, "rwops_testCompareRWFromMemWithRWFromFile", "Compare RWFromMem and RWFromFile RWops for read and seek", TEST_ENABLED
};
/* Sequence of RWops test cases */
static const SDLTest_TestCaseReference *rwopsTests[] = {
&rwopsTest1, &rwopsTest2, &rwopsTest3, &rwopsTest4, &rwopsTest5, &rwopsTest6,
&rwopsTest7, &rwopsTest8, NULL
};
/* RWops test suite (global) */
SDLTest_TestSuiteReference rwopsTestSuite = {
"RWops",
RWopsSetUp,
rwopsTests,
RWopsTearDown
};

View File

@ -141,7 +141,7 @@ static int stdlib_snprintf(void *arg)
int result;
int predicted;
char text[1024];
const char *expected;
const char *expected, *expected2, *expected3, *expected4, *expected5;
size_t size;
result = SDL_snprintf(text, sizeof(text), "%s", "foo");
@ -310,22 +310,58 @@ static int stdlib_snprintf(void *arg)
result = SDL_snprintf(text, sizeof(text), "%p", (void *)0x1234abcd);
expected = "0x1234abcd";
expected2 = "1234ABCD";
expected3 = "000000001234ABCD";
expected4 = "1234abcd";
expected5 = "000000001234abcd";
SDLTest_AssertPass("Call to SDL_snprintf(text, sizeof(text), \"%%p\", 0x1234abcd)");
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0, "Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected), "Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0 ||
SDL_strcmp(text, expected2) == 0 ||
SDL_strcmp(text, expected3) == 0 ||
SDL_strcmp(text, expected4) == 0 ||
SDL_strcmp(text, expected5) == 0,
"Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected) ||
result == SDL_strlen(expected2) ||
result == SDL_strlen(expected3) ||
result == SDL_strlen(expected4) ||
result == SDL_strlen(expected5),
"Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
result = SDL_snprintf(text, sizeof(text), "A %p B", (void *)0x1234abcd);
expected = "A 0x1234abcd B";
expected2 = "A 1234ABCD B";
expected3 = "A 000000001234ABCD B";
expected4 = "A 1234abcd B";
expected5 = "A 000000001234abcd B";
SDLTest_AssertPass("Call to SDL_snprintf(text, sizeof(text), \"A %%p B\", 0x1234abcd)");
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0, "Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected), "Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0 ||
SDL_strcmp(text, expected2) == 0 ||
SDL_strcmp(text, expected3) == 0 ||
SDL_strcmp(text, expected4) == 0 ||
SDL_strcmp(text, expected5) == 0,
"Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected) ||
result == SDL_strlen(expected2) ||
result == SDL_strlen(expected3) ||
result == SDL_strlen(expected4) ||
result == SDL_strlen(expected5),
"Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
if (sizeof(void *) >= 8) {
result = SDL_snprintf(text, sizeof(text), "%p", (void *)0x1ba07bddf60L);
expected = "0x1ba07bddf60";
expected2 = "000001BA07BDDF60";
expected3 = "000001ba07bddf60";
SDLTest_AssertPass("Call to SDL_snprintf(text, sizeof(text), \"%%p\", 0x1ba07bddf60)");
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0, "Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected), "Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
SDLTest_AssertCheck(SDL_strcmp(text, expected) == 0 ||
SDL_strcmp(text, expected2) == 0 ||
SDL_strcmp(text, expected3) == 0,
"Check text, expected: '%s', got: '%s'", expected, text);
SDLTest_AssertCheck(result == SDL_strlen(expected) ||
result == SDL_strlen(expected2) ||
result == SDL_strlen(expected3),
"Check result value, expected: %d, got: %d", (int)SDL_strlen(expected), result);
}
return TEST_COMPLETED;
}
@ -803,7 +839,7 @@ static int stdlib_sscanf(void *arg)
#ifdef _WIN64
#define SIZE_FORMAT "I64u"
#elif defined(__WIN32__)
#elif defined(SDL_PLATFORM_WIN32)
#define SIZE_FORMAT "I32u"
#else
#define SIZE_FORMAT "zu"

View File

@ -15,12 +15,12 @@ static void subsystemsSetUp(void *arg)
/* CHECKME: can we use SDL_Quit here, or this will break the flow of tests? */
SDL_Quit();
/* Alternate variant without SDL_Quit:
while (SDL_WasInit(SDL_INIT_EVERYTHING) != 0) {
SDL_QuitSubSystem(SDL_INIT_EVERYTHING);
while (SDL_WasInit(0) != 0) {
SDL_QuitSubSystem(~0U);
}
*/
SDLTest_AssertPass("Reset all subsystems before subsystems test");
SDLTest_AssertCheck(SDL_WasInit(SDL_INIT_EVERYTHING) == 0, "Check result from SDL_WasInit(SDL_INIT_EVERYTHING)");
SDLTest_AssertCheck(SDL_WasInit(0) == 0, "Check result from SDL_WasInit(0)");
}
static void subsystemsTearDown(void *arg)

View File

@ -17,6 +17,7 @@ extern SDLTest_TestSuiteReference hintsTestSuite;
extern SDLTest_TestSuiteReference intrinsicsTestSuite;
extern SDLTest_TestSuiteReference joystickTestSuite;
extern SDLTest_TestSuiteReference keyboardTestSuite;
extern SDLTest_TestSuiteReference logTestSuite;
extern SDLTest_TestSuiteReference mainTestSuite;
extern SDLTest_TestSuiteReference mathTestSuite;
extern SDLTest_TestSuiteReference mouseTestSuite;
@ -26,11 +27,12 @@ extern SDLTest_TestSuiteReference platformTestSuite;
extern SDLTest_TestSuiteReference propertiesTestSuite;
extern SDLTest_TestSuiteReference rectTestSuite;
extern SDLTest_TestSuiteReference renderTestSuite;
extern SDLTest_TestSuiteReference rwopsTestSuite;
extern SDLTest_TestSuiteReference iostrmTestSuite;
extern SDLTest_TestSuiteReference sdltestTestSuite;
extern SDLTest_TestSuiteReference stdlibTestSuite;
extern SDLTest_TestSuiteReference subsystemsTestSuite;
extern SDLTest_TestSuiteReference surfaceTestSuite;
extern SDLTest_TestSuiteReference timeTestSuite;
extern SDLTest_TestSuiteReference timerTestSuite;
extern SDLTest_TestSuiteReference videoTestSuite;

View File

@ -22,6 +22,15 @@
#include "testautomation_suites.h"
#include "testautomation_images.h"
#define CHECK_FUNC(FUNC, PARAMS) \
{ \
int result = FUNC PARAMS; \
if (result != 0) { \
SDLTest_AssertCheck(result == 0, "Validate result from %s, expected: 0, got: %i, %s", #FUNC, result, SDL_GetError()); \
} \
}
/* ================= Test Case Implementation ================== */
/* Shared test surface */
@ -146,13 +155,13 @@ static void testBlitBlendMode(int mode)
for (i = 0; i <= ni; i += 4) {
if (mode == -2) {
/* Set color mod. */
ret = SDL_SetSurfaceColorMod(face, (255 / nj) * j, (255 / ni) * i, (255 / nj) * j);
ret = SDL_SetSurfaceColorMod(face, (Uint8)((255 / nj) * j), (Uint8)((255 / ni) * i), (Uint8)((255 / nj) * j));
if (ret != 0) {
checkFailCount2++;
}
} else if (mode == -3) {
/* Set alpha mod. */
ret = SDL_SetSurfaceAlphaMod(face, (255 / ni) * i);
ret = SDL_SetSurfaceAlphaMod(face, (Uint8)((255 / ni) * i));
if (ret != 0) {
checkFailCount3++;
}
@ -327,10 +336,12 @@ static int surface_testCompleteSurfaceConversion(void *arg)
SDL_PIXELFORMAT_RGBA8888,
SDL_PIXELFORMAT_ABGR8888,
SDL_PIXELFORMAT_BGRA8888,
#if 0 /* We aren't testing HDR10 colorspace conversion */
SDL_PIXELFORMAT_XRGB2101010,
SDL_PIXELFORMAT_XBGR2101010,
SDL_PIXELFORMAT_ARGB2101010,
SDL_PIXELFORMAT_ABGR2101010,
#endif
};
SDL_Surface *face = NULL, *cvt1, *cvt2, *final;
SDL_PixelFormat *fmt1, *fmt2;
@ -353,17 +364,22 @@ static int surface_testCompleteSurfaceConversion(void *arg)
for (i = 0; i < SDL_arraysize(pixel_formats); ++i) {
for (j = 0; j < SDL_arraysize(pixel_formats); ++j) {
fmt1 = SDL_CreatePixelFormat(pixel_formats[i]);
SDL_assert(fmt1 != NULL);
SDLTest_AssertCheck(fmt1 != NULL, "SDL_CreatePixelFormat(%s[0x%08" SDL_PRIx32 "]) should return a non-null pixel format",
SDL_GetPixelFormatName(pixel_formats[i]), pixel_formats[i]);
cvt1 = SDL_ConvertSurface(face, fmt1);
SDL_assert(cvt1 != NULL);
SDLTest_AssertCheck(cvt1 != NULL, "SDL_ConvertSurface(..., %s[0x%08" SDL_PRIx32 "]) should return a non-null surface",
SDL_GetPixelFormatName(pixel_formats[i]), pixel_formats[i]);
fmt2 = SDL_CreatePixelFormat(pixel_formats[j]);
SDL_assert(fmt1 != NULL);
SDLTest_AssertCheck(fmt2 != NULL, "SDL_CreatePixelFormat(%s[0x%08" SDL_PRIx32 "]) should return a non-null pixel format",
SDL_GetPixelFormatName(pixel_formats[i]), pixel_formats[i]);
cvt2 = SDL_ConvertSurface(cvt1, fmt2);
SDL_assert(cvt2 != NULL);
SDLTest_AssertCheck(cvt2 != NULL, "SDL_ConvertSurface(..., %s[0x%08" SDL_PRIx32 "]) should return a non-null surface",
SDL_GetPixelFormatName(pixel_formats[i]), pixel_formats[i]);
if (fmt1->BytesPerPixel == face->format->BytesPerPixel &&
fmt2->BytesPerPixel == face->format->BytesPerPixel &&
if (fmt1 && fmt2 &&
fmt1->bytes_per_pixel == face->format->bytes_per_pixel &&
fmt2->bytes_per_pixel == face->format->bytes_per_pixel &&
(fmt1->Amask != 0) == (face->format->Amask != 0) &&
(fmt2->Amask != 0) == (face->format->Amask != 0)) {
final = SDL_ConvertSurface(cvt2, face->format);
@ -757,19 +773,29 @@ static int surface_testOverflow(void *arg)
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
if (sizeof(size_t) == 4 && sizeof(int) >= 4) {
expectedError = "Out of memory";
surface = SDL_CreateSurface(SDL_MAX_SINT32, 1, SDL_PIXELFORMAT_INDEX8);
SDLTest_AssertCheck(surface == NULL, "Should detect overflow in width + alignment");
SDL_ClearError();
expectedError = "aligning pitch would overflow";
/* 0x5555'5555 * 3bpp = 0xffff'ffff which fits in size_t, but adding
* alignment padding makes it overflow */
surface = SDL_CreateSurface(0x55555555, 1, SDL_PIXELFORMAT_RGB24);
SDLTest_AssertCheck(surface == NULL, "Should detect overflow in pitch + alignment");
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
surface = SDL_CreateSurface(SDL_MAX_SINT32 / 2, 1, SDL_PIXELFORMAT_ARGB8888);
SDL_ClearError();
expectedError = "width * bpp would overflow";
/* 0x4000'0000 * 4bpp = 0x1'0000'0000 which (just) overflows */
surface = SDL_CreateSurface(0x40000000, 1, SDL_PIXELFORMAT_ARGB8888);
SDLTest_AssertCheck(surface == NULL, "Should detect overflow in width * bytes per pixel");
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
SDL_ClearError();
expectedError = "height * pitch would overflow";
surface = SDL_CreateSurface((1 << 29) - 1, (1 << 29) - 1, SDL_PIXELFORMAT_INDEX8);
SDLTest_AssertCheck(surface == NULL, "Should detect overflow in width * height");
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
SDL_ClearError();
expectedError = "height * pitch would overflow";
surface = SDL_CreateSurface((1 << 15) + 1, (1 << 15) + 1, SDL_PIXELFORMAT_ARGB8888);
SDLTest_AssertCheck(surface == NULL, "Should detect overflow in width * height * bytes per pixel");
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
@ -781,6 +807,54 @@ static int surface_testOverflow(void *arg)
return TEST_COMPLETED;
}
static int surface_testFlip(void *arg)
{
SDL_Surface *surface;
Uint8 *pixels;
int offset;
const char *expectedError;
surface = SDL_CreateSurface(3, 3, SDL_PIXELFORMAT_RGB24);
SDLTest_AssertCheck(surface != NULL, "SDL_CreateSurface()");
SDL_ClearError();
expectedError = "Parameter 'surface' is invalid";
SDL_FlipSurface(NULL, SDL_FLIP_HORIZONTAL);
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
SDL_ClearError();
expectedError = "Parameter 'flip' is invalid";
SDL_FlipSurface(surface, SDL_FLIP_NONE);
SDLTest_AssertCheck(SDL_strcmp(SDL_GetError(), expectedError) == 0,
"Expected \"%s\", got \"%s\"", expectedError, SDL_GetError());
pixels = (Uint8 *)surface->pixels;
*pixels = 0xFF;
offset = 0;
SDLTest_AssertPass("Call to SDL_FlipSurface(surface, SDL_FLIP_VERTICAL)");
CHECK_FUNC(SDL_FlipSurface, (surface, SDL_FLIP_VERTICAL));
SDLTest_AssertCheck(pixels[offset] == 0x00,
"Expected pixels[%d] == 0x00 got 0x%.2X", offset, pixels[offset]);
offset = 2 * surface->pitch;
SDLTest_AssertCheck(pixels[offset] == 0xFF,
"Expected pixels[%d] == 0xFF got 0x%.2X", offset, pixels[offset]);
SDLTest_AssertPass("Call to SDL_FlipSurface(surface, SDL_FLIP_HORIZONTAL)");
CHECK_FUNC(SDL_FlipSurface, (surface, SDL_FLIP_HORIZONTAL));
SDLTest_AssertCheck(pixels[offset] == 0x00,
"Expected pixels[%d] == 0x00 got 0x%.2X", offset, pixels[offset]);
offset += (surface->w - 1) * surface->format->bytes_per_pixel;
SDLTest_AssertCheck(pixels[offset] == 0xFF,
"Expected pixels[%d] == 0xFF got 0x%.2X", offset, pixels[offset]);
SDL_DestroySurface(surface);
return TEST_COMPLETED;
}
/* ================= Test References ================== */
/* Surface test cases */
@ -839,11 +913,15 @@ static const SDLTest_TestCaseReference surfaceTestOverflow = {
surface_testOverflow, "surface_testOverflow", "Test overflow detection.", TEST_ENABLED
};
static const SDLTest_TestCaseReference surfaceTestFlip = {
surface_testFlip, "surface_testFlip", "Test surface flipping.", TEST_ENABLED
};
/* Sequence of Surface test cases */
static const SDLTest_TestCaseReference *surfaceTests[] = {
&surfaceTest1, &surfaceTest2, &surfaceTest3, &surfaceTest4, &surfaceTest5,
&surfaceTest6, &surfaceTest7, &surfaceTest8, &surfaceTest9, &surfaceTest10,
&surfaceTest11, &surfaceTest12, &surfaceTestOverflow, NULL
&surfaceTest11, &surfaceTest12, &surfaceTestOverflow, &surfaceTestFlip, NULL
};
/* Surface test suite (global) */

View File

@ -0,0 +1,201 @@
/**
* Timer test suite
*/
#include "testautomation_suites.h"
#include <SDL3/SDL.h>
#include <SDL3/SDL_test.h>
/* 2000-01-01T16:35:42 UTC */
#define JAN_1_2000_NS SDL_SECONDS_TO_NS(946744542)
/* Test case functions */
/**
* Call to SDL_GetRealtimeClock
*/
static int time_getRealtimeClock(void *arg)
{
int result;
SDL_Time ticks;
result = SDL_GetCurrentTime(&ticks);
SDLTest_AssertPass("Call to SDL_GetRealtimeClockTicks()");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
return TEST_COMPLETED;
}
/**
* Test bidirectional SDL_DateTime conversions.
*/
static int time_dateTimeConversion(void *arg)
{
int result;
SDL_Time ticks[2];
SDL_DateTime dt;
ticks[0] = JAN_1_2000_NS;
result = SDL_TimeToDateTime(ticks[0], &dt, SDL_FALSE);
SDLTest_AssertPass("Call to SDL_TimeToUTCDateTime()");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
SDLTest_AssertCheck(dt.year == 2000, "Check year value, expected 2000, got: %i", dt.year);
SDLTest_AssertCheck(dt.month == 1, "Check month value, expected 1, got: %i", dt.month);
SDLTest_AssertCheck(dt.day == 1, "Check day value, expected 1, got: %i", dt.day);
SDLTest_AssertCheck(dt.hour == 16, "Check hour value, expected 16, got: %i", dt.hour);
SDLTest_AssertCheck(dt.minute == 35, "Check hour value, expected 35, got: %i", dt.minute);
SDLTest_AssertCheck(dt.second == 42, "Check hour value, expected 42, got: %i", dt.second);
result = SDL_DateTimeToTime(&dt, &ticks[1]);
SDLTest_AssertPass("Call to SDL_DateTimeToTime()");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
result = ticks[0] == ticks[1];
SDLTest_AssertCheck(result, "Check that original and converted SDL_Time values match: ticks0 = %" SDL_PRIs64 ", ticks1 = %" SDL_PRIs64, ticks[0], ticks[1]);
/* Local time unknown, so just verify success. */
result = SDL_TimeToDateTime(ticks[0], &dt, SDL_TRUE);
SDLTest_AssertPass("Call to SDL_TimeToLocalDateTime()");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
/* Convert back and verify result. */
result = SDL_DateTimeToTime(&dt, &ticks[1]);
SDLTest_AssertPass("Call to SDL_DateTimeToTime()");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
result = ticks[0] == ticks[1];
SDLTest_AssertCheck(result, "Check that original and converted SDL_Time values match: ticks0 = %" SDL_PRIs64 ", ticks1 = %" SDL_PRIs64, ticks[0], ticks[1]);
/* Advance the time one day. */
++dt.day;
if (dt.day > SDL_GetDaysInMonth(dt.year, dt.month)) {
dt.day = 1;
++dt.month;
}
if (dt.month > 12) {
dt.month = 1;
++dt.year;
}
result = SDL_DateTimeToTime(&dt, &ticks[1]);
SDLTest_AssertPass("Call to SDL_DateTimeToTime() (one day advanced)");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
result = (ticks[0] + (Sint64)SDL_SECONDS_TO_NS(86400)) == ticks[1];
SDLTest_AssertCheck(result, "Check that the difference is exactly 86400 seconds, got: %" SDL_PRIs64, (Sint64)SDL_NS_TO_SECONDS(ticks[1] - ticks[0]));
/* Check dates that overflow/underflow an SDL_Time */
dt.year = 2400;
dt.month = 1;
dt.day = 1;
result = SDL_DateTimeToTime(&dt, &ticks[0]);
SDLTest_AssertPass("Call to SDL_DateTimeToTime() (year overflows an SDL_Time)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
dt.year = 1601;
result = SDL_DateTimeToTime(&dt, &ticks[0]);
SDLTest_AssertPass("Call to SDL_DateTimeToTime() (year underflows an SDL_Time)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
return TEST_COMPLETED;
}
/**
* Test time utility functions.
*/
static int time_dateTimeUtilities(void *arg)
{
int result;
/* Leap-year */
result = SDL_GetDaysInMonth(2000, 2);
SDLTest_AssertPass("Call to SDL_GetDaysInMonth(2000, 2)");
SDLTest_AssertCheck(result == 29, "Check result value, expected 29, got: %i", result);
result = SDL_GetDaysInMonth(2001, 2);
SDLTest_AssertPass("Call to SDL_GetDaysInMonth(2001, 2)");
SDLTest_AssertCheck(result == 28, "Check result value, expected 28, got: %i", result);
result = SDL_GetDaysInMonth(2001, 13);
SDLTest_AssertPass("Call to SDL_GetDaysInMonth(2001, 13)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
result = SDL_GetDaysInMonth(2001, -1);
SDLTest_AssertPass("Call to SDL_GetDaysInMonth(2001, 13)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
/* 2000-02-29 was a Tuesday */
result = SDL_GetDayOfWeek(2000, 2, 29);
SDLTest_AssertPass("Call to SDL_GetDayOfWeek(2000, 2, 29)");
SDLTest_AssertCheck(result == 2, "Check result value, expected %i, got: %i", 2, result);
/* Nonexistent day */
result = SDL_GetDayOfWeek(2001, 2, 29);
SDLTest_AssertPass("Call to SDL_GetDayOfWeek(2001, 2, 29)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
result = SDL_GetDayOfYear(2000, 1, 1);
SDLTest_AssertPass("Call to SDL_GetDayOfWeek(2001, 1, 1)");
SDLTest_AssertCheck(result == 0, "Check result value, expected 0, got: %i", result);
/* Leap-year */
result = SDL_GetDayOfYear(2000, 12, 31);
SDLTest_AssertPass("Call to SDL_GetDayOfYear(2000, 12, 31)");
SDLTest_AssertCheck(result == 365, "Check result value, expected 365, got: %i", result);
result = SDL_GetDayOfYear(2001, 12, 31);
SDLTest_AssertPass("Call to SDL_GetDayOfYear(2000, 12, 31)");
SDLTest_AssertCheck(result == 364, "Check result value, expected 364, got: %i", result);
/* Nonexistent day */
result = SDL_GetDayOfYear(2001, 2, 29);
SDLTest_AssertPass("Call to SDL_GetDayOfYear(2001, 2, 29)");
SDLTest_AssertCheck(result == -1, "Check result value, expected -1, got: %i", result);
/* Test Win32 time conversion */
Uint64 wintime = 11644473600LL * 10000000LL; /* The epoch */
SDL_Time ticks = SDL_TimeFromWindows((Uint32)(wintime & 0xFFFFFFFF), (Uint32)(wintime >> 32));
SDLTest_AssertPass("Call to SDL_TimeFromWindows()");
SDLTest_AssertCheck(ticks == 0, "Check result value, expected 0, got: %" SDL_PRIs64, ticks);
/* Out of range times should be clamped instead of rolling over */
wintime = 0;
ticks = SDL_TimeFromWindows((Uint32)(wintime & 0xFFFFFFFF), (Uint32)(wintime >> 32));
SDLTest_AssertPass("Call to SDL_TimeFromWindows()");
SDLTest_AssertCheck(ticks < 0 && ticks >= SDL_MIN_TIME, "Check result value, expected <0 && >=%" SDL_PRIs64 ", got: %" SDL_PRIs64, SDL_MIN_TIME, ticks);
wintime = 0xFFFFFFFFFFFFFFFFULL;
ticks = SDL_TimeFromWindows((Uint32)(wintime & 0xFFFFFFFF), (Uint32)(wintime >> 32));
SDLTest_AssertPass("Call to SDL_TimeFromWindows()");
SDLTest_AssertCheck(ticks > 0 && ticks <= SDL_MAX_TIME, "Check result value, expected >0 && <=%" SDL_PRIs64 ", got: %" SDL_PRIs64, SDL_MAX_TIME, ticks);
return TEST_COMPLETED;
}
/* ================= Test References ================== */
/* Time test cases */
static const SDLTest_TestCaseReference timeTest1 = {
(SDLTest_TestCaseFp)time_getRealtimeClock, "time_getRealtimeClock", "Call to SDL_GetRealtimeClockTicks", TEST_ENABLED
};
static const SDLTest_TestCaseReference timeTest2 = {
(SDLTest_TestCaseFp)time_dateTimeConversion, "time_dateTimeConversion", "Call to SDL_TimeToDateTime/SDL_DateTimeToTime", TEST_ENABLED
};
static const SDLTest_TestCaseReference timeTest3 = {
(SDLTest_TestCaseFp)time_dateTimeUtilities, "time_dateTimeUtilities", "Call to SDL_TimeToDateTime/SDL_DateTimeToTime", TEST_ENABLED
};
/* Sequence of Timer test cases */
static const SDLTest_TestCaseReference *timeTests[] = {
&timeTest1, &timeTest2, &timeTest3, NULL
};
/* Time test suite (global) */
SDLTest_TestSuiteReference timeTestSuite = {
"Time",
NULL,
timeTests,
NULL
};

View File

@ -131,7 +131,7 @@ static int timer_addRemoveTimer(void *arg)
/* Set timer with a long delay */
id = SDL_AddTimer(10000, timerTestCallback, NULL);
SDLTest_AssertPass("Call to SDL_AddTimer(10000,...)");
SDLTest_AssertCheck(id > 0, "Check result value, expected: >0, got: %d", id);
SDLTest_AssertCheck(id > 0, "Check result value, expected: >0, got: %" SDL_PRIu32, id);
/* Remove timer again and check that callback was not called */
result = SDL_RemoveTimer(id);
@ -153,7 +153,7 @@ static int timer_addRemoveTimer(void *arg)
/* Set timer with a short delay */
id = SDL_AddTimer(10, timerTestCallback, (void *)&param);
SDLTest_AssertPass("Call to SDL_AddTimer(10, param)");
SDLTest_AssertCheck(id > 0, "Check result value, expected: >0, got: %d", id);
SDLTest_AssertCheck(id > 0, "Check result value, expected: >0, got: %" SDL_PRIu32, id);
/* Wait to let timer trigger callback */
SDL_Delay(100);

View File

@ -15,7 +15,7 @@ static SDL_Window *createVideoSuiteTestWindow(const char *title)
SDL_Window *window;
SDL_Event event;
int w, h;
Uint32 flags;
SDL_WindowFlags flags;
SDL_bool needs_renderer = SDL_FALSE;
SDL_bool needs_events_pumped = SDL_FALSE;
@ -197,7 +197,7 @@ static int video_createWindowVariousFlags(void *arg)
const char *title = "video_createWindowVariousFlags Test Window";
int w, h;
int fVariation;
Uint32 flags;
SDL_WindowFlags flags;
/* Standard window */
w = SDLTest_RandomIntegerInRange(320, 1024);
@ -269,7 +269,7 @@ static int video_getWindowFlags(void *arg)
{
SDL_Window *window;
const char *title = "video_getWindowFlags Test Window";
Uint32 flags;
SDL_WindowFlags flags;
Uint32 actualFlags;
/* Reliable flag set always set in test window */
@ -336,7 +336,7 @@ static int video_getClosestDisplayModeCurrentResolution(void *arg)
/* Make calls for each display */
for (i = 0; displays[i]; ++i) {
SDLTest_Log("Testing against display: %" SDL_PRIu32 "", displays[i]);
SDLTest_Log("Testing against display: %" SDL_PRIu32, displays[i]);
/* Get first display mode to get a sane resolution; this should always work */
modes = SDL_GetFullscreenDisplayModes(displays[i], &num_modes);
@ -385,7 +385,7 @@ static int video_getClosestDisplayModeRandomResolution(void *arg)
/* Make calls for each display */
for (i = 0; displays[i]; ++i) {
SDLTest_Log("Testing against display: %" SDL_PRIu32 "", displays[i]);
SDLTest_Log("Testing against display: %" SDL_PRIu32, displays[i]);
for (variation = 0; variation < 16; variation++) {
@ -490,9 +490,6 @@ static void setAndCheckWindowMouseGrabState(SDL_Window *window, SDL_bool desired
SDLTest_AssertCheck(
SDL_GetGrabbedWindow() == window,
"Grabbed window should be to our window");
SDLTest_AssertCheck(
SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
SDLTest_AssertCheck(
SDL_GetWindowFlags(window) & SDL_WINDOW_MOUSE_GRABBED,
"SDL_WINDOW_MOUSE_GRABBED should be set");
@ -525,9 +522,6 @@ static void setAndCheckWindowKeyboardGrabState(SDL_Window *window, SDL_bool desi
SDLTest_AssertCheck(
SDL_GetGrabbedWindow() == window,
"Grabbed window should be set to our window");
SDLTest_AssertCheck(
SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
SDLTest_AssertCheck(
SDL_GetWindowFlags(window) & SDL_WINDOW_KEYBOARD_GRABBED,
"SDL_WINDOW_KEYBOARD_GRABBED should be set");
@ -541,8 +535,10 @@ static void setAndCheckWindowKeyboardGrabState(SDL_Window *window, SDL_bool desi
/**
* Tests keyboard and mouse grab support
*
* \sa SDL_GetWindowGrab
* \sa SDL_SetWindowGrab
* \sa SDL_GetWindowMouseGrab
* \sa SDL_GetWindowKeyboardGrab
* \sa SDL_SetWindowMouseGrab
* \sa SDL_SetWindowKeyboardGrab
*/
static int video_getSetWindowGrab(void *arg)
{
@ -588,8 +584,6 @@ static int video_getSetWindowGrab(void *arg)
/* F */
setAndCheckWindowKeyboardGrabState(window, SDL_FALSE);
setAndCheckWindowMouseGrabState(window, SDL_FALSE);
SDLTest_AssertCheck(!SDL_GetWindowGrab(window),
"SDL_GetWindowGrab should return SDL_FALSE");
SDLTest_AssertCheck(SDL_GetGrabbedWindow() == NULL,
"Expected NULL grabbed window");
@ -602,92 +596,47 @@ static int video_getSetWindowGrab(void *arg)
/* F --> T */
setAndCheckWindowMouseGrabState(window, SDL_TRUE);
setAndCheckWindowKeyboardGrabState(window, SDL_TRUE);
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
/* T --> T */
setAndCheckWindowKeyboardGrabState(window, SDL_TRUE);
setAndCheckWindowMouseGrabState(window, SDL_TRUE);
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
/* M: T --> F */
/* K: T --> T */
setAndCheckWindowKeyboardGrabState(window, SDL_TRUE);
setAndCheckWindowMouseGrabState(window, SDL_FALSE);
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
/* M: F --> T */
/* K: T --> F */
setAndCheckWindowMouseGrabState(window, SDL_TRUE);
setAndCheckWindowKeyboardGrabState(window, SDL_FALSE);
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
/* M: T --> F */
/* K: F --> F */
setAndCheckWindowMouseGrabState(window, SDL_FALSE);
setAndCheckWindowKeyboardGrabState(window, SDL_FALSE);
SDLTest_AssertCheck(!SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_FALSE");
SDLTest_AssertCheck(SDL_GetGrabbedWindow() == NULL,
"Expected NULL grabbed window");
/* Using the older SDL_SetWindowGrab API should only grab mouse by default */
SDL_SetWindowGrab(window, SDL_TRUE);
SDLTest_AssertPass("Call to SDL_SetWindowGrab(SDL_TRUE)");
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
SDLTest_AssertCheck(SDL_GetWindowMouseGrab(window),
"SDL_GetWindowMouseGrab() should return SDL_TRUE");
SDLTest_AssertCheck(!SDL_GetWindowKeyboardGrab(window),
"SDL_GetWindowKeyboardGrab() should return SDL_FALSE");
SDL_SetWindowGrab(window, SDL_FALSE);
SDLTest_AssertCheck(!SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_FALSE");
SDLTest_AssertCheck(!SDL_GetWindowMouseGrab(window),
"SDL_GetWindowMouseGrab() should return SDL_FALSE");
SDLTest_AssertCheck(!SDL_GetWindowKeyboardGrab(window),
"SDL_GetWindowKeyboardGrab() should return SDL_FALSE");
/* Now test with SDL_HINT_GRAB_KEYBOARD set. We should get keyboard grab now. */
SDL_SetHint(SDL_HINT_GRAB_KEYBOARD, "1");
SDL_SetWindowGrab(window, SDL_TRUE);
SDLTest_AssertPass("Call to SDL_SetWindowGrab(SDL_TRUE)");
SDLTest_AssertCheck(SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_TRUE");
SDLTest_AssertCheck(SDL_GetWindowMouseGrab(window),
"SDL_GetWindowMouseGrab() should return SDL_TRUE");
SDLTest_AssertCheck(SDL_GetWindowKeyboardGrab(window),
"SDL_GetWindowKeyboardGrab() should return SDL_TRUE");
SDL_SetWindowGrab(window, SDL_FALSE);
SDLTest_AssertCheck(!SDL_GetWindowGrab(window),
"SDL_GetWindowGrab() should return SDL_FALSE");
SDLTest_AssertCheck(!SDL_GetWindowMouseGrab(window),
"SDL_GetWindowMouseGrab() should return SDL_FALSE");
SDLTest_AssertCheck(!SDL_GetWindowKeyboardGrab(window),
"SDL_GetWindowKeyboardGrab() should return SDL_FALSE");
/* Negative tests */
SDL_GetWindowGrab(NULL);
SDLTest_AssertPass("Call to SDL_GetWindowGrab(window=NULL)");
SDL_GetWindowMouseGrab(NULL);
SDLTest_AssertPass("Call to SDL_GetWindowMouseGrab(window=NULL)");
checkInvalidWindowError();
SDL_GetWindowKeyboardGrab(NULL);
SDLTest_AssertPass("Call to SDL_GetWindowKeyboardGrab(window=NULL)");
checkInvalidWindowError();
SDL_SetWindowGrab(NULL, SDL_FALSE);
SDLTest_AssertPass("Call to SDL_SetWindowGrab(window=NULL,SDL_FALSE)");
SDL_SetWindowMouseGrab(NULL, SDL_FALSE);
SDLTest_AssertPass("Call to SDL_SetWindowMouseGrab(window=NULL,SDL_FALSE)");
checkInvalidWindowError();
SDL_SetWindowKeyboardGrab(NULL, SDL_FALSE);
SDLTest_AssertPass("Call to SDL_SetWindowKeyboardGrab(window=NULL,SDL_FALSE)");
checkInvalidWindowError();
SDL_SetWindowGrab(NULL, SDL_TRUE);
SDLTest_AssertPass("Call to SDL_SetWindowGrab(window=NULL,SDL_TRUE)");
SDL_SetWindowMouseGrab(NULL, SDL_TRUE);
SDLTest_AssertPass("Call to SDL_SetWindowMouseGrab(window=NULL,SDL_TRUE)");
checkInvalidWindowError();
SDL_SetWindowKeyboardGrab(NULL, SDL_TRUE);
@ -1682,13 +1631,11 @@ static int video_getSetWindowData(void *arg)
result = (char *)SDL_GetProperty(SDL_GetWindowProperties(window), NULL, NULL);
SDLTest_AssertPass("Call to SDL_GetWindowData(name=NULL)");
SDLTest_AssertCheck(result == NULL, "Validate that result is NULL");
checkInvalidParameterError();
/* Get data with empty name */
result = (char *)SDL_GetProperty(SDL_GetWindowProperties(window), "", NULL);
SDLTest_AssertPass("Call to SDL_GetWindowData(name='')");
SDLTest_AssertCheck(result == NULL, "Validate that result is NULL");
checkInvalidParameterError();
/* Clean up */
destroyVideoSuiteTestWindow(window);
@ -1750,7 +1697,7 @@ static int video_setWindowCenteredOnDisplay(void *arg)
int expectedX = 0, expectedY = 0;
int currentDisplay;
int expectedDisplay;
SDL_Rect expectedDisplayRect;
SDL_Rect expectedDisplayRect, expectedFullscreenRect;
SDL_PropertiesID props;
/* xVariation is the display we start on */
@ -1764,12 +1711,12 @@ static int video_setWindowCenteredOnDisplay(void *arg)
expectedY = (expectedDisplayRect.y + ((expectedDisplayRect.h - h) / 2));
props = SDL_CreateProperties();
SDL_SetStringProperty(props, SDL_PROPERTY_WINDOW_CREATE_TITLE_STRING, title);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_X_NUMBER, x);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_Y_NUMBER, y);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_WIDTH_NUMBER, w);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_HEIGHT_NUMBER, h);
SDL_SetBooleanProperty(props, SDL_PROPERTY_WINDOW_CREATE_BORDERLESS_BOOLEAN, SDL_TRUE);
SDL_SetStringProperty(props, SDL_PROP_WINDOW_CREATE_TITLE_STRING, title);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_X_NUMBER, x);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_Y_NUMBER, y);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_WIDTH_NUMBER, w);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_HEIGHT_NUMBER, h);
SDL_SetBooleanProperty(props, SDL_PROP_WINDOW_CREATE_BORDERLESS_BOOLEAN, SDL_TRUE);
window = SDL_CreateWindowWithProperties(props);
SDL_DestroyProperties(props);
SDLTest_AssertPass("Call to SDL_CreateWindow('Title',%d,%d,%d,%d,SHOWN)", x, y, w, h);
@ -1826,16 +1773,24 @@ static int video_setWindowCenteredOnDisplay(void *arg)
SDL_GetWindowSize(window, &currentW, &currentH);
SDL_GetWindowPosition(window, &currentX, &currentY);
/* Get the expected fullscreen rect.
* This needs to be queried after window creation and positioning as some drivers can alter the
* usable bounds based on the window scaling mode.
*/
result = SDL_GetDisplayBounds(expectedDisplay, &expectedFullscreenRect);
SDLTest_AssertPass("SDL_GetDisplayBounds()");
SDLTest_AssertCheck(result == 0, "Verify return value; expected: 0, got: %d", result);
if (!video_driver_is_wayland) {
SDLTest_AssertCheck(currentDisplay == expectedDisplay, "Validate display ID (current: %d, expected: %d)", currentDisplay, expectedDisplay);
} else {
SDLTest_Log("Skipping display ID validation: Wayland driver does not support window positioning");
}
SDLTest_AssertCheck(currentW == expectedDisplayRect.w, "Validate width (current: %d, expected: %d)", currentW, expectedDisplayRect.w);
SDLTest_AssertCheck(currentH == expectedDisplayRect.h, "Validate height (current: %d, expected: %d)", currentH, expectedDisplayRect.h);
SDLTest_AssertCheck(currentW == expectedFullscreenRect.w, "Validate width (current: %d, expected: %d)", currentW, expectedFullscreenRect.w);
SDLTest_AssertCheck(currentH == expectedFullscreenRect.h, "Validate height (current: %d, expected: %d)", currentH, expectedFullscreenRect.h);
if (!video_driver_is_wayland) {
SDLTest_AssertCheck(currentX == expectedDisplayRect.x, "Validate x (current: %d, expected: %d)", currentX, expectedDisplayRect.x);
SDLTest_AssertCheck(currentY == expectedDisplayRect.y, "Validate y (current: %d, expected: %d)", currentY, expectedDisplayRect.y);
SDLTest_AssertCheck(currentX == expectedFullscreenRect.x, "Validate x (current: %d, expected: %d)", currentX, expectedFullscreenRect.x);
SDLTest_AssertCheck(currentY == expectedFullscreenRect.y, "Validate y (current: %d, expected: %d)", currentY, expectedFullscreenRect.y);
} else {
SDLTest_Log("Skipping window position validation: Wayland driver does not support window positioning");
}
@ -1925,14 +1880,14 @@ static int video_getSetWindowState(void *arg)
SDL_Window *window;
int result;
SDL_Rect display;
Uint32 flags;
SDL_WindowFlags flags;
int windowedX, windowedY;
int currentX, currentY;
int desiredX = 0, desiredY = 0;
int windowedW, windowedH;
int currentW, currentH;
int desiredW = 0, desiredH = 0;
Uint32 skipFlags = 0;
SDL_WindowFlags skipFlags = 0;
const SDL_bool restoreHint = SDL_GetHintBoolean("SDL_BORDERLESS_RESIZABLE_STYLE", SDL_TRUE);
const SDL_bool skipPos = SDL_strcmp(SDL_GetCurrentVideoDriver(), "wayland") == 0;
@ -2311,7 +2266,7 @@ static const SDLTest_TestCaseReference videoTest9 = {
};
static const SDLTest_TestCaseReference videoTest10 = {
(SDLTest_TestCaseFp)video_getSetWindowGrab, "video_getSetWindowGrab", "Checks SDL_GetWindowGrab and SDL_SetWindowGrab positive and negative cases", TEST_ENABLED
(SDLTest_TestCaseFp)video_getSetWindowGrab, "video_getSetWindowGrab", "Checks input grab positive and negative cases", TEST_ENABLED
};
static const SDLTest_TestCaseReference videoTest11 = {

274
external/sdl/SDL/test/testcamera.c vendored Normal file
View File

@ -0,0 +1,274 @@
/*
Copyright (C) 1997-2024 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.
*/
#define SDL_MAIN_USE_CALLBACKS 1
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
static SDL_Window *window = NULL;
static SDL_Renderer *renderer = NULL;
static SDLTest_CommonState *state = NULL;
static SDL_Camera *camera = NULL;
static SDL_CameraSpec spec;
static SDL_Texture *texture = NULL;
static SDL_bool texture_updated = SDL_FALSE;
static SDL_Surface *frame_current = NULL;
static SDL_CameraDeviceID front_camera = 0;
static SDL_CameraDeviceID back_camera = 0;
int SDL_AppInit(void **appstate, int argc, char *argv[])
{
int devcount = 0;
int i;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, SDL_INIT_VIDEO | SDL_INIT_CAMERA);
if (!state) {
return -1;
}
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
if (!SDLTest_CommonDefaultArgs(state, argc, argv)) {
return -1;
}
state->num_windows = 1;
/* Load the SDL library */
if (!SDLTest_CommonInit(state)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't initialize SDL: %s", SDL_GetError());
return -1;
}
window = state->windows[0];
if (!window) {
SDL_Log("Couldn't create window: %s", SDL_GetError());
return -1;
}
SDL_LogSetAllPriority(SDL_LOG_PRIORITY_VERBOSE);
renderer = state->renderers[0];
if (!renderer) {
/* SDL_Log("Couldn't create renderer: %s", SDL_GetError()); */
return -1;
}
SDL_CameraDeviceID *devices = SDL_GetCameraDevices(&devcount);
if (!devices) {
SDL_Log("SDL_GetCameraDevices failed: %s", SDL_GetError());
return -1;
}
SDL_Log("Saw %d camera devices.", devcount);
for (i = 0; i < devcount; i++) {
const SDL_CameraDeviceID device = devices[i];
char *name = SDL_GetCameraDeviceName(device);
const SDL_CameraPosition position = SDL_GetCameraDevicePosition(device);
const char *posstr = "";
if (position == SDL_CAMERA_POSITION_FRONT_FACING) {
front_camera = device;
posstr = "[front-facing] ";
} else if (position == SDL_CAMERA_POSITION_BACK_FACING) {
back_camera = device;
posstr = "[back-facing] ";
}
SDL_Log(" - Camera #%d: %s %s", i, posstr, name);
SDL_free(name);
}
const SDL_CameraDeviceID devid = front_camera ? front_camera : devices[0]; /* no front-facing? just take the first one. */
SDL_free(devices);
if (!devid) {
SDL_Log("No cameras available?");
return -1;
}
SDL_CameraSpec *pspec = NULL;
#if 0 /* just for edge-case testing purposes, ignore. */
pspec = &spec;
spec.width = 100 /*1280 * 2*/;
spec.height = 100 /*720 * 2*/;
spec.format = SDL_PIXELFORMAT_YUY2 /*SDL_PIXELFORMAT_RGBA8888*/;
#endif
camera = SDL_OpenCameraDevice(devid, pspec);
if (!camera) {
SDL_Log("Failed to open camera device: %s", SDL_GetError());
return -1;
}
return 0; /* start the main app loop. */
}
static int FlipCamera(void)
{
static Uint64 last_flip = 0;
if ((SDL_GetTicks() - last_flip) < 3000) { /* must wait at least 3 seconds between flips. */
return 0;
}
if (camera) {
const SDL_CameraDeviceID current = SDL_GetCameraInstanceID(camera);
SDL_CameraDeviceID nextcam = 0;
if (current == front_camera) {
nextcam = back_camera;
} else if (current == back_camera) {
nextcam = front_camera;
}
if (nextcam) {
SDL_Log("Flip camera!");
if (frame_current) {
SDL_ReleaseCameraFrame(camera, frame_current);
frame_current = NULL;
}
SDL_CloseCamera(camera);
if (texture) {
SDL_DestroyTexture(texture);
texture = NULL; /* will rebuild when new camera is approved. */
}
camera = SDL_OpenCameraDevice(nextcam, NULL);
if (!camera) {
SDL_Log("Failed to open camera device: %s", SDL_GetError());
return -1;
}
last_flip = SDL_GetTicks();
}
}
return 0;
}
int SDL_AppEvent(void *appstate, const SDL_Event *event)
{
switch (event->type) {
case SDL_EVENT_KEY_DOWN: {
const SDL_Keycode sym = event->key.keysym.sym;
if (sym == SDLK_ESCAPE || sym == SDLK_AC_BACK) {
SDL_Log("Key : Escape!");
return 1;
} else if (sym == SDLK_SPACE) {
FlipCamera();
return 0;
}
break;
}
case SDL_EVENT_MOUSE_BUTTON_DOWN:
/* !!! FIXME: only flip if clicked in the area of a "flip" icon. */
return FlipCamera();
case SDL_EVENT_QUIT:
SDL_Log("Ctlr+C : Quit!");
return 1;
case SDL_EVENT_CAMERA_DEVICE_APPROVED:
SDL_Log("Camera approved!");
if (SDL_GetCameraFormat(camera, &spec) < 0) {
SDL_Log("Couldn't get camera spec: %s", SDL_GetError());
return -1;
}
/* Create texture with appropriate format */
SDL_assert(texture == NULL);
texture = SDL_CreateTexture(renderer, spec.format, SDL_TEXTUREACCESS_STATIC, spec.width, spec.height);
if (!texture) {
SDL_Log("Couldn't create texture: %s", SDL_GetError());
return -1;
}
break;
case SDL_EVENT_CAMERA_DEVICE_DENIED:
SDL_Log("Camera denied!");
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Camera permission denied!", "User denied access to the camera!", window);
return -1;
default:
break;
}
return SDLTest_CommonEventMainCallbacks(state, event);
}
int SDL_AppIterate(void *appstate)
{
SDL_SetRenderDrawColor(renderer, 0x99, 0x99, 0x99, 255);
SDL_RenderClear(renderer);
if (texture) { /* if not NULL, camera is ready to go. */
int win_w, win_h, tw, th;
SDL_FRect d;
Uint64 timestampNS = 0;
SDL_Surface *frame_next = camera ? SDL_AcquireCameraFrame(camera, &timestampNS) : NULL;
#if 0
if (frame_next) {
SDL_Log("frame: %p at %" SDL_PRIu64, (void*)frame_next->pixels, timestampNS);
}
#endif
if (frame_next) {
if (frame_current) {
if (SDL_ReleaseCameraFrame(camera, frame_current) < 0) {
SDL_Log("err SDL_ReleaseCameraFrame: %s", SDL_GetError());
}
}
/* It's not needed to keep the frame once updated the texture is updated.
* But in case of 0-copy, it's needed to have the frame while using the texture.
*/
frame_current = frame_next;
texture_updated = SDL_FALSE;
}
/* Update SDL_Texture with last video frame (only once per new frame) */
if (frame_current && !texture_updated) {
SDL_UpdateTexture(texture, NULL, frame_current->pixels, frame_current->pitch);
texture_updated = SDL_TRUE;
}
SDL_QueryTexture(texture, NULL, NULL, &tw, &th);
SDL_GetRenderOutputSize(renderer, &win_w, &win_h);
d.x = (float) ((win_w - tw) / 2);
d.y = (float) ((win_h - th) / 2);
d.w = (float) tw;
d.h = (float) th;
SDL_RenderTexture(renderer, texture, NULL, &d);
}
/* !!! FIXME: Render a "flip" icon if front_camera and back_camera are both != 0. */
SDL_RenderPresent(renderer);
return 0; /* keep iterating. */
}
void SDL_AppQuit(void *appstate)
{
SDL_ReleaseCameraFrame(camera, frame_current);
SDL_CloseCamera(camera);
SDL_DestroyTexture(texture);
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(window);
SDLTest_CommonQuit(state);
}

651
external/sdl/SDL/test/testcolorspace.c vendored Normal file
View File

@ -0,0 +1,651 @@
/*
Copyright (C) 1997-2024 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_test.h>
#include <SDL3/SDL_main.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#define WINDOW_WIDTH 640
#define WINDOW_HEIGHT 480
#define TEXT_START_X 6.0f
#define TEXT_START_Y 6.0f
#define TEXT_LINE_ADVANCE FONT_CHARACTER_SIZE * 2
static SDL_Window *window;
static SDL_Renderer *renderer;
static const char *renderer_name;
static SDL_Colorspace colorspace = SDL_COLORSPACE_SRGB;
static const char *colorspace_name = "sRGB";
static int renderer_count = 0;
static int renderer_index = 0;
static int stage_index = 0;
static int done;
static float HDR_headroom = 1.0f;
enum
{
StageClearBackground,
StageDrawBackground,
StageBlendDrawing,
StageBlendTexture,
StageGradientDrawing,
StageGradientTexture,
StageCount
};
static void FreeRenderer(void)
{
SDLTest_CleanupTextDrawing();
SDL_DestroyRenderer(renderer);
renderer = NULL;
}
static void UpdateHDRState(void)
{
SDL_PropertiesID props;
SDL_bool HDR_enabled;
props = SDL_GetDisplayProperties(SDL_GetDisplayForWindow(window));
HDR_enabled = SDL_GetBooleanProperty(props, SDL_PROP_DISPLAY_HDR_ENABLED_BOOLEAN, SDL_FALSE);
SDL_Log("HDR %s\n", HDR_enabled ? "enabled" : "disabled");
if (HDR_enabled) {
props = SDL_GetRendererProperties(renderer);
if (SDL_GetNumberProperty(props, SDL_PROP_RENDERER_OUTPUT_COLORSPACE_NUMBER, SDL_COLORSPACE_SRGB) != SDL_COLORSPACE_SRGB_LINEAR) {
SDL_Log("Run with --colorspace linear to display HDR colors\n");
}
HDR_headroom = SDL_GetFloatProperty(props, SDL_PROP_RENDERER_HDR_HEADROOM_FLOAT, 1.0f);
}
}
static void CreateRenderer(void)
{
SDL_PropertiesID props;
SDL_RendererInfo info;
props = SDL_CreateProperties();
SDL_SetProperty(props, SDL_PROP_RENDERER_CREATE_WINDOW_POINTER, window);
SDL_SetStringProperty(props, SDL_PROP_RENDERER_CREATE_NAME_STRING, SDL_GetRenderDriver(renderer_index));
SDL_SetNumberProperty(props, SDL_PROP_RENDERER_CREATE_OUTPUT_COLORSPACE_NUMBER, colorspace);
renderer = SDL_CreateRendererWithProperties(props);
SDL_DestroyProperties(props);
if (!renderer) {
SDL_Log("Couldn't create renderer: %s\n", SDL_GetError());
return;
}
SDL_GetRendererInfo(renderer, &info);
SDL_Log("Created renderer %s\n", info.name);
renderer_name = info.name;
UpdateHDRState();
}
static void NextRenderer( void )
{
if (renderer_count <= 0) {
return;
}
++renderer_index;
if (renderer_index == renderer_count) {
renderer_index = 0;
}
FreeRenderer();
CreateRenderer();
}
static void PrevRenderer(void)
{
if (renderer_count <= 0) {
return;
}
--renderer_index;
if (renderer_index == -1) {
renderer_index += renderer_count;
}
FreeRenderer();
CreateRenderer();
}
static void NextStage(void)
{
if (StageCount <= 0) {
return;
}
++stage_index;
if (stage_index == StageCount) {
stage_index = 0;
}
}
static void PrevStage(void)
{
--stage_index;
if (stage_index == -1) {
stage_index += StageCount;
}
}
static SDL_bool ReadPixel(int x, int y, SDL_Color *c)
{
SDL_Surface *surface;
SDL_Rect r;
SDL_bool result = SDL_FALSE;
r.x = x;
r.y = y;
r.w = 1;
r.h = 1;
surface = SDL_RenderReadPixels(renderer, &r);
if (surface) {
if (SDL_ReadSurfacePixel(surface, 0, 0, &c->r, &c->g, &c->b, &c->a) == 0) {
result = SDL_TRUE;
} else {
SDL_Log("Couldn't read pixel: %s\n", SDL_GetError());
}
SDL_DestroySurface(surface);
} else {
SDL_Log("Couldn't read back pixels: %s\n", SDL_GetError());
}
return result;
}
static void DrawText(float x, float y, const char *fmt, ...)
{
char *text;
va_list ap;
va_start(ap, fmt);
SDL_vasprintf(&text, fmt, ap);
va_end(ap);
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
SDLTest_DrawString(renderer, x + 1.0f, y + 1.0f, text);
SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255);
SDLTest_DrawString(renderer, x, y, text);
SDL_free(text);
}
static void RenderClearBackground(void)
{
/* Draw a 50% gray background.
* This will be darker when using sRGB colors and lighter using linear colors
*/
SDL_SetRenderDrawColor(renderer, 128, 128, 128, 255);
SDL_RenderClear(renderer);
/* Check the renderered pixels */
SDL_Color c;
if (!ReadPixel(0, 0, &c)) {
return;
}
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Clear 50%% Gray Background");
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Background color written: 0x808080, read: 0x%.2x%.2x%.2x", c.r, c.g, c.b);
y += TEXT_LINE_ADVANCE;
if (c.r != 128) {
DrawText(x, y, "Incorrect background color, unknown reason");
y += TEXT_LINE_ADVANCE;
}
}
static void RenderDrawBackground(void)
{
/* Draw a 50% gray background.
* This will be darker when using sRGB colors and lighter using linear colors
*/
SDL_SetRenderDrawColor(renderer, 128, 128, 128, 255);
SDL_RenderFillRect(renderer, NULL);
/* Check the renderered pixels */
SDL_Color c;
if (!ReadPixel(0, 0, &c)) {
return;
}
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Draw 50%% Gray Background");
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Background color written: 0x808080, read: 0x%.2x%.2x%.2x", c.r, c.g, c.b);
y += TEXT_LINE_ADVANCE;
if (c.r != 128) {
DrawText(x, y, "Incorrect background color, unknown reason");
y += TEXT_LINE_ADVANCE;
}
}
static void RenderBlendDrawing(void)
{
SDL_Color a = { 238, 70, 166, 255 }; /* red square */
SDL_Color b = { 147, 255, 0, 255 }; /* green square */
SDL_FRect rect;
/* Draw a green square blended over a red square
* This will have different effects based on whether sRGB colorspaces and sRGB vs linear blending is used.
*/
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
SDL_RenderClear(renderer);
rect.x = WINDOW_WIDTH / 3;
rect.y = 0;
rect.w = WINDOW_WIDTH / 3;
rect.h = WINDOW_HEIGHT;
SDL_SetRenderDrawColor(renderer, a.r, a.g, a.b, a.a);
SDL_RenderFillRect(renderer, &rect);
rect.x = 0;
rect.y = WINDOW_HEIGHT / 3;
rect.w = WINDOW_WIDTH;
rect.h = WINDOW_HEIGHT / 6;
SDL_SetRenderDrawColor(renderer, b.r, b.g, b.b, b.a);
SDL_RenderFillRect(renderer, &rect);
SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_BLEND);
SDL_SetRenderDrawColor(renderer, b.r, b.g, b.b, 128);
rect.y += WINDOW_HEIGHT / 6;
SDL_RenderFillRect(renderer, &rect);
SDL_Color ar, br, cr;
if (!ReadPixel(WINDOW_WIDTH / 2, 0, &ar) ||
!ReadPixel(WINDOW_WIDTH / 2, WINDOW_HEIGHT / 3, &br) ||
!ReadPixel(WINDOW_WIDTH / 2, WINDOW_HEIGHT / 2, &cr)) {
return;
}
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Draw Blending");
y += TEXT_LINE_ADVANCE;
if (cr.r == 199 && cr.g == 193 && cr.b == 121) {
DrawText(x, y, "Correct blend color, blending in linear space");
} else if ((cr.r == 192 && cr.g == 163 && cr.b == 83) ||
(cr.r == 191 && cr.g == 162 && cr.b == 82)) {
DrawText(x, y, "Correct blend color, blending in sRGB space");
} else if (cr.r == 214 && cr.g == 156 && cr.b == 113) {
DrawText(x, y, "Incorrect blend color, blending in PQ space");
} else {
DrawText(x, y, "Incorrect blend color, unknown reason");
}
y += TEXT_LINE_ADVANCE;
}
static void RenderBlendTexture(void)
{
SDL_Color color_a = { 238, 70, 166, 255 }; /* red square */
SDL_Color color_b = { 147, 255, 0, 255 }; /* green square */
SDL_Texture *a;
SDL_Texture *b;
SDL_FRect rect;
/* Draw a green square blended over a red square
* This will have different effects based on whether sRGB colorspaces and sRGB vs linear blending is used.
*/
a = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA32, SDL_TEXTUREACCESS_STATIC, 1, 1);
SDL_UpdateTexture(a, NULL, &color_a, sizeof(color_a));
b = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA32, SDL_TEXTUREACCESS_STATIC, 1, 1);
SDL_UpdateTexture(b, NULL, &color_b, sizeof(color_b));
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
SDL_RenderClear(renderer);
rect.x = WINDOW_WIDTH / 3;
rect.y = 0;
rect.w = WINDOW_WIDTH / 3;
rect.h = WINDOW_HEIGHT;
SDL_RenderTexture(renderer, a, NULL, &rect);
rect.x = 0;
rect.y = WINDOW_HEIGHT / 3;
rect.w = WINDOW_WIDTH;
rect.h = WINDOW_HEIGHT / 6;
SDL_RenderTexture(renderer, b, NULL, &rect);
rect.y += WINDOW_HEIGHT / 6;
SDL_SetTextureBlendMode(b, SDL_BLENDMODE_BLEND);
SDL_SetTextureAlphaModFloat(b, 128 / 255.0f);
SDL_RenderTexture(renderer, b, NULL, &rect);
SDL_Color ar, br, cr;
if (!ReadPixel(WINDOW_WIDTH / 2, 0, &ar) ||
!ReadPixel(WINDOW_WIDTH / 2, WINDOW_HEIGHT / 3, &br) ||
!ReadPixel(WINDOW_WIDTH / 2, WINDOW_HEIGHT / 2, &cr)) {
return;
}
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Texture Blending");
y += TEXT_LINE_ADVANCE;
if (cr.r == 199 && cr.g == 193 && cr.b == 121) {
DrawText(x, y, "Correct blend color, blending in linear space");
} else if ((cr.r == 192 && cr.g == 163 && cr.b == 83) ||
(cr.r == 191 && cr.g == 162 && cr.b == 82)) {
DrawText(x, y, "Correct blend color, blending in sRGB space");
} else {
DrawText(x, y, "Incorrect blend color, unknown reason");
}
y += TEXT_LINE_ADVANCE;
SDL_DestroyTexture(a);
SDL_DestroyTexture(b);
}
static void DrawGradient(float x, float y, float width, float height, float start, float end)
{
float xy[8];
const int xy_stride = 2 * sizeof(float);
SDL_FColor color[4];
const int color_stride = sizeof(SDL_FColor);
const int num_vertices = 4;
const int indices[6] = { 0, 1, 2, 0, 2, 3 };
const int num_indices = 6;
const int size_indices = 4;
float minx, miny, maxx, maxy;
SDL_FColor min_color = { start, start, start, 1.0f };
SDL_FColor max_color = { end, end, end, 1.0f };
minx = x;
miny = y;
maxx = minx + width;
maxy = miny + height;
xy[0] = minx;
xy[1] = miny;
xy[2] = maxx;
xy[3] = miny;
xy[4] = maxx;
xy[5] = maxy;
xy[6] = minx;
xy[7] = maxy;
color[0] = min_color;
color[1] = max_color;
color[2] = max_color;
color[3] = min_color;
SDL_RenderGeometryRawFloat(renderer, NULL, xy, xy_stride, color, color_stride, NULL, 0, num_vertices, indices, num_indices, size_indices);
}
static void RenderGradientDrawing(void)
{
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
SDL_RenderClear(renderer);
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Draw SDR and HDR gradients");
y += TEXT_LINE_ADVANCE;
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "SDR gradient");
y += TEXT_LINE_ADVANCE;
DrawGradient(x, y, WINDOW_WIDTH - 2 * x, 64.0f, 0.0f, 1.0f);
y += 64.0f;
y += TEXT_LINE_ADVANCE;
y += TEXT_LINE_ADVANCE;
if (HDR_headroom > 1.0f) {
DrawText(x, y, "HDR gradient");
} else {
DrawText(x, y, "No HDR headroom, HDR and SDR gradient are the same");
}
y += TEXT_LINE_ADVANCE;
/* Drawing is in the sRGB colorspace, so we need to use the color scale, which is applied in linear space, to get into high dynamic range */
SDL_SetRenderColorScale(renderer, HDR_headroom);
DrawGradient(x, y, WINDOW_WIDTH - 2 * x, 64.0f, 0.0f, 1.0f);
SDL_SetRenderColorScale(renderer, 1.0f);
y += 64.0f;
}
static SDL_Texture *CreateGradientTexture(int width, float start, float end)
{
SDL_Texture *texture;
float *pixels;
/* Floating point textures are in the linear colorspace by default */
texture = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA128_FLOAT, SDL_TEXTUREACCESS_STATIC, width, 1);
if (!texture) {
return NULL;
}
pixels = (float *)SDL_malloc(width * sizeof(float) * 4);
if (pixels) {
int i;
float length = (end - start);
for (i = 0; i < width; ++i) {
float v = (start + (length * i) / width);
pixels[i * 4 + 0] = v;
pixels[i * 4 + 1] = v;
pixels[i * 4 + 2] = v;
pixels[i * 4 + 3] = 1.0f;
}
SDL_UpdateTexture(texture, NULL, pixels, width * sizeof(float) * 4);
SDL_free(pixels);
}
return texture;
}
static void DrawGradientTexture(float x, float y, float width, float height, float start, float end)
{
SDL_FRect rect = { x, y, width, height };
SDL_Texture *texture = CreateGradientTexture((int)width, start, end);
SDL_RenderTexture(renderer, texture, NULL, &rect);
SDL_DestroyTexture(texture);
}
static void RenderGradientTexture(void)
{
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
SDL_RenderClear(renderer);
float x = TEXT_START_X;
float y = TEXT_START_Y;
DrawText(x, y, "%s %s", renderer_name, colorspace_name);
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "Test: Texture SDR and HDR gradients");
y += TEXT_LINE_ADVANCE;
y += TEXT_LINE_ADVANCE;
DrawText(x, y, "SDR gradient");
y += TEXT_LINE_ADVANCE;
DrawGradientTexture(x, y, WINDOW_WIDTH - 2 * x, 64.0f, 0.0f, 1.0f);
y += 64.0f;
y += TEXT_LINE_ADVANCE;
y += TEXT_LINE_ADVANCE;
if (HDR_headroom > 1.0f) {
DrawText(x, y, "HDR gradient");
} else {
DrawText(x, y, "No HDR headroom, HDR and SDR gradient are the same");
}
y += TEXT_LINE_ADVANCE;
/* The gradient texture is in the linear colorspace, so we can use the HDR_headroom value directly */
DrawGradientTexture(x, y, WINDOW_WIDTH - 2 * x, 64.0f, 0.0f, HDR_headroom);
y += 64.0f;
}
static void loop(void)
{
SDL_Event event;
/* Check for events */
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_KEY_DOWN) {
switch (event.key.keysym.sym) {
case SDLK_ESCAPE:
done = 1;
break;
case SDLK_SPACE:
case SDLK_RIGHT:
NextStage();
break;
case SDLK_LEFT:
PrevStage();
break;
case SDLK_DOWN:
NextRenderer();
break;
case SDLK_UP:
PrevRenderer();
break;
default:
break;
}
} else if (event.type == SDL_EVENT_DISPLAY_HDR_STATE_CHANGED) {
UpdateHDRState();
} else if (event.type == SDL_EVENT_QUIT) {
done = 1;
}
}
if (renderer) {
SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255);
SDL_RenderClear(renderer);
switch (stage_index) {
case StageClearBackground:
RenderClearBackground();
break;
case StageDrawBackground:
RenderDrawBackground();
break;
case StageBlendDrawing:
RenderBlendDrawing();
break;
case StageBlendTexture:
RenderBlendTexture();
break;
case StageGradientDrawing:
RenderGradientDrawing();
break;
case StageGradientTexture:
RenderGradientTexture();
break;
}
SDL_RenderPresent(renderer);
}
SDL_Delay(100);
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
#endif
}
static void LogUsage(const char *argv0)
{
SDL_Log("Usage: %s [--renderer renderer] [--colorspace colorspace]\n", argv0);
}
int main(int argc, char *argv[])
{
int return_code = 1;
int i;
for (i = 1; i < argc; ++i) {
if (SDL_strcmp(argv[i], "--renderer") == 0) {
if (argv[i + 1]) {
renderer_name = argv[i + 1];
++i;
} else {
LogUsage(argv[0]);
goto quit;
}
} else if (SDL_strcmp(argv[i], "--colorspace") == 0) {
if (argv[i + 1]) {
colorspace_name = argv[i + 1];
if (SDL_strcasecmp(colorspace_name, "sRGB") == 0) {
colorspace = SDL_COLORSPACE_SRGB;
} else if (SDL_strcasecmp(colorspace_name, "linear") == 0) {
colorspace = SDL_COLORSPACE_SRGB_LINEAR;
/* Not currently supported
} else if (SDL_strcasecmp(colorspace_name, "HDR10") == 0) {
colorspace = SDL_COLORSPACE_HDR10;
*/
} else {
SDL_Log("Unknown colorspace %s\n", argv[i + 1]);
goto quit;
}
++i;
} else {
LogUsage(argv[0]);
goto quit;
}
} else {
LogUsage(argv[0]);
goto quit;
}
}
window = SDL_CreateWindow("SDL colorspace test", WINDOW_WIDTH, WINDOW_HEIGHT, 0);
if (!window) {
SDL_Log("Couldn't create window: %s\n", SDL_GetError());
return_code = 2;
goto quit;
}
renderer_count = SDL_GetNumRenderDrivers();
SDL_Log("There are %d render drivers:\n", renderer_count);
for (i = 0; i < renderer_count; ++i) {
const char *name = SDL_GetRenderDriver(i);
if (renderer_name && SDL_strcasecmp(renderer_name, name) == 0) {
renderer_index = i;
}
SDL_Log(" %s\n", name);
}
CreateRenderer();
/* Main render loop */
done = 0;
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {
loop();
}
#endif
return_code = 0;
quit:
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(window);
SDL_Quit();
return return_code;
}

View File

@ -17,13 +17,13 @@
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_test_font.h>
#include "gamepadutils.h"
#include "testutils.h"
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include "gamepadutils.h"
#include "testutils.h"
#if 0
#define DEBUG_AXIS_MAPPING
#endif
@ -35,7 +35,7 @@
#define BUTTON_MARGIN 16
#define BUTTON_PADDING 12
#define GAMEPAD_WIDTH 512
#define GAMEPAD_HEIGHT 480
#define GAMEPAD_HEIGHT 560
#define SCREEN_WIDTH (PANEL_WIDTH + PANEL_SPACING + GAMEPAD_WIDTH + PANEL_SPACING + PANEL_WIDTH)
#define SCREEN_HEIGHT (TITLE_HEIGHT + GAMEPAD_HEIGHT)
@ -782,6 +782,12 @@ static const char *GetBindingInstruction(void)
return "Press the lower paddle under your left hand";
case SDL_GAMEPAD_BUTTON_TOUCHPAD:
return "Press down on the touchpad";
case SDL_GAMEPAD_BUTTON_MISC2:
case SDL_GAMEPAD_BUTTON_MISC3:
case SDL_GAMEPAD_BUTTON_MISC4:
case SDL_GAMEPAD_BUTTON_MISC5:
case SDL_GAMEPAD_BUTTON_MISC6:
return "Press any additional button not already bound";
case SDL_GAMEPAD_ELEMENT_AXIS_LEFTX_NEGATIVE:
return "Move the left thumbstick to the left";
case SDL_GAMEPAD_ELEMENT_AXIS_LEFTX_POSITIVE:
@ -977,6 +983,7 @@ static void HandleGamepadAdded(SDL_JoystickID id, SDL_bool verbose)
gamepad = controllers[i].gamepad;
if (gamepad) {
if (verbose) {
SDL_PropertiesID props = SDL_GetGamepadProperties(gamepad);
const char *name = SDL_GetGamepadName(gamepad);
const char *path = SDL_GetGamepadPath(gamepad);
SDL_Log("Opened gamepad %s%s%s\n", name, path ? ", " : "", path ? path : "");
@ -986,11 +993,15 @@ static void HandleGamepadAdded(SDL_JoystickID id, SDL_bool verbose)
SDL_Log("Firmware version: 0x%x (%d)\n", firmware_version, firmware_version);
}
if (SDL_GamepadHasRumble(gamepad)) {
if (SDL_GetBooleanProperty(props, SDL_PROP_GAMEPAD_CAP_PLAYER_LED_BOOLEAN, SDL_FALSE)) {
SDL_Log("Has player LED");
}
if (SDL_GetBooleanProperty(props, SDL_PROP_GAMEPAD_CAP_RUMBLE_BOOLEAN, SDL_FALSE)) {
SDL_Log("Rumble supported");
}
if (SDL_GamepadHasRumbleTriggers(gamepad)) {
if (SDL_GetBooleanProperty(props, SDL_PROP_GAMEPAD_CAP_TRIGGER_RUMBLE_BOOLEAN, SDL_FALSE)) {
SDL_Log("Trigger rumble supported");
}
@ -1318,7 +1329,7 @@ static void DrawGamepadInfo(SDL_Renderer *renderer)
if (display_mode == CONTROLLER_MODE_TESTING) {
Uint64 steam_handle = SDL_GetGamepadSteamHandle(controller->gamepad);
if (steam_handle) {
SDL_snprintf(text, SDL_arraysize(text), "Steam: 0x%.16" SDL_PRIx64 "", steam_handle);
SDL_snprintf(text, SDL_arraysize(text), "Steam: 0x%.16" SDL_PRIx64, steam_handle);
y = (float)SCREEN_HEIGHT - 2 * (8.0f + FONT_LINE_HEIGHT);
x = (float)SCREEN_WIDTH - 8.0f - (FONT_CHARACTER_SIZE * SDL_strlen(text));
SDLTest_DrawString(renderer, x, y, text);
@ -1883,7 +1894,7 @@ static void loop(void *arg)
SDL_Delay(16);
SDL_RenderPresent(screen);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -1906,13 +1917,12 @@ int main(int argc, char *argv[])
return 1;
}
SDL_SetHint(SDL_HINT_ACCELEROMETER_AS_JOYSTICK, "0");
SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_PS4_RUMBLE, "1");
SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_PS5_RUMBLE, "1");
SDL_SetHint(SDL_HINT_JOYSTICK_HIDAPI_STEAM, "1");
SDL_SetHint(SDL_HINT_JOYSTICK_ROG_CHAKRAM, "1");
SDL_SetHint(SDL_HINT_JOYSTICK_ALLOW_BACKGROUND_EVENTS, "1");
SDL_SetHint(SDL_HINT_LINUX_JOYSTICK_DEADZONES, "1");
SDL_SetHint(SDL_HINT_JOYSTICK_LINUX_DEADZONES, "1");
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
@ -2090,7 +2100,7 @@ int main(int argc, char *argv[])
}
/* Loop, getting gamepad events! */
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop_arg(loop, NULL, 0, 1);
#else
while (!done) {

View File

@ -9,15 +9,16 @@
including commercial applications, and to alter it and redistribute it
freely.
*/
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
/* Stolen from the mailing list */
/* Creates a new mouse cursor from an XPM */
@ -73,7 +74,6 @@ static const char *cross[] = {
". c #ffffff",
" c None",
/* pixels */
/* pixels */
" ",
" ",
" ",
@ -116,14 +116,14 @@ init_color_cursor(const char *file)
SDL_Surface *surface = SDL_LoadBMP(file);
if (surface) {
if (surface->format->palette) {
const Uint8 bpp = surface->format->BitsPerPixel;
const Uint8 bpp = surface->format->bits_per_pixel;
const Uint8 mask = (1 << bpp) - 1;
if (SDL_PIXELORDER(surface->format->format) == SDL_BITMAPORDER_4321)
SDL_SetSurfaceColorKey(surface, 1, (*(Uint8 *)surface->pixels) & mask);
else
SDL_SetSurfaceColorKey(surface, 1, ((*(Uint8 *)surface->pixels) >> (8 - bpp)) & mask);
} else {
switch (surface->format->BitsPerPixel) {
switch (surface->format->bits_per_pixel) {
case 15:
SDL_SetSurfaceColorKey(surface, 1, (*(Uint16 *)surface->pixels) & 0x00007FFF);
break;
@ -329,7 +329,7 @@ static void loop(void)
}
SDL_RenderPresent(renderer);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -411,7 +411,7 @@ int main(int argc, char *argv[])
/* Main render loop */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

161
external/sdl/SDL/test/testdialog.c vendored Normal file
View File

@ -0,0 +1,161 @@
/*
Copyright (C) 1997-2024 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.
*/
/* Sample program: Create open and save dialogs. */
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
const SDL_DialogFileFilter filters[4] = {
{ "All files", "*" },
{ "JPG images", "jpg;jpeg" },
{ "PNG images", "png" },
{ NULL, NULL }
};
static void SDLCALL callback(void* userdata, const char* const* files, int filter) {
if (files) {
const char* filter_name = "(filter fetching unsupported)";
if (filter != -1) {
if (filter < sizeof(filters) / sizeof(*filters)) {
filter_name = filters[filter].name;
} else {
filter_name = "(No filter was selected)";
}
}
SDL_Log("Filter used: '%s'\n", filter_name);
while (*files) {
SDL_Log("'%s'\n", *files);
files++;
}
} else {
SDL_Log("Error: %s\n", SDL_GetError());
}
}
int main(int argc, char *argv[]) {
SDL_Window *w;
SDL_Renderer *r;
SDLTest_CommonState *state;
const SDL_FRect open_file_rect = { 50, 50, 220, 140 };
const SDL_FRect save_file_rect = { 50, 290, 220, 140 };
const SDL_FRect open_folder_rect = { 370, 50, 220, 140 };
int i;
char *initial_path = NULL;
char path_with_trailing_slash[2048];
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
if (state == NULL) {
return 1;
}
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Parse commandline */
for (i = 1; i < argc;) {
int consumed;
consumed = SDLTest_CommonArg(state, i);
if (!consumed) {
}
if (consumed <= 0) {
static const char *options[] = { NULL };
SDLTest_CommonLogUsage(state, argv[0], options);
return 1;
}
i += consumed;
}
if (SDL_Init(SDL_INIT_VIDEO) < 0) {
SDL_Log("SDL_Init failed (%s)", SDL_GetError());
return 1;
}
if (SDL_CreateWindowAndRenderer(640, 480, 0, &w, &r) < 0) {
SDL_Log("Failed to create window and/or renderer: %s\n", SDL_GetError());
return 1;
}
initial_path = SDL_GetUserFolder(SDL_FOLDER_HOME);
if (!initial_path) {
SDL_Log("Will not use an initial path, couldn't get the home directory path: %s\n", SDL_GetError());
path_with_trailing_slash[0] = '\0';
} else {
SDL_snprintf(path_with_trailing_slash, sizeof(path_with_trailing_slash), "%s/", initial_path);
SDL_free(initial_path);
}
while (1) {
int quit = 0;
SDL_Event e;
while (SDL_PollEvent(&e)) {
if (e.type == SDL_EVENT_QUIT) {
quit = 1;
break;
} else if (e.type == SDL_EVENT_MOUSE_BUTTON_UP) {
const SDL_FPoint p = { e.button.x, e.button.y };
/*
* Arguments, in order:
* - A function to call when files are chosen (or dialog is canceled, or error happens)
* - A user-managed void pointer to pass to the function when it will be invoked
* - The window to bind the dialog to, or NULL if none
* - A list of filters for the files, see SDL_DialogFileFilter above (not for SDL_ShowOpenFolderDialog)
* - The path where the dialog should start. May be a folder or a file
* - Nonzero if the user is allowed to choose multiple entries (not for SDL_ShowSaveFileDialog)
*/
if (SDL_PointInRectFloat(&p, &open_file_rect)) {
SDL_ShowOpenFileDialog(callback, NULL, w, filters, path_with_trailing_slash, 1);
} else if (SDL_PointInRectFloat(&p, &open_folder_rect)) {
SDL_ShowOpenFolderDialog(callback, NULL, w, path_with_trailing_slash, 1);
} else if (SDL_PointInRectFloat(&p, &save_file_rect)) {
SDL_ShowSaveFileDialog(callback, NULL, w, filters, path_with_trailing_slash);
}
}
}
if (quit) {
break;
}
SDL_Delay(100);
SDL_SetRenderDrawColor(r, 0, 0, 0, SDL_ALPHA_OPAQUE);
SDL_RenderClear(r);
SDL_SetRenderDrawColor(r, 255, 0, 0, SDL_ALPHA_OPAQUE);
SDL_RenderFillRect(r, &open_file_rect);
SDL_SetRenderDrawColor(r, 0, 255, 0, SDL_ALPHA_OPAQUE);
SDL_RenderFillRect(r, &save_file_rect);
SDL_SetRenderDrawColor(r, 0, 0, 255, SDL_ALPHA_OPAQUE);
SDL_RenderFillRect(r, &open_folder_rect);
SDL_SetRenderDrawColor(r, 0, 0, 0, SDL_ALPHA_OPAQUE);
SDLTest_DrawString(r, open_file_rect.x+5, open_file_rect.y+open_file_rect.h/2, "Open File...");
SDLTest_DrawString(r, save_file_rect.x+5, save_file_rect.y+save_file_rect.h/2, "Save File...");
SDLTest_DrawString(r, open_folder_rect.x+5, open_folder_rect.y+open_folder_rect.h/2, "Open Folder...");
SDL_RenderPresent(r);
}
SDL_DestroyRenderer(r);
SDL_DestroyWindow(w);
SDLTest_CleanupTextDrawing();
SDL_Quit();
SDLTest_CommonDestroyState(state);
return 0;
}

View File

@ -12,17 +12,17 @@
/* Simple program: draw as many random objects on the screen as possible */
#include <stdlib.h>
#include <time.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test_common.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#include <time.h>
#define NUM_OBJECTS 100
static SDLTest_CommonState *state;
@ -200,7 +200,7 @@ static void loop(void)
SDL_RenderPresent(renderer);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -300,7 +300,7 @@ int main(int argc, char *argv[])
next_fps_check = SDL_GetTicks() + fps_check_delay;
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -14,14 +14,14 @@
/* Sample program: Draw a Chess Board by using SDL_CreateSoftwareRenderer API */
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
static SDL_Window *window;
static SDL_Renderer *renderer;
static SDL_Surface *surface;
@ -79,7 +79,7 @@ static void loop(void)
if (e.type == SDL_EVENT_QUIT) {
done = 1;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_cancel_main_loop();
#endif
return;
@ -87,7 +87,7 @@ static void loop(void)
if ((e.type == SDL_EVENT_KEY_DOWN) && (e.key.keysym.sym == SDLK_ESCAPE)) {
done = 1;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_cancel_main_loop();
#endif
return;
@ -144,7 +144,7 @@ int main(int argc, char *argv[])
/* Draw the Image on rendering surface */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -35,8 +35,8 @@ static int SDLCALL
ThreadFunc(void *data)
{
/* Set the child thread error string */
SDL_SetError("Thread %s (%lu) had a problem: %s",
(char *)data, SDL_ThreadID(), "nevermind");
SDL_SetError("Thread %s (%" SDL_PRIu64 ") had a problem: %s",
(char *)data, SDL_GetCurrentThreadID(), "nevermind");
while (alive) {
SDL_Log("Thread '%s' is alive!\n", (char *)data);
SDL_Delay(1 * 1000);

View File

@ -11,18 +11,31 @@
freely.
*/
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
/* Hack #1: avoid inclusion of SDL_main.h by SDL_internal.h */
#define SDL_main_h_
/* Hack to avoid dynapi renaming */
/* Hack #2: avoid dynapi renaming (must be done before #include <SDL3/SDL.h>) */
#include "../src/dynapi/SDL_dynapi.h"
#ifdef SDL_DYNAMIC_API
#undef SDL_DYNAMIC_API
#endif
#define SDL_DYNAMIC_API 0
#ifndef NO_BUILD_CONFIG
#include "../src/SDL_internal.h"
#endif
/* Hack #3: undo Hack #1 */
#ifdef SDL_main_h_
#undef SDL_main_h_
#endif
#ifdef SDL_MAIN_NOIMPL
#undef SDL_MAIN_NOIMPL
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include <stdio.h>
#include <string.h>

File diff suppressed because it is too large Load Diff

View File

@ -1,15 +0,0 @@
/*
Copyright (C) 1997-2024 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.
*/
extern SDL_bool SetupVideoToolboxOutput(SDL_Renderer *renderer);
extern SDL_bool DisplayVideoToolboxFrame(SDL_Renderer *renderer, void *buffer, int srcX, int srcY, int srcW, int srcH, int dstX, int dstY, int dstW, int dstH );
extern void CleanupVideoToolboxOutput();

View File

@ -1,147 +0,0 @@
/*
Copyright (C) 1997-2024 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 "testffmpeg_videotoolbox.h"
#include <CoreVideo/CoreVideo.h>
#include <Metal/Metal.h>
#include <QuartzCore/CAMetalLayer.h>
#include <simd/simd.h>
// Metal BT.601 to RGB conversion shader
static NSString *drawMetalShaderSource =
@" using namespace metal;\n"
"\n"
" struct Vertex\n"
" {\n"
" float4 position [[position]];\n"
" float2 texCoords;\n"
" };\n"
"\n"
" constexpr sampler s(coord::normalized, address::clamp_to_edge, filter::linear);\n"
"\n"
" vertex Vertex draw_vs(constant Vertex *vertices [[ buffer(0) ]], uint vid [[ vertex_id ]])\n"
" {\n"
" return vertices[ vid ];\n"
" }\n"
"\n"
" fragment float4 draw_ps_bt601(Vertex in [[ stage_in ]],\n"
" texture2d<float> textureY [[ texture(0) ]],\n"
" texture2d<float> textureUV [[ texture(1) ]])\n"
" {\n"
" float3 yuv = float3(textureY.sample(s, in.texCoords).r, textureUV.sample(s, in.texCoords).rg);\n"
" float3 rgb;\n"
" yuv += float3(-0.0627451017, -0.501960814, -0.501960814);\n"
" rgb.r = dot(yuv, float3(1.1644, 0.000, 1.596));\n"
" rgb.g = dot(yuv, float3(1.1644, -0.3918, -0.813));\n"
" rgb.b = dot(yuv, float3(1.1644, 2.0172, 0.000));\n"
" return float4(rgb, 1.0);\n"
" }\n"
;
// keep this structure aligned with the proceeding drawMetalShaderSource's struct Vertex
typedef struct Vertex
{
vector_float4 position;
vector_float2 texCoord;
} Vertex;
static void SetVertex(Vertex *vertex, float x, float y, float s, float t)
{
vertex->position[ 0 ] = x;
vertex->position[ 1 ] = y;
vertex->position[ 2 ] = 0.0f;
vertex->position[ 3 ] = 1.0f;
vertex->texCoord[ 0 ] = s;
vertex->texCoord[ 1 ] = t;
}
static CAMetalLayer *metal_layer;
static id<MTLLibrary> library;
static id<MTLRenderPipelineState> video_pipeline;
SDL_bool SetupVideoToolboxOutput(SDL_Renderer *renderer)
{ @autoreleasepool {
NSError *error;
// Create the metal view
metal_layer = (CAMetalLayer *)SDL_GetRenderMetalLayer(renderer);
if (!metal_layer) {
return SDL_FALSE;
}
// FIXME: Handle other colorspaces besides BT.601
library = [metal_layer.device newLibraryWithSource:drawMetalShaderSource options:nil error:&error];
MTLRenderPipelineDescriptor *videoPipelineDescriptor = [[MTLRenderPipelineDescriptor new] autorelease];
videoPipelineDescriptor.vertexFunction = [library newFunctionWithName:@"draw_vs"];
videoPipelineDescriptor.fragmentFunction = [library newFunctionWithName:@"draw_ps_bt601"];
videoPipelineDescriptor.colorAttachments[ 0 ].pixelFormat = metal_layer.pixelFormat;
video_pipeline = [metal_layer.device newRenderPipelineStateWithDescriptor:videoPipelineDescriptor error:nil];
if (!video_pipeline) {
SDL_SetError("Couldn't create video pipeline");
return SDL_FALSE;
}
return true;
}}
SDL_bool DisplayVideoToolboxFrame(SDL_Renderer *renderer, void *buffer, int srcX, int srcY, int srcW, int srcH, int dstX, int dstY, int dstW, int dstH )
{ @autoreleasepool {
CVPixelBufferRef pPixelBuffer = (CVPixelBufferRef)buffer;
size_t nPixelBufferWidth = CVPixelBufferGetWidthOfPlane(pPixelBuffer, 0);
size_t nPixelBufferHeight = CVPixelBufferGetHeightOfPlane(pPixelBuffer, 0);
id<MTLTexture> videoFrameTextureY = nil;
id<MTLTexture> videoFrameTextureUV = nil;
IOSurfaceRef pSurface = CVPixelBufferGetIOSurface(pPixelBuffer);
MTLTextureDescriptor *textureDescriptorY = [MTLTextureDescriptor texture2DDescriptorWithPixelFormat:MTLPixelFormatR8Unorm width:nPixelBufferWidth height:nPixelBufferHeight mipmapped:NO];
MTLTextureDescriptor *textureDescriptorUV = [MTLTextureDescriptor texture2DDescriptorWithPixelFormat:MTLPixelFormatRG8Unorm width:CVPixelBufferGetWidthOfPlane(pPixelBuffer, 1) height:CVPixelBufferGetHeightOfPlane(pPixelBuffer, 1) mipmapped:NO];
videoFrameTextureY = [[metal_layer.device newTextureWithDescriptor:textureDescriptorY iosurface:pSurface plane:0] autorelease];
videoFrameTextureUV = [[metal_layer.device newTextureWithDescriptor:textureDescriptorUV iosurface:pSurface plane:1] autorelease];
float flMinSrcX = ( srcX + 0.5f ) / nPixelBufferWidth;
float flMaxSrcX = ( srcX + srcW + 0.5f ) / nPixelBufferWidth;
float flMinSrcY = ( srcY + 0.5f ) / nPixelBufferHeight;
float flMaxSrcY = ( srcY + srcH + 0.5f ) / nPixelBufferHeight;
int nOutputWidth, nOutputHeight;
nOutputWidth = metal_layer.drawableSize.width;
nOutputHeight = metal_layer.drawableSize.height;
float flMinDstX = 2.0f * ( ( dstX + 0.5f ) / nOutputWidth ) - 1.0f;
float flMaxDstX = 2.0f * ( ( dstX + dstW + 0.5f ) / nOutputWidth ) - 1.0f;
float flMinDstY = 2.0f * ( ( nOutputHeight - dstY - 0.5f ) / nOutputHeight ) - 1.0f;
float flMaxDstY = 2.0f * ( ( nOutputHeight - ( dstY + dstH ) - 0.5f ) / nOutputHeight ) - 1.0f;
Vertex arrVerts[4];
SetVertex(&arrVerts[0], flMinDstX, flMaxDstY, flMinSrcX, flMaxSrcY);
SetVertex(&arrVerts[1], flMinDstX, flMinDstY, flMinSrcX, flMinSrcY);
SetVertex(&arrVerts[2], flMaxDstX, flMaxDstY, flMaxSrcX, flMaxSrcY);
SetVertex(&arrVerts[3], flMaxDstX, flMinDstY, flMaxSrcX, flMinSrcY);
id<MTLRenderCommandEncoder> renderEncoder = (id<MTLRenderCommandEncoder>)SDL_GetRenderMetalCommandEncoder(renderer);
[renderEncoder setRenderPipelineState:video_pipeline];
[renderEncoder setFragmentTexture:videoFrameTextureY atIndex:0];
[renderEncoder setFragmentTexture:videoFrameTextureUV atIndex:1];
[renderEncoder setVertexBytes:arrVerts length:sizeof(arrVerts) atIndex:0];
[renderEncoder drawPrimitives:MTLPrimitiveTypeTriangleStrip vertexStart:0 vertexCount:SDL_arraysize(arrVerts)];
return SDL_TRUE;
}}
void CleanupVideoToolboxOutput()
{
}

1004
external/sdl/SDL/test/testffmpeg_vulkan.c vendored Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,25 @@
/*
Copyright (C) 1997-2024 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 <libavutil/hwcontext.h>
#include <libavutil/hwcontext_vulkan.h>
typedef struct VulkanVideoContext VulkanVideoContext;
extern VulkanVideoContext *CreateVulkanVideoContext(SDL_Window *window);
extern void SetupVulkanRenderProperties(VulkanVideoContext *context, SDL_PropertiesID props);
extern void SetupVulkanDeviceContextData(VulkanVideoContext *context, AVVulkanDeviceContext *ctx);
extern SDL_Texture *CreateVulkanVideoTexture(VulkanVideoContext *context, AVFrame *frame, SDL_Renderer *renderer, SDL_PropertiesID props);
extern int BeginVulkanFrameRendering(VulkanVideoContext *context, AVFrame *frame, SDL_Renderer *renderer);
extern int FinishVulkanFrameRendering(VulkanVideoContext *context, AVFrame *frame, SDL_Renderer *renderer);
extern void DestroyVulkanVideoContext(VulkanVideoContext *context);

View File

@ -10,7 +10,7 @@
freely.
*/
/* sanity tests on SDL_rwops.c (useful for alternative implementations of stdio rwops) */
/* sanity tests on SDL_iostream.c (useful for alternative implementations of stdio iostream) */
/* quiet windows compiler warnings */
#if defined(_MSC_VER) && !defined(_CRT_NONSTDC_NO_WARNINGS)
@ -29,7 +29,7 @@
/* WARNING ! those 2 files will be destroyed by this test program */
#ifdef __IOS__
#ifdef SDL_PLATFORM_IOS
#define FBASENAME1 "../Documents/sdldata1" /* this file will be created during tests */
#define FBASENAME2 "../Documents/sdldata2" /* this file should not exist before starting test */
#else
@ -51,22 +51,22 @@ cleanup(void)
}
static void
rwops_error_quit(unsigned line, SDL_RWops *rwops)
iostrm_error_quit(unsigned line, SDL_IOStream *iostrm)
{
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "testfile.c(%d): failed\n", line);
if (rwops) {
SDL_RWclose(rwops); /* This calls SDL_DestroyRW(rwops); */
if (iostrm) {
SDL_CloseIO(iostrm);
}
cleanup();
SDLTest_CommonDestroyState(state);
exit(1); /* quit with rwops error (test failed) */
exit(1); /* quit with iostrm error (test failed) */
}
#define RWOP_ERR_QUIT(x) rwops_error_quit(__LINE__, (x))
#define RWOP_ERR_QUIT(x) iostrm_error_quit(__LINE__, (x))
int main(int argc, char *argv[])
{
SDL_RWops *rwops = NULL;
SDL_IOStream *iostrm = NULL;
char test_buf[30];
/* Initialize test framework */
@ -85,27 +85,27 @@ int main(int argc, char *argv[])
cleanup();
/* test 1 : basic argument test: all those calls to SDL_RWFromFile should fail */
/* test 1 : basic argument test: all those calls to SDL_IOFromFile should fail */
rwops = SDL_RWFromFile(NULL, NULL);
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(NULL, NULL);
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile(NULL, "ab+");
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(NULL, "ab+");
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile(NULL, "sldfkjsldkfj");
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(NULL, "sldfkjsldkfj");
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile("something", "");
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile("something", "");
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile("something", NULL);
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile("something", NULL);
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
SDL_Log("test1 OK\n");
@ -114,259 +114,259 @@ int main(int argc, char *argv[])
modes : a, a+, w, w+ checks that it succeeds (file may not exists)
*/
rwops = SDL_RWFromFile(FBASENAME2, "rb"); /* this file doesn't exist that call must fail */
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "rb"); /* this file doesn't exist that call must fail */
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile(FBASENAME2, "rb+"); /* this file doesn't exist that call must fail */
if (rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "rb+"); /* this file doesn't exist that call must fail */
if (iostrm) {
RWOP_ERR_QUIT(iostrm);
}
rwops = SDL_RWFromFile(FBASENAME2, "wb");
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "wb");
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
unlink(FBASENAME2);
rwops = SDL_RWFromFile(FBASENAME2, "wb+");
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "wb+");
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
unlink(FBASENAME2);
rwops = SDL_RWFromFile(FBASENAME2, "ab");
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "ab");
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
unlink(FBASENAME2);
rwops = SDL_RWFromFile(FBASENAME2, "ab+");
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME2, "ab+");
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
unlink(FBASENAME2);
SDL_Log("test2 OK\n");
/* test 3 : creation, writing , reading, seeking,
test : w mode, r mode, w+ mode
*/
rwops = SDL_RWFromFile(FBASENAME1, "wb"); /* write only */
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME1, "wb"); /* write only */
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWwrite(rwops, "1234567", 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_WriteIO(iostrm, "1234567", 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops); /* we are in write only mode */
if (0 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm); /* we are in write only mode */
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
rwops = SDL_RWFromFile(FBASENAME1, "rb"); /* read mode, file must exist */
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME1, "rb"); /* read mode, file must exist */
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (20 != SDL_RWseek(rwops, -7, SDL_RW_SEEK_END)) {
RWOP_ERR_QUIT(rwops);
if (20 != SDL_SeekIO(iostrm, -7, SDL_IO_SEEK_END)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWread(rwops, test_buf, 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_ReadIO(iostrm, test_buf, 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "1234567", 7) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1000)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1000)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, -27, SDL_RW_SEEK_CUR)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, -27, SDL_IO_SEEK_CUR)) {
RWOP_ERR_QUIT(iostrm);
}
if (27 != SDL_RWread(rwops, test_buf, 30)) {
RWOP_ERR_QUIT(rwops);
if (27 != SDL_ReadIO(iostrm, test_buf, 30)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "12345678901234567890", 20) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWwrite(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops); /* readonly mode */
if (0 != SDL_WriteIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm); /* readonly mode */
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
/* test 3: same with w+ mode */
rwops = SDL_RWFromFile(FBASENAME1, "wb+"); /* write + read + truncation */
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME1, "wb+"); /* write + read + truncation */
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWwrite(rwops, "1234567", 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_WriteIO(iostrm, "1234567", 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (1 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops); /* we are in read/write mode */
if (1 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm); /* we are in read/write mode */
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (20 != SDL_RWseek(rwops, -7, SDL_RW_SEEK_END)) {
RWOP_ERR_QUIT(rwops);
if (20 != SDL_SeekIO(iostrm, -7, SDL_IO_SEEK_END)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWread(rwops, test_buf, 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_ReadIO(iostrm, test_buf, 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "1234567", 7) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1000)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1000)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, -27, SDL_RW_SEEK_CUR)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, -27, SDL_IO_SEEK_CUR)) {
RWOP_ERR_QUIT(iostrm);
}
if (27 != SDL_RWread(rwops, test_buf, 30)) {
RWOP_ERR_QUIT(rwops);
if (27 != SDL_ReadIO(iostrm, test_buf, 30)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "12345678901234567890", 20) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
SDL_Log("test3 OK\n");
/* test 4: same in r+ mode */
rwops = SDL_RWFromFile(FBASENAME1, "rb+"); /* write + read + file must exists, no truncation */
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME1, "rb+"); /* write + read + file must exists, no truncation */
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWwrite(rwops, "1234567", 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_WriteIO(iostrm, "1234567", 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (1 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops); /* we are in read/write mode */
if (1 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm); /* we are in read/write mode */
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (20 != SDL_RWseek(rwops, -7, SDL_RW_SEEK_END)) {
RWOP_ERR_QUIT(rwops);
if (20 != SDL_SeekIO(iostrm, -7, SDL_IO_SEEK_END)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWread(rwops, test_buf, 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_ReadIO(iostrm, test_buf, 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "1234567", 7) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1000)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1000)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, -27, SDL_RW_SEEK_CUR)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, -27, SDL_IO_SEEK_CUR)) {
RWOP_ERR_QUIT(iostrm);
}
if (27 != SDL_RWread(rwops, test_buf, 30)) {
RWOP_ERR_QUIT(rwops);
if (27 != SDL_ReadIO(iostrm, test_buf, 30)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "12345678901234567890", 20) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
SDL_Log("test4 OK\n");
/* test5 : append mode */
rwops = SDL_RWFromFile(FBASENAME1, "ab+"); /* write + read + append */
if (!rwops) {
RWOP_ERR_QUIT(rwops);
iostrm = SDL_IOFromFile(FBASENAME1, "ab+"); /* write + read + append */
if (!iostrm) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (10 != SDL_RWwrite(rwops, "1234567890", 10)) {
RWOP_ERR_QUIT(rwops);
if (10 != SDL_WriteIO(iostrm, "1234567890", 10)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWwrite(rwops, "1234567", 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_WriteIO(iostrm, "1234567", 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (1 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops);
if (1 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (20 + 27 != SDL_RWseek(rwops, -7, SDL_RW_SEEK_END)) {
RWOP_ERR_QUIT(rwops);
if (20 + 27 != SDL_SeekIO(iostrm, -7, SDL_IO_SEEK_END)) {
RWOP_ERR_QUIT(iostrm);
}
if (7 != SDL_RWread(rwops, test_buf, 7)) {
RWOP_ERR_QUIT(rwops);
if (7 != SDL_ReadIO(iostrm, test_buf, 7)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "1234567", 7) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWread(rwops, test_buf, 1000)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_ReadIO(iostrm, test_buf, 1000)) {
RWOP_ERR_QUIT(iostrm);
}
if (27 != SDL_RWseek(rwops, -27, SDL_RW_SEEK_CUR)) {
RWOP_ERR_QUIT(rwops);
if (27 != SDL_SeekIO(iostrm, -27, SDL_IO_SEEK_CUR)) {
RWOP_ERR_QUIT(iostrm);
}
if (0 != SDL_RWseek(rwops, 0L, SDL_RW_SEEK_SET)) {
RWOP_ERR_QUIT(rwops);
if (0 != SDL_SeekIO(iostrm, 0L, SDL_IO_SEEK_SET)) {
RWOP_ERR_QUIT(iostrm);
}
if (30 != SDL_RWread(rwops, test_buf, 30)) {
RWOP_ERR_QUIT(rwops);
if (30 != SDL_ReadIO(iostrm, test_buf, 30)) {
RWOP_ERR_QUIT(iostrm);
}
if (SDL_memcmp(test_buf, "123456789012345678901234567123", 30) != 0) {
RWOP_ERR_QUIT(rwops);
RWOP_ERR_QUIT(iostrm);
}
SDL_RWclose(rwops);
SDL_CloseIO(iostrm);
SDL_Log("test5 OK\n");
cleanup();
SDL_Quit();

View File

@ -15,11 +15,54 @@
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
static int SDLCALL enum_callback(void *userdata, const char *origdir, const char *fname)
{
SDL_PathInfo info;
char *fullpath = NULL;
/* you can use '/' for a path separator on Windows, but to make the log output look correct, we'll #ifdef this... */
#ifdef SDL_PLATFORM_WINDOWS
const char *pathsep = "\\";
#else
const char *pathsep = "/";
#endif
if (SDL_asprintf(&fullpath, "%s%s%s", origdir, *origdir ? pathsep : "", fname) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Out of memory!");
return -1;
}
if (SDL_GetPathInfo(fullpath, &info) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't stat '%s': %s", fullpath, SDL_GetError());
} else {
const char *type;
if (info.type == SDL_PATHTYPE_FILE) {
type = "FILE";
} else if (info.type == SDL_PATHTYPE_DIRECTORY) {
type = "DIRECTORY";
} else {
type = "OTHER";
}
SDL_Log("%s (type=%s, size=%" SDL_PRIu64 ", create=%" SDL_PRIu64 ", mod=%" SDL_PRIu64 ", access=%" SDL_PRIu64 ")",
fullpath, type, info.size, info.modify_time, info.create_time, info.access_time);
if (info.type == SDL_PATHTYPE_DIRECTORY) {
if (SDL_EnumerateDirectory(fullpath, enum_callback, userdata) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Enumeration failed!");
}
}
}
SDL_free(fullpath);
return 1; /* keep going */
}
int main(int argc, char *argv[])
{
SDLTest_CommonState *state;
char *base_path;
char *pref_path;
char *base_path;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
@ -46,7 +89,6 @@ int main(int argc, char *argv[])
SDL_GetError());
} else {
SDL_Log("base path: '%s'\n", base_path);
SDL_free(base_path);
}
pref_path = SDL_GetPrefPath("libsdl", "test_filesystem");
@ -67,6 +109,31 @@ int main(int argc, char *argv[])
SDL_free(pref_path);
}
if (base_path) {
if (SDL_EnumerateDirectory(base_path, enum_callback, NULL) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Base path enumeration failed!");
}
/* !!! FIXME: put this in a subroutine and make it test more thoroughly (and put it in testautomation). */
if (SDL_CreateDirectory("testfilesystem-test") == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_CreateDirectory('testfilesystem-test') failed: %s", SDL_GetError());
} else if (SDL_CreateDirectory("testfilesystem-test/1") == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_CreateDirectory('testfilesystem-test/1') failed: %s", SDL_GetError());
} else if (SDL_CreateDirectory("testfilesystem-test/1") == -1) { /* THIS SHOULD NOT FAIL! Making a directory that already exists should succeed here. */
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_CreateDirectory('testfilesystem-test/1') failed: %s", SDL_GetError());
} else if (SDL_RenamePath("testfilesystem-test/1", "testfilesystem-test/2") == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_RenamePath('testfilesystem-test/1', 'testfilesystem-test/2') failed: %s", SDL_GetError());
} else if (SDL_RemovePath("testfilesystem-test/2") == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_RemovePath('testfilesystem-test/2') failed: %s", SDL_GetError());
} else if (SDL_RemovePath("testfilesystem-test") == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_RemovePath('testfilesystem-test') failed: %s", SDL_GetError());
} else if (SDL_RemovePath("testfilesystem-test") == -1) { /* THIS SHOULD NOT FAIL! Removing a directory that is already gone should succeed here. */
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "SDL_RemovePath('testfilesystem-test') failed: %s", SDL_GetError());
}
}
SDL_free(base_path);
SDL_Quit();
SDLTest_CommonDestroyState(state);
return 0;

View File

@ -12,16 +12,17 @@
/* Simple program: draw a RGB triangle, with texture */
#include <stdlib.h>
#include <time.h>
#include "testutils.h"
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test_common.h>
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#include <stdlib.h>
#include <time.h>
static SDLTest_CommonState *state;
static SDL_bool use_texture = SDL_FALSE;
@ -136,29 +137,29 @@ static void loop(void)
cx += translate_cx;
cy += translate_cy;
a = (angle * 3.1415f) / 180.0f;
a = (angle * SDL_PI_F) / 180.0f;
verts[0].position.x = cx + d * SDL_cosf(a);
verts[0].position.y = cy + d * SDL_sinf(a);
verts[0].color.r = 0xFF;
verts[0].color.r = 1.0f;
verts[0].color.g = 0;
verts[0].color.b = 0;
verts[0].color.a = 0xFF;
verts[0].color.a = 1.0f;
a = ((angle + 120) * 3.1415f) / 180.0f;
a = ((angle + 120) * SDL_PI_F) / 180.0f;
verts[1].position.x = cx + d * SDL_cosf(a);
verts[1].position.y = cy + d * SDL_sinf(a);
verts[1].color.r = 0;
verts[1].color.g = 0xFF;
verts[1].color.g = 1.0f;
verts[1].color.b = 0;
verts[1].color.a = 0xFF;
verts[1].color.a = 1.0f;
a = ((angle + 240) * 3.1415f) / 180.0f;
a = ((angle + 240) * SDL_PI_F) / 180.0f;
verts[2].position.x = cx + d * SDL_cosf(a);
verts[2].position.y = cy + d * SDL_sinf(a);
verts[2].color.r = 0;
verts[2].color.g = 0;
verts[2].color.b = 0xFF;
verts[2].color.a = 0xFF;
verts[2].color.b = 1.0f;
verts[2].color.a = 1.0f;
if (use_texture) {
verts[0].tex_coord.x = 0.5f;
@ -174,7 +175,7 @@ static void loop(void)
SDL_RenderPresent(renderer);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -266,7 +267,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -310,7 +310,7 @@ int main(int argc, char *argv[])
mode = SDL_GetCurrentDisplayMode(SDL_GetPrimaryDisplay());
if (mode) {
SDL_Log("Screen BPP : %" SDL_PRIu32 "\n", SDL_BITSPERPIXEL(mode->format));
SDL_Log("Screen BPP : %d\n", SDL_BITSPERPIXEL(mode->format));
}
LogSwapInterval();

View File

@ -14,7 +14,7 @@
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#if defined(__IOS__) || defined(__ANDROID__)
#if defined(SDL_PLATFORM_IOS) || defined(SDL_PLATFORM_ANDROID)
#define HAVE_OPENGLES
#endif
@ -335,7 +335,7 @@ int main(int argc, char *argv[])
SDL_Log("%2.2f frames per second\n",
((double)frames * 1000) / (now - then));
}
#ifndef __ANDROID__
#ifndef SDL_PLATFORM_ANDROID
quit(0);
#endif
return 0;

View File

@ -9,16 +9,17 @@
including commercial applications, and to alter it and redistribute it
freely.
*/
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#if defined(__IOS__) || defined(__ANDROID__) || defined(__EMSCRIPTEN__) || defined(__WINDOWS__) || defined(__LINUX__)
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#if defined(SDL_PLATFORM_IOS) || defined(SDL_PLATFORM_ANDROID) || defined(SDL_PLATFORM_EMSCRIPTEN) || defined(SDL_PLATFORM_WIN32) || defined(SDL_PLATFORM_LINUX)
#define HAVE_OPENGLES2
#endif
@ -535,7 +536,7 @@ Render(unsigned int width, unsigned int height, shader_data *data)
static int done;
static Uint32 frames;
static shader_data *datas;
#ifndef __EMSCRIPTEN__
#ifndef SDL_PLATFORM_EMSCRIPTEN
static thread_data *threads;
#endif
@ -560,14 +561,14 @@ render_window(int index)
++frames;
}
#ifndef __EMSCRIPTEN__
#ifndef SDL_PLATFORM_EMSCRIPTEN
static int SDLCALL
render_thread_fn(void *render_ctx)
{
thread_data *thread = render_ctx;
while (!done && !thread->done && state->windows[thread->index]) {
if (SDL_AtomicCAS(&thread->suspended, WAIT_STATE_ENTER_SEM, WAIT_STATE_WAITING_ON_SEM)) {
if (SDL_AtomicCompareAndSwap(&thread->suspended, WAIT_STATE_ENTER_SEM, WAIT_STATE_WAITING_ON_SEM)) {
SDL_WaitSemaphore(thread->suspend_sem);
}
render_window(thread->index);
@ -602,7 +603,7 @@ loop_threaded(void)
if (suspend_when_occluded && event.type == SDL_EVENT_WINDOW_OCCLUDED) {
tdata = GetThreadDataForWindow(event.window.windowID);
if (tdata) {
SDL_AtomicCAS(&tdata->suspended, WAIT_STATE_GO, WAIT_STATE_ENTER_SEM);
SDL_AtomicCompareAndSwap(&tdata->suspended, WAIT_STATE_GO, WAIT_STATE_ENTER_SEM);
}
} else if (suspend_when_occluded && event.type == SDL_EVENT_WINDOW_EXPOSED) {
tdata = GetThreadDataForWindow(event.window.windowID);
@ -652,7 +653,7 @@ loop(void)
render_window(i);
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
else {
emscripten_cancel_main_loop();
}
@ -912,7 +913,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
if (threaded) {
@ -950,7 +951,7 @@ int main(int argc, char *argv[])
SDL_Log("%2.2f frames per second\n",
((double)frames * 1000) / (now - then));
}
#ifndef __ANDROID__
#ifndef SDL_PLATFORM_ANDROID
quit(0);
#endif
return 0;

View File

@ -9,17 +9,18 @@
including commercial applications, and to alter it and redistribute it
freely.
*/
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#if defined(__IOS__) || defined(__ANDROID__) || defined(__EMSCRIPTEN__) || defined(__WINDOWS__) || defined(__LINUX__)
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#if defined(SDL_PLATFORM_IOS) || defined(SDL_PLATFORM_ANDROID) || defined(SDL_PLATFORM_EMSCRIPTEN) || defined(SDL_PLATFORM_WIN32) || defined(SDL_PLATFORM_LINUX)
#define HAVE_OPENGLES2
#endif
@ -425,7 +426,7 @@ static void loop(void)
SDL_GL_SwapWindow(state->windows[i]);
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
else {
emscripten_cancel_main_loop();
}
@ -769,7 +770,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {
@ -783,7 +784,7 @@ int main(int argc, char *argv[])
SDL_Log("%2.2f frames per second\n",
((double)frames * 1000) / (now - then));
}
#ifndef __ANDROID__
#ifndef SDL_PLATFORM_ANDROID
quit(0);
#endif
return 0;

View File

@ -40,6 +40,8 @@ int main(int argc, char **argv)
int id[9];
int nefx;
unsigned int supported;
SDL_HapticID *haptics;
int num_haptics;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
@ -81,41 +83,52 @@ int main(int argc, char **argv)
/* Initialize the force feedbackness */
SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_JOYSTICK |
SDL_INIT_HAPTIC);
SDL_Log("%d Haptic devices detected:\n", SDL_NumHaptics());
for (i = 0; i < SDL_NumHaptics(); ++i) {
SDL_Log(" %s\n", SDL_HapticName(i));
haptics = SDL_GetHaptics(&num_haptics);
SDL_Log("%d Haptic devices detected.\n", num_haptics);
for (i = 0; i < num_haptics; ++i) {
SDL_Log(" %s\n", SDL_GetHapticInstanceName(haptics[i]));
}
if (SDL_NumHaptics() > 0) {
if (haptics) {
if (num_haptics == 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "No Haptic devices found!\n");
SDL_free(haptics);
return 1;
}
/* We'll just use index or the first force feedback device found */
if (!name) {
i = (index != -1) ? index : 0;
if (i >= num_haptics) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Index out of range, aborting.\n");
SDL_free(haptics);
return 1;
}
}
/* Try to find matching device */
else {
for (i = 0; i < SDL_NumHaptics(); i++) {
if (SDL_strstr(SDL_HapticName(i), name) != NULL) {
for (i = 0; i < num_haptics; i++) {
if (SDL_strstr(SDL_GetHapticInstanceName(haptics[i]), name) != NULL) {
break;
}
}
if (i >= SDL_NumHaptics()) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to find device matching '%s', aborting.\n",
name);
if (i >= num_haptics) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to find device matching '%s', aborting.\n", name);
SDL_free(haptics);
return 1;
}
}
haptic = SDL_HapticOpen(i);
haptic = SDL_OpenHaptic(haptics[i]);
if (!haptic) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to create the haptic device: %s\n",
SDL_GetError());
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to create the haptic device: %s\n", SDL_GetError());
SDL_free(haptics);
return 1;
}
SDL_Log("Device: %s\n", SDL_HapticName(i));
SDL_Log("Device: %s\n", SDL_GetHapticName(haptic));
HapticPrintSupported(haptic);
} else {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "No Haptic devices found!\n");
return 1;
SDL_free(haptics);
}
/* We only want force feedback errors. */
@ -124,7 +137,7 @@ int main(int argc, char **argv)
/* Create effects. */
SDL_memset(efx, 0, sizeof(efx));
nefx = 0;
supported = SDL_HapticQuery(haptic);
supported = SDL_GetHapticFeatures(haptic);
SDL_Log("\nUploading effects\n");
/* First we'll try a SINE effect. */
@ -137,7 +150,7 @@ int main(int argc, char **argv)
efx[nefx].periodic.length = 5000;
efx[nefx].periodic.attack_length = 1000;
efx[nefx].periodic.fade_length = 1000;
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -153,7 +166,7 @@ int main(int argc, char **argv)
efx[nefx].periodic.length = 5000;
efx[nefx].periodic.attack_length = 1000;
efx[nefx].periodic.fade_length = 1000;
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -171,7 +184,7 @@ int main(int argc, char **argv)
efx[nefx].constant.level = 0x6000;
efx[nefx].constant.attack_length = 1000;
efx[nefx].constant.fade_length = 1000;
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -184,14 +197,14 @@ int main(int argc, char **argv)
SDL_Log(" effect %d: Condition Spring\n", nefx);
efx[nefx].type = SDL_HAPTIC_SPRING;
efx[nefx].condition.length = 5000;
for (i = 0; i < SDL_HapticNumAxes(haptic); i++) {
for (i = 0; i < SDL_GetNumHapticAxes(haptic); i++) {
efx[nefx].condition.right_sat[i] = 0xFFFF;
efx[nefx].condition.left_sat[i] = 0xFFFF;
efx[nefx].condition.right_coeff[i] = 0x2000;
efx[nefx].condition.left_coeff[i] = 0x2000;
efx[nefx].condition.center[i] = 0x1000; /* Displace the center for it to move. */
}
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -203,13 +216,13 @@ int main(int argc, char **argv)
SDL_Log(" effect %d: Condition Damper\n", nefx);
efx[nefx].type = SDL_HAPTIC_DAMPER;
efx[nefx].condition.length = 5000;
for (i = 0; i < SDL_HapticNumAxes(haptic); i++) {
for (i = 0; i < SDL_GetNumHapticAxes(haptic); i++) {
efx[nefx].condition.right_sat[i] = 0xFFFF;
efx[nefx].condition.left_sat[i] = 0xFFFF;
efx[nefx].condition.right_coeff[i] = 0x2000;
efx[nefx].condition.left_coeff[i] = 0x2000;
}
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -221,14 +234,14 @@ int main(int argc, char **argv)
SDL_Log(" effect %d: Condition Inertia\n", nefx);
efx[nefx].type = SDL_HAPTIC_INERTIA;
efx[nefx].condition.length = 5000;
for (i = 0; i < SDL_HapticNumAxes(haptic); i++) {
for (i = 0; i < SDL_GetNumHapticAxes(haptic); i++) {
efx[nefx].condition.right_sat[i] = 0xFFFF;
efx[nefx].condition.left_sat[i] = 0xFFFF;
efx[nefx].condition.right_coeff[i] = 0x2000;
efx[nefx].condition.left_coeff[i] = 0x2000;
efx[nefx].condition.deadband[i] = 0x1000; /* 1/16th of axis-range around the center is 'dead'. */
}
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -240,13 +253,13 @@ int main(int argc, char **argv)
SDL_Log(" effect %d: Condition Friction\n", nefx);
efx[nefx].type = SDL_HAPTIC_FRICTION;
efx[nefx].condition.length = 5000;
for (i = 0; i < SDL_HapticNumAxes(haptic); i++) {
for (i = 0; i < SDL_GetNumHapticAxes(haptic); i++) {
efx[nefx].condition.right_sat[i] = 0xFFFF;
efx[nefx].condition.left_sat[i] = 0xFFFF;
efx[nefx].condition.right_coeff[i] = 0x2000;
efx[nefx].condition.left_coeff[i] = 0x2000;
}
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -266,7 +279,7 @@ int main(int argc, char **argv)
efx[nefx].ramp.end = -0x4000;
efx[nefx].ramp.attack_length = 1000;
efx[nefx].ramp.fade_length = 1000;
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -281,7 +294,7 @@ int main(int argc, char **argv)
efx[nefx].leftright.length = 5000;
efx[nefx].leftright.large_magnitude = 0x3000;
efx[nefx].leftright.small_magnitude = 0xFFFF;
id[nefx] = SDL_HapticNewEffect(haptic, &efx[nefx]);
id[nefx] = SDL_CreateHapticEffect(haptic, &efx[nefx]);
if (id[nefx] < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "UPLOADING EFFECT ERROR: %s\n", SDL_GetError());
abort_execution();
@ -292,13 +305,13 @@ int main(int argc, char **argv)
SDL_Log("\nNow playing effects for 5 seconds each with 1 second delay between\n");
for (i = 0; i < nefx; i++) {
SDL_Log(" Playing effect %d\n", i);
SDL_HapticRunEffect(haptic, id[i], 1);
SDL_RunHapticEffect(haptic, id[i], 1);
SDL_Delay(6000); /* Effects only have length 5000 */
}
/* Quit */
if (haptic) {
SDL_HapticClose(haptic);
SDL_CloseHaptic(haptic);
}
SDL_Quit();
SDLTest_CommonDestroyState(state);
@ -314,7 +327,7 @@ abort_execution(void)
{
SDL_Log("\nAborting program execution.\n");
SDL_HapticClose(haptic);
SDL_CloseHaptic(haptic);
SDL_Quit();
SDLTest_CommonDestroyState(state);
@ -329,18 +342,17 @@ HapticPrintSupported(SDL_Haptic *ptr)
{
unsigned int supported;
supported = SDL_HapticQuery(ptr);
supported = SDL_GetHapticFeatures(ptr);
SDL_Log(" Supported effects [%d effects, %d playing]:\n",
SDL_HapticNumEffects(ptr), SDL_HapticNumEffectsPlaying(ptr));
SDL_GetMaxHapticEffects(ptr), SDL_GetMaxHapticEffectsPlaying(ptr));
if (supported & SDL_HAPTIC_CONSTANT) {
SDL_Log(" constant\n");
}
if (supported & SDL_HAPTIC_SINE) {
SDL_Log(" sine\n");
}
/* !!! FIXME: put this back when we have more bits in 2.1 */
/* if (supported & SDL_HAPTIC_SQUARE)
SDL_Log(" square\n"); */
if (supported & SDL_HAPTIC_SQUARE)
SDL_Log(" square\n");
if (supported & SDL_HAPTIC_TRIANGLE) {
SDL_Log(" triangle\n");
}

View File

@ -153,6 +153,8 @@ int main(int argc, char **argv)
case SDL_EVENT_QUIT:
done = 1;
break;
default:
break;
}
}

View File

@ -20,6 +20,8 @@
int main(int argc, char *argv[])
{
int num_keyboards = 0;
int num_mice = 0;
int num_joysticks = 0;
SDL_Joystick *joystick = NULL;
SDL_Haptic *haptic = NULL;
@ -78,10 +80,19 @@ int main(int argc, char *argv[])
//SDL_CreateWindow("Dummy", 128, 128, 0);
*/
SDL_free(SDL_GetKeyboards(&num_keyboards));
SDL_Log("There are %d keyboards at startup\n", num_keyboards);
SDL_free(SDL_GetMice(&num_mice));
SDL_Log("There are %d mice at startup\n", num_mice);
SDL_free(SDL_GetJoysticks(&num_joysticks));
SDL_Log("There are %d joysticks at startup\n", num_joysticks);
if (enable_haptic) {
SDL_Log("There are %d haptic devices at startup\n", SDL_NumHaptics());
int num_haptics;
SDL_free(SDL_GetHaptics(&num_haptics));
SDL_Log("There are %d haptic devices at startup\n", num_haptics);
}
while (keepGoing) {
@ -91,6 +102,18 @@ int main(int argc, char *argv[])
case SDL_EVENT_QUIT:
keepGoing = SDL_FALSE;
break;
case SDL_EVENT_KEYBOARD_ADDED:
SDL_Log("Keyboard '%s' added : %" SDL_PRIu32 "\n", SDL_GetKeyboardInstanceName(event.kdevice.which), event.kdevice.which);
break;
case SDL_EVENT_KEYBOARD_REMOVED:
SDL_Log("Keyboard removed: %" SDL_PRIu32 "\n", event.kdevice.which);
break;
case SDL_EVENT_MOUSE_ADDED:
SDL_Log("Mouse '%s' added : %" SDL_PRIu32 "\n", SDL_GetMouseInstanceName(event.mdevice.which), event.mdevice.which);
break;
case SDL_EVENT_MOUSE_REMOVED:
SDL_Log("Mouse removed: %" SDL_PRIu32 "\n", event.mdevice.which);
break;
case SDL_EVENT_JOYSTICK_ADDED:
if (joystick) {
SDL_Log("Only one joystick supported by this test\n");
@ -99,13 +122,13 @@ int main(int argc, char *argv[])
instance = event.jdevice.which;
SDL_Log("Joy Added : %" SDL_PRIu32 " : %s\n", event.jdevice.which, SDL_GetJoystickName(joystick));
if (enable_haptic) {
if (SDL_JoystickIsHaptic(joystick)) {
haptic = SDL_HapticOpenFromJoystick(joystick);
if (SDL_IsJoystickHaptic(joystick)) {
haptic = SDL_OpenHapticFromJoystick(joystick);
if (haptic) {
SDL_Log("Joy Haptic Opened\n");
if (SDL_HapticRumbleInit(haptic) != 0) {
if (SDL_InitHapticRumble(haptic) != 0) {
SDL_Log("Could not init Rumble!: %s\n", SDL_GetError());
SDL_HapticClose(haptic);
SDL_CloseHaptic(haptic);
haptic = NULL;
}
} else {
@ -122,7 +145,7 @@ int main(int argc, char *argv[])
SDL_Log("Joy Removed: %" SDL_PRIs32 "\n", event.jdevice.which);
instance = 0;
if (enable_haptic && haptic) {
SDL_HapticClose(haptic);
SDL_CloseHaptic(haptic);
haptic = NULL;
}
SDL_CloseJoystick(joystick);
@ -136,13 +159,13 @@ int main(int argc, char *argv[])
// SDL_Log("Axis Move: %d\n", event.jaxis.axis);
*/
if (enable_haptic) {
SDL_HapticRumblePlay(haptic, 0.25, 250);
SDL_PlayHapticRumble(haptic, 0.25, 250);
}
break;
case SDL_EVENT_JOYSTICK_BUTTON_DOWN:
SDL_Log("Button Press: %d\n", event.jbutton.button);
if (enable_haptic && haptic) {
SDL_HapticRumblePlay(haptic, 0.25, 250);
SDL_PlayHapticRumble(haptic, 0.25, 250);
}
if (event.jbutton.button == 0) {
SDL_Log("Exiting due to button press of button 0\n");
@ -152,6 +175,8 @@ int main(int argc, char *argv[])
case SDL_EVENT_JOYSTICK_BUTTON_UP:
SDL_Log("Button Release: %d\n", event.jbutton.button);
break;
default:
break;
}
}
}

View File

@ -27,9 +27,9 @@
#endif
#ifdef HAVE_SDL_TTF
#ifdef __MACOS__
#ifdef SDL_PLATFORM_MACOS
#define DEFAULT_FONT "/System/Library/Fonts/华文细黑.ttf"
#elif defined(__WIN32__)
#elif defined(SDL_PLATFORM_WIN32)
/* Some japanese font present on at least Windows 8.1. */
#define DEFAULT_FONT "C:\\Windows\\Fonts\\yugothic.ttf"
#else
@ -109,7 +109,7 @@ static int unifont_init(const char *fontname)
Uint32 numGlyphs = 0;
int lineNumber = 1;
size_t bytesRead;
SDL_RWops *hexFile;
SDL_IOStream *hexFile;
const size_t unifontGlyphSize = UNIFONT_NUM_GLYPHS * sizeof(struct UnifontGlyph);
const size_t unifontTextureSize = UNIFONT_NUM_TEXTURES * state->num_windows * sizeof(void *);
char *filename;
@ -135,7 +135,7 @@ static int unifont_init(const char *fontname)
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Out of memory\n");
return -1;
}
hexFile = SDL_RWFromFile(filename, "rb");
hexFile = SDL_IOFromFile(filename, "rb");
SDL_free(filename);
if (!hexFile) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "unifont: Failed to open font file: %s\n", fontname);
@ -149,7 +149,7 @@ static int unifont_init(const char *fontname)
Uint8 glyphWidth;
Uint32 codepoint;
bytesRead = SDL_RWread(hexFile, hexBuffer, 9);
bytesRead = SDL_ReadIO(hexFile, hexBuffer, 9);
if (numGlyphs > 0 && bytesRead == 0) {
break; /* EOF */
}
@ -185,11 +185,7 @@ static int unifont_init(const char *fontname)
if (codepointHexSize < 8) {
SDL_memmove(hexBuffer, hexBuffer + codepointHexSize + 1, bytesOverread);
}
bytesRead = SDL_RWread(hexFile, hexBuffer + bytesOverread, 33 - bytesOverread);
if (bytesRead < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "error SDL_RWread\n");
return -1;
}
bytesRead = SDL_ReadIO(hexFile, hexBuffer + bytesOverread, 33 - bytesOverread);
if (bytesRead < (33 - bytesOverread)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "unifont: Unexpected end of hex file.\n");
@ -199,12 +195,7 @@ static int unifont_init(const char *fontname)
glyphWidth = 8;
} else {
glyphWidth = 16;
bytesRead = SDL_RWread(hexFile, hexBuffer + 33, 32);
if (bytesRead < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "error SDL_RWread\n");
return -1;
}
bytesRead = SDL_ReadIO(hexFile, hexBuffer + 33, 32);
if (bytesRead < 32) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "unifont: Unexpected end of hex file.\n");
return -1;
@ -232,7 +223,7 @@ static int unifont_init(const char *fontname)
lineNumber++;
} while (bytesRead > 0);
SDL_RWclose(hexFile);
SDL_CloseIO(hexFile);
SDL_Log("unifont: Loaded %" SDL_PRIu32 " glyphs.\n", numGlyphs);
return 0;
}
@ -468,7 +459,9 @@ static void _Redraw(int rendererID)
SDL_Renderer *renderer = state->renderers[rendererID];
SDL_FRect drawnTextRect, cursorRect, underlineRect;
drawnTextRect.x = textRect.x;
drawnTextRect.y = 0;
drawnTextRect.w = 0;
drawnTextRect.h = 0;
SDL_SetRenderDrawColor(renderer, backColor.r, backColor.g, backColor.b, backColor.a);
SDL_RenderFillRect(renderer, &textRect);
@ -501,7 +494,7 @@ static void _Redraw(int rendererID)
drawnTextRect.y = dstrect.y;
drawnTextRect.h = dstrect.h;
while ((codepoint = utf8_decode(utext, len = utf8_length(*utext)))) {
while ((codepoint = utf8_decode(utext, len = utf8_length(*utext))) != 0) {
Sint32 advance = unifont_draw_glyph(codepoint, rendererID, &dstrect) * UNIFONT_DRAW_SCALE;
dstrect.x += advance;
drawnTextRect.w += advance;
@ -573,7 +566,7 @@ static void _Redraw(int rendererID)
drawnTextRect.y = dstrect.y;
drawnTextRect.h = dstrect.h;
while ((codepoint = utf8_decode(utext, len = utf8_length(*utext)))) {
while ((codepoint = utf8_decode(utext, len = utf8_length(*utext))) != 0) {
Sint32 advance = unifont_draw_glyph(codepoint, rendererID, &dstrect) * UNIFONT_DRAW_SCALE;
dstrect.x += advance;
drawnTextRect.w += advance;
@ -740,6 +733,8 @@ int main(int argc, char *argv[])
Redraw();
}
break;
default:
break;
}
if (done) {
@ -780,6 +775,9 @@ int main(int argc, char *argv[])
cursor = event.edit.start;
Redraw();
break;
default:
break;
}
}
}

View File

@ -12,15 +12,15 @@
/* Simple program: draw as many random objects on the screen as possible */
#include <stdlib.h>
#include <time.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include <stdlib.h>
#include <time.h>
#define SWAP(typ, a, b) \
do { \
@ -251,6 +251,8 @@ static void loop(void *arg)
(float)(rand() % 480));
}
break;
default:
break;
}
break;
default:
@ -273,7 +275,7 @@ static void loop(void *arg)
SDL_RenderPresent(renderer);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (*done) {
emscripten_cancel_main_loop();
}
@ -368,7 +370,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop_arg(loop, &done, 0, 1);
#else
while (!done) {

View File

@ -22,7 +22,7 @@
#include <SDL3/SDL_test.h>
static SDL_Mutex *mutex = NULL;
static SDL_threadID mainthread;
static SDL_ThreadID mainthread;
static SDL_AtomicInt doterminate;
static int nb_threads = 6;
static SDL_Thread **threads;
@ -42,7 +42,7 @@ SDL_Quit_Wrapper(void)
static void printid(void)
{
SDL_Log("Thread %lu: exiting\n", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": exiting\n", SDL_GetCurrentThreadID());
}
static void terminate(int sig)
@ -53,9 +53,9 @@ static void terminate(int sig)
static void closemutex(int sig)
{
SDL_threadID id = SDL_ThreadID();
SDL_ThreadID id = SDL_GetCurrentThreadID();
int i;
SDL_Log("Thread %lu: Cleaning up...\n", id == mainthread ? 0 : id);
SDL_Log("Thread %" SDL_PRIu64 ": Cleaning up...\n", id == mainthread ? 0 : id);
SDL_AtomicSet(&doterminate, 1);
if (threads) {
for (i = 0; i < nb_threads; ++i) {
@ -74,26 +74,28 @@ static void closemutex(int sig)
static int SDLCALL
Run(void *data)
{
if (SDL_ThreadID() == mainthread) {
SDL_ThreadID current_thread = SDL_GetCurrentThreadID();
if (current_thread == mainthread) {
(void)signal(SIGTERM, closemutex);
}
SDL_Log("Thread %lu: starting up", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": starting up", current_thread);
while (!SDL_AtomicGet(&doterminate)) {
SDL_Log("Thread %lu: ready to work\n", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": ready to work\n", current_thread);
SDL_LockMutex(mutex);
SDL_Log("Thread %lu: start work!\n", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": start work!\n", current_thread);
SDL_Delay(1 * worktime);
SDL_Log("Thread %lu: work done!\n", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": work done!\n", current_thread);
SDL_UnlockMutex(mutex);
/* If this sleep isn't done, then threads may starve */
SDL_Delay(10);
}
if (SDL_ThreadID() == mainthread && SDL_AtomicGet(&doterminate)) {
SDL_Log("Thread %lu: raising SIGTERM\n", SDL_ThreadID());
if (current_thread == mainthread && SDL_AtomicGet(&doterminate)) {
SDL_Log("Thread %" SDL_PRIu64 ": raising SIGTERM\n", current_thread);
(void)raise(SIGTERM);
}
SDL_Log("Thread %lu: exiting!\n", SDL_ThreadID());
SDL_Log("Thread %" SDL_PRIu64 ": exiting!\n", current_thread);
return 0;
}
@ -187,8 +189,8 @@ int main(int argc, char *argv[])
exit(1);
}
mainthread = SDL_ThreadID();
SDL_Log("Main thread: %lu\n", mainthread);
mainthread = SDL_GetCurrentThreadID();
SDL_Log("Main thread: %" SDL_PRIu64 "\n", mainthread);
(void)atexit(printid);
for (i = 0; i < nb_threads; ++i) {
char name[64];

552
external/sdl/SDL/test/testmanymouse.c vendored Normal file
View File

@ -0,0 +1,552 @@
/*
Copyright (C) 1997-2024 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_test_common.h>
#include <SDL3/SDL_main.h>
/* Stolen from the mailing list */
/* Creates a new mouse cursor from an XPM */
/* XPM */
static const char *arrow[] = {
/* width height num_colors chars_per_pixel */
" 32 32 3 1",
/* colors */
"X c #000000",
". c #ffffff",
" c None",
/* pixels */
"X ",
"XX ",
"X.X ",
"X..X ",
"X...X ",
"X....X ",
"X.....X ",
"X......X ",
"X.......X ",
"X........X ",
"X.....XXXXX ",
"X..X..X ",
"X.X X..X ",
"XX X..X ",
"X X..X ",
" X..X ",
" X..X ",
" X..X ",
" XX ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
"0,0"
};
static const char *cross[] = {
/* width height num_colors chars_per_pixel */
" 32 32 3 1",
/* colors */
"o c #ffffff",
". c #000000",
" c None",
/* pixels */
" ",
" ",
" ",
" ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oooooooooooooooooooooooo ",
" oooooooooooooooooooooooo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" oo ",
" ",
" ",
" ",
" ",
"0,0"
};
static SDLTest_CommonState *state;
static int done;
#define PROP_ARROW_CURSOR_TEXTURE "arrow_cursor_texture"
#define PROP_CROSS_CURSOR_TEXTURE "cross_cursor_texture"
#define MAX_MICE 3
#define MAX_KEYBOARDS 3
#define CURSOR_SIZE 48.0f
#define MAX_TRAIL 500
#define TRAIL_SIZE 8.0f
static SDL_Color colors[] = {
{ 0, 255, 255, 255 }, /* mouse 1, cyan */
{ 255, 0, 255, 255 }, /* mouse 2, magenta */
{ 255, 255, 0, 255 }, /* mouse 3, yellow */
};
SDL_COMPILE_TIME_ASSERT(mouse_colors, SDL_arraysize(colors) == MAX_MICE);
SDL_COMPILE_TIME_ASSERT(keyboard_colors, SDL_arraysize(colors) == MAX_KEYBOARDS);
typedef struct
{
SDL_MouseID instance_id;
SDL_bool active;
Uint8 button_state;
SDL_FPoint position;
int trail_head;
int trail_length;
SDL_FPoint trail[MAX_TRAIL];
} MouseState;
static MouseState mice[MAX_MICE];
typedef struct
{
SDL_KeyboardID instance_id;
SDL_bool active;
Uint8 button_state;
SDL_FPoint position;
} KeyboardState;
static KeyboardState keyboards[MAX_KEYBOARDS];
static SDL_Texture *CreateTexture(const char *image[], SDL_Renderer *renderer)
{
SDL_Surface *surface;
SDL_Palette *palette;
SDL_Texture *texture;
int row;
surface = SDL_CreateSurface(32, 32, SDL_PIXELFORMAT_INDEX8);
for (row = 0; row < surface->h; ++row) {
SDL_memcpy((Uint8 *)surface->pixels + row * surface->pitch, image[4 + row], surface->w);
}
palette = SDL_CreatePalette(256);
if (!palette) {
SDL_DestroySurface(surface);
return NULL;
}
palette->colors['.'].r = 0xFF;
palette->colors['.'].g = 0xFF;
palette->colors['.'].b = 0xFF;
palette->colors['o'].r = 0xFF;
palette->colors['o'].g = 0xFF;
palette->colors['o'].b = 0xFF;
palette->colors['X'].r = 0x00;
palette->colors['X'].g = 0x00;
palette->colors['X'].b = 0x00;
SDL_SetSurfacePalette(surface, palette);
SDL_DestroyPalette(palette);
SDL_SetSurfaceColorKey(surface, SDL_TRUE, ' ');
texture = SDL_CreateTextureFromSurface(renderer, surface);
SDL_DestroySurface(surface);
return texture;
}
static void HandleMouseAdded(SDL_MouseID instance_id)
{
SDL_Window *window = state->windows[0];
int i, w = 0, h = 0;
SDL_GetWindowSize(window, &w, &h);
for (i = 0; i < SDL_arraysize(mice); ++i) {
MouseState *mouse_state = &mice[i];
if (!mouse_state->active) {
mouse_state->instance_id = instance_id;
mouse_state->active = SDL_TRUE;
mouse_state->position.x = w * 0.5f;
mouse_state->position.y = h * 0.5f;
return;
}
}
}
static void HandleMouseRemoved(SDL_MouseID instance_id)
{
int i;
for (i = 0; i < SDL_arraysize(mice); ++i) {
MouseState *mouse_state = &mice[i];
if (instance_id == mouse_state->instance_id) {
SDL_zerop(mouse_state);
return;
}
}
}
static void ActivateMouse(SDL_MouseID instance_id)
{
int i;
for (i = 0; i < SDL_arraysize(mice); ++i) {
MouseState *mouse_state = &mice[i];
if (mouse_state->active && instance_id == mouse_state->instance_id) {
return;
}
}
HandleMouseAdded(instance_id);
}
static void HandleMouseMotion(SDL_MouseMotionEvent *event)
{
SDL_Window *window = state->windows[0];
int i, w = 0, h = 0;
if (event->which == 0) {
/* The system pointer, not a distinct mouse device */
return;
}
ActivateMouse(event->which);
SDL_GetWindowSize(window, &w, &h);
for (i = 0; i < SDL_arraysize(mice); ++i) {
MouseState *mouse_state = &mice[i];
if (!mouse_state->active) {
continue;
}
if (event->which == mouse_state->instance_id) {
float x = (mouse_state->position.x + event->xrel);
float y = (mouse_state->position.y + event->yrel);
x = SDL_clamp(x, 0.0f, (float)w);
y = SDL_clamp(y, 0.0f, (float)h);
mouse_state->position.x = x;
mouse_state->position.y = y;
if (mouse_state->button_state) {
/* Add a spot to the mouse trail */
SDL_FPoint *spot = &mouse_state->trail[mouse_state->trail_head];
spot->x = x - TRAIL_SIZE * 0.5f;
spot->y = y - TRAIL_SIZE * 0.5f;
if (mouse_state->trail_length < MAX_TRAIL) {
++mouse_state->trail_length;
}
mouse_state->trail_head = (mouse_state->trail_head + 1) % MAX_TRAIL;
}
}
}
}
static void HandleMouseButton(SDL_MouseButtonEvent *event)
{
int i;
if (event->which == 0) {
/* The system pointer, not a distinct mouse device */
return;
}
ActivateMouse(event->which);
for (i = 0; i < SDL_arraysize(mice); ++i) {
MouseState *mouse_state = &mice[i];
if (!mouse_state->active) {
continue;
}
if (event->which == mouse_state->instance_id) {
if (event->state) {
mouse_state->button_state |= SDL_BUTTON(event->button);
} else {
mouse_state->button_state &= ~SDL_BUTTON(event->button);
}
}
}
}
static void DrawMouseState(SDL_Window *window, SDL_Renderer *renderer, MouseState *mouse_state, SDL_Texture *cursor, SDL_Color *color)
{
SDL_FRect rect;
if (!mouse_state->active) {
return;
}
if (mouse_state->trail_length > 0) {
int i;
int spot = mouse_state->trail_head - mouse_state->trail_length;
if (spot < 0) {
spot += MAX_TRAIL;
}
rect.w = TRAIL_SIZE;
rect.h = TRAIL_SIZE;
SDL_SetRenderDrawColor(renderer, color->r, color->g, color->b, color->a);
for (i = 0; i < mouse_state->trail_length; ++i) {
rect.x = mouse_state->trail[spot].x;
rect.y = mouse_state->trail[spot].y;
SDL_RenderFillRect(renderer, &rect);
spot = (spot + 1) % MAX_TRAIL;
}
}
rect.x = mouse_state->position.x;
rect.y = mouse_state->position.y;
rect.w = CURSOR_SIZE;
rect.h = CURSOR_SIZE;
SDL_SetTextureColorMod(cursor, color->r, color->g, color->b);
SDL_RenderTexture(renderer, cursor, NULL, &rect);
}
static void HandleKeyboardAdded(SDL_KeyboardID instance_id)
{
SDL_Window *window = state->windows[0];
int i, w = 0, h = 0;
SDL_GetWindowSize(window, &w, &h);
for (i = 0; i < SDL_arraysize(keyboards); ++i) {
KeyboardState *keyboard_state = &keyboards[i];
if (!keyboard_state->active) {
keyboard_state->instance_id = instance_id;
keyboard_state->active = SDL_TRUE;
keyboard_state->position.x = w * 0.5f;
keyboard_state->position.y = h * 0.5f;
return;
}
}
}
static void HandleKeyboardRemoved(SDL_KeyboardID instance_id)
{
int i;
for (i = 0; i < SDL_arraysize(keyboards); ++i) {
KeyboardState *keyboard_state = &keyboards[i];
if (instance_id == keyboard_state->instance_id) {
SDL_zerop(keyboard_state);
return;
}
}
}
static void ActivateKeyboard(SDL_KeyboardID instance_id)
{
int i;
for (i = 0; i < SDL_arraysize(keyboards); ++i) {
KeyboardState *keyboard_state = &keyboards[i];
if (keyboard_state->active && instance_id == keyboard_state->instance_id) {
return;
}
}
HandleKeyboardAdded(instance_id);
}
static void HandleKeyboardKeyDown(SDL_KeyboardEvent *event)
{
SDL_Window *window = state->windows[0];
int i, w = 0, h = 0;
SDL_GetWindowSize(window, &w, &h);
ActivateKeyboard(event->which);
for (i = 0; i < SDL_arraysize(keyboards); ++i) {
KeyboardState *keyboard_state = &keyboards[i];
if (!keyboard_state->active) {
continue;
}
if (event->which == keyboard_state->instance_id) {
switch (event->keysym.sym) {
case SDLK_LEFT:
keyboard_state->position.x -= CURSOR_SIZE;
if (keyboard_state->position.x < 0.0f) {
keyboard_state->position.x = 0.0f;
}
break;
case SDLK_RIGHT:
keyboard_state->position.x += CURSOR_SIZE;
if (keyboard_state->position.x > w) {
keyboard_state->position.x = w;
}
break;
case SDLK_UP:
keyboard_state->position.y -= CURSOR_SIZE;
if (keyboard_state->position.y < 0.0f) {
keyboard_state->position.y = 0.0f;
}
break;
case SDLK_DOWN:
keyboard_state->position.y += CURSOR_SIZE;
if (keyboard_state->position.y > h) {
keyboard_state->position.y = h;
}
break;
default:
break;
}
}
}
}
static void DrawKeyboardState(SDL_Window *window, SDL_Renderer *renderer, KeyboardState *keyboard_state, SDL_Texture *cursor, SDL_Color *color)
{
SDL_FRect rect;
if (!keyboard_state->active) {
return;
}
rect.x = keyboard_state->position.x - CURSOR_SIZE / 2;
rect.y = keyboard_state->position.y - CURSOR_SIZE / 2;
rect.w = CURSOR_SIZE;
rect.h = CURSOR_SIZE;
SDL_SetTextureColorMod(cursor, color->r, color->g, color->b);
SDL_RenderTexture(renderer, cursor, NULL, &rect);
}
static void loop(void)
{
int i, j;
SDL_Event event;
/* Check for events */
while (SDL_PollEvent(&event)) {
SDLTest_CommonEvent(state, &event, &done);
switch (event.type) {
case SDL_EVENT_KEYBOARD_ADDED:
/* Wait for events before activating this keyboard */
break;
case SDL_EVENT_KEYBOARD_REMOVED:
HandleKeyboardRemoved(event.kdevice.which);
break;
case SDL_EVENT_KEY_DOWN:
HandleKeyboardKeyDown(&event.key);
break;
case SDL_EVENT_MOUSE_ADDED:
/* Wait for events before activating this mouse */
break;
case SDL_EVENT_MOUSE_REMOVED:
HandleMouseRemoved(event.mdevice.which);
break;
case SDL_EVENT_MOUSE_MOTION:
HandleMouseMotion(&event.motion);
break;
case SDL_EVENT_MOUSE_BUTTON_DOWN:
case SDL_EVENT_MOUSE_BUTTON_UP:
HandleMouseButton(&event.button);
break;
default:
break;
}
}
for (i = 0; i < state->num_windows; ++i) {
SDL_Window *window = state->windows[i];
SDL_Renderer *renderer = state->renderers[i];
SDL_Texture *arrow_cursor = (SDL_Texture *)SDL_GetProperty(SDL_GetRendererProperties(renderer), PROP_ARROW_CURSOR_TEXTURE, NULL);
SDL_Texture *cross_cursor = (SDL_Texture *)SDL_GetProperty(SDL_GetRendererProperties(renderer), PROP_CROSS_CURSOR_TEXTURE, NULL);
SDL_SetRenderDrawColor(renderer, 128, 128, 128, 255);
SDL_RenderClear(renderer);
for (j = 0; j < SDL_arraysize(mice); ++j) {
DrawMouseState(window, renderer, &mice[j], arrow_cursor, &colors[j]);
}
for (j = 0; j < SDL_arraysize(keyboards); ++j) {
DrawKeyboardState(window, renderer, &keyboards[j], cross_cursor, &colors[j]);
}
SDL_RenderPresent(renderer);
}
}
int main(int argc, char *argv[])
{
int i;
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Log all events, including mouse motion */
SDL_SetHint(SDL_HINT_EVENT_LOGGING, "2");
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, SDL_INIT_VIDEO);
if (!state) {
return 1;
}
for (i = 1; i < argc;) {
int consumed;
consumed = SDLTest_CommonArg(state, i);
if (consumed < 0) {
SDLTest_CommonLogUsage(state, argv[0], NULL);
SDLTest_CommonQuit(state);
return 1;
}
}
if (!SDLTest_CommonInit(state)) {
SDLTest_CommonQuit(state);
return 2;
}
/* Create the cursor textures */
for (i = 0; i < state->num_windows; ++i) {
SDL_Renderer *renderer = state->renderers[i];
SDL_Texture *cursor_arrow = CreateTexture(arrow, renderer);
SDL_Texture *cursor_cross = CreateTexture(cross, renderer);
SDL_SetProperty(SDL_GetRendererProperties(renderer), PROP_ARROW_CURSOR_TEXTURE, cursor_arrow);
SDL_SetProperty(SDL_GetRendererProperties(renderer), PROP_CROSS_CURSOR_TEXTURE, cursor_cross);
}
/* We only get mouse motion for distinct devices when relative mode is enabled */
SDL_SetRelativeMouseMode(SDL_TRUE);
/* Main render loop */
done = 0;
while (!done) {
loop();
}
SDLTest_CommonQuit(state);
return 0;
}

View File

@ -182,8 +182,8 @@ int main(int argc, char *argv[])
{
int status = 0;
SDL_Event event;
intptr_t eventNumber = SDL_RegisterEvents(1);
SDL_Thread *thread = SDL_CreateThread(&button_messagebox, "MessageBox", (void *)eventNumber);
Uint32 eventNumber = SDL_RegisterEvents(1);
SDL_Thread *thread = SDL_CreateThread(&button_messagebox, "MessageBox", (void *)(uintptr_t)eventNumber);
while (SDL_WaitEvent(&event)) {
if (event.type == eventNumber) {

View File

@ -14,13 +14,13 @@
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h> /* exit() */
#ifdef __IOS__
#ifdef SDL_PLATFORM_IOS
#define SCREEN_WIDTH 320
#define SCREEN_HEIGHT 480
#else
@ -213,6 +213,8 @@ static void loop(void *arg)
active->isRect = isRect;
}
break;
default:
break;
}
break;
@ -245,7 +247,7 @@ static void loop(void *arg)
SDL_RenderPresent(renderer);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (loop_data->done) {
emscripten_cancel_main_loop();
}
@ -294,7 +296,7 @@ int main(int argc, char *argv[])
}
/* Main render loop */
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop_arg(loop, &loop_data, 0, 1);
#else
while (loop_data.done == SDL_FALSE) {

View File

@ -15,13 +15,11 @@
#include "testutils.h"
#include <stdio.h> /* for fflush() and stdout */
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include "testutils.h"
#include <stdio.h> /* for fflush() and stdout */
static SDL_AudioSpec spec;
static Uint8 *sound = NULL; /* Pointer to wave data */
@ -31,7 +29,7 @@ static Uint32 soundlen = 0; /* Length of wave data */
static SDL_AudioStream *stream = NULL;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
static void loop(void)
{
if (SDL_GetAudioStreamAvailable(stream) == 0) {
@ -51,7 +49,7 @@ test_multi_audio(SDL_AudioDeviceID *devices, int devcount)
SDL_AudioStream **streams = NULL;
int i;
#ifdef __ANDROID__ /* !!! FIXME: maybe always create a window, in the SDLTest layer, so these #ifdefs don't have to be here? */
#ifdef SDL_PLATFORM_ANDROID /* !!! FIXME: maybe always create a window, in the SDLTest layer, so these #ifdefs don't have to be here? */
SDL_Event event;
/* Create a Window to get fully initialized event processing for testing pause on Android. */
@ -69,11 +67,11 @@ test_multi_audio(SDL_AudioDeviceID *devices, int devcount)
SDL_ResumeAudioDevice(SDL_GetAudioStreamDevice(stream));
SDL_PutAudioStreamData(stream, sound, soundlen);
SDL_FlushAudioStream(stream);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (SDL_GetAudioStreamAvailable(stream) > 0) {
#ifdef __ANDROID__
#ifdef SDL_PLATFORM_ANDROID
/* Empty queue, some application events would prevent pause. */
while (SDL_PollEvent(&event)) {
}
@ -118,7 +116,7 @@ test_multi_audio(SDL_AudioDeviceID *devices, int devcount)
keep_going = 1;
}
}
#ifdef __ANDROID__
#ifdef SDL_PLATFORM_ANDROID
/* Empty queue, some application events would prevent pause. */
while (SDL_PollEvent(&event)) {}
#endif

View File

@ -152,9 +152,9 @@ int main(int argc, char *argv[])
}
props = SDL_CreateProperties();
SDL_SetProperty(props, "sdl2-compat.external_window", native_window);
SDL_SetBooleanProperty(props, SDL_PROPERTY_WINDOW_CREATE_OPENGL_BOOLEAN, SDL_TRUE);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_WIDTH_NUMBER, WINDOW_W);
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_HEIGHT_NUMBER, WINDOW_H);
SDL_SetBooleanProperty(props, SDL_PROP_WINDOW_CREATE_OPENGL_BOOLEAN, SDL_TRUE);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_WIDTH_NUMBER, WINDOW_W);
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_HEIGHT_NUMBER, WINDOW_H);
window = SDL_CreateWindowWithProperties(props);
SDL_DestroyProperties(props);
if (!window) {

View File

@ -116,7 +116,7 @@ static void *CreateWindowWayland(int w, int h)
/* Export the display object from SDL and use it to create a registry object,
* which will enumerate the wl_compositor and xdg_wm_base protocols.
*/
state.wl_display = SDL_GetProperty(SDL_GetGlobalProperties(), SDL_PROPERTY_GLOBAL_VIDEO_WAYLAND_WL_DISPLAY_POINTER, NULL);
state.wl_display = SDL_GetProperty(SDL_GetGlobalProperties(), SDL_PROP_GLOBAL_VIDEO_WAYLAND_WL_DISPLAY_POINTER, NULL);
if (!state.wl_display) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Invalid 'wl_display' object!");

View File

@ -12,18 +12,18 @@
/* Simple program: picks the offscreen backend and renders each frame to a bmp */
#include <stdlib.h>
#include <time.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_opengl.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#include <time.h>
static SDL_Renderer *renderer = NULL;
static SDL_Window *window = NULL;
static int done = SDL_FALSE;
@ -52,15 +52,10 @@ static void draw(void)
static void save_surface_to_bmp(void)
{
SDL_Surface* surface;
Uint32 pixel_format;
SDL_Surface *surface;
char file[128];
pixel_format = SDL_GetWindowPixelFormat(window);
surface = SDL_CreateSurface(width, height, pixel_format);
SDL_RenderReadPixels(renderer, NULL, pixel_format, surface->pixels, surface->pitch);
surface = SDL_RenderReadPixels(renderer, NULL);
(void)SDL_snprintf(file, sizeof(file), "SDL_window%" SDL_PRIs32 "-%8.8d.bmp",
SDL_GetWindowID(window), ++frame_number);
@ -79,13 +74,15 @@ static void loop(void)
case SDL_EVENT_QUIT:
done = SDL_TRUE;
break;
default:
break;
}
}
draw();
save_surface_to_bmp();
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -94,7 +91,7 @@ static void loop(void)
int main(int argc, char *argv[])
{
#ifndef __EMSCRIPTEN__
#ifndef SDL_PLATFORM_EMSCRIPTEN
Uint64 then, now;
Uint32 frames;
#endif
@ -142,7 +139,7 @@ int main(int argc, char *argv[])
srand((unsigned int)time(NULL));
#ifndef __EMSCRIPTEN__
#ifndef SDL_PLATFORM_EMSCRIPTEN
/* Main render loop */
frames = 0;
then = SDL_GetTicks();
@ -151,7 +148,7 @@ int main(int argc, char *argv[])
SDL_Log("Rendering %u frames offscreen\n", max_frames);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done && frames < max_frames) {

View File

@ -16,17 +16,17 @@
* *
********************************************************************************/
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#define MOOSEPIC_W 64
#define MOOSEPIC_H 88
@ -282,10 +282,13 @@ static void loop(void)
if (event.key.keysym.sym != SDLK_ESCAPE) {
break;
}
break;
default:
break;
}
}
#ifndef __EMSCRIPTEN__
#ifndef SDL_PLATFORM_EMSCRIPTEN
SDL_Delay(fpsdelay);
#endif
@ -295,7 +298,7 @@ static void loop(void)
}
MoveSprites(state->renderers[i]);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -316,7 +319,7 @@ static void loop(void)
int main(int argc, char **argv)
{
SDL_RWops *handle;
SDL_IOStream *handle;
int i;
int j;
int fps = 12;
@ -441,16 +444,16 @@ int main(int argc, char **argv)
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Out of memory\n");
quit(2);
}
handle = SDL_RWFromFile(filename, "rb");
handle = SDL_IOFromFile(filename, "rb");
SDL_free(filename);
if (!handle) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Can't find the file moose.dat !\n");
quit(2);
}
SDL_RWread(handle, RawMooseData, MOOSEFRAME_SIZE * MOOSEFRAMES_COUNT);
SDL_ReadIO(handle, RawMooseData, MOOSEFRAME_SIZE * MOOSEFRAMES_COUNT);
SDL_RWclose(handle);
SDL_CloseIO(handle);
/* Create the window and renderer */
window_w = MOOSEPIC_W * scale;
@ -529,7 +532,7 @@ int main(int argc, char **argv)
done = 0;
/* Loop, waiting for QUIT or RESIZE */
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, nodelay ? 0 : fps, 1);
#else
while (!done) {

View File

@ -19,11 +19,9 @@
3. This notice may not be removed or altered from any source distribution.
*/
#include <math.h>
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_test_common.h>
#define WIDTH 1600
#define HEIGHT 1200
@ -152,13 +150,13 @@ static void DrawScreen(SDL_Renderer *renderer)
(color & 0x01) ? 0xff : 0,
(color & 0x02) ? 0xff : 0,
(color & 0x04) ? 0xff : 0,
(int)(0xff * last_pressure));
(Uint8)(0xff * last_pressure));
/* Cone base width based on pressure: */
SDL_RenderLine(renderer, X, Y, endx + (ydelta * last_pressure / 3.0f), endy - (xdelta * last_pressure / 3.0f));
SDL_RenderLine(renderer, X, Y, endx - (ydelta * last_pressure / 3.0f), endy + (xdelta * last_pressure / 3.0f));
/* If tilt is very small (or zero, for pens that don't have tilt), add some extra lines, rotated by the current rotation value */
if (ALWAYS_SHOW_PRESSURE_BOX || (fabs(tilt_vec_x) < 0.2f && fabs(tilt_vec_y) < 0.2f)) {
if (ALWAYS_SHOW_PRESSURE_BOX || (SDL_fabsf(tilt_vec_x) < 0.2f && SDL_fabsf(tilt_vec_y) < 0.2f)) {
int rot;
float pressure = last_pressure * 80.0f;
@ -468,7 +466,7 @@ static void process_event(SDL_Event event)
last_button = 0;
last_touching = (ev->type != SDL_EVENT_FINGER_UP);
#if VERBOSE
SDL_Log("[%lu] finger %s: %s (touchId: %" SDL_PRIs64 ", fingerId: %" SDL_PRIs64 ") at (%.4f, %.4f); pressure=%.3f\n",
SDL_Log("[%lu] finger %s: %s (touchId: %" SDL_PRIu64 ", fingerId: %" SDL_PRIu64 ") at (%.4f, %.4f); pressure=%.3f\n",
(unsigned long) ev->timestamp,
ev->type == SDL_EVENT_FINGER_DOWN ? "down" : (ev->type == SDL_EVENT_FINGER_MOTION ? "motion" : "up"),
SDL_GetTouchDeviceName(ev->touchId),
@ -509,8 +507,6 @@ int main(int argc, char *argv[])
return 1;
}
SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "2");
state->window_title = "Pressure-Sensitive Pen Test";
state->window_w = WIDTH;
state->window_h = HEIGHT;

View File

@ -238,124 +238,124 @@ typedef struct
} LL_Test;
static LL_Test LL_Tests[] = {
/* UNDEFINED {"_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 65, 0x0000000000000000ll}, */
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 1, 0xFFFFFFFFFFFFFFFEll },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 32, 0xFFFFFFFF00000000ll },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 33, 0xFFFFFFFE00000000ll },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 0, 0xFFFFFFFFFFFFFFFFll },
/* UNDEFINED {"_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 65, 0x0000000000000000ll}, */
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 1, 0xFFFFFFFFFFFFFFFEllu },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 32, 0xFFFFFFFF00000000llu },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 33, 0xFFFFFFFE00000000llu },
{ "_allshl", &TST_allshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_allshr", &TST_allshr, 0xAAAAAAAA55555555ll, 0ll, 63, 0xFFFFFFFFFFFFFFFFll },
/* UNDEFINED {"_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 65, 0xFFFFFFFFFFFFFFFFll}, */
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 1, 0xFFFFFFFFFFFFFFFFll },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 32, 0xFFFFFFFFFFFFFFFFll },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 33, 0xFFFFFFFFFFFFFFFFll },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 0, 0xFFFFFFFFFFFFFFFFll },
/* UNDEFINED {"_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fll, 0ll, 65, 0x0000000000000000ll}, */
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fll, 0ll, 1, 0x2FAFAFAFAFAFAFAFll },
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fll, 0ll, 32, 0x000000005F5F5F5Fll },
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fll, 0ll, 33, 0x000000002FAFAFAFll },
{ "_allshr", &TST_allshr, 0xAAAAAAAA55555555llu, 0llu, 63, 0xFFFFFFFFFFFFFFFFllu },
/* UNDEFINED {"_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 65, 0xFFFFFFFFFFFFFFFFll}, */
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 1, 0xFFFFFFFFFFFFFFFFllu },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 32, 0xFFFFFFFFFFFFFFFFllu },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 33, 0xFFFFFFFFFFFFFFFFllu },
{ "_allshr", &TST_allshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 0, 0xFFFFFFFFFFFFFFFFllu },
/* UNDEFINED {"_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fllu, 0llu, 65, 0x0000000000000000ll}, */
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fllu, 0llu, 1, 0x2FAFAFAFAFAFAFAFllu },
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fllu, 0llu, 32, 0x000000005F5F5F5Fllu },
{ "_allshr", &TST_allshr, 0x5F5F5F5F5F5F5F5Fllu, 0llu, 33, 0x000000002FAFAFAFllu },
/* UNDEFINED {"_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 65, 0x0000000000000000ll}, */
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 1, 0xFFFFFFFFFFFFFFFEll },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 32, 0xFFFFFFFF00000000ll },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 33, 0xFFFFFFFE00000000ll },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFll, 0ll, 0, 0xFFFFFFFFFFFFFFFFll },
/* UNDEFINED {"_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 65, 0x0000000000000000ll}, */
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 1, 0xFFFFFFFFFFFFFFFEllu },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 32, 0xFFFFFFFF00000000llu },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 33, 0xFFFFFFFE00000000llu },
{ "_aullshl", &TST_aullshl, 0xFFFFFFFFFFFFFFFFllu, 0llu, 0, 0xFFFFFFFFFFFFFFFFllu },
/* UNDEFINED {"_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 65, 0x0000000000000000ll}, */
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 1, 0x7FFFFFFFFFFFFFFFll },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 32, 0x00000000FFFFFFFFll },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 33, 0x000000007FFFFFFFll },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFll, 0ll, 0, 0xFFFFFFFFFFFFFFFFll },
/* UNDEFINED {"_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 65, 0x0000000000000000ll}, */
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 1, 0x7FFFFFFFFFFFFFFFllu },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 32, 0x00000000FFFFFFFFllu },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 33, 0x000000007FFFFFFFllu },
{ "_aullshr", &TST_aullshr, 0xFFFFFFFFFFFFFFFFllu, 0llu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFFll, 0x0000000000000000ll, 0, 0x0000000000000000ll },
{ "_allmul", &TST_allmul, 0x0000000000000000ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFll, 0x0000000000000001ll, 0, 0x000000000FFFFFFFll },
{ "_allmul", &TST_allmul, 0x0000000000000001ll, 0x000000000FFFFFFFll, 0, 0x000000000FFFFFFFll },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFll, 0x0000000000000010ll, 0, 0x00000000FFFFFFF0ll },
{ "_allmul", &TST_allmul, 0x0000000000000010ll, 0x000000000FFFFFFFll, 0, 0x00000000FFFFFFF0ll },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFll, 0x0000000000000100ll, 0, 0x0000000FFFFFFF00ll },
{ "_allmul", &TST_allmul, 0x0000000000000100ll, 0x000000000FFFFFFFll, 0, 0x0000000FFFFFFF00ll },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFll, 0x0000000010000000ll, 0, 0x00FFFFFFF0000000ll },
{ "_allmul", &TST_allmul, 0x0000000010000000ll, 0x000000000FFFFFFFll, 0, 0x00FFFFFFF0000000ll },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFll, 0x0000000080000000ll, 0, 0x07FFFFFF80000000ll },
{ "_allmul", &TST_allmul, 0x0000000080000000ll, 0x000000000FFFFFFFll, 0, 0x07FFFFFF80000000ll },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000000ll, 0, 0xFFFFFFFF00000000ll },
{ "_allmul", &TST_allmul, 0x0000000080000000ll, 0xFFFFFFFFFFFFFFFEll, 0, 0xFFFFFFFF00000000ll },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000008ll, 0, 0xFFFFFFFEFFFFFFF0ll },
{ "_allmul", &TST_allmul, 0x0000000080000008ll, 0xFFFFFFFFFFFFFFFEll, 0, 0xFFFFFFFEFFFFFFF0ll },
{ "_allmul", &TST_allmul, 0x00000000FFFFFFFFll, 0x00000000FFFFFFFFll, 0, 0xFFFFFFFE00000001ll },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFFllu, 0x0000000000000000llu, 0, 0x0000000000000000llu },
{ "_allmul", &TST_allmul, 0x0000000000000000llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFllu, 0x0000000000000001llu, 0, 0x000000000FFFFFFFllu },
{ "_allmul", &TST_allmul, 0x0000000000000001llu, 0x000000000FFFFFFFllu, 0, 0x000000000FFFFFFFllu },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFllu, 0x0000000000000010llu, 0, 0x00000000FFFFFFF0llu },
{ "_allmul", &TST_allmul, 0x0000000000000010llu, 0x000000000FFFFFFFllu, 0, 0x00000000FFFFFFF0llu },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFllu, 0x0000000000000100llu, 0, 0x0000000FFFFFFF00llu },
{ "_allmul", &TST_allmul, 0x0000000000000100llu, 0x000000000FFFFFFFllu, 0, 0x0000000FFFFFFF00llu },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFllu, 0x0000000010000000llu, 0, 0x00FFFFFFF0000000llu },
{ "_allmul", &TST_allmul, 0x0000000010000000llu, 0x000000000FFFFFFFllu, 0, 0x00FFFFFFF0000000llu },
{ "_allmul", &TST_allmul, 0x000000000FFFFFFFllu, 0x0000000080000000llu, 0, 0x07FFFFFF80000000llu },
{ "_allmul", &TST_allmul, 0x0000000080000000llu, 0x000000000FFFFFFFllu, 0, 0x07FFFFFF80000000llu },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000000llu, 0, 0xFFFFFFFF00000000llu },
{ "_allmul", &TST_allmul, 0x0000000080000000llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0xFFFFFFFF00000000llu },
{ "_allmul", &TST_allmul, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000008llu, 0, 0xFFFFFFFEFFFFFFF0llu },
{ "_allmul", &TST_allmul, 0x0000000080000008llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0xFFFFFFFEFFFFFFF0llu },
{ "_allmul", &TST_allmul, 0x00000000FFFFFFFFllu, 0x00000000FFFFFFFFllu, 0, 0xFFFFFFFE00000001llu },
{ "_alldiv", &TST_alldiv, 0x0000000000000000ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_alldiv", &TST_alldiv, 0x0000000000000000ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_alldiv", &TST_alldiv, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0xFFFFFFFFFFFFFFFFll },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFFll, 0x0000000000000001ll, 0, 0xFFFFFFFFFFFFFFFFll },
{ "_alldiv", &TST_alldiv, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0xFFFFFFFFFFFFFFFFll },
{ "_alldiv", &TST_alldiv, 0x0000000000000001ll, 0x0000000000000001ll, 0, 0x0000000000000001ll },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFFll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000001ll },
{ "_alldiv", &TST_alldiv, 0x000000000FFFFFFFll, 0x0000000000000001ll, 0, 0x000000000FFFFFFFll },
{ "_alldiv", &TST_alldiv, 0x0000000FFFFFFFFFll, 0x0000000000000010ll, 0, 0x00000000FFFFFFFFll },
{ "_alldiv", &TST_alldiv, 0x0000000000000100ll, 0x000000000FFFFFFFll, 0, 0x0000000000000000ll },
{ "_alldiv", &TST_alldiv, 0x00FFFFFFF0000000ll, 0x0000000010000000ll, 0, 0x000000000FFFFFFFll },
{ "_alldiv", &TST_alldiv, 0x07FFFFFF80000000ll, 0x0000000080000000ll, 0, 0x000000000FFFFFFFll },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000000ll, 0, 0x0000000000000000ll },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x0000000080000008ll },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0xC000000080000008ll },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0ll, 0x0000FFFFFFFFFFFEll, 0, 0x0000000000007FFFll },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0ll, 0x7FFFFFFEFFFFFFF0ll, 0, 0x0000000000000001ll },
{ "_alldiv", &TST_alldiv, 0x0000000000000000llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_alldiv", &TST_alldiv, 0x0000000000000000llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_alldiv", &TST_alldiv, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFFllu, 0x0000000000000001llu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0x0000000000000001llu, 0x0000000000000001llu, 0, 0x0000000000000001llu },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFFllu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000001llu },
{ "_alldiv", &TST_alldiv, 0x000000000FFFFFFFllu, 0x0000000000000001llu, 0, 0x000000000FFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0x0000000FFFFFFFFFllu, 0x0000000000000010llu, 0, 0x00000000FFFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0x0000000000000100llu, 0x000000000FFFFFFFllu, 0, 0x0000000000000000llu },
{ "_alldiv", &TST_alldiv, 0x00FFFFFFF0000000llu, 0x0000000010000000llu, 0, 0x000000000FFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0x07FFFFFF80000000llu, 0x0000000080000000llu, 0, 0x000000000FFFFFFFllu },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000000llu, 0, 0x0000000000000000llu },
{ "_alldiv", &TST_alldiv, 0xFFFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x0000000080000008llu },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0xC000000080000008llu },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0llu, 0x0000FFFFFFFFFFFEllu, 0, 0x0000000000007FFFllu },
{ "_alldiv", &TST_alldiv, 0x7FFFFFFEFFFFFFF0llu, 0x7FFFFFFEFFFFFFF0llu, 0, 0x0000000000000001llu },
{ "_allrem", &TST_allrem, 0x0000000000000000ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000000000000ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFFll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000000000001ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFFll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x000000000FFFFFFFll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000FFFFFFFFFll, 0x0000000000000010ll, 0, 0x000000000000000Fll },
{ "_allrem", &TST_allrem, 0x0000000000000100ll, 0x000000000FFFFFFFll, 0, 0x0000000000000100ll },
{ "_allrem", &TST_allrem, 0x00FFFFFFF0000000ll, 0x0000000010000000ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x07FFFFFF80000000ll, 0x0000000080000000ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000000ll, 0, 0xFFFFFFFFFFFFFFFEll },
{ "_allrem", &TST_allrem, 0xFFFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0ll, 0x0000FFFFFFFFFFFEll, 0, 0x0000FFFF0000FFEEll },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0ll, 0x7FFFFFFEFFFFFFF0ll, 0, 0x0000000000000000ll },
{ "_allrem", &TST_allrem, 0x0000000000000000llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x0000000000000000llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFFllu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x0000000000000001llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFFllu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x000000000FFFFFFFllu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x0000000FFFFFFFFFllu, 0x0000000000000010llu, 0, 0x000000000000000Fllu },
{ "_allrem", &TST_allrem, 0x0000000000000100llu, 0x000000000FFFFFFFllu, 0, 0x0000000000000100llu },
{ "_allrem", &TST_allrem, 0x00FFFFFFF0000000llu, 0x0000000010000000llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x07FFFFFF80000000llu, 0x0000000080000000llu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000000llu, 0, 0xFFFFFFFFFFFFFFFEllu },
{ "_allrem", &TST_allrem, 0xFFFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x0000000000000000llu },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0llu, 0x0000FFFFFFFFFFFEllu, 0, 0x0000FFFF0000FFEEllu },
{ "_allrem", &TST_allrem, 0x7FFFFFFEFFFFFFF0llu, 0x7FFFFFFEFFFFFFF0llu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000000ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000000ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFFll, 0x0000000000000001ll, 0, 0xFFFFFFFFFFFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001ll, 0x0000000000000001ll, 0, 0x0000000000000001ll },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFFll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000001ll },
{ "_ualldiv", &TST_ualldiv, 0x000000000FFFFFFFll, 0x0000000000000001ll, 0, 0x000000000FFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0x0000000FFFFFFFFFll, 0x0000000000000010ll, 0, 0x00000000FFFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000100ll, 0x000000000FFFFFFFll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x00FFFFFFF0000000ll, 0x0000000010000000ll, 0, 0x000000000FFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0x07FFFFFF80000000ll, 0x0000000080000000ll, 0, 0x000000000FFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000000ll, 0, 0x00000001FFFFFFFFll },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x0000000000000000ll },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0ll, 0x0000FFFFFFFFFFFEll, 0, 0x0000000000007FFFll },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0ll, 0x7FFFFFFEFFFFFFF0ll, 0, 0x0000000000000001ll },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000000llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000000llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFFllu, 0x0000000000000001llu, 0, 0xFFFFFFFFFFFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000001llu, 0x0000000000000001llu, 0, 0x0000000000000001llu },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFFllu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000001llu },
{ "_ualldiv", &TST_ualldiv, 0x000000000FFFFFFFllu, 0x0000000000000001llu, 0, 0x000000000FFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0x0000000FFFFFFFFFllu, 0x0000000000000010llu, 0, 0x00000000FFFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0x0000000000000100llu, 0x000000000FFFFFFFllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x00FFFFFFF0000000llu, 0x0000000010000000llu, 0, 0x000000000FFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0x07FFFFFF80000000llu, 0x0000000080000000llu, 0, 0x000000000FFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000000llu, 0, 0x00000001FFFFFFFFllu },
{ "_ualldiv", &TST_ualldiv, 0xFFFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x0000000000000000llu },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0llu, 0x0000FFFFFFFFFFFEllu, 0, 0x0000000000007FFFllu },
{ "_ualldiv", &TST_ualldiv, 0x7FFFFFFEFFFFFFF0llu, 0x7FFFFFFEFFFFFFF0llu, 0, 0x0000000000000001llu },
{ "_uallrem", &TST_uallrem, 0x0000000000000000ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x0000000000000000ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000001ll },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFFll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x0000000000000001ll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000001ll },
{ "_uallrem", &TST_uallrem, 0x0000000000000001ll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFFll, 0xFFFFFFFFFFFFFFFFll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x000000000FFFFFFFll, 0x0000000000000001ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x0000000FFFFFFFFFll, 0x0000000000000010ll, 0, 0x000000000000000Fll },
{ "_uallrem", &TST_uallrem, 0x0000000000000100ll, 0x000000000FFFFFFFll, 0, 0x0000000000000100ll },
{ "_uallrem", &TST_uallrem, 0x00FFFFFFF0000000ll, 0x0000000010000000ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x07FFFFFF80000000ll, 0x0000000080000000ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFEll, 0x0000000080000000ll, 0, 0x000000007FFFFFFEll },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0xFFFFFFFEFFFFFFF0ll },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0ll, 0xFFFFFFFFFFFFFFFEll, 0, 0x7FFFFFFEFFFFFFF0ll },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0ll, 0x0000FFFFFFFFFFFEll, 0, 0x0000FFFF0000FFEEll },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0ll, 0x7FFFFFFEFFFFFFF0ll, 0, 0x0000000000000000ll },
{ "_uallrem", &TST_uallrem, 0x0000000000000000llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x0000000000000000llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000001llu },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFFllu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x0000000000000001llu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000001llu },
{ "_uallrem", &TST_uallrem, 0x0000000000000001llu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFFllu, 0xFFFFFFFFFFFFFFFFllu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x000000000FFFFFFFllu, 0x0000000000000001llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x0000000FFFFFFFFFllu, 0x0000000000000010llu, 0, 0x000000000000000Fllu },
{ "_uallrem", &TST_uallrem, 0x0000000000000100llu, 0x000000000FFFFFFFllu, 0, 0x0000000000000100llu },
{ "_uallrem", &TST_uallrem, 0x00FFFFFFF0000000llu, 0x0000000010000000llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0x07FFFFFF80000000llu, 0x0000000080000000llu, 0, 0x0000000000000000llu },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFFFFFFFFFEllu, 0x0000000080000000llu, 0, 0x000000007FFFFFFEllu },
{ "_uallrem", &TST_uallrem, 0xFFFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0xFFFFFFFEFFFFFFF0llu },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0llu, 0xFFFFFFFFFFFFFFFEllu, 0, 0x7FFFFFFEFFFFFFF0llu },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0llu, 0x0000FFFFFFFFFFFEllu, 0, 0x0000FFFF0000FFEEllu },
{ "_uallrem", &TST_uallrem, 0x7FFFFFFEFFFFFFF0llu, 0x7FFFFFFEFFFFFFF0llu, 0, 0x0000000000000000llu },
{ NULL, NULL, 0, 0, 0, 0 }
};

View File

@ -11,17 +11,17 @@ freely.
*/
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
#include <time.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_test_font.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#include <time.h>
#define MENU_WIDTH 120
#define MENU_HEIGHT 300
@ -95,7 +95,7 @@ static SDL_bool create_popup(struct PopupWindow *new_popup, SDL_bool is_menu)
const int w = is_menu ? MENU_WIDTH : TOOLTIP_WIDTH;
const int h = is_menu ? MENU_HEIGHT : TOOLTIP_HEIGHT;
const int v_off = is_menu ? 0 : 32;
const Uint32 flags = is_menu ? SDL_WINDOW_POPUP_MENU : SDL_WINDOW_TOOLTIP;
const SDL_WindowFlags flags = is_menu ? SDL_WINDOW_POPUP_MENU : SDL_WINDOW_TOOLTIP;
float x, y;
focus = SDL_GetMouseFocus();
@ -269,7 +269,7 @@ int main(int argc, char *argv[])
/* Main render loop */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -14,6 +14,8 @@
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
static int a_global_var = 77;
static int SDLCALL
num_compare(const void *_a, const void *_b)
{
@ -22,20 +24,36 @@ num_compare(const void *_a, const void *_b)
return (a < b) ? -1 : ((a > b) ? 1 : 0);
}
static int SDLCALL
num_compare_r(void *userdata, const void *a, const void *b)
{
if (userdata != &a_global_var) {
SDL_Log("Uhoh, invalid userdata during qsort!");
}
return num_compare(a, b);
}
static void
test_sort(const char *desc, int *nums, const int arraylen)
{
static int nums_copy[1024 * 100];
int i;
int prev;
SDL_assert(SDL_arraysize(nums_copy) >= arraylen);
SDL_Log("test: %s arraylen=%d", desc, arraylen);
SDL_memcpy(nums_copy, nums, arraylen * sizeof (*nums));
SDL_qsort(nums, arraylen, sizeof(nums[0]), num_compare);
SDL_qsort_r(nums_copy, arraylen, sizeof(nums[0]), num_compare_r, &a_global_var);
prev = nums[0];
for (i = 1; i < arraylen; i++) {
const int val = nums[i];
if (val < prev) {
const int val2 = nums_copy[i];
if ((val < prev) || (val != val2)) {
SDL_Log("sort is broken!");
return;
}
@ -53,6 +71,8 @@ int main(int argc, char *argv[])
SDLTest_CommonState *state;
int seed_seen = 0;
SDL_zero(rndctx);
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
if (!state) {

View File

@ -12,16 +12,16 @@
/* Simple program: Test relative mouse motion */
#include <stdlib.h>
#include <time.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#include <time.h>
static SDLTest_CommonState *state;
static int i, done;
static float mouseX, mouseY;
@ -47,6 +47,8 @@ static void loop(void)
mouseX += event.motion.xrel;
mouseY += event.motion.yrel;
} break;
default:
break;
}
}
for (i = 0; i < state->num_windows; ++i) {
@ -77,7 +79,7 @@ static void loop(void)
SDL_RenderPresent(renderer);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -124,7 +126,7 @@ int main(int argc, char *argv[])
rect.h = 10;
/* Main render loop */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -11,16 +11,16 @@
*/
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
static SDLTest_CommonState *state;
typedef struct
@ -78,7 +78,7 @@ static void Draw(DrawState *s)
s->sprite_rect.x = (float)((viewport.w - s->sprite_rect.w) / 2);
s->sprite_rect.y = (float)((viewport.h - s->sprite_rect.h) / 2);
SDL_RenderTextureRotated(s->renderer, s->sprite, NULL, &s->sprite_rect, (double)s->sprite_rect.w, center, (SDL_RendererFlip)s->scale_direction);
SDL_RenderTextureRotated(s->renderer, s->sprite, NULL, &s->sprite_rect, (double)s->sprite_rect.w, center, SDL_FLIP_NONE);
SDL_SetRenderTarget(s->renderer, NULL);
SDL_RenderTexture(s->renderer, target, NULL, NULL);
@ -105,7 +105,7 @@ static void loop(void)
}
Draw(&drawstates[i]);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -155,7 +155,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -11,16 +11,16 @@
*/
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
static SDLTest_CommonState *state;
typedef struct
@ -54,11 +54,11 @@ DrawComposite(DrawState *s)
SDL_Rect viewport;
SDL_FRect R;
SDL_Texture *target;
SDL_Surface *surface;
static SDL_bool blend_tested = SDL_FALSE;
if (!blend_tested) {
SDL_Texture *A, *B;
Uint32 P;
A = SDL_CreateTexture(s->renderer, SDL_PIXELFORMAT_ARGB8888, SDL_TEXTUREACCESS_TARGET, 1, 1);
SDL_SetTextureBlendMode(A, SDL_BLENDMODE_BLEND);
@ -74,9 +74,15 @@ DrawComposite(DrawState *s)
SDL_SetRenderDrawColor(s->renderer, 0x00, 0x00, 0x00, 0x00);
SDL_RenderFillRect(s->renderer, NULL);
SDL_RenderTexture(s->renderer, A, NULL, NULL);
SDL_RenderReadPixels(s->renderer, NULL, SDL_PIXELFORMAT_ARGB8888, &P, sizeof(P));
SDL_Log("Blended pixel: 0x%8.8" SDL_PRIX32 "\n", P);
surface = SDL_RenderReadPixels(s->renderer, NULL);
if (surface) {
Uint8 r, g, b, a;
if (SDL_ReadSurfacePixel(surface, 0, 0, &r, &g, &b, &a) == 0) {
SDL_Log("Blended pixel: 0x%.2x%.2x%.2x%.2x\n", r, g, b, a);
}
SDL_DestroySurface(surface);
}
SDL_DestroyTexture(A);
SDL_DestroyTexture(B);
@ -199,7 +205,7 @@ static void loop(void)
}
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -269,7 +275,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -30,7 +30,7 @@ int main(int argc, char **argv)
int bitsize = 0;
int blockalign = 0;
int avgbytes = 0;
SDL_RWops *io = NULL;
SDL_IOStream *io = NULL;
int dst_len;
int ret = 0;
int argpos = 0;
@ -115,9 +115,9 @@ int main(int argc, char **argv)
}
/* write out a WAV header... */
io = SDL_RWFromFile(file_out, "wb");
io = SDL_IOFromFile(file_out, "wb");
if (!io) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "fopen('%s') failed: %s\n", file_out, SDL_GetError());
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "opening '%s' failed: %s\n", file_out, SDL_GetError());
ret = 5;
goto end;
}
@ -132,17 +132,17 @@ int main(int argc, char **argv)
SDL_WriteU32LE(io, 0x20746D66); /* fmt */
SDL_WriteU32LE(io, 16); /* chunk size */
SDL_WriteU16LE(io, SDL_AUDIO_ISFLOAT(spec.format) ? 3 : 1); /* uncompressed */
SDL_WriteU16LE(io, cvtspec.channels); /* channels */
SDL_WriteU16LE(io, (Uint16)cvtspec.channels); /* channels */
SDL_WriteU32LE(io, cvtspec.freq); /* sample rate */
SDL_WriteU32LE(io, avgbytes); /* average bytes per second */
SDL_WriteU16LE(io, blockalign); /* block align */
SDL_WriteU16LE(io, bitsize); /* significant bits per sample */
SDL_WriteU16LE(io, (Uint16)blockalign); /* block align */
SDL_WriteU16LE(io, (Uint16)bitsize); /* significant bits per sample */
SDL_WriteU32LE(io, 0x61746164); /* data */
SDL_WriteU32LE(io, dst_len); /* size */
SDL_RWwrite(io, dst_buf, dst_len);
SDL_WriteIO(io, dst_buf, dst_len);
if (SDL_RWclose(io) == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "fclose('%s') failed: %s\n", file_out, SDL_GetError());
if (SDL_CloseIO(io) == -1) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "closing '%s' failed: %s\n", file_out, SDL_GetError());
ret = 6;
goto end;
}

View File

@ -39,6 +39,8 @@ int main(int argc, char **argv)
char *name = NULL;
int index;
SDLTest_CommonState *state;
SDL_HapticID *haptics;
int num_haptics;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
@ -85,37 +87,48 @@ int main(int argc, char **argv)
/* Initialize the force feedbackness */
SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_JOYSTICK |
SDL_INIT_HAPTIC);
SDL_Log("%d Haptic devices detected.\n", SDL_NumHaptics());
if (SDL_NumHaptics() > 0) {
haptics = SDL_GetHaptics(&num_haptics);
SDL_Log("%d Haptic devices detected.\n", num_haptics);
if (haptics) {
if (num_haptics == 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "No Haptic devices found!\n");
SDL_free(haptics);
return 1;
}
/* We'll just use index or the first force feedback device found */
if (!name) {
i = (index != -1) ? index : 0;
if (i >= num_haptics) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Index out of range, aborting.\n");
SDL_free(haptics);
return 1;
}
}
/* Try to find matching device */
else {
for (i = 0; i < SDL_NumHaptics(); i++) {
if (SDL_strstr(SDL_HapticName(i), name) != NULL) {
for (i = 0; i < num_haptics; i++) {
if (SDL_strstr(SDL_GetHapticInstanceName(haptics[i]), name) != NULL) {
break;
}
}
if (i >= SDL_NumHaptics()) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to find device matching '%s', aborting.\n",
name);
if (i >= num_haptics) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to find device matching '%s', aborting.\n", name);
SDL_free(haptics);
return 1;
}
}
haptic = SDL_HapticOpen(i);
haptic = SDL_OpenHaptic(haptics[i]);
if (!haptic) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to create the haptic device: %s\n",
SDL_GetError());
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Unable to create the haptic device: %s\n", SDL_GetError());
SDL_free(haptics);
return 1;
}
SDL_Log("Device: %s\n", SDL_HapticName(i));
} else {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "No Haptic devices found!\n");
return 1;
SDL_Log("Device: %s\n", SDL_GetHapticName(haptic));
SDL_free(haptics);
}
/* We only want force feedback errors. */
@ -125,21 +138,21 @@ int main(int argc, char **argv)
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Rumble not supported!\n");
return 1;
}
if (SDL_HapticRumbleInit(haptic) != 0) {
if (SDL_InitHapticRumble(haptic) != 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed to initialize rumble: %s\n", SDL_GetError());
return 1;
}
SDL_Log("Playing 2 second rumble at 0.5 magnitude.\n");
if (SDL_HapticRumblePlay(haptic, 0.5, 5000) != 0) {
if (SDL_PlayHapticRumble(haptic, 0.5, 5000) != 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed to play rumble: %s\n", SDL_GetError());
return 1;
}
SDL_Delay(2000);
SDL_Log("Stopping rumble.\n");
SDL_HapticRumbleStop(haptic);
SDL_StopHapticRumble(haptic);
SDL_Delay(2000);
SDL_Log("Playing 2 second rumble at 0.3 magnitude.\n");
if (SDL_HapticRumblePlay(haptic, 0.3f, 5000) != 0) {
if (SDL_PlayHapticRumble(haptic, 0.3f, 5000) != 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed to play rumble: %s\n", SDL_GetError());
return 1;
}
@ -147,7 +160,7 @@ int main(int argc, char **argv)
/* Quit */
if (haptic) {
SDL_HapticClose(haptic);
SDL_CloseHaptic(haptic);
}
SDL_Quit();

View File

@ -19,7 +19,7 @@
#include <SDL3/SDL_test.h>
static SDL_RWLock *rwlock = NULL;
static SDL_threadID mainthread;
static SDL_ThreadID mainthread;
static SDL_AtomicInt doterminate;
static int nb_threads = 6;
static SDL_Thread **threads;
@ -30,20 +30,20 @@ static SDLTest_CommonState *state;
static void DoWork(const int workticks) /* "Work" */
{
const SDL_threadID tid = SDL_ThreadID();
const SDL_ThreadID tid = SDL_GetCurrentThreadID();
const SDL_bool is_reader = tid != mainthread;
const char *typestr = is_reader ? "Reader" : "Writer";
SDL_Log("%s Thread %lu: ready to work\n", typestr, (unsigned long) tid);
SDL_Log("%s Thread %" SDL_PRIu64 ": ready to work\n", typestr, tid);
if (is_reader) {
SDL_LockRWLockForReading(rwlock);
} else {
SDL_LockRWLockForWriting(rwlock);
}
SDL_Log("%s Thread %lu: start work!\n", typestr, (unsigned long) tid);
SDL_Log("%s Thread %" SDL_PRIu64 ": start work!\n", typestr, tid);
SDL_Delay(workticks);
SDL_Log("%s Thread %lu: work done!\n", typestr, (unsigned long) tid);
SDL_Log("%s Thread %" SDL_PRIu64 ": work done!\n", typestr, tid);
SDL_UnlockRWLock(rwlock);
/* If this sleep isn't done, then threads may starve */
@ -53,11 +53,11 @@ static void DoWork(const int workticks) /* "Work" */
static int SDLCALL
ReaderRun(void *data)
{
SDL_Log("Reader Thread %lu: starting up", SDL_ThreadID());
SDL_Log("Reader Thread %" SDL_PRIu64 ": starting up", SDL_GetCurrentThreadID());
while (!SDL_AtomicGet(&doterminate)) {
DoWork(worktime);
}
SDL_Log("Reader Thread %lu: exiting!\n", SDL_ThreadID());
SDL_Log("Reader Thread %" SDL_PRIu64 ": exiting!\n", SDL_GetCurrentThreadID());
return 0;
}
@ -148,8 +148,8 @@ int main(int argc, char *argv[])
return 1;
}
mainthread = SDL_ThreadID();
SDL_Log("Writer thread: %lu\n", mainthread);
mainthread = SDL_GetCurrentThreadID();
SDL_Log("Writer thread: %" SDL_PRIu64 "\n", mainthread);
for (i = 0; i < nb_threads; ++i) {
char name[64];
(void)SDL_snprintf(name, sizeof(name), "Reader%d", i);

View File

@ -11,16 +11,16 @@
*/
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
static SDLTest_CommonState *state;
typedef struct
@ -92,7 +92,7 @@ static void loop(void)
}
Draw(&drawstates[i]);
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -146,7 +146,7 @@ int main(int argc, char *argv[])
then = SDL_GetTicks();
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -9,408 +9,134 @@
including commercial applications, and to alter it and redistribute it
freely.
*/
#include <stdlib.h>
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#define SHAPED_WINDOW_DIMENSION 640
#include "glass.h"
/** An enum denoting the specific type of contents present in an SDL_WindowShapeParams union. */
typedef enum
static SDL_HitTestResult SDLCALL ShapeHitTest(SDL_Window *window, const SDL_Point *area, void *userdata)
{
/** The default mode, a binarized alpha cutoff of 1. */
ShapeModeDefault,
/** A binarized alpha cutoff with a given integer value. */
ShapeModeBinarizeAlpha,
/** A binarized alpha cutoff with a given integer value, but with the opposite comparison. */
ShapeModeReverseBinarizeAlpha,
/** A color key is applied. */
ShapeModeColorKey
} WindowShapeMode;
SDL_Surface *shape = (SDL_Surface *)userdata;
Uint8 r, g, b, a;
/** A union containing parameters for shaped windows. */
typedef union
{
/** A cutoff alpha value for binarization of the window shape's alpha channel. */
Uint8 binarizationCutoff;
SDL_Color colorKey;
} SDL_WindowShapeParams;
/** A struct that tags the SDL_WindowShapeParams union with an enum describing the type of its contents. */
typedef struct SDL_WindowShapeMode
{
/** The mode of these window-shape parameters. */
WindowShapeMode mode;
/** Window-shape parameters. */
SDL_WindowShapeParams parameters;
} SDL_WindowShapeMode;
typedef struct LoadedPicture
{
SDL_Surface *surface;
int num_textures;
SDL_Texture **textures;
SDL_Texture **shape_textures;
SDL_WindowShapeMode mode;
const char *name;
struct LoadedPicture *next;
} LoadedPicture;
static Uint8 *g_bitmap = NULL;
static int g_bitmap_w = 0, g_bitmap_h = 0;
static SDL_Surface *g_shape_surface = NULL;
static void log_usage(SDLTest_CommonState *state, char *progname) {
static const char *options[] = { "sample1.bmp [sample2.bmp [sample3.bmp ...]]", NULL };
SDLTest_CommonLogUsage(state, progname, options);
}
/* REQUIRES that bitmap point to a w-by-h bitmap with ppb pixels-per-byte. */
static void SDL_CalculateShapeBitmap(SDL_WindowShapeMode mode, SDL_Surface *shape, Uint8 *bitmap, Uint8 ppb)
{
int x = 0;
int y = 0;
Uint8 r = 0, g = 0, b = 0, alpha = 0;
Uint32 mask_value = 0;
size_t bytes_per_scanline = (size_t)(shape->w + (ppb - 1)) / ppb;
Uint8 *bitmap_scanline;
SDL_Color key;
if (SDL_MUSTLOCK(shape)) {
SDL_LockSurface(shape);
}
SDL_memset(bitmap, 0, shape->h * bytes_per_scanline);
for (y = 0; y < shape->h; y++) {
bitmap_scanline = bitmap + y * bytes_per_scanline;
for (x = 0; x < shape->w; x++) {
alpha = 0;
if (SDLTest_ReadSurfacePixel(shape, x, y, &r, &g, &b, &alpha) != 0) {
continue;
}
switch (mode.mode) {
case (ShapeModeDefault):
mask_value = (alpha >= 1 ? 1 : 0);
break;
case (ShapeModeBinarizeAlpha):
mask_value = (alpha >= mode.parameters.binarizationCutoff ? 1 : 0);
break;
case (ShapeModeReverseBinarizeAlpha):
mask_value = (alpha <= mode.parameters.binarizationCutoff ? 1 : 0);
break;
case (ShapeModeColorKey):
key = mode.parameters.colorKey;
mask_value = ((key.r != r || key.g != g || key.b != b) ? 1 : 0);
break;
}
bitmap_scanline[x / ppb] |= mask_value << (x % ppb);
if (SDL_ReadSurfacePixel(shape, area->x, area->y, &r, &g, &b, &a) == 0) {
if (a != SDL_ALPHA_TRANSPARENT) {
/* We'll just make everything draggable */
return SDL_HITTEST_DRAGGABLE;
}
}
if (SDL_MUSTLOCK(shape)) {
SDL_UnlockSurface(shape);
}
return SDL_HITTEST_NORMAL;
}
static int SDL3_SetWindowShape(LoadedPicture *picture, SDL_WindowShapeMode *shape_mode)
int main(int argc, char *argv[])
{
if (g_bitmap) {
SDL_free(g_bitmap);
g_bitmap = NULL;
}
if (!picture) {
return SDL_SetError("picture");
}
if (picture->shape_textures[0]) {
int i;
for (i = 0; i < picture->num_textures; i++) {
SDL_DestroyTexture(picture->shape_textures[i]);
picture->shape_textures[i] = NULL;
}
}
if (g_shape_surface) {
SDL_DestroySurface(g_shape_surface);
g_shape_surface = NULL;
}
if (!shape_mode) {
return SDL_SetError("shape_mode");
}
g_bitmap_w = picture->surface->w;
g_bitmap_h = picture->surface->h;
g_bitmap = (Uint8*) SDL_malloc(picture->surface->w * picture->surface->h);
if (!g_bitmap) {
return -1;
}
SDL_CalculateShapeBitmap(*shape_mode, picture->surface, g_bitmap, 1);
g_shape_surface = SDL_CreateSurface(g_bitmap_w, g_bitmap_h, SDL_PIXELFORMAT_ABGR8888);
if (g_shape_surface) {
int x, y, i = 0;
Uint32 *ptr = g_shape_surface->pixels;
for (y = 0; y < g_bitmap_h; y++) {
for (x = 0; x < g_bitmap_w; x++) {
Uint8 val = g_bitmap[i++];
if (val == 0) {
ptr[x] = 0;
} else {
ptr[x] = 0xffffffff;
}
}
ptr = (Uint32 *)((Uint8 *)ptr + g_shape_surface->pitch);
}
}
return 0;
}
static void render(int index, SDL_Renderer *renderer, LoadedPicture *picture)
{
/* Clear render-target to blue. */
SDL_SetRenderDrawColor(renderer, 0x00, 0x00, 0xff, 0xff);
SDL_RenderClear(renderer);
/* Render the texture. */
SDL_RenderTexture(renderer, picture->textures[index], NULL, NULL);
/* Apply the shape */
if (g_shape_surface) {
SDL_RendererInfo info;
SDL_GetRendererInfo(renderer, &info);
if (info.flags & SDL_RENDERER_SOFTWARE) {
if (g_bitmap) {
int x, y, i = 0;
Uint8 r, g, b, a;
SDL_GetRenderDrawColor(renderer, &r, &g, &b, &a);
SDL_SetRenderDrawColor(renderer, 0, 0, 0, 0);
for (y = 0; y < g_bitmap_h; y++) {
for (x = 0; x < g_bitmap_w; x++) {
Uint8 val = g_bitmap[i++];
if (val == 0) {
SDL_RenderPoint(renderer, (float)x, (float)y);
}
}
}
SDL_SetRenderDrawColor(renderer, r, g, b, a);
}
} else {
if (!picture->shape_textures[index]) {
SDL_BlendMode bm;
picture->shape_textures[index] = SDL_CreateTextureFromSurface(renderer, g_shape_surface);
/* if Alpha is 0, set all to 0, else leave unchanged. */
bm = SDL_ComposeCustomBlendMode(
SDL_BLENDFACTOR_ZERO, SDL_BLENDFACTOR_SRC_ALPHA, SDL_BLENDOPERATION_ADD,
SDL_BLENDFACTOR_ZERO, SDL_BLENDFACTOR_SRC_ALPHA, SDL_BLENDOPERATION_ADD);
SDL_SetTextureBlendMode(picture->shape_textures[index], bm);
}
SDL_RenderTexture(renderer, picture->shape_textures[index], NULL, NULL);
}
}
SDL_RenderPresent(renderer);
}
int main(int argc, char **argv)
{
int num_pictures = 0;
LoadedPicture *pic_i = NULL;
LoadedPicture *picture_linked_list = NULL;
LoadedPicture **pictures = NULL;
const char *image_file = NULL;
SDL_Window *window = NULL;
SDL_Renderer *renderer = NULL;
SDL_Surface *shape = NULL;
SDL_bool resizable = SDL_FALSE;
SDL_WindowFlags flags;
SDL_bool done = SDL_FALSE;
SDL_Event event;
int i;
int j;
const SDL_DisplayMode *mode;
SDL_PixelFormat *format = NULL;
SDL_Color black = { 0, 0, 0, 0xff };
int done = 0;
int current_picture;
int button_down;
Uint32 pixelFormat = 0;
int w, h, access = 0;
SDLTest_CommonState *state;
int rc;
int return_code = 1;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, SDL_INIT_VIDEO);
if (!state) {
return 1;
}
state->window_flags |= SDL_WINDOW_TRANSPARENT;
state->window_flags &= ~SDL_WINDOW_RESIZABLE;
rc = 0;
/* SDL_SetHint(SDL_HINT_RENDER_DRIVER, "software"); */
/* SDL_SetHint(SDL_HINT_VIDEO_FORCE_EGL, "0"); */
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Parse commandline */
for (i = 1; i < argc;) {
int consumed;
consumed = SDLTest_CommonArg(state, i);
if (!consumed) {
LoadedPicture *new_picture;
new_picture = SDL_malloc(sizeof(LoadedPicture));
new_picture->name = argv[i];
new_picture->next = picture_linked_list;
picture_linked_list = new_picture;
num_pictures++;
consumed = 1;
}
if (consumed <= 0) {
log_usage(state, argv[0]);
exit(-1);
}
i += consumed;
}
if (!num_pictures) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "testshape requires at least one bitmap file as argument.");
log_usage(state, argv[0]);
rc = -1;
goto ret;
}
if (!SDLTest_CommonInit(state)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Could not initialize SDL video.");
rc = -2;
goto ret;
}
mode = SDL_GetDesktopDisplayMode(SDL_GetPrimaryDisplay());
if (!mode) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't get desktop display mode: %s", SDL_GetError());
rc = -2;
goto ret;
}
/* Allocate an array of LoadedPicture pointers for convenience accesses. */
pictures = (LoadedPicture **)SDL_malloc(sizeof(LoadedPicture*) * num_pictures);
if (!pictures) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Could not allocate memory.");
rc = 1;
goto ret;
}
for (i = 0, pic_i = picture_linked_list; i < num_pictures; i++, pic_i = pic_i->next) {
pictures[i] = pic_i;
pictures[i]->surface = NULL;
}
for (i = 0; i < num_pictures; i++) {
pictures[i]->surface = SDL_LoadBMP(pictures[i]->name);
if (pictures[i]->surface == NULL) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Could not load surface from named bitmap file: %s", pictures[i]->name);
rc = -3;
goto ret;
}
format = pictures[i]->surface->format;
if (SDL_ISPIXELFORMAT_ALPHA(format->format)) {
pictures[i]->mode.mode = ShapeModeBinarizeAlpha;
pictures[i]->mode.parameters.binarizationCutoff = 255;
for (i = 1; i < argc; ++i) {
if (SDL_strcmp(argv[i], "--resizable") == 0) {
resizable = SDL_TRUE;
} else if (!image_file) {
image_file = argv[i];
} else {
pictures[i]->mode.mode = ShapeModeColorKey;
pictures[i]->mode.parameters.colorKey = black;
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Usage: %s [--resizable] [shape.bmp]\n", argv[0]);
goto quit;
}
}
for (i = 0; i < num_pictures; i++) {
pictures[i]->textures = SDL_calloc(state->num_windows, sizeof(SDL_Texture *));
pictures[i]->shape_textures = SDL_calloc(state->num_windows, sizeof(SDL_Texture *));
if (!pictures[i]->textures || !pictures[i]->shape_textures) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Could not create textures array(s).");
rc = -4;
goto ret;
if (image_file) {
shape = SDL_LoadBMP(image_file);
if (!shape) {
SDL_Log("Couldn't load %s: %s\n", image_file, SDL_GetError());
goto quit;
}
for (j = 0; j < state->num_windows; j++) {
pictures[i]->textures[j] = SDL_CreateTextureFromSurface(state->renderers[j], pictures[i]->surface);
if (!pictures[i]->textures[j]) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Could not create textures for SDL_shape.");
rc = -5;
goto ret;
}
} else {
shape = SDL_LoadBMP_IO(SDL_IOFromConstMem(glass_bmp, sizeof(glass_bmp)), SDL_TRUE);
if (!shape) {
SDL_Log("Couldn't load glass.bmp: %s\n", SDL_GetError());
goto quit;
}
}
done = 0;
current_picture = 0;
button_down = 0;
SDL_LogInfo(SDL_LOG_CATEGORY_APPLICATION, "Changing to shaped bmp: %s", pictures[current_picture]->name);
for (i = 0; i < state->num_windows; i++) {
SDL_QueryTexture(pictures[current_picture]->textures[i], &pixelFormat, &access, &w, &h);
/* We want to set the window size in pixels */
SDL_SetWindowSize(state->windows[i], (int)SDL_ceilf(w / mode->pixel_density), (int)SDL_ceilf(h / mode->pixel_density));
/* Create the window hidden so we can set the shape before it's visible */
flags = (SDL_WINDOW_HIDDEN | SDL_WINDOW_TRANSPARENT);
if (resizable) {
flags |= SDL_WINDOW_RESIZABLE;
} else {
flags |= SDL_WINDOW_BORDERLESS;
}
SDL3_SetWindowShape(pictures[current_picture], &pictures[current_picture]->mode);
window = SDL_CreateWindow("SDL Shape Test", shape->w, shape->h, flags);
if (!window) {
SDL_Log("Couldn't create transparent window: %s\n", SDL_GetError());
goto quit;
}
renderer = SDL_CreateRenderer(window, NULL, 0);
if (!renderer) {
SDL_Log("Couldn't create renderer: %s\n", SDL_GetError());
goto quit;
}
if (!SDL_ISPIXELFORMAT_ALPHA(shape->format->format)) {
/* Set the colorkey to the top-left pixel */
Uint8 r, g, b, a;
SDL_ReadSurfacePixel(shape, 0, 0, &r, &g, &b, &a);
SDL_SetSurfaceColorKey(shape, 1, SDL_MapRGBA(shape->format, r, g, b, a));
}
if (!resizable) {
/* Set the hit test callback so we can drag the window */
if (SDL_SetWindowHitTest(window, ShapeHitTest, shape) < 0) {
SDL_Log("Couldn't set hit test callback: %s\n", SDL_GetError());
goto quit;
}
}
/* Set the window size to the size of our shape and show it */
SDL_SetWindowShape(window, shape);
SDL_ShowWindow(window);
/* We're ready to go! */
while (!done) {
SDL_Event event;
while (SDL_PollEvent(&event)) {
SDLTest_CommonEvent(state, &event, &done);
if (event.type == SDL_EVENT_KEY_DOWN) {
button_down = 1;
}
if (button_down && event.type == SDL_EVENT_KEY_UP) {
button_down = 0;
current_picture += 1;
if (current_picture >= num_pictures) {
current_picture = 0;
}
SDL_LogInfo(SDL_LOG_CATEGORY_APPLICATION, "Changing to shaped bmp: %s", pictures[current_picture]->name);
for (i = 0; i < state->num_windows; i++) {
SDL_QueryTexture(pictures[current_picture]->textures[i], &pixelFormat, &access, &w, &h);
SDL_SetWindowSize(state->windows[i], (int)SDL_ceilf(w / mode->pixel_density),(int)SDL_ceilf(h / mode->pixel_density));
SDL3_SetWindowShape(pictures[current_picture], &pictures[current_picture]->mode);
switch (event.type) {
case SDL_EVENT_KEY_DOWN:
if (event.key.keysym.sym == SDLK_ESCAPE) {
done = SDL_TRUE;
}
break;
case SDL_EVENT_QUIT:
done = SDL_TRUE;
break;
default:
break;
}
}
for (i = 0; i < state->num_windows; i++) {
render(i, state->renderers[i], pictures[current_picture]);
}
SDL_Delay(10);
/* We'll clear to white, but you could do other drawing here */
SDL_SetRenderDrawColor(renderer, 255, 255, 255, SDL_ALPHA_OPAQUE);
SDL_RenderClear(renderer);
/* Show everything on the screen and wait a bit */
SDL_RenderPresent(renderer);
SDL_Delay(100);
}
ret:
/* Free the textures + original surfaces backing the textures. */
for (pic_i = picture_linked_list; pic_i; ) {
LoadedPicture *next = pic_i->next;
for (j = 0; j < state->num_windows; j++) {
SDL_DestroyTexture(pic_i->textures[i]);
}
SDL_free(pic_i->textures);
SDL_DestroySurface(pic_i->surface);
SDL_free(pic_i);
pic_i = next;
}
SDL_free(pictures);
/* Success! */
return_code = 0;
if (g_bitmap) {
SDL_free(g_bitmap);
g_bitmap = NULL;
}
if (g_shape_surface) {
SDL_DestroySurface(g_shape_surface);
g_shape_surface = NULL;
}
SDLTest_CommonQuit(state);
return rc;
quit:
SDL_DestroySurface(shape);
SDL_Quit();
return return_code;
}

View File

@ -45,7 +45,7 @@ static SDL_bool suspend_when_occluded;
/* -1: infinite random moves (default); >=0: enables N deterministic moves */
static int iterations = -1;
void SDL_AppQuit(void)
void SDL_AppQuit(void *appstate)
{
SDL_free(sprites);
SDL_free(positions);
@ -127,7 +127,9 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
/* Test horizontal and vertical lines */
SDL_SetRenderDrawColor(renderer, 0x00, 0xFF, 0x00, 0xFF);
SDL_RenderLine(renderer, 1.0f, 0.0f, (float)(viewport.w - 2), 0.0f);
SDL_SetRenderDrawColor(renderer, 0xFF, 0x00, 0x00, 0xFF);
SDL_RenderLine(renderer, 1.0f, (float)(viewport.h - 1), (float)(viewport.w - 2), (float)(viewport.h - 1));
SDL_SetRenderDrawColor(renderer, 0x00, 0x00, 0xFF, 0xFF);
SDL_RenderLine(renderer, 0.0f, 1.0f, 0.0f, (float)(viewport.h - 2));
SDL_RenderLine(renderer, (float)(viewport.w - 1), 1.0f, (float)(viewport.w - 1), (float)(viewport.h - 2));
@ -141,13 +143,13 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
SDL_RenderFillRect(renderer, &temp);
} else {
/* Draw two triangles, filled, uniform */
SDL_Color color;
SDL_FColor color;
SDL_Vertex verts[3];
SDL_zeroa(verts);
color.r = 0xFF;
color.g = 0xFF;
color.b = 0xFF;
color.a = 0xFF;
color.r = 1.0f;
color.g = 1.0f;
color.b = 1.0f;
color.a = 1.0f;
verts[0].position.x = temp.x;
verts[0].position.y = temp.y;
@ -243,9 +245,9 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
SDL_Vertex *verts = (SDL_Vertex *)SDL_malloc(num_sprites * sizeof(SDL_Vertex) * 6);
SDL_Vertex *verts2 = verts;
if (verts) {
SDL_Color color;
SDL_GetTextureColorMod(sprite, &color.r, &color.g, &color.b);
SDL_GetTextureAlphaMod(sprite, &color.a);
SDL_FColor color;
SDL_GetTextureColorModFloat(sprite, &color.r, &color.g, &color.b);
SDL_GetTextureAlphaModFloat(sprite, &color.a);
for (i = 0; i < num_sprites; ++i) {
position = &positions[i];
/* 0 */
@ -314,9 +316,9 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
int *indices2 = indices;
if (verts && indices) {
int pos = 0;
SDL_Color color;
SDL_GetTextureColorMod(sprite, &color.r, &color.g, &color.b);
SDL_GetTextureAlphaMod(sprite, &color.a);
SDL_FColor color;
SDL_GetTextureColorModFloat(sprite, &color.r, &color.g, &color.b);
SDL_GetTextureAlphaModFloat(sprite, &color.a);
for (i = 0; i < num_sprites; ++i) {
position = &positions[i];
/* 0 */
@ -384,12 +386,12 @@ static void MoveSprites(SDL_Renderer *renderer, SDL_Texture *sprite)
SDL_RenderPresent(renderer);
}
int SDL_AppEvent(const SDL_Event *event)
int SDL_AppEvent(void *appstate, const SDL_Event *event)
{
return SDLTest_CommonEventMainCallbacks(state, event);
}
int SDL_AppIterate(void)
int SDL_AppIterate(void *appstate)
{
Uint64 now;
int i;
@ -423,7 +425,7 @@ int SDL_AppIterate(void)
return 0; /* keep going */
}
int SDL_AppInit(int argc, char *argv[])
int SDL_AppInit(void **appstate, int argc, char *argv[])
{
int i;
Uint64 seed;

View File

@ -11,15 +11,15 @@
*/
/* Simple program: Move N sprites around on the screen as fast as possible */
#include <stdlib.h>
#include <time.h>
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <stdlib.h>
#include <time.h>
#include "icon.h"
@ -39,9 +39,9 @@ static int done;
static SDL_Texture *CreateTexture(SDL_Renderer *r, unsigned char *data, unsigned int len, int *w, int *h) {
SDL_Texture *texture = NULL;
SDL_Surface *surface;
SDL_RWops *src = SDL_RWFromConstMem(data, len);
SDL_IOStream *src = SDL_IOFromConstMem(data, len);
if (src) {
surface = SDL_LoadBMP_RW(src, SDL_TRUE);
surface = SDL_LoadBMP_IO(src, SDL_TRUE);
if (surface) {
/* Treat white as transparent */
SDL_SetSurfaceColorKey(surface, SDL_TRUE, SDL_MapRGB(surface->format, 255, 255, 255));
@ -100,7 +100,7 @@ static void loop(void)
}
}
MoveSprites();
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -157,7 +157,7 @@ int main(int argc, char *argv[])
/* Main render loop */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -15,17 +15,17 @@
* *
********************************************************************************/
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
#define MOOSEPIC_W 64
#define MOOSEPIC_H 88
@ -114,6 +114,8 @@ static void loop(void)
case SDL_EVENT_QUIT:
done = SDL_TRUE;
break;
default:
break;
}
}
@ -124,7 +126,7 @@ static void loop(void)
SDL_RenderTexture(renderer, MooseTexture, NULL, NULL);
SDL_RenderPresent(renderer);
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -134,7 +136,7 @@ static void loop(void)
int main(int argc, char **argv)
{
SDL_Window *window;
SDL_RWops *handle;
SDL_IOStream *handle;
char *filename = NULL;
/* Initialize test framework */
@ -162,14 +164,14 @@ int main(int argc, char **argv)
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Out of memory\n");
return -1;
}
handle = SDL_RWFromFile(filename, "rb");
handle = SDL_IOFromFile(filename, "rb");
SDL_free(filename);
if (!handle) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Can't find the file moose.dat !\n");
quit(2);
}
SDL_RWread(handle, MooseFrames, MOOSEFRAME_SIZE * MOOSEFRAMES_COUNT);
SDL_RWclose(handle);
SDL_ReadIO(handle, MooseFrames, MOOSEFRAME_SIZE * MOOSEFRAMES_COUNT);
SDL_CloseIO(handle);
/* Create the window and renderer */
window = SDL_CreateWindow("Happy Moose", MOOSEPIC_W * 4, MOOSEPIC_H * 4, SDL_WINDOW_RESIZABLE);
@ -193,7 +195,7 @@ int main(int argc, char **argv)
/* Loop, waiting for QUIT or the escape key */
frame = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -65,7 +65,7 @@ get_channel_name(int channel_index, int channel_count)
case 8:
return "Back Left";
}
SDL_assert(0);
break;
case 5:
switch (channel_count) {
case 6:
@ -75,7 +75,7 @@ get_channel_name(int channel_index, int channel_count)
case 8:
return "Back Right";
}
SDL_assert(0);
break;
case 6:
switch (channel_count) {
case 7:
@ -83,11 +83,12 @@ get_channel_name(int channel_index, int channel_count)
case 8:
return "Side Left";
}
SDL_assert(0);
break;
case 7:
return "Side Right";
}
SDLTest_AssertCheck(SDL_FALSE, "Invalid channel_index for channel_count: channel_count=%d channel_index=%d", channel_count, channel_index);
SDL_assert(0);
return NULL;
}

View File

@ -59,8 +59,8 @@ ThreadFunc(void *data)
SDL_ThreadPriority prio = SDL_THREAD_PRIORITY_NORMAL;
SDL_SetTLS(tls, "baby thread", NULL);
SDL_Log("Started thread %s: My thread id is %lu, thread data = %s\n",
(char *)data, SDL_ThreadID(), (const char *)SDL_GetTLS(tls));
SDL_Log("Started thread %s: My thread id is %" SDL_PRIu64 ", thread data = %s\n",
(char *)data, SDL_GetCurrentThreadID(), (const char *)SDL_GetTLS(tls));
while (alive) {
SDL_Log("Thread '%s' is alive!\n", (char *)data);

213
external/sdl/SDL/test/testtime.c vendored Normal file
View File

@ -0,0 +1,213 @@
/*
Copyright (C) 1997-2024 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.
*/
/* Test program to verify the SDL date/time APIs */
#include <SDL3/SDL.h>
#include <SDL3/SDL_main.h>
#include <SDL3/SDL_test.h>
#define CAL_Y_OFF 100.0f
#define CAL_X_OFF 19.0f
#define CELL_WIDTH 86.0f
#define CELL_HEIGHT 60.0f
static int cal_year;
static int cal_month;
static SDL_TIME_FORMAT time_format;
static SDL_DATE_FORMAT date_format;
static void RenderDateTime(SDL_Renderer *r)
{
const char *const WDAY[] = { "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" };
const char *const MNAME[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul",
"Aug", "Sep", "Oct", "Nov", "Dec" };
const char *const TIMEPOST[] = { "", " AM", " PM" };
int day, len;
const char *postfix = TIMEPOST[0];
float x, y;
const float x_max = CAL_X_OFF + (CELL_WIDTH * 7);
const float y_max = CAL_Y_OFF + (CELL_HEIGHT * 6);
char str[256];
char short_date[128];
SDL_Time ticks;
SDL_DateTime dt;
SDL_SetRenderDrawColor(r, 0xFF, 0xFF, 0xFF, 0xFF);
/* Query the current time and print it. */
SDL_GetCurrentTime(&ticks);
SDL_TimeToDateTime(ticks, &dt, SDL_FALSE);
switch (date_format) {
case SDL_DATE_FORMAT_YYYYMMDD:
SDL_snprintf(short_date, sizeof(short_date), "%04d-%02d-%02d", dt.year, dt.month, dt.day);
break;
case SDL_DATE_FORMAT_DDMMYYYY:
SDL_snprintf(short_date, sizeof(short_date), "%02d.%02d.%04d", dt.day, dt.month, dt.year);
break;
case SDL_DATE_FORMAT_MMDDYYYY:
SDL_snprintf(short_date, sizeof(short_date), "%02d/%02d/%04d", dt.month, dt.day, dt.year);
break;
}
if (time_format) {
if (dt.hour > 12) { /* PM */
dt.hour -= 12;
postfix = TIMEPOST[2];
} else {
if (!dt.hour) { /* AM */
dt.hour = 12; /* Midnight */
}
postfix = TIMEPOST[1];
}
}
SDL_snprintf(str, sizeof(str), "UTC: %s %02d %s %04d (%s) %02d:%02d:%02d.%09d%s %+05d",
WDAY[dt.day_of_week], dt.day, MNAME[dt.month - 1], dt.year, short_date,
dt.hour, dt.minute, dt.second, dt.nanosecond, postfix, ((dt.utc_offset / 3600) * 100) + (dt.utc_offset % 3600));
SDLTest_DrawString(r, 10, 15, str);
SDL_TimeToDateTime(ticks, &dt, SDL_TRUE);
SDL_snprintf(str, sizeof(str), "Local: %s %02d %s %04d (%s) %02d:%02d:%02d.%09d%s %+05d",
WDAY[dt.day_of_week], dt.day, MNAME[dt.month - 1], dt.year, short_date,
dt.hour, dt.minute, dt.second, dt.nanosecond, postfix,
((dt.utc_offset / 3600) * 100) + (dt.utc_offset % 3600));
SDLTest_DrawString(r, 10, 30, str);
/* Draw a calendar. */
if (!cal_month) {
cal_month = dt.month;
cal_year = dt.year;
}
for (y = CAL_Y_OFF; y <= CAL_Y_OFF + (CELL_HEIGHT * 6); y += CELL_HEIGHT) {
SDL_RenderLine(r, CAL_X_OFF, y, x_max, y);
}
for (x = CAL_X_OFF; x <= CAL_X_OFF + (CELL_WIDTH * 7); x += CELL_WIDTH) {
SDL_RenderLine(r, x, CAL_Y_OFF, x, y_max);
}
/* Draw the month and year. */
len = SDL_snprintf(str, sizeof(str), "%s %04d", MNAME[cal_month - 1], cal_year);
SDLTest_DrawString(r, (CAL_X_OFF + ((x_max - CAL_X_OFF) / 2)) - ((FONT_CHARACTER_SIZE * len) / 2), CAL_Y_OFF - (FONT_LINE_HEIGHT * 3), str);
/* Draw day names */
for (x = 0; x < 7; ++x) {
float offset = ((CAL_X_OFF + (CELL_WIDTH * x)) + (CELL_WIDTH / 2)) - ((FONT_CHARACTER_SIZE * 3) / 2);
SDLTest_DrawString(r, offset, CAL_Y_OFF - FONT_LINE_HEIGHT, WDAY[(int)x]);
}
day = SDL_GetDayOfWeek(cal_year, cal_month, 1);
x = CAL_X_OFF + (day * CELL_WIDTH + (CELL_WIDTH - (FONT_CHARACTER_SIZE * 3)));
day = 0;
y = CAL_Y_OFF + FONT_LINE_HEIGHT;
while (++day <= SDL_GetDaysInMonth(cal_year, cal_month)) {
SDL_snprintf(str, sizeof(str), "%02d", day);
/* Highlight the current day in red. */
if (cal_year == dt.year && cal_month == dt.month && day == dt.day) {
SDL_SetRenderDrawColor(r, 0xFF, 0, 0, 0xFF);
}
SDLTest_DrawString(r, x, y, str);
SDL_SetRenderDrawColor(r, 0xFF, 0xFF, 0xFF, 0xFF);
x += CELL_WIDTH;
if (x >= x_max) {
x = CAL_X_OFF + (CELL_WIDTH - (FONT_CHARACTER_SIZE * 3));
y += CELL_HEIGHT;
}
}
}
int main(int argc, char *argv[])
{
SDLTest_CommonState *state;
SDL_Event event;
int done;
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, SDL_INIT_VIDEO);
if (!state) {
return 1;
}
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Parse commandline */
if (!SDLTest_CommonDefaultArgs(state, argc, argv)) {
return 1;
}
if (!SDLTest_CommonInit(state)) {
goto quit;
}
time_format = SDL_GetNumberProperty(SDL_GetGlobalProperties(), SDL_PROP_GLOBAL_SYSTEM_TIME_FORMAT_NUMBER, SDL_TIME_FORMAT_24HR);
date_format = SDL_GetNumberProperty(SDL_GetGlobalProperties(), SDL_PROP_GLOBAL_SYSTEM_DATE_FORMAT_NUMBER, SDL_DATE_FORMAT_YYYYMMDD);
/* Main render loop */
done = 0;
while (!done) {
/* Check for events */
while (SDL_PollEvent(&event)) {
SDLTest_CommonEvent(state, &event, &done);
if (event.type == SDL_EVENT_KEY_DOWN) {
switch (event.key.keysym.sym) {
case SDLK_UP:
if (++cal_month > 12) {
cal_month = 1;
++cal_year;
}
break;
case SDLK_DOWN:
if (--cal_month < 1) {
cal_month = 12;
--cal_year;
}
break;
case SDLK_1:
time_format = SDL_TIME_FORMAT_24HR;
break;
case SDLK_2:
time_format = SDL_TIME_FORMAT_12HR;
break;
case SDLK_3:
date_format = SDL_DATE_FORMAT_YYYYMMDD;
break;
case SDLK_4:
date_format = SDL_DATE_FORMAT_DDMMYYYY;
break;
case SDLK_5:
date_format = SDL_DATE_FORMAT_MMDDYYYY;
break;
default:
break;
}
}
}
SDL_SetRenderDrawColor(state->renderers[0], 0x00, 0x00, 0x00, 0xFF);
SDL_RenderClear(state->renderers[0]);
RenderDateTime(state->renderers[0]);
SDL_RenderPresent(state->renderers[0]);
}
quit:
SDLTest_CommonQuit(state);
return 0;
}

View File

@ -29,7 +29,7 @@ GetNearbyFilename(const char *file)
base = SDL_GetBasePath();
if (base) {
SDL_RWops *rw;
SDL_IOStream *rw;
size_t len = SDL_strlen(base) + SDL_strlen(file) + 1;
path = SDL_malloc(len);
@ -42,9 +42,9 @@ GetNearbyFilename(const char *file)
(void)SDL_snprintf(path, len, "%s%s", base, file);
SDL_free(base);
rw = SDL_RWFromFile(path, "rb");
rw = SDL_IOFromFile(path, "rb");
if (rw) {
SDL_RWclose(rw);
SDL_CloseIO(rw);
return path;
}
@ -104,14 +104,14 @@ LoadTexture(SDL_Renderer *renderer, const char *file, SDL_bool transparent,
/* Set transparent pixel as the pixel at (0,0) */
if (transparent) {
if (temp->format->palette) {
const Uint8 bpp = temp->format->BitsPerPixel;
const Uint8 bpp = temp->format->bits_per_pixel;
const Uint8 mask = (1 << bpp) - 1;
if (SDL_PIXELORDER(temp->format->format) == SDL_BITMAPORDER_4321)
SDL_SetSurfaceColorKey(temp, SDL_TRUE, (*(Uint8 *)temp->pixels) & mask);
else
SDL_SetSurfaceColorKey(temp, SDL_TRUE, ((*(Uint8 *)temp->pixels) >> (8 - bpp)) & mask);
} else {
switch (temp->format->BitsPerPixel) {
switch (temp->format->bits_per_pixel) {
case 15:
SDL_SetSurfaceColorKey(temp, SDL_TRUE,
(*(Uint16 *)temp->pixels) & 0x00007FFF);

View File

@ -19,8 +19,8 @@
int main(int argc, char *argv[])
{
SDL_version compiled;
SDL_version linked;
SDL_Version compiled;
SDL_Version linked;
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);

View File

@ -1,770 +0,0 @@
/*
Copyright (C) 1997-2024 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_main.h"
#include "SDL3/SDL.h"
#include "SDL3/SDL_test.h"
#include "SDL3/SDL_video_capture.h"
#include <stdio.h>
#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: switch to, and 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)
{
Uint64 now = SDL_GetTicks();
Uint64 deadline;
m->frame_counter++;
if (m->check_delay == 0) {
m->check_delay = 1500;
}
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);
m->next_check = now + m->check_delay;
m->frame_counter = 0;
}
}
#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
struct data_capture_t {
SDL_VideoCaptureDevice *device;
SDL_VideoCaptureSpec obtained;
int stopped;
SDL_VideoCaptureFrame frame_current;
measure_fps_t fps_capture;
SDL_Texture *texture;
int texture_updated;
};
#define SAVE_CAPTURE_STATE(x) \
data_capture_tab[(x)].device = device; \
data_capture_tab[(x)].obtained = obtained; \
data_capture_tab[(x)].stopped = stopped; \
data_capture_tab[(x)].frame_current = frame_current; \
data_capture_tab[(x)].fps_capture = fps_capture; \
data_capture_tab[(x)].texture = texture; \
data_capture_tab[(x)].texture_updated = texture_updated; \
#define RESTORE_CAPTURE_STATE(x) \
device = data_capture_tab[(x)].device; \
obtained = data_capture_tab[(x)].obtained; \
stopped = data_capture_tab[(x)].stopped; \
frame_current = data_capture_tab[(x)].frame_current; \
fps_capture = data_capture_tab[(x)].fps_capture; \
texture = data_capture_tab[(x)].texture; \
texture_updated = data_capture_tab[(x)].texture_updated; \
static SDL_VideoCaptureDeviceID get_instance_id(int index) {
int ret = 0;
int num = 0;
SDL_VideoCaptureDeviceID *devices;
devices = SDL_GetVideoCaptureDevices(&num);
if (devices) {
if (index >= 0 && index < num) {
ret = devices[index];
}
SDL_free(devices);
}
if (ret == 0) {
/* SDL_Log("invalid index"); */
}
return ret;
}
int main(int argc, char **argv)
{
SDL_Window *window = NULL;
SDL_Renderer *renderer = NULL;
SDL_Event evt;
int quit = 0;
SDLTest_CommonState *state;
int current_dev = 0;
measure_fps_t fps_main;
SDL_FRect r_playstop = { 50, 50, 120, 50 };
SDL_FRect r_close = { 50 + (120 + 50) * 1, 50, 120, 50 };
SDL_FRect r_open = { 50 + (120 + 50) * 2, 50, 120, 50 };
SDL_FRect r_format = { 50 + (120 + 50) * 3, 50, 120, 50 };
SDL_FRect r_listdev = { 50 + (120 + 50) * 4, 50, 120, 50 };
SDL_VideoCaptureDevice *device;
SDL_VideoCaptureSpec obtained;
int stopped = 0;
SDL_VideoCaptureFrame frame_current;
measure_fps_t fps_capture;
SDL_Texture *texture = NULL;
int texture_updated = 0;
struct data_capture_t data_capture_tab[16];
const int data_capture_tab_size = SDL_arraysize(data_capture_tab);
SDL_zero(fps_main);
SDL_zero(fps_capture);
SDL_zero(frame_current);
SDL_zeroa(data_capture_tab);
/* Set 0 to disable TouchEvent to be duplicated as MouseEvent with SDL_TOUCH_MOUSEID */
SDL_SetHint(SDL_HINT_TOUCH_MOUSE_EVENTS, "0");
/* Set 0 to disable MouseEvent to be duplicated as TouchEvent with SDL_MOUSE_TOUCHID */
SDL_SetHint(SDL_HINT_MOUSE_TOUCH_EVENTS, "0");
{
int i;
for (i = 0; i < data_capture_tab_size; i++) {
data_capture_tab[i].device = NULL;
}
}
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
if (state == NULL) {
return 1;
}
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Parse commandline */
{
int i;
for (i = 1; i < argc;) {
int consumed;
consumed = SDLTest_CommonArg(state, i);
if (consumed <= 0) {
static const char *options[] = {NULL};
SDLTest_CommonLogUsage(state, argv[0], options);
SDLTest_CommonDestroyState(state);
return 1;
}
i += consumed;
}
}
SDL_Log("%s", usage);
/* Load the SDL library */
if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_JOYSTICK) < 0) { /* FIXME: SDL_INIT_JOYSTICK needed for add/removing devices at runtime */
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't initialize SDL: %s", SDL_GetError());
return 1;
}
window = SDL_CreateWindow("Local Video", 1000, 800, 0);
if (window == NULL) {
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;
}
SDL_LogSetAllPriority(SDL_LOG_PRIORITY_INFO);
device = SDL_OpenVideoCapture(0);
if (!device) {
SDL_Log("Error SDL_OpenVideoCapture: %s", SDL_GetError());
}
{
/* List formats */
int i, num = SDL_GetNumVideoCaptureFormats(device);
for (i = 0; i < num; i++) {
Uint32 format;
SDL_GetVideoCaptureFormat(device, i, &format);
SDL_Log("format %d/%d: %s", i, num, SDL_GetPixelFormatName(format));
{
int w, h;
int j, num2 = SDL_GetNumVideoCaptureFrameSizes(device, format);
for (j = 0; j < num2; j++) {
SDL_GetVideoCaptureFrameSize(device, format, j, &w, &h);
SDL_Log(" framesizes %d/%d : %d x %d", j, num2, w, h);
}
}
}
}
/* Set Spec */
{
int ret;
/* forced_format */
SDL_VideoCaptureSpec desired;
SDL_zero(desired);
desired.width = 640 * 2;
desired.height = 360 * 2;
desired.format = SDL_PIXELFORMAT_NV12;
ret = SDL_SetVideoCaptureSpec(device, &desired, &obtained, SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE);
if (ret < 0) {
SDL_SetVideoCaptureSpec(device, NULL, &obtained, 0);
}
}
SDL_Log("Open capture video device. Obtained spec: size=%d x %d format=%s",
obtained.width, obtained.height, SDL_GetPixelFormatName(obtained.format));
{
SDL_VideoCaptureSpec spec;
if (SDL_GetVideoCaptureSpec(device, &spec) == 0) {
SDL_Log("Read spec: size=%d x %d format=%s",
spec.width, spec.height, SDL_GetPixelFormatName(spec.format));
} else {
SDL_Log("Error read spec: %s", SDL_GetError());
}
}
if (SDL_StartVideoCapture(device) < 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_open);
SDL_RenderFillRect(renderer, &r_format);
SDL_RenderFillRect(renderer, &r_listdev);
SDL_SetRenderDrawColor(renderer, 0xcc, 0xcc, 0xcc, 255);
SDLTest_DrawString(renderer, r_playstop.x + 5, r_playstop.y + 5, "play stop");
SDLTest_DrawString(renderer, r_close.x + 5, r_close.y + 5, "close");
SDLTest_DrawString(renderer, r_open.x + 5, r_open.y + 5, "open dev");
SDLTest_DrawString(renderer, r_format.x + 5, r_format.y + 5, "formats");
{
char buf[256];
SDL_snprintf(buf, 256, "device %d", current_dev);
SDLTest_DrawString(renderer, r_listdev.x + 5, r_listdev.y + 5, buf);
}
while (SDL_PollEvent(&evt)) {
SDL_FRect *r = NULL;
SDL_FPoint pt;
int sym = 0;
pt.x = 0;
pt.y = 0;
SDL_ConvertEventToRenderCoordinates(renderer, &evt);
switch (evt.type)
{
case SDL_EVENT_KEY_DOWN:
{
sym = evt.key.keysym.sym;
break;
}
case SDL_EVENT_QUIT:
{
quit = 1;
SDL_Log("Ctlr+C : Quit!");
}
break;
case SDL_EVENT_FINGER_DOWN:
{
pt.x = evt.tfinger.x;
pt.y = evt.tfinger.y;
}
break;
case SDL_EVENT_MOUSE_BUTTON_DOWN:
{
pt.x = evt.button.x;
pt.y = evt.button.y;
}
break;
}
if (pt.x != 0 && pt.y != 0) {
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_open)) {
r = &r_open;
sym = SDLK_o;
}
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);
}
if (sym == SDLK_c) {
if (frame_current.num_planes) {
SDL_ReleaseVideoCaptureFrame(device, &frame_current);
}
SDL_CloseVideoCapture(device);
device = NULL;
SDL_Log("Close");
}
if (sym == SDLK_o) {
if (device) {
SDL_Log("Close previous ..");
if (frame_current.num_planes) {
SDL_ReleaseVideoCaptureFrame(device, &frame_current);
}
SDL_CloseVideoCapture(device);
}
texture_updated = 0;
SDL_ClearError();
SDL_Log("Try to open:%s", SDL_GetVideoCaptureDeviceName(get_instance_id(current_dev)));
obtained.width = 640 * 2;
obtained.height = 360 * 2;
device = SDL_OpenVideoCaptureWithSpec(get_instance_id(current_dev), &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 device:%p %s", (void*)device, SDL_GetError());
stopped = 0;
}
if (sym == SDLK_l) {
int num = 0;
SDL_VideoCaptureDeviceID *devices;
int i;
devices = SDL_GetVideoCaptureDevices(&num);
SDL_Log("Num devices : %d", num);
for (i = 0; i < num; i++) {
SDL_Log("Device %d/%d : %s", i, num, SDL_GetVideoCaptureDeviceName(devices[i]));
}
SDL_free(devices);
SAVE_CAPTURE_STATE(current_dev);
current_dev += 1;
if (current_dev >= num || current_dev >= (int) SDL_arraysize(data_capture_tab)) {
current_dev = 0;
}
RESTORE_CAPTURE_STATE(current_dev);
SDL_Log("--> select dev %d / %d", current_dev, num);
}
if (sym == SDLK_i) {
SDL_VideoCaptureStatus status = SDL_GetVideoCaptureStatus(device);
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) {
if (stopped) {
SDL_Log("Stop");
SDL_StopVideoCapture(device);
} else {
SDL_Log("Start");
SDL_StartVideoCapture(device);
}
stopped = !stopped;
}
if (sym == SDLK_f) {
SDL_Log("List formats");
if (!device) {
device = SDL_OpenVideoCapture(get_instance_id(current_dev));
}
/* List formats */
{
int i, num = SDL_GetNumVideoCaptureFormats(device);
for (i = 0; i < num; i++) {
Uint32 format;
SDL_GetVideoCaptureFormat(device, i, &format);
SDL_Log("format %d/%d : %s", i, num, SDL_GetPixelFormatName(format));
{
int w, h;
int j, num2 = SDL_GetNumVideoCaptureFrameSizes(device, format);
for (j = 0; j < num2; j++) {
SDL_GetVideoCaptureFrameSize(device, format, j, &w, &h);
SDL_Log(" framesizes %d/%d : %d x %d", j, num2, w, h);
}
}
}
}
}
if (sym == SDLK_ESCAPE || sym == SDLK_AC_BACK) {
quit = 1;
SDL_Log("Key : Escape!");
}
if (sym == SDLK_h || sym == SDLK_F1) {
SDL_Log("%s", usage);
}
}
SAVE_CAPTURE_STATE(current_dev);
{
int i, n = SDL_arraysize(data_capture_tab);
for (i = 0; i < n; i++) {
RESTORE_CAPTURE_STATE(i);
if (!device) {
/* device has been closed */
frame_current.num_planes = 0;
texture_updated = 0;
} else {
int ret;
SDL_VideoCaptureFrame frame_next;
SDL_zero(frame_next);
ret = SDL_AcquireVideoCaptureFrame(device, &frame_next);
if (ret < 0) {
SDL_Log("dev[%d] err SDL_AcquireVideoCaptureFrame: %s", i, SDL_GetError());
}
#if 1
if (frame_next.num_planes) {
SDL_Log("dev[%d] frame: %p at %" SDL_PRIu64, i, (void*)frame_next.data[0], frame_next.timestampNS);
}
#endif
if (frame_next.num_planes) {
update_fps(&fps_capture);
if (frame_current.num_planes) {
ret = SDL_ReleaseVideoCaptureFrame(device, &frame_current);
if (ret < 0) {
SDL_Log("dev[%d] err SDL_ReleaseVideoCaptureFrame: %s", i, SDL_GetError());
}
}
frame_current = frame_next;
texture_updated = 0;
}
}
SAVE_CAPTURE_STATE(i);
}
}
RESTORE_CAPTURE_STATE(current_dev);
/* 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);
SAVE_CAPTURE_STATE(current_dev);
{
int i, n = SDL_arraysize(data_capture_tab);
for (i = 0; i < n; i++) {
RESTORE_CAPTURE_STATE(i);
/* Update SDL_Texture with last video frame (only once per new frame) */
if (frame_current.num_planes && texture_updated == 0) {
/* Create texture with appropriate format (for DMABUF or not) */
if (texture == NULL) {
Uint32 format = obtained.format;
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;
}
}
{
/* Use software data */
if (frame_current.num_planes == 1) {
SDL_UpdateTexture(texture, NULL,
frame_current.data[0], frame_current.pitch[0]);
} else if (frame_current.num_planes == 2) {
SDL_UpdateNVTexture(texture, NULL,
frame_current.data[0], frame_current.pitch[0],
frame_current.data[1], frame_current.pitch[1]);
} else if (frame_current.num_planes == 3) {
SDL_UpdateYUVTexture(texture, NULL, frame_current.data[0], frame_current.pitch[0],
frame_current.data[1], frame_current.pitch[1],
frame_current.data[2], frame_current.pitch[2]);
}
texture_updated = 1;
}
}
SAVE_CAPTURE_STATE(i);
}
}
RESTORE_CAPTURE_STATE(current_dev);
{
int i, n = SDL_arraysize(data_capture_tab);
int win_w, win_h;
int total_texture_updated = 0;
int curr_texture_updated = 0;
for (i = 0; i < n; i++) {
if (data_capture_tab[i].texture_updated) {
total_texture_updated += 1;
}
}
SDL_GetRenderOutputSize(renderer, &win_w, &win_h);
for (i = 0; i < n; i++) {
RESTORE_CAPTURE_STATE(i);
/* RenderCopy the SDL_Texture */
if (texture_updated == 1) {
/* Scale texture to fit the screen */
int tw, th;
int w;
SDL_FRect d;
SDL_QueryTexture(texture, NULL, NULL, &tw, &th);
w = win_w / total_texture_updated;
if (tw > w - 20) {
float scale = (float) (w - 20) / (float) tw;
tw = w - 20;
th = (int)((float) th * scale);
}
d.x = (float)(10 + curr_texture_updated * w);
d.y = (float)(win_h - th);
d.w = (float)tw;
d.h = (float)(th - 10);
SDL_RenderTexture(renderer, texture, NULL, &d);
curr_texture_updated += 1;
}
}
}
RESTORE_CAPTURE_STATE(current_dev);
/* display status and FPS */
if (!device) {
#ifdef __IOS__
const float x_offset = 500;
#else
const float x_offset = 0;
#endif
char buf[256];
SDL_snprintf(buf, 256, "Device %d (%s) is not opened", current_dev, SDL_GetVideoCaptureDeviceName(get_instance_id(current_dev)));
SDLTest_DrawString(renderer, x_offset + 10, 10, buf);
} else {
#ifdef __IOS__
const float x_offset = 500;
#else
const float x_offset = 0;
#endif
const char *status = "no status";
char buf[256];
if (device) {
SDL_VideoCaptureStatus s = SDL_GetVideoCaptureStatus(device);
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";
} else if (s == SDL_VIDEO_CAPTURE_FAIL) {
status = "failed";
}
}
/* capture device, capture fps, capture status */
SDL_snprintf(buf, 256, "Device %d - %2.2f fps - %s", current_dev, fps_capture.last_fps, status);
SDLTest_DrawString(renderer, x_offset + 10, 10, buf);
/* capture spec */
SDL_snprintf(buf, sizeof(buf), "%d x %d %s", obtained.width, obtained.height, SDL_GetPixelFormatName(obtained.format));
SDLTest_DrawString(renderer, x_offset + 10, 20, buf);
/* video fps */
SDL_snprintf(buf, sizeof(buf), "%2.2f fps", fps_main.last_fps);
SDLTest_DrawString(renderer, x_offset + 10, 30, buf);
}
/* display last error */
{
SDLTest_DrawString(renderer, 400, 10, SDL_GetError());
}
/* 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);
SDLTest_DrawString(renderer, 800, 10, buf);
}
}
#endif
SDL_Delay(20);
SDL_RenderPresent(renderer);
update_fps(&fps_main);
}
SAVE_CAPTURE_STATE(current_dev);
{
int i, n = SDL_arraysize(data_capture_tab);
for (i = 0; i < n; i++) {
RESTORE_CAPTURE_STATE(i);
if (device) {
if (SDL_StopVideoCapture(device) < 0) {
SDL_Log("error SDL_StopVideoCapture(): %s", SDL_GetError());
}
if (frame_current.num_planes) {
SDL_ReleaseVideoCaptureFrame(device, &frame_current);
}
SDL_CloseVideoCapture(device);
}
if (texture) {
SDL_DestroyTexture(texture);
}
}
}
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(window);
SDL_Quit();
SDLTest_CommonDestroyState(state);
return 0;
}

View File

@ -1,206 +0,0 @@
/*
Copyright (C) 1997-2024 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_main.h"
#include "SDL3/SDL.h"
#include "SDL3/SDL_test.h"
#include "SDL3/SDL_video_capture.h"
#include <stdio.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
int main(int argc, char **argv)
{
SDL_Window *window = NULL;
SDL_Renderer *renderer = NULL;
SDL_Event evt;
int quit = 0;
SDLTest_CommonState *state = NULL;
SDL_VideoCaptureDevice *device = NULL;
SDL_VideoCaptureSpec obtained;
SDL_VideoCaptureFrame frame_current;
SDL_Texture *texture = NULL;
int texture_updated = 0;
SDL_zero(evt);
SDL_zero(obtained);
SDL_zero(frame_current);
/* Set 0 to disable TouchEvent to be duplicated as MouseEvent with SDL_TOUCH_MOUSEID */
SDL_SetHint(SDL_HINT_TOUCH_MOUSE_EVENTS, "0");
/* Set 0 to disable MouseEvent to be duplicated as TouchEvent with SDL_MOUSE_TOUCHID */
SDL_SetHint(SDL_HINT_MOUSE_TOUCH_EVENTS, "0");
/* Initialize test framework */
state = SDLTest_CommonCreateState(argv, 0);
if (state == NULL) {
return 1;
}
/* Enable standard application logging */
SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO);
/* Load the SDL library */
if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_JOYSTICK) < 0) { /* FIXME: SDL_INIT_JOYSTICK needed for add/removing devices at runtime */
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't initialize SDL: %s", SDL_GetError());
return 1;
}
window = SDL_CreateWindow("Local Video", 1000, 800, 0);
if (window == NULL) {
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;
}
device = SDL_OpenVideoCaptureWithSpec(0, NULL, &obtained, SDL_VIDEO_CAPTURE_ALLOW_ANY_CHANGE);
if (!device) {
SDL_Log("No video capture? %s", SDL_GetError());
return 1;
}
if (SDL_StartVideoCapture(device) < 0) {
SDL_Log("error SDL_StartVideoCapture(): %s", SDL_GetError());
return 1;
}
/* Create texture with appropriate format */
if (texture == NULL) {
texture = SDL_CreateTexture(renderer, obtained.format, SDL_TEXTUREACCESS_STATIC, obtained.width, obtained.height);
if (texture == NULL) {
SDL_Log("Couldn't create texture: %s", SDL_GetError());
return 1;
}
}
while (!quit) {
while (SDL_PollEvent(&evt)) {
int sym = 0;
switch (evt.type)
{
case SDL_EVENT_KEY_DOWN:
{
sym = evt.key.keysym.sym;
break;
}
case SDL_EVENT_QUIT:
{
quit = 1;
SDL_Log("Ctlr+C : Quit!");
}
}
if (sym == SDLK_ESCAPE || sym == SDLK_AC_BACK) {
quit = 1;
SDL_Log("Key : Escape!");
}
}
{
SDL_VideoCaptureFrame frame_next;
SDL_zero(frame_next);
if (SDL_AcquireVideoCaptureFrame(device, &frame_next) < 0) {
SDL_Log("err SDL_AcquireVideoCaptureFrame: %s", SDL_GetError());
}
#if 0
if (frame_next.num_planes) {
SDL_Log("frame: %p at %" SDL_PRIu64, (void*)frame_next.data[0], frame_next.timestampNS);
}
#endif
if (frame_next.num_planes) {
if (frame_current.num_planes) {
if (SDL_ReleaseVideoCaptureFrame(device, &frame_current) < 0) {
SDL_Log("err SDL_ReleaseVideoCaptureFrame: %s", SDL_GetError());
}
}
/* It's not needed to keep the frame once updated the texture is updated.
* But in case of 0-copy, it's needed to have the frame while using the texture.
*/
frame_current = frame_next;
texture_updated = 0;
}
}
/* Update SDL_Texture with last video frame (only once per new frame) */
if (frame_current.num_planes && texture_updated == 0) {
/* Use software data */
if (frame_current.num_planes == 1) {
SDL_UpdateTexture(texture, NULL,
frame_current.data[0], frame_current.pitch[0]);
} else if (frame_current.num_planes == 2) {
SDL_UpdateNVTexture(texture, NULL,
frame_current.data[0], frame_current.pitch[0],
frame_current.data[1], frame_current.pitch[1]);
} else if (frame_current.num_planes == 3) {
SDL_UpdateYUVTexture(texture, NULL, frame_current.data[0], frame_current.pitch[0],
frame_current.data[1], frame_current.pitch[1],
frame_current.data[2], frame_current.pitch[2]);
}
texture_updated = 1;
}
SDL_SetRenderDrawColor(renderer, 0x99, 0x99, 0x99, 255);
SDL_RenderClear(renderer);
{
int win_w, win_h, tw, th, w;
SDL_FRect d;
SDL_QueryTexture(texture, NULL, NULL, &tw, &th);
SDL_GetRenderOutputSize(renderer, &win_w, &win_h);
w = win_w;
if (tw > w - 20) {
float scale = (float) (w - 20) / (float) tw;
tw = w - 20;
th = (int)((float) th * scale);
}
d.x = (float)(10 );
d.y = (float)(win_h - th);
d.w = (float)tw;
d.h = (float)(th - 10);
SDL_RenderTexture(renderer, texture, NULL, &d);
}
SDL_Delay(10);
SDL_RenderPresent(renderer);
}
if (SDL_StopVideoCapture(device) < 0) {
SDL_Log("error SDL_StopVideoCapture(): %s", SDL_GetError());
}
if (frame_current.num_planes) {
SDL_ReleaseVideoCaptureFrame(device, &frame_current);
}
SDL_CloseVideoCapture(device);
if (texture) {
SDL_DestroyTexture(texture);
}
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(window);
SDL_Quit();
SDLTest_CommonDestroyState(state);
return 0;
}

View File

@ -11,23 +11,23 @@
*/
/* Simple program: Check viewports */
#include <stdlib.h>
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test.h>
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#include "testutils.h"
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
#include <stdlib.h>
static SDLTest_CommonState *state;
static SDL_Rect viewport;
static int done, j;
static SDL_bool use_target = SDL_FALSE;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
static Uint32 wait_start;
#endif
static SDL_Texture *sprite;
@ -109,7 +109,7 @@ static void loop(void)
{
SDL_Event event;
int i;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
/* Avoid using delays */
if (SDL_GetTicks() - wait_start < 1000) {
return;
@ -148,7 +148,7 @@ static void loop(void)
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -217,7 +217,7 @@ int main(int argc, char *argv[])
done = 0;
j = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
wait_start = SDL_GetTicks();
emscripten_set_main_loop(loop, 0, 1);
#else

View File

@ -14,7 +14,7 @@
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_main.h>
#if defined(__ANDROID__) && defined(__ARM_EABI__) && !defined(__ARM_ARCH_7A__)
#if defined(SDL_PLATFORM_ANDROID) && defined(__ARM_EABI__) && !defined(__ARM_ARCH_7A__)
int main(int argc, char *argv[])
{
@ -426,7 +426,7 @@ static void findPhysicalDevice(void)
static void createDevice(void)
{
VkDeviceQueueCreateInfo deviceQueueCreateInfo[1] = { { 0 } };
VkDeviceQueueCreateInfo deviceQueueCreateInfo[2] = { { 0 }, { 0 } };
static const float queuePriority[] = { 1.0f };
VkDeviceCreateInfo deviceCreateInfo = { 0 };
static const char *const deviceExtensionNames[] = {
@ -434,17 +434,27 @@ static void createDevice(void)
};
VkResult result;
deviceQueueCreateInfo->sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
deviceQueueCreateInfo->queueFamilyIndex = vulkanContext->graphicsQueueFamilyIndex;
deviceQueueCreateInfo->queueCount = 1;
deviceQueueCreateInfo->pQueuePriorities = &queuePriority[0];
deviceCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO;
deviceCreateInfo.queueCreateInfoCount = 1;
deviceCreateInfo.queueCreateInfoCount = 0;
deviceCreateInfo.pQueueCreateInfos = deviceQueueCreateInfo;
deviceCreateInfo.pEnabledFeatures = NULL;
deviceCreateInfo.enabledExtensionCount = SDL_arraysize(deviceExtensionNames);
deviceCreateInfo.ppEnabledExtensionNames = deviceExtensionNames;
deviceQueueCreateInfo[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
deviceQueueCreateInfo[0].queueFamilyIndex = vulkanContext->graphicsQueueFamilyIndex;
deviceQueueCreateInfo[0].queueCount = 1;
deviceQueueCreateInfo[0].pQueuePriorities = queuePriority;
++deviceCreateInfo.queueCreateInfoCount;
if (vulkanContext->presentQueueFamilyIndex != vulkanContext->graphicsQueueFamilyIndex) {
deviceQueueCreateInfo[1].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
deviceQueueCreateInfo[1].queueFamilyIndex = vulkanContext->presentQueueFamilyIndex;
deviceQueueCreateInfo[1].queueCount = 1;
deviceQueueCreateInfo[1].pQueuePriorities = queuePriority;
++deviceCreateInfo.queueCreateInfoCount;
}
result = vkCreateDevice(vulkanContext->physicalDevice, &deviceCreateInfo, NULL, &vulkanContext->device);
if (result != VK_SUCCESS) {
vulkanContext->device = VK_NULL_HANDLE;
@ -602,7 +612,7 @@ static SDL_bool createSwapchain(void)
int w, h;
VkSwapchainCreateInfoKHR createInfo = { 0 };
VkResult result;
Uint32 flags;
SDL_WindowFlags flags;
// pick an image count
vulkanContext->swapchainDesiredImageCount = vulkanContext->surfaceCapabilities.minImageCount + 1;
@ -1091,7 +1101,7 @@ int main(int argc, char **argv)
mode = SDL_GetCurrentDisplayMode(SDL_GetPrimaryDisplay());
if (mode) {
SDL_Log("Screen BPP : %" SDL_PRIu32 "\n", SDL_BITSPERPIXEL(mode->format));
SDL_Log("Screen BPP : %d\n", SDL_BITSPERPIXEL(mode->format));
}
SDL_GetWindowSize(state->windows[0], &dw, &dh);
SDL_Log("Window Size : %d,%d\n", dw, dh);

View File

@ -36,9 +36,9 @@ static SDL_Texture *CreateTexture(SDL_Renderer *r, unsigned char *data, unsigned
{
SDL_Texture *texture = NULL;
SDL_Surface *surface;
SDL_RWops *src = SDL_RWFromConstMem(data, len);
SDL_IOStream *src = SDL_IOFromConstMem(data, len);
if (src) {
surface = SDL_LoadBMP_RW(src, SDL_TRUE);
surface = SDL_LoadBMP_IO(src, SDL_TRUE);
if (surface) {
/* Treat white as transparent */
SDL_SetSurfaceColorKey(surface, SDL_TRUE, SDL_MapRGB(surface->format, 255, 255, 255));
@ -209,12 +209,12 @@ int main(int argc, char **argv)
/* Create a window with the custom surface role property set. */
props = SDL_CreateProperties();
SDL_SetBooleanProperty(props, SDL_PROPERTY_WINDOW_CREATE_WAYLAND_SURFACE_ROLE_CUSTOM_BOOLEAN, SDL_TRUE); /* Roleless surface */
SDL_SetBooleanProperty(props, SDL_PROPERTY_WINDOW_CREATE_OPENGL_BOOLEAN, SDL_TRUE); /* OpenGL enabled */
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_WIDTH_NUMBER, WINDOW_WIDTH); /* Default width */
SDL_SetNumberProperty(props, SDL_PROPERTY_WINDOW_CREATE_HEIGHT_NUMBER, WINDOW_HEIGHT); /* Default height */
SDL_SetBooleanProperty(props, SDL_PROPERTY_WINDOW_CREATE_HIGH_PIXEL_DENSITY_BOOLEAN, SDL_TRUE); /* Handle DPI scaling internally */
SDL_SetStringProperty(props, SDL_PROPERTY_WINDOW_CREATE_TITLE_STRING, "Wayland custom surface role test"); /* Default title */
SDL_SetBooleanProperty(props, SDL_PROP_WINDOW_CREATE_WAYLAND_SURFACE_ROLE_CUSTOM_BOOLEAN, SDL_TRUE); /* Roleless surface */
SDL_SetBooleanProperty(props, SDL_PROP_WINDOW_CREATE_OPENGL_BOOLEAN, SDL_TRUE); /* OpenGL enabled */
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_WIDTH_NUMBER, WINDOW_WIDTH); /* Default width */
SDL_SetNumberProperty(props, SDL_PROP_WINDOW_CREATE_HEIGHT_NUMBER, WINDOW_HEIGHT); /* Default height */
SDL_SetBooleanProperty(props, SDL_PROP_WINDOW_CREATE_HIGH_PIXEL_DENSITY_BOOLEAN, SDL_TRUE); /* Handle DPI scaling internally */
SDL_SetStringProperty(props, SDL_PROP_WINDOW_CREATE_TITLE_STRING, "Wayland custom surface role test"); /* Default title */
window = SDL_CreateWindowWithProperties(props);
SDL_DestroyProperties(props);
@ -231,7 +231,7 @@ int main(int argc, char **argv)
}
/* Get the display object and use it to create a registry object, which will enumerate the xdg_wm_base protocol. */
state.wl_display = SDL_GetProperty(SDL_GetWindowProperties(window), SDL_PROPERTY_WINDOW_WAYLAND_DISPLAY_POINTER, NULL);
state.wl_display = SDL_GetProperty(SDL_GetWindowProperties(window), SDL_PROP_WINDOW_WAYLAND_DISPLAY_POINTER, NULL);
state.wl_registry = wl_display_get_registry(state.wl_display);
wl_registry_add_listener(state.wl_registry, &wl_registry_listener, NULL);
@ -244,7 +244,7 @@ int main(int argc, char **argv)
}
/* Get the wl_surface object from the SDL_Window, and create a toplevel window with it. */
state.wl_surface = SDL_GetProperty(SDL_GetWindowProperties(window), SDL_PROPERTY_WINDOW_WAYLAND_SURFACE_POINTER, NULL);
state.wl_surface = SDL_GetProperty(SDL_GetWindowProperties(window), SDL_PROP_WINDOW_WAYLAND_SURFACE_POINTER, NULL);
/* Create the xdg_surface from the wl_surface. */
state.xdg_surface = xdg_wm_base_get_xdg_surface(state.xdg_wm_base, state.wl_surface);

View File

@ -10,14 +10,14 @@
freely.
*/
#ifdef __EMSCRIPTEN__
#include <emscripten/emscripten.h>
#endif
#include <SDL3/SDL_test_common.h>
#include <SDL3/SDL_test_font.h>
#include <SDL3/SDL_main.h>
#ifdef SDL_PLATFORM_EMSCRIPTEN
#include <emscripten/emscripten.h>
#endif
static SDLTest_CommonState *state;
static int done;
@ -154,7 +154,17 @@ static void loop(void)
{
int i;
SDL_Event event;
/* Check for events */
#ifdef TEST_WAITEVENTTIMEOUT
/* Wait up to 20 ms for input, as a test */
Uint64 then = SDL_GetTicks();
if (SDL_WaitEventTimeout(NULL, 20)) {
SDL_Log("Got an event!\n");
}
Uint64 now = SDL_GetTicks();
SDL_Log("Waited %d ms for events\n", (int)(now - then));
#endif
while (SDL_PollEvent(&event)) {
SDLTest_CommonEvent(state, &event, &done);
@ -248,7 +258,7 @@ static void loop(void)
SDL_RenderPresent(renderer);
}
}
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
if (done) {
emscripten_cancel_main_loop();
}
@ -281,7 +291,7 @@ int main(int argc, char *argv[])
/* Main render loop */
done = 0;
#ifdef __EMSCRIPTEN__
#ifdef SDL_PLATFORM_EMSCRIPTEN
emscripten_set_main_loop(loop, 0, 1);
#else
while (!done) {

View File

@ -15,8 +15,8 @@
#include "testyuv_cvt.h"
#include "testutils.h"
/* 422 (YUY2, etc) formats are the largest */
#define MAX_YUV_SURFACE_SIZE(W, H, P) (H * 4 * (W + P + 1) / 2)
/* 422 (YUY2, etc) and P010 formats are the largest */
#define MAX_YUV_SURFACE_SIZE(W, H, P) ((H + 1) * ((W + 1) + P) * 4)
/* Return true if the YUV format is packed pixels */
static SDL_bool is_packed_yuv_format(Uint32 format)
@ -65,9 +65,8 @@ static SDL_Surface *generate_test_pattern(int pattern_size)
return pattern;
}
static SDL_bool verify_yuv_data(Uint32 format, const Uint8 *yuv, int yuv_pitch, SDL_Surface *surface)
static SDL_bool verify_yuv_data(Uint32 format, SDL_Colorspace colorspace, const Uint8 *yuv, int yuv_pitch, SDL_Surface *surface, int tolerance)
{
const int tolerance = 20;
const int size = (surface->h * surface->pitch);
Uint8 *rgb;
SDL_bool result = SDL_FALSE;
@ -78,7 +77,7 @@ static SDL_bool verify_yuv_data(Uint32 format, const Uint8 *yuv, int yuv_pitch,
return SDL_FALSE;
}
if (SDL_ConvertPixels(surface->w, surface->h, format, yuv, yuv_pitch, surface->format->format, rgb, surface->pitch) == 0) {
if (SDL_ConvertPixelsAndColorspace(surface->w, surface->h, format, colorspace, 0, yuv, yuv_pitch, surface->format->format, SDL_COLORSPACE_SRGB, 0, rgb, surface->pitch) == 0) {
int x, y;
result = SDL_TRUE;
for (y = 0; y < surface->h; ++y) {
@ -122,6 +121,10 @@ static int run_automated_tests(int pattern_size, int extra_pitch)
Uint8 *yuv1 = (Uint8 *)SDL_malloc(yuv_len);
Uint8 *yuv2 = (Uint8 *)SDL_malloc(yuv_len);
int yuv1_pitch, yuv2_pitch;
YUV_CONVERSION_MODE mode;
SDL_Colorspace colorspace;
const int tight_tolerance = 20;
const int loose_tolerance = 333;
int result = -1;
if (!pattern || !yuv1 || !yuv2) {
@ -129,14 +132,17 @@ static int run_automated_tests(int pattern_size, int extra_pitch)
goto done;
}
mode = GetYUVConversionModeForResolution(pattern->w, pattern->h);
colorspace = GetColorspaceForYUVConversionMode(mode);
/* Verify conversion from YUV formats */
for (i = 0; i < SDL_arraysize(formats); ++i) {
if (!ConvertRGBtoYUV(formats[i], pattern->pixels, pattern->pitch, yuv1, pattern->w, pattern->h, SDL_GetYUVConversionModeForResolution(pattern->w, pattern->h), 0, 100)) {
if (!ConvertRGBtoYUV(formats[i], pattern->pixels, pattern->pitch, yuv1, pattern->w, pattern->h, mode, 0, 100)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "ConvertRGBtoYUV() doesn't support converting to %s\n", SDL_GetPixelFormatName(formats[i]));
goto done;
}
yuv1_pitch = CalculateYUVPitch(formats[i], pattern->w);
if (!verify_yuv_data(formats[i], yuv1, yuv1_pitch, pattern)) {
if (!verify_yuv_data(formats[i], colorspace, yuv1, yuv1_pitch, pattern, tight_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from %s to RGB\n", SDL_GetPixelFormatName(formats[i]));
goto done;
}
@ -145,11 +151,11 @@ static int run_automated_tests(int pattern_size, int extra_pitch)
/* Verify conversion to YUV formats */
for (i = 0; i < SDL_arraysize(formats); ++i) {
yuv1_pitch = CalculateYUVPitch(formats[i], pattern->w) + extra_pitch;
if (SDL_ConvertPixels(pattern->w, pattern->h, pattern->format->format, pattern->pixels, pattern->pitch, formats[i], yuv1, yuv1_pitch) < 0) {
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, pattern->format->format, SDL_COLORSPACE_SRGB, 0, pattern->pixels, pattern->pitch, formats[i], colorspace, 0, yuv1, yuv1_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(pattern->format->format), SDL_GetPixelFormatName(formats[i]), SDL_GetError());
goto done;
}
if (!verify_yuv_data(formats[i], yuv1, yuv1_pitch, pattern)) {
if (!verify_yuv_data(formats[i], colorspace, yuv1, yuv1_pitch, pattern, tight_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from RGB to %s\n", SDL_GetPixelFormatName(formats[i]));
goto done;
}
@ -160,15 +166,15 @@ static int run_automated_tests(int pattern_size, int extra_pitch)
for (j = 0; j < SDL_arraysize(formats); ++j) {
yuv1_pitch = CalculateYUVPitch(formats[i], pattern->w) + extra_pitch;
yuv2_pitch = CalculateYUVPitch(formats[j], pattern->w) + extra_pitch;
if (SDL_ConvertPixels(pattern->w, pattern->h, pattern->format->format, pattern->pixels, pattern->pitch, formats[i], yuv1, yuv1_pitch) < 0) {
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, pattern->format->format, SDL_COLORSPACE_SRGB, 0, pattern->pixels, pattern->pitch, formats[i], colorspace, 0, yuv1, yuv1_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(pattern->format->format), SDL_GetPixelFormatName(formats[i]), SDL_GetError());
goto done;
}
if (SDL_ConvertPixels(pattern->w, pattern->h, formats[i], yuv1, yuv1_pitch, formats[j], yuv2, yuv2_pitch) < 0) {
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, formats[i], colorspace, 0, yuv1, yuv1_pitch, formats[j], colorspace, 0, yuv2, yuv2_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(formats[i]), SDL_GetPixelFormatName(formats[j]), SDL_GetError());
goto done;
}
if (!verify_yuv_data(formats[j], yuv2, yuv2_pitch, pattern)) {
if (!verify_yuv_data(formats[j], colorspace, yuv2, yuv2_pitch, pattern, tight_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from %s to %s\n", SDL_GetPixelFormatName(formats[i]), SDL_GetPixelFormatName(formats[j]));
goto done;
}
@ -185,21 +191,45 @@ static int run_automated_tests(int pattern_size, int extra_pitch)
yuv1_pitch = CalculateYUVPitch(formats[i], pattern->w) + extra_pitch;
yuv2_pitch = CalculateYUVPitch(formats[j], pattern->w) + extra_pitch;
if (SDL_ConvertPixels(pattern->w, pattern->h, pattern->format->format, pattern->pixels, pattern->pitch, formats[i], yuv1, yuv1_pitch) < 0) {
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, pattern->format->format, SDL_COLORSPACE_SRGB, 0, pattern->pixels, pattern->pitch, formats[i], colorspace, 0, yuv1, yuv1_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(pattern->format->format), SDL_GetPixelFormatName(formats[i]), SDL_GetError());
goto done;
}
if (SDL_ConvertPixels(pattern->w, pattern->h, formats[i], yuv1, yuv1_pitch, formats[j], yuv1, yuv2_pitch) < 0) {
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, formats[i], colorspace, 0, yuv1, yuv1_pitch, formats[j], colorspace, 0, yuv1, yuv2_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(formats[i]), SDL_GetPixelFormatName(formats[j]), SDL_GetError());
goto done;
}
if (!verify_yuv_data(formats[j], yuv1, yuv2_pitch, pattern)) {
if (!verify_yuv_data(formats[j], colorspace, yuv1, yuv2_pitch, pattern, tight_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from %s to %s\n", SDL_GetPixelFormatName(formats[i]), SDL_GetPixelFormatName(formats[j]));
goto done;
}
}
}
/* Verify round trip through BT.2020 */
colorspace = SDL_COLORSPACE_BT2020_FULL;
if (!ConvertRGBtoYUV(SDL_PIXELFORMAT_P010, pattern->pixels, pattern->pitch, yuv1, pattern->w, pattern->h, YUV_CONVERSION_BT2020, 0, 100)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "ConvertRGBtoYUV() doesn't support converting to %s\n", SDL_GetPixelFormatName(SDL_PIXELFORMAT_P010));
goto done;
}
yuv1_pitch = CalculateYUVPitch(SDL_PIXELFORMAT_P010, pattern->w);
if (!verify_yuv_data(SDL_PIXELFORMAT_P010, colorspace, yuv1, yuv1_pitch, pattern, tight_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from %s to RGB\n", SDL_GetPixelFormatName(SDL_PIXELFORMAT_P010));
goto done;
}
/* The pitch needs to be Uint16 aligned for P010 pixels */
yuv1_pitch = CalculateYUVPitch(SDL_PIXELFORMAT_P010, pattern->w) + ((extra_pitch + 1) & ~1);
if (SDL_ConvertPixelsAndColorspace(pattern->w, pattern->h, pattern->format->format, SDL_COLORSPACE_SRGB, 0, pattern->pixels, pattern->pitch, SDL_PIXELFORMAT_P010, colorspace, 0, yuv1, yuv1_pitch) < 0) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't convert %s to %s: %s\n", SDL_GetPixelFormatName(pattern->format->format), SDL_GetPixelFormatName(SDL_PIXELFORMAT_P010), SDL_GetError());
goto done;
}
/* Going through XRGB2101010 format during P010 conversion is slightly lossy, so use looser tolerance here */
if (!verify_yuv_data(SDL_PIXELFORMAT_P010, colorspace, yuv1, yuv1_pitch, pattern, loose_tolerance)) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed conversion from RGB to %s\n", SDL_GetPixelFormatName(SDL_PIXELFORMAT_P010));
goto done;
}
result = 0;
done:
@ -217,6 +247,8 @@ int main(int argc, char **argv)
int pattern_size;
int extra_pitch;
} automated_test_params[] = {
/* Test: single pixel */
{ SDL_FALSE, 1, 0 },
/* Test: even width and height */
{ SDL_FALSE, 2, 0 },
{ SDL_FALSE, 4, 0 },
@ -249,10 +281,16 @@ int main(int argc, char **argv)
SDL_Texture *output[3];
const char *titles[3] = { "ORIGINAL", "SOFTWARE", "HARDWARE" };
char title[128];
const char *yuv_name;
const char *yuv_mode;
Uint32 rgb_format = SDL_PIXELFORMAT_RGBX8888;
YUV_CONVERSION_MODE yuv_mode;
const char *yuv_mode_name;
Uint32 yuv_format = SDL_PIXELFORMAT_YV12;
const char *yuv_format_name;
SDL_Colorspace yuv_colorspace;
Uint32 rgb_format = SDL_PIXELFORMAT_RGBX8888;
SDL_Colorspace rgb_colorspace = SDL_COLORSPACE_SRGB;
SDL_PropertiesID props;
SDL_bool monochrome = SDL_FALSE;
int luminance = 100;
int current = 0;
int pitch;
Uint8 *raw_yuv;
@ -277,16 +315,19 @@ int main(int argc, char **argv)
consumed = SDLTest_CommonArg(state, i);
if (!consumed) {
if (SDL_strcmp(argv[i], "--jpeg") == 0) {
SDL_SetYUVConversionMode(SDL_YUV_CONVERSION_JPEG);
SetYUVConversionMode(YUV_CONVERSION_JPEG);
consumed = 1;
} else if (SDL_strcmp(argv[i], "--bt601") == 0) {
SDL_SetYUVConversionMode(SDL_YUV_CONVERSION_BT601);
SetYUVConversionMode(YUV_CONVERSION_BT601);
consumed = 1;
} else if (SDL_strcmp(argv[i], "--bt709") == 0) {
SDL_SetYUVConversionMode(SDL_YUV_CONVERSION_BT709);
SetYUVConversionMode(YUV_CONVERSION_BT709);
consumed = 1;
} else if (SDL_strcmp(argv[i], "--bt2020") == 0) {
SetYUVConversionMode(YUV_CONVERSION_BT2020);
consumed = 1;
} else if (SDL_strcmp(argv[i], "--auto") == 0) {
SDL_SetYUVConversionMode(SDL_YUV_CONVERSION_AUTOMATIC);
SetYUVConversionMode(YUV_CONVERSION_AUTOMATIC);
consumed = 1;
} else if (SDL_strcmp(argv[i], "--yv12") == 0) {
yuv_format = SDL_PIXELFORMAT_YV12;
@ -330,6 +371,12 @@ int main(int argc, char **argv)
} else if (SDL_strcmp(argv[i], "--bgra") == 0) {
rgb_format = SDL_PIXELFORMAT_BGRA8888;
consumed = 1;
} else if (SDL_strcmp(argv[i], "--monochrome") == 0) {
monochrome = SDL_TRUE;
consumed = 1;
} else if (SDL_strcmp(argv[i], "--luminance") == 0 && argv[i+1]) {
luminance = SDL_atoi(argv[i+1]);
consumed = 2;
} else if (SDL_strcmp(argv[i], "--automated") == 0) {
should_run_automated_tests = SDL_TRUE;
consumed = 1;
@ -340,9 +387,10 @@ int main(int argc, char **argv)
}
if (consumed <= 0) {
static const char *options[] = {
"[--jpeg|--bt601|-bt709|--auto]",
"[--jpeg|--bt601|--bt709|--bt2020|--auto]",
"[--yv12|--iyuv|--yuy2|--uyvy|--yvyu|--nv12|--nv21]",
"[--rgb555|--rgb565|--rgb24|--argb|--abgr|--rgba|--bgra]",
"[--monochrome] [--luminance N%]",
"[--automated]",
"[sample.bmp]",
NULL,
@ -377,10 +425,31 @@ int main(int argc, char **argv)
return 3;
}
yuv_mode = GetYUVConversionModeForResolution(original->w, original->h);
switch (yuv_mode) {
case YUV_CONVERSION_JPEG:
yuv_mode_name = "JPEG";
break;
case YUV_CONVERSION_BT601:
yuv_mode_name = "BT.601";
break;
case YUV_CONVERSION_BT709:
yuv_mode_name = "BT.709";
break;
case YUV_CONVERSION_BT2020:
yuv_mode_name = "BT.2020";
yuv_format = SDL_PIXELFORMAT_P010;
rgb_format = SDL_PIXELFORMAT_XBGR2101010;
rgb_colorspace = SDL_COLORSPACE_HDR10;
break;
default:
yuv_mode_name = "UNKNOWN";
break;
}
yuv_colorspace = GetColorspaceForYUVConversionMode(yuv_mode);
raw_yuv = SDL_calloc(1, MAX_YUV_SURFACE_SIZE(original->w, original->h, 0));
ConvertRGBtoYUV(yuv_format, original->pixels, original->pitch, raw_yuv, original->w, original->h,
SDL_GetYUVConversionModeForResolution(original->w, original->h),
0, 100);
ConvertRGBtoYUV(yuv_format, original->pixels, original->pitch, raw_yuv, original->w, original->h, yuv_mode, monochrome, luminance);
pitch = CalculateYUVPitch(yuv_format, original->w);
converted = SDL_CreateSurface(original->w, original->h, rgb_format);
@ -391,7 +460,7 @@ int main(int argc, char **argv)
then = SDL_GetTicks();
for (i = 0; i < iterations; ++i) {
SDL_ConvertPixels(original->w, original->h, yuv_format, raw_yuv, pitch, rgb_format, converted->pixels, converted->pitch);
SDL_ConvertPixelsAndColorspace(original->w, original->h, yuv_format, yuv_colorspace, 0, raw_yuv, pitch, rgb_format, rgb_colorspace, 0, converted->pixels, converted->pitch);
}
now = SDL_GetTicks();
SDL_LogInfo(SDL_LOG_CATEGORY_APPLICATION, "%d iterations in %" SDL_PRIu64 " ms, %.2fms each\n", iterations, (now - then), (float)(now - then) / iterations);
@ -410,31 +479,23 @@ int main(int argc, char **argv)
output[0] = SDL_CreateTextureFromSurface(renderer, original);
output[1] = SDL_CreateTextureFromSurface(renderer, converted);
output[2] = SDL_CreateTexture(renderer, yuv_format, SDL_TEXTUREACCESS_STREAMING, original->w, original->h);
props = SDL_CreateProperties();
SDL_SetNumberProperty(props, SDL_PROP_TEXTURE_CREATE_COLORSPACE_NUMBER, yuv_colorspace);
SDL_SetNumberProperty(props, SDL_PROP_TEXTURE_CREATE_FORMAT_NUMBER, yuv_format);
SDL_SetNumberProperty(props, SDL_PROP_TEXTURE_CREATE_ACCESS_NUMBER, SDL_TEXTUREACCESS_STREAMING);
SDL_SetNumberProperty(props, SDL_PROP_TEXTURE_CREATE_WIDTH_NUMBER, original->w);
SDL_SetNumberProperty(props, SDL_PROP_TEXTURE_CREATE_HEIGHT_NUMBER, original->h);
output[2] = SDL_CreateTextureWithProperties(renderer, props);
SDL_DestroyProperties(props);
if (!output[0] || !output[1] || !output[2]) {
SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Couldn't set create texture: %s\n", SDL_GetError());
return 5;
}
SDL_UpdateTexture(output[2], NULL, raw_yuv, pitch);
yuv_name = SDL_GetPixelFormatName(yuv_format);
if (SDL_strncmp(yuv_name, "SDL_PIXELFORMAT_", 16) == 0) {
yuv_name += 16;
}
switch (SDL_GetYUVConversionModeForResolution(original->w, original->h)) {
case SDL_YUV_CONVERSION_JPEG:
yuv_mode = "JPEG";
break;
case SDL_YUV_CONVERSION_BT601:
yuv_mode = "BT.601";
break;
case SDL_YUV_CONVERSION_BT709:
yuv_mode = "BT.709";
break;
default:
yuv_mode = "UNKNOWN";
break;
yuv_format_name = SDL_GetPixelFormatName(yuv_format);
if (SDL_strncmp(yuv_format_name, "SDL_PIXELFORMAT_", 16) == 0) {
yuv_format_name += 16;
}
{
@ -477,7 +538,7 @@ int main(int argc, char **argv)
if (current == 0) {
SDLTest_DrawString(renderer, 4, 4, titles[current]);
} else {
(void)SDL_snprintf(title, sizeof(title), "%s %s %s", titles[current], yuv_name, yuv_mode);
(void)SDL_snprintf(title, sizeof(title), "%s %s %s", titles[current], yuv_format_name, yuv_mode_name);
SDLTest_DrawString(renderer, 4, 4, title);
}
SDL_RenderPresent(renderer);

View File

@ -14,68 +14,215 @@
#include "testyuv_cvt.h"
#define YUV_SD_THRESHOLD 576
static YUV_CONVERSION_MODE YUV_ConversionMode = YUV_CONVERSION_BT601;
void SetYUVConversionMode(YUV_CONVERSION_MODE mode)
{
YUV_ConversionMode = mode;
}
YUV_CONVERSION_MODE GetYUVConversionMode(void)
{
return YUV_ConversionMode;
}
YUV_CONVERSION_MODE GetYUVConversionModeForResolution(int width, int height)
{
YUV_CONVERSION_MODE mode = GetYUVConversionMode();
if (mode == YUV_CONVERSION_AUTOMATIC) {
if (height <= YUV_SD_THRESHOLD) {
mode = YUV_CONVERSION_BT601;
} else {
mode = YUV_CONVERSION_BT709;
}
}
return mode;
}
SDL_Colorspace GetColorspaceForYUVConversionMode(YUV_CONVERSION_MODE mode)
{
SDL_Colorspace colorspace;
switch (mode) {
case YUV_CONVERSION_JPEG:
colorspace = SDL_DEFINE_COLORSPACE(SDL_COLOR_TYPE_YCBCR,
SDL_COLOR_RANGE_FULL,
SDL_COLOR_PRIMARIES_BT709,
SDL_TRANSFER_CHARACTERISTICS_BT601,
SDL_MATRIX_COEFFICIENTS_BT601,
SDL_CHROMA_LOCATION_CENTER);
break;
case YUV_CONVERSION_BT601:
colorspace = SDL_DEFINE_COLORSPACE(SDL_COLOR_TYPE_YCBCR,
SDL_COLOR_RANGE_LIMITED,
SDL_COLOR_PRIMARIES_BT709,
SDL_TRANSFER_CHARACTERISTICS_BT601,
SDL_MATRIX_COEFFICIENTS_BT601,
SDL_CHROMA_LOCATION_CENTER);
break;
case YUV_CONVERSION_BT709:
colorspace = SDL_DEFINE_COLORSPACE(SDL_COLOR_TYPE_YCBCR,
SDL_COLOR_RANGE_LIMITED,
SDL_COLOR_PRIMARIES_BT709,
SDL_TRANSFER_CHARACTERISTICS_BT709,
SDL_MATRIX_COEFFICIENTS_BT709,
SDL_CHROMA_LOCATION_CENTER);
break;
case YUV_CONVERSION_BT2020:
colorspace = SDL_COLORSPACE_BT2020_FULL;
break;
default:
colorspace = SDL_COLORSPACE_UNKNOWN;
break;
}
return colorspace;
}
static float clip3(float x, float y, float z)
{
return (z < x) ? x : ((z > y) ? y : z);
}
static void RGBtoYUV(const Uint8 *rgb, int *yuv, SDL_YUV_CONVERSION_MODE mode, int monochrome, int luminance)
static float sRGBtoNits(float v)
{
if (mode == SDL_YUV_CONVERSION_JPEG) {
/* Full range YUV */
yuv[0] = (int)(0.299 * rgb[0] + 0.587 * rgb[1] + 0.114 * rgb[2]);
yuv[1] = (int)((rgb[2] - yuv[0]) * 0.565 + 128);
yuv[2] = (int)((rgb[0] - yuv[0]) * 0.713 + 128);
/* Normalize from 0..255 */
v /= 255.0f;
/* Convert from sRGB */
v = v <= 0.04045f ? (v / 12.92f) : SDL_powf(((v + 0.055f) / 1.055f), 2.4f);
/* Convert to nits, using a default SDR whitepoint of 203 */
v *= 203.0f;
return v;
}
static float PQfromNits(float v)
{
const float c1 = 0.8359375f;
const float c2 = 18.8515625f;
const float c3 = 18.6875f;
const float m1 = 0.1593017578125f;
const float m2 = 78.84375f;
float y = SDL_clamp(v / 10000.0f, 0.0f, 1.0f);
float num = c1 + c2 * SDL_powf(y, m1);
float den = 1.0f + c3 * SDL_powf(y, m1);
return SDL_powf(num / den, m2);
}
void ConvertRec709toRec2020(float *fR, float *fG, float *fB)
{
static const float mat709to2020[] = {
0.627404f, 0.329283f, 0.043313f,
0.069097f, 0.919541f, 0.011362f,
0.016391f, 0.088013f, 0.895595f,
};
const float *matrix = mat709to2020;
float v[3];
v[0] = *fR;
v[1] = *fG;
v[2] = *fB;
*fR = matrix[0 * 3 + 0] * v[0] + matrix[0 * 3 + 1] * v[1] + matrix[0 * 3 + 2] * v[2];
*fG = matrix[1 * 3 + 0] * v[0] + matrix[1 * 3 + 1] * v[1] + matrix[1 * 3 + 2] * v[2];
*fB = matrix[2 * 3 + 0] * v[0] + matrix[2 * 3 + 1] * v[1] + matrix[2 * 3 + 2] * v[2];
}
static void RGBtoYUV(const Uint8 *rgb, int rgb_bits, int *yuv, int yuv_bits, YUV_CONVERSION_MODE mode, int monochrome, int luminance)
{
/**
* This formula is from Microsoft's documentation:
* https://msdn.microsoft.com/en-us/library/windows/desktop/dd206750(v=vs.85).aspx
* L = Kr * R + Kb * B + (1 - Kr - Kb) * G
* Y = floor(2^(M-8) * (219*(L-Z)/S + 16) + 0.5);
* U = clip3(0, (2^M)-1, floor(2^(M-8) * (112*(B-L) / ((1-Kb)*S) + 128) + 0.5));
* V = clip3(0, (2^M)-1, floor(2^(M-8) * (112*(R-L) / ((1-Kr)*S) + 128) + 0.5));
*/
SDL_bool studio_RGB = SDL_FALSE;
SDL_bool full_range_YUV = SDL_FALSE;
float N, M, S, Z, R, G, B, L, Kr, Kb, Y, U, V;
N = (float)rgb_bits;
M = (float)yuv_bits;
switch (mode) {
case YUV_CONVERSION_JPEG:
case YUV_CONVERSION_BT601:
/* BT.601 */
Kr = 0.299f;
Kb = 0.114f;
break;
case YUV_CONVERSION_BT709:
/* BT.709 */
Kr = 0.2126f;
Kb = 0.0722f;
break;
case YUV_CONVERSION_BT2020:
/* BT.2020 */
Kr = 0.2627f;
Kb = 0.0593f;
break;
default:
/* Invalid */
Kr = 1.0f;
Kb = 1.0f;
break;
}
R = rgb[0];
G = rgb[1];
B = rgb[2];
if (mode == YUV_CONVERSION_JPEG || mode == YUV_CONVERSION_BT2020) {
full_range_YUV = SDL_TRUE;
}
if (mode == YUV_CONVERSION_BT2020) {
/* Input is sRGB, need to convert to BT.2020 PQ YUV */
R = sRGBtoNits(R);
G = sRGBtoNits(G);
B = sRGBtoNits(B);
ConvertRec709toRec2020(&R, &G, &B);
R = PQfromNits(R);
G = PQfromNits(G);
B = PQfromNits(B);
S = 1.0f;
Z = 0.0f;
} else if (studio_RGB) {
S = 219.0f * SDL_powf(2.0f, N - 8);
Z = 16.0f * SDL_powf(2.0f, N - 8);
} else {
/**
* This formula is from Microsoft's documentation:
* https://msdn.microsoft.com/en-us/library/windows/desktop/dd206750(v=vs.85).aspx
* L = Kr * R + Kb * B + (1 - Kr - Kb) * G
* Y = SDL_floor(2^(M-8) * (219*(L-Z)/S + 16) + 0.5);
* U = clip3(0, (2^M)-1, SDL_floor(2^(M-8) * (112*(B-L) / ((1-Kb)*S) + 128) + 0.5));
* V = clip3(0, (2^M)-1, SDL_floor(2^(M-8) * (112*(R-L) / ((1-Kr)*S) + 128) + 0.5));
*/
float S, Z, R, G, B, L, Kr, Kb, Y, U, V;
if (mode == SDL_YUV_CONVERSION_BT709) {
/* BT.709 */
Kr = 0.2126f;
Kb = 0.0722f;
} else {
/* BT.601 */
Kr = 0.299f;
Kb = 0.114f;
}
S = 255.0f;
Z = 0.0f;
R = rgb[0];
G = rgb[1];
B = rgb[2];
L = Kr * R + Kb * B + (1 - Kr - Kb) * G;
Y = (Uint8)SDL_floorf((219 * (L - Z) / S + 16) + 0.5f);
U = (Uint8)clip3(0, 255, SDL_floorf((112.0f * (B - L) / ((1.0f - Kb) * S) + 128) + 0.5f));
V = (Uint8)clip3(0, 255, SDL_floorf((112.0f * (R - L) / ((1.0f - Kr) * S) + 128) + 0.5f));
yuv[0] = (Uint8)Y;
yuv[1] = (Uint8)U;
yuv[2] = (Uint8)V;
}
L = Kr * R + Kb * B + (1 - Kr - Kb) * G;
if (monochrome) {
yuv[1] = 128;
yuv[2] = 128;
R = L;
B = L;
}
if (full_range_YUV) {
Y = SDL_floorf((SDL_powf(2.0f, M) - 1) * ((L - Z) / S) + 0.5f);
U = clip3(0, SDL_powf(2.0f, M) - 1, SDL_floorf((SDL_powf(2.0f, M) / 2 - 1) * ((B - L) / ((1.0f - Kb) * S)) + SDL_powf(2.0f, M) / 2 + 0.5f));
V = clip3(0, SDL_powf(2.0f, M) - 1, SDL_floorf((SDL_powf(2.0f, M) / 2 - 1) * ((R - L) / ((1.0f - Kr) * S)) + SDL_powf(2.0f, M) / 2 + 0.5f));
} else {
Y = SDL_floorf(SDL_powf(2.0f, (M - 8)) * (219.0f * (L - Z) / S + 16) + 0.5f);
U = clip3(0, SDL_powf(2.0f, M) - 1, SDL_floorf(SDL_powf(2.0f, (M - 8)) * (112.0f * (B - L) / ((1.0f - Kb) * S) + 128) + 0.5f));
V = clip3(0, SDL_powf(2.0f, M) - 1, SDL_floorf(SDL_powf(2.0f, (M - 8)) * (112.0f * (R - L) / ((1.0f - Kr) * S) + 128) + 0.5f));
}
yuv[0] = (int)Y;
yuv[1] = (int)U;
yuv[2] = (int)V;
if (luminance != 100) {
yuv[0] = yuv[0] * luminance / 100;
if (yuv[0] > 255) {
yuv[0] = 255;
}
yuv[0] = (int)clip3(0, SDL_powf(2.0f, M) - 1, SDL_roundf(yuv[0] * (luminance / 100.0f)));
}
}
static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, SDL_YUV_CONVERSION_MODE mode, int monochrome, int luminance)
static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, YUV_CONVERSION_MODE mode, int monochrome, int luminance)
{
int x, y;
int yuv[4][3];
@ -117,19 +264,19 @@ static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *o
for (y = 0; y < (h - 1); y += 2) {
for (x = 0; x < (w - 1); x += 2) {
RGBtoYUV(rgb1, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[0], 8, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = (Uint8)yuv[0][0];
RGBtoYUV(rgb1, yuv[1], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[1], 8, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = (Uint8)yuv[1][0];
RGBtoYUV(rgb2, yuv[2], mode, monochrome, luminance);
RGBtoYUV(rgb2, 8, yuv[2], 8, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = (Uint8)yuv[2][0];
RGBtoYUV(rgb2, yuv[3], mode, monochrome, luminance);
RGBtoYUV(rgb2, 8, yuv[3], 8, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = (Uint8)yuv[3][0];
@ -141,11 +288,11 @@ static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *o
}
/* Last column */
if (x == (w - 1)) {
RGBtoYUV(rgb1, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[0], 8, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = (Uint8)yuv[0][0];
RGBtoYUV(rgb2, yuv[2], mode, monochrome, luminance);
RGBtoYUV(rgb2, 8, yuv[2], 8, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = (Uint8)yuv[2][0];
@ -163,11 +310,11 @@ static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *o
/* Last row */
if (y == (h - 1)) {
for (x = 0; x < (w - 1); x += 2) {
RGBtoYUV(rgb1, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[0], 8, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = (Uint8)yuv[0][0];
RGBtoYUV(rgb1, yuv[1], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[1], 8, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = (Uint8)yuv[1][0];
@ -179,7 +326,7 @@ static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *o
}
/* Last column */
if (x == (w - 1)) {
RGBtoYUV(rgb1, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb1, 8, yuv[0], 8, mode, monochrome, luminance);
*Y1++ = (Uint8)yuv[0][0];
*U = (Uint8)yuv[0][1];
@ -191,7 +338,113 @@ static void ConvertRGBtoPlanar2x2(Uint32 format, Uint8 *src, int pitch, Uint8 *o
}
}
static void ConvertRGBtoPacked4(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, SDL_YUV_CONVERSION_MODE mode, int monochrome, int luminance)
static Uint16 Pack10to16(int v)
{
return (Uint16)(v << 6);
}
static void ConvertRGBtoPlanar2x2_P010(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, YUV_CONVERSION_MODE mode, int monochrome, int luminance)
{
int x, y;
int yuv[4][3];
Uint16 *Y1, *Y2, *U, *V;
Uint8 *rgb1, *rgb2;
int rgb_row_advance = (pitch - w * 3) + pitch;
int UV_advance;
rgb1 = src;
rgb2 = src + pitch;
Y1 = (Uint16 *)out;
Y2 = Y1 + w;
switch (format) {
case SDL_PIXELFORMAT_P010:
U = (Y1 + h * w);
V = U + 1;
UV_advance = 2;
break;
default:
SDL_assert(!"Unsupported planar YUV format");
return;
}
for (y = 0; y < (h - 1); y += 2) {
for (x = 0; x < (w - 1); x += 2) {
RGBtoYUV(rgb1, 8, yuv[0], 10, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = Pack10to16(yuv[0][0]);
RGBtoYUV(rgb1, 8, yuv[1], 10, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = Pack10to16(yuv[1][0]);
RGBtoYUV(rgb2, 8, yuv[2], 10, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = Pack10to16(yuv[2][0]);
RGBtoYUV(rgb2, 8, yuv[3], 10, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = Pack10to16(yuv[3][0]);
*U = Pack10to16((int)SDL_floorf((yuv[0][1] + yuv[1][1] + yuv[2][1] + yuv[3][1]) / 4.0f + 0.5f));
U += UV_advance;
*V = Pack10to16((int)SDL_floorf((yuv[0][2] + yuv[1][2] + yuv[2][2] + yuv[3][2]) / 4.0f + 0.5f));
V += UV_advance;
}
/* Last column */
if (x == (w - 1)) {
RGBtoYUV(rgb1, 8, yuv[0], 10, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = Pack10to16(yuv[0][0]);
RGBtoYUV(rgb2, 8, yuv[2], 10, mode, monochrome, luminance);
rgb2 += 3;
*Y2++ = Pack10to16(yuv[2][0]);
*U = Pack10to16((int)SDL_floorf((yuv[0][1] + yuv[2][1]) / 2.0f + 0.5f));
U += UV_advance;
*V = Pack10to16((int)SDL_floorf((yuv[0][2] + yuv[2][2]) / 2.0f + 0.5f));
V += UV_advance;
}
Y1 += w;
Y2 += w;
rgb1 += rgb_row_advance;
rgb2 += rgb_row_advance;
}
/* Last row */
if (y == (h - 1)) {
for (x = 0; x < (w - 1); x += 2) {
RGBtoYUV(rgb1, 8, yuv[0], 10, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = Pack10to16(yuv[0][0]);
RGBtoYUV(rgb1, 8, yuv[1], 10, mode, monochrome, luminance);
rgb1 += 3;
*Y1++ = Pack10to16(yuv[1][0]);
*U = Pack10to16((int)SDL_floorf((yuv[0][1] + yuv[1][1]) / 2.0f + 0.5f));
U += UV_advance;
*V = Pack10to16((int)SDL_floorf((yuv[0][2] + yuv[1][2]) / 2.0f + 0.5f));
V += UV_advance;
}
/* Last column */
if (x == (w - 1)) {
RGBtoYUV(rgb1, 8, yuv[0], 10, mode, monochrome, luminance);
*Y1++ = Pack10to16(yuv[0][0]);
*U = Pack10to16(yuv[0][1]);
U += UV_advance;
*V = Pack10to16(yuv[0][2]);
V += UV_advance;
}
}
}
static void ConvertRGBtoPacked4(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, YUV_CONVERSION_MODE mode, int monochrome, int luminance)
{
int x, y;
int yuv[2][3];
@ -227,12 +480,12 @@ static void ConvertRGBtoPacked4(Uint32 format, Uint8 *src, int pitch, Uint8 *out
for (y = 0; y < h; ++y) {
for (x = 0; x < (w - 1); x += 2) {
RGBtoYUV(rgb, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb, 8, yuv[0], 8, mode, monochrome, luminance);
rgb += 3;
*Y1 = (Uint8)yuv[0][0];
Y1 += 4;
RGBtoYUV(rgb, yuv[1], mode, monochrome, luminance);
RGBtoYUV(rgb, 8, yuv[1], 8, mode, monochrome, luminance);
rgb += 3;
*Y2 = (Uint8)yuv[1][0];
Y2 += 4;
@ -245,7 +498,7 @@ static void ConvertRGBtoPacked4(Uint32 format, Uint8 *src, int pitch, Uint8 *out
}
/* Last column */
if (x == (w - 1)) {
RGBtoYUV(rgb, yuv[0], mode, monochrome, luminance);
RGBtoYUV(rgb, 8, yuv[0], 8, mode, monochrome, luminance);
rgb += 3;
*Y2 = *Y1 = (Uint8)yuv[0][0];
Y1 += 4;
@ -261,9 +514,12 @@ static void ConvertRGBtoPacked4(Uint32 format, Uint8 *src, int pitch, Uint8 *out
}
}
SDL_bool ConvertRGBtoYUV(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, SDL_YUV_CONVERSION_MODE mode, int monochrome, int luminance)
SDL_bool ConvertRGBtoYUV(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, YUV_CONVERSION_MODE mode, int monochrome, int luminance)
{
switch (format) {
case SDL_PIXELFORMAT_P010:
ConvertRGBtoPlanar2x2_P010(format, src, pitch, out, w, h, mode, monochrome, luminance);
return SDL_TRUE;
case SDL_PIXELFORMAT_YV12:
case SDL_PIXELFORMAT_IYUV:
case SDL_PIXELFORMAT_NV12:
@ -283,6 +539,8 @@ SDL_bool ConvertRGBtoYUV(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w
int CalculateYUVPitch(Uint32 format, int width)
{
switch (format) {
case SDL_PIXELFORMAT_P010:
return width * 2;
case SDL_PIXELFORMAT_YV12:
case SDL_PIXELFORMAT_IYUV:
case SDL_PIXELFORMAT_NV12:

View File

@ -12,5 +12,17 @@
/* These functions are designed for testing correctness, not for speed */
extern SDL_bool ConvertRGBtoYUV(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, SDL_YUV_CONVERSION_MODE mode, int monochrome, int luminance);
typedef enum
{
YUV_CONVERSION_JPEG, /**< Full range JPEG */
YUV_CONVERSION_BT601, /**< BT.601 (the default) */
YUV_CONVERSION_BT709, /**< BT.709 */
YUV_CONVERSION_BT2020, /**< BT.2020 */
YUV_CONVERSION_AUTOMATIC /**< BT.601 for SD content, BT.709 for HD content */
} YUV_CONVERSION_MODE;
extern void SetYUVConversionMode(YUV_CONVERSION_MODE mode);
extern YUV_CONVERSION_MODE GetYUVConversionModeForResolution(int width, int height);
extern SDL_Colorspace GetColorspaceForYUVConversionMode(YUV_CONVERSION_MODE mode);
extern SDL_bool ConvertRGBtoYUV(Uint32 format, Uint8 *src, int pitch, Uint8 *out, int w, int h, YUV_CONVERSION_MODE mode, int monochrome, int luminance);
extern int CalculateYUVPitch(Uint32 format, int width);