diff --git a/src/Gui/GcSideBarItem.cpp b/src/Gui/GcSideBarItem.cpp index 44a70fb18..51be22b8c 100644 --- a/src/Gui/GcSideBarItem.cpp +++ b/src/Gui/GcSideBarItem.cpp @@ -290,8 +290,8 @@ GcSplitterHandle::init(QString title, Qt::Orientation orientation, // set handle size according to font metric QFont font; QFontMetrics fm(font); - bigHandle = fm.height() + 5; - smallHandle = fm.height() + 2; + bigHandle = fm.height() + 8; + smallHandle = fm.height() + 5; // use the sizes as set if (metal) setFixedHeight(bigHandle); @@ -347,7 +347,7 @@ GcSplitterHandle::addActions(QList actions) QToolButton *p = new QToolButton(this); p->setStyleSheet("QToolButton { border: none; padding: 0px; }"); p->setAutoFillBackground(false); - p->setFixedSize(20*dpiXFactor,20*dpiYFactor); + p->setFixedSize(22*dpiXFactor,22*dpiYFactor); p->setIcon(action->icon()); p->setIconSize(QSize(10*dpiXFactor,10*dpiYFactor)); p->setFocusPolicy(Qt::NoFocus); @@ -402,7 +402,7 @@ GcSplitterHandle::paintBackground(QPaintEvent *) GcSplitterControl::GcSplitterControl(QWidget *parent) : QToolBar(parent) { setContentsMargins(0,0,0,0); - setFixedHeight(20 *dpiYFactor); + setFixedHeight(22 *dpiYFactor); setIconSize(QSize(14 *dpiXFactor,14 *dpiYFactor)); setToolButtonStyle(Qt::ToolButtonIconOnly); setAutoFillBackground(false); @@ -429,8 +429,8 @@ GcSplitterControl::paintBackground(QPaintEvent *) // setup a painter and the area to paint QPainter painter(this); - QLinearGradient active = GCColor::linearGradient(20 *dpiYFactor, true); - QLinearGradient inactive = GCColor::linearGradient(20 *dpiYFactor, false); + QLinearGradient active = GCColor::linearGradient(22 *dpiYFactor, true); + QLinearGradient inactive = GCColor::linearGradient(22 *dpiYFactor, false); // fill with a linear gradient painter.setPen(Qt::NoPen); diff --git a/src/Gui/GcToolBar.cpp b/src/Gui/GcToolBar.cpp index d9fb53ba7..36f1e83c4 100644 --- a/src/Gui/GcToolBar.cpp +++ b/src/Gui/GcToolBar.cpp @@ -24,7 +24,7 @@ GcToolBar::GcToolBar(QWidget *parent) : QWidget(parent) //Height will be set when widget is added in MainWindow setContentsMargins(0,0,0,0); layout = new QHBoxLayout(this); - layout->setSpacing(10 *dpiXFactor); + layout->setSpacing(5 *dpiXFactor); layout->setContentsMargins(0,0,0,0); installEventFilter(this); } diff --git a/src/Gui/GcToolBar.h b/src/Gui/GcToolBar.h index fe7972db8..31bc58202 100644 --- a/src/Gui/GcToolBar.h +++ b/src/Gui/GcToolBar.h @@ -24,6 +24,7 @@ #include #include #include +#include "Colors.h" class GcToolBar : public QWidget { @@ -48,10 +49,10 @@ class Spacer : public QWidget { public: Spacer(QWidget *parent) : QWidget(parent) { - QSizePolicy sizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed); + QSizePolicy sizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); setSizePolicy(sizePolicy); } - QSize sizeHint() const { return QSize(10, 1); } + QSize sizeHint() const { return QSize(40*dpiXFactor, 1); } }; #endif diff --git a/src/Gui/MainWindow.cpp b/src/Gui/MainWindow.cpp index a49a851cc..4af6d4af4 100644 --- a/src/Gui/MainWindow.cpp +++ b/src/Gui/MainWindow.cpp @@ -88,9 +88,9 @@ // GUI Widgets #include "Tab.h" #include "GcToolBar.h" +#include "NewSideBar.h" #include "HelpWindow.h" #include "HomeWindow.h" -#include "GcScopeBar.h" #if !defined(Q_OS_MAC) #include "QTFullScreen.h" // not mac! #endif @@ -214,14 +214,38 @@ MainWindow::MainWindow(const QDir &home) appsettings->setValue(GC_SETTINGS_LAST, context->athlete->home->root().dirName()); /*---------------------------------------------------------------------- - * ScopeBar + * ScopeBar as sidebar from v3.6 *--------------------------------------------------------------------*/ - scopebar = new GcScopeBar(context); - connect(scopebar, SIGNAL(selectDiary()), this, SLOT(selectDiary())); - connect(scopebar, SIGNAL(selectHome()), this, SLOT(selectHome())); - connect(scopebar, SIGNAL(selectAnal()), this, SLOT(selectAnalysis())); - connect(scopebar, SIGNAL(selectTrain()), this, SLOT(selectTrain())); - connect(scopebar, SIGNAL(selectInterval()), this, SLOT(selectInterval())); + + sidebar = new NewSideBar(context, this); + sidebar->addItem(QImage(":sidebar/athlete.png"), tr("athletes"), 0); + sidebar->setItemEnabled(0, false); + + sidebar->addItem(QImage(":sidebar/plan.png"), tr("plan"), 1); + sidebar->setItemEnabled(1, false); + + sidebar->addItem(QImage(":sidebar/trends.png"), tr("trends"), 2); + sidebar->addItem(QImage(":sidebar/assess.png"), tr("activities"), 3); + sidebar->setItemSelected(3, true); + + sidebar->addItem(QImage(":sidebar/reflect.png"), tr("reflect"), 4); + sidebar->setItemEnabled(4, false); + + sidebar->addItem(QImage(":sidebar/train.png"), tr("train"), 5); + + sidebar->addStretch(); + sidebar->addItem(QImage(":sidebar/apps.png"), tr("apps"), 6); + sidebar->setItemEnabled(6, false); + sidebar->addStretch(); + + // we can click on the quick icons, but they aren't selectable views + sidebar->addItem(QImage(":sidebar/sync.png"), tr("sync"), 7); + sidebar->setItemSelectable(7, false); + sidebar->addItem(QImage(":sidebar/prefs.png"), tr("settings"), 8); + sidebar->setItemSelectable(8, false); + + connect(sidebar, SIGNAL(itemClicked(int)), this, SLOT(sidebarClicked(int))); + connect(sidebar, SIGNAL(itemSelected(int)), this, SLOT(sidebarSelected(int))); /*---------------------------------------------------------------------- * What's this Context Help @@ -266,16 +290,16 @@ MainWindow::MainWindow(const QDir &home) HelpWhatsThis *helpLowBar = new HelpWhatsThis(lowbar); lowbar->setWhatsThis(helpLowBar->getWhatsThisText(HelpWhatsThis::ToolBar_ToggleComparePane)); - sidebar = new QPushButton(this); - sidebar->setIcon(sidebarIcon); - sidebar->setFixedHeight(24 * dpiYFactor); - sidebar->setIconSize(isize); - sidebar->setStyle(toolStyle); - sidebar->setToolTip(tr("Toggle Sidebar")); - sidebar->setPalette(metal); - connect(sidebar, SIGNAL(clicked(bool)), this, SLOT(toggleSidebar())); - HelpWhatsThis *helpSideBar = new HelpWhatsThis(sidebar); - sidebar->setWhatsThis(helpSideBar->getWhatsThisText(HelpWhatsThis::ToolBar_ToggleSidebar)); + sidelist = new QPushButton(this); + sidelist->setIcon(sidebarIcon); + sidelist->setFixedHeight(24 * dpiYFactor); + sidelist->setIconSize(isize); + sidelist->setStyle(toolStyle); + sidelist->setToolTip(tr("Toggle Sidebar")); + sidelist->setPalette(metal); + connect(sidelist, SIGNAL(clicked(bool)), this, SLOT(toggleSidebar())); + HelpWhatsThis *helpSideBar = new HelpWhatsThis(sidelist); + sidelist->setWhatsThis(helpSideBar->getWhatsThisText(HelpWhatsThis::ToolBar_ToggleSidebar)); styleSelector = new QtSegmentControl(this); styleSelector->setStyle(toolStyle); @@ -295,37 +319,35 @@ MainWindow::MainWindow(const QDir &home) if (dpiXFactor > 1) { QString nopad = QString("QPushButton { padding-left: 0px; padding-right: 0px; " " padding-top: 0px; padding-bottom: 0px; }"); - sidebar->setStyleSheet(nopad); + sidelist->setStyleSheet(nopad); lowbar->setStyleSheet(nopad); } #endif - head->addWidget(new Spacer(this)); - head->addStretch(); - head->addWidget(scopebar); - head->addStretch(); - head->addWidget(sidebar); - head->addWidget(lowbar); - head->addWidget(styleSelector); - head->setFixedHeight(scopebar->height() + 7); - // add a search box on far right, but with a little space too searchBox = new SearchFilterBox(this,context,false); - anim = new QPropertyAnimation(searchBox, "xwidth", this); searchBox->setStyle(toolStyle); - searchBox->setFixedWidth(150 * dpiYFactor); - head->addWidget(searchBox); + searchBox->setFixedWidth(400 * dpiXFactor); + searchBox->setFixedHeight(28 * dpiYFactor); + head->addStretch(); + head->addWidget(sidelist); + head->addWidget(lowbar); + head->addWidget(styleSelector); + head->setFixedHeight(searchBox->height() + (10 *dpiXFactor)); + connect(searchBox, SIGNAL(searchResults(QStringList)), this, SLOT(setFilter(QStringList))); connect(searchBox, SIGNAL(searchClear()), this, SLOT(clearFilter())); - connect(searchBox->searchbox, SIGNAL(haveFocus()), this, SLOT(searchFocusIn())); - connect(searchBox->searchbox, SIGNAL(lostFocus()), this, SLOT(searchFocusOut())); HelpWhatsThis *helpSearchBox = new HelpWhatsThis(searchBox); searchBox->setWhatsThis(helpSearchBox->getWhatsThisText(HelpWhatsThis::SearchFilterBox)); Spacer *spacer = new Spacer(this); spacer->setFixedWidth(5 *dpiYFactor); head->addWidget(spacer); + head->addWidget(searchBox); + spacer = new Spacer(this); + spacer->setFixedWidth(5 *dpiYFactor); + head->addWidget(spacer); /*---------------------------------------------------------------------- @@ -364,8 +386,17 @@ MainWindow::MainWindow(const QDir &home) mainLayout->setSpacing(0); mainLayout->setContentsMargins(0,0,0,0); mainLayout->addWidget(head); - mainLayout->addWidget(tabbar); - mainLayout->addWidget(tabStack); + QHBoxLayout *lrlayout = new QHBoxLayout(); + mainLayout->addLayout(lrlayout); + lrlayout->setSpacing(0); + lrlayout->setContentsMargins(0,0,0,0); + lrlayout->addWidget(sidebar); + QVBoxLayout *tablayout = new QVBoxLayout(); + tablayout->setSpacing(0); + tablayout->setContentsMargins(0,0,0,0); + lrlayout->addLayout(tablayout); + tablayout->addWidget(tabbar); + tablayout->addWidget(tabStack); setCentralWidget(central); /*---------------------------------------------------------------------- @@ -561,7 +592,6 @@ MainWindow::MainWindow(const QDir &home) viewMenu->addSeparator(); viewMenu->addAction(tr("Activities"), this, SLOT(selectAnalysis())); viewMenu->addAction(tr("Trends"), this, SLOT(selectHome())); - viewMenu->addAction(tr("Train"), this, SLOT(selectTrain())); #ifdef GC_HAVE_ICAL viewMenu->addAction(tr("Diary"), this, SLOT(selectDiary())); #endif @@ -959,6 +989,7 @@ MainWindow::moveEvent(QMoveEvent*) void MainWindow::closeEvent(QCloseEvent* event) { + fprintf(stderr,"window close started\n"); fflush(stderr); QList closing = tabList; bool needtosave = false; bool importrunning = false; @@ -1008,6 +1039,8 @@ MainWindow::closeEvent(QCloseEvent* event) } appsettings->setValue(GC_SETTINGS_MAIN_GEOM, saveGeometry()); appsettings->setValue(GC_SETTINGS_MAIN_STATE, saveState()); + + fprintf(stderr,"window close compeleted\n"); fflush(stderr); } MainWindow::~MainWindow() @@ -1147,6 +1180,34 @@ MainWindow::support() QDesktopServices::openUrl(QUrl("https://groups.google.com/forum/#!forum/golden-cheetah-users")); } +void +MainWindow::sidebarClicked(int id) +{ + // sync quick link + if (id == 7) checkCloud(); + + // prefs + if (id == 8) showOptions(); + +} + +void +MainWindow::sidebarSelected(int id) +{ + switch (id) { + case 0: // athlete not written yet + case 1: // plan not written yet + break; + case 2: selectHome(); break; + case 3: selectAnalysis(); break; + case 4: // reflect not written yet + break; + case 5: selectTrain(); break; + case 6: // apps not written yet + break; + } +} + void MainWindow::selectAnalysis() { @@ -1223,12 +1284,9 @@ MainWindow::setToolButtons() } #endif #ifdef Q_OS_MAC // bizarre issue with searchbox focus on tab voew change - anim->stop(); searchBox->clearFocus(); searchFocusOut(); - scopebar->setFocus(Qt::TabFocusReason); #endif - scopebar->setSelected(index); } /*---------------------------------------------------------------------- @@ -1923,7 +1981,6 @@ MainWindow::saveGCState(Context *context) context->showToolbar = showhideToolbar->isChecked(); context->searchText = searchBox->text(); context->style = styleAction->isChecked(); - context->setIndex(scopebar->selected()); } void @@ -1934,9 +1991,6 @@ MainWindow::restoreGCState(Context *context) showToolbar(context->showToolbar); //showTabbar(context->showTabbar); showLowbar(context->showLowbar); - scopebar->setSelected(context->viewIndex); - scopebar->setContext(context); - scopebar->setHighlighted(); // to reflect context searchBox->setContext(context); searchBox->setText(context->searchText); } @@ -2266,26 +2320,6 @@ void MainWindow::showCreateFixPyScriptDlg() { } #endif -// grow/shrink searchbox if there is space... -void -MainWindow::searchFocusIn() -{ - if (searchBox->searchbox->hasFocus()) { - anim->setDuration(300); - anim->setEasingCurve(QEasingCurve::InOutQuad); - anim->setStartValue(searchBox->width()); - anim->setEndValue(500 * dpiYFactor); - anim->start(); - } -} - -void -MainWindow::searchFocusOut() -{ - anim->stop(); - searchBox->setFixedWidth(150 *dpiYFactor); -} - #ifdef GC_HAS_CLOUD_DB void MainWindow::cloudDBuserEditChart() diff --git a/src/Gui/MainWindow.h b/src/Gui/MainWindow.h index 02dcb8033..602376938 100644 --- a/src/Gui/MainWindow.h +++ b/src/Gui/MainWindow.h @@ -62,6 +62,7 @@ class QtSegmentControl; class SaveSingleDialogWidget; class ChooseCyclistDialog; class SearchFilterBox; +class NewSideBar; class MainWindow; @@ -128,10 +129,6 @@ class MainWindow : public QMainWindow // chart importing void importCharts(QStringList); - // search box gets and loses focus - make big/small - void searchFocusIn(); - void searchFocusOut(); - // open and closing windows and tabs void closeAll(); // close all windows and tabs @@ -149,6 +146,10 @@ class MainWindow : public QMainWindow void removeTab(Tab*); // remove without question void switchTab(int index); // for switching between one tab and another + // sidebar selecting views and actions + void sidebarClicked(int id); + void sidebarSelected(int id); + // Athlete Backup void setBackupAthleteMenu(); void backupAthlete(QString name); @@ -263,19 +264,18 @@ class MainWindow : public QMainWindow private: - GcScopeBar *scopebar; + NewSideBar *sidebar; Tab *currentTab; QList tabList; #ifndef Q_OS_MAC QTFullScreen *fullScreen; #endif - QPropertyAnimation *anim; SearchFilterBox *searchBox; // Not on Mac so use other types - QPushButton *sidebar, *lowbar; + QPushButton *sidelist, *lowbar; QtSegmentControl *styleSelector; GcToolBar *head; diff --git a/src/Gui/NewSideBar.cpp b/src/Gui/NewSideBar.cpp new file mode 100644 index 000000000..b8b8f5665 --- /dev/null +++ b/src/Gui/NewSideBar.cpp @@ -0,0 +1,278 @@ +#include "Context.h" +#include "NewSideBar.h" +#include "Colors.h" + +static constexpr int gl_itemwidth = 70; +static constexpr int gl_itemheight = 50; +static constexpr int gl_margin = 0; + +NewSideBar::NewSideBar(Context *context, QWidget *parent) : QWidget(parent), context(context) + +{ + setFixedWidth(gl_itemwidth *dpiXFactor); + setAutoFillBackground(true); + lastid=0; + + QVBoxLayout *mainlayout = new QVBoxLayout(this); + mainlayout->setSpacing(0); + mainlayout->setContentsMargins(0,0,0,0); + top=new QWidget(this); + bottom=new QWidget(this); + middle=new QWidget(this); + middle->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding)); + mainlayout->addWidget(top); + mainlayout->addWidget(middle); + mainlayout->addWidget(bottom); + + layout = new QVBoxLayout(middle); + layout->setSpacing(0); + layout->setContentsMargins(0,gl_margin *dpiXFactor,0,gl_margin*dpiYFactor); + + connect(context, SIGNAL(configChanged(qint32)), this, SLOT(configChanged(qint32))); + configChanged(0); + + show(); +} + +void +NewSideBar::clicked(int id) +{ + // un selectable item was clicked (e.g. symc or settings) + emit itemClicked(id); +} + +void +NewSideBar::selected(int id) +{ + // we selected one, so need to set it selected + // and deselect everyone else + QMapIteratori(items); + while(i.hasNext()) { + i.next(); + if (i.key() == id) i.value()->setSelected(true); + else i.value()->setSelected(false); + i.value()->update(); + } + emit itemSelected(id); +} + +int +NewSideBar::addItem(QImage icon, QString name, int id) +{ + // allocated an id + if (id == -1) id=lastid++; + + NewSideBarItem *add = new NewSideBarItem(this, id, icon, name); + layout->addWidget(add); + items.insert(id, add); + + return id; +} + +// leave a gap- we have main icons, gap, apps, gap, sync, prefs +void +NewSideBar::addStretch() +{ + layout->addStretch(); +} + + +// is it shown, is it usable? +void +NewSideBar::setItemVisible(int id, bool x) +{ + NewSideBarItem *item = items.value(id, NULL); + if (item) item->setVisible(x); +} + +void +NewSideBar::setItemEnabled(int id, bool x) +{ + NewSideBarItem *item = items.value(id, NULL); + if (item) item->setEnabled(x); +} + +// can we select it, select it by program? +void +NewSideBar::setItemSelectable(int id, bool x) +{ + NewSideBarItem *item = items.value(id, NULL); + if (item) item->setSelectable(x); +} + +void +NewSideBar::setItemSelected(int id, bool x) +{ + NewSideBarItem *item = items.value(id, NULL); + if (item) item->setSelected(x); +} + +void +NewSideBar::configChanged(qint32) +{ + QFont font; + QFontMetrics fm(font); + top->setFixedHeight(fm.height() + 8); // no scaling... + bottom->setFixedHeight(fm.height() + 4); // no scaling... + QColor col=GColor(CCHROME); + QString style=QString("QWidget { background: rgb(%1,%2,%3); }").arg(col.red()).arg(col.green()).arg(col.blue()); + top->setStyleSheet(style); + bottom->setStyleSheet(style); + col=GColor(CPLOTBACKGROUND); + col=GCColor::invertColor(col); // invert makes dark white, light black + col=GCColor::invertColor(col); // invert again, so now its white or black + style=QString("QWidget { background: rgb(%1,%2,%3); }").arg(col.red()).arg(col.green()).arg(col.blue()); + middle->setStyleSheet(style); +} + +NewSideBarItem::NewSideBarItem(NewSideBar *sidebar, int id, QImage icon, QString name) : QWidget(sidebar), sidebar(sidebar), id(id), icon(icon), name(name) +{ + clicked = selected = false; + selectable = enabled = true; + + // some basics + setFixedSize(gl_itemwidth *dpiXFactor,gl_itemheight *dpiYFactor); + setAutoFillBackground(true); + + // trap events + installEventFilter(this); + connect(sidebar->context, SIGNAL(configChanged(qint32)), this, SLOT(configChanged(qint32))); + + configChanged(0); + + show(); +} + +void +NewSideBarItem::setSelectable(bool x) +{ + selectable = x; + update(); +} + +void +NewSideBarItem::setEnabled(bool x) +{ + enabled = x; + update(); +} + +void +NewSideBarItem::setSelected(bool x) +{ + selected = x; + update(); +} + +// trap all events for me +bool +NewSideBarItem::eventFilter(QObject *, QEvent *e) +{ + switch(e->type()) { + case QEvent::Enter: + case QEvent::Leave: + case QEvent::MouseMove: + update(); + break; + + case QEvent::MouseButtonPress: + clicked=true; + break; + case QEvent::MouseButtonRelease: + if (underMouse() && clicked) { + // user clicked on us! + if (enabled && selectable && !selected) sidebar->selected(id); + else if (enabled && !selectable) sidebar->clicked(id); + } + clicked=false; + break; + default: + break; + } + + return false; +} + +static QImage imageRGB(QImage &source, QColor target) +{ + QImage returning = source; + + if (target == QColor(Qt::white)) target = QColor(255,255,254, 255); // white is the alpha + + for(int x=0; x< returning.width(); x++) + for(int y=0; y< returning.height(); y++) { + QColor v = returning.pixelColor(x,y); + if (v.red() == 0 && v.blue() == 0 && v.green() == 0) + returning.setPixelColor(x,y,target); + } + + return returning; +} + +void +NewSideBarItem::configChanged(qint32) +{ + QColor col(Qt::darkGray); + QString style=QString("QWidget { background: rgb(%1,%2,%3); }").arg(col.red()).arg(col.green()).arg(col.blue()); + setStyleSheet(style); + + // set foreground colors + fg_normal = GCColor::invertColor(GColor(CPLOTBACKGROUND)); + + // if foreground is white then we're "dark" if its + // black the we're "light" so this controls palette + bool dark = (fg_normal == QColor(Qt::white)); + + if (dark) fg_disabled = QColor(80,80,80); + else fg_disabled = QColor(180,180,180); + + // set background colors + col=GColor(CPLOTBACKGROUND); + bool isblack = (col == QColor(Qt::black)); // e.g. mustang theme + col=GCColor::invertColor(col); // invert makes dark white, light black + col=GCColor::invertColor(col); // invert again, so now its white or black + bg_normal = col; + + // on select + bg_select =GColor(CPLOTBACKGROUND); + if (dark) bg_select = bg_select.lighter(200); + else bg_select = bg_select.darker(200); + if (isblack) bg_select = QColor(30,30,30); + + // on hover + bg_hover =GColor(CPLOTBACKGROUND); + if (dark) bg_hover = bg_hover.lighter(300); + else bg_hover = bg_hover.darker(300); + if (isblack) bg_hover = QColor(50,50,50); + + iconNormal = QPixmap::fromImage(imageRGB(icon, fg_normal), Qt::ColorOnly|Qt::PreferDither|Qt::DiffuseAlphaDither); + iconDisabled = QPixmap::fromImage(imageRGB(icon, fg_disabled), Qt::ColorOnly|Qt::PreferDither|Qt::DiffuseAlphaDither); +} + +void +NewSideBarItem::paintEvent(QPaintEvent *) +{ + QPainter painter(this); + + // background is normal, unless selected or hovering + QBrush brush(bg_normal); + if (selected) brush = QBrush(bg_select); + else if (underMouse() && enabled) brush = QBrush(bg_hover); + painter.fillRect(QRectF(0,0,gl_itemwidth*dpiXFactor, gl_itemheight*dpiXFactor), brush); + + // icon is normal or disabled + if (enabled) painter.drawPixmap(27*dpiXFactor,6*dpiXFactor,24*dpiXFactor,24*dpiXFactor,iconNormal); + else painter.drawPixmap(27*dpiXFactor,6*dpiXFactor,24*dpiXFactor,24*dpiXFactor,iconDisabled); + + // block + if (selected) painter.fillRect(QRectF(0,0,3*dpiXFactor,gl_itemheight*dpiXFactor), QBrush(GColor(CPLOTMARKER))); + + // draw name + QPen pen(fg_normal); + if (!enabled) pen = QPen(fg_disabled); + QFont f; + f.setPixelSize(12*dpiYFactor); + painter.setFont(f); + painter.setPen(pen); + painter.drawText(QRect(5*dpiXFactor,24*dpiYFactor,(gl_itemwidth-5)*dpiXFactor,20*dpiYFactor), Qt::AlignCenter| Qt::AlignBottom, name); +} diff --git a/src/Gui/NewSideBar.h b/src/Gui/NewSideBar.h new file mode 100644 index 000000000..f458e7b80 --- /dev/null +++ b/src/Gui/NewSideBar.h @@ -0,0 +1,105 @@ +#include +#include +#include + +class Context; +class NewSideBarItem; +class NewSideBar : public QWidget +{ + + Q_OBJECT + + friend class ::NewSideBarItem; + + public: + NewSideBar(Context *context, QWidget *parent); + + public slots: + + // managing items - the id can be assigned or will get a default + // it returns the id used + int addItem(QImage icon, QString name, int id=-1); + + // leave a gap- we have main icons, gap, apps, gap, sync, prefs + void addStretch(); + + // is it shown, is it usable? + void setItemVisible(int id, bool); + void setItemEnabled(int id, bool); + + // can we select it, select it by program? + void setItemSelectable(int id, bool); + void setItemSelected(int id, bool); + + // config changed + void configChanged(qint32); + + // called by children + void clicked(int id); + void selected(int id); + + signals: + + void itemSelected(int id); + void itemClicked(int id); + + protected: + Context *context; + + private: + + QWidget *top, *middle, *bottom; // bars at top and the bottom + QMap items; + + int lastid; // when autoallocating + QVBoxLayout *layout; +}; + +// tightly bound with parent +class NewSideBarItem : public QWidget +{ + Q_OBJECT + + public: + + NewSideBarItem(NewSideBar *sidebar, int id, QImage icon, QString name); + + void setSelectable(bool); + void setEnabled(bool); + void setSelected(bool); + //void setVisible(bool); - standard qwidget method, we do not need to implement + + bool isSelected() const { return selected; } + bool isEnabled() const { return enabled; } + bool isSelectable() const { return selectable; } + //bool isVisible() const { return QWidget::isVisible(); } - standard qwidget method + + // trap all events for me + bool eventFilter(QObject *oj, QEvent *e); + + public slots: + + // config changed + void configChanged(qint32); + + void paintEvent(QPaintEvent *event); + + private: + + NewSideBar *sidebar; // for emitting signals + int id; + + // pre-rendered/calculated icons and colors + QImage icon; + QPixmap iconNormal, iconDisabled; + QColor fg_normal, fg_disabled; + QColor bg_normal, bg_hover, bg_select, bg_disable; + QFont textfont; + + QString name; + + bool selected; + bool selectable; + bool enabled; + bool clicked; +}; diff --git a/src/Gui/RideNavigator.cpp b/src/Gui/RideNavigator.cpp index e74752e1f..8a32b5dfd 100644 --- a/src/Gui/RideNavigator.cpp +++ b/src/Gui/RideNavigator.cpp @@ -56,7 +56,7 @@ RideNavigator::RideNavigator(Context *context, bool mainwindow) : GcChartWindow( mainLayout = new QVBoxLayout; setChartLayout(mainLayout); mainLayout->setSpacing(0); - if (mainwindow) mainLayout->setContentsMargins(0,0,0,0); + if (mainwindow) mainLayout->setContentsMargins(5*dpiXFactor,0,0,0); else mainLayout->setContentsMargins(2,2,2,2); // so we can resize! searchFilter = new SearchFilter(this); diff --git a/src/Gui/SearchBox.cpp b/src/Gui/SearchBox.cpp index 4557a727a..b2584a78f 100644 --- a/src/Gui/SearchBox.cpp +++ b/src/Gui/SearchBox.cpp @@ -35,7 +35,7 @@ SearchBox::SearchBox(Context *context, QWidget *parent, bool nochooser) : QLineEdit(parent), context(context), parent(parent), filtered(false), nochooser(nochooser), active(false) { - setFixedHeight(21 *dpiYFactor); + //setFixedHeight(21 *dpiYFactor); //clear button clearButton = new QToolButton(this); clearButton->setStyleSheet("QToolButton { border: none; padding: 0px; }"); diff --git a/src/Gui/SearchFilterBox.cpp b/src/Gui/SearchFilterBox.cpp index f56b858b8..1b55795c1 100644 --- a/src/Gui/SearchFilterBox.cpp +++ b/src/Gui/SearchFilterBox.cpp @@ -35,6 +35,7 @@ SearchFilterBox::SearchFilterBox(QWidget *parent, Context *context, bool nochoos // no column chooser if my parent widget is a modal widget searchbox = new SearchBox(context, this, nochooser); + searchbox->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding)); contents->addWidget(searchbox); freeSearch = new FreeSearch(this, context); diff --git a/src/Resources/application.qrc b/src/Resources/application.qrc index 86fbdf032..79a7b47d9 100644 --- a/src/Resources/application.qrc +++ b/src/Resources/application.qrc @@ -1,6 +1,15 @@ webservice/httpserver.ini + sidebar/apps.png + sidebar/assess.png + sidebar/athlete.png + sidebar/plan.png + sidebar/prefs.png + sidebar/reflect.png + sidebar/sync.png + sidebar/train.png + sidebar/trends.png images/devices/garminusb.png images/devices/computrainer.png images/devices/kickr.png diff --git a/src/Resources/sidebar/apps.png b/src/Resources/sidebar/apps.png new file mode 100644 index 000000000..1067f1fd4 Binary files /dev/null and b/src/Resources/sidebar/apps.png differ diff --git a/src/Resources/sidebar/assess.png b/src/Resources/sidebar/assess.png new file mode 100644 index 000000000..92ca51109 Binary files /dev/null and b/src/Resources/sidebar/assess.png differ diff --git a/src/Resources/sidebar/athlete.png b/src/Resources/sidebar/athlete.png new file mode 100644 index 000000000..8a6bcc1f1 Binary files /dev/null and b/src/Resources/sidebar/athlete.png differ diff --git a/src/Resources/sidebar/plan.png b/src/Resources/sidebar/plan.png new file mode 100644 index 000000000..6bb479304 Binary files /dev/null and b/src/Resources/sidebar/plan.png differ diff --git a/src/Resources/sidebar/prefs.png b/src/Resources/sidebar/prefs.png new file mode 100644 index 000000000..42fabcbdb Binary files /dev/null and b/src/Resources/sidebar/prefs.png differ diff --git a/src/Resources/sidebar/reflect.png b/src/Resources/sidebar/reflect.png new file mode 100644 index 000000000..bfe096de6 Binary files /dev/null and b/src/Resources/sidebar/reflect.png differ diff --git a/src/Resources/sidebar/sync.png b/src/Resources/sidebar/sync.png new file mode 100644 index 000000000..8df84118b Binary files /dev/null and b/src/Resources/sidebar/sync.png differ diff --git a/src/Resources/sidebar/train.png b/src/Resources/sidebar/train.png new file mode 100644 index 000000000..9243a9c0a Binary files /dev/null and b/src/Resources/sidebar/train.png differ diff --git a/src/Resources/sidebar/trends.png b/src/Resources/sidebar/trends.png new file mode 100644 index 000000000..426503137 Binary files /dev/null and b/src/Resources/sidebar/trends.png differ diff --git a/src/src.pro b/src/src.pro index d97006751..8c2682af7 100644 --- a/src/src.pro +++ b/src/src.pro @@ -754,7 +754,7 @@ HEADERS += Gui/AboutDialog.h Gui/AddIntervalDialog.h Gui/AnalysisSidebar.h Gui/C Gui/GcWindowRegistry.h Gui/GenerateHeatMapDialog.h Gui/GProgressDialog.h Gui/HelpWhatsThis.h Gui/HelpWindow.h \ Gui/IntervalTreeView.h Gui/LTMSidebar.h Gui/MainWindow.h Gui/NewCyclistDialog.h Gui/Pages.h Gui/RideNavigator.h Gui/RideNavigatorProxy.h \ Gui/SaveDialogs.h Gui/SearchBox.h Gui/SearchFilterBox.h Gui/SolveCPDialog.h Gui/Tab.h Gui/TabView.h Gui/ToolsRhoEstimator.h \ - Gui/Views.h Gui/BatchExportDialog.h Gui/DownloadRideDialog.h Gui/ManualRideDialog.h Gui/NewMainWindow.h \ + Gui/Views.h Gui/BatchExportDialog.h Gui/DownloadRideDialog.h Gui/ManualRideDialog.h Gui/NewMainWindow.h Gui/NewSideBar.h \ Gui/MergeActivityWizard.h Gui/RideImportWizard.h Gui/SplitActivityWizard.h Gui/SolverDisplay.h # metrics and models @@ -852,7 +852,7 @@ SOURCES += Gui/AboutDialog.cpp Gui/AddIntervalDialog.cpp Gui/AnalysisSidebar.cpp Gui/GcWindowRegistry.cpp Gui/GenerateHeatMapDialog.cpp Gui/GProgressDialog.cpp Gui/HelpWhatsThis.cpp Gui/HelpWindow.cpp \ Gui/IntervalTreeView.cpp Gui/LTMSidebar.cpp Gui/MainWindow.cpp Gui/NewCyclistDialog.cpp Gui/Pages.cpp Gui/RideNavigator.cpp Gui/SaveDialogs.cpp \ Gui/SearchBox.cpp Gui/SearchFilterBox.cpp Gui/SolveCPDialog.cpp Gui/Tab.cpp Gui/TabView.cpp Gui/ToolsRhoEstimator.cpp Gui/Views.cpp \ - Gui/BatchExportDialog.cpp Gui/DownloadRideDialog.cpp Gui/ManualRideDialog.cpp Gui/EditUserMetricDialog.cpp Gui/NewMainWindow.cpp \ + Gui/BatchExportDialog.cpp Gui/DownloadRideDialog.cpp Gui/ManualRideDialog.cpp Gui/EditUserMetricDialog.cpp Gui/NewMainWindow.cpp Gui/NewSideBar.cpp \ Gui/MergeActivityWizard.cpp Gui/RideImportWizard.cpp Gui/SplitActivityWizard.cpp Gui/SolverDisplay.cpp ## Models and Metrics