How to specify context of translation in Django {% trans %} {% blocktrans %}? - django

Documentation of Django says Contextual markers are also supported by the trans and blocktrans template tags. but it not explained how to do it?
Can you help marking translation context since I have some words with several meanings.
In Python I can do in such way:
pgettext("month name", "May")
pgettext("verb", "May")
How to specify translation context in Django template?
{% blocktrans %}May{% endblocktrans %}

It is explained at the very end of their specific paragraphs:
https://docs.djangoproject.com/en/dev/topics/i18n/translation/#trans-template-tag
{% trans %} also supports contextual markers using the context keyword:
{% trans "May" context "month name" %}
https://docs.djangoproject.com/en/dev/topics/i18n/translation/#blocktrans-template-tag
{% blocktrans %} also supports contextual markers using the context keyword:
{% blocktrans with name=user.username context "greeting" %}Hi {{ name }}{% endblocktrans %}

{% blocktrans context "month name" %}May{% endblocktrans %}

Related

Django i18n blocktrans vs trans

In Django templates, what exactly is the difference between these two:
{% blocktrans %}My Text{% endblocktrans %}
{% trans 'My Text' %}
From Django Docs
Trans template tag
The {% trans %} template tag translates either a constant string (enclosed in single or >double quotes) or variable content:
With a Trans tag, you are limited to a single constant string or variable. So you would have to use
{# These Would Work! #}
title>{% trans "This is the title." %}</title>
<title>{% trans myvar %}</title>
But could not use
{%trans "This is my title {{ myvar }}" %}
Blocktrans template tag
Contrarily to the trans tag, the blocktrans tag allows you to mark complex sentences
consisting of literals and variable content for translation by making use of placeholders:
With a Blocktrans, this kind of code is possible:
{% blocktrans with book_t=book|title author_t=author|title %}
This is {{ book_t }} by {{ author_t }}
{% endblocktrans %}
So Blocktrans is going to allow you to be a bit more complex and through in your output.
But to answer your question literally: not much. Except for the presentation style, both will be sent to the translator as the string 'My Text'

How I can use another Translation for a template rendering

How I can say to the render function which language my e-mail should use if I use i18n?
FYI:
It now looks like this
{% load i18n %}
{% language language %}
{% trans "Hello" %} {{ name }}
{% endlanguage %}
You can wrap the template in the language tag:
{% load i18n %}
{% language email_language %}
...
{% endlanguage %}
In your Python code you should pass the value for email_language to the template. This is the language in which the e-mail will be rendered as the language tag activates that language for that part of the template.

Django template {% trans %} pluralization

According to this section in the Django docs I should use {% blocktrans %} for cases where I need to translate pluralizations. However, with an example like the following, isn't there something more convenient I can do?
{% blocktrans count video.views.count as views %}
The video has been viewed <span>{{ views }}</span> time
{% plural %}
The video has been viewed <span>{{ views }}</span> times
{% endblocktrans %}
I tried to do the following:
{% blocktrans %}time{% plural %}times{% endblocktrans %}
But it threw TemplateSyntaxError: 'blocktrans' doesn't allow other block tags (seen u'plural') inside it
You forgot the count variable as variable_name in the blocktrans tag
The value of that variable will be used to detect if it's plural or not.
{% blocktrans count variable as variable_name %}
time
{% plural %}
{{ variable_name }} times
{% endblocktrans %}
You can use:
{% blocktrans with video.views.count|pluralize as foo and video.views.count as views %}
The video has been viewed <span>{{ views }}</span> time{{ foo }}
{% endblocktrans %}

Django: Passing the result of {% trans %} via a filter

I have a string that I want passed via the "linebreaks" filter.
{% trans "my string"|linebreaks %}
Doesn't work.
Is there another way ?
See filter.
{% filter force_escape|lower %}
{% blocktrans %}This text will be translated, HTML-escaped, and will appear in all lowercase.{% endblocktrans %}
{% endfilter %}
If you need to filter before translation, you can also use:
{% blocktrans with value|filter as myvar %}
This will have {{ myvar }} inside.
{% endblocktrans %}

django blocktrans and i18n in templates

I have an i18n problem in django:
This works fine :
{% trans cat.name %}
cat.name will be translated
But this doesn't work:
{% blocktrans with cat.name|slugify as cat_slug %}{{ cat_slug }}{% endblocktrans %}
cat.name is not translated
If I change the filter :
{% blocktrans with cat.name|capfirst as cat_slug %}{{ cat_slug }}{% endblocktrans %}
I can see that the filter is working, but there is no translation...
I'm only just getting started with Django internationalization, but I think you're misunderstanding how the {% blocktrans %} tag handles placeholders.
The point of blocktrans is to allow the text around the placeholders to be translated. It won't translate anything inside {{...}}.
If you look at the generated .po file, you'll see that the following template code:
{% blocktrans %}This is my variable: {{variable}}{% endblocktrans %}
Will get converted into something like the following:
msgid:"This is my variable: %s"
I don't think you can translate a variable within a blocktrans tag. You can probably do constant strings with {% blocktrans with _("string") as x %}{{x}}{% endblocktrans %} but I can't think why you'd want to.
You'll have to do what you want in your view or model code I think.
This works:
{% filter slugify %}{% trans cat.name %}{% endfilter %}
As Tom pointed out blocktrans will preserve what you put inside the with statement instead of translating it. What you need to do is use the with before the translation. In your example, it would look like this:
{% with cat_slug=cat.name|slugify %}
{% trans cat_slug %}
{% endwith %}
P.S. I know I'm answering a 6yr old question, but I've run across this exact situation a couple times now and haven't seen a SO question/answer that handles it.
{% blocktrans with cat.name as cat_slug %}{{ cat_slug|capfirst }}{% endblocktrans %}
?
EDIT: you were right the doc says the filter as to be placed in the blocktrans
{% blocktrans with cat_slug=cat.name|capfirst %}{{ cat_slug }}{% endblocktrans %}