Skip to content

Commit

Permalink
run cef window on linux (#66)
Browse files Browse the repository at this point in the history
Co-authored-by: zhixinyan <[email protected]>
  • Loading branch information
SinyimZhi and zhixinyan authored Jun 16, 2023
1 parent 1e07d24 commit 5398807
Show file tree
Hide file tree
Showing 283 changed files with 12,305 additions and 11,414 deletions.
3 changes: 3 additions & 0 deletions common/webview_app.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ class WebviewApp : public CefApp, public CefBrowserProcessHandler {
command_line->AppendSwitch("use-mock-keychain");
command_line->AppendSwitch("single-process");
#endif
#ifdef __linux__

#endif
}

// CefBrowserProcessHandler methods:
Expand Down
204 changes: 204 additions & 0 deletions common/webview_plugin.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,204 @@
#include "webview_plugin.h"

#include "webview_app.h"

#include <math.h>
#include <memory>
#include <thread>
#include <iostream>
#include <mutex>

namespace webview_cef {
bool init = false;
int64_t texture_id;
// std::unique_ptr<uint8_t> backing_pixel_buffer;
// std::mutex buffer_mutex_;

CefRefPtr<WebviewHandler> handler(new WebviewHandler());
CefRefPtr<WebviewApp> app(new WebviewApp(handler));
CefMainArgs mainArgs;

// void SwapBufferFromBgraToRgba(void* _dest, const void* _src, int width, int height) {
// int32_t* dest = (int32_t*)_dest;
// int32_t* src = (int32_t*)_src;
// int32_t rgba;
// int32_t bgra;
// int length = width * height;
// for (int i = 0; i < length; i++) {
// bgra = src[i];
// // BGRA in hex = 0xAARRGGBB.
// rgba = (bgra & 0x00ff0000) >> 16 // Red >> Blue.
// | (bgra & 0xff00ff00) // Green Alpha.
// | (bgra & 0x000000ff) << 16; // Blue >> Red.
// dest[i] = rgba;
// }
// }

// template <typename T>
// std::optional<T> GetOptionalValue(const flutter::EncodableMap& map,
// const std::string& key) {
// const auto it = map.find(flutter::EncodableValue(key));
// if (it != map.end()) {
// const auto val = std::get_if<T>(&it->second);
// if (val) {
// return *val;
// }
// }
// return std::nullopt;
// }

static const std::optional<std::pair<int, int>> GetPointFromArgs(
const PluginValue *args) {
const PluginValueList* list = std::get_if<PluginValueList>(args);
if (!list || list->size() != 2) {
return std::nullopt;
}
const auto x = std::get_if<int64_t>(&(*list)[0]);
const auto y = std::get_if<int64_t>(&(*list)[1]);
if (!x || !y) {
return std::nullopt;
}
return std::make_pair(*x, *y);
}

void initCEFProcesses(CefMainArgs args){
mainArgs = args;
CefExecuteProcess(mainArgs, app, nullptr);
}

void sendKeyEvent(CefKeyEvent ev)
{
handler.get()->sendKeyEvent(ev);
}

void startCEF() {
CefWindowInfo window_info;
CefBrowserSettings settings;
window_info.SetAsWindowless(0);

// handler.get()->onPaintCallback = [](const void* buffer, int32_t width, int32_t height) {
// const std::lock_guard<std::mutex> lock(buffer_mutex_);
// if (!pixel_buffer.get() || pixel_buffer.get()->width != width || pixel_buffer.get()->height != height) {
// if (!pixel_buffer.get()) {
// pixel_buffer = std::make_unique<FlutterDesktopPixelBuffer>();
// pixel_buffer->release_context = &buffer_mutex_;
// // Gets invoked after the FlutterDesktopPixelBuffer's
// // backing buffer has been uploaded.
// pixel_buffer->release_callback = [](void* opaque) {
// auto mutex = reinterpret_cast<std::mutex*>(opaque);
// // Gets locked just before |CopyPixelBuffer| returns.
// mutex->unlock();
// };
// }
// pixel_buffer->width = width;
// pixel_buffer->height = height;
// const auto size = width * height * 4;
// backing_pixel_buffer.reset(new uint8_t[size]);
// pixel_buffer->buffer = backing_pixel_buffer.get();
// }

// SwapBufferFromBgraToRgba((void*)pixel_buffer->buffer, buffer, width, height);
// texture_registrar->MarkTextureFrameAvailable(texture_id);
// };

// handler.get()->onUrlChangedCb = [](std::string url) {
// channel->InvokeMethod("urlChanged", std::make_unique<flutter::EncodableValue>(url));
// };

// handler.get()->onTitleChangedCb = [](std::string title) {
// channel->InvokeMethod("titleChanged", std::make_unique<flutter::EncodableValue>(title));
// };

CefSettings cefs;
cefs.windowless_rendering_enabled = true;
cefs.no_sandbox = true;
CefInitialize(mainArgs, cefs, app.get(), nullptr);
CefRunMessageLoop();
CefShutdown();
}

int HandleMethodCall(std::string name, PluginValue* values, PluginValue* response) {
int result = -1;
if(name.compare("init") == 0)
{
if(!init)
{
response = new PluginValue(texture_id);
new std::thread(startCEF);
init = true;
result = 1;
}
}
else if (name.compare("loadUrl") == 0) {
if (const auto url = std::get_if<std::string>(values)) {
handler.get()->loadUrl(*url);
result = 1;
}
}
else if (name.compare("setSize") == 0) {
const PluginValueList* list = std::get_if<PluginValueList>(values);
const auto dpi = *std::get_if<double>(&(*list)[0]);
const auto width = *std::get_if<double>(&(*list)[1]);
const auto height = *std::get_if<double>(&(*list)[2]);
handler.get()->changeSize((float)dpi, (int)std::round(width), (int)std::round(height));
result = 1;
}
else if (name.compare("cursorClickDown") == 0) {
const auto point = GetPointFromArgs(values);
handler.get()->cursorClick(point->first, point->second, false);
result = 1;
}
else if (name.compare("cursorClickUp") == 0) {
const auto point = GetPointFromArgs(values);
handler.get()->cursorClick(point->first, point->second, true);
result = 1;
}
else if (name.compare("cursorMove") == 0) {
const auto point = GetPointFromArgs(values);
handler.get()->cursorMove(point->first, point->second, false);
result = 1;
}
else if (name.compare("cursorDragging") == 0) {
const auto point = GetPointFromArgs(values);
handler.get()->cursorMove(point->first, point->second, true);
result = 1;
}
else if (name.compare("setScrollDelta") == 0) {
const PluginValueList* list = std::get_if<PluginValueList>(values);
const auto x = *std::get_if<int64_t>(&(*list)[0]);
const auto y = *std::get_if<int64_t>(&(*list)[1]);
const auto deltaX = *std::get_if<int64_t>(&(*list)[2]);
const auto deltaY = *std::get_if<int64_t>(&(*list)[3]);
handler.get()->sendScrollEvent(x, y, deltaX, deltaY);
result = 1;
}
else if (name.compare("goForward") == 0) {
handler.get()->goForward();
result = 1;
}
else if (name.compare("goBack") == 0) {
handler.get()->goBack();
result = 1;
}
else if (name.compare("reload") == 0) {
handler.get()->reload();
result = 1;
}
else if (name.compare("openDevTools") == 0) {
handler.get()->openDevTools();
result = 1;
}
else {
result = 0;
}
if(response == nullptr){
response = new PluginValue(nullptr);
}
return result;
}

void setTextureId(int textureId)
{
texture_id = textureId;
}
}
74 changes: 74 additions & 0 deletions common/webview_plugin.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
#ifndef WEBVIEW_PLUGIN_H
#define WEBVIEW_PLUGIN_H

// #include <functional>

#include <any>
#include <cassert>
#include <cstdint>
#include <map>
#include <string>
#include <utility>
#include <variant>
#include <vector>
#include <../third/cef/include/internal/cef_types_wrappers.h>
#include <../third/cef/include/internal/cef_linux.h>

namespace webview_cef {

class PluginValue;

using PluginValueList = std::vector<PluginValue>;
using PluginValueMap = std::map<PluginValue,PluginValue>;
using PluginValueVariant = std::variant<std::monostate,
bool,
int32_t,
int64_t,
double,
std::string,
std::vector<uint8_t>,
std::vector<int32_t>,
std::vector<int64_t>,
std::vector<float>,
std::vector<double>,
PluginValueList,
PluginValueMap>;

class PluginValue: public PluginValueVariant
{
public:
using super = PluginValueVariant;
using super::super;
using super::operator=;

explicit PluginValue() = default;

explicit PluginValue(const char* str) : super(std::string(str)) {}
PluginValue& operator=(const char* other) {
*this = std::string(other);
return *this;
}

template <class T>
constexpr explicit PluginValue(T&& t) noexcept : super(t) {}

bool IsNull() const { return std::holds_alternative<std::monostate>(*this); }

int64_t LongValue() const {
if(std::holds_alternative<int32_t>(*this)){
return std::get<int32_t>(*this);
}
return std::get<int64_t>(*this);
}

};


void initCEFProcesses(CefMainArgs args);
void sendKeyEvent(CefKeyEvent ev);
int HandleMethodCall(std::string name, PluginValue* values, PluginValue* response);
void setTextureId(int textureId);

}

#endif //WEBVIEW_PLUGIN_H
2 changes: 1 addition & 1 deletion example/linux/main.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
#include <webview_cef/webview_cef_plugin.h>

int main(int argc, char** argv) {
startCef();
initCEFProcesses(argc, argv);
g_autoptr(MyApplication) app = my_application_new();
return g_application_run(G_APPLICATION(app), argc, argv);
}
3 changes: 1 addition & 2 deletions linux/.gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -17,5 +17,4 @@ x86/
!*.[Cc]ache/

cmake-build-debug
prebuilt.zip
third/cef/bins
prebuilt.zip
5 changes: 4 additions & 1 deletion linux/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ cmake_minimum_required(VERSION 3.10)
set(PROJECT_NAME "webview_cef")
project(${PROJECT_NAME} LANGUAGES CXX C)

set(CEF_ROOT "${CMAKE_CURRENT_SOURCE_DIR}/third/cef")
set(CEF_ROOT "${CMAKE_CURRENT_SOURCE_DIR}/../third/cef")
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CEF_ROOT}/cmake")
find_package(CEF REQUIRED)

Expand All @@ -21,10 +21,13 @@ set(PLUGIN_NAME "webview_cef_plugin")
# Any new source files that you add to the plugin should be added here.
add_library(${PLUGIN_NAME} SHARED
"webview_cef_plugin.cc"
"webview_cef_texture.h"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_app.cc"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_app.h"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_handler.cc"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_handler.h"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_plugin.cc"
"${CMAKE_CURRENT_SOURCE_DIR}/../common/webview_plugin.h"
)

# Apply a standard set of build settings that are configured in the
Expand Down
4 changes: 1 addition & 3 deletions linux/include/webview_cef/webview_cef_plugin.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,6 @@

#include <flutter_linux/flutter_linux.h>

#include "webview_app.h"

G_BEGIN_DECLS

#ifdef FLUTTER_PLUGIN_IMPL
Expand All @@ -25,6 +23,6 @@ FLUTTER_PLUGIN_EXPORT void webview_cef_plugin_register_with_registrar(

G_END_DECLS

FLUTTER_PLUGIN_EXPORT void startCef();
FLUTTER_PLUGIN_EXPORT void initCEFProcesses(int argc, char** argv);

#endif // FLUTTER_PLUGIN_WEBVIEW_CEF_PLUGIN_H_
Loading

0 comments on commit 5398807

Please sign in to comment.