mirror of
https://bitbucket.org/chromiumembedded/cef
synced 2025-02-02 12:17:15 +01:00
Add support for modal dialogs (issue #250).
git-svn-id: https://chromiumembedded.googlecode.com/svn/trunk@255 5089003a-bbd8-11dd-ad1f-f1f9622dbc98
This commit is contained in:
parent
d757adb020
commit
02d6f3e384
@ -612,6 +612,14 @@ public:
|
||||
/*--cef()--*/
|
||||
virtual CefWindowHandle GetWindowHandle() =0;
|
||||
|
||||
///
|
||||
// Retrieve the window handle of the browser that opened this browser. Will
|
||||
// return NULL for non-popup windows. This method can be used in combination
|
||||
// with custom handling of modal windows.
|
||||
///
|
||||
/*--cef()--*/
|
||||
virtual CefWindowHandle GetOpenerWindowHandle() =0;
|
||||
|
||||
///
|
||||
// Returns true if the window is a popup window.
|
||||
///
|
||||
@ -972,10 +980,28 @@ public:
|
||||
virtual void OnAfterCreated(CefRefPtr<CefBrowser> browser) {}
|
||||
|
||||
///
|
||||
// Called just before a window is closed.
|
||||
// Called just before a window is closed. If this is a modal window and you
|
||||
// handled the RunModal() event you can use this callback to restore
|
||||
// the opener window to a usable state.
|
||||
///
|
||||
/*--cef()--*/
|
||||
virtual void OnBeforeClose(CefRefPtr<CefBrowser> browser) {}
|
||||
|
||||
///
|
||||
// Called to enter the modal loop. Provide your own modal loop here. Return
|
||||
// true if you ran your own modal loop and false to use the default. You can
|
||||
// also use this event to know when a modal window is about to start.
|
||||
///
|
||||
/*--cef()--*/
|
||||
virtual bool RunModal(CefRefPtr<CefBrowser> browser) { return false; }
|
||||
|
||||
///
|
||||
// Called when a modal browser window has been destroyed. You must implement
|
||||
// this if you are handling RunModal(). You can also use this event to know
|
||||
// when a modal window is about to be closed.
|
||||
///
|
||||
/*--cef()--*/
|
||||
virtual void QuitModal(CefRefPtr<CefBrowser> browser) { }
|
||||
};
|
||||
|
||||
|
||||
|
@ -451,6 +451,14 @@ typedef struct _cef_browser_t
|
||||
cef_window_handle_t (CEF_CALLBACK *get_window_handle)(
|
||||
struct _cef_browser_t* self);
|
||||
|
||||
///
|
||||
// Retrieve the window handle of the browser that opened this browser. Will
|
||||
// return NULL for non-popup windows. This function can be used in combination
|
||||
// with custom handling of modal windows.
|
||||
///
|
||||
cef_window_handle_t (CEF_CALLBACK *get_opener_window_handle)(
|
||||
struct _cef_browser_t* self);
|
||||
|
||||
///
|
||||
// Returns true (1) if the window is a popup window.
|
||||
///
|
||||
@ -815,11 +823,29 @@ typedef struct _cef_life_span_handler_t
|
||||
struct _cef_browser_t* browser);
|
||||
|
||||
///
|
||||
// Called just before a window is closed.
|
||||
// Called just before a window is closed. If this is a modal window and you
|
||||
// handled the run_modal() event you can use this callback to restore the
|
||||
// opener window to a usable state.
|
||||
///
|
||||
void (CEF_CALLBACK *on_before_close)(struct _cef_life_span_handler_t* self,
|
||||
struct _cef_browser_t* browser);
|
||||
|
||||
///
|
||||
// Called to enter the modal loop. Provide your own modal loop here. Return
|
||||
// true (1) if you ran your own modal loop and false (0) to use the default.
|
||||
// You can also use this event to know when a modal window is about to start.
|
||||
///
|
||||
int (CEF_CALLBACK *run_modal)(struct _cef_life_span_handler_t* self,
|
||||
struct _cef_browser_t* browser);
|
||||
|
||||
///
|
||||
// Called when a modal browser window has been destroyed. You must implement
|
||||
// this if you are handling run_modal(). You can also use this event to know
|
||||
// when a modal window is about to be closed.
|
||||
///
|
||||
void (CEF_CALLBACK *quit_modal)(struct _cef_life_span_handler_t* self,
|
||||
struct _cef_browser_t* browser);
|
||||
|
||||
} cef_life_span_handler_t;
|
||||
|
||||
|
||||
|
@ -150,7 +150,7 @@ CefRefPtr<CefBrowser> CefBrowser::CreateBrowserSync(
|
||||
}
|
||||
|
||||
CefRefPtr<CefBrowser> browser(
|
||||
new CefBrowserImpl(windowInfo, settings, false, client));
|
||||
new CefBrowserImpl(windowInfo, settings, NULL, client));
|
||||
static_cast<CefBrowserImpl*>(browser.get())->UIT_CreateBrowser(url);
|
||||
|
||||
return browser;
|
||||
@ -158,12 +158,17 @@ CefRefPtr<CefBrowser> CefBrowser::CreateBrowserSync(
|
||||
|
||||
|
||||
CefBrowserImpl::CefBrowserImpl(const CefWindowInfo& windowInfo,
|
||||
const CefBrowserSettings& settings, bool popup,
|
||||
const CefBrowserSettings& settings,
|
||||
gfx::NativeView opener,
|
||||
CefRefPtr<CefClient> client)
|
||||
: window_info_(windowInfo), settings_(settings), is_popup_(popup),
|
||||
: window_info_(windowInfo), settings_(settings), opener_(opener),
|
||||
is_modal_(false), client_(client), webviewhost_(NULL), popuphost_(NULL),
|
||||
zoom_level_(0.0), can_go_back_(false), can_go_forward_(false),
|
||||
main_frame_(NULL), unique_id_(0)
|
||||
#if defined(OS_WIN)
|
||||
, opener_was_disabled_by_modal_loop_(false),
|
||||
internal_modal_message_loop_is_active_(false)
|
||||
#endif
|
||||
{
|
||||
delegate_.reset(new BrowserWebViewDelegate(this));
|
||||
popup_delegate_.reset(new BrowserWebViewDelegate(this));
|
||||
@ -674,13 +679,28 @@ WebFrame* CefBrowserImpl::UIT_GetWebFrame(CefRefPtr<CefFrame> frame)
|
||||
|
||||
void CefBrowserImpl::UIT_DestroyBrowser()
|
||||
{
|
||||
if(client_.get()) {
|
||||
CefRefPtr<CefLifeSpanHandler> handler = client_->GetLifeSpanHandler();
|
||||
if (handler.get()) {
|
||||
// Notify the handler that the window is about to be closed.
|
||||
handler->OnBeforeClose(this);
|
||||
#if defined(OS_WIN)
|
||||
if (is_modal_) {
|
||||
// Exit our own internal modal message loop now.
|
||||
if (internal_modal_message_loop_is_active_) {
|
||||
MessageLoop* message_loop = MessageLoop::current();
|
||||
message_loop->QuitNow();
|
||||
}
|
||||
|
||||
// If the client implemented its own modal loop then the above would not
|
||||
// run, so this call is for the client to exit its loop. Otherwise,
|
||||
// QuitModal can be used to let clients know that the modal loop is about
|
||||
// to exit.
|
||||
if (client_.get()) {
|
||||
CefRefPtr<CefLifeSpanHandler> handler = client_->GetLifeSpanHandler();
|
||||
if (handler.get()) {
|
||||
// Notify the handler that it can exit its modal loop if it was in one.
|
||||
handler->QuitModal(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
UIT_GetWebViewDelegate()->RevokeDragDrop();
|
||||
|
||||
// If the current browser window is a dev tools client then disconnect from
|
||||
@ -705,7 +725,7 @@ void CefBrowserImpl::UIT_DestroyBrowser()
|
||||
// Clean up anything associated with the WebViewHost widget.
|
||||
UIT_GetWebViewHost()->webwidget()->close();
|
||||
webviewhost_.reset();
|
||||
|
||||
|
||||
// Remove the reference added in UIT_CreateBrowser().
|
||||
Release();
|
||||
|
||||
@ -716,10 +736,20 @@ void CefBrowserImpl::UIT_DestroyBrowser()
|
||||
void CefBrowserImpl::UIT_CloseBrowser()
|
||||
{
|
||||
REQUIRE_UIT();
|
||||
if (!IsWindowRenderingDisabled())
|
||||
UIT_CloseView(UIT_GetMainWndHandle());
|
||||
else
|
||||
if (IsWindowRenderingDisabled()) {
|
||||
// There is no window here so we need to notify the client that this
|
||||
// browser instance is about to go away.
|
||||
if (client_.get()) {
|
||||
CefRefPtr<CefLifeSpanHandler> handler = client_->GetLifeSpanHandler();
|
||||
if (handler.get()) {
|
||||
// Notify the handler that the window is about to be closed.
|
||||
handler->OnBeforeClose(this);
|
||||
}
|
||||
}
|
||||
UIT_DestroyBrowser();
|
||||
} else {
|
||||
UIT_CloseView(UIT_GetMainWndHandle());
|
||||
}
|
||||
}
|
||||
|
||||
void CefBrowserImpl::UIT_LoadURL(CefRefPtr<CefFrame> frame,
|
||||
@ -1082,8 +1112,11 @@ CefRefPtr<CefBrowserImpl> CefBrowserImpl::UIT_CreatePopupWindow(
|
||||
}
|
||||
}
|
||||
|
||||
// Modal windows need to know which window is being suspended (the opener)
|
||||
// so that it can be disabled while the modal window is open.
|
||||
CefRefPtr<CefBrowserImpl> browser(
|
||||
new CefBrowserImpl(info, settings, true, client));
|
||||
new CefBrowserImpl(info, settings, UIT_GetMainWndHandle(), client));
|
||||
|
||||
// Don't pass the URL to UIT_CreateBrowser for popup windows or the URL will
|
||||
// be loaded twice.
|
||||
browser->UIT_CreateBrowser(CefString());
|
||||
|
@ -50,7 +50,8 @@ public:
|
||||
};
|
||||
|
||||
CefBrowserImpl(const CefWindowInfo& windowInfo,
|
||||
const CefBrowserSettings& settings, bool popup,
|
||||
const CefBrowserSettings& settings,
|
||||
gfx::NativeView opener,
|
||||
CefRefPtr<CefClient> client);
|
||||
virtual ~CefBrowserImpl() {}
|
||||
|
||||
@ -71,6 +72,8 @@ public:
|
||||
virtual void StopLoad() OVERRIDE;
|
||||
virtual void SetFocus(bool enable) OVERRIDE;
|
||||
virtual CefWindowHandle GetWindowHandle() OVERRIDE;
|
||||
virtual CefWindowHandle GetOpenerWindowHandle() OVERRIDE
|
||||
{ return opener_window(); }
|
||||
virtual bool IsPopup() OVERRIDE { return is_popup(); }
|
||||
virtual CefRefPtr<CefClient> GetClient() OVERRIDE { return client_; }
|
||||
virtual CefRefPtr<CefFrame> GetMainFrame() OVERRIDE
|
||||
@ -309,7 +312,8 @@ public:
|
||||
// These variables are read-only.
|
||||
const CefBrowserSettings& settings() const { return settings_; }
|
||||
const FilePath& file_system_root() const { return file_system_root_.path(); }
|
||||
bool is_popup() { return is_popup_; }
|
||||
gfx::NativeView opener_window() { return opener_; }
|
||||
bool is_popup() { return (opener_ != NULL); }
|
||||
|
||||
// These variables may be read/written from multiple threads.
|
||||
void set_zoom_level(double zoomLevel);
|
||||
@ -318,6 +322,17 @@ public:
|
||||
bool can_go_back();
|
||||
bool can_go_forward();
|
||||
|
||||
#if defined(OS_WIN)
|
||||
void set_opener_was_disabled_by_modal_loop(bool disabled)
|
||||
{
|
||||
opener_was_disabled_by_modal_loop_ = disabled;
|
||||
}
|
||||
void set_internal_modal_message_loop_is_active(bool active)
|
||||
{
|
||||
internal_modal_message_loop_is_active_ = active;
|
||||
}
|
||||
#endif
|
||||
|
||||
void set_popup_rect(const gfx::Rect& rect) { popup_rect_ = rect; }
|
||||
|
||||
static bool ImplementsThreadSafeReferenceCounting() { return true; }
|
||||
@ -332,7 +347,8 @@ protected:
|
||||
protected:
|
||||
CefWindowInfo window_info_;
|
||||
CefBrowserSettings settings_;
|
||||
bool is_popup_;
|
||||
// Handle of the browser window that opened this window.
|
||||
gfx::NativeView opener_;
|
||||
bool is_modal_;
|
||||
CefRefPtr<CefClient> client_;
|
||||
scoped_ptr<WebViewHost> webviewhost_;
|
||||
@ -355,6 +371,10 @@ protected:
|
||||
#if defined(OS_WIN)
|
||||
// Context object used to manage printing.
|
||||
printing::PrintingContext print_context_;
|
||||
|
||||
// Used to re-enable the opener when a modal window gets closed.
|
||||
bool opener_was_disabled_by_modal_loop_;
|
||||
bool internal_modal_message_loop_is_active_;
|
||||
#endif
|
||||
|
||||
typedef std::map<CefString, CefFrame*> FrameMap;
|
||||
|
@ -38,6 +38,35 @@ LRESULT CALLBACK CefBrowserImpl::WndProc(HWND hwnd, UINT message,
|
||||
static_cast<CefBrowserImpl*>(ui::GetWindowUserData(hwnd));
|
||||
|
||||
switch (message) {
|
||||
case WM_CLOSE:
|
||||
// It is the responsibility of the client to send this message to this
|
||||
// window if it is created as a child window of a client's frame window.
|
||||
// This is particularly important when this window is modal.
|
||||
if(browser) {
|
||||
// Here the window really is about to get closed.
|
||||
if (browser->client_.get()) {
|
||||
CefRefPtr<CefLifeSpanHandler> handler =
|
||||
browser->client_->GetLifeSpanHandler();
|
||||
if (handler.get()) {
|
||||
// Notify the handler that the window is about to be closed.
|
||||
handler->OnBeforeClose(browser);
|
||||
}
|
||||
}
|
||||
|
||||
// We must re-enable the opener (owner of the modal window)
|
||||
// before we close the popup to avoid focus/activation/z-order issues.
|
||||
if (browser->opener_ && browser->opener_was_disabled_by_modal_loop_) {
|
||||
HWND owner = ::GetAncestor(browser->opener_, GA_ROOT);
|
||||
::EnableWindow(owner, TRUE);
|
||||
}
|
||||
|
||||
// Don't do the default if this is a contained window as the destruction
|
||||
// will occur when the parent frame window is destroyed.
|
||||
if (::GetAncestor(hwnd, GA_ROOT) != hwnd)
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_DESTROY:
|
||||
if (browser) {
|
||||
// Clear the user data pointer.
|
||||
|
@ -178,8 +178,48 @@ void BrowserWebViewDelegate::runModal() {
|
||||
|
||||
browser_->UIT_SetIsModal(true);
|
||||
|
||||
// TODO(CEF): Add a handler notification for modal windows so the client can
|
||||
// make the window behave modally.
|
||||
CefRefPtr<CefClient> client = browser_->GetClient();
|
||||
CefRefPtr<CefLifeSpanHandler> handler;
|
||||
|
||||
if( client.get())
|
||||
handler = client->GetLifeSpanHandler();
|
||||
|
||||
bool handled(false);
|
||||
|
||||
if (handler.get()) {
|
||||
// Let the client override the modal message loop.
|
||||
handled = handler->RunModal(browser_);
|
||||
}
|
||||
|
||||
if (!handled) {
|
||||
HWND child = ::GetAncestor(browser_->UIT_GetMainWndHandle(), GA_ROOT);
|
||||
HWND owner = ::GetAncestor(browser_->opener_window(), GA_ROOT);
|
||||
|
||||
if (child && owner) {
|
||||
// Set the owner so that Windows keeps this window above the owner.
|
||||
::SetWindowLong(child, GWL_HWNDPARENT, (LONG)owner);
|
||||
// Disable the owner if it is enabled so that you can't interact with it.
|
||||
// while this child window is open.
|
||||
if (::IsWindowEnabled(owner)) {
|
||||
::EnableWindow(owner, FALSE);
|
||||
browser_->set_opener_was_disabled_by_modal_loop(true);
|
||||
}
|
||||
DWORD dwStyle = ::GetWindowLong(child, GWL_STYLE);
|
||||
DWORD dwNewStyle = dwStyle | WS_POPUP;
|
||||
if(dwStyle != dwNewStyle)
|
||||
::SetWindowLong(child, GWL_STYLE, dwNewStyle);
|
||||
}
|
||||
|
||||
// Tell the browser to exit this message loop when this window closes.
|
||||
browser_->set_internal_modal_message_loop_is_active(true);
|
||||
|
||||
// Start a new message loop here and return when this window closes.
|
||||
MessageLoop* message_loop = MessageLoop::current();
|
||||
bool old_state = message_loop->NestableTasksAllowed();
|
||||
message_loop->SetNestableTasksAllowed(true);
|
||||
message_loop->Run();
|
||||
message_loop->SetNestableTasksAllowed(old_state);
|
||||
}
|
||||
}
|
||||
|
||||
// WebPluginPageDelegate ------------------------------------------------------
|
||||
|
@ -160,6 +160,16 @@ cef_window_handle_t CEF_CALLBACK browser_get_window_handle(
|
||||
return CefBrowserCppToC::Get(self)->GetWindowHandle();
|
||||
}
|
||||
|
||||
cef_window_handle_t CEF_CALLBACK browser_get_opener_window_handle(
|
||||
struct _cef_browser_t* self)
|
||||
{
|
||||
DCHECK(self);
|
||||
if(!self)
|
||||
return NULL;
|
||||
|
||||
return CefBrowserCppToC::Get(self)->GetOpenerWindowHandle();
|
||||
}
|
||||
|
||||
int CEF_CALLBACK browser_is_popup(struct _cef_browser_t* self)
|
||||
{
|
||||
DCHECK(self);
|
||||
@ -450,6 +460,7 @@ CefBrowserCppToC::CefBrowserCppToC(CefBrowser* cls)
|
||||
struct_.struct_.stop_load = browser_stop_load;
|
||||
struct_.struct_.set_focus = browser_set_focus;
|
||||
struct_.struct_.get_window_handle = browser_get_window_handle;
|
||||
struct_.struct_.get_opener_window_handle = browser_get_opener_window_handle;
|
||||
struct_.struct_.is_popup = browser_is_popup;
|
||||
struct_.struct_.get_client = browser_get_client;
|
||||
struct_.struct_.get_main_frame = browser_get_main_frame;
|
||||
|
@ -97,6 +97,30 @@ void CEF_CALLBACK life_span_handler_on_before_close(
|
||||
CefBrowserCToCpp::Wrap(browser));
|
||||
}
|
||||
|
||||
int CEF_CALLBACK life_span_handler_run_modal(
|
||||
struct _cef_life_span_handler_t* self, cef_browser_t* browser)
|
||||
{
|
||||
DCHECK(self);
|
||||
DCHECK(browser);
|
||||
if (!self || !browser)
|
||||
return 0;
|
||||
|
||||
return CefLifeSpanHandlerCppToC::Get(self)->RunModal(
|
||||
CefBrowserCToCpp::Wrap(browser));
|
||||
}
|
||||
|
||||
void CEF_CALLBACK life_span_handler_quit_modal(
|
||||
struct _cef_life_span_handler_t* self, cef_browser_t* browser)
|
||||
{
|
||||
DCHECK(self);
|
||||
DCHECK(browser);
|
||||
if (!self || !browser)
|
||||
return;
|
||||
|
||||
CefLifeSpanHandlerCppToC::Get(self)->QuitModal(
|
||||
CefBrowserCToCpp::Wrap(browser));
|
||||
}
|
||||
|
||||
|
||||
// CONSTRUCTOR - Do not edit by hand.
|
||||
|
||||
@ -107,6 +131,8 @@ CefLifeSpanHandlerCppToC::CefLifeSpanHandlerCppToC(CefLifeSpanHandler* cls)
|
||||
struct_.struct_.on_before_popup = life_span_handler_on_before_popup;
|
||||
struct_.struct_.on_after_created = life_span_handler_on_after_created;
|
||||
struct_.struct_.on_before_close = life_span_handler_on_before_close;
|
||||
struct_.struct_.run_modal = life_span_handler_run_modal;
|
||||
struct_.struct_.quit_modal = life_span_handler_quit_modal;
|
||||
}
|
||||
|
||||
#ifndef NDEBUG
|
||||
|
@ -120,6 +120,14 @@ CefWindowHandle CefBrowserCToCpp::GetWindowHandle()
|
||||
return struct_->get_window_handle(struct_);
|
||||
}
|
||||
|
||||
CefWindowHandle CefBrowserCToCpp::GetOpenerWindowHandle()
|
||||
{
|
||||
if (CEF_MEMBER_MISSING(struct_, get_opener_window_handle))
|
||||
return 0;
|
||||
|
||||
return struct_->get_opener_window_handle(struct_);
|
||||
}
|
||||
|
||||
bool CefBrowserCToCpp::IsPopup()
|
||||
{
|
||||
if(CEF_MEMBER_MISSING(struct_, is_popup))
|
||||
|
@ -41,6 +41,7 @@ public:
|
||||
virtual void StopLoad() OVERRIDE;
|
||||
virtual void SetFocus(bool enable) OVERRIDE;
|
||||
virtual CefWindowHandle GetWindowHandle() OVERRIDE;
|
||||
virtual CefWindowHandle GetOpenerWindowHandle() OVERRIDE;
|
||||
virtual bool IsPopup() OVERRIDE;
|
||||
virtual CefRefPtr<CefClient> GetClient() OVERRIDE;
|
||||
virtual CefRefPtr<CefFrame> GetMainFrame() OVERRIDE;
|
||||
|
@ -52,7 +52,7 @@ void CefLifeSpanHandlerCToCpp::OnAfterCreated(CefRefPtr<CefBrowser> browser)
|
||||
if (CEF_MEMBER_MISSING(struct_, on_after_created))
|
||||
return;
|
||||
|
||||
return struct_->on_after_created(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
struct_->on_after_created(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
}
|
||||
|
||||
void CefLifeSpanHandlerCToCpp::OnBeforeClose(CefRefPtr<CefBrowser> browser)
|
||||
@ -60,7 +60,25 @@ void CefLifeSpanHandlerCToCpp::OnBeforeClose(CefRefPtr<CefBrowser> browser)
|
||||
if (CEF_MEMBER_MISSING(struct_, on_before_close))
|
||||
return;
|
||||
|
||||
return struct_->on_before_close(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
struct_->on_before_close(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
}
|
||||
|
||||
bool CefLifeSpanHandlerCToCpp::RunModal(CefRefPtr<CefBrowser> browser)
|
||||
{
|
||||
if (CEF_MEMBER_MISSING(struct_, run_modal))
|
||||
return false;
|
||||
|
||||
int rv = struct_->run_modal(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
|
||||
return (rv ? true : false);
|
||||
}
|
||||
|
||||
void CefLifeSpanHandlerCToCpp::QuitModal(CefRefPtr<CefBrowser> browser)
|
||||
{
|
||||
if (CEF_MEMBER_MISSING(struct_, quit_modal))
|
||||
return;
|
||||
|
||||
struct_->quit_modal(struct_, CefBrowserCppToC::Wrap(browser));
|
||||
}
|
||||
|
||||
|
||||
|
@ -39,6 +39,8 @@ public:
|
||||
CefBrowserSettings& settings) OVERRIDE;
|
||||
virtual void OnAfterCreated(CefRefPtr<CefBrowser> browser) OVERRIDE;
|
||||
virtual void OnBeforeClose(CefRefPtr<CefBrowser> browser) OVERRIDE;
|
||||
virtual bool RunModal(CefRefPtr<CefBrowser> browser) OVERRIDE;
|
||||
virtual void QuitModal(CefRefPtr<CefBrowser> browser) OVERRIDE;
|
||||
};
|
||||
|
||||
#endif // BUILDING_CEF_SHARED
|
||||
|
@ -307,3 +307,8 @@ void RunDragDropTest(CefRefPtr<CefBrowser> browser)
|
||||
{
|
||||
browser->GetMainFrame()->LoadURL("http://html5demos.com/drag");
|
||||
}
|
||||
|
||||
void RunModalDialogTest(CefRefPtr<CefBrowser> browser)
|
||||
{
|
||||
browser->GetMainFrame()->LoadURL("http://tests/modalmain");
|
||||
}
|
||||
|
@ -31,5 +31,6 @@ void RunXMLHTTPRequestTest(CefRefPtr<CefBrowser> browser);
|
||||
void RunWebURLRequestTest(CefRefPtr<CefBrowser> browser);
|
||||
void RunDOMAccessTest(CefRefPtr<CefBrowser> browser);
|
||||
void RunDragDropTest(CefRefPtr<CefBrowser> browser);
|
||||
void RunModalDialogTest(CefRefPtr<CefBrowser> browser);
|
||||
|
||||
#endif // _CEFCLIENT_H
|
||||
|
@ -35,6 +35,8 @@ IDS_LOGOBALL BINARY "res\\logoball.png"
|
||||
IDS_LOCALSTORAGE BINARY "res\\localstorage.html"
|
||||
IDS_XMLHTTPREQUEST BINARY "res\\xmlhttprequest.html"
|
||||
IDS_DOMACCESS BINARY "res\\domaccess.html"
|
||||
IDS_MODALMAIN BINARY "res\\modalmain.html"
|
||||
IDS_MODALDIALOG BINARY "res\\modaldialog.html"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
@ -92,6 +94,7 @@ BEGIN
|
||||
MENUITEM "Reset Zoom", ID_TESTS_ZOOM_RESET
|
||||
MENUITEM "Show Developer Tools", ID_TESTS_DEVTOOLS_SHOW
|
||||
MENUITEM "Close Developer Tools", ID_TESTS_DEVTOOLS_CLOSE
|
||||
MENUITEM "Modal Dialog", ID_TESTS_MODALDIALOG
|
||||
END
|
||||
END
|
||||
|
||||
|
@ -560,6 +560,10 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
if (browser.get())
|
||||
browser->CloseDevTools();
|
||||
return 0;
|
||||
case ID_TESTS_MODALDIALOG:
|
||||
if(browser.get())
|
||||
RunModalDialogTest(browser);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -606,6 +610,18 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_CLOSE:
|
||||
// All clients must forward the WM_CLOSE call to all contained browser
|
||||
// windows to give those windows a chance to cleanup before the window
|
||||
// closes. Don't forward this message if you are cancelling the request.
|
||||
if(g_handler.get())
|
||||
{
|
||||
HWND hWnd = g_handler->GetBrowserHwnd();
|
||||
if (hWnd)
|
||||
::SendMessage(hWnd, WM_CLOSE, 0, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_DESTROY:
|
||||
// The frame window has exited
|
||||
|
@ -87,6 +87,14 @@ bool ClientHandler::OnBeforeResourceLoad(CefRefPtr<CefBrowser> browser,
|
||||
resourceStream = GetBinaryResourceReader(IDS_LOGOBALL);
|
||||
response->SetMimeType("image/png");
|
||||
response->SetStatus(200);
|
||||
} else if(url == "http://tests/modalmain") {
|
||||
resourceStream = GetBinaryResourceReader(IDS_MODALMAIN);
|
||||
response->SetMimeType("text/html");
|
||||
response->SetStatus(200);
|
||||
} else if(url == "http://tests/modaldialog") {
|
||||
resourceStream = GetBinaryResourceReader(IDS_MODALDIALOG);
|
||||
response->SetMimeType("text/html");
|
||||
response->SetStatus(200);
|
||||
}
|
||||
|
||||
return false;
|
||||
|
78
tests/cefclient/res/modaldialog.html
Normal file
78
tests/cefclient/res/modaldialog.html
Normal file
@ -0,0 +1,78 @@
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<title>A Modal Dialog</title>
|
||||
</head>
|
||||
<body>
|
||||
Argument:<input id="argument" type="text" size="32"><br>
|
||||
<br>
|
||||
Reply:<input id="reply" type="text" autofocus="autofocus" size="32"><br>
|
||||
<p>
|
||||
<button onclick="OnOK(false)">Cancel</button> <button onclick="OnOK(true)">OK</button>
|
||||
</p>
|
||||
<p id="time"></p>
|
||||
<script>
|
||||
|
||||
function init()
|
||||
{
|
||||
timer();
|
||||
setInterval(timer, 200);
|
||||
setValueToId('argument', dialogArguments.msg);
|
||||
}
|
||||
|
||||
function timer()
|
||||
{
|
||||
updateId("time",new Date().toLocaleString());
|
||||
}
|
||||
|
||||
function updateId(id, html, append)
|
||||
{
|
||||
id = document.getElementById(id);
|
||||
if (typeof html == "boolean")
|
||||
html = html?"Yes":"No";
|
||||
if (append)
|
||||
id.innerHTML += html + '<br>';
|
||||
else
|
||||
id.innerHTML = html;
|
||||
}
|
||||
|
||||
function setValueToId(id, v)
|
||||
{
|
||||
id = document.getElementById(id);
|
||||
id.value = v;
|
||||
}
|
||||
|
||||
function getValueFromId(id)
|
||||
{
|
||||
id = document.getElementById(id);
|
||||
if (id)
|
||||
return id.value;
|
||||
else
|
||||
return "";
|
||||
}
|
||||
|
||||
function OnOK(what)
|
||||
{
|
||||
if (what)
|
||||
returnValue = { dialogResult:true, msg: "'"+ getValueFromId('reply') + "'" };
|
||||
else
|
||||
returnValue = { dialogResult:false, msg:'(cancelled)' };
|
||||
window.close();
|
||||
}
|
||||
|
||||
function keydown(e)
|
||||
{
|
||||
if (!e) e= event;
|
||||
if (e.keyCode == 27) {
|
||||
OnOK(false);
|
||||
} else if (e.keyCode == 13) {
|
||||
OnOK(true);
|
||||
}
|
||||
}
|
||||
|
||||
document.addEventListener('keydown', keydown, false);
|
||||
window.addEventListener('load', init, false);
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
57
tests/cefclient/res/modalmain.html
Normal file
57
tests/cefclient/res/modalmain.html
Normal file
@ -0,0 +1,57 @@
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<title>Test Modal Dialog</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<h3>Test Modal Dialog</h3>
|
||||
Click this <button onclick="doModal()">button</button> to open a modal dialog.
|
||||
|
||||
<h3>Time (timers are suppresed while the modal dialog is open)</h3>
|
||||
<div id="time"></div>
|
||||
|
||||
<h3>Result Log</h3>
|
||||
<div id="result"></div>
|
||||
|
||||
<script>
|
||||
|
||||
function init()
|
||||
{
|
||||
timer();
|
||||
setInterval(timer, 200);
|
||||
}
|
||||
|
||||
function timer()
|
||||
{
|
||||
updateId("time",new Date().toLocaleString());
|
||||
}
|
||||
|
||||
function updateId(id, html, append)
|
||||
{
|
||||
id = document.getElementById(id);
|
||||
if (typeof html == "boolean")
|
||||
html = html?"Yes":"No";
|
||||
if (append)
|
||||
id.innerHTML += html + '<br>';
|
||||
else
|
||||
id.innerHTML = html;
|
||||
}
|
||||
|
||||
function doModal()
|
||||
{
|
||||
updateId('result', "Modal dialog is open...", true);
|
||||
var result = window.showModalDialog("http://tests/modaldialog", { msg:"Hi from parent"} );
|
||||
if (typeof result == "object") {
|
||||
updateId('result', "Result: " + result.msg, true);
|
||||
} else {
|
||||
updateId('result', "Dialog was closed", true);
|
||||
}
|
||||
}
|
||||
|
||||
window.addEventListener('load', init, false);
|
||||
|
||||
</script>
|
||||
|
||||
</body>
|
||||
</html>
|
@ -51,6 +51,7 @@
|
||||
#define ID_TESTS_DOMACCESS 32791
|
||||
#define ID_TESTS_DRAGDROP 32792
|
||||
#define ID_TESTS_OSRAPP 32793
|
||||
#define ID_TESTS_MODALDIALOG 32794
|
||||
#define IDC_STATIC -1
|
||||
#define IDS_LOGO 1000
|
||||
#define IDS_UIPLUGIN 1001
|
||||
@ -59,6 +60,8 @@
|
||||
#define IDS_XMLHTTPREQUEST 1004
|
||||
#define IDS_DOMACCESS 1005
|
||||
#define IDS_OSRPLUGIN 1006
|
||||
#define IDS_MODALMAIN 1007
|
||||
#define IDS_MODALDIALOG 1008
|
||||
|
||||
// Avoid files associated with MacOS
|
||||
#define _X86_
|
||||
@ -69,7 +72,7 @@
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NO_MFC 1
|
||||
#define _APS_NEXT_RESOURCE_VALUE 130
|
||||
#define _APS_NEXT_COMMAND_VALUE 32793
|
||||
#define _APS_NEXT_COMMAND_VALUE 32795
|
||||
#define _APS_NEXT_CONTROL_VALUE 1000
|
||||
#define _APS_NEXT_SYMED_VALUE 110
|
||||
#endif
|
||||
|
Loading…
x
Reference in New Issue
Block a user