16 #include <QApplication>
17 #include <QFileDialog>
19 #include <QTextStream>
20 #include <QTextDocument>
22 #include <type_traits>
24 #include "../../../backend/drivers/cswordmoduleinfo.h"
25 #include "../../../backend/keys/cswordversekey.h"
26 #include "../../../util/btassert.h"
27 #include "../../../util/tool.h"
56 , m_searchedText(std::move(searchedText))
58 setBackgroundBrush(QBrush(Qt::white));
59 setSceneRect(0, 0, 1, 1);
61 for (
auto const & result : results)
66 auto const numberOfModules =
m_results.size();
77 qApp->processEvents(QEventLoop::AllEvents);
78 for (
auto const & moduleresultPtr : result.results) {
81 BT_ASSERT(
dynamic_cast<sword::VerseKey
const *
>(
82 moduleresultPtr.get()));
83 auto const *
const vk =
84 static_cast<sword::VerseKey
const *
>(
85 moduleresultPtr.get());
86 auto key = std::tuple(vk->getTestament(), vk->getBook());
88 static_assert(std::is_same_v<decltype(key),
91 analysisItem = it->second;
95 QString::fromUtf8(vk->getBookName()),
97 m_itemList.emplace(std::move(key), analysisItem);
99 auto const count = ++analysisItem->
counts()[moduleIndex];
110 auto & analysisItem = *vp.second;
111 addItem(&analysisItem);
112 analysisItem.setRect(xPos,
114 analysisItem.rect().width(),
115 analysisItem.rect().height());
118 QStringList toolTipItems;
121 auto const *
const info = result.module;
123 auto const count = result.results.size();
124 double const percent =
126 ? ((
static_cast<double>(analysisItem.counts()[i])
127 *
static_cast<double>(100.0))
128 /
static_cast<double>(count))
131 QStringLiteral(
"%1\">%2</span></b></td><td>%3 (%4")
133 info ? info->name() : QString(),
134 QString::number(analysisItem.counts()[i]),
135 QString::number(percent,
'g', 2)));
138 #define ROW_START "<tr bgcolor=\"white\"><td><b><span style=\"color:"
139 #define ROW_END "%)</td></tr>"
140 analysisItem.setToolTip(
142 "<center><b>%1</b></center><hr/>"
143 "<table cellspacing=\"0\" cellpadding=\"3\" "
144 "width=\"100%\" height=\"100%\" align=\"center\">"
146 .arg(analysisItem.bookName().toHtmlEscaped(),
165 auto & analysisItem = *vp.second;
166 analysisItem.setScaleFactor(scaleFactor);
167 analysisItem.setRect(analysisItem.rect().x(),
181 return Qt::darkGreen;
197 return Qt::darkMagenta;
204 auto const fileName =
205 QFileDialog::getSaveFileName(
207 tr(
"Save Search Analysis"),
209 QObject::tr(
"HTML files") + QStringLiteral(
" (*.html *.htm);;")
210 + QObject::tr(
"All files") + QStringLiteral(
" (*)"));
211 if (fileName.isEmpty())
215 static auto const writer =
216 +[](QTextStream & out,
void * userPtr)
217 {
static_cast<UserData
const *
>(userPtr)->obj.
saveAsHTML(out); };
222 auto const title(tr(
"BibleTime Search Analysis"));
223 out << QStringLiteral(
224 "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
225 "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\" "
226 "\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">"
227 "<html xmlns=\"http://www.w3.org/1999/xhtml\"><head><title>")
231 "<style type=\"text/css\">"
232 "body{background-color:#fff;color:#000}"
233 "table{border-collapse:collapse}"
234 "td{border:1px solid #333}"
235 "th{font-size:130%;text-align:left;vertical-align:top}"
236 "td,th{text-align:left;padding:0.2em 0.5em}"
237 ".r{text-align:right}"
239 "<meta http-equiv=\"Content-Type\" "
240 "content=\"text/html; charset=utf-8\"/>"
243 << QStringLiteral(
"</h1><p><span style=\"font-weight:bold\">")
244 << tr(
"Search text:")
245 << QStringLiteral(
"</span> ")
247 << QStringLiteral(
"</p><table><caption>")
248 << tr(
"Results by work and book")
249 << QStringLiteral(
"</caption><tr><th>")
251 << QStringLiteral(
"</th>");
254 out << QStringLiteral(
"<th>")
255 << result.module->name().toHtmlEscaped()
256 << QStringLiteral(
"</th>");
257 out << QStringLiteral(
"</tr>");
260 auto const & analysisItem = *vp.second;
261 out << QStringLiteral(
"<tr><td>")
262 << analysisItem.bookName().toHtmlEscaped()
263 << QStringLiteral(
"</td>");
264 for (
auto const count : analysisItem.counts())
265 out << QStringLiteral(
"<td class=\"r\">")
266 << QString::number(count)
267 << QStringLiteral(
"</td>");
268 out << QStringLiteral(
"</tr>");
270 out << QStringLiteral(
"<tr><th class=\"r\">")
272 << QStringLiteral(
"</th>");
275 out << QStringLiteral(
"<td class=\"r\">")
276 << QString::number(result.results.size())
277 << QStringLiteral(
"</td>");
280 out << QStringLiteral(
"</tr></table><p style=\"text-align:center;"
281 "font-size:x-small\">")
282 << tr(
"Created by <a href=\"https://bibletime.info/\">BibleTime</a>")
283 << QStringLiteral(
"</p></body></html>");
287 setSceneRect(0, 0, sceneRect().width(), height);
std::unique_ptr< CSearchAnalysisLegendItem > m_legend
void resizeHeight(int height)
std::map< std::tuple< char, char >, CSearchAnalysisItem * > m_itemList
CSwordModuleSearch::Results m_results
CSearchAnalysisScene(QString searchedText, CSwordModuleSearch::Results const &results, QObject *parent)
static QColor getColor(int index)
QString const m_searchedText
std::vector< ModuleSearchResult > Results
const int SPACE_BETWEEN_PARTS
const int BAR_LOWER_BORDER
const int LEGEND_INNER_BORDER