2015-09-29 21:53:56 +02:00
|
|
|
/* ============================================================
|
|
|
|
* QupZilla - QtWebEngine based browser
|
|
|
|
* Copyright (C) 2015 David Rosca <nowrep@gmail.com>
|
|
|
|
*
|
|
|
|
* This program is free software: you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU General Public License as published by
|
|
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
* ============================================================ */
|
|
|
|
#include "webhittestresult.h"
|
|
|
|
#include "webpage.h"
|
|
|
|
|
|
|
|
WebHitTestResult::WebHitTestResult(const WebPage *page, const QPoint &pos)
|
|
|
|
: m_isNull(true)
|
|
|
|
, m_isContentEditable(false)
|
|
|
|
, m_isContentSelected(false)
|
2015-09-30 15:26:52 +02:00
|
|
|
, m_mediaPaused(false)
|
|
|
|
, m_mediaMuted(false)
|
2015-09-30 14:57:08 +02:00
|
|
|
, m_pos(pos)
|
2015-09-29 21:53:56 +02:00
|
|
|
{
|
|
|
|
QString source = QL1S("(function() {"
|
|
|
|
"var e = document.elementFromPoint(%1, %2);"
|
|
|
|
"if (!e)"
|
|
|
|
" return;"
|
|
|
|
"function isMediaElement(e) {"
|
|
|
|
" return e.tagName == 'AUDIO' || e.tagName == 'VIDEO';"
|
|
|
|
"}"
|
|
|
|
"function isEditableElement(e) {"
|
|
|
|
" if (e.isContentEditable)"
|
|
|
|
" return true;"
|
|
|
|
" if (e.tagName == 'INPUT' || e.tagName == 'TEXTAREA')"
|
2015-09-30 13:38:57 +02:00
|
|
|
" return e.getAttribute('readonly') != 'readonly';"
|
2015-09-29 21:53:56 +02:00
|
|
|
" return false;"
|
|
|
|
"}"
|
2015-10-05 20:29:26 +02:00
|
|
|
"function isSelected(e) {"
|
|
|
|
" var selection = window.getSelection();"
|
|
|
|
" if (selection.type != 'Range')"
|
|
|
|
" return false;"
|
|
|
|
" return window.getSelection().containsNode(e, true);"
|
|
|
|
"}"
|
2015-09-29 21:53:56 +02:00
|
|
|
"var res = {"
|
|
|
|
" alternateText: e.getAttribute('alt'),"
|
|
|
|
" boundingRect: '',"
|
|
|
|
" imageUrl: '',"
|
|
|
|
" contentEditable: isEditableElement(e),"
|
2015-10-05 20:29:26 +02:00
|
|
|
" contentSelected: isSelected(e),"
|
2015-09-29 23:15:46 +02:00
|
|
|
" linkTitle: '',"
|
2015-09-29 21:53:56 +02:00
|
|
|
" linkUrl: '',"
|
|
|
|
" mediaUrl: '',"
|
|
|
|
" tagName: e.tagName.toLowerCase()"
|
|
|
|
"};"
|
|
|
|
"var r = e.getBoundingClientRect();"
|
|
|
|
"res.boundingRect = [r.top, r.left, r.width, r.height];"
|
|
|
|
"if (e.tagName == 'IMG')"
|
|
|
|
" res.imageUrl = e.getAttribute('src');"
|
2015-09-29 23:15:46 +02:00
|
|
|
"if (e.tagName == 'A') {"
|
|
|
|
" res.linkTitle = e.text;"
|
2015-09-29 21:53:56 +02:00
|
|
|
" res.linkUrl = e.getAttribute('href');"
|
2015-09-29 23:15:46 +02:00
|
|
|
"}"
|
2015-09-30 15:26:52 +02:00
|
|
|
"while (e) {"
|
|
|
|
" if (res.linkTitle == '' && e.tagName == 'A')"
|
|
|
|
" res.linkTitle = e.text;"
|
|
|
|
" if (res.linkUrl == '' && e.tagName == 'A')"
|
|
|
|
" res.linkUrl = e.getAttribute('href');"
|
|
|
|
" if (res.mediaUrl == '' && isMediaElement(e)) {"
|
|
|
|
" res.mediaUrl = e.currentSrc;"
|
|
|
|
" res.mediaPaused = e.paused;"
|
|
|
|
" res.mediaMuted = e.muted;"
|
|
|
|
" }"
|
|
|
|
" e = e.parentElement;"
|
2015-09-29 21:53:56 +02:00
|
|
|
"}"
|
|
|
|
"return res;"
|
|
|
|
"})()");
|
|
|
|
|
|
|
|
WebPage *p = const_cast<WebPage*>(page);
|
2015-10-09 20:42:25 +02:00
|
|
|
const QString &js = source.arg(pos.x()).arg(pos.y());
|
2015-09-29 21:53:56 +02:00
|
|
|
init(page->url(), p->execJavaScript(js).toMap());
|
|
|
|
}
|
|
|
|
|
|
|
|
QString WebHitTestResult::alternateText() const
|
|
|
|
{
|
|
|
|
return m_alternateText;
|
|
|
|
}
|
|
|
|
|
|
|
|
QRect WebHitTestResult::boundingRect() const
|
|
|
|
{
|
|
|
|
return m_boundingRect;
|
|
|
|
}
|
|
|
|
|
|
|
|
QUrl WebHitTestResult::imageUrl() const
|
|
|
|
{
|
|
|
|
return m_imageUrl;
|
|
|
|
}
|
|
|
|
|
|
|
|
bool WebHitTestResult::isContentEditable() const
|
|
|
|
{
|
|
|
|
return m_isContentEditable;
|
|
|
|
}
|
|
|
|
|
2015-09-29 23:15:46 +02:00
|
|
|
bool WebHitTestResult::isContentSelected() const
|
|
|
|
{
|
|
|
|
return m_isContentSelected;
|
|
|
|
}
|
|
|
|
|
2015-09-29 21:53:56 +02:00
|
|
|
bool WebHitTestResult::isNull() const
|
|
|
|
{
|
|
|
|
return m_isNull;
|
|
|
|
}
|
|
|
|
|
2015-09-29 23:15:46 +02:00
|
|
|
QString WebHitTestResult::linkTitle() const
|
|
|
|
{
|
|
|
|
return m_linkTitle;
|
|
|
|
}
|
|
|
|
|
2015-09-29 21:53:56 +02:00
|
|
|
QUrl WebHitTestResult::linkUrl() const
|
|
|
|
{
|
|
|
|
return m_linkUrl;
|
|
|
|
}
|
|
|
|
|
|
|
|
QUrl WebHitTestResult::mediaUrl() const
|
|
|
|
{
|
|
|
|
return m_mediaUrl;
|
|
|
|
}
|
|
|
|
|
2015-09-30 15:26:52 +02:00
|
|
|
bool WebHitTestResult::mediaPaused() const
|
|
|
|
{
|
|
|
|
return m_mediaPaused;
|
|
|
|
}
|
|
|
|
|
|
|
|
bool WebHitTestResult::mediaMuted() const
|
|
|
|
{
|
|
|
|
return m_mediaMuted;
|
|
|
|
}
|
|
|
|
|
2015-09-29 21:53:56 +02:00
|
|
|
QPoint WebHitTestResult::pos() const
|
|
|
|
{
|
|
|
|
return m_pos;
|
|
|
|
}
|
|
|
|
|
|
|
|
QString WebHitTestResult::tagName() const
|
|
|
|
{
|
|
|
|
return m_tagName;
|
|
|
|
}
|
|
|
|
|
|
|
|
void WebHitTestResult::init(const QUrl &url, const QVariantMap &map)
|
|
|
|
{
|
|
|
|
if (map.isEmpty())
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_alternateText = map.value(QSL("alternateText")).toString();
|
|
|
|
m_imageUrl = map.value(QSL("imageUrl")).toUrl();
|
|
|
|
m_isContentEditable = map.value(QSL("contentEditable")).toBool();
|
|
|
|
m_isContentSelected = map.value(QSL("contentSelected")).toBool();
|
2015-09-29 23:15:46 +02:00
|
|
|
m_linkTitle = map.value(QSL("linkTitle")).toString();
|
2015-09-29 21:53:56 +02:00
|
|
|
m_linkUrl = map.value(QSL("linkUrl")).toUrl();
|
|
|
|
m_mediaUrl = map.value(QSL("mediaUrl")).toUrl();
|
2015-09-30 15:26:52 +02:00
|
|
|
m_mediaPaused = map.value(QSL("mediaPaused")).toBool();
|
|
|
|
m_mediaMuted = map.value(QSL("mediaMuted")).toBool();
|
2015-09-29 21:53:56 +02:00
|
|
|
m_tagName = map.value(QSL("tagName")).toString();
|
|
|
|
|
|
|
|
const QVariantList &rect = map.value(QSL("boundingRect")).toList();
|
|
|
|
if (rect.size() == 4)
|
|
|
|
m_boundingRect = QRect(rect.at(0).toInt(), rect.at(1).toInt(), rect.at(2).toInt(), rect.at(3).toInt());
|
|
|
|
|
2015-10-09 15:57:35 +02:00
|
|
|
if (!m_imageUrl.isEmpty())
|
|
|
|
m_imageUrl = url.resolved(m_imageUrl);
|
2015-09-29 21:53:56 +02:00
|
|
|
if (!m_linkUrl.isEmpty())
|
|
|
|
m_linkUrl = url.resolved(m_linkUrl);
|
|
|
|
if (!m_mediaUrl.isEmpty())
|
|
|
|
m_mediaUrl = url.resolved(m_mediaUrl);
|
|
|
|
}
|
|
|
|
|