Project

General

Profile

Bug #2501 » code.cpp

Marco Gulino, 12/04/2013 04:32 PM

 
WTemplate printable;
Dbo::Transaction t(d->session);
printable.setTemplateText("\
${<render-type-html>}\
<html>\n\
<head>\n\
<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\">\
<title>${title}</title>\n\
<style type=\"text/css\">\n\
@media print {\
table { page-break-inside:auto }\
tr { page-break-inside:avoid; page-break-after:auto }\
td { page-break-inside:avoid; page-break-after:auto }\
}\
</style>\n\
</head>\
<body>\n\
${</render-type-html>}\
${<render-type-pdf>}\
<style type=\"text/css\">\n\
table { page-break-inside:auto }\
tr { page-break-inside:avoid; page-break-after:auto }\
</style>\n\
${</render-type-pdf>}\
<h2 style=\"text-align: center; \">${title}</h2>\n\
${<have-place>}\
<p>${sessionDate}, Moon Phase: ${moonPhase}%</p>\n\
<p>Sun: rising at ${sunRise}, setting at ${sunSet}</p>\n\
<p>Moon: rising at ${moonRise}, setting at ${moonSet}</p>\n\
${<have-telescope>}<p>Suggestions for telescope: \"${telescope-name}\", diameter ${telescope-diameter}mm, focal length ${telescope-focal-length}mm</p>${</have-telescope>}\
${</have-place>}\
<table border=\"1\">\n\
<thead>\n\
<tr>\n\
<th>Names</th>\n\
<th>AR</th>\n\
<th>Dec</th>\n\
<th>Constellation</th>\n\
<th>Size</th>\n\
<th>Magn.</th>\n\
<th>Type</th>\n\
${<have-place>}\
<th>Highest</th>\n\
<th>Max</th>\n\
${</have-place>}\
${<have-telescope>}\
<th>Difficulty</th>\n\
${</have-telescope>}\
</tr>\n\
</thead>\n\
<tbody>\n\
${table-rows}\
</tbody>\n\
</table>\n\
${<render-type-html>}\
</body></html>\n\
${</render-type-html>}\
", XHTMLUnsafeText);
printable.setCondition("render-type-html", d->reportType == HTML);
printable.setCondition("render-type-pdf", d->reportType == PDF);
printable.bindString("title", d->astroSession->name());
printable.setCondition("have-place", d->astroSession->position());
printable.setCondition("have-telescope", d->telescope);
if(d->telescope) {
printable.bindString("telescope-name", d->telescope->name());
printable.bindInt("telescope-diameter", d->telescope->diameter());
printable.bindInt("telescope-focal-length", d->telescope->focalLength());
}
Ephemeris ephemeris(d->astroSession->position());
printable.bindInt("moonPhase", static_cast<int>(ephemeris.moonPhase(d->astroSession->when()).illuminated_fraction*100.));
printable.bindString("sessionDate", d->astroSession->wDateWhen().date().toString("dddd dd MMMM yyyy"));
if(d->astroSession->position()) {
auto sun = ephemeris.sun(d->astroSession->when());
auto moon = ephemeris.moon(d->astroSession->when());
auto formatTime = [](const boost::posix_time::ptime &t) { return (format("%02d:%02d") % t.time_of_day().hours() % t.time_of_day().minutes()).str(); };
printable.bindString("sunRise",formatTime(sun.rise));
printable.bindString("sunSet", formatTime(sun.set));
printable.bindString("moonRise", formatTime(moon.rise));
printable.bindString("moonSet", formatTime(moon.set));
}
stringstream tableRows;
auto sessionObjectsDbCollection = d->astroSession->astroSessionObjects();
vector<dbo::ptr<AstroSessionObject>> sessionObjects(sessionObjectsDbCollection.begin(), sessionObjectsDbCollection.end());
sort(begin(sessionObjects), end(sessionObjects), [&](const dbo::ptr<AstroSessionObject> &a, const dbo::ptr<AstroSessionObject> &b){
return a->bestAltitude(ephemeris, -3 ).when < b->bestAltitude(ephemeris, -3).when;
});
for(auto sessionObject: sessionObjects) {
WTemplate rowTemplate;
rowTemplate.setTemplateText("<tr style=\"page-break-inside:avoid; page-break-after:auto\">\n\
<td>${namesWidget}</td>\n\
<td>${ar}</td>\n\
<td>${dec}</td>\n\
<td>${constellation}</td>\n\
<td>${size}</td>\n\
<td>${magnitude}</td>\n\
<td>${type}</td>\n\
${<have-place>}\
<td>${highestAt}</td>\n\
<td>${maxAltitude}</td>\n\
${</have-place>}\
${<have-telescope>}\
<td>${difficulty}</td>\n\
${</have-telescope>}\
</tr>\n\
${<have-description>}\
<tr><td colspan=\"${total-columns}\">${description}</td></tr>\n\
${</have-description>}\
${<have-rows-spacing>}\
<tr style=\"page-break-inside:avoid; page-break-after:auto\">\
<td colspan=\"${total-columns}\" style=\"height: ${rows-spacing}em; page-break-inside:avoid; page-break-after:auto\" />\
</tr>\n\
${</have-rows-spacing>}\
\n", XHTMLUnsafeText);
rowTemplate.bindWidget("namesWidget", new ObjectNamesWidget{sessionObject->ngcObject(), d->session, d->astroSession, ObjectNamesWidget::Printable});
rowTemplate.bindString("ar", sessionObject->coordinates().rightAscension.printable(Angle::Hourly));
rowTemplate.bindWidget("dec", new WText{WString::fromUTF8( sessionObject->coordinates().declination.printable(Angle::Degrees, Angle::HTML) ) } );
rowTemplate.bindString("constellation", ConstellationFinder::getName(sessionObject->coordinates()).name);
rowTemplate.bindString("size", WString::fromUTF8( Angle::degrees(sessionObject->ngcObject()->angularSize()).printable(Angle::Degrees, Angle::HTML) ));
rowTemplate.bindString("magnitude", format("%.1f") % sessionObject->ngcObject()->magnitude() );
rowTemplate.bindString("type", sessionObject->ngcObject()->typeDescription());
rowTemplate.setCondition("have-place", d->astroSession->position());
rowTemplate.setCondition("have-telescope", d->telescope);
rowTemplate.bindInt("total-columns", d->astroSession->position() ? 10 : 8);
auto bestAltitude = sessionObject->bestAltitude(ephemeris, 1);
if(d->astroSession->position()) {
rowTemplate.bindString("highestAt", WDateTime::fromPosixTime( bestAltitude.when).time().toString() );
rowTemplate.bindString("maxAltitude", WString::fromUTF8(bestAltitude.coordinates.altitude.printable(Angle::Degrees, Angle::HTML)) );
}
rowTemplate.bindWidget("difficulty", new ObjectDifficultyWidget{sessionObject->ngcObject(), d->telescope, bestAltitude.coordinates.altitude.degrees() });
rowTemplate.setCondition("have-description", !sessionObject->description().empty());
rowTemplate.bindString("description", Utils::htmlEncode(WString::fromUTF8(sessionObject->description())));
rowTemplate.setCondition("have-rows-spacing", d->rowsSpacing > 0);
rowTemplate.bindString("rows-spacing", format("%.1f") % (static_cast<double>(d->rowsSpacing) * 1.3) );
rowTemplate.renderTemplate(tableRows);
}
printable.bindString("table-rows", WString::fromUTF8(tableRows.str()));
if(d->reportType == HTML) {
printable.renderTemplate(response.out());
return;
}
suggestFileName(format("%s.pdf") % d->astroSession->name());
response.setMimeType("application/pdf");
HPDF_Doc pdf = HPDF_New(error_handler, 0);
#ifdef HAVE_LIBHARU_UTF8
HPDF_UseUTFEncodings(pdf);
HPDF_SetCurrentEncoder(pdf, "UTF-8");
#endif
HPDF_Page page = HPDF_AddPage(pdf);
HPDF_Page_SetSize(page, HPDF_PAGE_SIZE_A4, HPDF_PAGE_LANDSCAPE);
Wt::Render::WPdfRenderer renderer(pdf, page);
renderer.setMargin(2.54);
renderer.setDpi(96);
renderer.addFontCollection("/usr/share/fonts", true);
stringstream buffer;
printable.renderTemplate(buffer);
string b = buffer.str();
boost::replace_all(b, "°", "&deg;");
cerr << "--------------------" << endl << b << endl << "----------------------" << endl;
renderer.render(WString::fromUTF8(b));
HPDF_SaveToStream(pdf);
unsigned int size = HPDF_GetStreamSize(pdf);
HPDF_BYTE *buf = new HPDF_BYTE[size];
HPDF_ReadFromStream (pdf, buf, &size);
HPDF_Free(pdf);
response.out().write((char*)buf, size);
delete[] buf;
(1-1/3)