camera selection menu
This commit is contained in:
		
							parent
							
								
									3e6bf957f7
								
							
						
					
					
						commit
						943db8cf5e
					
				
					 1 changed files with 152 additions and 63 deletions
				
			
		
							
								
								
									
										215
									
								
								main.c
									
										
									
									
									
								
							
							
						
						
									
										215
									
								
								main.c
									
										
									
									
									
								
							| 
						 | 
				
			
			@ -1,7 +1,8 @@
 | 
			
		|||
#include "SDL3/SDL_camera.h"
 | 
			
		||||
#define SDL_MAIN_USE_CALLBACKS 1
 | 
			
		||||
#include "SDL3/SDL_blendmode.h"
 | 
			
		||||
#include "SDL3/SDL_camera.h"
 | 
			
		||||
#include "SDL3/SDL_error.h"
 | 
			
		||||
#include "SDL3/SDL_events.h"
 | 
			
		||||
#include "SDL3/SDL_init.h"
 | 
			
		||||
#include "SDL3/SDL_keycode.h"
 | 
			
		||||
#include "SDL3/SDL_log.h"
 | 
			
		||||
| 
						 | 
				
			
			@ -17,7 +18,8 @@
 | 
			
		|||
#include "mgba/core/core.h"
 | 
			
		||||
#include "mgba/core/interface.h"
 | 
			
		||||
#include "mgba/feature/commandline.h"
 | 
			
		||||
//#include "mgba-util/image.h"
 | 
			
		||||
 | 
			
		||||
#include <stdio.h>
 | 
			
		||||
 | 
			
		||||
#define NUM_CHANNELS 3
 | 
			
		||||
#define FRAMESKIP_LIMIT 20
 | 
			
		||||
| 
						 | 
				
			
			@ -132,14 +134,156 @@ void myRequestImageBlue(struct mImageSource* self, const void** buf, size_t* str
 | 
			
		|||
 | 
			
		||||
struct mImageSource gb_img_src[3];
 | 
			
		||||
 | 
			
		||||
SDL_AppResult SDL_AppInit(void** appstate, int argc, char *argv[]) {
 | 
			
		||||
bool SelectCamera(SDL_Renderer* renderer) {
 | 
			
		||||
    SDL_Event event;
 | 
			
		||||
 | 
			
		||||
    int devcount = 0;
 | 
			
		||||
    int cam_idx = 0, spec_idx = 0;
 | 
			
		||||
 | 
			
		||||
    while (camera == NULL) {
 | 
			
		||||
        if (cam_idx >= devcount) {
 | 
			
		||||
            cam_idx = 0;
 | 
			
		||||
        } else if (cam_idx < 0) {
 | 
			
		||||
            cam_idx = devcount - 1;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        SDL_CameraID *devices = SDL_GetCameras(&devcount);
 | 
			
		||||
        if (!devices) {
 | 
			
		||||
            SDL_Log("SDL_GetCameras failed: %s", SDL_GetError());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (devcount == 0) {
 | 
			
		||||
            SDL_free(devices);
 | 
			
		||||
 | 
			
		||||
            SDL_SetRenderDrawColor(renderer, 0, 0, 0, 0);
 | 
			
		||||
            SDL_RenderClear(renderer);
 | 
			
		||||
 | 
			
		||||
            SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
 | 
			
		||||
            SDL_RenderDebugText(renderer, 4, 4, "connect a camera");
 | 
			
		||||
 | 
			
		||||
            SDL_RenderPresent(renderer);
 | 
			
		||||
 | 
			
		||||
            if (!SDL_WaitEvent(&event)) {
 | 
			
		||||
                SDL_Log("Error waiting for event: %s", SDL_GetError());
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            if (event.type == SDL_EVENT_QUIT) {
 | 
			
		||||
                SDL_Log("Quit!");
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            continue;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        const SDL_CameraID device = devices[cam_idx];
 | 
			
		||||
        const char *name = SDL_GetCameraName(device);
 | 
			
		||||
 | 
			
		||||
        const SDL_CameraPosition position = SDL_GetCameraPosition(device);
 | 
			
		||||
        const char *posstr = "";
 | 
			
		||||
 | 
			
		||||
        char snprintfbuf[20];
 | 
			
		||||
 | 
			
		||||
        int formats_len = 0;
 | 
			
		||||
 | 
			
		||||
        SDL_CameraSpec** formats = SDL_GetCameraSupportedFormats(device, &formats_len);
 | 
			
		||||
        if (spec_idx >= formats_len) {
 | 
			
		||||
            spec_idx = 0;
 | 
			
		||||
        } else if (spec_idx < 0) {
 | 
			
		||||
            spec_idx = formats_len - 1;
 | 
			
		||||
        }
 | 
			
		||||
        SDL_CameraSpec* format = formats[spec_idx];
 | 
			
		||||
        const char* pixfmt_name = SDL_GetPixelFormatName(format->format);
 | 
			
		||||
        if (strncmp("SDL_PIXELFORMAT_", pixfmt_name, 16) == 0) {
 | 
			
		||||
            pixfmt_name += 16;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (position == SDL_CAMERA_POSITION_FRONT_FACING) {
 | 
			
		||||
            front_camera = device;
 | 
			
		||||
            posstr = "[frontfacing]";
 | 
			
		||||
        } else if (position == SDL_CAMERA_POSITION_BACK_FACING) {
 | 
			
		||||
            back_camera = device;
 | 
			
		||||
            posstr = "[backfacing]";
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        SDL_SetRenderDrawColor(renderer, 0, 0, 0, 0);
 | 
			
		||||
        SDL_RenderClear(renderer);
 | 
			
		||||
 | 
			
		||||
        SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 4, "camera: (up/down)");
 | 
			
		||||
        snprintf(snprintfbuf, sizeof(snprintfbuf), "%d. %s", cam_idx, posstr);
 | 
			
		||||
        SDL_RenderDebugText(renderer, 8, 16, snprintfbuf);
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 28, name);
 | 
			
		||||
        SDL_free((void*)name);
 | 
			
		||||
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 52, "mode: (left/right)");
 | 
			
		||||
        snprintf(
 | 
			
		||||
            snprintfbuf,
 | 
			
		||||
            sizeof(snprintfbuf),
 | 
			
		||||
            "%d.",
 | 
			
		||||
            spec_idx
 | 
			
		||||
        );
 | 
			
		||||
        SDL_RenderDebugText(renderer, 8, 64, snprintfbuf);
 | 
			
		||||
 | 
			
		||||
        snprintf(
 | 
			
		||||
            snprintfbuf,
 | 
			
		||||
            sizeof(snprintfbuf),
 | 
			
		||||
            "%dx%d",
 | 
			
		||||
            format->width,
 | 
			
		||||
            format->height
 | 
			
		||||
        );
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 76, snprintfbuf);
 | 
			
		||||
 | 
			
		||||
        snprintf(
 | 
			
		||||
            snprintfbuf,
 | 
			
		||||
            sizeof(snprintfbuf),
 | 
			
		||||
            "%.1f Hz",
 | 
			
		||||
            ((float)format->framerate_numerator / (float)format->framerate_denominator)
 | 
			
		||||
        );
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 88, snprintfbuf);
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 100, pixfmt_name);
 | 
			
		||||
 | 
			
		||||
        SDL_RenderDebugText(renderer, 4, 124, "confirm: (enter)");
 | 
			
		||||
 | 
			
		||||
        if (!SDL_WaitEvent(&event)) {
 | 
			
		||||
            SDL_Log("Error waiting for event: %s", SDL_GetError());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        switch (event.type) {
 | 
			
		||||
            case SDL_EVENT_QUIT:
 | 
			
		||||
                SDL_Log("Quit!");
 | 
			
		||||
                return false;
 | 
			
		||||
 | 
			
		||||
            case SDL_EVENT_KEY_DOWN:
 | 
			
		||||
                switch (event.key.key) {
 | 
			
		||||
                    case SDLK_UP: cam_idx -= 1; break;
 | 
			
		||||
                    case SDLK_DOWN: cam_idx += 1; break;
 | 
			
		||||
                    case SDLK_LEFT: spec_idx -= 1; break;
 | 
			
		||||
                    case SDLK_RIGHT: spec_idx += 1; break;
 | 
			
		||||
                    case SDLK_RETURN:
 | 
			
		||||
                        camera = SDL_OpenCamera(device, format);
 | 
			
		||||
                        break;
 | 
			
		||||
                    default: break;
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            default: break;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        SDL_free(formats);
 | 
			
		||||
        SDL_free(devices);
 | 
			
		||||
 | 
			
		||||
        SDL_RenderPresent(renderer);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
SDL_AppResult SDL_AppInit(void** appstate, int argc, char *argv[]) {
 | 
			
		||||
    int i;
 | 
			
		||||
    unsigned w, h;
 | 
			
		||||
 | 
			
		||||
    SDL_CameraID *devices;
 | 
			
		||||
    SDL_CameraID devid;
 | 
			
		||||
 | 
			
		||||
    struct mArguments args;
 | 
			
		||||
    bool parsed = mArgumentsParse(&args, argc, argv, NULL, 0);
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -208,62 +352,7 @@ SDL_AppResult SDL_AppInit(void** appstate, int argc, char *argv[]) {
 | 
			
		|||
 | 
			
		||||
    SDL_SetLogPriorities(SDL_LOG_PRIORITY_VERBOSE);
 | 
			
		||||
 | 
			
		||||
    devices = SDL_GetCameras(&devcount);
 | 
			
		||||
    if (!devices) {
 | 
			
		||||
        SDL_Log("SDL_GetCameras failed: %s", SDL_GetError());
 | 
			
		||||
        return SDL_APP_FAILURE;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    SDL_Log("Saw %d camera devices.", devcount);
 | 
			
		||||
    for (i = 0; i < devcount; i++) {
 | 
			
		||||
        const SDL_CameraID device = devices[i];
 | 
			
		||||
        const char *name = SDL_GetCameraName(device);
 | 
			
		||||
        const SDL_CameraPosition position = SDL_GetCameraPosition(device);
 | 
			
		||||
        const char *posstr = "";
 | 
			
		||||
        int j, formats_len = 0;
 | 
			
		||||
        SDL_CameraSpec** formats = SDL_GetCameraSupportedFormats(device, &formats_len);
 | 
			
		||||
 | 
			
		||||
        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("  - %sCamera #%d: %s", posstr, i, name);
 | 
			
		||||
        SDL_free((void*)name);
 | 
			
		||||
 | 
			
		||||
        for (j = 0; j < formats_len; j++) {
 | 
			
		||||
            SDL_CameraSpec* fmt = formats[j];
 | 
			
		||||
            SDL_Log("    - Format %d: %s %dx%d @ %d/%d",
 | 
			
		||||
                j,
 | 
			
		||||
                SDL_GetPixelFormatName(fmt->format),
 | 
			
		||||
                fmt->width,
 | 
			
		||||
                fmt->height,
 | 
			
		||||
                fmt->framerate_numerator,
 | 
			
		||||
                fmt->framerate_denominator
 | 
			
		||||
            );
 | 
			
		||||
            spec = *fmt;
 | 
			
		||||
        }
 | 
			
		||||
        SDL_free(formats);
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    /* HACK: no front-facing? just use hardcoded index til we have selection menu. */
 | 
			
		||||
    devid = front_camera ? front_camera : devices[0];
 | 
			
		||||
    SDL_free(devices);
 | 
			
		||||
 | 
			
		||||
    if (!devid) {
 | 
			
		||||
        SDL_Log("No cameras available?");
 | 
			
		||||
        return SDL_APP_FAILURE;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    spec.format = SDL_PIXELFORMAT_XBGR1555;
 | 
			
		||||
    //spec.width = 320;
 | 
			
		||||
    //spec.height = 240;
 | 
			
		||||
    spec.framerate_numerator = 30;
 | 
			
		||||
    spec.framerate_denominator = 1;
 | 
			
		||||
    camera = SDL_OpenCamera(devid, &spec);
 | 
			
		||||
    if (!camera) {
 | 
			
		||||
    if (!SelectCamera(renderer)) {
 | 
			
		||||
        SDL_Log("Failed to open camera device: %s", SDL_GetError());
 | 
			
		||||
        return SDL_APP_FAILURE;
 | 
			
		||||
    }
 | 
			
		||||
| 
						 | 
				
			
			@ -444,7 +533,7 @@ SDL_AppResult SDL_AppIterate(void* appstate) {
 | 
			
		|||
            }
 | 
			
		||||
 | 
			
		||||
            SDL_ReleaseCameraFrame(camera, frame);
 | 
			
		||||
            
 | 
			
		||||
 | 
			
		||||
            SDL_SetSurfaceColorMod(scaled, 255, 0, 0);
 | 
			
		||||
            SDL_BlitSurface(scaled, NULL, filtered[0], NULL);
 | 
			
		||||
            SDL_SetSurfaceColorMod(scaled, 0, 255, 0);
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		
		Reference in a new issue