From 9b62c53833b514e0838fbbd2fc480beebbdf926c Mon Sep 17 00:00:00 2001 From: manongjohn Date: Oct 31 2018 02:56:59 +0000 Subject: Timeline height and keyframe area adjustments (#2268) * Increase timeline layer height * Narrow keyframe active area * Display thumbnail in Timeline * Move timeline Sound icon to thumbnail area * Move timeline Sound volume control to config button * Move timeline Filter color icon to thumbnail close #2261 close #2262 --- diff --git a/toonz/sources/include/orientation.h b/toonz/sources/include/orientation.h index d9ba1c0..58584cd 100644 --- a/toonz/sources/include/orientation.h +++ b/toonz/sources/include/orientation.h @@ -120,7 +120,11 @@ enum class PredefinedRect { LAYER_FOOTER_PANEL, PREVIEW_FRAME_AREA, SHIFTTRACE_DOT, - SHIFTTRACE_DOT_AREA + SHIFTTRACE_DOT_AREA, + PANEL_EYE, + PANEL_PREVIEW_LAYER, + PANEL_LOCK, + PANEL_LAYER_NAME }; enum class PredefinedLine { LOCKED, //! dotted vertical line when cell is locked diff --git a/toonz/sources/toonz/layerheaderpanel.cpp b/toonz/sources/toonz/layerheaderpanel.cpp index 429f096..8187f38 100644 --- a/toonz/sources/toonz/layerheaderpanel.cpp +++ b/toonz/sources/toonz/layerheaderpanel.cpp @@ -77,9 +77,9 @@ void LayerHeaderPanel::paintEvent(QPaintEvent *event) { ? m_viewer->getLayerHeaderLockOverImage() : m_viewer->getLayerHeaderLockImage()); - drawIcon(p, PredefinedRect::EYE, boost::none, preview); - drawIcon(p, PredefinedRect::PREVIEW_LAYER, boost::none, camstand); - drawIcon(p, PredefinedRect::LOCK, boost::none, lock); + drawIcon(p, PredefinedRect::PANEL_EYE, boost::none, preview); + drawIcon(p, PredefinedRect::PANEL_PREVIEW_LAYER, boost::none, camstand); + drawIcon(p, PredefinedRect::PANEL_LOCK, boost::none, lock); QRect numberRect = o->rect(PredefinedRect::LAYER_NUMBER); @@ -91,7 +91,7 @@ void LayerHeaderPanel::paintEvent(QPaintEvent *event) { } QRect nameRect = - o->rect(PredefinedRect::LAYER_NAME).adjusted(leftadj, 0, -1, 0); + o->rect(PredefinedRect::PANEL_LAYER_NAME).adjusted(leftadj, 0, -1, 0); p.drawText(nameRect, Qt::AlignLeft | Qt::AlignVCenter | Qt::TextSingleLine, QObject::tr("Layer name")); diff --git a/toonz/sources/toonz/xshcellviewer.cpp b/toonz/sources/toonz/xshcellviewer.cpp index eefc461..33bc362 100644 --- a/toonz/sources/toonz/xshcellviewer.cpp +++ b/toonz/sources/toonz/xshcellviewer.cpp @@ -2299,17 +2299,11 @@ void CellArea::drawKeyframe(QPainter &p, const QRect toBeUpdated) { handleRow1)) { QPoint topLeft = m_viewer->positionToXY(CellPosition(handleRow0, col)); - if (!o->isVerticalTimeline() && - m_viewer->getFrameZoomFactor() <= 50) - topLeft.setY(topLeft.y() - 1); m_viewer->drawPredefinedPath(p, PredefinedPath::BEGIN_EASE_TRIANGLE, topLeft + QPoint(-frameAdj / 2, 0), keyFrameColor, outline); topLeft = m_viewer->positionToXY(CellPosition(handleRow1, col)); - if (!o->isVerticalTimeline() && - m_viewer->getFrameZoomFactor() <= 50) - topLeft.setY(topLeft.y() - 1); m_viewer->drawPredefinedPath(p, PredefinedPath::END_EASE_TRIANGLE, topLeft + QPoint(-frameAdj / 2, 0), keyFrameColor, outline); @@ -2409,13 +2403,6 @@ void CellArea::drawKeyframeLine(QPainter &p, int col, keyRect.center() + m_viewer->positionToXY(CellPosition(rows.from(), col)); QPoint end = keyRect.center() + m_viewer->positionToXY(CellPosition(rows.to(), col)); - - if (!m_viewer->orientation()->isVerticalTimeline() && - m_viewer->getFrameZoomFactor() <= 50) { - begin.setY(begin.y() - 1); - end.setY(end.y() - 1); - } - p.setPen(Qt::white); p.drawLine(QLine(begin, end)); } @@ -2557,6 +2544,56 @@ public: int getHistoryType() override { return HistoryType::Xsheet; } }; //---------------------------------------------------------- +bool CellArea::isKeyFrameArea(int col, int row, QPoint mouseInCell) { + if (!Preferences::instance()->isShowKeyframesOnXsheetCellAreaEnabled()) + return false; + + TXsheet *xsh = m_viewer->getXsheet(); + if (!xsh) return false; + + TStageObject *pegbar = xsh->getStageObject(m_viewer->getObjectId(col)); + int k0, k1; + + bool isKeyframeFrame = pegbar && pegbar->getKeyframeRange(k0, k1) && + (k1 > k0 || k0 == row) && k0 <= row && row <= k1 + 1; + + if (!isKeyframeFrame) return false; + + const Orientation *o = m_viewer->orientation(); + int frameAdj = m_viewer->getFrameZoomAdjustment(); + + if (o->isVerticalTimeline()) + return o->rect(PredefinedRect::KEYFRAME_AREA) + .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) + .contains(mouseInCell) && + row < k1 + 1; + + QRect activeArea = (m_viewer->getFrameZoomFactor() > 50 + ? o->rect(PredefinedRect::KEYFRAME_AREA) + : o->rect(PredefinedRect::FRAME_MARKER_AREA)); + + // If directly over keyframe icon, return true + if (pegbar->isKeyframe(row) && + activeArea.adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) + .contains(mouseInCell) && + row < k1 + 1) + return true; + + // In the white line area, if zoomed in.. narrow height by using frame marker + // area since it has a narrower height + if (m_viewer->getFrameZoomFactor() > 50) + activeArea = o->rect(PredefinedRect::FRAME_MARKER_AREA); + + // Adjust left and/or right edge depending on which part of white line you are + // on + if (row > k0) activeArea.adjust(-activeArea.left(), 0, 0, 0); + if (row < k1) + activeArea.adjust(0, 0, (o->cellWidth() - activeArea.right()), 0); + + return activeArea.adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) + .contains(mouseInCell) && + row < k1 + 1; +} void CellArea::mousePressEvent(QMouseEvent *event) { const Orientation *o = m_viewer->orientation(); @@ -2628,23 +2665,12 @@ void CellArea::mousePressEvent(QMouseEvent *event) { bool isKeyframeFrame = pegbar && pegbar->getKeyframeRange(k0, k1) && (k1 > k0 || k0 == row) && k0 <= row && row <= k1 + 1; - - bool isKeyFrameArea = - isKeyframeFrame && - ((o->isVerticalTimeline() && - o->rect(PredefinedRect::KEYFRAME_AREA) - .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) - .contains(mouseInCell)) - - || (!o->isVerticalTimeline() && - o->rect(PredefinedRect::FRAME_MARKER_AREA) - .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) - .contains(mouseInCell))) && - row < k1 + 1; bool accept = false; - if (isKeyFrameArea) { // They are in the keyframe selection - if (pegbar->isKeyframe(row)) // in the keyframe + if (isKeyframeFrame && + isKeyFrameArea(col, row, + mouseInCell)) { // They are in the keyframe selection + if (pegbar->isKeyframe(row)) // in the keyframe { m_viewer->setCurrentRow( row); // If you click on the key, change the current row as well @@ -2796,13 +2822,8 @@ void CellArea::mouseMoveEvent(QMouseEvent *event) { bool isKeyframeFrame = Preferences::instance()->isShowKeyframesOnXsheetCellAreaEnabled() && pegbar && pegbar->getKeyframeRange(k0, k1) && k0 <= row && row <= k1 + 1; - bool isKeyFrameArea = isKeyframeFrame && - o->rect(PredefinedRect::KEYFRAME_AREA) - .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) - .contains(mouseInCell) && - row < k1 + 1; - if (isKeyFrameArea) { + if (isKeyframeFrame && isKeyFrameArea(col, row, mouseInCell)) { if (pegbar->isKeyframe(row)) // key frame m_tooltip = tr("Click to select keyframe, drag to move it"); else { @@ -2926,14 +2947,8 @@ void CellArea::mouseDoubleClickEvent(QMouseEvent *event) { int k0, k1; bool isKeyframeFrame = pegbar && pegbar->getKeyframeRange(k0, k1) && k0 <= row && row <= k1 + 1; - bool isKeyFrameArea = isKeyframeFrame && - o->rect(PredefinedRect::KEYFRAME_AREA) - .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) - .contains(mouseInCell) && - row < k1 + 1; - // If you are in the keyframe area, open a function editor - if (isKeyFrameArea) { + if (isKeyframeFrame && isKeyFrameArea(col, row, mouseInCell)) { QAction *action = CommandManager::instance()->getAction(MI_OpenFunctionEditor); action->trigger(); @@ -2996,13 +3011,8 @@ void CellArea::contextMenuEvent(QContextMenuEvent *event) { bool isKeyframeFrame = Preferences::instance()->isShowKeyframesOnXsheetCellAreaEnabled() && pegbar && pegbar->getKeyframeRange(k0, k1) && k0 <= row && row <= k1 + 1; - bool isKeyFrameArea = isKeyframeFrame && - o->rect(PredefinedRect::KEYFRAME_AREA) - .adjusted(-frameAdj / 2, 0, -frameAdj / 2, 0) - .contains(mouseInCell) && - row < k1 + 1; - if (isKeyFrameArea) { + if (isKeyframeFrame && isKeyFrameArea(col, row, mouseInCell)) { TStageObjectId objectId; if (col < 0) objectId = TStageObjectId::CameraId(0); diff --git a/toonz/sources/toonz/xshcellviewer.h b/toonz/sources/toonz/xshcellviewer.h index a552fa6..43a219a 100644 --- a/toonz/sources/toonz/xshcellviewer.h +++ b/toonz/sources/toonz/xshcellviewer.h @@ -109,6 +109,8 @@ class CellArea final : public QWidget { // Restistusce true bool getEaseHandles(int r0, int r1, double e0, double e1, int &rh0, int &rh1); + bool isKeyFrameArea(int col, int row, QPoint mouseInCell); + DragTool *getDragTool() const; void setDragTool(DragTool *dragTool); diff --git a/toonz/sources/toonz/xshcolumnviewer.cpp b/toonz/sources/toonz/xshcolumnviewer.cpp index 6894f3b..e077e5a 100644 --- a/toonz/sources/toonz/xshcolumnviewer.cpp +++ b/toonz/sources/toonz/xshcolumnviewer.cpp @@ -788,8 +788,9 @@ void ColumnArea::DrawHeader::drawConfig() const { p.fillRect(configRect, bgColor); if (o->flag(PredefinedFlag::CONFIG_AREA_BORDER)) p.drawRect(configRect); - if (column->getSoundColumn() || column->getPaletteColumn() || - column->getSoundTextColumn()) + TXshZeraryFxColumn *zColumn = dynamic_cast(column); + + if (zColumn || column->getPaletteColumn() || column->getSoundTextColumn()) return; p.drawImage(configImgRect, icon); @@ -865,13 +866,6 @@ void ColumnArea::DrawHeader::drawColumnName() const { leftadj = 24; } - if (!o->isVerticalTimeline()) { - if (column->getSoundColumn()) - rightadj -= 97; - else if (column->getFilterColorId()) - rightadj -= 15; - } - p.setPen((isCurrent) ? m_viewer->getSelectedColumnTextColor() : nameBacklit ? Qt::black : m_viewer->getTextColor()); } else @@ -897,13 +891,14 @@ void ColumnArea::DrawHeader::drawThumbnail(QPixmap &iconPixmap) const { xsh->getColumn(col) ? xsh->getColumn(col)->getSoundColumn() : 0; drawSoundIcon(sc->isPlaying()); - drawVolumeControl(sc->getVolume()); + // Volume control now in config button. If no config button + // draw control + if (!o->flag(PredefinedFlag::CONFIG_AREA_VISIBLE)) + drawVolumeControl(sc->getVolume()); return; } - if (!o->isVerticalTimeline() || - !o->flag(PredefinedFlag::THUMBNAIL_AREA_VISIBLE)) - return; + if (!o->flag(PredefinedFlag::THUMBNAIL_AREA_VISIBLE)) return; QRect thumbnailImageRect = o->rect(PredefinedRect::THUMBNAIL).translated(orig); @@ -1112,7 +1107,8 @@ ColumnArea::ColumnArea(XsheetViewer *parent, Qt::WFlags flags) , m_col(-1) , m_columnTransparencyPopup(0) , m_transparencyPopupTimer(0) - , m_isPanning(false) { + , m_isPanning(false) + , m_soundColumnPopup(0) { TXsheetHandle *xsheetHandle = TApp::instance()->getCurrentXsheet(); #ifndef LINETEST TObjectHandle *objectHandle = TApp::instance()->getCurrentObject(); @@ -1359,7 +1355,7 @@ void ColumnArea::drawSoundColumnHead(QPainter &p, int col) { // AREA drawHeader.levelColors(columnColor, dragColor); drawHeader.drawBaseFill(columnColor, dragColor); drawHeader.drawEye(); - drawHeader.drawPreviewToggle(255); + drawHeader.drawPreviewToggle(sc ? (troundp(255.0 * sc->getVolume())) : 0); drawHeader.drawLock(); drawHeader.drawConfig(); drawHeader.drawColumnName(); @@ -1584,7 +1580,7 @@ using namespace DVGui; ColumnTransparencyPopup::ColumnTransparencyPopup(QWidget *parent) : QWidget(parent, Qt::Popup) { - setFixedWidth(8 + 30 + 8 + 100 + 8 + 8 + 8 + 7); + setFixedWidth(8 + 78 + 8 + 100 + 8 + 8 + 8 + 7); m_slider = new QSlider(Qt::Horizontal, this); m_slider->setMinimum(1); @@ -1610,6 +1606,7 @@ m_value->setFont(font);*/ } QLabel *filterLabel = new QLabel(tr("Filter:"), this); + QLabel *sliderLabel = new QLabel(tr("Opacity:"), this); QVBoxLayout *mainLayout = new QVBoxLayout(); mainLayout->setMargin(3); @@ -1619,6 +1616,7 @@ m_value->setFont(font);*/ // hlayout->setContentsMargins(0, 3, 0, 3); hlayout->setMargin(0); hlayout->setSpacing(3); + hlayout->addWidget(sliderLabel, 0); hlayout->addWidget(m_slider); hlayout->addWidget(m_value); hlayout->addWidget(new QLabel("%")); @@ -1722,6 +1720,106 @@ void ColumnTransparencyPopup::mouseReleaseEvent(QMouseEvent *e) { //------------------------------------------------------------------------------ +SoundColumnPopup::SoundColumnPopup(QWidget *parent) + : QWidget(parent, Qt::Popup) { + setFixedWidth(8 + 78 + 8 + 100 + 8 + 8 + 8 + 7); + + m_slider = new QSlider(Qt::Horizontal, this); + m_slider->setMinimum(0); + m_slider->setMaximum(100); + m_slider->setFixedHeight(14); + m_slider->setFixedWidth(100); + + m_value = new DVGui::IntLineEdit(this, 1, 1, 100); + + QLabel *sliderLabel = new QLabel(tr("Volume:"), this); + + QVBoxLayout *mainLayout = new QVBoxLayout(); + mainLayout->setMargin(3); + mainLayout->setSpacing(3); + { + QHBoxLayout *hlayout = new QHBoxLayout; + // hlayout->setContentsMargins(0, 3, 0, 3); + hlayout->setMargin(0); + hlayout->setSpacing(3); + hlayout->addWidget(sliderLabel, 0); + hlayout->addWidget(m_slider); + hlayout->addWidget(m_value); + hlayout->addWidget(new QLabel("%")); + mainLayout->addLayout(hlayout, 0); + } + setLayout(mainLayout); + + bool ret = connect(m_slider, SIGNAL(sliderReleased()), this, + SLOT(onSliderReleased())); + ret = ret && connect(m_slider, SIGNAL(sliderMoved(int)), this, + SLOT(onSliderChange(int))); + ret = ret && connect(m_slider, SIGNAL(valueChanged(int)), this, + SLOT(onSliderValueChanged(int))); + ret = ret && connect(m_value, SIGNAL(textChanged(const QString &)), this, + SLOT(onValueChanged(const QString &))); + assert(ret); +} + +//---------------------------------------------------------------- + +void SoundColumnPopup::onSliderValueChanged(int val) { + if (m_slider->isSliderDown()) return; + m_value->setText(QString::number(val)); + onSliderReleased(); +} + +void SoundColumnPopup::onSliderReleased() { + int val = m_slider->value(); + m_column->getSoundColumn()->setVolume(((double)val / 100.0)); + TApp::instance()->getCurrentXsheet()->notifyXsheetSoundChanged(); + TApp::instance()->getCurrentScene()->notifySceneChanged(); + TApp::instance()->getCurrentXsheet()->notifyXsheetChanged(); + ((ColumnArea *)parent())->update(); +} + +//----------------------------------------------------------------------- + +void SoundColumnPopup::onSliderChange(int val) { + disconnect(m_value, SIGNAL(textChanged(const QString &)), 0, 0); + m_value->setText(QString::number(val)); + connect(m_value, SIGNAL(textChanged(const QString &)), this, + SLOT(onValueChanged(const QString &))); +} + +//---------------------------------------------------------------- + +void SoundColumnPopup::onValueChanged(const QString &str) { + int val = str.toInt(); + m_slider->setValue(val); + m_column->getSoundColumn()->setVolume(((double)val / 100.0)); + + TApp::instance()->getCurrentXsheet()->notifyXsheetSoundChanged(); + TApp::instance()->getCurrentScene()->notifySceneChanged(); + TApp::instance()->getCurrentXsheet()->notifyXsheetChanged(); + ((ColumnArea *)parent())->update(); +} + +//---------------------------------------------------------------- + +void SoundColumnPopup::setColumn(TXshColumn *column) { + m_column = column; + assert(m_column); + double volume = m_column->getSoundColumn()->getVolume(); + int val = (int)troundp(100.0 * volume); + m_slider->setValue(val); + disconnect(m_value, SIGNAL(textChanged(const QString &)), 0, 0); + m_value->setText(QString::number(val)); + connect(m_value, SIGNAL(textChanged(const QString &)), this, + SLOT(onValueChanged(const QString &))); +} + +void SoundColumnPopup::mouseReleaseEvent(QMouseEvent *e) { + // hide(); +} + +//---------------------------------------------------------------- + void ColumnArea::openTransparencyPopup() { if (m_transparencyPopupTimer) m_transparencyPopupTimer->stop(); if (m_col < 0) return; @@ -1739,6 +1837,23 @@ void ColumnArea::openTransparencyPopup() { m_columnTransparencyPopup->show(); } +void ColumnArea::openSoundColumnPopup() { + if (m_col < 0) return; + TXshColumn *column = m_viewer->getXsheet()->getColumn(m_col); + if (!column || column->isEmpty()) return; + + if (!column->isCamstandVisible()) { + column->setCamstandVisible(true); + TApp::instance()->getCurrentXsheet()->notifyXsheetSoundChanged(); + TApp::instance()->getCurrentScene()->notifySceneChanged(); + TApp::instance()->getCurrentXsheet()->notifyXsheetChanged(); + update(); + } + + m_soundColumnPopup->setColumn(column); + m_soundColumnPopup->show(); +} + //---------------------------------------------------------------- void ColumnArea::startTransparencyPopupTimer(QMouseEvent *e) { // AREA @@ -1856,7 +1971,7 @@ void ColumnArea::mousePressEvent(QMouseEvent *event) { TXshZeraryFxColumn *zColumn = dynamic_cast(column); - if (zColumn || column->getSoundColumn() || column->getPaletteColumn() || + if (zColumn || column->getPaletteColumn() || column->getSoundTextColumn()) { // do nothing } else @@ -1884,7 +1999,8 @@ void ColumnArea::mousePressEvent(QMouseEvent *event) { QTimer::singleShot(interval, this, SLOT(update())); } update(); - } else if (o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) + } else if (!o->flag(PredefinedFlag::CONFIG_AREA_VISIBLE) && + o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) setDragTool(XsheetGUI::DragTool::makeVolumeDragTool(m_viewer)); else setDragTool(XsheetGUI::DragTool::makeColumnSelectionTool(m_viewer)); @@ -1999,7 +2115,8 @@ void ColumnArea::mouseMoveEvent(QMouseEvent *event) { // sound column if (o->rect(PredefinedRect::SOUND_ICON).contains(mouseInCell)) m_tooltip = tr("Click to play the soundtrack back"); - else if (o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) + else if (!o->flag(PredefinedFlag::CONFIG_AREA_VISIBLE) && + o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) m_tooltip = tr("Set the volume of the soundtrack"); } else m_tooltip = tr("Click to select column, double-click to edit"); @@ -2017,7 +2134,8 @@ void ColumnArea::mouseMoveEvent(QMouseEvent *event) { // sound column if (o->rect(PredefinedRect::SOUND_ICON).contains(mouseInCell)) m_tooltip = tr("Click to play the soundtrack back"); - else if (o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) + else if (!o->flag(PredefinedFlag::CONFIG_AREA_VISIBLE) && + o->rect(PredefinedRect::VOLUME_AREA).contains(mouseInCell)) m_tooltip = tr("Set the volume of the soundtrack"); } else if (Preferences::instance()->getColumnIconLoadingPolicy() == Preferences::LoadOnDemand) @@ -2057,9 +2175,6 @@ void ColumnArea::mouseReleaseEvent(QMouseEvent *event) { else if (m_doOnRelease == ToggleLock) column->lock(!column->isLocked()); else if (m_doOnRelease == OpenSettings) { - if (!m_columnTransparencyPopup) - m_columnTransparencyPopup = new ColumnTransparencyPopup(this); - // Align popup to be below to CONFIG button QRect configRect = m_viewer->orientation()->rect(PredefinedRect::CONFIG_AREA); @@ -2073,10 +2188,24 @@ void ColumnArea::mouseReleaseEvent(QMouseEvent *event) { int y = mouseInCell.y() - configRect.bottom(); // distance from bottum edge of CONFIG button - m_columnTransparencyPopup->move(event->globalPos().x() + x, - event->globalPos().y() - y); - openTransparencyPopup(); + if (column->getSoundColumn()) { + if (!m_soundColumnPopup) + m_soundColumnPopup = new SoundColumnPopup(this); + + m_soundColumnPopup->move(event->globalPos().x() + x, + event->globalPos().y() - y); + + openSoundColumnPopup(); + } else { + if (!m_columnTransparencyPopup) + m_columnTransparencyPopup = new ColumnTransparencyPopup(this); + + m_columnTransparencyPopup->move(event->globalPos().x() + x, + event->globalPos().y() - y); + + openTransparencyPopup(); + } } else if (m_doOnRelease == ToggleAllPreviewVisible) { for (col = 0; col < totcols; col++) { TXshColumn *column = xsh->getColumn(col); diff --git a/toonz/sources/toonz/xshcolumnviewer.h b/toonz/sources/toonz/xshcolumnviewer.h index 82fda4d..d006981 100644 --- a/toonz/sources/toonz/xshcolumnviewer.h +++ b/toonz/sources/toonz/xshcolumnviewer.h @@ -178,6 +178,28 @@ protected slots: void onFilterColorChanged(int id); }; +class SoundColumnPopup final : public QWidget { + Q_OBJECT + + QSlider *m_slider; + QLineEdit *m_value; + TXshColumn *m_column; + +public: + SoundColumnPopup(QWidget *parent); + void setColumn(TXshColumn *column); + +protected: + // void mouseMoveEvent ( QMouseEvent * e ); + void mouseReleaseEvent(QMouseEvent *e) override; + +protected slots: + void onSliderReleased(); + void onSliderChange(int val); + void onSliderValueChanged(int); + void onValueChanged(const QString &); +}; + //! The class in charge of the region showing layer headers class ColumnArea final : public QWidget { Q_OBJECT @@ -193,6 +215,7 @@ class ColumnArea final : public QWidget { }; ColumnTransparencyPopup *m_columnTransparencyPopup; + SoundColumnPopup *m_soundColumnPopup; QTimer *m_transparencyPopupTimer; int m_doOnRelease; XsheetViewer *m_viewer; @@ -302,6 +325,7 @@ protected: protected slots: void onSubSampling(QAction *); void openTransparencyPopup(); + void openSoundColumnPopup(); }; //----------------------------------------------------------------------------- diff --git a/toonz/sources/toonzlib/orientation.cpp b/toonz/sources/toonzlib/orientation.cpp index eb2b13f..de5de1b 100644 --- a/toonz/sources/toonzlib/orientation.cpp +++ b/toonz/sources/toonzlib/orientation.cpp @@ -80,8 +80,8 @@ public: class LeftToRightOrientation : public Orientation { const int CELL_WIDTH = 50; - const int CELL_HEIGHT = 20; - const int CELL_DRAG_HEIGHT = 5; + const int CELL_HEIGHT = 24; + const int CELL_DRAG_HEIGHT = 7; const int EXTENDER_WIDTH = 8; const int EXTENDER_HEIGHT = 12; const int SOUND_PREVIEW_HEIGHT = 6; @@ -92,14 +92,17 @@ class LeftToRightOrientation : public Orientation { const int ICON_HEIGHT = 20; const int ICON_OFFSET = ICON_WIDTH; const int ICONS_WIDTH = ICON_OFFSET * 4; // 88 + const int THUMBNAIL_WIDTH = 43; const int LAYER_NUMBER_WIDTH = 20; const int LAYER_NAME_WIDTH = 150; const int LAYER_HEADER_WIDTH = - ICONS_WIDTH + LAYER_NUMBER_WIDTH + LAYER_NAME_WIDTH; + ICONS_WIDTH + THUMBNAIL_WIDTH + LAYER_NUMBER_WIDTH + LAYER_NAME_WIDTH; const int FOLDED_LAYER_HEADER_HEIGHT = 8; const int FOLDED_LAYER_HEADER_WIDTH = LAYER_HEADER_WIDTH; const int TRACKLEN = 60; const int SHIFTTRACE_DOT_OFFSET = 5; + const int LAYER_HEADER_PANEL_HEIGHT = 20; + const int LAYER_FOOTER_PANEL_HEIGHT = 16; public: LeftToRightOrientation(); @@ -315,7 +318,13 @@ TopToBottomOrientation::TopToBottomOrientation() { QRect(QPoint(0, 0), QSize(FRAME_HEADER_WIDTH, use_header_height - 1))); addRect(PredefinedRect::NOTE_ICON, QRect(QPoint(0, 0), QSize(CELL_WIDTH - 2, CELL_HEIGHT - 2))); - addRect(PredefinedRect::LAYER_HEADER_PANEL, QRect(0, 0, -1, -1)); // hide + + // Layer header panel + addRect(PredefinedRect::LAYER_HEADER_PANEL, QRect(0, 0, -1, -1)); // hide + addRect(PredefinedRect::PANEL_EYE, QRect(0, 0, -1, -1)); // hide + addRect(PredefinedRect::PANEL_PREVIEW_LAYER, QRect(0, 0, -1, -1)); // hide + addRect(PredefinedRect::PANEL_LOCK, QRect(0, 0, -1, -1)); // hide + addRect(PredefinedRect::PANEL_LAYER_NAME, QRect(0, 0, -1, -1)); // hide // Row viewer addRect(PredefinedRect::FRAME_LABEL, @@ -442,9 +451,11 @@ TopToBottomOrientation::TopToBottomOrientation() { QRect(thumbnail.right() - 14, thumbnail.top() + 3, 12, 12)); addRect(PredefinedRect::SOUND_ICON, - QRect(thumbnailArea.topLeft(), QSize(27, 20)) - .adjusted((thumbnailArea.width() / 2) - (27 / 2), 3, - (thumbnailArea.width() / 2) - (27 / 2), 3)); + QRect(thumbnailArea.topLeft(), QSize(40, 30)) + .adjusted((thumbnailArea.width() / 2) - (40 / 2), + (thumbnailArea.height() / 2) - (30 / 2), + (thumbnailArea.width() / 2) - (40 / 2), + (thumbnailArea.height() / 2) - (30 / 2))); volumeArea = QRect(QPoint(thumbnailArea.left() + 3, thumbnailArea.bottom() - 16), @@ -545,9 +556,11 @@ TopToBottomOrientation::TopToBottomOrientation() { QRect(thumbnail.right() - 14, thumbnail.top() + 3, 12, 12)); addRect(PredefinedRect::SOUND_ICON, - QRect(thumbnailArea.topLeft(), QSize(27, 20)) - .adjusted((thumbnailArea.width() / 2) - (27 / 2), 3, - (thumbnailArea.width() / 2) - (27 / 2), 3)); + QRect(thumbnailArea.topLeft(), QSize(40, 30)) + .adjusted((thumbnailArea.width() / 2) - (40 / 2), + (thumbnailArea.height() / 2) - (30 / 2), + (thumbnailArea.width() / 2) - (40 / 2), + (thumbnailArea.height() / 2) - (30 / 2))); volumeArea = QRect(QPoint(thumbnailArea.left() + 3, thumbnailArea.bottom() - 16), @@ -888,15 +901,16 @@ LeftToRightOrientation::LeftToRightOrientation() { addRect(PredefinedRect::DRAG_HANDLE_CORNER, QRect(0, 0, CELL_WIDTH, CELL_DRAG_HEIGHT)); QRect keyRect((CELL_WIDTH - KEY_ICON_WIDTH) / 2, - CELL_HEIGHT - KEY_ICON_HEIGHT, KEY_ICON_WIDTH, KEY_ICON_HEIGHT); + CELL_HEIGHT - KEY_ICON_HEIGHT - 2, KEY_ICON_WIDTH, + KEY_ICON_HEIGHT); addRect(PredefinedRect::KEY_ICON, keyRect); QRect nameRect = cellRect.adjusted(4, 4, -6, 0); addRect(PredefinedRect::CELL_NAME, nameRect); addRect(PredefinedRect::CELL_NAME_WITH_KEYFRAME, nameRect); addRect(PredefinedRect::END_EXTENDER, - QRect(0, -EXTENDER_HEIGHT - 10, EXTENDER_WIDTH, EXTENDER_HEIGHT)); + QRect(0, -EXTENDER_HEIGHT - 14, EXTENDER_WIDTH, EXTENDER_HEIGHT)); addRect(PredefinedRect::BEGIN_EXTENDER, - QRect(-EXTENDER_WIDTH, -EXTENDER_HEIGHT - 10, EXTENDER_WIDTH, + QRect(-EXTENDER_WIDTH, -EXTENDER_HEIGHT - 14, EXTENDER_WIDTH, EXTENDER_HEIGHT)); addRect(PredefinedRect::KEYFRAME_AREA, keyRect); addRect(PredefinedRect::DRAG_AREA, QRect(0, 0, CELL_WIDTH, CELL_DRAG_HEIGHT)); @@ -913,7 +927,7 @@ LeftToRightOrientation::LeftToRightOrientation() { CELL_HEIGHT - CELL_DRAG_HEIGHT)); addRect(PredefinedRect::LOOP_ICON, QRect(0, keyRect.top(), 10, 11)); QRect frameMarker((CELL_WIDTH - FRAME_MARKER_SIZE) / 2 - 1, - CELL_HEIGHT - FRAME_MARKER_SIZE - 6, FRAME_MARKER_SIZE, + CELL_HEIGHT - FRAME_MARKER_SIZE - 7, FRAME_MARKER_SIZE, FRAME_MARKER_SIZE); addRect(PredefinedRect::FRAME_MARKER_AREA, frameMarker); @@ -923,9 +937,21 @@ LeftToRightOrientation::LeftToRightOrientation() { QRect(QPoint(0, 0), QSize(LAYER_HEADER_WIDTH - 1, FRAME_HEADER_HEIGHT))); addRect(PredefinedRect::NOTE_ICON, QRect(QPoint(0, 0), QSize(CELL_WIDTH - 2, CELL_HEIGHT - 2))); + + // Layer header panel addRect(PredefinedRect::LAYER_HEADER_PANEL, QRect(0, FRAME_HEADER_HEIGHT - CELL_HEIGHT, LAYER_HEADER_WIDTH, - CELL_HEIGHT)); + LAYER_HEADER_PANEL_HEIGHT)); + QRect panelEye(1, 0, ICON_WIDTH, ICON_HEIGHT); + addRect(PredefinedRect::PANEL_EYE, panelEye.adjusted(1, 1, -1, -1)); + addRect(PredefinedRect::PANEL_PREVIEW_LAYER, + panelEye.translated(ICON_OFFSET, 0).adjusted(1, 1, -1, -1)); + addRect(PredefinedRect::PANEL_LOCK, + panelEye.translated(2 * ICON_OFFSET, 0).adjusted(1, 1, -1, -1)); + QRect panelName(ICONS_WIDTH + THUMBNAIL_WIDTH + 1, 0, + LAYER_NAME_WIDTH + LAYER_NUMBER_WIDTH - 4, + LAYER_HEADER_PANEL_HEIGHT); + addRect(PredefinedRect::PANEL_LAYER_NAME, panelName); // Row viewer addRect(PredefinedRect::FRAME_LABEL, @@ -975,60 +1001,72 @@ LeftToRightOrientation::LeftToRightOrientation() { addRect( PredefinedRect::FOLDED_LAYER_HEADER, QRect(1, 0, FOLDED_LAYER_HEADER_WIDTH - 2, FOLDED_LAYER_HEADER_HEIGHT)); - QRect columnName(ICONS_WIDTH + 1, 0, + QRect columnName(ICONS_WIDTH + THUMBNAIL_WIDTH + 1, 0, LAYER_NAME_WIDTH + LAYER_NUMBER_WIDTH - 4, CELL_HEIGHT); addRect(PredefinedRect::RENAME_COLUMN, columnName); - QRect eye(1, 0, ICON_WIDTH, ICON_HEIGHT); - addRect(PredefinedRect::EYE_AREA, eye); + QRect eyeArea(1, 0, ICON_WIDTH, CELL_HEIGHT); + QRect eye(1, + eyeArea.top() + ((eyeArea.height() / 2) - ((ICON_HEIGHT - 1) / 2)), + ICON_WIDTH, ICON_HEIGHT); + addRect(PredefinedRect::EYE_AREA, eyeArea); addRect(PredefinedRect::EYE, eye.adjusted(1, 1, -1, -1)); - addRect(PredefinedRect::PREVIEW_LAYER_AREA, eye.translated(ICON_OFFSET, 0)); + addRect(PredefinedRect::PREVIEW_LAYER_AREA, + eyeArea.translated(ICON_OFFSET, 0)); addRect(PredefinedRect::PREVIEW_LAYER, eye.translated(ICON_OFFSET, 0).adjusted(1, 1, -1, -1)); - addRect(PredefinedRect::LOCK_AREA, eye.translated(2 * ICON_OFFSET, 0)); + addRect(PredefinedRect::LOCK_AREA, eyeArea.translated(2 * ICON_OFFSET, 0)); addRect(PredefinedRect::LOCK, eye.translated(2 * ICON_OFFSET, 0).adjusted(1, 1, -1, -1)); - addRect(PredefinedRect::CONFIG_AREA, eye.translated(3 * ICON_OFFSET, 0)); + addRect(PredefinedRect::CONFIG_AREA, eyeArea.translated(3 * ICON_OFFSET, 0)); addRect(PredefinedRect::CONFIG, eye.translated(3 * ICON_OFFSET, 0).adjusted(1, 1, -1, -1)); addRect(PredefinedRect::DRAG_LAYER, - QRect(ICONS_WIDTH + 1, 0, LAYER_HEADER_WIDTH - ICONS_WIDTH - 3, + QRect(ICONS_WIDTH + THUMBNAIL_WIDTH + 1, 0, + LAYER_HEADER_WIDTH - ICONS_WIDTH - THUMBNAIL_WIDTH - 3, CELL_DRAG_HEIGHT)); addRect(PredefinedRect::LAYER_NAME, columnName); addRect(PredefinedRect::LAYER_NUMBER, - QRect(ICONS_WIDTH + 1, 0, LAYER_NUMBER_WIDTH, CELL_HEIGHT)); - addRect(PredefinedRect::THUMBNAIL_AREA, QRect(0, 0, -1, -1)); // hide - addRect(PredefinedRect::THUMBNAIL, QRect(0, 0, -1, -1)); // hide + QRect(ICONS_WIDTH + THUMBNAIL_WIDTH + 1, 0, LAYER_NUMBER_WIDTH, + CELL_HEIGHT)); + QRect thumbnailArea = QRect(ICONS_WIDTH + 1, 0, THUMBNAIL_WIDTH, CELL_HEIGHT); + addRect(PredefinedRect::THUMBNAIL_AREA, thumbnailArea); + QRect thumbnail = thumbnailArea.adjusted(1, 1, 0, 0); + addRect(PredefinedRect::THUMBNAIL, thumbnail); addRect(PredefinedRect::FILTER_COLOR, - QRect(LAYER_HEADER_WIDTH - 17, 6, 12, 12)); + QRect(thumbnail.right() - 14, thumbnail.top() + 3, 12, 12)); addRect(PredefinedRect::PEGBAR_NAME, QRect(0, 0, -1, -1)); // hide addRect(PredefinedRect::PARENT_HANDLE_NAME, QRect(0, 0, -1, -1)); // hide addRect(PredefinedRect::SOUND_ICON, - QRect(columnName.topRight(), QSize(27, columnName.height())) - .adjusted(-28, 0, -28, 0)); + QRect(thumbnailArea.topLeft(), QSize(27, thumbnailArea.height())) + .adjusted((thumbnailArea.width() / 2) - (27 / 2), 0, + (thumbnailArea.width() / 2) - (27 / 2), 0)); - QRect volumeArea(QRect(columnName.topRight(), QSize(TRACKLEN + 8, 14)) - .adjusted(-97, 4, -97, 4)); + QRect volumeArea( + QRect(columnName.topRight(), QSize(TRACKLEN + 8, 14)) + .adjusted(-77, CELL_DRAG_HEIGHT + 1, -77, CELL_DRAG_HEIGHT + 1)); addRect(PredefinedRect::VOLUME_AREA, volumeArea); QPoint soundTopLeft(volumeArea.left() + 4, volumeArea.bottom() - 6); addRect(PredefinedRect::VOLUME_TRACK, QRect(soundTopLeft, QSize(TRACKLEN, 3))); // Layer footer panel - QRect layerFooterPanel(QRect(0, 0, LAYER_HEADER_WIDTH + 2, 16)); + QRect layerFooterPanel( + QRect(0, 0, LAYER_HEADER_WIDTH + 2, LAYER_FOOTER_PANEL_HEIGHT)); addRect(PredefinedRect::LAYER_FOOTER_PANEL, layerFooterPanel); QRect zoomSlider, zoomIn, zoomOut; - zoomSlider = QRect(layerFooterPanel.width() - 100, 0, 81, 16); + zoomSlider = + QRect(layerFooterPanel.width() - 100, 0, 81, LAYER_FOOTER_PANEL_HEIGHT); addRect(PredefinedRect::ZOOM_SLIDER_AREA, zoomSlider); addRect(PredefinedRect::ZOOM_SLIDER, zoomSlider.adjusted(1, 0, 0, 0)); - zoomIn = QRect(zoomSlider.right() + 1, 0, 16, 16); + zoomIn = QRect(zoomSlider.right() + 1, 0, 16, LAYER_FOOTER_PANEL_HEIGHT); addRect(PredefinedRect::ZOOM_IN_AREA, zoomIn); addRect(PredefinedRect::ZOOM_IN, zoomIn.adjusted(1, 1, 0, 0)); - zoomOut = QRect(zoomSlider.left() - 16, 0, 16, 16); + zoomOut = QRect(zoomSlider.left() - 16, 0, 16, LAYER_FOOTER_PANEL_HEIGHT); addRect(PredefinedRect::ZOOM_OUT_AREA, zoomOut); addRect(PredefinedRect::ZOOM_OUT, zoomOut.adjusted(1, 1, 0, 0)); @@ -1051,8 +1089,8 @@ LeftToRightOrientation::LeftToRightOrientation() { addFlag(PredefinedFlag::PEGBAR_NAME_VISIBLE, false); addFlag(PredefinedFlag::PARENT_HANDLE_NAME_BORDER, false); addFlag(PredefinedFlag::PARENT_HANDLE_NAME_VISIBILE, false); - addFlag(PredefinedFlag::THUMBNAIL_AREA_BORDER, false); - addFlag(PredefinedFlag::THUMBNAIL_AREA_VISIBLE, false); + addFlag(PredefinedFlag::THUMBNAIL_AREA_BORDER, true); + addFlag(PredefinedFlag::THUMBNAIL_AREA_VISIBLE, true); addFlag(PredefinedFlag::VOLUME_AREA_VERTICAL, false); //