diff --git a/README.md b/README.md index fa55b92f..8a55173d 100644 --- a/README.md +++ b/README.md @@ -9,7 +9,7 @@ and _MacOS_. ## Requirements -The Android part requires at least API 21 (Android 5.0). +The Android part requires at least API 19 (Android 4.4). You need [adb]. It is available in the [Android SDK platform tools][platform-tools], or packaged in your distribution (`android-adb-tools`). diff --git a/server/build.gradle b/server/build.gradle index 066fe52d..5fed22be 100644 --- a/server/build.gradle +++ b/server/build.gradle @@ -4,7 +4,7 @@ android { compileSdkVersion 27 defaultConfig { applicationId "com.genymobile.scrcpy" - minSdkVersion 21 + minSdkVersion 19 targetSdkVersion 27 versionCode 2 versionName "1.1" diff --git a/server/src/main/java/com/genymobile/scrcpy/ScreenEncoder.java b/server/src/main/java/com/genymobile/scrcpy/ScreenEncoder.java index 3014397c..01c87303 100644 --- a/server/src/main/java/com/genymobile/scrcpy/ScreenEncoder.java +++ b/server/src/main/java/com/genymobile/scrcpy/ScreenEncoder.java @@ -6,6 +6,7 @@ import android.graphics.Rect; import android.media.MediaCodec; import android.media.MediaCodecInfo; import android.media.MediaFormat; +import android.os.Build; import android.os.IBinder; import android.view.Surface; @@ -77,11 +78,17 @@ public class ScreenEncoder implements Device.RotationListener { } } + @SuppressWarnings("deprecation") // Android API 19 requires to call deprecated methods private boolean encode(MediaCodec codec, OutputStream outputStream) throws IOException { @SuppressWarnings("checkstyle:MagicNumber") byte[] buf = new byte[bitRate / 8]; // may contain up to 1 second of video boolean eof = false; MediaCodec.BufferInfo bufferInfo = new MediaCodec.BufferInfo(); + + ByteBuffer[] outputBuffers = null; + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { + outputBuffers = codec.getOutputBuffers(); + } while (!consumeRotationChange() && !eof) { int outputBufferId = codec.dequeueOutputBuffer(bufferInfo, -1); eof = (bufferInfo.flags & MediaCodec.BUFFER_FLAG_END_OF_STREAM) != 0; @@ -91,7 +98,12 @@ public class ScreenEncoder implements Device.RotationListener { break; } if (outputBufferId >= 0) { - ByteBuffer outputBuffer = codec.getOutputBuffer(outputBufferId); + ByteBuffer outputBuffer; + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + outputBuffer = codec.getOutputBuffer(outputBufferId); + } else { + outputBuffer = outputBuffers[outputBufferId]; + } while (outputBuffer.hasRemaining()) { int remaining = outputBuffer.remaining(); int len = Math.min(buf.length, remaining); @@ -100,6 +112,8 @@ public class ScreenEncoder implements Device.RotationListener { outputBuffer.get(buf, 0, len); outputStream.write(buf, 0, len); } + } else if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP && outputBufferId == MediaCodec.INFO_OUTPUT_BUFFERS_CHANGED) { + outputBuffers = codec.getOutputBuffers(); } } finally { if (outputBufferId >= 0) {