18 #include "grantleeview_p.h" 20 #include "application.h" 26 #include <grantlee/qtlocalizer.h> 29 #include <QDirIterator> 30 #include <QtCore/QLoggingCategory> 31 #include <QTranslator> 33 Q_LOGGING_CATEGORY(CUTELYST_GRANTLEE,
"cutelyst.grantlee", QtWarningMsg)
43 d->engine =
new Grantlee::Engine(
this);
44 d->engine->addTemplateLoader(d->loader);
48 for (
const QByteArray &dir : dirs) {
49 d->engine->addPluginPath(QString::fromLocal8Bit(dir));
52 d->engine->addDefaultLibrary(QStringLiteral(
"grantlee_cutelyst"));
54 auto app = qobject_cast<Application *>(parent);
61 d->cutelystVar = app->config(QStringLiteral(
"CUTELYST_VAR"), QStringLiteral(
"c")).toString();
63 app->loadTranslations(QStringLiteral(
"plugin_view_grantlee"));
73 return d->includePaths;
79 d->loader->setTemplateDirs(paths);
80 d->includePaths = paths;
93 d->extension = extension;
114 if (enable != d->cache.isNull()) {
119 d->engine =
new Grantlee::Engine(
this);
123 d->engine->addTemplateLoader(d->cache);
126 d->engine->addTemplateLoader(d->loader);
147 QDirIterator it(includePath, {
150 QDir::Files | QDir::NoDotAndDotDot,
151 QDirIterator::Subdirectories);
152 while (it.hasNext()) {
153 QString path = it.next();
154 path.remove(includePath);
159 if (d->cache->canLoadTemplate(path)) {
160 d->cache->loadByName(path, d->engine);
169 return !d->cache.isNull();
177 c->
setStash(d->cutelystVar, QVariant::fromValue(c));
178 const QVariantHash stash = c->
stash();
179 auto it = stash.constFind(QStringLiteral(
"template"));
180 QString templateFile;
181 if (it != stash.constEnd()) {
182 templateFile = it.value().toString();
184 if (c->action() && !c->action()->
reverse().isEmpty()) {
185 templateFile = c->action()->
reverse() + d->extension;
187 templateFile.remove(0, 1);
191 if (templateFile.isEmpty()) {
192 c->
error(QStringLiteral(
"Cannot render template, template name or template stash key not defined"));
197 qCDebug(CUTELYST_GRANTLEE) <<
"Rendering template" << templateFile;
199 Grantlee::Context gc(stash);
203 auto transIt = d->translators.constFind(c->
locale());
204 if (transIt != d->translators.constEnd()) {
205 localizer.data()->installTranslator(transIt.value(), transIt.key().name());
208 auto catalogIt = d->translationCatalogs.constBegin();
209 while (catalogIt != d->translationCatalogs.constEnd()) {
210 localizer.data()->loadCatalog(catalogIt.value(), catalogIt.key());
214 gc.setLocalizer(localizer);
216 Grantlee::Template tmpl = d->engine->loadByName(templateFile);
217 if (tmpl->error() != Grantlee::NoError) {
223 QString content = tmpl->render(&gc);
224 if (tmpl->error() != Grantlee::NoError) {
230 if (!d->wrapper.isEmpty()) {
231 Grantlee::Template
wrapper = d->engine->loadByName(d->wrapper);
232 if (tmpl->error() != Grantlee::NoError) {
238 Grantlee::SafeString safeContent(content,
true);
239 gc.insert(QStringLiteral(
"content"), safeContent);
240 content =
wrapper->render(&gc);
242 if (
wrapper->error() != Grantlee::NoError) {
249 ret = content.toUtf8();
256 Q_ASSERT_X(translator,
"add translator to GrantleeView",
"invalid QTranslator object");
257 d->translators.insert(locale, translator);
268 Q_ASSERT_X(!path.isEmpty(),
"add translation catalog to GrantleeView",
"empty path");
269 Q_ASSERT_X(!catalog.isEmpty(),
"add translation catalog to GrantleeView",
"empty catalog name");
270 d->translationCatalogs.insert(catalog, path);
276 Q_ASSERT_X(!catalogs.
empty(),
"add translation catalogs to GranteleeView",
"empty QHash");
277 d->translationCatalogs.unite(catalogs);
282 QVector<QLocale> locales;
284 if (Q_LIKELY(!filename.isEmpty() && !directory.isEmpty())) {
285 const QDir i18nDir(directory);
286 if (Q_LIKELY(i18nDir.exists())) {
287 const QString _prefix = prefix.isEmpty() ? QStringLiteral(
".") : prefix;
288 const QString _suffix = suffix.isEmpty() ? QStringLiteral(
".qm") : suffix;
290 const QFileInfoList tsFiles = i18nDir.entryInfoList(namesFilter, QDir::Files);
291 if (Q_LIKELY(!tsFiles.empty())) {
292 locales.reserve(tsFiles.size());
293 for (
const QFileInfo &ts : tsFiles) {
294 const QString fn = ts.fileName();
295 const int prefIdx = fn.
indexOf(_prefix);
296 const QString locString = fn.mid(prefIdx + _prefix.length(), fn.length() - prefIdx - _suffix.length() - _prefix.length());
297 QLocale loc(locString);
298 if (Q_LIKELY(loc.language() != QLocale::C)) {
299 auto trans =
new QTranslator(
this);
300 if (Q_LIKELY(trans->load(loc, filename, _prefix, directory))) {
303 qCDebug(CUTELYST_GRANTLEE) <<
"Loaded translations for locale" << loc <<
"from" << ts.absoluteFilePath();
306 qCWarning(CUTELYST_GRANTLEE) <<
"Can not load translations for locale" << loc;
309 qCWarning(CUTELYST_GRANTLEE) <<
"Can not load translations for invalid locale string" << locString;
314 qCWarning(CUTELYST_GRANTLEE) <<
"Can not find translation files for" << filename <<
"in directory" << directory;
317 qCWarning(CUTELYST_GRANTLEE) <<
"Can not load translations from not existing directory:" << directory;
320 qCWarning(CUTELYST_GRANTLEE) <<
"Can not load translations for empty file name or empty path.";
326 #include "moc_grantleeview.cpp"
QStringList includePaths() const
Returns the list of include paths.
QSharedPointer< T > create()
bool isCaching() const
Returns true if caching is enabled.
void setIncludePaths(const QStringList &paths)
Sets the list of include paths which will be looked for when resolving templates files.
void setStash(const QString &key, const QVariant &value)
QVector< QLocale > loadTranslationsFromDir(const QString &filename, const QString &directory, const QString &prefix=QStringLiteral("."), const QString &suffix=QStringLiteral(".qm"))
QByteArray render(Context *c) const final
GrantleeView(QObject *parent=nullptr, const QString &name=QString())
Constructs a GrantleeView object with the given parent and name.
QString translate(const char *context, const char *sourceText, const char *disambiguation=nullptr, int n=-1) const
The Cutelyst namespace holds all public Cutelyst API.
void setWrapper(const QString &name)
Sets the template wrapper name, the template will be rendered into content variable in which the wrap...
QString wrapper() const
Returns the template wrapper.
void setTemplateExtension(const QString &extension)
Sets the template extension, defaults to ".html".
void addTranslationCatalogs(const QHash< QString, QString > &catalogs)
QString templateExtension() const
Returns the template extension.
Cutelyst View abstract view component
int indexOf(const int &rx, int from) const const
void addTranslator(const QLocale &locale, QTranslator *translator)
void setBody(QIODevice *body)
Grantlee::Engine * engine() const
void addTranslationCatalog(const QString &path, const QString &catalog)
bool error() const
Returns true if an error was set.
void setCache(bool enable)
Sets if template caching should be done, this increases performance at the cost of higher memory usag...
void stash(const QVariantHash &unite)