How to display a web page using QT/C++ - c++

I am trying to display a web page using the below code
QWebView *view = new QWebView();
view->load(QUrl("qrc://images//sample page.html/"));
view->show();
sample page.html is added to project resources/Images. The web page frame is loading, but I can't see any html data.
I tested with the below web url and it loaded the page
view->load(QUrl("http://www.google.com/"));

You will have to go through a few steps as follows:
1) Get the QWebPage object:
QWebPage *page = view->page();
2) Get the QWebFrame object:
QWebFrame *frame = page->currentFrame();
3) Call the toHtml member function on the current frame:
QString html = frame->toHtml();
Of course, you will need to add appropriate error checks in between.

Related

How can I interact with html elements use QT

For example, I have a simple HTML page with button and label (or something else). How can I change the text in label (or something else) and catch the button click use QT.
I try to use QWebEngineView to show html, but I don`t know how to interact with elements from QT modul, just change the url, but I dont think its a better way
To be able to interact with HTML rendered with QWebEngine you need to use QWebChannel. You can find the basic guidelines at Qt WebChannel JavaScript API page.
To implement intercommunication with JavaScript in your HTML page you need:
Add Qt += webchannel in your project file
Implement a QObject derived class that should be a proxy between C++ and JavaScript. The simpliest way to make it usable in JavaScript is to create getters, setters and signals for the values you intend to use in JavaScript, and expose them as Q_PROPERTY.
Example:
class ProxyClass: public QObject
{
Q_OBJECT
Q_PROPERTY(QString value READ value WRITE setValue NOTIFY valueChanged)
public:
explicit ProxyClass(QObject *parent = nullptr);
QString value() const;
void setValue(const QString &aValue);
signals:
void valueChanged(const QString &aValue);
};
Set HTML to QWebEngineView with QWebEngineView::setHtml, instantiate your "proxy" class and create QWebChannel for the page (note that you can register multiple objects in QWebChannel). Example:
//create QWebEngineView and set HTML from resources
auto webView = new QWebEngineView;
QFile htmlFile(":/page.html");
htmlFile.open(QIODevice::ReadOnly);
QString html = htmlFile.readAll();
webView->setHtml(html);
//create and set up the instance of your "proxy" class
auto proxy = new ProxyClass;
//create QWebChannel and set it for the page
QWebChannel *webChannel = new QWebChannel(webView->page());
webChannel->registerObject(QStringLiteral("proxy"), proxy);
webView->page()->setWebChannel(webChannel);
Embed qwebchannel.js file in HTML. File is located at <Qt installation directory>/Examples/Qt-<version>/webchannel/shared directory. You can include it in application resources and embed in HTML with <script type="text/javascript" src="qrc:/qwebchannel.js"></script>
Create onload event handler in HTML and initialize QWebChannel in it. Example:
function loaded() {
new QWebChannel(qt.webChannelTransport, function (channel) {
<!--get and assign "proxy"-->
window.proxy = channel.objects.proxy;
<!--now you can-->
<!--get values-->
let proxyValue = proxy.value;
<!--connect signals-->
proxy.valueChanged.connect(() => {
...
});
});
}
function someFunction(newValue) {
<!--set values-->
proxy.value = newValue;
}
...
<body onload="loaded()">...</body>
Once you initialized a web channel and assigned "proxy" object to the window object, you are free to use it everywhere in JavaScript.

QtWebEngine, How to Save Cookies in C++/Qt6.2.4?

Since I change Qt5 to Qt6 for my app,
What worked for Qt5 (to save the cookies, I followed this thread QT 5.6 QWebEngine doesn't save cookies),
Doesn't work now :
QWebEngineProfile::defaultProfile()->setPersistentCookiesPolicy(QWebEngineProfile::ForcePersistentCookies);
QWebEngineProfile* defaultProfile = QWebEngineProfile::defaultProfile();
defaultProfile->setHttpCacheType(QWebEngineProfile::DiskHttpCache);
defaultProfile->setPersistentCookiesPolicy(QWebEngineProfile::ForcePersistentCookies);
QHttpPart* header = new QHttpPart;
header->setRawHeader("X-Frame-Options", "ALLOWALL");
defaultProfile->setCachePath(QStandardPaths::writableLocation(QStandardPaths::CacheLocation));
defaultProfile->setPersistentStoragePath(QStandardPaths::writableLocation(QStandardPaths::AppLocalDataLocation));
I need to save Cookies.
The Solution is :
QWebEngineProfile *profile = new QWebEngineProfile(QString::fromLatin1("MyApplication.%1").arg(qWebEngineChromiumVersion())); // unique profile store per qtwbengine version
QWebEnginePage *page = new QWebEnginePage(profile); // page using profile
QWebEngineView *view = new QWebEngineView();
view->setPage(page);
view->setUrl(AccueilUrl);
view->setZoomFactor(1.2);
setCentralWidget(view);

Blackberry 10 WebView: Content doesn't get updated after URL changes

I wrote a code that updates WebView URL of Blackberry main.qml after certain process gets executed. Qt/C++ code that updates WebView URL is given below
QmlDocument *qml = QmlDocument::create("asset:///main.qml").parent(this);
qml->setContextProperty("app",this);
AbstractPane *root = qml->createRootObject<AbstractPane>();
responseWebPage = root->findChild<WebView *>("responseWebPage");
responseWebPage->setUrl(QUrl(homePath + "/Appname/updatedhtml.html"));
WebView section of main.qml is
WebView {
id: responseWebPage
objectName: "responseWebPage"
accessibility.name: "responseWebPage"
url: "local:///assets/initialcontent.html"
onUrlChanged: {
console.debug("URL is changed. New URL is " + responseWebPage.url);
}
}
I am able to see updated URL name in logs printed by WebView console debug. I also verified that that updatedhtml.html file exists. (Checked through Target File System Navigator). Yet after the URL is set, I do not see content of updatedhtml.html being displayed either in device or simulator. Is there any step I am missing? Any help is greatly appreciated

Get webview document title when HTML is loaded

I have the following Qt webview:
QWebView *view = new QWebView();
view->load(QUrl("http://example.com"));
I want to get the title of document when load is finished, and use it to set the main window title.
From what I suppose view->loadFinished() returns true if page was loaded or not.
For setting the window title I use webView->setWindowTitle(newTitle). So, I need that newTitle variable that I want to be the document title.
How can I do this?
QWebView::loadFinished is a signal. You can subscribe to it to know when the page is loaded:
connect(view, SIGNAL(loadFinished(bool)), this, SLOT(onLoaded()));
To access HTML title you can use QWebView::title property.
void onLoaded()
{
window->setWindowTitle(view->title());
}
Rather then using loadFinished it may be more appropriate to use signal titleChanged(const QString& title) to apply a new title to the window:
connect(view, SIGNAL(titleChanged(QString)), this, SLOT(setWindowTitle(QString)));
EDIT:
Example:
QWebView* webView = new QWebView();
connect(webView, SIGNAL(titleChanged(QString)), webView, SLOT(setWindowTitle(QString)));
webView->load(QUrl("http://yahoo.com"));
webView->show();

Qt get DOM from page without updating GUI

I'm modifying the DOM Traversal example that comes with Qt. However, whenever I see a link, I want to "go" to that URL and also traverse its DOM, but I don't want to reload the GUI. Right now I'm still using the code from the example to get the homepage:
void Window::on_webView_loadFinished()
{
treeWidget->clear();
QWebFrame *frame = webView->page()->mainFrame();
QWebElement document = frame->documentElement();
examineChildElements(document, treeWidget->invisibleRootItem());
}
This works great. In examineChildElements(), when I encounter a specific link, I then call another function with the URL (I checked the URL string; it's correct):
void Window::parse_page(QString page_URL)
{
QWebView *innerPage = new QWebView();
innerPage->setUrl(page_URL);
QWebFrame *frameInner = innerPage->page()->mainFrame();
QWebElement documentBetrieb = frameInner->documentElement();
get_biz_info(documentBetrieb);
delete innerPage;
return;
}
But when I traverse this document (documentBetrieb), there is only an HTML tag. Is there a step I'm missing, or a way of putting the DOM from a URL directly into a QWebElement without using QWebView?
Are you sure setUrl() is loading the URL synchronously? I suppose you need listen to QWebView::loadFinished(bool ok) signal before accessing the DOM.