mirror of
https://github.com/aseprite/aseprite.git
synced 2025-03-17 13:20:45 +00:00
Add feedback to Workspace to drop tabs on it
This commit is contained in:
parent
9e27930f95
commit
2cfef9e250
@ -247,6 +247,17 @@ void MainWindow::onActiveViewChange()
|
||||
configureWorkspaceLayout();
|
||||
}
|
||||
|
||||
bool MainWindow::onIsModified(Tabs* tabs, TabView* tabView)
|
||||
{
|
||||
if (DocumentView* docView = dynamic_cast<DocumentView*>(tabView)) {
|
||||
Document* document = docView->getDocument();
|
||||
return document->isModified();
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::onSelectTab(Tabs* tabs, TabView* tabView)
|
||||
{
|
||||
if (!tabView)
|
||||
@ -286,15 +297,16 @@ void MainWindow::onMouseOverTab(Tabs* tabs, TabView* tabView)
|
||||
}
|
||||
}
|
||||
|
||||
bool MainWindow::onIsModified(Tabs* tabs, TabView* tabView)
|
||||
void MainWindow::onFloatingTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos)
|
||||
{
|
||||
if (DocumentView* docView = dynamic_cast<DocumentView*>(tabView)) {
|
||||
Document* document = docView->getDocument();
|
||||
return document->isModified();
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
}
|
||||
m_workspace->setDropViewPreview(pos);
|
||||
}
|
||||
|
||||
DropTabResult MainWindow::onDropTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos)
|
||||
{
|
||||
m_workspace->removeDropViewPreview(pos);
|
||||
m_workspace->dropViewAt(pos, dynamic_cast<WorkspaceView*>(tabView));
|
||||
return DropTabResult::IGNORE;
|
||||
}
|
||||
|
||||
void MainWindow::configureWorkspaceLayout()
|
||||
|
@ -74,11 +74,13 @@ namespace app {
|
||||
void popTimeline();
|
||||
|
||||
// TabsDelegate implementation.
|
||||
bool onIsModified(Tabs* tabs, TabView* tabView) override;
|
||||
void onSelectTab(Tabs* tabs, TabView* tabView) override;
|
||||
void onCloseTab(Tabs* tabs, TabView* tabView) override;
|
||||
void onContextMenuTab(Tabs* tabs, TabView* tabView) override;
|
||||
void onMouseOverTab(Tabs* tabs, TabView* tabView) override;
|
||||
bool onIsModified(Tabs* tabs, TabView* tabView) override;
|
||||
void onFloatingTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos) override;
|
||||
DropTabResult onDropTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos) override;
|
||||
|
||||
protected:
|
||||
bool onProcessMessage(ui::Message* msg) override;
|
||||
|
@ -250,6 +250,9 @@ bool Tabs::onProcessMessage(Message* msg)
|
||||
createFloatingTab(m_selected);
|
||||
|
||||
m_floatingOverlay->moveOverlay(mousePos - m_dragOffset);
|
||||
|
||||
if (m_delegate)
|
||||
m_delegate->onFloatingTab(this, m_selected->view, mousePos);
|
||||
}
|
||||
else {
|
||||
justDocked = m_floatingTab;
|
||||
@ -332,8 +335,13 @@ bool Tabs::onProcessMessage(Message* msg)
|
||||
|
||||
releaseMouse();
|
||||
|
||||
if (m_isDragging)
|
||||
if (m_isDragging) {
|
||||
if (m_delegate)
|
||||
m_delegate->onDropTab(this, m_selected->view,
|
||||
mouseMsg->position());
|
||||
|
||||
stopDrag();
|
||||
}
|
||||
|
||||
if (m_clickedCloseButton) {
|
||||
m_clickedCloseButton = false;
|
||||
|
@ -41,11 +41,20 @@ namespace app {
|
||||
virtual TabIcon getTabIcon() = 0;
|
||||
};
|
||||
|
||||
enum class DropTabResult {
|
||||
IGNORE,
|
||||
DOCKED_IN_OTHER_PLACE,
|
||||
};
|
||||
|
||||
// Interface used to control notifications from the Tabs widget.
|
||||
class TabsDelegate {
|
||||
public:
|
||||
|
||||
virtual ~TabsDelegate() { }
|
||||
|
||||
// Returns true if the tab represent a modified document.
|
||||
virtual bool onIsModified(Tabs* tabs, TabView* tabView) = 0;
|
||||
|
||||
// Called when the user selected the tab with the left mouse button.
|
||||
virtual void onSelectTab(Tabs* tabs, TabView* tabView) = 0;
|
||||
|
||||
@ -59,7 +68,9 @@ namespace app {
|
||||
// mouse just leave all tabs)
|
||||
virtual void onMouseOverTab(Tabs* tabs, TabView* tabView) = 0;
|
||||
|
||||
virtual bool onIsModified(Tabs* tabs, TabView* tabView) = 0;
|
||||
// Called when the user is dragging a tab outside the Tabs bar.
|
||||
virtual void onFloatingTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos) = 0;
|
||||
virtual DropTabResult onDropTab(Tabs* tabs, TabView* tabView, const gfx::Point& pos) = 0;
|
||||
};
|
||||
|
||||
// Tabs control. Used to show opened documents.
|
||||
|
@ -30,6 +30,7 @@ Workspace::Workspace()
|
||||
: Widget(kGenericWidget)
|
||||
, m_tabsBar(nullptr)
|
||||
, m_activeView(nullptr)
|
||||
, m_dropPreview(false)
|
||||
{
|
||||
SkinTheme* theme = static_cast<SkinTheme*>(getTheme());
|
||||
setBgColor(theme->colors.workspace());
|
||||
@ -100,4 +101,58 @@ void Workspace::onPaint(PaintEvent& ev)
|
||||
ev.getGraphics()->fillRect(getBgColor(), getClientBounds());
|
||||
}
|
||||
|
||||
void Workspace::onResize(ui::ResizeEvent& ev)
|
||||
{
|
||||
setBoundsQuietly(ev.getBounds());
|
||||
|
||||
gfx::Rect cpos = getChildrenBounds();
|
||||
|
||||
// Preview to drop tabs in workspace
|
||||
if (m_dropPreview && cpos.contains(m_dropPos)) {
|
||||
int left = ABS(cpos.x - m_dropPos.x);
|
||||
int top = ABS(cpos.y - m_dropPos.y);
|
||||
int right = ABS(cpos.x + cpos.w - m_dropPos.x);
|
||||
int bottom = ABS(cpos.y + cpos.h - m_dropPos.y);
|
||||
int threshold = 32*guiscale();
|
||||
if (threshold > cpos.w/2) threshold = cpos.w/2;
|
||||
if (threshold > cpos.h/2) threshold = cpos.h/2;
|
||||
|
||||
if (left < threshold && left < right && left < top && left < bottom) {
|
||||
cpos.x += threshold;
|
||||
cpos.w -= threshold;
|
||||
}
|
||||
else if (top < threshold && top < left && top < right && top < bottom) {
|
||||
cpos.y += threshold;
|
||||
cpos.h -= threshold;
|
||||
}
|
||||
else if (right < threshold && right < left && right < top && right < bottom) {
|
||||
cpos.w -= threshold;
|
||||
}
|
||||
else if (bottom < threshold && bottom < left && bottom < top && bottom < right) {
|
||||
cpos.h -= threshold;
|
||||
}
|
||||
}
|
||||
|
||||
for (Widget* child : getChildren())
|
||||
child->setBounds(cpos);
|
||||
}
|
||||
|
||||
void Workspace::setDropViewPreview(const gfx::Point& pos)
|
||||
{
|
||||
m_dropPos = pos;
|
||||
m_dropPreview = true;
|
||||
|
||||
layout();
|
||||
}
|
||||
|
||||
void Workspace::removeDropViewPreview(const gfx::Point& pos)
|
||||
{
|
||||
m_dropPreview = false;
|
||||
layout();
|
||||
}
|
||||
|
||||
void Workspace::dropViewAt(const gfx::Point& pos, WorkspaceView* view)
|
||||
{
|
||||
}
|
||||
|
||||
} // namespace app
|
||||
|
@ -40,15 +40,23 @@ namespace app {
|
||||
WorkspaceView* activeView();
|
||||
void setActiveView(WorkspaceView* view);
|
||||
|
||||
// Drop views into workspace
|
||||
void setDropViewPreview(const gfx::Point& pos);
|
||||
void removeDropViewPreview(const gfx::Point& pos);
|
||||
void dropViewAt(const gfx::Point& pos, WorkspaceView* view);
|
||||
|
||||
Signal0<void> ActiveViewChanged;
|
||||
|
||||
protected:
|
||||
void onPaint(ui::PaintEvent& ev) override;
|
||||
void onResize(ui::ResizeEvent& ev) override;
|
||||
|
||||
private:
|
||||
Tabs* m_tabsBar;
|
||||
WorkspaceViews m_views;
|
||||
WorkspaceView* m_activeView;
|
||||
bool m_dropPreview;
|
||||
gfx::Point m_dropPos;
|
||||
};
|
||||
|
||||
} // namespace app
|
||||
|
Loading…
x
Reference in New Issue
Block a user