WebEngine Notifications Example▲
WebEngine Notifications demonstrates how to use the QWebEngineProfile::setNotificationPresenter() method and QWebEngineNotification class to show an HTML5 web notification to the user.
Running the Example▲
To run the example from Qt Creator, open the Welcome mode and select the example from Examples. For more information, visit Building and Running an Example.
HTML Page▲
In this example, we create an internal HTML page that is added through a resource collection file (.qrc). The page displays buttons for requesting permissions and contains necessary JavaScript code to trigger this request:
Notification.requestPermission().then(function (permission) {
if
(permission ==
'granted')
createNotification()
}
)
Also page contains a button for creating a notification. The following JavaScript constructions are executed on the press event:
function createNotification() {
let title =
'Notification #' +
++
notificationsCreated
let options =
{
body: 'Visit doc.qt.io for
more info!
', icon: 'icon.png', }
let notification =
new
Notification(title, options)
}
Main Function▲
In the main function, we instantiate a QWebEngineView, load our internal HTML page, and set up the required callbacks for notifications handling.
Requesting Feature Permissions▲
We then use the QWebEnginePage::featurePermissionRequested() call to request the user's permission to show notifications on their device.
QObject::
connect(view.page(), &
amp;QWebEnginePage::
featurePermissionRequested,
[&
amp;] (const
QUrl &
amp;origin, QWebEnginePage::
Feature feature) {
if
(feature !=
QWebEnginePage::
Notifications)
return
;
view.page()-&
gt;setFeaturePermission(origin, feature, QWebEnginePage::
PermissionGrantedByUser);
}
);
Handling New Notifications▲
We then construct a NotificationPopup that encapsulates the data of the HTML web notification. We also use the QWebEngineProfile::setNotificationPresenter() call to set our handler, which we use in conjunction with our popup to handle all new notifications.
auto
popup =
new
NotificationPopup(&
amp;view);
profile-&
gt;setNotificationPresenter([&
amp;] (std::
unique_ptr&
lt;QWebEngineNotification&
gt; notification)
{
popup-&
gt;present(notification); }
);
Presenting Notifications to Users▲
The NotificationPopup class in this example is a simple QWidget-based class that uses multiple QLabel instances for displaying the notification's title, message, and icon.
class
NotificationPopup : public
QWidget
{
Q_OBJECT
QLabel m_icon, m_title, m_message;
std::
unique_ptr&
lt;QWebEngineNotification&
gt; notification;
Presenting Notifications▲
Inside the present method, we first close and release the previous notification if we have one and then take ownership of a new notification by calling the std::unique_ptr::swap method on our internal notification instance.
void
present(std::
unique_ptr&
lt;QWebEngineNotification&
gt; &
amp;newNotification)
{
if
(notification) {
notification-&
gt;close();
notification.reset();
}
notification.swap(newNotification);
Then we query the notification instance for a title, a message, and an icon by calling QWebEngineNotification::title(), QWebEngineNotification::message(), QWebEngineNotification::icon() and set up the appropriate labels in our popup.
m_title.setText("<b>"
+
notification-&
gt;title() +
"</b>"
);
m_message.setText(notification-&
gt;message());
m_icon.setPixmap(QPixmap::
fromImage(notification-&
gt;icon()).scaledToHeight(m_icon.height()));
After that we are ready to display our notification to the user by calling the QWidget::show() method. On this step we also call the QWebEngineNotification::show() method to notify JavaScript code about our show event.
show();
notification-&
gt;show();
Finally, we set up a callback to handle the close event from the JavaScript side by connecting to the QWebEngineNotification::closed() signal. We also schedule a timer event to close our active notification automatically.
connect(notification.get(), &
amp;QWebEngineNotification::
closed, this
, &
amp;NotificationPopup::
onClosed);
QTimer::
singleShot(10000
, notification.get(), [&
amp;] () {
onClosed(); }
);
}
Closing Active Notification▲
We execute the close step for the currently active notification either by timeout or by handling the JavaScript event. First, we hide the popup widget itself by calling QWidget::hide(). Then, we notify the JavaScript code by calling the QWebEngineNotification::close() method. Finally, we destroy the notification object through the std::unique_ptr::reset() method.
void
onClosed()
{
hide();
notification-&
gt;close();
notification.reset();
}
Implementing User Interaction▲
To implement the click step for a notification, we handle mouse interaction through QWidget::mouseReleaseEvent(). On this event, the JavaScript code is notified by calling the QWebEngineNotification::click() method. Then we automatically perform the close step as a notification is considered fully handled and no longer needed, and therefore can be destroyed.
void
mouseReleaseEvent(QMouseEvent *
event) override
{
QWidget::
mouseReleaseEvent(event);
if
(notification &
amp;&
amp; event-&
gt;button() ==
Qt::
LeftButton) {
notification-&
gt;click();
onClosed();
}
}