From ce064fb5e00f6999d9fe9f66e932d6dee71dfe7d Mon Sep 17 00:00:00 2001 From: Romain Vimont Date: Sun, 9 Apr 2023 19:52:01 +0200 Subject: [PATCH] Move options parsing to Options class --- .../java/com/genymobile/scrcpy/Options.java | 192 +++++++++++++++++ .../java/com/genymobile/scrcpy/Server.java | 195 +----------------- 2 files changed, 193 insertions(+), 194 deletions(-) diff --git a/server/src/main/java/com/genymobile/scrcpy/Options.java b/server/src/main/java/com/genymobile/scrcpy/Options.java index 2a3de757..0ebb790f 100644 --- a/server/src/main/java/com/genymobile/scrcpy/Options.java +++ b/server/src/main/java/com/genymobile/scrcpy/Options.java @@ -3,6 +3,7 @@ package com.genymobile.scrcpy; import android.graphics.Rect; import java.util.List; +import java.util.Locale; public class Options { @@ -289,4 +290,195 @@ public class Options { public void setSendCodecMeta(boolean sendCodecMeta) { this.sendCodecMeta = sendCodecMeta; } + + @SuppressWarnings("MethodLength") + public static Options parse(String... args) { + if (args.length < 1) { + throw new IllegalArgumentException("Missing client version"); + } + + String clientVersion = args[0]; + if (!clientVersion.equals(BuildConfig.VERSION_NAME)) { + throw new IllegalArgumentException( + "The server version (" + BuildConfig.VERSION_NAME + ") does not match the client " + "(" + clientVersion + ")"); + } + + Options options = new Options(); + + for (int i = 1; i < args.length; ++i) { + String arg = args[i]; + int equalIndex = arg.indexOf('='); + if (equalIndex == -1) { + throw new IllegalArgumentException("Invalid key=value pair: \"" + arg + "\""); + } + String key = arg.substring(0, equalIndex); + String value = arg.substring(equalIndex + 1); + switch (key) { + case "scid": + int scid = Integer.parseInt(value, 0x10); + if (scid < -1) { + throw new IllegalArgumentException("scid may not be negative (except -1 for 'none'): " + scid); + } + options.setScid(scid); + break; + case "log_level": + Ln.Level level = Ln.Level.valueOf(value.toUpperCase(Locale.ENGLISH)); + options.setLogLevel(level); + break; + case "audio": + boolean audio = Boolean.parseBoolean(value); + options.setAudio(audio); + break; + case "video_codec": + VideoCodec videoCodec = VideoCodec.findByName(value); + if (videoCodec == null) { + throw new IllegalArgumentException("Video codec " + value + " not supported"); + } + options.setVideoCodec(videoCodec); + break; + case "audio_codec": + AudioCodec audioCodec = AudioCodec.findByName(value); + if (audioCodec == null) { + throw new IllegalArgumentException("Audio codec " + value + " not supported"); + } + options.setAudioCodec(audioCodec); + break; + case "max_size": + int maxSize = Integer.parseInt(value) & ~7; // multiple of 8 + options.setMaxSize(maxSize); + break; + case "video_bit_rate": + int videoBitRate = Integer.parseInt(value); + options.setVideoBitRate(videoBitRate); + break; + case "audio_bit_rate": + int audioBitRate = Integer.parseInt(value); + options.setAudioBitRate(audioBitRate); + break; + case "max_fps": + int maxFps = Integer.parseInt(value); + options.setMaxFps(maxFps); + break; + case "lock_video_orientation": + int lockVideoOrientation = Integer.parseInt(value); + options.setLockVideoOrientation(lockVideoOrientation); + break; + case "tunnel_forward": + boolean tunnelForward = Boolean.parseBoolean(value); + options.setTunnelForward(tunnelForward); + break; + case "crop": + Rect crop = parseCrop(value); + options.setCrop(crop); + break; + case "control": + boolean control = Boolean.parseBoolean(value); + options.setControl(control); + break; + case "display_id": + int displayId = Integer.parseInt(value); + options.setDisplayId(displayId); + break; + case "show_touches": + boolean showTouches = Boolean.parseBoolean(value); + options.setShowTouches(showTouches); + break; + case "stay_awake": + boolean stayAwake = Boolean.parseBoolean(value); + options.setStayAwake(stayAwake); + break; + case "video_codec_options": + List videoCodecOptions = CodecOption.parse(value); + options.setVideoCodecOptions(videoCodecOptions); + break; + case "audio_codec_options": + List audioCodecOptions = CodecOption.parse(value); + options.setAudioCodecOptions(audioCodecOptions); + break; + case "video_encoder": + if (!value.isEmpty()) { + options.setVideoEncoder(value); + } + break; + case "audio_encoder": + if (!value.isEmpty()) { + options.setAudioEncoder(value); + } + case "power_off_on_close": + boolean powerOffScreenOnClose = Boolean.parseBoolean(value); + options.setPowerOffScreenOnClose(powerOffScreenOnClose); + break; + case "clipboard_autosync": + boolean clipboardAutosync = Boolean.parseBoolean(value); + options.setClipboardAutosync(clipboardAutosync); + break; + case "downsize_on_error": + boolean downsizeOnError = Boolean.parseBoolean(value); + options.setDownsizeOnError(downsizeOnError); + break; + case "cleanup": + boolean cleanup = Boolean.parseBoolean(value); + options.setCleanup(cleanup); + break; + case "power_on": + boolean powerOn = Boolean.parseBoolean(value); + options.setPowerOn(powerOn); + break; + case "list_encoders": + boolean listEncoders = Boolean.parseBoolean(value); + options.setListEncoders(listEncoders); + break; + case "list_displays": + boolean listDisplays = Boolean.parseBoolean(value); + options.setListDisplays(listDisplays); + break; + case "send_device_meta": + boolean sendDeviceMeta = Boolean.parseBoolean(value); + options.setSendDeviceMeta(sendDeviceMeta); + break; + case "send_frame_meta": + boolean sendFrameMeta = Boolean.parseBoolean(value); + options.setSendFrameMeta(sendFrameMeta); + break; + case "send_dummy_byte": + boolean sendDummyByte = Boolean.parseBoolean(value); + options.setSendDummyByte(sendDummyByte); + break; + case "send_codec_meta": + boolean sendCodecMeta = Boolean.parseBoolean(value); + options.setSendCodecMeta(sendCodecMeta); + break; + case "raw_video_stream": + boolean rawVideoStream = Boolean.parseBoolean(value); + if (rawVideoStream) { + options.setSendDeviceMeta(false); + options.setSendFrameMeta(false); + options.setSendDummyByte(false); + options.setSendCodecMeta(false); + } + break; + default: + Ln.w("Unknown server option: " + key); + break; + } + } + + return options; + } + + private static Rect parseCrop(String crop) { + if (crop.isEmpty()) { + return null; + } + // input format: "width:height:x:y" + String[] tokens = crop.split(":"); + if (tokens.length != 4) { + throw new IllegalArgumentException("Crop must contains 4 values separated by colons: \"" + crop + "\""); + } + int width = Integer.parseInt(tokens[0]); + int height = Integer.parseInt(tokens[1]); + int x = Integer.parseInt(tokens[2]); + int y = Integer.parseInt(tokens[3]); + return new Rect(x, y, x + width, y + height); + } } diff --git a/server/src/main/java/com/genymobile/scrcpy/Server.java b/server/src/main/java/com/genymobile/scrcpy/Server.java index 244913cf..067b1670 100644 --- a/server/src/main/java/com/genymobile/scrcpy/Server.java +++ b/server/src/main/java/com/genymobile/scrcpy/Server.java @@ -1,13 +1,11 @@ package com.genymobile.scrcpy; -import android.graphics.Rect; import android.os.BatteryManager; import android.os.Build; import java.io.IOException; import java.util.ArrayList; import java.util.List; -import java.util.Locale; public final class Server { @@ -161,203 +159,12 @@ public final class Server { return thread; } - @SuppressWarnings("MethodLength") - private static Options createOptions(String... args) { - if (args.length < 1) { - throw new IllegalArgumentException("Missing client version"); - } - - String clientVersion = args[0]; - if (!clientVersion.equals(BuildConfig.VERSION_NAME)) { - throw new IllegalArgumentException( - "The server version (" + BuildConfig.VERSION_NAME + ") does not match the client " + "(" + clientVersion + ")"); - } - - Options options = new Options(); - - for (int i = 1; i < args.length; ++i) { - String arg = args[i]; - int equalIndex = arg.indexOf('='); - if (equalIndex == -1) { - throw new IllegalArgumentException("Invalid key=value pair: \"" + arg + "\""); - } - String key = arg.substring(0, equalIndex); - String value = arg.substring(equalIndex + 1); - switch (key) { - case "scid": - int scid = Integer.parseInt(value, 0x10); - if (scid < -1) { - throw new IllegalArgumentException("scid may not be negative (except -1 for 'none'): " + scid); - } - options.setScid(scid); - break; - case "log_level": - Ln.Level level = Ln.Level.valueOf(value.toUpperCase(Locale.ENGLISH)); - options.setLogLevel(level); - break; - case "audio": - boolean audio = Boolean.parseBoolean(value); - options.setAudio(audio); - break; - case "video_codec": - VideoCodec videoCodec = VideoCodec.findByName(value); - if (videoCodec == null) { - throw new IllegalArgumentException("Video codec " + value + " not supported"); - } - options.setVideoCodec(videoCodec); - break; - case "audio_codec": - AudioCodec audioCodec = AudioCodec.findByName(value); - if (audioCodec == null) { - throw new IllegalArgumentException("Audio codec " + value + " not supported"); - } - options.setAudioCodec(audioCodec); - break; - case "max_size": - int maxSize = Integer.parseInt(value) & ~7; // multiple of 8 - options.setMaxSize(maxSize); - break; - case "video_bit_rate": - int videoBitRate = Integer.parseInt(value); - options.setVideoBitRate(videoBitRate); - break; - case "audio_bit_rate": - int audioBitRate = Integer.parseInt(value); - options.setAudioBitRate(audioBitRate); - break; - case "max_fps": - int maxFps = Integer.parseInt(value); - options.setMaxFps(maxFps); - break; - case "lock_video_orientation": - int lockVideoOrientation = Integer.parseInt(value); - options.setLockVideoOrientation(lockVideoOrientation); - break; - case "tunnel_forward": - boolean tunnelForward = Boolean.parseBoolean(value); - options.setTunnelForward(tunnelForward); - break; - case "crop": - Rect crop = parseCrop(value); - options.setCrop(crop); - break; - case "control": - boolean control = Boolean.parseBoolean(value); - options.setControl(control); - break; - case "display_id": - int displayId = Integer.parseInt(value); - options.setDisplayId(displayId); - break; - case "show_touches": - boolean showTouches = Boolean.parseBoolean(value); - options.setShowTouches(showTouches); - break; - case "stay_awake": - boolean stayAwake = Boolean.parseBoolean(value); - options.setStayAwake(stayAwake); - break; - case "video_codec_options": - List videoCodecOptions = CodecOption.parse(value); - options.setVideoCodecOptions(videoCodecOptions); - break; - case "audio_codec_options": - List audioCodecOptions = CodecOption.parse(value); - options.setAudioCodecOptions(audioCodecOptions); - break; - case "video_encoder": - if (!value.isEmpty()) { - options.setVideoEncoder(value); - } - break; - case "audio_encoder": - if (!value.isEmpty()) { - options.setAudioEncoder(value); - } - case "power_off_on_close": - boolean powerOffScreenOnClose = Boolean.parseBoolean(value); - options.setPowerOffScreenOnClose(powerOffScreenOnClose); - break; - case "clipboard_autosync": - boolean clipboardAutosync = Boolean.parseBoolean(value); - options.setClipboardAutosync(clipboardAutosync); - break; - case "downsize_on_error": - boolean downsizeOnError = Boolean.parseBoolean(value); - options.setDownsizeOnError(downsizeOnError); - break; - case "cleanup": - boolean cleanup = Boolean.parseBoolean(value); - options.setCleanup(cleanup); - break; - case "power_on": - boolean powerOn = Boolean.parseBoolean(value); - options.setPowerOn(powerOn); - break; - case "list_encoders": - boolean listEncoders = Boolean.parseBoolean(value); - options.setListEncoders(listEncoders); - break; - case "list_displays": - boolean listDisplays = Boolean.parseBoolean(value); - options.setListDisplays(listDisplays); - break; - case "send_device_meta": - boolean sendDeviceMeta = Boolean.parseBoolean(value); - options.setSendDeviceMeta(sendDeviceMeta); - break; - case "send_frame_meta": - boolean sendFrameMeta = Boolean.parseBoolean(value); - options.setSendFrameMeta(sendFrameMeta); - break; - case "send_dummy_byte": - boolean sendDummyByte = Boolean.parseBoolean(value); - options.setSendDummyByte(sendDummyByte); - break; - case "send_codec_meta": - boolean sendCodecMeta = Boolean.parseBoolean(value); - options.setSendCodecMeta(sendCodecMeta); - break; - case "raw_video_stream": - boolean rawVideoStream = Boolean.parseBoolean(value); - if (rawVideoStream) { - options.setSendDeviceMeta(false); - options.setSendFrameMeta(false); - options.setSendDummyByte(false); - options.setSendCodecMeta(false); - } - break; - default: - Ln.w("Unknown server option: " + key); - break; - } - } - - return options; - } - - private static Rect parseCrop(String crop) { - if (crop.isEmpty()) { - return null; - } - // input format: "width:height:x:y" - String[] tokens = crop.split(":"); - if (tokens.length != 4) { - throw new IllegalArgumentException("Crop must contains 4 values separated by colons: \"" + crop + "\""); - } - int width = Integer.parseInt(tokens[0]); - int height = Integer.parseInt(tokens[1]); - int x = Integer.parseInt(tokens[2]); - int y = Integer.parseInt(tokens[3]); - return new Rect(x, y, x + width, y + height); - } - public static void main(String... args) throws Exception { Thread.setDefaultUncaughtExceptionHandler((t, e) -> { Ln.e("Exception on thread " + t, e); }); - Options options = createOptions(args); + Options options = Options.parse(args); Ln.initLogLevel(options.getLogLevel());