diff --git a/flutter_inappwebview/pubspec.yaml b/flutter_inappwebview/pubspec.yaml index 21ef16a2f4..e3eb4b406d 100755 --- a/flutter_inappwebview/pubspec.yaml +++ b/flutter_inappwebview/pubspec.yaml @@ -32,8 +32,11 @@ dependencies: # path: ../flutter_inappwebview_web flutter_inappwebview_windows: ^0.7.0-beta.3 # path: ../flutter_inappwebview_windows - flutter_inappwebview_linux: ^0.1.0-beta.1 - # path: ../flutter_inappwebview_linux + # flutter_inappwebview_linux: ^0.1.0-beta.1 + flutter_inappwebview_linux: + git: + url: https://github.com/MSOB7YY/flutter_inappwebview + path: flutter_inappwebview_linux dev_dependencies: flutter_test: diff --git a/flutter_inappwebview_linux/linux/CMakeLists.txt b/flutter_inappwebview_linux/linux/CMakeLists.txt index 27f9334810..c50eeaae5e 100644 --- a/flutter_inappwebview_linux/linux/CMakeLists.txt +++ b/flutter_inappwebview_linux/linux/CMakeLists.txt @@ -17,6 +17,95 @@ set(CMAKE_CXX_STANDARD_REQUIRED ON) # nlohmann/json version for JSON parsing set(NLOHMANN_JSON_VERSION "3.11.3") +set(WPE_BUNDLE_ENABLED ON) +if(DISABLE_WPE_WEBKIT OR (DEFINED ENV{DISABLE_WPE_WEBKIT} AND "$ENV{DISABLE_WPE_WEBKIT}" STREQUAL "1")) + set(WPE_BUNDLE_ENABLED OFF) +endif() + + +# Plugin source files +list(APPEND PLUGIN_SOURCES + "flutter_inappwebview_linux_plugin.cc" + "plugin_instance.cc" + "cookie_manager.cc" + "credential_database.cc" + "proxy_manager.cc" + "utils/software_rendering.cc" + "web_storage_manager.cc" + "webview_environment.cc" + "content_blocker/content_blocker_handler.cc" + "find_interaction/find_interaction_controller.cc" + "find_interaction/find_interaction_channel_delegate.cc" + "headless_in_app_webview/headless_in_app_webview.cc" + "headless_in_app_webview/headless_in_app_webview_manager.cc" + "headless_in_app_webview/headless_webview_channel_delegate.cc" + "in_app_browser/in_app_browser.cc" + "in_app_browser/in_app_browser_channel_delegate.cc" + "in_app_browser/in_app_browser_manager.cc" + "in_app_browser/in_app_browser_settings.cc" + "in_app_webview/in_app_webview_manager.cc" + "in_app_webview/custom_platform_view.cc" + "in_app_webview/inappwebview_texture.cc" + "in_app_webview/inappwebview_egl_texture.cc" + "in_app_webview/in_app_webview.cc" + "in_app_webview/in_app_webview_settings.cc" + "in_app_webview/user_content_controller.cc" + "in_app_webview/webview_channel_delegate.cc" + "types/channel_delegate.cc" + "types/client_cert_challenge.cc" + "types/client_cert_response.cc" + "types/content_world.cc" + "types/context_menu_popup.cc" + "types/create_window_action.cc" + "types/custom_scheme_response.cc" + "types/download_start_request.cc" + "types/download_start_response.cc" + "types/find_session.cc" + "types/http_auth_response.cc" + "types/http_authentication_challenge.cc" + "types/javascript_handler_function_data.cc" + "types/js_alert_request.cc" + "types/js_alert_response.cc" + "types/js_before_unload_response.cc" + "types/js_confirm_request.cc" + "types/js_confirm_response.cc" + "types/js_prompt_request.cc" + "types/js_prompt_response.cc" + "types/hit_test_result.cc" + "types/navigation_action.cc" + "types/option_menu_popup.cc" + "types/permission_request.cc" + "types/permission_response.cc" + "types/plugin_script.cc" + "types/server_trust_auth_response.cc" + "types/server_trust_challenge.cc" + "types/show_file_chooser_response.cc" + "types/ssl_certificate.cc" + "types/url_credential.cc" + "types/url_protection_space.cc" + "types/url_request.cc" + "types/user_script.cc" + "types/web_resource_error.cc" + "types/web_resource_request.cc" + "types/web_resource_response.cc" + "types/web_view_transport.cc" + "web_message/web_message_channel.cc" + "web_message/web_message_listener.cc" + "web_message/web_message_listener_channel_delegate.cc" +) + +if(NOT WPE_BUNDLE_ENABLED) + file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/stub.cc" " + extern \"C\" __attribute__((visibility(\"default\"))) + void flutter_inappwebview_linux_plugin_register_with_registrar(void* registrar) {} + ") + add_library(${PLUGIN_NAME} SHARED "${CMAKE_CURRENT_BINARY_DIR}/stub.cc") + target_compile_options(${PLUGIN_NAME} PRIVATE -fvisibility=default) + target_include_directories(${PLUGIN_NAME} INTERFACE "${CMAKE_CURRENT_SOURCE_DIR}/include") + set(flutter_inappwebview_linux_bundled_libraries "" PARENT_SCOPE) + return() +endif() + # === WPE WebKit Backend === # This plugin uses WPE WebKit for offscreen web rendering. # WPE WebKit is designed for embedded systems and provides excellent offscreen @@ -167,77 +256,6 @@ FetchContent_MakeAvailable(nlohmann_json) set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-deprecated-literal-operator") message(STATUS "flutter_inappwebview_linux: nlohmann/json ${NLOHMANN_JSON_VERSION} configured") -# Plugin source files -list(APPEND PLUGIN_SOURCES - "flutter_inappwebview_linux_plugin.cc" - "plugin_instance.cc" - "cookie_manager.cc" - "credential_database.cc" - "proxy_manager.cc" - "utils/software_rendering.cc" - "web_storage_manager.cc" - "webview_environment.cc" - "content_blocker/content_blocker_handler.cc" - "find_interaction/find_interaction_controller.cc" - "find_interaction/find_interaction_channel_delegate.cc" - "headless_in_app_webview/headless_in_app_webview.cc" - "headless_in_app_webview/headless_in_app_webview_manager.cc" - "headless_in_app_webview/headless_webview_channel_delegate.cc" - "in_app_browser/in_app_browser.cc" - "in_app_browser/in_app_browser_channel_delegate.cc" - "in_app_browser/in_app_browser_manager.cc" - "in_app_browser/in_app_browser_settings.cc" - "in_app_webview/in_app_webview_manager.cc" - "in_app_webview/custom_platform_view.cc" - "in_app_webview/inappwebview_texture.cc" - "in_app_webview/inappwebview_egl_texture.cc" - "in_app_webview/in_app_webview.cc" - "in_app_webview/in_app_webview_settings.cc" - "in_app_webview/user_content_controller.cc" - "in_app_webview/webview_channel_delegate.cc" - "types/channel_delegate.cc" - "types/client_cert_challenge.cc" - "types/client_cert_response.cc" - "types/content_world.cc" - "types/context_menu_popup.cc" - "types/create_window_action.cc" - "types/custom_scheme_response.cc" - "types/download_start_request.cc" - "types/download_start_response.cc" - "types/find_session.cc" - "types/http_auth_response.cc" - "types/http_authentication_challenge.cc" - "types/javascript_handler_function_data.cc" - "types/js_alert_request.cc" - "types/js_alert_response.cc" - "types/js_before_unload_response.cc" - "types/js_confirm_request.cc" - "types/js_confirm_response.cc" - "types/js_prompt_request.cc" - "types/js_prompt_response.cc" - "types/hit_test_result.cc" - "types/navigation_action.cc" - "types/option_menu_popup.cc" - "types/permission_request.cc" - "types/permission_response.cc" - "types/plugin_script.cc" - "types/server_trust_auth_response.cc" - "types/server_trust_challenge.cc" - "types/show_file_chooser_response.cc" - "types/ssl_certificate.cc" - "types/url_credential.cc" - "types/url_protection_space.cc" - "types/url_request.cc" - "types/user_script.cc" - "types/web_resource_error.cc" - "types/web_resource_request.cc" - "types/web_resource_response.cc" - "types/web_view_transport.cc" - "web_message/web_message_channel.cc" - "web_message/web_message_listener.cc" - "web_message/web_message_listener_channel_delegate.cc" -) - # Define the plugin library target. Its name must not be changed (see comment # on PLUGIN_NAME above). add_library(${PLUGIN_NAME} SHARED @@ -357,6 +375,15 @@ if(HAVE_WPE_FDO) find_and_add_library("libWPEBackend-fdo-1.0" "${WPE_LIB_DIRS}" WPE_BUNDLED_LIBS) endif() +# Bundle WPEWebKit subprocess binaries +file(GLOB_RECURSE WPE_EXEC_FILES "/usr/lib/wpe-webkit-2.0/*") +foreach(WPE_FILE ${WPE_EXEC_FILES}) + if(NOT IS_SYMLINK "${WPE_FILE}") + list(APPEND WPE_BUNDLED_LIBS "${WPE_FILE}") + message(STATUS "flutter_inappwebview_linux: Will bundle ${WPE_FILE}") + endif() +endforeach() + # Also need to create symlinks for the sonames that the libraries expect # This will be handled at install time in the example CMakeLists.txt @@ -368,6 +395,65 @@ set(flutter_inappwebview_linux_bundled_libraries # Export library info for downstream use set(FLUTTER_INAPPWEBVIEW_WPE_LIBS ${WPE_BUNDLED_LIBS} CACHE INTERNAL "WPE libraries to bundle") + +# === WPE Library Symlink Creation === +# Create the necessary soname symlinks so the WPE libraries can find each other at runtime +install(CODE " + # Create symlinks for WPE libraries in the lib directory + set(LIB_DIR \"\${CMAKE_INSTALL_PREFIX}/lib\") + + # Function to create soname symlinks for a library + macro(create_lib_symlinks LIB_PATTERN SONAME_BASE) + file(GLOB LIB_FILES \"\${LIB_DIR}/\${LIB_PATTERN}\") + if(LIB_FILES) + list(GET LIB_FILES 0 REAL_LIB) + get_filename_component(REAL_LIB_NAME \"\${REAL_LIB}\" NAME) + + # Create .so.X symlink (e.g., libwpe-1.0.so.1 -> libwpe-1.0.so.1.10.0) + set(SONAME_LINK \"\${LIB_DIR}/\${SONAME_BASE}.so.1\") + if(NOT EXISTS \"\${SONAME_LINK}\") + execute_process(COMMAND \${CMAKE_COMMAND} -E create_symlink + \"\${REAL_LIB_NAME}\" \"\${SONAME_LINK}\") + message(STATUS \"Created symlink: \${SONAME_LINK} -> \${REAL_LIB_NAME}\") + endif() + + # Create .so symlink (e.g., libwpe-1.0.so -> libwpe-1.0.so.1) + set(SO_LINK \"\${LIB_DIR}/\${SONAME_BASE}.so\") + if(NOT EXISTS \"\${SO_LINK}\") + execute_process(COMMAND \${CMAKE_COMMAND} -E create_symlink + \"\${SONAME_BASE}.so.1\" \"\${SO_LINK}\") + message(STATUS \"Created symlink: \${SO_LINK} -> \${SONAME_BASE}.so.1\") + endif() + endif() + endmacro() + + # Create symlinks for each WPE library + create_lib_symlinks(\"libWPEWebKit-2.0.so.*.*.*\" \"libWPEWebKit-2.0\") + create_lib_symlinks(\"libwpe-1.0.so.*.*.*\" \"libwpe-1.0\") + create_lib_symlinks(\"libWPEBackend-fdo-1.0.so.*.*.*\" \"libWPEBackend-fdo-1.0\") + + # Create the default backend symlink that WPE expects + set(DEFAULT_BACKEND_LINK \"\${LIB_DIR}/libWPEBackend-default.so\") + if(NOT EXISTS \"\${DEFAULT_BACKEND_LINK}\") + execute_process(COMMAND \${CMAKE_COMMAND} -E create_symlink + \"libWPEBackend-fdo-1.0.so.1\" \"\${DEFAULT_BACKEND_LINK}\") + message(STATUS \"Created symlink: \${DEFAULT_BACKEND_LINK} -> libWPEBackend-fdo-1.0.so.1\") + endif() + " COMPONENT Runtime) + +# === Try fixing rpath in so === +install(CODE " + file(GLOB_RECURSE ALL_BUNDLED \"\${CMAKE_INSTALL_PREFIX}/lib/*\") + foreach(F \${ALL_BUNDLED}) + if(NOT IS_SYMLINK \"\${F}\") + execute_process(COMMAND patchelf --set-rpath \"\$ORIGIN\" + \"\${F}\" + ERROR_QUIET) + endif() + endforeach() + message(STATUS \"Patched RPATH for all bundled files\") +") + # === Tests === # These unit tests can be run from a terminal after building the example. diff --git a/flutter_inappwebview_platform_interface/lib/src/util.dart b/flutter_inappwebview_platform_interface/lib/src/util.dart index d7f5e3b0ee..45ff36bd29 100644 --- a/flutter_inappwebview_platform_interface/lib/src/util.dart +++ b/flutter_inappwebview_platform_interface/lib/src/util.dart @@ -656,7 +656,7 @@ extension InternalChannelController on ChannelController { disposeChannel({bool removeMethodCallHandler = true}) { if (removeMethodCallHandler) { - channel?.setMethodCallHandler(null); + this._channel?.setMethodCallHandler(null); } channel = null; handler = null;