演示管理 Windows DWM (桌面窗口管理器) 特征、跳转列表、任务栏按钮叠加和缩略图工具栏。
音乐播放器范例演示如何使用各种提供特征通过 QtWinExtras 模块。
注意: 范例使用来自 QtMultimedia 模块的 QMediaPlayer 来播放音乐,但本文所聚焦的部分是 QtWinExtras 特征的使用。
范例使用 Windows DWM (桌面窗口管理器) 特征以将窗口内容视觉集成到窗口框架,并使主窗口、音量弹出窗口半透明和模糊。
范例基于是否启用合成,应用不同外观。当合成被启用时,主窗口变半透明且窗口框架会扩展到客户端区域,以使窗口内容无缝集成到窗口框架,如上所示。当合成被禁用时,将着色颜色用作背景颜色。以下屏幕截图阐明 Music Player 范例外观如何当合成被禁用时。
各自代码组合扩展或重置系统框架,调节必要 QWidget 属性,并设置适当样式表以达成期望外观。
void MusicPlayer::stylize() { if (QOperatingSystemVersion::current() < QOperatingSystemVersion::Windows8) { // Set styling options relevant only to Windows 7. if (QtWin::isCompositionEnabled()) { QtWin::extendFrameIntoClientArea(this, -1, -1, -1, -1); setAttribute(Qt::WA_TranslucentBackground, true); setAttribute(Qt::WA_NoSystemBackground, false); setStyleSheet(QStringLiteral("MusicPlayer { background: transparent; }")); } else { QtWin::resetExtendedFrame(this); setAttribute(Qt::WA_TranslucentBackground, false); setStyleSheet(QStringLiteral("MusicPlayer { background: %1; }").arg(QtWin::realColorizationColor().name())); } volumeButton->stylize(); } }
音量弹出窗口没有窗口框架,因此足以模糊弹出窗口当启用合成时。此外,应用样式表能获得遵循着色颜色的边框。就像主窗口,当禁用合成时,着色颜色将用作背景颜色。
void VolumeButton::stylize() { if (QOperatingSystemVersion::current() < QOperatingSystemVersion::Windows8) { // Set styling options relevant only to Windows 7. if (QtWin::isCompositionEnabled()) { QtWin::enableBlurBehindWindow(menu); QString css("QMenu { border: 1px solid %1; border-radius: 2px; background: transparent; }"); menu->setStyleSheet(css.arg(QtWin::realColorizationColor().name())); } else { QtWin::disableBlurBehindWindow(menu); QString css("QMenu { border: 1px solid black; background: %1; }"); menu->setStyleSheet(css.arg(QtWin::realColorizationColor().name())); } } }
The example application respects the user's composition settings, reacts to dynamic composition changes, and looks solid regardless of whether composition is enabled or not. It accomplishes this by catching QWinEvent::CompositionChange and QWinEvent::ColorizationChange events and adjusting its looks accordingly.
bool MusicPlayer::event(QEvent *event) { if (event->type() == QWinEvent::CompositionChange || event->type() == QWinEvent::ColorizationChange) stylize(); return QWidget::event(event); }
范例创建自定义跳转列表,为用户提供对最近播放音乐文件的快速访问。
void MusicPlayer::createJumpList() { QWinJumpList jumplist; jumplist.recent()->setVisible(true); }
要启用应用程序跳转列表以展示期望的最近文件,使用以下帮手函数注册相应文件类型。
static bool associateFileTypes() { QString displayName = QGuiApplication::applicationDisplayName(); QString filePath = QCoreApplication::applicationFilePath(); QString fileName = QFileInfo(filePath).fileName(); const QString key = QStringLiteral("HKEY_CURRENT_USER\\Software\\Classes\\Applications\\") + fileName; QSettings settings(key, QSettings::NativeFormat); if (settings.status() != QSettings::NoError) { qWarning() << "Cannot access registry key" << key; return false; } settings.setValue(QStringLiteral("FriendlyAppName"), displayName); settings.beginGroup(QStringLiteral("SupportedTypes")); QMimeDatabase mimeDatabase; const QStringList supportedMimeTypes = MusicPlayer::supportedMimeTypes(); for (const QString &fileType : supportedMimeTypes) { const QStringList suffixes = mimeDatabase.mimeTypeForName(fileType).suffixes(); for (QString suffix : suffixes) { suffix.prepend('.'); settings.setValue(suffix, QString()); } } settings.endGroup(); settings.beginGroup(QStringLiteral("shell")); settings.beginGroup(QStringLiteral("open")); settings.setValue(QStringLiteral("FriendlyAppName"), displayName); settings.beginGroup(QStringLiteral("Command")); settings.setValue(QStringLiteral("."), QLatin1Char('"') + QDir::toNativeSeparators(filePath) + QStringLiteral("\" \"%1\"")); return true; }
范例使用 Windows 任务栏为 2 件事;设置表示当前音乐回放状态的叠加图标,和在任务栏按钮指示回放进度。
The following snippet shows how the taskbar button is prepared. The playback progress is wired directly to the taskbar progress indicator by using signals and slots.
void MusicPlayer::createTaskbar() { taskbarButton = new QWinTaskbarButton(this); taskbarButton->setWindow(windowHandle()); taskbarProgress = taskbarButton->progress(); connect(positionSlider, &QAbstractSlider::valueChanged, taskbarProgress, &QWinTaskbarProgress::setValue); connect(positionSlider, &QAbstractSlider::rangeChanged, taskbarProgress, &QWinTaskbarProgress::setRange); connect(&mediaPlayer, &QMediaPlayer::stateChanged, this, &MusicPlayer::updateTaskbar); }
会更新叠加图标和进度指示器,每当音乐回放状态改变时。
void MusicPlayer::updateTaskbar() { switch (mediaPlayer.state()) { case QMediaPlayer::PlayingState: taskbarButton->setOverlayIcon(style()->standardIcon(QStyle::SP_MediaPlay)); taskbarProgress->show(); taskbarProgress->resume(); break; case QMediaPlayer::PausedState: taskbarButton->setOverlayIcon(style()->standardIcon(QStyle::SP_MediaPause)); taskbarProgress->show(); taskbarProgress->pause(); break; case QMediaPlayer::StoppedState: taskbarButton->setOverlayIcon(style()->standardIcon(QStyle::SP_MediaStop)); taskbarProgress->hide(); break; } }
Windows 缩略图工具栏用于提供基本音乐回放控件。这些控件可用于控制应用程序,不必激活应用程序。
void MusicPlayer::createThumbnailToolBar() { thumbnailToolBar = new QWinThumbnailToolBar(this); thumbnailToolBar->setWindow(windowHandle()); playToolButton = new QWinThumbnailToolButton(thumbnailToolBar); playToolButton->setEnabled(false); playToolButton->setToolTip(tr("Play")); playToolButton->setIcon(style()->standardIcon(QStyle::SP_MediaPlay)); connect(playToolButton, &QWinThumbnailToolButton::clicked, this, &MusicPlayer::togglePlayback); forwardToolButton = new QWinThumbnailToolButton(thumbnailToolBar); forwardToolButton->setEnabled(false); forwardToolButton->setToolTip(tr("Fast forward")); forwardToolButton->setIcon(style()->standardIcon(QStyle::SP_MediaSeekForward)); connect(forwardToolButton, &QWinThumbnailToolButton::clicked, this, &MusicPlayer::seekForward); backwardToolButton = new QWinThumbnailToolButton(thumbnailToolBar); backwardToolButton->setEnabled(false); backwardToolButton->setToolTip(tr("Rewind")); backwardToolButton->setIcon(style()->standardIcon(QStyle::SP_MediaSeekBackward)); connect(backwardToolButton, &QWinThumbnailToolButton::clicked, this, &MusicPlayer::seekBackward); thumbnailToolBar->addButton(backwardToolButton); thumbnailToolBar->addButton(playToolButton); thumbnailToolBar->addButton(forwardToolButton); connect(&mediaPlayer, &QMediaPlayer::positionChanged, this, &MusicPlayer::updateThumbnailToolBar); connect(&mediaPlayer, &QMediaPlayer::durationChanged, this, &MusicPlayer::updateThumbnailToolBar); connect(&mediaPlayer, &QMediaPlayer::stateChanged, this, &MusicPlayer::updateThumbnailToolBar); }
会相应更新缩略图工具栏按钮,每当音乐回放状态改变时。
void MusicPlayer::updateThumbnailToolBar() { playToolButton->setEnabled(mediaPlayer.duration() > 0); backwardToolButton->setEnabled(mediaPlayer.position() > 0); forwardToolButton->setEnabled(mediaPlayer.position() < mediaPlayer.duration()); if (mediaPlayer.state() == QMediaPlayer::PlayingState) { playToolButton->setToolTip(tr("Pause")); playToolButton->setIcon(style()->standardIcon(QStyle::SP_MediaPause)); } else { playToolButton->setToolTip(tr("Play")); playToolButton->setIcon(style()->standardIcon(QStyle::SP_MediaPlay)); } }
文件: