mirror of
https://github.com/electron/electron.git
synced 2026-02-26 03:01:17 -05:00
Compare commits
52 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5ead4f655a | ||
|
|
b975d4c41f | ||
|
|
cca0d8d583 | ||
|
|
d7a54cf3a6 | ||
|
|
a50d3bde5c | ||
|
|
7f496f1994 | ||
|
|
395eb067d1 | ||
|
|
98fcc93862 | ||
|
|
b21e5a6300 | ||
|
|
ac11c95da6 | ||
|
|
5bbf749693 | ||
|
|
3d518c2105 | ||
|
|
839f875045 | ||
|
|
2369f6cc41 | ||
|
|
ff88535cd5 | ||
|
|
7a38307d1f | ||
|
|
877277d837 | ||
|
|
d4e7fe3eb8 | ||
|
|
03e6d564d7 | ||
|
|
f5fc26d8fc | ||
|
|
86ebd6e8e3 | ||
|
|
a80fe40f56 | ||
|
|
b1f0c2d174 | ||
|
|
ac794c8085 | ||
|
|
663ab8e0bf | ||
|
|
d2162bf9f4 | ||
|
|
b7a71b885e | ||
|
|
9aefb9c2d3 | ||
|
|
a3e1fa3350 | ||
|
|
bf6fb3872e | ||
|
|
84307dd329 | ||
|
|
c814803c94 | ||
|
|
61d54f0558 | ||
|
|
9d0a11580f | ||
|
|
7a6db019e8 | ||
|
|
fdecf09d99 | ||
|
|
7e7f0888e5 | ||
|
|
5a837f5850 | ||
|
|
d3e6166de6 | ||
|
|
c6f0968d17 | ||
|
|
abea550a4d | ||
|
|
d7261073e7 | ||
|
|
01a9ac21a5 | ||
|
|
8b41e78245 | ||
|
|
9ab3b5293c | ||
|
|
7a83b16cc4 | ||
|
|
679959eeb5 | ||
|
|
e96a3abdf9 | ||
|
|
788ed588c9 | ||
|
|
35229255bb | ||
|
|
f4b648385c | ||
|
|
eb1675a90f |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -5,6 +5,7 @@
|
||||
/out/
|
||||
/vendor/brightray/vendor/download/
|
||||
/vendor/python_26/
|
||||
/vendor/npm/
|
||||
node_modules/
|
||||
*.xcodeproj
|
||||
*.swp
|
||||
|
||||
3
atom.gyp
3
atom.gyp
@@ -32,6 +32,7 @@
|
||||
'atom/common/api/lib/shell.coffee',
|
||||
'atom/common/lib/init.coffee',
|
||||
'atom/renderer/lib/init.coffee',
|
||||
'atom/renderer/lib/inspector.coffee',
|
||||
'atom/renderer/lib/override.coffee',
|
||||
'atom/renderer/api/lib/ipc.coffee',
|
||||
'atom/renderer/api/lib/remote.coffee',
|
||||
@@ -93,6 +94,8 @@
|
||||
'atom/browser/browser_observer.h',
|
||||
'atom/browser/devtools_delegate.cc',
|
||||
'atom/browser/devtools_delegate.h',
|
||||
'atom/browser/devtools_web_contents_observer.cc',
|
||||
'atom/browser/devtools_web_contents_observer.h',
|
||||
'atom/browser/native_window.cc',
|
||||
'atom/browser/native_window.h',
|
||||
'atom/browser/native_window_gtk.cc',
|
||||
|
||||
@@ -4,10 +4,10 @@
|
||||
|
||||
#include "atom/browser/api/atom_api_event.h"
|
||||
|
||||
#include "atom/browser/native_window.h"
|
||||
#include "atom/common/api/api_messages.h"
|
||||
#include "atom/common/v8/node_common.h"
|
||||
#include "atom/common/v8/native_type_conversions.h"
|
||||
#include "content/public/browser/web_contents.h"
|
||||
|
||||
namespace atom {
|
||||
|
||||
@@ -22,8 +22,6 @@ Event::Event()
|
||||
}
|
||||
|
||||
Event::~Event() {
|
||||
if (sender_ != NULL)
|
||||
sender_->RemoveObserver(this);
|
||||
}
|
||||
|
||||
// static
|
||||
@@ -44,16 +42,17 @@ v8::Handle<v8::Object> Event::CreateV8Object() {
|
||||
return t->NewInstance(0, NULL);
|
||||
}
|
||||
|
||||
void Event::SetSenderAndMessage(NativeWindow* sender, IPC::Message* message) {
|
||||
void Event::SetSenderAndMessage(content::WebContents* sender,
|
||||
IPC::Message* message) {
|
||||
DCHECK(!sender_);
|
||||
DCHECK(!message_);
|
||||
sender_ = sender;
|
||||
message_ = message;
|
||||
|
||||
sender_->AddObserver(this);
|
||||
Observe(sender);
|
||||
}
|
||||
|
||||
void Event::OnWindowClosed() {
|
||||
void Event::WebContentsDestroyed(content::WebContents* web_contents) {
|
||||
sender_ = NULL;
|
||||
message_ = NULL;
|
||||
}
|
||||
|
||||
@@ -5,11 +5,11 @@
|
||||
#ifndef ATOM_BROWSER_API_ATOM_API_EVENT_H_
|
||||
#define ATOM_BROWSER_API_ATOM_API_EVENT_H_
|
||||
|
||||
#include "atom/common/v8/scoped_persistent.h"
|
||||
#include "base/basictypes.h"
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/strings/string16.h"
|
||||
#include "atom/browser/native_window_observer.h"
|
||||
#include "atom/common/v8/scoped_persistent.h"
|
||||
#include "content/public/browser/web_contents_observer.h"
|
||||
#include "vendor/node/src/node_object_wrap.h"
|
||||
|
||||
namespace IPC {
|
||||
@@ -18,12 +18,10 @@ class Message;
|
||||
|
||||
namespace atom {
|
||||
|
||||
class NativeWindow;
|
||||
|
||||
namespace api {
|
||||
|
||||
class Event : public node::ObjectWrap,
|
||||
public NativeWindowObserver {
|
||||
public content::WebContentsObserver {
|
||||
public:
|
||||
virtual ~Event();
|
||||
|
||||
@@ -31,7 +29,7 @@ class Event : public node::ObjectWrap,
|
||||
static v8::Handle<v8::Object> CreateV8Object();
|
||||
|
||||
// Pass the sender and message to be replied.
|
||||
void SetSenderAndMessage(NativeWindow* sender, IPC::Message* message);
|
||||
void SetSenderAndMessage(content::WebContents* sender, IPC::Message* message);
|
||||
|
||||
// Whether event.preventDefault() is called.
|
||||
bool prevent_default() const { return prevent_default_; }
|
||||
@@ -39,8 +37,8 @@ class Event : public node::ObjectWrap,
|
||||
protected:
|
||||
Event();
|
||||
|
||||
// NativeWindowObserver implementations:
|
||||
virtual void OnWindowClosed() OVERRIDE;
|
||||
// content::WebContentsObserver implementations:
|
||||
virtual void WebContentsDestroyed(content::WebContents*) OVERRIDE;
|
||||
|
||||
private:
|
||||
static void New(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
@@ -52,7 +50,7 @@ class Event : public node::ObjectWrap,
|
||||
static ScopedPersistent<v8::Function> constructor_template_;
|
||||
|
||||
// Replyer for the synchronous messages.
|
||||
NativeWindow* sender_;
|
||||
content::WebContents* sender_;
|
||||
IPC::Message* message_;
|
||||
|
||||
bool prevent_default_;
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
|
||||
#import "atom/browser/api/atom_api_menu_mac.h"
|
||||
|
||||
#include "base/mac/scoped_sending_event.h"
|
||||
#include "base/message_loop/message_loop.h"
|
||||
#include "base/strings/sys_string_conversions.h"
|
||||
#include "atom/browser/native_window.h"
|
||||
@@ -45,23 +44,10 @@ void MenuMac::Popup(NativeWindow* native_window) {
|
||||
clickCount:1
|
||||
pressure:1.0];
|
||||
|
||||
{
|
||||
// Make sure events can be pumped while the menu is up.
|
||||
base::MessageLoop::ScopedNestableTaskAllower allow(
|
||||
base::MessageLoop::current());
|
||||
|
||||
// One of the events that could be pumped is |window.close()|.
|
||||
// User-initiated event-tracking loops protect against this by
|
||||
// setting flags in -[CrApplication sendEvent:], but since
|
||||
// web-content menus are initiated by IPC message the setup has to
|
||||
// be done manually.
|
||||
base::mac::ScopedSendingEvent sendingEventScoper;
|
||||
|
||||
// Show the menu.
|
||||
[NSMenu popUpContextMenu:[menu_controller menu]
|
||||
withEvent:clickEvent
|
||||
forView:web_contents->GetView()->GetContentNativeView()];
|
||||
}
|
||||
// Show the menu.
|
||||
[NSMenu popUpContextMenu:[menu_controller menu]
|
||||
withEvent:clickEvent
|
||||
forView:web_contents->GetView()->GetContentNativeView()];
|
||||
}
|
||||
|
||||
// static
|
||||
|
||||
@@ -503,6 +503,31 @@ void Window::IsCrashed(const v8::FunctionCallbackInfo<v8::Value>& args) {
|
||||
args.GetReturnValue().Set(self->window_->GetWebContents()->IsCrashed());
|
||||
}
|
||||
|
||||
// static
|
||||
void Window::GetDevTools(const v8::FunctionCallbackInfo<v8::Value>& args) {
|
||||
UNWRAP_WINDOW_AND_CHECK;
|
||||
|
||||
content::WebContents* web_contents = self->window_->GetDevToolsWebContents();
|
||||
v8::Local<v8::Object> devtools = v8::Object::New();
|
||||
devtools->Set(ToV8Value("processId"),
|
||||
ToV8Value(web_contents->GetRenderProcessHost()->GetID()));
|
||||
devtools->Set(ToV8Value("routingId"),
|
||||
ToV8Value(web_contents->GetRoutingID()));
|
||||
args.GetReturnValue().Set(devtools);
|
||||
}
|
||||
|
||||
// static
|
||||
void Window::ExecuteJavaScriptInDevTools(
|
||||
const v8::FunctionCallbackInfo<v8::Value>& args) {
|
||||
UNWRAP_WINDOW_AND_CHECK;
|
||||
|
||||
std::string code;
|
||||
if (!FromV8Arguments(args, &code))
|
||||
return node::ThrowTypeError("Bad argument");
|
||||
|
||||
self->window_->ExecuteJavaScriptInDevTools(code);
|
||||
}
|
||||
|
||||
// static
|
||||
void Window::LoadURL(const v8::FunctionCallbackInfo<v8::Value>& args) {
|
||||
UNWRAP_WINDOW_AND_CHECK;
|
||||
@@ -686,6 +711,10 @@ void Window::Initialize(v8::Handle<v8::Object> target) {
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "getProcessId", GetProcessID);
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "isCrashed", IsCrashed);
|
||||
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "getDevTools", GetDevTools);
|
||||
NODE_SET_PROTOTYPE_METHOD(
|
||||
t, "executeJavaScriptInDevTools", ExecuteJavaScriptInDevTools);
|
||||
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "loadUrl", LoadURL);
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "getUrl", GetURL);
|
||||
NODE_SET_PROTOTYPE_METHOD(t, "canGoBack", CanGoBack);
|
||||
|
||||
@@ -103,6 +103,11 @@ class Window : public EventEmitter,
|
||||
static void GetProcessID(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
static void IsCrashed(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
|
||||
// APIs for devtools.
|
||||
static void GetDevTools(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
static void ExecuteJavaScriptInDevTools(
|
||||
const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
|
||||
// APIs for NavigationController.
|
||||
static void LoadURL(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
static void GetURL(const v8::FunctionCallbackInfo<v8::Value>& args);
|
||||
|
||||
@@ -57,7 +57,7 @@ void AtomBrowserBindings::OnRendererMessageSync(
|
||||
int routing_id,
|
||||
const string16& channel,
|
||||
const base::ListValue& args,
|
||||
NativeWindow* sender,
|
||||
content::WebContents* sender,
|
||||
IPC::Message* message) {
|
||||
v8::Locker locker(node_isolate);
|
||||
v8::HandleScope handle_scope(node_isolate);
|
||||
|
||||
@@ -13,14 +13,16 @@ namespace base {
|
||||
class ListValue;
|
||||
}
|
||||
|
||||
namespace content {
|
||||
class WebContents;
|
||||
}
|
||||
|
||||
namespace IPC {
|
||||
class Message;
|
||||
}
|
||||
|
||||
namespace atom {
|
||||
|
||||
class NativeWindow;
|
||||
|
||||
class AtomBrowserBindings : public AtomBindings {
|
||||
public:
|
||||
AtomBrowserBindings();
|
||||
@@ -37,7 +39,7 @@ class AtomBrowserBindings : public AtomBindings {
|
||||
int routing_id,
|
||||
const string16& channel,
|
||||
const base::ListValue& args,
|
||||
NativeWindow* sender,
|
||||
content::WebContents* sender,
|
||||
IPC::Message* message);
|
||||
|
||||
private:
|
||||
|
||||
@@ -55,4 +55,11 @@ BrowserWindow.fromProcessIdAndRoutingId = (processId, routingId) ->
|
||||
return window for window in windows when window.getProcessId() == processId and
|
||||
window.getRoutingId() == routingId
|
||||
|
||||
BrowserWindow.fromDevTools = (processId, routingId) ->
|
||||
windows = BrowserWindow.getAllWindows()
|
||||
for window in windows
|
||||
devtools = window.getDevTools()
|
||||
return window if devtools.processId == processId and
|
||||
devtools.routingId == routingId
|
||||
|
||||
module.exports = BrowserWindow
|
||||
|
||||
64
atom/browser/devtools_web_contents_observer.cc
Normal file
64
atom/browser/devtools_web_contents_observer.cc
Normal file
@@ -0,0 +1,64 @@
|
||||
// Copyright (c) 2014 GitHub, Inc. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "atom/browser/devtools_web_contents_observer.h"
|
||||
|
||||
#include "atom/browser/api/atom_browser_bindings.h"
|
||||
#include "atom/browser/atom_browser_main_parts.h"
|
||||
#include "atom/browser/native_window.h"
|
||||
#include "atom/common/api/api_messages.h"
|
||||
#include "base/logging.h"
|
||||
#include "content/public/browser/render_process_host.h"
|
||||
#include "ipc/ipc_message_macros.h"
|
||||
|
||||
namespace atom {
|
||||
|
||||
DevToolsWebContentsObserver::DevToolsWebContentsObserver(
|
||||
NativeWindow* native_window,
|
||||
content::WebContents* web_contents)
|
||||
: content::WebContentsObserver(web_contents),
|
||||
inspected_window_(native_window) {
|
||||
DCHECK(native_window);
|
||||
}
|
||||
|
||||
DevToolsWebContentsObserver::~DevToolsWebContentsObserver() {
|
||||
}
|
||||
|
||||
bool DevToolsWebContentsObserver::OnMessageReceived(
|
||||
const IPC::Message& message) {
|
||||
bool handled = true;
|
||||
IPC_BEGIN_MESSAGE_MAP(DevToolsWebContentsObserver, message)
|
||||
IPC_MESSAGE_HANDLER(AtomViewHostMsg_Message, OnRendererMessage)
|
||||
IPC_MESSAGE_HANDLER_DELAY_REPLY(AtomViewHostMsg_Message_Sync,
|
||||
OnRendererMessageSync)
|
||||
IPC_MESSAGE_UNHANDLED(handled = false)
|
||||
IPC_END_MESSAGE_MAP()
|
||||
|
||||
return handled;
|
||||
}
|
||||
|
||||
void DevToolsWebContentsObserver::OnRendererMessage(
|
||||
const string16& channel,
|
||||
const base::ListValue& args) {
|
||||
AtomBrowserMainParts::Get()->atom_bindings()->OnRendererMessage(
|
||||
web_contents()->GetRenderProcessHost()->GetID(),
|
||||
web_contents()->GetRoutingID(),
|
||||
channel,
|
||||
args);
|
||||
}
|
||||
|
||||
void DevToolsWebContentsObserver::OnRendererMessageSync(
|
||||
const string16& channel,
|
||||
const base::ListValue& args,
|
||||
IPC::Message* reply_msg) {
|
||||
AtomBrowserMainParts::Get()->atom_bindings()->OnRendererMessageSync(
|
||||
web_contents()->GetRenderProcessHost()->GetID(),
|
||||
web_contents()->GetRoutingID(),
|
||||
channel,
|
||||
args,
|
||||
web_contents(),
|
||||
reply_msg);
|
||||
}
|
||||
|
||||
} // namespace atom
|
||||
41
atom/browser/devtools_web_contents_observer.h
Normal file
41
atom/browser/devtools_web_contents_observer.h
Normal file
@@ -0,0 +1,41 @@
|
||||
// Copyright (c) 2014 GitHub, Inc. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#ifndef ATOM_BROWSER_DEVTOOLS_WEB_CONTENTS_OBSERVER_H_
|
||||
#define ATOM_BROWSER_DEVTOOLS_WEB_CONTENTS_OBSERVER_H_
|
||||
|
||||
#include "content/public/browser/web_contents_observer.h"
|
||||
|
||||
namespace base {
|
||||
class ListValue;
|
||||
}
|
||||
|
||||
namespace atom {
|
||||
|
||||
class NativeWindow;
|
||||
|
||||
class DevToolsWebContentsObserver : public content::WebContentsObserver {
|
||||
public:
|
||||
DevToolsWebContentsObserver(NativeWindow* native_window,
|
||||
content::WebContents* web_contents);
|
||||
virtual ~DevToolsWebContentsObserver();
|
||||
|
||||
protected:
|
||||
virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE;
|
||||
|
||||
void OnRendererMessage(const string16& channel,
|
||||
const base::ListValue& args);
|
||||
void OnRendererMessageSync(const string16& channel,
|
||||
const base::ListValue& args,
|
||||
IPC::Message* reply_msg);
|
||||
|
||||
private:
|
||||
NativeWindow* inspected_window_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(DevToolsWebContentsObserver);
|
||||
};
|
||||
|
||||
} // namespace atom
|
||||
|
||||
#endif // ATOM_BROWSER_DEVTOOLS_WEB_CONTENTS_OBSERVER_H_
|
||||
@@ -98,6 +98,7 @@ ipc.on 'ATOM_BROWSER_CURRENT_WINDOW', (event, processId, routingId) ->
|
||||
try
|
||||
BrowserWindow = require 'browser-window'
|
||||
window = BrowserWindow.fromProcessIdAndRoutingId processId, routingId
|
||||
window = BrowserWindow.fromDevTools processId, routingId unless window?
|
||||
event.returnValue = valueToMeta processId, routingId, window
|
||||
catch e
|
||||
event.returnValue = errorToMeta e
|
||||
|
||||
@@ -8,20 +8,26 @@
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "base/command_line.h"
|
||||
#include "base/file_util.h"
|
||||
#include "base/prefs/pref_service.h"
|
||||
#include "base/message_loop/message_loop.h"
|
||||
#include "base/strings/stringprintf.h"
|
||||
#include "base/strings/utf_string_conversions.h"
|
||||
#include "base/values.h"
|
||||
#include "atom/browser/api/atom_browser_bindings.h"
|
||||
#include "atom/browser/atom_browser_context.h"
|
||||
#include "atom/browser/atom_browser_main_parts.h"
|
||||
#include "atom/browser/atom_javascript_dialog_manager.h"
|
||||
#include "atom/browser/browser.h"
|
||||
#include "atom/browser/devtools_delegate.h"
|
||||
#include "atom/browser/devtools_web_contents_observer.h"
|
||||
#include "atom/browser/ui/file_dialog.h"
|
||||
#include "atom/browser/window_list.h"
|
||||
#include "atom/common/api/api_messages.h"
|
||||
#include "atom/common/atom_version.h"
|
||||
#include "atom/common/options_switches.h"
|
||||
#include "base/command_line.h"
|
||||
#include "base/file_util.h"
|
||||
#include "base/json/json_writer.h"
|
||||
#include "base/prefs/pref_service.h"
|
||||
#include "base/message_loop/message_loop.h"
|
||||
#include "base/strings/stringprintf.h"
|
||||
#include "base/strings/utf_string_conversions.h"
|
||||
#include "base/values.h"
|
||||
#include "content/public/browser/devtools_agent_host.h"
|
||||
#include "content/public/browser/invalidate_type.h"
|
||||
#include "content/public/browser/navigation_entry.h"
|
||||
@@ -33,9 +39,6 @@
|
||||
#include "content/public/browser/render_widget_host_view.h"
|
||||
#include "content/public/browser/web_contents_view.h"
|
||||
#include "content/public/common/renderer_preferences.h"
|
||||
#include "atom/common/api/api_messages.h"
|
||||
#include "atom/common/atom_version.h"
|
||||
#include "atom/common/options_switches.h"
|
||||
#include "ipc/ipc_message_macros.h"
|
||||
#include "ui/gfx/codec/png_codec.h"
|
||||
#include "ui/gfx/point.h"
|
||||
@@ -50,12 +53,6 @@ using content::NavigationEntry;
|
||||
|
||||
namespace atom {
|
||||
|
||||
namespace {
|
||||
|
||||
const char kDockSidePref[] = "brightray.devtools.dockside";
|
||||
|
||||
} // namespace
|
||||
|
||||
NativeWindow::NativeWindow(content::WebContents* web_contents,
|
||||
base::DictionaryValue* options)
|
||||
: content::WebContentsObserver(web_contents),
|
||||
@@ -194,8 +191,12 @@ bool NativeWindow::HasModalDialog() {
|
||||
void NativeWindow::OpenDevTools() {
|
||||
if (devtools_window_) {
|
||||
devtools_window_->Focus(true);
|
||||
devtools_web_contents_observer_.reset(new DevToolsWebContentsObserver(
|
||||
this, devtools_window_->GetWebContents()));
|
||||
} else {
|
||||
inspectable_web_contents()->ShowDevTools();
|
||||
devtools_web_contents_observer_.reset(new DevToolsWebContentsObserver(
|
||||
this, GetDevToolsWebContents()));
|
||||
#if defined(OS_MACOSX)
|
||||
// Temporary fix for flashing devtools, try removing this after upgraded to
|
||||
// Chrome 32.
|
||||
@@ -208,7 +209,7 @@ void NativeWindow::CloseDevTools() {
|
||||
if (devtools_window_)
|
||||
devtools_window_->Close();
|
||||
else
|
||||
inspectable_web_contents()->GetView()->CloseDevTools();
|
||||
inspectable_web_contents()->CloseDevTools();
|
||||
}
|
||||
|
||||
bool NativeWindow::IsDevToolsOpened() {
|
||||
@@ -224,6 +225,11 @@ void NativeWindow::InspectElement(int x, int y) {
|
||||
agent->InspectElement(x, y);
|
||||
}
|
||||
|
||||
void NativeWindow::ExecuteJavaScriptInDevTools(const std::string& script) {
|
||||
GetDevToolsWebContents()->GetRenderViewHost()->ExecuteJavascriptInWebFrame(
|
||||
string16(), base::UTF8ToUTF16(script));
|
||||
}
|
||||
|
||||
void NativeWindow::FocusOnWebView() {
|
||||
GetWebContents()->GetRenderViewHost()->Focus();
|
||||
}
|
||||
@@ -264,12 +270,28 @@ base::ProcessHandle NativeWindow::GetRenderProcessHandle() {
|
||||
|
||||
void NativeWindow::CapturePage(const gfx::Rect& rect,
|
||||
const CapturePageCallback& callback) {
|
||||
content::RenderViewHost* render_view_host =
|
||||
GetWebContents()->GetRenderViewHost();
|
||||
content::RenderWidgetHostView* render_widget_host_view =
|
||||
render_view_host->GetView();
|
||||
|
||||
if (!render_widget_host_view) {
|
||||
callback.Run(std::vector<unsigned char>());
|
||||
return;
|
||||
}
|
||||
|
||||
gfx::Rect flipped_y_rect = rect;
|
||||
flipped_y_rect.set_y(-rect.y());
|
||||
|
||||
gfx::Size size;
|
||||
if (flipped_y_rect.IsEmpty())
|
||||
size = render_widget_host_view->GetViewBounds().size();
|
||||
else
|
||||
size = flipped_y_rect.size();
|
||||
|
||||
GetWebContents()->GetRenderViewHost()->CopyFromBackingStore(
|
||||
flipped_y_rect,
|
||||
gfx::Size(),
|
||||
size,
|
||||
base::Bind(&NativeWindow::OnCapturePageDone,
|
||||
weak_factory_.GetWeakPtr(),
|
||||
callback));
|
||||
@@ -288,20 +310,11 @@ void NativeWindow::CloseWebContents() {
|
||||
content::WebContents* web_contents(GetWebContents());
|
||||
|
||||
// Assume the window is not responding if it doesn't cancel the close and is
|
||||
// not closed in 500ms, in this way we can quickly show the unresponsive
|
||||
// not closed in 5000ms, in this way we can quickly show the unresponsive
|
||||
// dialog when the window is busy executing some script withouth waiting for
|
||||
// the unresponsive timeout.
|
||||
if (!Browser::Get()->is_quiting() &&
|
||||
window_unresposive_closure_.IsCancelled()) {
|
||||
window_unresposive_closure_.Reset(
|
||||
base::Bind(&NativeWindow::RendererUnresponsive,
|
||||
weak_factory_.GetWeakPtr(),
|
||||
web_contents));
|
||||
base::MessageLoop::current()->PostDelayedTask(
|
||||
FROM_HERE,
|
||||
window_unresposive_closure_.callback(),
|
||||
base::TimeDelta::FromMilliseconds(500));
|
||||
}
|
||||
if (window_unresposive_closure_.IsCancelled())
|
||||
ScheduleUnresponsiveEvent(5000);
|
||||
|
||||
if (web_contents->NeedToFireBeforeUnload())
|
||||
web_contents->GetRenderViewHost()->FirePageBeforeUnload(false);
|
||||
@@ -446,12 +459,10 @@ bool NativeWindow::IsPopupOrPanel(const content::WebContents* source) const {
|
||||
}
|
||||
|
||||
void NativeWindow::RendererUnresponsive(content::WebContents* source) {
|
||||
window_unresposive_closure_.Cancel();
|
||||
|
||||
if (!HasModalDialog())
|
||||
FOR_EACH_OBSERVER(NativeWindowObserver,
|
||||
observers_,
|
||||
OnRendererUnresponsive());
|
||||
// Schedule the unresponsive shortly later, since we may receive the
|
||||
// responsive event soon.
|
||||
// This could happen after the whole application had blocked for a while.
|
||||
ScheduleUnresponsiveEvent(50);
|
||||
}
|
||||
|
||||
void NativeWindow::RendererResponsive(content::WebContents* source) {
|
||||
@@ -524,6 +535,60 @@ bool NativeWindow::DevToolsShow(std::string* dock_side) {
|
||||
return false;
|
||||
}
|
||||
|
||||
void NativeWindow::DevToolsSaveToFile(const std::string& url,
|
||||
const std::string& content,
|
||||
bool save_as) {
|
||||
base::FilePath path;
|
||||
PathsMap::iterator it = saved_files_.find(url);
|
||||
if (it != saved_files_.end() && !save_as) {
|
||||
path = it->second;
|
||||
} else {
|
||||
if (!file_dialog::ShowSaveDialog(this, url, base::FilePath(url), &path))
|
||||
return;
|
||||
}
|
||||
|
||||
saved_files_[url] = path;
|
||||
file_util::WriteFile(path, content.data(), content.size());
|
||||
|
||||
// Notify devtools.
|
||||
base::StringValue url_value(url);
|
||||
CallDevToolsFunction("InspectorFrontendAPI.savedURL", &url_value);
|
||||
|
||||
// TODO(zcbenz): In later Chrome we need to call canceledSaveURL when the save
|
||||
// failed.
|
||||
}
|
||||
|
||||
void NativeWindow::DevToolsAppendToFile(const std::string& url,
|
||||
const std::string& content) {
|
||||
PathsMap::iterator it = saved_files_.find(url);
|
||||
if (it == saved_files_.end())
|
||||
return;
|
||||
file_util::AppendToFile(it->second, content.data(), content.size());
|
||||
|
||||
// Notify devtools.
|
||||
base::StringValue url_value(url);
|
||||
CallDevToolsFunction("InspectorFrontendAPI.appendedToURL", &url_value);
|
||||
}
|
||||
|
||||
void NativeWindow::ScheduleUnresponsiveEvent(int ms) {
|
||||
window_unresposive_closure_.Reset(
|
||||
base::Bind(&NativeWindow::NotifyWindowUnresponsive,
|
||||
weak_factory_.GetWeakPtr()));
|
||||
base::MessageLoop::current()->PostDelayedTask(
|
||||
FROM_HERE,
|
||||
window_unresposive_closure_.callback(),
|
||||
base::TimeDelta::FromMilliseconds(ms));
|
||||
}
|
||||
|
||||
void NativeWindow::NotifyWindowUnresponsive() {
|
||||
window_unresposive_closure_.Cancel();
|
||||
|
||||
if (!HasModalDialog())
|
||||
FOR_EACH_OBSERVER(NativeWindowObserver,
|
||||
observers_,
|
||||
OnRendererUnresponsive());
|
||||
}
|
||||
|
||||
void NativeWindow::OnCapturePageDone(const CapturePageCallback& callback,
|
||||
bool succeed,
|
||||
const SkBitmap& bitmap) {
|
||||
@@ -533,6 +598,27 @@ void NativeWindow::OnCapturePageDone(const CapturePageCallback& callback,
|
||||
callback.Run(data);
|
||||
}
|
||||
|
||||
void NativeWindow::CallDevToolsFunction(const std::string& function_name,
|
||||
const base::Value* arg1,
|
||||
const base::Value* arg2,
|
||||
const base::Value* arg3) {
|
||||
std::string params;
|
||||
if (arg1) {
|
||||
std::string json;
|
||||
base::JSONWriter::Write(arg1, &json);
|
||||
params.append(json);
|
||||
if (arg2) {
|
||||
base::JSONWriter::Write(arg2, &json);
|
||||
params.append(", " + json);
|
||||
if (arg3) {
|
||||
base::JSONWriter::Write(arg3, &json);
|
||||
params.append(", " + json);
|
||||
}
|
||||
}
|
||||
}
|
||||
ExecuteJavaScriptInDevTools(function_name + "(" + params + ");");
|
||||
}
|
||||
|
||||
void NativeWindow::OnRendererMessage(const string16& channel,
|
||||
const base::ListValue& args) {
|
||||
AtomBrowserMainParts::Get()->atom_bindings()->OnRendererMessage(
|
||||
@@ -550,7 +636,7 @@ void NativeWindow::OnRendererMessageSync(const string16& channel,
|
||||
GetWebContents()->GetRoutingID(),
|
||||
channel,
|
||||
args,
|
||||
this,
|
||||
GetWebContents(),
|
||||
reply_msg);
|
||||
}
|
||||
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#ifndef ATOM_BROWSER_NATIVE_WINDOW_H_
|
||||
#define ATOM_BROWSER_NATIVE_WINDOW_H_
|
||||
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
@@ -41,14 +42,11 @@ class Rect;
|
||||
class Size;
|
||||
}
|
||||
|
||||
namespace IPC {
|
||||
class Message;
|
||||
}
|
||||
|
||||
namespace atom {
|
||||
|
||||
class AtomJavaScriptDialogManager;
|
||||
class DevToolsDelegate;
|
||||
class DevToolsWebContentsObserver;
|
||||
struct DraggableRegion;
|
||||
|
||||
class NativeWindow : public brightray::DefaultWebContentsDelegate,
|
||||
@@ -138,6 +136,7 @@ class NativeWindow : public brightray::DefaultWebContentsDelegate,
|
||||
virtual void CloseDevTools();
|
||||
virtual bool IsDevToolsOpened();
|
||||
virtual void InspectElement(int x, int y);
|
||||
virtual void ExecuteJavaScriptInDevTools(const std::string& script);
|
||||
|
||||
virtual void FocusOnWebView();
|
||||
virtual void BlurWebView();
|
||||
@@ -240,6 +239,11 @@ class NativeWindow : public brightray::DefaultWebContentsDelegate,
|
||||
virtual bool DevToolsSetDockSide(const std::string& dock_side,
|
||||
bool* succeed) OVERRIDE;
|
||||
virtual bool DevToolsShow(std::string* dock_side) OVERRIDE;
|
||||
virtual void DevToolsSaveToFile(const std::string& url,
|
||||
const std::string& content,
|
||||
bool save_as) OVERRIDE;
|
||||
virtual void DevToolsAppendToFile(const std::string& url,
|
||||
const std::string& content) OVERRIDE;
|
||||
|
||||
// Whether window has standard frame.
|
||||
bool has_frame_;
|
||||
@@ -248,6 +252,18 @@ class NativeWindow : public brightray::DefaultWebContentsDelegate,
|
||||
gfx::Image icon_;
|
||||
|
||||
private:
|
||||
// Schedule a notification unresponsive event.
|
||||
void ScheduleUnresponsiveEvent(int ms);
|
||||
|
||||
// Dispatch unresponsive event to observers.
|
||||
void NotifyWindowUnresponsive();
|
||||
|
||||
// Call a function in devtools.
|
||||
void CallDevToolsFunction(const std::string& function_name,
|
||||
const base::Value* arg1 = NULL,
|
||||
const base::Value* arg2 = NULL,
|
||||
const base::Value* arg3 = NULL);
|
||||
|
||||
// Called when CapturePage has done.
|
||||
void OnCapturePageDone(const CapturePageCallback& callback,
|
||||
bool succeed,
|
||||
@@ -282,11 +298,18 @@ class NativeWindow : public brightray::DefaultWebContentsDelegate,
|
||||
base::WeakPtrFactory<NativeWindow> weak_factory_;
|
||||
|
||||
base::WeakPtr<NativeWindow> devtools_window_;
|
||||
|
||||
scoped_ptr<DevToolsDelegate> devtools_delegate_;
|
||||
|
||||
// WebContentsObserver for the WebContents of devtools.
|
||||
scoped_ptr<DevToolsWebContentsObserver> devtools_web_contents_observer_;
|
||||
|
||||
scoped_ptr<AtomJavaScriptDialogManager> dialog_manager_;
|
||||
scoped_ptr<brightray::InspectableWebContents> inspectable_web_contents_;
|
||||
|
||||
// Maps url to file path, used by the file requests sent from devtools.
|
||||
typedef std::map<std::string, base::FilePath> PathsMap;
|
||||
PathsMap saved_files_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(NativeWindow);
|
||||
};
|
||||
|
||||
|
||||
@@ -7,15 +7,19 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "base/values.h"
|
||||
#include "chrome/browser/ui/gtk/gtk_window_util.h"
|
||||
#include "atom/common/draggable_region.h"
|
||||
#include "atom/common/options_switches.h"
|
||||
#include "base/environment.h"
|
||||
#include "base/nix/xdg_util.h"
|
||||
#include "base/values.h"
|
||||
#include "chrome/browser/ui/gtk/gtk_window_util.h"
|
||||
#include "content/public/browser/native_web_keyboard_event.h"
|
||||
#include "content/public/browser/web_contents.h"
|
||||
#include "content/public/browser/web_contents_view.h"
|
||||
#include "content/public/common/renderer_preferences.h"
|
||||
#include "ui/base/accelerators/platform_accelerator_gtk.h"
|
||||
#include "ui/base/models/simple_menu_model.h"
|
||||
#include "ui/base/x/active_window_watcher_x.h"
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/gfx/gtk_util.h"
|
||||
#include "ui/gfx/rect.h"
|
||||
@@ -30,6 +34,26 @@ namespace {
|
||||
// This matches the logic in the WebKit GTK port.
|
||||
const double kGtkCursorBlinkCycleFactor = 2000.0;
|
||||
|
||||
// Substract window border's size from window size according to current window
|
||||
// manager.
|
||||
void SubstractBorderSize(int* width, int* height) {
|
||||
scoped_ptr<base::Environment> env(base::Environment::Create());
|
||||
base::nix::DesktopEnvironment de(base::nix::GetDesktopEnvironment(env.get()));
|
||||
if (de == base::nix::DESKTOP_ENVIRONMENT_UNITY) {
|
||||
*width -= 2;
|
||||
*height -= 29;
|
||||
} else if (de == base::nix::DESKTOP_ENVIRONMENT_GNOME) {
|
||||
*width -= 2;
|
||||
*height -= 33;
|
||||
} else if (de == base::nix::DESKTOP_ENVIRONMENT_XFCE) {
|
||||
*width -= 6;
|
||||
*height -= 27;
|
||||
} else {
|
||||
*width -= 2;
|
||||
*height -= 29;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
NativeWindowGtk::NativeWindowGtk(content::WebContents* web_contents,
|
||||
@@ -39,7 +63,9 @@ NativeWindowGtk::NativeWindowGtk(content::WebContents* web_contents,
|
||||
vbox_(gtk_vbox_new(FALSE, 0)),
|
||||
state_(GDK_WINDOW_STATE_WITHDRAWN),
|
||||
is_always_on_top_(false),
|
||||
is_active_(false),
|
||||
suppress_window_raise_(false),
|
||||
has_ever_been_shown_(false),
|
||||
frame_cursor_(NULL) {
|
||||
gtk_container_add(GTK_CONTAINER(window_), vbox_);
|
||||
gtk_container_add(GTK_CONTAINER(vbox_),
|
||||
@@ -48,11 +74,26 @@ NativeWindowGtk::NativeWindowGtk(content::WebContents* web_contents,
|
||||
int width = 800, height = 600;
|
||||
options->GetInteger(switches::kWidth, &width);
|
||||
options->GetInteger(switches::kHeight, &height);
|
||||
gtk_window_set_default_size(window_, width, height);
|
||||
|
||||
// Fixup the initial window size.
|
||||
if (has_frame_)
|
||||
SubstractBorderSize(&width, &height);
|
||||
|
||||
// Force a size allocation so the web page of hidden window can have correct
|
||||
// value of $(window).width().
|
||||
GtkAllocation size = { 0, 0, width, height };
|
||||
gtk_widget_show_all(vbox_);
|
||||
gtk_widget_size_allocate(GTK_WIDGET(window_), &size);
|
||||
gtk_window_util::SetWindowSize(window_, gfx::Size(width, height));
|
||||
|
||||
// Create the underlying gdk window.
|
||||
gtk_widget_realize(GTK_WIDGET(window_));
|
||||
|
||||
if (!icon_.IsEmpty())
|
||||
gtk_window_set_icon(window_, icon_.ToGdkPixbuf());
|
||||
|
||||
ui::ActiveWindowWatcherX::AddObserver(this);
|
||||
|
||||
// In some (older) versions of compiz, raising top-level windows when they
|
||||
// are partially off-screen causes them to get snapped back on screen, not
|
||||
// always even on the current virtual desktop. If we are running under
|
||||
@@ -64,8 +105,8 @@ NativeWindowGtk::NativeWindowGtk(content::WebContents* web_contents,
|
||||
G_CALLBACK(OnWindowDeleteEventThunk), this);
|
||||
g_signal_connect(window_, "focus-out-event",
|
||||
G_CALLBACK(OnFocusOutThunk), this);
|
||||
g_signal_connect(window_, "key-press-event",
|
||||
G_CALLBACK(OnKeyPressThunk), this);
|
||||
g_signal_connect(window_, "window-state-event",
|
||||
G_CALLBACK(OnWindowStateThunk), this);
|
||||
|
||||
if (!has_frame_) {
|
||||
gtk_window_set_decorated(window_, false);
|
||||
@@ -80,6 +121,8 @@ NativeWindowGtk::NativeWindowGtk(content::WebContents* web_contents,
|
||||
}
|
||||
|
||||
NativeWindowGtk::~NativeWindowGtk() {
|
||||
ui::ActiveWindowWatcherX::RemoveObserver(this);
|
||||
|
||||
if (window_)
|
||||
gtk_widget_destroy(GTK_WIDGET(window_));
|
||||
}
|
||||
@@ -95,7 +138,7 @@ void NativeWindowGtk::CloseImmediately() {
|
||||
|
||||
void NativeWindowGtk::Move(const gfx::Rect& pos) {
|
||||
gtk_window_move(window_, pos.x(), pos.y());
|
||||
gtk_window_resize(window_, pos.width(), pos.height());
|
||||
SetSize(pos.size());
|
||||
}
|
||||
|
||||
void NativeWindowGtk::Focus(bool focus) {
|
||||
@@ -109,10 +152,15 @@ void NativeWindowGtk::Focus(bool focus) {
|
||||
}
|
||||
|
||||
bool NativeWindowGtk::IsFocused() {
|
||||
if (ui::ActiveWindowWatcherX::WMSupportsActivation())
|
||||
return is_active_;
|
||||
|
||||
// This still works even though we don't get the activation notification.
|
||||
return gtk_window_is_active(window_);
|
||||
}
|
||||
|
||||
void NativeWindowGtk::Show() {
|
||||
has_ever_been_shown_ = true;
|
||||
gtk_widget_show_all(GTK_WIDGET(window_));
|
||||
}
|
||||
|
||||
@@ -152,7 +200,13 @@ bool NativeWindowGtk::IsFullscreen() {
|
||||
}
|
||||
|
||||
void NativeWindowGtk::SetSize(const gfx::Size& size) {
|
||||
gtk_window_resize(window_, size.width(), size.height());
|
||||
// When the window has not been mapped the window size does not include frame.
|
||||
int width = size.width();
|
||||
int height = size.height();
|
||||
if (has_frame_ && !has_ever_been_shown_)
|
||||
SubstractBorderSize(&width, &height);
|
||||
|
||||
gtk_window_util::SetWindowSize(window_, gfx::Size(width, height));
|
||||
}
|
||||
|
||||
gfx::Size NativeWindowGtk::GetSize() {
|
||||
@@ -290,6 +344,22 @@ void NativeWindowGtk::UpdateDraggableRegions(
|
||||
}
|
||||
}
|
||||
|
||||
void NativeWindowGtk::HandleKeyboardEvent(
|
||||
content::WebContents*,
|
||||
const content::NativeWebKeyboardEvent& event) {
|
||||
if (event.type == WebKit::WebInputEvent::RawKeyDown) {
|
||||
GdkEventKey* os_event = reinterpret_cast<GdkEventKey*>(event.os_event);
|
||||
ui::Accelerator accelerator = ui::AcceleratorForGdkKeyCodeAndModifier(
|
||||
os_event->keyval, static_cast<GdkModifierType>(os_event->state));
|
||||
accelerator_util::TriggerAcceleratorTableCommand(&accelerator_table_,
|
||||
accelerator);
|
||||
}
|
||||
}
|
||||
|
||||
void NativeWindowGtk::ActiveWindowChanged(GdkWindow* active_window) {
|
||||
is_active_ = gtk_widget_get_window(GTK_WIDGET(window_)) == active_window;
|
||||
}
|
||||
|
||||
void NativeWindowGtk::RegisterAccelerators() {
|
||||
DCHECK(menu_);
|
||||
accelerator_table_.clear();
|
||||
@@ -448,13 +518,6 @@ gboolean NativeWindowGtk::OnButtonPress(GtkWidget* widget,
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
gboolean NativeWindowGtk::OnKeyPress(GtkWidget* widget, GdkEventKey* event) {
|
||||
ui::Accelerator accelerator = ui::AcceleratorForGdkKeyCodeAndModifier(
|
||||
event->keyval, static_cast<GdkModifierType>(event->state));
|
||||
return accelerator_util::TriggerAcceleratorTableCommand(
|
||||
&accelerator_table_, accelerator) ? TRUE: FALSE;
|
||||
}
|
||||
|
||||
// static
|
||||
NativeWindow* NativeWindow::Create(content::WebContents* web_contents,
|
||||
base::DictionaryValue* options) {
|
||||
|
||||
@@ -16,12 +16,14 @@
|
||||
#include "third_party/skia/include/core/SkRegion.h"
|
||||
#include "ui/base/accelerators/accelerator.h"
|
||||
#include "ui/base/gtk/gtk_signal.h"
|
||||
#include "ui/base/x/active_window_watcher_x_observer.h"
|
||||
#include "ui/gfx/size.h"
|
||||
|
||||
namespace atom {
|
||||
|
||||
class NativeWindowGtk : public NativeWindow,
|
||||
public MenuGtk::Delegate {
|
||||
public MenuGtk::Delegate,
|
||||
public ui::ActiveWindowWatcherXObserver {
|
||||
public:
|
||||
explicit NativeWindowGtk(content::WebContents* web_contents,
|
||||
base::DictionaryValue* options);
|
||||
@@ -69,6 +71,14 @@ class NativeWindowGtk : public NativeWindow,
|
||||
virtual void UpdateDraggableRegions(
|
||||
const std::vector<DraggableRegion>& regions) OVERRIDE;
|
||||
|
||||
// Overridden from content::WebContentsDelegate:
|
||||
virtual void HandleKeyboardEvent(
|
||||
content::WebContents*,
|
||||
const content::NativeWebKeyboardEvent&) OVERRIDE;
|
||||
|
||||
// Overridden from ActiveWindowWatcherXObserver.
|
||||
virtual void ActiveWindowChanged(GdkWindow* active_window) OVERRIDE;
|
||||
|
||||
private:
|
||||
// Register accelerators supported by the menu model.
|
||||
void RegisterAccelerators();
|
||||
@@ -96,9 +106,6 @@ class NativeWindowGtk : public NativeWindow,
|
||||
CHROMEGTK_CALLBACK_1(NativeWindowGtk, gboolean, OnButtonPress,
|
||||
GdkEventButton*);
|
||||
|
||||
// Key press event callback.
|
||||
CHROMEGTK_CALLBACK_1(NativeWindowGtk, gboolean, OnKeyPress, GdkEventKey*);
|
||||
|
||||
GtkWindow* window_;
|
||||
GtkWidget* vbox_;
|
||||
|
||||
@@ -111,10 +118,20 @@ class NativeWindowGtk : public NativeWindow,
|
||||
// clicked to maximize.
|
||||
scoped_ptr<SkRegion> draggable_region_;
|
||||
|
||||
// True if the window manager thinks the window is active. It could happpen
|
||||
// that the WM thinks a window is active but it's actually not, like when
|
||||
// showing a context menu.
|
||||
bool is_active_;
|
||||
|
||||
// If true, don't call gdk_window_raise() when we get a click in the title
|
||||
// bar or window border. This is to work around a compiz bug.
|
||||
bool suppress_window_raise_;
|
||||
|
||||
// True if the window has been visible for once, on Linux the window frame
|
||||
// would // only be considered as part of the window untill the window has
|
||||
// been shown, so we need it to correctly set the window size.
|
||||
bool has_ever_been_shown_;
|
||||
|
||||
// The current window cursor. We set it to a resize cursor when over the
|
||||
// custom frame border. We set it to NULL if we want the default cursor.
|
||||
GdkCursor* frame_cursor_;
|
||||
|
||||
@@ -199,7 +199,8 @@ NativeWindowMac::NativeWindowMac(content::WebContents* web_contents,
|
||||
|
||||
NativeWindowMac::~NativeWindowMac() {
|
||||
if (window())
|
||||
[window() release];
|
||||
// Use autorelease since we may have delegates or observers at this time.
|
||||
[window() autorelease];
|
||||
}
|
||||
|
||||
void NativeWindowMac::Close() {
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
<key>CFBundleIconFile</key>
|
||||
<string>atom.icns</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>0.11.1</string>
|
||||
<string>0.11.7</string>
|
||||
<key>NSMainNibFile</key>
|
||||
<string>MainMenu</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
|
||||
@@ -50,8 +50,8 @@ END
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION 0,11,1,0
|
||||
PRODUCTVERSION 0,11,1,0
|
||||
FILEVERSION 0,11,7,0
|
||||
PRODUCTVERSION 0,11,7,0
|
||||
FILEFLAGSMASK 0x3fL
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
@@ -68,12 +68,12 @@ BEGIN
|
||||
BEGIN
|
||||
VALUE "CompanyName", "GitHub, Inc."
|
||||
VALUE "FileDescription", "Atom-Shell"
|
||||
VALUE "FileVersion", "0.11.1"
|
||||
VALUE "FileVersion", "0.11.7"
|
||||
VALUE "InternalName", "atom.exe"
|
||||
VALUE "LegalCopyright", "Copyright (C) 2013 GitHub, Inc. All rights reserved."
|
||||
VALUE "OriginalFilename", "atom.exe"
|
||||
VALUE "ProductName", "Atom-Shell"
|
||||
VALUE "ProductVersion", "0.11.1"
|
||||
VALUE "ProductVersion", "0.11.7"
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
|
||||
@@ -11,6 +11,8 @@
|
||||
|
||||
#if defined(TOOLKIT_GTK)
|
||||
#include "base/command_line.h"
|
||||
#include "base/environment.h"
|
||||
#include "base/nix/xdg_util.h"
|
||||
#include "ui/gfx/gtk_util.h"
|
||||
#endif
|
||||
|
||||
@@ -25,7 +27,23 @@ namespace api {
|
||||
|
||||
namespace {
|
||||
|
||||
v8::Handle<v8::Object> DisplayToV8Value(const gfx::Display& display) {
|
||||
gfx::Display AdaptToWindowManager(const gfx::Display& display) {
|
||||
gfx::Display changed(display);
|
||||
#if defined(TOOLKIT_GTK)
|
||||
scoped_ptr<base::Environment> env(base::Environment::Create());
|
||||
base::nix::DesktopEnvironment de(base::nix::GetDesktopEnvironment(env.get()));
|
||||
if (de == base::nix::DESKTOP_ENVIRONMENT_UNITY) {
|
||||
// Unity's 24px global menu bar should not be included in the work area.
|
||||
gfx::Rect rect(changed.work_area());
|
||||
rect.set_height(rect.height() - 24);
|
||||
changed.set_work_area(rect);
|
||||
}
|
||||
#endif
|
||||
return changed;
|
||||
}
|
||||
|
||||
v8::Handle<v8::Object> DisplayToV8Value(const gfx::Display& raw) {
|
||||
gfx::Display display(AdaptToWindowManager(raw));
|
||||
v8::Handle<v8::Object> obj = v8::Object::New();
|
||||
obj->Set(ToV8Value("bounds"), ToV8Value(display.bounds()));
|
||||
obj->Set(ToV8Value("workArea"), ToV8Value(display.work_area()));
|
||||
|
||||
@@ -1 +1,6 @@
|
||||
module.exports = process.atomBinding 'clipboard'
|
||||
module.exports =
|
||||
if process.platform is 'linux'
|
||||
# On Linux we could not access clipboard in renderer process.
|
||||
require('remote').process.atomBinding 'clipboard'
|
||||
else
|
||||
process.atomBinding 'clipboard'
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||
#define ATOM_MAJOR_VERSION 0
|
||||
#define ATOM_MINOR_VERSION 11
|
||||
#define ATOM_PATCH_VERSION 1
|
||||
#define ATOM_PATCH_VERSION 7
|
||||
|
||||
#define ATOM_VERSION_IS_RELEASE 1
|
||||
|
||||
|
||||
@@ -28,9 +28,6 @@ const char* kSecurityManualEnableIframe = "manual-enable-iframe";
|
||||
const char* kSecurityDisable = "disable";
|
||||
const char* kSecurityEnableNodeIntegration = "enable-node-integration";
|
||||
|
||||
// Scheme used by devtools
|
||||
const char* kChromeDevToolsScheme = "chrome-devtools";
|
||||
|
||||
} // namespace
|
||||
|
||||
AtomRendererClient::AtomRendererClient()
|
||||
@@ -159,10 +156,6 @@ bool AtomRendererClient::ShouldFork(WebKit::WebFrame* frame,
|
||||
bool AtomRendererClient::IsNodeBindingEnabled(WebKit::WebFrame* frame) {
|
||||
if (node_integration_ == DISABLE)
|
||||
return false;
|
||||
// Do not pollute devtools.
|
||||
else if (frame != NULL &&
|
||||
GURL(frame->document().url()).SchemeIs(kChromeDevToolsScheme))
|
||||
return false;
|
||||
// Node integration is enabled in main frame unless explictly disabled.
|
||||
else if (frame == main_frame_)
|
||||
return true;
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
path = require 'path'
|
||||
url = require 'url'
|
||||
Module = require 'module'
|
||||
|
||||
# Expose information of current process.
|
||||
@@ -42,5 +43,9 @@ else
|
||||
global.__filename = __filename
|
||||
global.__dirname = __dirname
|
||||
|
||||
# Override default web functions.
|
||||
require path.join(__dirname, 'override')
|
||||
if location.protocol is 'chrome-devtools:'
|
||||
# Override some inspector APIs.
|
||||
require path.join(__dirname, 'inspector')
|
||||
else
|
||||
# Override default web functions.
|
||||
require path.join(__dirname, 'override')
|
||||
|
||||
61
atom/renderer/lib/inspector.coffee
Normal file
61
atom/renderer/lib/inspector.coffee
Normal file
@@ -0,0 +1,61 @@
|
||||
window.onload = ->
|
||||
# Use menu API to show context menu.
|
||||
WebInspector.ContextMenu.prototype.show = ->
|
||||
menuObject = @_buildDescriptor()
|
||||
if menuObject.length
|
||||
WebInspector._contextMenu = this
|
||||
createMenu(menuObject, @_event)
|
||||
@_event.consume()
|
||||
|
||||
# Use dialog API to override file chooser dialog.
|
||||
WebInspector.createFileSelectorElement = (callback) ->
|
||||
fileSelectorElement = document.createElement 'span'
|
||||
fileSelectorElement.style.display = 'none'
|
||||
fileSelectorElement.click = showFileChooserDialog.bind this, callback
|
||||
return fileSelectorElement
|
||||
|
||||
convertToMenuTemplate = (items) ->
|
||||
template = []
|
||||
for item in items
|
||||
do (item) ->
|
||||
transformed =
|
||||
if item.type is 'subMenu'
|
||||
type: 'submenu'
|
||||
label: item.label
|
||||
enabled: item.enabled
|
||||
submenu: convertToMenuTemplate item.subItems
|
||||
else if item.type is 'separator'
|
||||
type: 'separator'
|
||||
else if item.type is 'checkbox'
|
||||
type: 'checkbox'
|
||||
label: item.label
|
||||
enabled: item.enabled
|
||||
checked: item.checked
|
||||
else
|
||||
type: 'normal'
|
||||
label: item.label
|
||||
enabled: item.enabled
|
||||
if item.id?
|
||||
transformed.click = -> WebInspector.contextMenuItemSelected item.id
|
||||
template.push transformed
|
||||
template
|
||||
|
||||
createMenu = (items, event) ->
|
||||
remote = require 'remote'
|
||||
Menu = remote.require 'menu'
|
||||
|
||||
menu = Menu.buildFromTemplate convertToMenuTemplate(items)
|
||||
menu.popup remote.getCurrentWindow()
|
||||
event.consume true
|
||||
|
||||
showFileChooserDialog = (callback) ->
|
||||
remote = require 'remote'
|
||||
dialog = remote.require 'dialog'
|
||||
dialog.showOpenDialog remote.getCurrentWindow(), null, (files) ->
|
||||
callback pathToHtml5FileObject(files[0]) if files?
|
||||
|
||||
pathToHtml5FileObject = (path) ->
|
||||
fs = require 'fs'
|
||||
blob = new Blob([fs.readFileSync(path)])
|
||||
blob.name = path
|
||||
blob
|
||||
@@ -334,6 +334,13 @@ Closes the developer tools.
|
||||
|
||||
Starts inspecting element at position (`x`, `y`).
|
||||
|
||||
### BrowserWindow.executeJavaScriptInDevTools(code)
|
||||
|
||||
* `code` String
|
||||
|
||||
Evaluate `code` in devtools to use
|
||||
[InspectorFrontendAPI](https://code.google.com/p/chromium/codesearch#chromium/src/third_party/WebKit/Source/devtools/front_end/InspectorFrontendAPI.js&q=InspectorFrontendAPI&sq=package:chromium&type=cs)
|
||||
|
||||
### BrowserWindow.focusOnWebView()
|
||||
|
||||
### BrowserWindow.blurWebView()
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "atom-shell",
|
||||
"version": "0.11.1",
|
||||
"version": "0.11.7",
|
||||
|
||||
"devDependencies": {
|
||||
"coffee-script": "~1.6.3",
|
||||
|
||||
@@ -6,7 +6,7 @@ import subprocess
|
||||
import sys
|
||||
|
||||
from lib.config import LIBCHROMIUMCONTENT_COMMIT, BASE_URL
|
||||
from lib.util import scoped_cwd
|
||||
from lib.util import execute, scoped_cwd
|
||||
|
||||
|
||||
SOURCE_ROOT = os.path.abspath(os.path.dirname(os.path.dirname(__file__)))
|
||||
@@ -41,25 +41,27 @@ def parse_args():
|
||||
|
||||
|
||||
def update_submodules():
|
||||
subprocess.check_call(['git', 'submodule', 'sync', '--quiet'])
|
||||
subprocess.check_call(['git', 'submodule', 'update', '--init',
|
||||
'--recursive'])
|
||||
execute(['git', 'submodule', 'sync'])
|
||||
execute(['git', 'submodule', 'update', '--init', '--recursive'])
|
||||
|
||||
|
||||
def bootstrap_brightray(url):
|
||||
bootstrap = os.path.join(VENDOR_DIR, 'brightray', 'script', 'bootstrap')
|
||||
subprocess.check_call([sys.executable, bootstrap, '--commit',
|
||||
LIBCHROMIUMCONTENT_COMMIT, url])
|
||||
execute([sys.executable, bootstrap, '--commit', LIBCHROMIUMCONTENT_COMMIT,
|
||||
url])
|
||||
|
||||
|
||||
def update_apm():
|
||||
## NB: Without this, subprocess incorrectly searches for npm.exe
|
||||
npm_cmd = 'npm'
|
||||
if sys.platform in ['win32', 'cygwin']:
|
||||
npm_cmd += '.cmd'
|
||||
npm = 'npm.cmd' if sys.platform == 'win32' else 'npm'
|
||||
|
||||
if os.environ.get('CI') == '1':
|
||||
execute([npm, 'install', 'npm'])
|
||||
npm = os.path.join(SOURCE_ROOT, 'node_modules', '.bin', 'npm')
|
||||
if sys.platform == 'win32':
|
||||
npm += '.cmd'
|
||||
|
||||
with scoped_cwd(os.path.join('vendor', 'apm')):
|
||||
subprocess.check_call([npm_cmd, 'install', '.'])
|
||||
execute([npm, 'install', '.'])
|
||||
|
||||
|
||||
def update_node_modules():
|
||||
@@ -70,16 +72,15 @@ def update_node_modules():
|
||||
def update_node_modules_for_dir(dirname):
|
||||
with scoped_cwd(dirname):
|
||||
apm = os.path.join(SOURCE_ROOT, 'vendor', 'apm', 'bin', 'apm')
|
||||
subprocess.check_call(['node', os.path.relpath(apm), 'install'])
|
||||
if sys.platform in ['win32', 'cygwin']:
|
||||
apm += '.cmd'
|
||||
subprocess.check_call([apm, 'install'])
|
||||
|
||||
|
||||
def update_win32_python():
|
||||
with scoped_cwd(VENDOR_DIR):
|
||||
if not os.path.exists('python_26'):
|
||||
subprocess.check_call(['git', 'clone', PYTHON_26_URL])
|
||||
else:
|
||||
with scoped_cwd('python_26'):
|
||||
subprocess.check_call(['git', 'pull', '--rebase', 'origin', 'master'])
|
||||
execute(['git', 'clone', PYTHON_26_URL])
|
||||
|
||||
|
||||
def touch_config_gypi():
|
||||
@@ -92,7 +93,7 @@ def touch_config_gypi():
|
||||
|
||||
def update_atom_shell():
|
||||
update = os.path.join(SOURCE_ROOT, 'script', 'update.py')
|
||||
subprocess.check_call([sys.executable, update])
|
||||
execute([sys.executable, update])
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
@@ -2,10 +2,9 @@
|
||||
|
||||
import os
|
||||
import re
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
from lib.util import get_atom_shell_version, scoped_cwd
|
||||
from lib.util import execute, get_atom_shell_version, scoped_cwd
|
||||
|
||||
|
||||
SOURCE_ROOT = os.path.abspath(os.path.dirname(os.path.dirname(__file__)))
|
||||
@@ -126,13 +125,13 @@ def update_info_plist(version):
|
||||
|
||||
|
||||
def tag_version(version):
|
||||
subprocess.check_call(['git', 'commit', '-a', '-m',
|
||||
'Bump v{0}.'.format(version)])
|
||||
subprocess.check_call(['git', 'tag', 'v{0}'.format(version)])
|
||||
execute(['git', 'commit', '-a', '-m', 'Bump v{0}.'.format(version)])
|
||||
execute(['git', 'tag', 'v{0}'.format(version)])
|
||||
|
||||
|
||||
def git_push():
|
||||
subprocess.check_call(['git', 'push', '--follow-tags'])
|
||||
execute(['git', 'push'])
|
||||
execute(['git', 'push', '--tags'])
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
@@ -27,7 +27,6 @@ def main():
|
||||
run_script('coffeelint.py')
|
||||
run_script('build.py')
|
||||
run_script('test.py', ['--ci'])
|
||||
run_script('create-dist.py')
|
||||
|
||||
|
||||
def run_script(script, args=[]):
|
||||
|
||||
2
vendor/apm
vendored
2
vendor/apm
vendored
Submodule vendor/apm updated: 90cd546860...2ce1206e67
2
vendor/brightray
vendored
2
vendor/brightray
vendored
Submodule vendor/brightray updated: 1a8afaa871...dab731f232
2
vendor/node
vendored
2
vendor/node
vendored
Submodule vendor/node updated: 38862fe819...a926cced2d
Reference in New Issue
Block a user