twine
twine copied to clipboard
Support plural forms
A feature request, we would love it twine supported plural forms. Something like:
[delete_things]
en:one = Delete this object?
en:other = Delete these objects?
Android has support for plural forms in its string resources:
<plurals
name="plural_name">
<item
quantity=["zero" | "one" | "two" | "few" | "many" | "other"]
>text_string</item>
</plurals>
iOS could use Smartling
gettext also has support for plural forms
A very good idea! We have actually talked about this briefly, but have not taken it any further than casual discussion.
The way I currently do plurals in twine is having a separate key for each plural, such as cool_things_one
cool_things_other
, then do
<plurals
name="cool_things">
<item quantity="one">@string/cool_things_one</item>
<item quantity="other">@string/cool_things_other</item>
</plurals>
in a separate xml file in values/ that isn't managed by twine.
@yincrash that's a pretty good solution, but that means we need to maintain the list of keys in 2 places
iOS and Mac actually support plurals natively as of 10.9 and iOS 7. You can read about this in the 10.9 Foundation Release Notes.
That said, plurals are tricky. One of the goals for Twine has been to maintain a simple feature set that all of the string file formats support. By fully supporting plural forms for Android, Mac, and iOS, we have to be careful that we don't prevent those strings from being written out to other formats like jQuery, gettext, etc.
I think the trick to implementing this feature properly is to use some sort of convention such that all strings can be written out to all formats. Maybe the twine syntax is modified as @jobi suggested. Plurals could be written out to formats that support it and those that don't will get multiple strings with well-defined suffixes like "delete_things__one", "delete_things__many", etc.
This is a great idea @scelis , I like this approach. This is even a challenge when sending strings for translation since most services don't support the plural format.
The more I think about this feature, the more I think that the benefits do not outweigh the additional complexity.
We had this problem consolidating Android and iOS translations for our app and we ended up implementing it in a project fork (with some convention ideas from here!). We'd be happy to send a PR if you think that would be useful.
@wujessica Thanks for this! I am sure others may find it useful. It might be hard to merge into the main repo until we figure out how it functions with the other (non-iOS and Android) formatters.
@scelis - any way I can convince you to revisit your cost/benefit analysis above :) Any project will sooner or later encounter the need to pluralize. Having to maintain a separate per-platform file as @yincrash is doing it brings the problem twine is solving right back (granted, on a smaller scale). It seems like there must be a way to unlock this functionality for plural-aware formatters, while keeping it neutral for the rest (e.g., by convention only picking the first of key:qty
occurrences). Also, if using up :blah
just for this purpose it too greedy, a more generic scheme can be applied.
@mvarshavsky Is there really great cost to not using plurals in your string files? We use plurals in our apps all the time and it requires just a few lines of code given our twine string file:
if numItems == 1 {
label.string = localizedString("NumItemsSingular", numItems)
} else {
label.string = localizedString("NumItemsPlural", numItems)
}
So yeah, I don't think that the amount of complexity this would add to twine would be worth it just to turn the above chunk of code into:
label.string = localizedString("NumItemsWithPlurals", numItems)
A lot of time it's three: no items / 1 item / n items - but that's besides the point; in my eyes it's just ugly superfluous code that detracts from readability. My belief is that placeholders/interpolation (which twine has) and ability to pluralize is something that all decent-sized projects eventually need and therefore all platforms will eventually evolve to support. I get you're trying to keep complexity out - but that choice pushes it to all consumers of your library :) Anyway, I'm not here to argue, it's your decision, just chiming in with another "+1" on the feature request. We have @wujessica's fork to fall back on. Appreciate all the work you've put into this!
Another consideration is that, while the following code works just fine for English and some other languages, there are many languages where such logic may not be appropriate (e.g. Korean, Chinese, Russian, etc.). These cases are where the platform's in-built plurals system helps you, and requires a more robust set of translations.
if numItems == 1 {
// singular
} else {
// plural
}
Fair point. Once you need to support more than (0 | 1 | more) then it can get trickier. I would not be opposed to twine having decent plural support were a good PR to be submitted (which is why this feature request is still open), but it really is a huge undertaking and still not one that I am convinced is completely worth the effort.
The submitted PR would need to do the following:
- Not break formatters that don't natively support plurals by using some sort of fallback convention.
- Work for both reading and writing the localization files (both
generate-localization-file
andconsume-localization-file
) - Not make the twine file syntax significantly more complex.
It would be awesome if the Android and iOS plural was merged to master.
my team is also looking for this feature, why was the PR closed?
We've implemented this functionality in our fork here: https://github.com/mapsme/twine Usage:
[placepage_summary_rating_description]
en:one = Based on %d review
en:other = Based on %d reviews
ru:one = На основе %d отзыва
ru:other = На основе %d отзывов
...
Plural strings works only for android
and ios
(see separate formatter apple-plural
).
Possible plural modificators.
Hope this will be useful :)
@greshilov - Coming late into the conversation, can you elaborate a bit on what you did? I think I'm going to use something similar in my setup.
Hi @greshilov, I don't understand why you added apple-plural along with apple can't they be merged?
We've implemented this functionality in our fork here: https://github.com/mapsme/twine Usage:
@altagir if I'm not mistaken it was difficult to me to use same logic in one formatter for iOs plural/non plural strings. Unlike android, apple strings are actually generating to different files (.strings
, .stringsdict
).
This script here is using for generating all strings in mapsme, maybe helpful.
@tomgs looks like I've lost your question :( If you still have any questions feel free to ask.
@scelis , The fork from @greshilov works great for plural form (android and ios) could it be merged ? this feature indicates "needs code".
@altagir As far as I can tell, that code isn't really mergeable and was implemented as a one-off fork. I am still amenable to merging this feature into Twine proper, but my requirements from above still stand.
hi @greshilov
on android translations, the character ' is not properly formatted in values/
A plural traduction of "don't ..." should be "don\'t..." else Android Studio cannot parse the xml
only happens with plural form
We use '
to handle correct output for ios and android