From fba89e6f730386bdfae0b7760086d2663146e17c Mon Sep 17 00:00:00 2001 From: Romain Vimont Date: Sun, 3 Nov 2019 18:00:11 +0100 Subject: [PATCH] Add option to specify the initial window size Add --window-width and --window-height parameters. If only one is provided, the other is computed so that the aspect ratio is preserved. --- app/scrcpy.1 | 11 +++++++++++ app/src/main.c | 49 ++++++++++++++++++++++++++++++++++++++++++++++++ app/src/scrcpy.c | 3 ++- app/src/scrcpy.h | 2 ++ app/src/screen.c | 31 ++++++++++++++++++++++++++---- app/src/screen.h | 3 ++- 6 files changed, 93 insertions(+), 6 deletions(-) diff --git a/app/scrcpy.1 b/app/scrcpy.1 index 92deef44..0c58c810 100644 --- a/app/scrcpy.1 +++ b/app/scrcpy.1 @@ -118,6 +118,17 @@ Set the initial window vertical position. Default is -1 (automatic).\n +.TP +.BI \-\-window\-width " value +Set the initial window width. + +Default is 0 (automatic).\n + +.TP +.BI \-\-window\-height " value +Set the initial window height. + +Default is 0 (automatic).\n .SH SHORTCUTS diff --git a/app/src/main.c b/app/src/main.c index 7b11bcbb..4d954740 100644 --- a/app/src/main.c +++ b/app/src/main.c @@ -31,6 +31,8 @@ struct args { uint32_t bit_rate; int16_t window_x; int16_t window_y; + uint16_t window_width; + uint16_t window_height; bool always_on_top; bool turn_screen_off; bool render_expired_frames; @@ -128,6 +130,14 @@ static void usage(const char *arg0) { " Set the initial window vertical position.\n" " Default is -1 (automatic).\n" "\n" + " --window-width value\n" + " Set the initial window width.\n" + " Default is -1 (automatic).\n" + "\n" + " --window-height value\n" + " Set the initial window width.\n" + " Default is -1 (automatic).\n" + "\n" "Shortcuts:\n" "\n" " " CTRL_OR_CMD "+f\n" @@ -289,6 +299,27 @@ parse_window_position(char *optarg, int16_t *position) { return true; } +static bool +parse_window_dimension(char *optarg, uint16_t *dimension) { + char *endptr; + if (*optarg == '\0') { + LOGE("Window dimension parameter is empty"); + return false; + } + long value = strtol(optarg, &endptr, 0); + if (*endptr != '\0') { + LOGE("Invalid window dimension: %s", optarg); + return false; + } + if (value & ~0xffff) { + LOGE("Window position must be between 0 and 65535: %ld", value); + return false; + } + + *dimension = (uint16_t) value; + return true; +} + static bool parse_port(char *optarg, uint16_t *port) { char *endptr; @@ -345,6 +376,8 @@ guess_record_format(const char *filename) { #define OPT_WINDOW_TITLE 1002 #define OPT_WINDOW_X 1003 #define OPT_WINDOW_Y 1004 +#define OPT_WINDOW_WIDTH 1005 +#define OPT_WINDOW_HEIGHT 1006 static bool parse_args(struct args *args, int argc, char *argv[]) { @@ -371,6 +404,8 @@ parse_args(struct args *args, int argc, char *argv[]) { {"window-title", required_argument, NULL, OPT_WINDOW_TITLE}, {"window-x", required_argument, NULL, OPT_WINDOW_X}, {"window-y", required_argument, NULL, OPT_WINDOW_Y}, + {"window-width", required_argument, NULL, OPT_WINDOW_WIDTH}, + {"window-height", required_argument, NULL, OPT_WINDOW_HEIGHT}, {NULL, 0, NULL, 0 }, }; int c; @@ -446,6 +481,16 @@ parse_args(struct args *args, int argc, char *argv[]) { return false; } break; + case OPT_WINDOW_WIDTH: + if (!parse_window_dimension(optarg, &args->window_width)) { + return false; + } + break; + case OPT_WINDOW_HEIGHT: + if (!parse_window_dimension(optarg, &args->window_height)) { + return false; + } + break; case OPT_PUSH_TARGET: args->push_target = optarg; break; @@ -516,6 +561,8 @@ main(int argc, char *argv[]) { .bit_rate = DEFAULT_BIT_RATE, .window_x = -1, .window_y = -1, + .window_width = 0, + .window_height = 0, .always_on_top = false, .no_control = false, .no_display = false, @@ -562,6 +609,8 @@ main(int argc, char *argv[]) { .bit_rate = args.bit_rate, .window_x = args.window_x, .window_y = args.window_y, + .window_width = args.window_width, + .window_height = args.window_height, .show_touches = args.show_touches, .fullscreen = args.fullscreen, .always_on_top = args.always_on_top, diff --git a/app/src/scrcpy.c b/app/src/scrcpy.c index d96afecc..19a7e50b 100644 --- a/app/src/scrcpy.c +++ b/app/src/scrcpy.c @@ -391,7 +391,8 @@ scrcpy(const struct scrcpy_options *options) { if (!screen_init_rendering(&screen, window_title, frame_size, options->always_on_top, options->window_x, - options->window_y)) { + options->window_y, options->window_width, + options->window_height)) { goto end; } diff --git a/app/src/scrcpy.h b/app/src/scrcpy.h index aa9f7d4b..f46773a3 100644 --- a/app/src/scrcpy.h +++ b/app/src/scrcpy.h @@ -19,6 +19,8 @@ struct scrcpy_options { uint32_t bit_rate; int16_t window_x; int16_t window_y; + uint16_t window_width; + uint16_t window_height; bool show_touches; bool fullscreen; bool always_on_top; diff --git a/app/src/screen.c b/app/src/screen.c index 85884878..f8e99090 100644 --- a/app/src/screen.c +++ b/app/src/screen.c @@ -117,9 +117,30 @@ get_optimal_window_size(const struct screen *screen, struct size frame_size) { } // initially, there is no current size, so use the frame size as current size +// req_width and req_height, if not 0, are the sizes requested by the user static inline struct size -get_initial_optimal_size(struct size frame_size) { - return get_optimal_size(frame_size, frame_size); +get_initial_optimal_size(struct size frame_size, uint16_t req_width, + uint16_t req_height) { + struct size window_size; + if (!req_width && !req_height) { + window_size = get_optimal_size(frame_size, frame_size); + } else { + if (req_width) { + window_size.width = req_width; + } else { + // compute from the requested height + window_size.width = (uint32_t) req_height * frame_size.width + / frame_size.height; + } + if (req_height) { + window_size.height = req_height; + } else { + // compute from the requested width + window_size.height = (uint32_t) req_width * frame_size.height + / frame_size.width; + } + } + return window_size; } void @@ -137,10 +158,12 @@ create_texture(SDL_Renderer *renderer, struct size frame_size) { bool screen_init_rendering(struct screen *screen, const char *window_title, struct size frame_size, bool always_on_top, - int16_t window_x, int16_t window_y) { + int16_t window_x, int16_t window_y, uint16_t window_width, + uint16_t window_height) { screen->frame_size = frame_size; - struct size window_size = get_initial_optimal_size(frame_size); + struct size window_size = + get_initial_optimal_size(frame_size, window_width, window_height); uint32_t window_flags = SDL_WINDOW_HIDDEN | SDL_WINDOW_RESIZABLE; #ifdef HIDPI_SUPPORT window_flags |= SDL_WINDOW_ALLOW_HIGHDPI; diff --git a/app/src/screen.h b/app/src/screen.h index 3c77d69b..606115b9 100644 --- a/app/src/screen.h +++ b/app/src/screen.h @@ -47,7 +47,8 @@ screen_init(struct screen *screen); bool screen_init_rendering(struct screen *screen, const char *window_title, struct size frame_size, bool always_on_top, - int16_t window_x, int16_t window_y); + int16_t window_x, int16_t window_y, uint16_t window_width, + uint16_t window_height); // show the window void