mirror of
https://github.com/aseprite/aseprite.git
synced 2025-01-29 03:32:48 +00:00
Move drop files event to she library
This commit is contained in:
parent
be6b98995e
commit
1212906d5a
@ -105,7 +105,6 @@ add_library(app-lib
|
||||
document_location.cpp
|
||||
document_undo.cpp
|
||||
documents.cpp
|
||||
drop_files.cpp
|
||||
file/ase_format.cpp
|
||||
file/bmp_format.cpp
|
||||
file/file.cpp
|
||||
|
@ -32,7 +32,6 @@
|
||||
#include "app/document_exporter.h"
|
||||
#include "app/document_location.h"
|
||||
#include "app/document_observer.h"
|
||||
#include "app/drop_files.h"
|
||||
#include "app/file/file.h"
|
||||
#include "app/file/file_formats_manager.h"
|
||||
#include "app/file_system.h"
|
||||
@ -235,9 +234,6 @@ int App::run()
|
||||
|
||||
// Run the GUI
|
||||
if (isGui()) {
|
||||
// Support to drop files from Windows explorer
|
||||
install_drop_files();
|
||||
|
||||
#ifdef ENABLE_UPDATER
|
||||
// Launch the thread to check for updates.
|
||||
app::CheckUpdateThreadLauncher checkUpdate;
|
||||
@ -253,9 +249,6 @@ int App::run()
|
||||
// Run the GUI main message loop
|
||||
gui_run();
|
||||
|
||||
// Uninstall support to drop files
|
||||
uninstall_drop_files();
|
||||
|
||||
// Destroy all documents in the UIContext.
|
||||
const Documents& docs = m_modules->m_ui_context.getDocuments();
|
||||
while (!docs.empty())
|
||||
|
@ -1,163 +0,0 @@
|
||||
/* Aseprite
|
||||
* Copyright (C) 2001-2013 David Capello
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include "app/app.h"
|
||||
#include "app/ui/main_window.h"
|
||||
#include "base/mutex.h"
|
||||
#include "base/scoped_lock.h"
|
||||
#include "app/commands/commands.h"
|
||||
#include "app/commands/params.h"
|
||||
#include "ui/manager.h"
|
||||
#include "ui/window.h"
|
||||
#include "app/ui_context.h"
|
||||
|
||||
#include <allegro.h>
|
||||
#include <vector>
|
||||
|
||||
#ifdef ALLEGRO_WINDOWS
|
||||
#include <winalleg.h>
|
||||
|
||||
#if defined STRICT || defined __GNUC__
|
||||
typedef WNDPROC wndproc_t;
|
||||
#else
|
||||
typedef FARPROC wndproc_t;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
namespace app {
|
||||
|
||||
#ifdef ALLEGRO_WINDOWS
|
||||
|
||||
static wndproc_t base_wnd_proc = NULL;
|
||||
static std::vector<base::string>* dropped_files;
|
||||
static base::mutex* dropped_files_mutex = NULL;
|
||||
|
||||
static void subclass_hwnd();
|
||||
static void unsubclass_hwnd();
|
||||
static LRESULT CALLBACK ase_wnd_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam);
|
||||
|
||||
void install_drop_files()
|
||||
{
|
||||
dropped_files = new std::vector<base::string>();
|
||||
dropped_files_mutex = new base::mutex();
|
||||
|
||||
subclass_hwnd();
|
||||
}
|
||||
|
||||
void uninstall_drop_files()
|
||||
{
|
||||
unsubclass_hwnd();
|
||||
|
||||
delete dropped_files_mutex;
|
||||
dropped_files_mutex = NULL;
|
||||
|
||||
delete dropped_files;
|
||||
}
|
||||
|
||||
void check_for_dropped_files()
|
||||
{
|
||||
if (!base_wnd_proc) // drop-files hook not installed
|
||||
return;
|
||||
|
||||
// If the main window is not the current foreground one. We discard
|
||||
// the drop-files event.
|
||||
if (ui::Manager::getDefault()->getForegroundWindow() != App::instance()->getMainWindow())
|
||||
return;
|
||||
|
||||
base::scoped_lock lock(*dropped_files_mutex);
|
||||
if (!dropped_files->empty()) {
|
||||
std::vector<base::string> files = *dropped_files;
|
||||
dropped_files->clear();
|
||||
|
||||
// open all files
|
||||
|
||||
Command* cmd_open_file =
|
||||
CommandsModule::instance()->getCommandByName(CommandId::OpenFile);
|
||||
Params params;
|
||||
|
||||
for (std::vector<base::string>::iterator
|
||||
it = files.begin(); it != files.end(); ++it) {
|
||||
params.set("filename", it->c_str());
|
||||
UIContext::instance()->executeCommand(cmd_open_file, ¶ms);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void subclass_hwnd()
|
||||
{
|
||||
HWND hwnd = win_get_window();
|
||||
|
||||
// add the WS_EX_ACCEPTFILES
|
||||
SetWindowLong(hwnd, GWL_EXSTYLE,
|
||||
GetWindowLong(hwnd, GWL_EXSTYLE) | WS_EX_ACCEPTFILES);
|
||||
|
||||
// set the GWL_WNDPROC to globalWndProc
|
||||
base_wnd_proc = (wndproc_t)SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)ase_wnd_proc);
|
||||
}
|
||||
|
||||
static void unsubclass_hwnd()
|
||||
{
|
||||
HWND hwnd = win_get_window();
|
||||
|
||||
// restore the old wndproc
|
||||
SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)base_wnd_proc);
|
||||
base_wnd_proc = NULL;
|
||||
}
|
||||
|
||||
static LRESULT CALLBACK ase_wnd_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
|
||||
{
|
||||
switch (msg) {
|
||||
|
||||
case WM_DROPFILES:
|
||||
{
|
||||
base::scoped_lock lock(*dropped_files_mutex);
|
||||
HDROP hdrop = (HDROP)(wparam);
|
||||
int index, count, length;
|
||||
|
||||
count = DragQueryFile(hdrop, 0xFFFFFFFF, NULL, 0);
|
||||
for (index=0; index<count; ++index) {
|
||||
length = DragQueryFile(hdrop, index, NULL, 0);
|
||||
if (length > 0) {
|
||||
TCHAR* lpstr = new TCHAR[length+1];
|
||||
DragQueryFile(hdrop, index, lpstr, length+1);
|
||||
dropped_files->push_back(base::to_utf8(lpstr));
|
||||
delete[] lpstr;
|
||||
}
|
||||
}
|
||||
|
||||
DragFinish(hdrop);
|
||||
}
|
||||
break;
|
||||
|
||||
}
|
||||
return ::CallWindowProc(base_wnd_proc, hwnd, msg, wparam, lparam);
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
void install_drop_files() { }
|
||||
void uninstall_drop_files() { }
|
||||
void check_for_dropped_files() { }
|
||||
|
||||
#endif
|
||||
|
||||
} // namespace app
|
@ -1,31 +0,0 @@
|
||||
/* Aseprite
|
||||
* Copyright (C) 2001-2013 David Capello
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef APP_DROP_FILES_H_INCLUDED
|
||||
#define APP_DROP_FILES_H_INCLUDED
|
||||
|
||||
namespace app {
|
||||
|
||||
void install_drop_files();
|
||||
void uninstall_drop_files();
|
||||
|
||||
void check_for_dropped_files();
|
||||
|
||||
} // namespace app
|
||||
|
||||
#endif
|
@ -25,7 +25,6 @@
|
||||
#include "app/commands/commands.h"
|
||||
#include "app/commands/params.h"
|
||||
#include "app/console.h"
|
||||
#include "app/drop_files.h"
|
||||
#include "app/ini_file.h"
|
||||
#include "app/modules/editors.h"
|
||||
#include "app/modules/gfx.h"
|
||||
@ -741,11 +740,30 @@ bool CustomizedGuiManager::onProcessMessage(Message* msg)
|
||||
}
|
||||
break;
|
||||
|
||||
case kDropFilesMessage:
|
||||
{
|
||||
// If the main window is not the current foreground one. We
|
||||
// discard the drop-files event.
|
||||
if (getForegroundWindow() != App::instance()->getMainWindow())
|
||||
break;
|
||||
|
||||
const DropFilesMessage::Files& files = static_cast<DropFilesMessage*>(msg)->files();
|
||||
|
||||
// Open all files
|
||||
Command* cmd_open_file =
|
||||
CommandsModule::instance()->getCommandByName(CommandId::OpenFile);
|
||||
Params params;
|
||||
|
||||
for (DropFilesMessage::Files::const_iterator
|
||||
it = files.begin(); it != files.end(); ++it) {
|
||||
params.set("filename", it->c_str());
|
||||
UIContext::instance()->executeCommand(cmd_open_file, ¶ms);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case kQueueProcessingMessage:
|
||||
gui_feedback();
|
||||
|
||||
// Open dropped files
|
||||
check_for_dropped_files();
|
||||
break;
|
||||
|
||||
case kKeyDownMessage: {
|
||||
|
@ -7,21 +7,31 @@
|
||||
#ifndef SHE_EVENT_H_INCLUDED
|
||||
#define SHE_EVENT_H_INCLUDED
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace she {
|
||||
|
||||
class Event {
|
||||
public:
|
||||
enum Type {
|
||||
None,
|
||||
DropFiles,
|
||||
};
|
||||
|
||||
typedef std::vector<std::string> Files;
|
||||
|
||||
Event() : m_type(None) { }
|
||||
|
||||
int type() const { return m_type; }
|
||||
void setType(Type type) { m_type = type; }
|
||||
|
||||
const Files& files() const { return m_files; }
|
||||
void setFiles(const Files& files) { m_files = files; }
|
||||
|
||||
private:
|
||||
Type m_type;
|
||||
Files m_files;
|
||||
};
|
||||
|
||||
} // namespace she
|
||||
|
@ -10,6 +10,9 @@
|
||||
|
||||
#include "she.h"
|
||||
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/string.h"
|
||||
|
||||
#include <allegro.h>
|
||||
#include <allegro/internal/aintern.h>
|
||||
|
||||
@ -163,19 +166,48 @@ private:
|
||||
#if WIN32
|
||||
namespace {
|
||||
|
||||
Display* g_display = NULL;
|
||||
Display* unique_display = NULL;
|
||||
wndproc_t base_wndproc = NULL;
|
||||
|
||||
static LRESULT CALLBACK wndproc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
|
||||
{
|
||||
// TODO
|
||||
// switch (msg) {
|
||||
// }
|
||||
switch (msg) {
|
||||
|
||||
case WM_DROPFILES:
|
||||
{
|
||||
HDROP hdrop = (HDROP)(wparam);
|
||||
Event::Files files;
|
||||
|
||||
int count = DragQueryFile(hdrop, 0xFFFFFFFF, NULL, 0);
|
||||
for (int index=0; index<count; ++index) {
|
||||
int length = DragQueryFile(hdrop, index, NULL, 0);
|
||||
if (length > 0) {
|
||||
std::vector<TCHAR> str(length+1);
|
||||
DragQueryFile(hdrop, index, &str[0], str.size());
|
||||
files.push_back(base::to_utf8(&str[0]));
|
||||
}
|
||||
}
|
||||
|
||||
DragFinish(hdrop);
|
||||
|
||||
Event ev;
|
||||
ev.setType(Event::DropFiles);
|
||||
ev.setFiles(files);
|
||||
static_cast<Alleg4EventQueue*>(unique_display->getEventQueue())
|
||||
->queueEvent(ev);
|
||||
}
|
||||
break;
|
||||
|
||||
}
|
||||
return ::CallWindowProc(base_wndproc, hwnd, msg, wparam, lparam);
|
||||
}
|
||||
|
||||
void subclass_hwnd(HWND hwnd)
|
||||
{
|
||||
// Add the WS_EX_ACCEPTFILES
|
||||
SetWindowLong(hwnd, GWL_EXSTYLE,
|
||||
GetWindowLong(hwnd, GWL_EXSTYLE) | WS_EX_ACCEPTFILES);
|
||||
|
||||
base_wndproc = (wndproc_t)SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)wndproc);
|
||||
}
|
||||
|
||||
@ -193,6 +225,8 @@ public:
|
||||
Alleg4Display(int width, int height, int scale)
|
||||
: m_surface(NULL)
|
||||
, m_scale(0) {
|
||||
unique_display = this;
|
||||
|
||||
if (install_mouse() < 0) throw DisplayCreationException(allegro_error);
|
||||
if (install_keyboard() < 0) throw DisplayCreationException(allegro_error);
|
||||
|
||||
@ -240,29 +274,31 @@ public:
|
||||
|
||||
m_surface->dispose();
|
||||
set_gfx_mode(GFX_TEXT, 0, 0, 0, 0);
|
||||
|
||||
unique_display = NULL;
|
||||
}
|
||||
|
||||
void dispose() {
|
||||
void dispose() OVERRIDE {
|
||||
delete this;
|
||||
}
|
||||
|
||||
int width() const {
|
||||
int width() const OVERRIDE {
|
||||
return SCREEN_W;
|
||||
}
|
||||
|
||||
int height() const {
|
||||
int height() const OVERRIDE {
|
||||
return SCREEN_H;
|
||||
}
|
||||
|
||||
int originalWidth() const {
|
||||
int originalWidth() const OVERRIDE {
|
||||
return original_width > 0 ? original_width: width();
|
||||
}
|
||||
|
||||
int originalHeight() const {
|
||||
int originalHeight() const OVERRIDE {
|
||||
return original_height > 0 ? original_height: height();
|
||||
}
|
||||
|
||||
void setScale(int scale) {
|
||||
void setScale(int scale) OVERRIDE {
|
||||
ASSERT(scale >= 1);
|
||||
|
||||
if (m_scale == scale)
|
||||
@ -276,11 +312,11 @@ public:
|
||||
m_surface = newSurface;
|
||||
}
|
||||
|
||||
NotDisposableSurface* getSurface() {
|
||||
NotDisposableSurface* getSurface() OVERRIDE {
|
||||
return static_cast<NotDisposableSurface*>(m_surface);
|
||||
}
|
||||
|
||||
bool flip() {
|
||||
bool flip() OVERRIDE {
|
||||
#ifdef ALLEGRO4_WITH_RESIZE_PATCH
|
||||
if (display_flags & DISPLAY_FLAG_WINDOW_RESIZE) {
|
||||
display_flags ^= DISPLAY_FLAG_WINDOW_RESIZE;
|
||||
@ -307,13 +343,13 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
void maximize() {
|
||||
void maximize() OVERRIDE {
|
||||
#ifdef WIN32
|
||||
::ShowWindow(win_get_window(), SW_MAXIMIZE);
|
||||
#endif
|
||||
}
|
||||
|
||||
bool isMaximized() const {
|
||||
bool isMaximized() const OVERRIDE {
|
||||
#ifdef WIN32
|
||||
return (::GetWindowLong(win_get_window(), GWL_STYLE) & WS_MAXIMIZE ? true: false);
|
||||
#else
|
||||
@ -321,11 +357,11 @@ public:
|
||||
#endif
|
||||
}
|
||||
|
||||
EventQueue* getEventQueue() {
|
||||
EventQueue* getEventQueue() OVERRIDE {
|
||||
return m_queue;
|
||||
}
|
||||
|
||||
void* nativeHandle() {
|
||||
void* nativeHandle() OVERRIDE {
|
||||
#ifdef WIN32
|
||||
return reinterpret_cast<void*>(win_get_window());
|
||||
#else
|
||||
|
@ -460,9 +460,17 @@ bool Manager::generateMessages()
|
||||
if (sheEvent.type() == she::Event::None)
|
||||
break;
|
||||
|
||||
// TODO
|
||||
// switch (sheEvent.type()) {
|
||||
// }
|
||||
switch (sheEvent.type()) {
|
||||
|
||||
case she::Event::DropFiles:
|
||||
{
|
||||
Message* msg = new DropFilesMessage(sheEvent.files());
|
||||
msg->addRecipient(this);
|
||||
enqueueMessage(msg);
|
||||
}
|
||||
break;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
// Generate messages for timers
|
||||
|
@ -16,6 +16,9 @@
|
||||
#include "ui/mouse_buttons.h"
|
||||
#include "ui/widgets_list.h"
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace ui {
|
||||
|
||||
class Timer;
|
||||
@ -128,6 +131,21 @@ namespace ui {
|
||||
Timer* m_timer; // Timer handle
|
||||
};
|
||||
|
||||
class DropFilesMessage : public Message
|
||||
{
|
||||
public:
|
||||
typedef std::vector<std::string> Files;
|
||||
|
||||
DropFilesMessage(const Files& files)
|
||||
: Message(kDropFilesMessage), m_files(files) {
|
||||
}
|
||||
|
||||
const Files& files() const { return m_files; }
|
||||
|
||||
private:
|
||||
Files m_files;
|
||||
};
|
||||
|
||||
} // namespace ui
|
||||
|
||||
#endif
|
||||
|
@ -17,6 +17,7 @@ namespace ui {
|
||||
kCloseAppMessage, // The user wants to close the entire application.
|
||||
kPaintMessage, // Widget needs be repainted.
|
||||
kTimerMessage, // A timer timeout.
|
||||
kDropFilesMessage, // Drop files in the manager.
|
||||
kWinMoveMessage, // Window movement.
|
||||
kQueueProcessingMessage, // Only sent to manager which indicate
|
||||
// the last message in the queue.
|
||||
|
Loading…
x
Reference in New Issue
Block a user