File indexing completed on 2024-04-28 05:45:18
0001 /* 0002 * SPDX-FileCopyrightText: 2006-2012 Peter Penz <peter.penz19@gmail.com> 0003 * 0004 * SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #include "dolphinstatusbar.h" 0008 0009 #include "dolphin_generalsettings.h" 0010 #include "statusbarspaceinfo.h" 0011 #include "views/dolphinview.h" 0012 #include "views/zoomlevelinfo.h" 0013 0014 #include <KLocalizedString> 0015 #include <KSqueezedTextLabel> 0016 0017 #include <QApplication> 0018 #include <QHBoxLayout> 0019 #include <QHelpEvent> 0020 #include <QIcon> 0021 #include <QMenu> 0022 #include <QPainter> 0023 #include <QProgressBar> 0024 #include <QSlider> 0025 #include <QStyleOption> 0026 #include <QTimer> 0027 #include <QToolButton> 0028 0029 namespace 0030 { 0031 const int UpdateDelay = 50; 0032 } 0033 0034 DolphinStatusBar::DolphinStatusBar(QWidget *parent) 0035 : QWidget(parent) 0036 , m_text() 0037 , m_defaultText() 0038 , m_label(nullptr) 0039 , m_zoomLabel(nullptr) 0040 , m_spaceInfo(nullptr) 0041 , m_zoomSlider(nullptr) 0042 , m_progressBar(nullptr) 0043 , m_stopButton(nullptr) 0044 , m_progress(100) 0045 , m_showProgressBarTimer(nullptr) 0046 , m_delayUpdateTimer(nullptr) 0047 , m_textTimestamp() 0048 { 0049 setProperty("_breeze_statusbar_separator", true); 0050 // Initialize text label 0051 m_label = new KSqueezedTextLabel(m_text, this); 0052 m_label->setWordWrap(true); 0053 m_label->setTextFormat(Qt::PlainText); 0054 0055 // Initialize zoom slider's explanatory label 0056 m_zoomLabel = new KSqueezedTextLabel(i18nc("Used as a noun, i.e. 'Here is the zoom level:'", "Zoom:"), this); 0057 0058 // Initialize zoom widget 0059 m_zoomSlider = new QSlider(Qt::Horizontal, this); 0060 m_zoomSlider->setAccessibleName(i18n("Zoom")); 0061 m_zoomSlider->setAccessibleDescription(i18nc("Description for zoom-slider (accessibility)", "Sets the size of the file icons.")); 0062 m_zoomSlider->setPageStep(1); 0063 m_zoomSlider->setRange(ZoomLevelInfo::minimumLevel(), ZoomLevelInfo::maximumLevel()); 0064 0065 connect(m_zoomSlider, &QSlider::valueChanged, this, &DolphinStatusBar::zoomLevelChanged); 0066 connect(m_zoomSlider, &QSlider::valueChanged, this, &DolphinStatusBar::updateZoomSliderToolTip); 0067 connect(m_zoomSlider, &QSlider::sliderMoved, this, &DolphinStatusBar::showZoomSliderToolTip); 0068 0069 // Initialize space information 0070 m_spaceInfo = new StatusBarSpaceInfo(this); 0071 0072 // Initialize progress information 0073 m_stopButton = new QToolButton(this); 0074 m_stopButton->setIcon(QIcon::fromTheme(QStringLiteral("process-stop"))); 0075 m_stopButton->setAccessibleName(i18n("Stop")); 0076 m_stopButton->setAutoRaise(true); 0077 m_stopButton->setToolTip(i18nc("@tooltip", "Stop loading")); 0078 m_stopButton->hide(); 0079 connect(m_stopButton, &QToolButton::clicked, this, &DolphinStatusBar::stopPressed); 0080 0081 m_progressTextLabel = new QLabel(this); 0082 m_progressTextLabel->hide(); 0083 0084 m_progressBar = new QProgressBar(this); 0085 m_progressBar->hide(); 0086 0087 m_showProgressBarTimer = new QTimer(this); 0088 m_showProgressBarTimer->setInterval(500); 0089 m_showProgressBarTimer->setSingleShot(true); 0090 connect(m_showProgressBarTimer, &QTimer::timeout, this, &DolphinStatusBar::updateProgressInfo); 0091 0092 // initialize text updater delay timer 0093 m_delayUpdateTimer = new QTimer(this); 0094 m_delayUpdateTimer->setInterval(UpdateDelay); 0095 m_delayUpdateTimer->setSingleShot(true); 0096 connect(m_delayUpdateTimer, &QTimer::timeout, this, &DolphinStatusBar::updateLabelText); 0097 0098 // Initialize top layout and size policies 0099 const int fontHeight = QFontMetrics(m_label->font()).height(); 0100 const int zoomSliderHeight = m_zoomSlider->minimumSizeHint().height(); 0101 const int buttonHeight = m_stopButton->height(); 0102 const int contentHeight = qMax(qMax(fontHeight, zoomSliderHeight), buttonHeight); 0103 0104 QFontMetrics fontMetrics(m_label->font()); 0105 0106 m_label->setFixedHeight(contentHeight); 0107 m_label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed); 0108 0109 m_zoomSlider->setMaximumWidth(fontMetrics.averageCharWidth() * 15); 0110 0111 m_spaceInfo->setFixedHeight(contentHeight); 0112 m_spaceInfo->setMaximumWidth(fontMetrics.averageCharWidth() * 25); 0113 m_spaceInfo->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed); 0114 0115 m_progressBar->setFixedHeight(zoomSliderHeight); 0116 m_progressBar->setMaximumWidth(fontMetrics.averageCharWidth() * 20); 0117 0118 QHBoxLayout *topLayout = new QHBoxLayout(this); 0119 updateContentsMargins(); 0120 topLayout->setSpacing(4); 0121 topLayout->addWidget(m_label, 1); 0122 topLayout->addWidget(m_zoomLabel); 0123 topLayout->addWidget(m_zoomSlider, 1); 0124 topLayout->addWidget(m_spaceInfo, 1); 0125 topLayout->addWidget(m_stopButton); 0126 topLayout->addWidget(m_progressTextLabel); 0127 topLayout->addWidget(m_progressBar); 0128 0129 setVisible(GeneralSettings::showStatusBar()); 0130 setExtensionsVisible(true); 0131 setWhatsThis(xi18nc("@info:whatsthis Statusbar", 0132 "<para>This is " 0133 "the <emphasis>Statusbar</emphasis>. It contains three elements " 0134 "by default (left to right):<list><item>A <emphasis>text field" 0135 "</emphasis> that displays the size of selected items. If only " 0136 "one item is selected the name and type is shown as well.</item>" 0137 "<item>A <emphasis>zoom slider</emphasis> that allows you " 0138 "to adjust the size of the icons in the view.</item>" 0139 "<item><emphasis>Space information</emphasis> about the " 0140 "current storage device.</item></list></para>")); 0141 } 0142 0143 DolphinStatusBar::~DolphinStatusBar() 0144 { 0145 } 0146 0147 void DolphinStatusBar::setText(const QString &text) 0148 { 0149 if (m_text == text) { 0150 return; 0151 } 0152 0153 m_textTimestamp = QTime::currentTime(); 0154 0155 m_text = text; 0156 // will update status bar text in 50ms 0157 m_delayUpdateTimer->start(); 0158 } 0159 0160 QString DolphinStatusBar::text() const 0161 { 0162 return m_text; 0163 } 0164 0165 void DolphinStatusBar::setProgressText(const QString &text) 0166 { 0167 m_progressTextLabel->setText(text); 0168 } 0169 0170 QString DolphinStatusBar::progressText() const 0171 { 0172 return m_progressTextLabel->text(); 0173 } 0174 0175 void DolphinStatusBar::setProgress(int percent) 0176 { 0177 // Show a busy indicator if a value < 0 is provided: 0178 m_progressBar->setMaximum((percent < 0) ? 0 : 100); 0179 0180 percent = qBound(0, percent, 100); 0181 const bool progressRestarted = (percent < 100) && (percent < m_progress); 0182 m_progress = percent; 0183 if (progressRestarted && !m_progressBar->isVisible()) { 0184 // Show the progress bar delayed: In the case if 100 % are reached within 0185 // a short time, no progress bar will be shown at all. 0186 m_showProgressBarTimer->start(); 0187 } 0188 0189 m_progressBar->setValue(m_progress); 0190 if (percent == 100) { 0191 // The end of the progress has been reached. Assure that the progress bar 0192 // gets hidden and the extensions widgets get visible again. 0193 m_showProgressBarTimer->stop(); 0194 updateProgressInfo(); 0195 } 0196 } 0197 0198 int DolphinStatusBar::progress() const 0199 { 0200 return m_progress; 0201 } 0202 0203 void DolphinStatusBar::resetToDefaultText() 0204 { 0205 m_text.clear(); 0206 0207 QTime currentTime; 0208 if (currentTime.msecsTo(m_textTimestamp) < UpdateDelay) { 0209 m_delayUpdateTimer->start(); 0210 } else { 0211 updateLabelText(); 0212 } 0213 } 0214 0215 void DolphinStatusBar::setDefaultText(const QString &text) 0216 { 0217 m_defaultText = text; 0218 updateLabelText(); 0219 } 0220 0221 QString DolphinStatusBar::defaultText() const 0222 { 0223 return m_defaultText; 0224 } 0225 0226 void DolphinStatusBar::setUrl(const QUrl &url) 0227 { 0228 if (GeneralSettings::showSpaceInfo()) { 0229 m_spaceInfo->setUrl(url); 0230 } 0231 } 0232 0233 QUrl DolphinStatusBar::url() const 0234 { 0235 return m_spaceInfo->url(); 0236 } 0237 0238 void DolphinStatusBar::setZoomLevel(int zoomLevel) 0239 { 0240 if (zoomLevel != m_zoomSlider->value()) { 0241 m_zoomSlider->setValue(zoomLevel); 0242 } 0243 } 0244 0245 int DolphinStatusBar::zoomLevel() const 0246 { 0247 return m_zoomSlider->value(); 0248 } 0249 0250 void DolphinStatusBar::readSettings() 0251 { 0252 setVisible(GeneralSettings::showStatusBar()); 0253 setExtensionsVisible(true); 0254 } 0255 0256 void DolphinStatusBar::updateSpaceInfo() 0257 { 0258 m_spaceInfo->update(); 0259 } 0260 0261 void DolphinStatusBar::contextMenuEvent(QContextMenuEvent *event) 0262 { 0263 Q_UNUSED(event) 0264 0265 QMenu menu(this); 0266 0267 QAction *showZoomSliderAction = menu.addAction(i18nc("@action:inmenu", "Show Zoom Slider")); 0268 showZoomSliderAction->setCheckable(true); 0269 showZoomSliderAction->setChecked(GeneralSettings::showZoomSlider()); 0270 0271 QAction *showSpaceInfoAction = menu.addAction(i18nc("@action:inmenu", "Show Space Information")); 0272 showSpaceInfoAction->setCheckable(true); 0273 showSpaceInfoAction->setChecked(GeneralSettings::showSpaceInfo()); 0274 0275 const QAction *action = menu.exec(event->reason() == QContextMenuEvent::Reason::Mouse ? QCursor::pos() : mapToGlobal(QPoint(width() / 2, height() / 2))); 0276 if (action == showZoomSliderAction) { 0277 const bool visible = showZoomSliderAction->isChecked(); 0278 GeneralSettings::setShowZoomSlider(visible); 0279 m_zoomSlider->setVisible(visible); 0280 m_zoomLabel->setVisible(visible); 0281 } else if (action == showSpaceInfoAction) { 0282 const bool visible = showSpaceInfoAction->isChecked(); 0283 GeneralSettings::setShowSpaceInfo(visible); 0284 m_spaceInfo->setVisible(visible); 0285 } 0286 updateContentsMargins(); 0287 } 0288 0289 void DolphinStatusBar::showZoomSliderToolTip(int zoomLevel) 0290 { 0291 updateZoomSliderToolTip(zoomLevel); 0292 0293 QPoint global = m_zoomSlider->rect().topLeft(); 0294 global.ry() += m_zoomSlider->height() / 2; 0295 QHelpEvent toolTipEvent(QEvent::ToolTip, QPoint(0, 0), m_zoomSlider->mapToGlobal(global)); 0296 QApplication::sendEvent(m_zoomSlider, &toolTipEvent); 0297 } 0298 0299 void DolphinStatusBar::updateProgressInfo() 0300 { 0301 if (m_progress < 100) { 0302 // Show the progress information and hide the extensions 0303 m_stopButton->show(); 0304 m_progressTextLabel->show(); 0305 m_progressBar->show(); 0306 setExtensionsVisible(false); 0307 } else { 0308 // Hide the progress information and show the extensions 0309 m_stopButton->hide(); 0310 m_progressTextLabel->hide(); 0311 m_progressBar->hide(); 0312 setExtensionsVisible(true); 0313 } 0314 } 0315 0316 void DolphinStatusBar::updateLabelText() 0317 { 0318 const QString text = m_text.isEmpty() ? m_defaultText : m_text; 0319 m_label->setText(text); 0320 } 0321 0322 void DolphinStatusBar::updateZoomSliderToolTip(int zoomLevel) 0323 { 0324 const int size = ZoomLevelInfo::iconSizeForZoomLevel(zoomLevel); 0325 m_zoomSlider->setToolTip(i18ncp("@info:tooltip", "Size: 1 pixel", "Size: %1 pixels", size)); 0326 } 0327 0328 void DolphinStatusBar::setExtensionsVisible(bool visible) 0329 { 0330 bool showSpaceInfo = visible; 0331 bool showZoomSlider = visible; 0332 if (visible) { 0333 showSpaceInfo = GeneralSettings::showSpaceInfo(); 0334 showZoomSlider = GeneralSettings::showZoomSlider(); 0335 } 0336 0337 m_spaceInfo->setShown(showSpaceInfo); 0338 m_spaceInfo->setVisible(showSpaceInfo); 0339 m_zoomSlider->setVisible(showZoomSlider); 0340 m_zoomLabel->setVisible(showZoomSlider); 0341 updateContentsMargins(); 0342 } 0343 0344 void DolphinStatusBar::updateContentsMargins() 0345 { 0346 if (GeneralSettings::showSpaceInfo()) { 0347 // We reduce the outside margin for the flat button so it visually has the same margin as the status bar text label on the other end of the bar. 0348 layout()->setContentsMargins(6, 0, 2, 0); 0349 } else { 0350 layout()->setContentsMargins(6, 0, 6, 0); 0351 } 0352 } 0353 0354 void DolphinStatusBar::paintEvent(QPaintEvent *paintEvent) 0355 { 0356 Q_UNUSED(paintEvent) 0357 QPainter p(this); 0358 QStyleOption opt; 0359 opt.initFrom(this); 0360 style()->drawPrimitive(QStyle::PE_PanelStatusBar, &opt, &p, this); 0361 } 0362 0363 #include "moc_dolphinstatusbar.cpp"