diff --git a/engine/src/flutter/shell/platform/android/android_surface_software.cc b/engine/src/flutter/shell/platform/android/android_surface_software.cc index 7d0a213590..ff823bbbb8 100644 --- a/engine/src/flutter/shell/platform/android/android_surface_software.cc +++ b/engine/src/flutter/shell/platform/android/android_surface_software.cc @@ -16,7 +16,26 @@ namespace shell { -AndroidSurfaceSoftware::AndroidSurfaceSoftware() : AndroidSurface() {} +namespace { + +bool GetSkColorType(int32_t buffer_format, SkColorType* color_type) { + switch (buffer_format) { + case WINDOW_FORMAT_RGB_565: + *color_type = kRGB_565_SkColorType; + return true; + case WINDOW_FORMAT_RGBA_8888: + *color_type = kRGBA_8888_SkColorType; + return true; + default: + return false; + } +} + +} // anonymous namespace + +AndroidSurfaceSoftware::AndroidSurfaceSoftware() + : AndroidSurface(), + target_color_type_(kRGBA_8888_SkColorType) {} AndroidSurfaceSoftware::~AndroidSurfaceSoftware() = default; @@ -56,8 +75,11 @@ sk_sp AndroidSurfaceSoftware::AcquireBackingStore( return sk_surface_; } - sk_surface_ = SkSurface::MakeRasterN32Premul( - size.fWidth, size.fHeight, nullptr /* SkSurfaceProps as out */); + SkImageInfo image_info = SkImageInfo::Make( + size.fWidth, size.fHeight, target_color_type_, kPremul_SkAlphaType); + + sk_surface_ = SkSurface::MakeRaster(image_info); + return sk_surface_; } @@ -73,24 +95,33 @@ bool AndroidSurfaceSoftware::PresentBackingStore( return false; } - // Some basic sanity checking. - uint64_t expected_pixmap_data_size = pixmap.width() * pixmap.height() * 4; - - if (expected_pixmap_data_size != pixmap.getSize64()) { + ANativeWindow_Buffer native_buffer; + if (ANativeWindow_lock(native_window_->handle(), &native_buffer, nullptr)) { return false; } - // Pass the sk_surface buffer to the android FlutterView. - JNIEnv* env = fml::jni::AttachCurrentThread(); + SkColorType color_type; + if (GetSkColorType(native_buffer.format, &color_type)) { + SkImageInfo native_image_info = SkImageInfo::Make( + native_buffer.width, native_buffer.height, color_type, kPremul_SkAlphaType); - // Buffer will be copied into a Bitmap Java-side. - fml::jni::ScopedJavaLocalRef direct_buffer( - env, - env->NewDirectByteBuffer(pixmap.writable_addr(), pixmap.getSize64())); + std::unique_ptr canvas = SkCanvas::MakeRasterDirect( + native_image_info, + native_buffer.bits, + native_buffer.stride * SkColorTypeBytesPerPixel(color_type)); - FlutterViewUpdateSoftwareBuffer(env, flutter_view_.get(env).obj(), - direct_buffer.obj(), pixmap.width(), - pixmap.height()); + if (canvas) { + SkBitmap bitmap; + if (bitmap.installPixels(pixmap)) { + canvas->drawBitmapRect( + bitmap, + SkRect::MakeIWH(native_buffer.width, native_buffer.height), + nullptr); + } + } + } + + ANativeWindow_unlockAndPost(native_window_->handle()); return true; } @@ -108,6 +139,14 @@ bool AndroidSurfaceSoftware::OnScreenSurfaceResize(const SkISize& size) const { bool AndroidSurfaceSoftware::SetNativeWindow( ftl::RefPtr window, PlatformView::SurfaceConfig config) { + native_window_ = std::move(window); + if (!(native_window_ && native_window_->IsValid())) + return false; + int32_t window_format = ANativeWindow_getFormat(native_window_->handle()); + if (window_format < 0) + return false; + if (!GetSkColorType(window_format, &target_color_type_)) + return false; return true; } diff --git a/engine/src/flutter/shell/platform/android/android_surface_software.h b/engine/src/flutter/shell/platform/android/android_surface_software.h index 0971e68a4a..8bc10bab9b 100644 --- a/engine/src/flutter/shell/platform/android/android_surface_software.h +++ b/engine/src/flutter/shell/platform/android/android_surface_software.h @@ -47,6 +47,9 @@ class AndroidSurfaceSoftware : public AndroidSurface, fml::jni::JavaObjectWeakGlobalRef flutter_view_; + ftl::RefPtr native_window_; + SkColorType target_color_type_; + FTL_DISALLOW_COPY_AND_ASSIGN(AndroidSurfaceSoftware); }; diff --git a/engine/src/flutter/shell/platform/android/io/flutter/view/FlutterView.java b/engine/src/flutter/shell/platform/android/io/flutter/view/FlutterView.java index 316ff53ec0..039eba3f95 100644 --- a/engine/src/flutter/shell/platform/android/io/flutter/view/FlutterView.java +++ b/engine/src/flutter/shell/platform/android/io/flutter/view/FlutterView.java @@ -204,18 +204,6 @@ public class FlutterView extends SurfaceView return super.onKeyDown(keyCode, event); } - // This method will be called on the GPU Thread. - public void updateSoftwareBuffer(ByteBuffer buffer, int width, int height) { - Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888); - bitmap.copyPixelsFromBuffer(buffer); - - Canvas canvas = getHolder().lockCanvas(); - if (canvas != null) { - canvas.drawBitmap(bitmap, new Matrix(), null); - getHolder().unlockCanvasAndPost(canvas); - } - } - public void addActivityLifecycleListener(ActivityLifecycleListener listener) { mActivityLifecycleListeners.add(listener); } diff --git a/engine/src/flutter/shell/platform/android/platform_view_android_jni.cc b/engine/src/flutter/shell/platform/android/platform_view_android_jni.cc index 270bbdf815..bb0c8c54db 100644 --- a/engine/src/flutter/shell/platform/android/platform_view_android_jni.cc +++ b/engine/src/flutter/shell/platform/android/platform_view_android_jni.cc @@ -49,17 +49,6 @@ void FlutterViewUpdateSemantics(JNIEnv* env, FTL_CHECK(env->ExceptionCheck() == JNI_FALSE); } -static jmethodID g_handle_platform_update_software_buffer = nullptr; -void FlutterViewUpdateSoftwareBuffer(JNIEnv* env, - jobject obj, - jobject buffer, - jint width, - jint height) { - env->CallVoidMethod(obj, g_handle_platform_update_software_buffer, buffer, - width, height); - FTL_CHECK(env->ExceptionCheck() == JNI_FALSE); -} - // Called By Java static jlong Attach(JNIEnv* env, jclass clazz, jobject flutterView) { @@ -350,13 +339,6 @@ bool PlatformViewAndroid::Register(JNIEnv* env) { return false; } - g_handle_platform_update_software_buffer = - env->GetMethodID(g_flutter_view_class->obj(), "updateSoftwareBuffer", - "(Ljava/nio/ByteBuffer;II)V"); - - if (g_handle_platform_update_software_buffer == nullptr) { - return false; - } return true; } diff --git a/engine/src/flutter/shell/platform/android/platform_view_android_jni.h b/engine/src/flutter/shell/platform/android/platform_view_android_jni.h index a4019a55f6..1bdfec3274 100644 --- a/engine/src/flutter/shell/platform/android/platform_view_android_jni.h +++ b/engine/src/flutter/shell/platform/android/platform_view_android_jni.h @@ -27,12 +27,6 @@ void FlutterViewUpdateSemantics(JNIEnv* env, jobject buffer, jobjectArray strings); -void FlutterViewUpdateSoftwareBuffer(JNIEnv* env, - jobject obj, - jobject buffer, - jint width, - jint height); - } // namespace shell #endif // FLUTTER_SHELL_PLATFORM_ANDROID_PLATFORM_VIEW_ANDROID_JNI_H_