提交 9b108f11 编写于 作者: A Adam Barth

SkyShell should be able to draw a green square with GL

This CL teaches SkyShell how to initialize GL and draw a green square.

R=eseidel@google.com, eseidel@chromium.org

Review URL: https://codereview.chromium.org/890803004
上级 08c612bd
......@@ -16,17 +16,26 @@ group("shell") {
generate_jni("jni_headers") {
sources = [
"apk/src/org/domokit/sky/shell/SkyMain.java",
"apk/src/org/domokit/sky/shell/SkyView.java",
]
jni_package = "sky/shell"
}
shared_library("sky_shell") {
sources = [
"gpu_driver.cc",
"gpu_driver.h",
"library_loader.cc",
"shell.cc",
"shell.h",
"sky_main.cc",
"sky_main.h",
"sky_view.cc",
"sky_view.h",
]
configs += [ "//third_party/khronos:khronos_headers" ]
deps = [
"//base",
"//build/config/sanitizers:deps",
......@@ -40,6 +49,7 @@ android_library("java") {
"apk/src/org/domokit/sky/shell/SkyMain.java",
"apk/src/org/domokit/sky/shell/SkyShellActivity.java",
"apk/src/org/domokit/sky/shell/SkyShellApplication.java",
"apk/src/org/domokit/sky/shell/SkyView.java",
]
deps = [
......
// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package org.domokit.sky.shell;
import android.app.Activity;
import android.content.Context;
import android.view.Surface;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import org.chromium.base.CalledByNative;
import org.chromium.base.JNINamespace;
/**
* A view containing Sky
*/
@JNINamespace("sky::shell")
public class SkyView extends SurfaceView {
private long mNativeSkyView;
private final SurfaceHolder.Callback mSurfaceCallback;
@SuppressWarnings("unused")
@CalledByNative
public static void createForActivity(Activity activity, long nativeSkyView) {
activity.setContentView(new SkyView(activity, nativeSkyView));
}
public SkyView(Context context, long nativeSkyView) {
super(context);
setFocusable(true);
setFocusableInTouchMode(true);
mNativeSkyView = nativeSkyView;
assert mNativeSkyView != 0;
final float density = context.getResources().getDisplayMetrics().density;
mSurfaceCallback = new SurfaceHolder.Callback() {
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
assert mNativeSkyView != 0;
nativeSurfaceSetSize(mNativeSkyView, width, height, density);
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
assert mNativeSkyView != 0;
nativeSurfaceCreated(mNativeSkyView, holder.getSurface());
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
assert mNativeSkyView != 0;
nativeSurfaceDestroyed(mNativeSkyView);
}
};
getHolder().addCallback(mSurfaceCallback);
}
public void destroy() {
getHolder().removeCallback(mSurfaceCallback);
nativeDestroy(mNativeSkyView);
mNativeSkyView = 0;
}
@Override
protected void onWindowVisibilityChanged(int visibility) {
super.onWindowVisibilityChanged(visibility);
if (visibility == View.VISIBLE) {
requestFocusFromTouch();
requestFocus();
}
}
private static native void nativeDestroy(long nativeSkyView);
private static native void nativeSurfaceCreated(long nativeSkyView, Surface surface);
private static native void nativeSurfaceDestroyed(long nativeSkyView);
private static native void nativeSurfaceSetSize(
long nativeSkyView, int width, int height, float density);
}
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "sky/shell/gpu_driver.h"
#include "ui/gl/gl_bindings.h"
#include "ui/gl/gl_context.h"
#include "ui/gl/gl_share_group.h"
#include "ui/gl/gl_surface.h"
namespace sky {
namespace shell {
GPUDriver::GPUDriver() : weak_factory_(this) {
}
GPUDriver::~GPUDriver() {
}
base::WeakPtr<GPUDriver> GPUDriver::GetWeakPtr() {
return weak_factory_.GetWeakPtr();
}
void GPUDriver::Init(gfx::AcceleratedWidget widget) {
share_group_ = make_scoped_refptr(new gfx::GLShareGroup());
surface_ = gfx::GLSurface::CreateViewGLSurface(widget);
CHECK(surface_) << "GLSurface required.";
context_ = gfx::GLContext::CreateGLContext(share_group_.get(), surface_.get(),
gfx::PreferIntegratedGpu);
CHECK(context_) << "GLContext required.";
CHECK(context_->MakeCurrent(surface_.get()));
glClearColor(0.0, 1.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT);
surface_->SwapBuffers();
}
} // namespace shell
} // namespace sky
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SKY_SHELL_GPU_DRIVER_H_
#define SKY_SHELL_GPU_DRIVER_H_
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
class GLContext;
class GLShareGroup;
class GLSurface;
}
namespace sky {
namespace shell {
class GPUDriver {
public:
explicit GPUDriver();
~GPUDriver();
base::WeakPtr<GPUDriver> GetWeakPtr();
void Init(gfx::AcceleratedWidget widget);
private:
scoped_refptr<gfx::GLShareGroup> share_group_;
scoped_refptr<gfx::GLSurface> surface_;
scoped_refptr<gfx::GLContext> context_;
base::WeakPtrFactory<GPUDriver> weak_factory_;
DISALLOW_COPY_AND_ASSIGN(GPUDriver);
};
} // namespace shell
} // namespace sky
#endif // SKY_SHELL_GPU_DRIVER_H_
......@@ -8,11 +8,13 @@
#include "base/android/library_loader/library_loader_hooks.h"
#include "base/logging.h"
#include "sky/shell/sky_main.h"
#include "sky/shell/sky_view.h"
namespace {
base::android::RegistrationMethod kSkyRegisteredMethods[] = {
{"SkyMain", sky::shell::RegisterSkyMain},
{"SkyView", sky::shell::SkyView::Register},
};
bool RegisterMojoJni(JNIEnv* env) {
......
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "sky/shell/shell.h"
#include "base/bind.h"
#include "base/single_thread_task_runner.h"
#include "base/threading/thread.h"
#include "sky/shell/sky_view.h"
namespace sky {
namespace shell {
Shell::Shell(scoped_refptr<base::SingleThreadTaskRunner> java_task_runner)
: java_task_runner_(java_task_runner) {
}
Shell::~Shell() {
}
void Shell::Init() {
gpu_thread_.reset(new base::Thread("gpu_thread"));
gpu_thread_->Start();
gpu_driver_.reset(new GPUDriver());
view_.reset(new SkyView(this));
view_->Init();
}
void Shell::OnAcceleratedWidgetAvailable(gfx::AcceleratedWidget widget) {
gpu_thread_->message_loop()->PostTask(
FROM_HERE,
base::Bind(&GPUDriver::Init, gpu_driver_->GetWeakPtr(), widget));
}
void Shell::OnDestroyed() {
}
} // namespace shell
} // namespace sky
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SKY_SHELL_SHELL_H_
#define SKY_SHELL_SHELL_H_
#include "base/macros.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "sky/shell/gpu_driver.h"
#include "sky/shell/sky_view.h"
namespace base {
class Thread;
class SingleThreadTaskRunner;
}
namespace sky {
namespace shell {
class SkyView;
class Shell : public SkyView::Delegate {
public:
explicit Shell(scoped_refptr<base::SingleThreadTaskRunner> java_task_runner);
~Shell();
void Init();
private:
void OnAcceleratedWidgetAvailable(gfx::AcceleratedWidget widget) override;
void OnDestroyed() override;
scoped_refptr<base::SingleThreadTaskRunner> java_task_runner_;
scoped_ptr<base::Thread> gpu_thread_;
scoped_ptr<SkyView> view_;
scoped_ptr<GPUDriver> gpu_driver_;
DISALLOW_COPY_AND_ASSIGN(Shell);
};
} // namespace shell
} // namespace sky
#endif // SKY_SHELL_SHELL_H_
......@@ -17,6 +17,8 @@
#include "base/run_loop.h"
#include "base/threading/simple_thread.h"
#include "jni/SkyMain_jni.h"
#include "sky/shell/shell.h"
#include "ui/gl/gl_surface_egl.h"
using base::LazyInstance;
......@@ -31,6 +33,8 @@ LazyInstance<scoped_ptr<base::MessageLoop>> g_java_message_loop =
LazyInstance<base::android::ScopedJavaGlobalRef<jobject>> g_main_activiy =
LAZY_INSTANCE_INITIALIZER;
LazyInstance<scoped_ptr<Shell>> g_shell = LAZY_INSTANCE_INITIALIZER;
void InitializeLogging() {
logging::LoggingSettings settings;
settings.logging_dest = logging::LOG_TO_SYSTEM_DEBUG_LOG;
......@@ -58,6 +62,14 @@ static void Init(JNIEnv* env,
g_java_message_loop.Get().reset(new base::MessageLoopForUI);
base::MessageLoopForUI::current()->Start();
gfx::GLSurface::InitializeOneOff();
g_shell.Get().reset(new Shell(g_java_message_loop.Get()->task_runner()));
g_java_message_loop.Get()->PostTask(
FROM_HERE,
base::Bind(&Shell::Init, base::Unretained(g_shell.Get().get())));
}
static jboolean Start(JNIEnv* env, jclass clazz) {
......
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "sky/shell/sky_view.h"
#include <android/input.h>
#include <android/native_window_jni.h>
#include "base/android/jni_android.h"
#include "jni/SkyView_jni.h"
namespace sky {
namespace shell {
// static
bool SkyView::Register(JNIEnv* env) {
return RegisterNativesImpl(env);
}
SkyView::Delegate::~Delegate() {
}
SkyView::SkyView(Delegate* delegate) : delegate_(delegate), window_(NULL) {
}
SkyView::~SkyView() {
if (window_)
ReleaseWindow();
}
void SkyView::Init() {
JNIEnv* env = base::android::AttachCurrentThread();
Java_SkyView_createForActivity(env, base::android::GetApplicationContext(),
reinterpret_cast<jlong>(this));
}
void SkyView::Destroy(JNIEnv* env, jobject obj) {
delegate_->OnDestroyed();
}
void SkyView::SurfaceCreated(JNIEnv* env, jobject obj, jobject jsurface) {
base::android::ScopedJavaLocalRef<jobject> protector(env, jsurface);
// Note: This ensures that any local references used by
// ANativeWindow_fromSurface are released immediately. This is needed as a
// workaround for https://code.google.com/p/android/issues/detail?id=68174
{
base::android::ScopedJavaLocalFrame scoped_local_reference_frame(env);
window_ = ANativeWindow_fromSurface(env, jsurface);
}
delegate_->OnAcceleratedWidgetAvailable(window_);
}
void SkyView::SurfaceDestroyed(JNIEnv* env, jobject obj) {
DCHECK(window_);
ReleaseWindow();
}
void SkyView::SurfaceSetSize(JNIEnv* env,
jobject obj,
jint width,
jint height,
jfloat density) {
}
void SkyView::ReleaseWindow() {
ANativeWindow_release(window_);
window_ = NULL;
}
} // namespace shell
} // namespace sky
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SKY_SHELL_SKY_VIEW_H_
#define SKY_SHELL_SKY_VIEW_H_
#include "base/android/jni_weak_ref.h"
#include "base/android/scoped_java_ref.h"
#include "base/macros.h"
#include "ui/gfx/native_widget_types.h"
struct ANativeWindow;
namespace sky {
namespace shell {
class SkyView {
public:
static bool Register(JNIEnv* env);
class Delegate {
public:
virtual void OnAcceleratedWidgetAvailable(
gfx::AcceleratedWidget widget) = 0;
virtual void OnDestroyed() = 0;
protected:
virtual ~Delegate();
};
explicit SkyView(Delegate* delegate);
~SkyView();
void Init();
// Called from Java
void Destroy(JNIEnv* env, jobject obj);
void SurfaceCreated(JNIEnv* env, jobject obj, jobject jsurface);
void SurfaceDestroyed(JNIEnv* env, jobject obj);
void SurfaceSetSize(JNIEnv* env,
jobject obj,
jint width,
jint height,
jfloat density);
private:
void ReleaseWindow();
Delegate* delegate_;
ANativeWindow* window_;
DISALLOW_COPY_AND_ASSIGN(SkyView);
};
} // namespace shell
} // namespace sky
#endif // SKY_SHELL_SKY_VIEW_H_
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册