diff --git a/cmake/SuperBuild/Builddtk-deps.cmake b/cmake/SuperBuild/Builddtk-deps.cmake index 39b5fc4..64838fe 100644 --- a/cmake/SuperBuild/Builddtk-deps.cmake +++ b/cmake/SuperBuild/Builddtk-deps.cmake @@ -1,7 +1,7 @@ include(ExternalProject) set(dtk_GIT_REPOSITORY "https://github.com/darbyjohnston/dtk.git") -set(dtk_GIT_TAG "0.1.0") +set(dtk_GIT_TAG "d3fb154f63d96f3f3d8bb6b650c4165049767824") set(dtk-deps_ARGS ${toucan_EXTERNAL_PROJECT_ARGS} diff --git a/cmake/SuperBuild/Builddtk.cmake b/cmake/SuperBuild/Builddtk.cmake index 7a9956d..9d8398a 100644 --- a/cmake/SuperBuild/Builddtk.cmake +++ b/cmake/SuperBuild/Builddtk.cmake @@ -1,7 +1,7 @@ include(ExternalProject) set(dtk_GIT_REPOSITORY "https://github.com/darbyjohnston/dtk.git") -set(dtk_GIT_TAG "0.1.0") +set(dtk_GIT_TAG "d3fb154f63d96f3f3d8bb6b650c4165049767824") set(dtk_DEPS dtk-deps) set(dtk_ARGS diff --git a/lib/toucanView/CMakeLists.txt b/lib/toucanView/CMakeLists.txt index a6c13bd..e1512d9 100644 --- a/lib/toucanView/CMakeLists.txt +++ b/lib/toucanView/CMakeLists.txt @@ -1,6 +1,5 @@ set(HEADERS App.h - BottomBar.h ClipItem.h DocumentTab.h Document.h @@ -11,8 +10,9 @@ set(HEADERS GraphTool.h IItem.h IToolWidget.h - InspectorTool.h + JSONTool.h MenuBar.h + PlaybackBar.h PlaybackModel.h SelectionModel.h StackItem.h @@ -30,7 +30,6 @@ set(HEADERS set(SOURCE App.cpp - BottomBar.cpp ClipItem.cpp DocumentTab.cpp Document.cpp @@ -41,8 +40,9 @@ set(SOURCE GraphTool.cpp IItem.cpp IToolWidget.cpp - InspectorTool.cpp + JSONTool.cpp MenuBar.cpp + PlaybackBar.cpp PlaybackModel.cpp SelectionModel.cpp StackItem.cpp diff --git a/lib/toucanView/InspectorTool.cpp b/lib/toucanView/JSONTool.cpp similarity index 83% rename from lib/toucanView/InspectorTool.cpp rename to lib/toucanView/JSONTool.cpp index d038644..5883504 100644 --- a/lib/toucanView/InspectorTool.cpp +++ b/lib/toucanView/JSONTool.cpp @@ -1,7 +1,7 @@ // SPDX-License-Identifier: Apache-2.0 // Copyright Contributors to the toucan project. -#include "InspectorTool.h" +#include "JSONTool.h" #include "App.h" @@ -12,12 +12,12 @@ namespace toucan { - void InspectorWidget::_init( + void JSONWidget::_init( const std::shared_ptr& context, const OTIO_NS::SerializableObject::Retainer& item, const std::shared_ptr& parent) { - IWidget::_init(context, "toucan::InspectorWidget", parent); + IWidget::_init(context, "toucan::JSONWidget", parent); _item = item; @@ -30,42 +30,42 @@ namespace toucan _bellows->setOpen(true); } - InspectorWidget::~InspectorWidget() + JSONWidget::~JSONWidget() {} - std::shared_ptr InspectorWidget::create( + std::shared_ptr JSONWidget::create( const std::shared_ptr& context, const OTIO_NS::SerializableObject::Retainer& item, const std::shared_ptr& parent) { - auto out = std::shared_ptr(new InspectorWidget); + auto out = std::shared_ptr(new JSONWidget); out->_init(context, item, parent); return out; } - void InspectorWidget::setOpen(bool value) + void JSONWidget::setOpen(bool value) { _bellows->setOpen(value); } - void InspectorWidget::setGeometry(const dtk::Box2I& value) + void JSONWidget::setGeometry(const dtk::Box2I& value) { IWidget::setGeometry(value); _bellows->setGeometry(value); } - void InspectorWidget::sizeHintEvent(const dtk::SizeHintEvent& event) + void JSONWidget::sizeHintEvent(const dtk::SizeHintEvent& event) { IWidget::sizeHintEvent(event); _setSizeHint(_bellows->getSizeHint()); } - void InspectorTool::_init( + void JSONTool::_init( const std::shared_ptr& context, const std::shared_ptr& app, const std::shared_ptr& parent) { - IToolWidget::_init(context, app, "toucan::InspectorTool", "Inspector", parent); + IToolWidget::_init(context, app, "toucan::JSONTool", "JSON", parent); _layout = dtk::VerticalLayout::create(context, shared_from_this()); _layout->setSpacingRole(dtk::SizeRole::None); @@ -130,7 +130,7 @@ namespace toucan auto context = getContext(); for (const auto& item : selection) { - auto widget = InspectorWidget::create(context, item, _scrollLayout); + auto widget = JSONWidget::create(context, item, _scrollLayout); _widgets.push_back(widget); } }); @@ -147,26 +147,26 @@ namespace toucan }); } - InspectorTool::~InspectorTool() + JSONTool::~JSONTool() {} - std::shared_ptr InspectorTool::create( + std::shared_ptr JSONTool::create( const std::shared_ptr& context, const std::shared_ptr& app, const std::shared_ptr& parent) { - auto out = std::shared_ptr(new InspectorTool); + auto out = std::shared_ptr(new JSONTool); out->_init(context, app, parent); return out; } - void InspectorTool::setGeometry(const dtk::Box2I& value) + void JSONTool::setGeometry(const dtk::Box2I& value) { IToolWidget::setGeometry(value); _layout->setGeometry(value); } - void InspectorTool::sizeHintEvent(const dtk::SizeHintEvent& event) + void JSONTool::sizeHintEvent(const dtk::SizeHintEvent& event) { IToolWidget::sizeHintEvent(event); _setSizeHint(_layout->getSizeHint()); diff --git a/lib/toucanView/InspectorTool.h b/lib/toucanView/JSONTool.h similarity index 85% rename from lib/toucanView/InspectorTool.h rename to lib/toucanView/JSONTool.h index b7a7191..ec56e6e 100644 --- a/lib/toucanView/InspectorTool.h +++ b/lib/toucanView/JSONTool.h @@ -14,7 +14,7 @@ namespace toucan { class Document; - class InspectorWidget : public dtk::IWidget + class JSONWidget : public dtk::IWidget { protected: void _init( @@ -23,9 +23,9 @@ namespace toucan const std::shared_ptr& parent); public: - virtual ~InspectorWidget(); + virtual ~JSONWidget(); - static std::shared_ptr create( + static std::shared_ptr create( const std::shared_ptr&, const OTIO_NS::SerializableObject::Retainer&, const std::shared_ptr& parent = nullptr); @@ -40,7 +40,7 @@ namespace toucan std::shared_ptr _bellows; }; - class InspectorTool : public IToolWidget + class JSONTool : public IToolWidget { protected: void _init( @@ -49,9 +49,9 @@ namespace toucan const std::shared_ptr& parent); public: - virtual ~InspectorTool(); + virtual ~JSONTool(); - static std::shared_ptr create( + static std::shared_ptr create( const std::shared_ptr&, const std::shared_ptr&, const std::shared_ptr& parent = nullptr); @@ -65,7 +65,7 @@ namespace toucan std::shared_ptr _layout; std::shared_ptr _scrollWidget; std::shared_ptr _scrollLayout; - std::vector > _widgets; + std::vector > _widgets; std::shared_ptr > > _documentObserver; std::shared_ptr > > _selectionObserver; diff --git a/lib/toucanView/MenuBar.cpp b/lib/toucanView/MenuBar.cpp index fb4fe16..5d0b4b8 100644 --- a/lib/toucanView/MenuBar.cpp +++ b/lib/toucanView/MenuBar.cpp @@ -27,11 +27,30 @@ namespace toucan _documentsModel = app->getDocumentsModel(); _fileMenuInit(context, app); - _editMenuInit(context, app); + _selectMenuInit(context, app); _timeMenuInit(context, app); _playbackMenuInit(context, app); - _viewMenuInit(context, app); _windowMenuInit(context, app, window); + _viewMenuInit(context, app); + + _documentsObserver = dtk::ListObserver >::create( + _documentsModel->observeDocuments(), + [this](const std::vector >& documents) + { + _menus["Files"]->clear(); + _filesActions.clear(); + for (int i = 0; i < documents.size(); ++i) + { + auto item = std::make_shared( + documents[i]->getPath().filename().string(), + [this, i] + { + _documentsModel->setCurrentIndex(i); + }); + _menus["Files"]->addItem(item); + _filesActions.push_back(item); + } + }); _documentObserver = dtk::ValueObserver >::create( _documentsModel->observeCurrent(), @@ -39,11 +58,21 @@ namespace toucan { _document = document; _fileMenuUpdate(); - _editMenuUpdate(); + _selectMenuUpdate(); _timeMenuUpdate(); _playbackMenuUpdate(); - _viewMenuUpdate(); _windowMenuUpdate(); + _viewMenuUpdate(); + }); + + _documentIndexObserver = dtk::ValueObserver::create( + _documentsModel->observeCurrentIndex(), + [this](int index) + { + for (int i = 0; i < _filesActions.size(); ++i) + { + _menus["Files"]->setItemChecked(_filesActions[i], i == index); + } }); } @@ -176,46 +205,17 @@ namespace toucan } }); _menus["File"]->addItem(_actions["File/Exit"]); - - _documentsObserver = dtk::ListObserver >::create( - _documentsModel->observeDocuments(), - [this](const std::vector >& documents) - { - _menus["Files"]->clear(); - _filesActions.clear(); - for (int i = 0; i < documents.size(); ++i) - { - auto item = std::make_shared( - documents[i]->getPath().filename().string(), - [this, i] - { - _documentsModel->setCurrentIndex(i); - }); - _menus["Files"]->addItem(item); - _filesActions.push_back(item); - } - }); - - _documentIndexObserver = dtk::ValueObserver::create( - _documentsModel->observeCurrentIndex(), - [this](int index) - { - for (int i = 0; i < _filesActions.size(); ++i) - { - _menus["Files"]->setItemChecked(_filesActions[i], i == index); - } - }); } - void MenuBar::_editMenuInit( + void MenuBar::_selectMenuInit( const std::shared_ptr& context, const std::shared_ptr& app) { - _menus["Edit"] = dtk::Menu::create(context); - addMenu("Edit", _menus["Edit"]); + _menus["Select"] = dtk::Menu::create(context); + addMenu("Select", _menus["Select"]); - _actions["Edit/SelectAll"] = std::make_shared( - "Select All", + _actions["Select/All"] = std::make_shared( + "All", dtk::Key::A, static_cast(dtk::KeyModifier::Control), [this] @@ -225,10 +225,10 @@ namespace toucan _document->getSelectionModel()->selectAll(_document->getTimeline()); } }); - _menus["Edit"]->addItem(_actions["Edit/SelectAll"]); + _menus["Select"]->addItem(_actions["Select/All"]); - _actions["Edit/SelectNone"] = std::make_shared( - "Select None", + _actions["Select/None"] = std::make_shared( + "None", dtk::Key::A, static_cast(dtk::KeyModifier::Shift) | static_cast(dtk::KeyModifier::Control), @@ -239,10 +239,10 @@ namespace toucan _document->getSelectionModel()->clearSelection(); } }); - _menus["Edit"]->addItem(_actions["Edit/SelectNone"]); + _menus["Select"]->addItem(_actions["Select/None"]); - _actions["Edit/SelectInvert"] = std::make_shared( - "Invert Selection", + _actions["Select/Invert"] = std::make_shared( + "Invert", dtk::Key::I, static_cast(dtk::KeyModifier::Control), [this] @@ -252,7 +252,7 @@ namespace toucan _document->getSelectionModel()->invertSelection(_document->getTimeline()); } }); - _menus["Edit"]->addItem(_actions["Edit/SelectInvert"]); + _menus["Select"]->addItem(_actions["Select/Invert"]); } void MenuBar::_timeMenuInit( @@ -430,68 +430,6 @@ namespace toucan _menus["Playback"]->addItem(_actions["Playback/Toggle"]); } - void MenuBar::_viewMenuInit( - const std::shared_ptr& context, - const std::shared_ptr& app) - { - _menus["View"] = dtk::Menu::create(context); - addMenu("View", _menus["View"]); - - _actions["View/ZoomIn"] = std::make_shared( - "Zoom In", - dtk::Key::Equal, - 0, - [this] - { - if (_document) - { - _document->getViewModel()->zoomIn(); - } - }); - _menus["View"]->addItem(_actions["View/ZoomIn"]); - - _actions["View/ZoomOut"] = std::make_shared( - "Zoom Out", - dtk::Key::Minus, - 0, - [this] - { - if (_document) - { - _document->getViewModel()->zoomOut(); - } - }); - _menus["View"]->addItem(_actions["View/ZoomOut"]); - - _actions["View/ZoomReset"] = std::make_shared( - "Zoom Reset", - dtk::Key::_0, - 0, - [this] - { - if (_document) - { - _document->getViewModel()->zoomReset(); - } - }); - _menus["View"]->addItem(_actions["View/ZoomReset"]); - - _menus["View"]->addDivider(); - - _actions["View/FrameView"] = std::make_shared( - "Frame View", - dtk::Key::Backspace, - 0, - [this](bool value) - { - if (_document) - { - _document->getViewModel()->setFrame(value); - } - }); - _menus["View"]->addItem(_actions["View/FrameView"]); - } - void MenuBar::_windowMenuInit( const std::shared_ptr& context, const std::shared_ptr& app, @@ -527,7 +465,7 @@ namespace toucan const std::vector controls = { { WindowControl::ToolBar, "ToolBar", "Tool Bar" }, - { WindowControl::BottomBar, "BottomBar", "Bottom Bar" }, + { WindowControl::PlaybackBar, "PlaybackBar", "Playback Bar" }, { WindowControl::TimelineWidget, "TimelineWidget", "Timeline Widget" }, { WindowControl::Tools, "Tools", "Tools" } }; @@ -654,8 +592,8 @@ namespace toucan { auto i = value.find(WindowControl::ToolBar); _menus["Window"]->setItemChecked(_actions["Window/ToolBar"], i->second); - i = value.find(WindowControl::BottomBar); - _menus["Window"]->setItemChecked(_actions["Window/BottomBar"], i->second); + i = value.find(WindowControl::PlaybackBar); + _menus["Window"]->setItemChecked(_actions["Window/PlaybackBar"], i->second); i = value.find(WindowControl::TimelineWidget); _menus["Window"]->setItemChecked(_actions["Window/TimelineWidget"], i->second); i = value.find(WindowControl::Tools); @@ -680,6 +618,76 @@ namespace toucan }); } + void MenuBar::_viewMenuInit( + const std::shared_ptr& context, + const std::shared_ptr& app) + { + _menus["View"] = dtk::Menu::create(context); + addMenu("View", _menus["View"]); + + _actions["View/ZoomIn"] = std::make_shared( + "Zoom In", + "ViewZoomIn", + dtk::Key::Equal, + 0, + [this] + { + if (_document) + { + _document->getViewModel()->zoomIn(); + } + }); + _actions["View/ZoomIn"]->toolTip = "View zoom in"; + _menus["View"]->addItem(_actions["View/ZoomIn"]); + + _actions["View/ZoomOut"] = std::make_shared( + "Zoom Out", + "ViewZoomOut", + dtk::Key::Minus, + 0, + [this] + { + if (_document) + { + _document->getViewModel()->zoomOut(); + } + }); + _actions["View/ZoomOut"]->toolTip = "View zoom out"; + _menus["View"]->addItem(_actions["View/ZoomOut"]); + + _actions["View/ZoomReset"] = std::make_shared( + "Zoom Reset", + "ViewZoomReset", + dtk::Key::_0, + 0, + [this] + { + if (_document) + { + _document->getViewModel()->zoomReset(); + } + }); + _actions["View/ZoomReset"]->toolTip = "Reset the view zoom"; + _menus["View"]->addItem(_actions["View/ZoomReset"]); + + _menus["View"]->addDivider(); + + _actions["View/Frame"] = std::make_shared( + "Frame View", + "ViewFrame", + dtk::Key::Backspace, + 0, + [this](bool value) + { + if (_document) + { + _document->getViewModel()->setFrame(value); + } + }); + _actions["View/Frame"]->toolTip = "Frame the view"; + _menus["View"]->addItem(_actions["View/Frame"]); + } + void MenuBar::_fileMenuUpdate() { _menus["File"]->setItemEnabled(_actions["File/Close"], _document.get()); @@ -689,11 +697,11 @@ namespace toucan _menus["File"]->setItemEnabled(_actions["File/Prev"], _filesActions.size() > 1); } - void MenuBar::_editMenuUpdate() + void MenuBar::_selectMenuUpdate() { - _menus["Edit"]->setItemEnabled(_actions["Edit/SelectAll"], _document.get()); - _menus["Edit"]->setItemEnabled(_actions["Edit/SelectNone"], _document.get()); - _menus["Edit"]->setItemEnabled(_actions["Edit/SelectInvert"], _document.get()); + _menus["Select"]->setItemEnabled(_actions["Select/All"], _document.get()); + _menus["Select"]->setItemEnabled(_actions["Select/None"], _document.get()); + _menus["Select"]->setItemEnabled(_actions["Select/Invert"], _document.get()); } void MenuBar::_timeMenuUpdate() @@ -728,6 +736,10 @@ namespace toucan _menus["Playback"]->setItemEnabled(_actions["Playback/Toggle"], _document.get()); } + void MenuBar::_windowMenuUpdate() + { + } + void MenuBar::_viewMenuUpdate() { if (_document) @@ -736,7 +748,7 @@ namespace toucan _document->getViewModel()->observeFrame(), [this](bool value) { - _menus["View"]->setItemChecked(_actions["View/FrameView"], value); + _menus["View"]->setItemChecked(_actions["View/Frame"], value); }); } else @@ -747,10 +759,6 @@ namespace toucan _menus["View"]->setItemEnabled(_actions["View/ZoomIn"], _document.get()); _menus["View"]->setItemEnabled(_actions["View/ZoomOut"], _document.get()); _menus["View"]->setItemEnabled(_actions["View/ZoomReset"], _document.get()); - _menus["View"]->setItemEnabled(_actions["View/FrameView"], _document.get()); - } - - void MenuBar::_windowMenuUpdate() - { + _menus["View"]->setItemEnabled(_actions["View/Frame"], _document.get()); } } diff --git a/lib/toucanView/MenuBar.h b/lib/toucanView/MenuBar.h index 1712844..56ca6f7 100644 --- a/lib/toucanView/MenuBar.h +++ b/lib/toucanView/MenuBar.h @@ -41,7 +41,7 @@ namespace toucan void _fileMenuInit( const std::shared_ptr&, const std::shared_ptr&); - void _editMenuInit( + void _selectMenuInit( const std::shared_ptr&, const std::shared_ptr&); void _timeMenuInit( @@ -50,20 +50,20 @@ namespace toucan void _playbackMenuInit( const std::shared_ptr&, const std::shared_ptr&); - void _viewMenuInit( - const std::shared_ptr&, - const std::shared_ptr&); void _windowMenuInit( const std::shared_ptr&, const std::shared_ptr&, const std::shared_ptr&); + void _viewMenuInit( + const std::shared_ptr&, + const std::shared_ptr&); void _fileMenuUpdate(); - void _editMenuUpdate(); + void _selectMenuUpdate(); void _timeMenuUpdate(); void _playbackMenuUpdate(); - void _viewMenuUpdate(); void _windowMenuUpdate(); + void _viewMenuUpdate(); std::weak_ptr _app; std::shared_ptr _documentsModel; @@ -77,12 +77,12 @@ namespace toucan std::shared_ptr > > _documentObserver; std::shared_ptr > _documentIndexObserver; std::shared_ptr > _playbackObserver; - std::shared_ptr > _frameViewObserver; std::shared_ptr > _fullScreenObserver; std::shared_ptr > _controlsObserver; std::shared_ptr > _displayScaleObserver; std::shared_ptr > _tooltipsObserver; std::shared_ptr > _timeUnitsObserver; + std::shared_ptr > _frameViewObserver; }; } diff --git a/lib/toucanView/BottomBar.cpp b/lib/toucanView/PlaybackBar.cpp similarity index 88% rename from lib/toucanView/BottomBar.cpp rename to lib/toucanView/PlaybackBar.cpp index 049d3dc..19662cc 100644 --- a/lib/toucanView/BottomBar.cpp +++ b/lib/toucanView/PlaybackBar.cpp @@ -1,18 +1,18 @@ // SPDX-License-Identifier: Apache-2.0 // Copyright Contributors to the toucan project. -#include "BottomBar.h" +#include "PlaybackBar.h" #include "App.h" namespace toucan { - void BottomBar::_init( + void PlaybackBar::_init( const std::shared_ptr& context, const std::shared_ptr& app, const std::shared_ptr& parent) { - dtk::IWidget::_init(context, "toucan::BottomBar", parent); + dtk::IWidget::_init(context, "toucan::PlaybackBar", parent); _layout = dtk::HorizontalLayout::create(context, shared_from_this()); _layout->setMarginRole(dtk::SizeRole::MarginInside); @@ -108,47 +108,47 @@ namespace toucan }); } - BottomBar::~BottomBar() + PlaybackBar::~PlaybackBar() {} - std::shared_ptr BottomBar::create( + std::shared_ptr PlaybackBar::create( const std::shared_ptr& context, const std::shared_ptr& app, const std::shared_ptr& parent) { - auto out = std::shared_ptr(new BottomBar); + auto out = std::shared_ptr(new PlaybackBar); out->_init(context, app, parent); return out; } - void BottomBar::setGeometry(const dtk::Box2I& value) + void PlaybackBar::setGeometry(const dtk::Box2I& value) { IWidget::setGeometry(value); _layout->setGeometry(value); } - void BottomBar::sizeHintEvent(const dtk::SizeHintEvent& event) + void PlaybackBar::sizeHintEvent(const dtk::SizeHintEvent& event) { IWidget::sizeHintEvent(event); _setSizeHint(_layout->getSizeHint()); } - void BottomBar::_timelineUpdate() + void PlaybackBar::_timelineUpdate() {} - void BottomBar::_timeRangeUpdate() + void PlaybackBar::_timeRangeUpdate() { _timeEdit->setTimeRange(_timeRange); _durationLabel->setTime(_timeRange.duration()); } - void BottomBar::_currentTimeUpdate() + void PlaybackBar::_currentTimeUpdate() { _timeEdit->setTime(_currentTime); } - void BottomBar::_playbackUpdate() + void PlaybackBar::_playbackUpdate() { _playbackButtons->setPlayback(_playback); } diff --git a/lib/toucanView/BottomBar.h b/lib/toucanView/PlaybackBar.h similarity index 92% rename from lib/toucanView/BottomBar.h rename to lib/toucanView/PlaybackBar.h index d387ee6..8446f5d 100644 --- a/lib/toucanView/BottomBar.h +++ b/lib/toucanView/PlaybackBar.h @@ -13,7 +13,7 @@ namespace toucan class App; class Document; - class BottomBar : public dtk::IWidget + class PlaybackBar : public dtk::IWidget { protected: void _init( @@ -22,9 +22,9 @@ namespace toucan const std::shared_ptr& parent); public: - virtual ~BottomBar(); + virtual ~PlaybackBar(); - static std::shared_ptr create( + static std::shared_ptr create( const std::shared_ptr&, const std::shared_ptr&, const std::shared_ptr& parent = nullptr); diff --git a/lib/toucanView/ToolBar.cpp b/lib/toucanView/ToolBar.cpp index 783d26f..26bea6f 100644 --- a/lib/toucanView/ToolBar.cpp +++ b/lib/toucanView/ToolBar.cpp @@ -4,6 +4,7 @@ #include "ToolBar.h" #include "App.h" +#include "ViewModel.h" #include @@ -21,7 +22,7 @@ namespace toucan _layout = dtk::HorizontalLayout::create(context, shared_from_this()); _layout->setSpacingRole(dtk::SizeRole::SpacingTool); - const std::vector actionNames = + std::vector actionNames = { "File/Open", "File/Close", @@ -61,6 +62,48 @@ namespace toucan }); _buttons["Window/FullScreen"] = button; + dtk::Divider::create(context, dtk::Orientation::Horizontal, _layout); + + actionNames = + { + "View/ZoomIn", + "View/ZoomOut", + "View/ZoomReset" + }; + for (const auto& name : actionNames) + { + i = actions.find(name); + button = dtk::ToolButton::create(context, _layout); + button->setIcon(i->second->icon); + button->setTooltip(i->second->toolTip); + button->setClickedCallback( + [i] + { + if (i->second->callback) + { + i->second->callback(); + } + }); + _buttons[name] = button; + } + + i = actions.find("View/Frame"); + button = dtk::ToolButton::create(context, _layout); + button->setIcon(i->second->icon); + button->setCheckable(true); + button->setTooltip(i->second->toolTip); + button->setCheckedCallback( + [i](bool value) + { + if (i->second->checkedCallback) + { + i->second->checkedCallback(value); + } + }); + _buttons["View/Frame"] = button; + + dtk::Divider::create(context, dtk::Orientation::Horizontal, _layout); + _widgetUpdate(); _documentsObserver = dtk::ListObserver >::create( @@ -71,6 +114,14 @@ namespace toucan _widgetUpdate(); }); + _documentObserver = dtk::ValueObserver >::create( + app->getDocumentsModel()->observeCurrent(), + [this](const std::shared_ptr& document) + { + _document = document; + _widgetUpdate(); + }); + _fullScreenObserver = dtk::ValueObserver::create( window->observeFullScreen(), [this](bool value) @@ -110,5 +161,19 @@ namespace toucan { _buttons["File/Close"]->setEnabled(_documentsSize > 0); _buttons["File/CloseAll"]->setEnabled(_documentsSize > 0); + + if (_document) + { + _frameViewObserver = dtk::ValueObserver::create( + _document->getViewModel()->observeFrame(), + [this](bool value) + { + _buttons["View/Frame"]->setChecked(value); + }); + } + else + { + _frameViewObserver.reset(); + } } } diff --git a/lib/toucanView/ToolBar.h b/lib/toucanView/ToolBar.h index 0254de4..6dc6cff 100644 --- a/lib/toucanView/ToolBar.h +++ b/lib/toucanView/ToolBar.h @@ -42,12 +42,15 @@ namespace toucan void _widgetUpdate(); size_t _documentsSize = 0; + std::shared_ptr _document; std::shared_ptr _layout; std::map > _buttons; std::shared_ptr > > _documentsObserver; + std::shared_ptr > > _documentObserver; std::shared_ptr > _fullScreenObserver; + std::shared_ptr > _frameViewObserver; }; } diff --git a/lib/toucanView/Window.cpp b/lib/toucanView/Window.cpp index 8a83841..6ab13ff 100644 --- a/lib/toucanView/Window.cpp +++ b/lib/toucanView/Window.cpp @@ -4,12 +4,12 @@ #include "Window.h" #include "App.h" -#include "BottomBar.h" #include "DocumentTab.h" #include "ExportTool.h" #include "GraphTool.h" -#include "InspectorTool.h" +#include "JSONTool.h" #include "MenuBar.h" +#include "PlaybackBar.h" #include "TimelineWidget.h" #include "ToolBar.h" @@ -59,7 +59,7 @@ namespace toucan _tabWidget->setVStretch(dtk::Stretch::Expanding); _toolWidget = dtk::TabWidget::create(context, _hSplitter); - _toolWidgets.push_back(InspectorTool::create(context, app)); + _toolWidgets.push_back(JSONTool::create(context, app)); _toolWidgets.push_back(GraphTool::create(context, app)); _toolWidgets.push_back(ExportTool::create(context, app)); for (const auto& toolWidget : _toolWidgets) @@ -69,7 +69,7 @@ namespace toucan _bottomLayout = dtk::VerticalLayout::create(context, _vSplitter); _bottomLayout->setSpacingRole(dtk::SizeRole::None); - _bottomBar = BottomBar::create(context, app, _bottomLayout); + _playbackBar = PlaybackBar::create(context, app, _bottomLayout); _timelineWidget = TimelineWidget::create(context, app, _bottomLayout); _timelineWidget->setVStretch(dtk::Stretch::Expanding); @@ -148,8 +148,8 @@ namespace toucan _toolBarDivider->setVisible(i->second); i = value.find(WindowControl::TimelineWidget); _timelineWidget->setVisible(i->second); - auto j = value.find(WindowControl::BottomBar); - _bottomBar->setVisible(j->second); + auto j = value.find(WindowControl::PlaybackBar); + _playbackBar->setVisible(j->second); _bottomLayout->setVisible(i->second || j->second); i = value.find(WindowControl::Tools); _toolWidget->setVisible(i->second); diff --git a/lib/toucanView/Window.h b/lib/toucanView/Window.h index f5acd5d..e4a1595 100644 --- a/lib/toucanView/Window.h +++ b/lib/toucanView/Window.h @@ -15,11 +15,11 @@ namespace toucan { class App; - class BottomBar; class Document; class DocumentTab; class IToolWidget; class MenuBar; + class PlaybackBar; class TimelineWidget; class ToolBar; @@ -64,7 +64,7 @@ namespace toucan std::shared_ptr _toolWidget; std::vector > _toolWidgets; std::shared_ptr _bottomLayout; - std::shared_ptr _bottomBar; + std::shared_ptr _playbackBar; std::shared_ptr _timelineWidget; std::shared_ptr > > _documentsObserver; diff --git a/lib/toucanView/WindowModel.cpp b/lib/toucanView/WindowModel.cpp index 9df240e..f04d1c1 100644 --- a/lib/toucanView/WindowModel.cpp +++ b/lib/toucanView/WindowModel.cpp @@ -10,7 +10,7 @@ namespace toucan std::map values = { { WindowControl::ToolBar, true }, - { WindowControl::BottomBar, true }, + { WindowControl::PlaybackBar, true }, { WindowControl::TimelineWidget, true }, { WindowControl::Tools, true } }; diff --git a/lib/toucanView/WindowModel.h b/lib/toucanView/WindowModel.h index 84ffa9e..9ee6d72 100644 --- a/lib/toucanView/WindowModel.h +++ b/lib/toucanView/WindowModel.h @@ -11,7 +11,7 @@ namespace toucan enum class WindowControl { ToolBar, - BottomBar, + PlaybackBar, TimelineWidget, Tools };