godot_core/tools/
translate.rs

1/*
2 * Copyright (c) godot-rust; Bromeon and contributors.
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at https://mozilla.org/MPL/2.0/.
6 */
7
8//! Macros for translation.
9
10pub use crate::{tr, tr_n};
11
12/// A convenience macro for using the [`Object::tr()`](crate::classes::Object::tr()) and [`Object::tr_ex()`](crate::classes::Object::tr_ex())
13///  methods.
14///
15/// Takes a format string literal, with optional arguments. Optionally, `context` for potentially ambiguous words can be
16/// added before the format arguments, separated with a `;`.
17///
18/// Using named or positional parameters instead of `{}` may make it easier to use dynamic formatting once gdext supports it:
19/// ```no_run
20/// # #[macro_use] extern crate godot;
21/// # use godot::builtin::Vector2i;
22/// # let a = Vector2i { x: 0, y: 0 };
23/// # let b = Vector2i { x: 0, y: 0 };
24/// # let context = "context";
25/// use godot::tools::tr;
26///
27/// // Good.
28/// tr!(context; "{a} is a {b}"); // inlined, with context
29/// tr!("{0} is a {1}", a, b); // positional, without context
30/// tr!("{c} is a {d}", c = a.x, d = b.y); // named (inlining not possible here)
31///
32/// // Not as good, much more fragile.
33/// tr!("{} is a {}", a, b);
34/// ```
35/// The methods are called from the [`Engine`](crate::classes::Engine) singleton.
36///
37/// See also: [Translation contexts](https://docs.godotengine.org/en/stable/tutorials/i18n/internationalizing_games.html#translation-contexts)
38/// in Godot.
39#[macro_export]
40macro_rules! tr {
41    ($fmt:literal $(, $($args:tt)*)?) => {{
42        let msg = format!($fmt $(, $($args)*)?);
43
44        <$crate::classes::Engine as $crate::obj::Singleton>::singleton().tr(&msg)
45    }};
46
47    ($context:expr; $fmt:literal $(, $($args:tt)*)?) => {{
48        let msg = format!($fmt $(, $($args)*)?);
49        let context = format!("{}", $context);
50
51        <$crate::classes::Engine as $crate::obj::Singleton>::singleton()
52            .tr_ex(&msg)
53            .context(&context)
54            .done()
55    }};
56}
57
58/// A convenience macro for using the [`Object::tr_n()`](crate::classes::Object::tr_n()) and
59/// [`Object::tr_n_ex()`](crate::classes::Object::tr_n_ex()) methods.
60///
61/// Allows for the use of format strings with arbitrary arguments. `n` is given prior to the format string, followed by `;`.
62/// Optionally, `context` for potentially ambiguous words can be added with `,` after `n` and before `;`.
63///
64/// Using named or positional parameters instead of `{}` may make it easier to use dynamic formatting once gdext supports it:
65/// ```no_run
66/// # #[macro_use] extern crate godot;
67/// # use godot::builtin::Vector2i;
68/// # let a = Vector2i { x: 0, y: 0 };
69/// # let b = Vector2i { x: 0, y: 0 };
70/// # let context = "context";
71/// # let n = 2;
72/// use godot::tools::tr_n;
73///
74/// // Good.
75/// tr_n!(n, context; "{a} is a {b}", "{a}s are {b}s"); // inlined, with context
76/// tr_n!(n; "{0} is a {1}", "{0}s are {1}s", a, b); // positional, without context
77/// tr_n!(n; "{c} is a {d}", "{c}s are {d}s", c = a.x, d = b.y); // named (inlining not possible here)
78///
79/// // Not as good, much more fragile.
80/// // Additionally, such syntax requires that BOTH format strings use ALL listed arguments.
81/// tr_n!(n; "{} is a {}", "{}s are {}s", a, b);
82/// ```
83/// The methods are called from the [`Engine`](crate::classes::Engine) singleton.
84///
85/// See also: [Translation contexts](https://docs.godotengine.org/en/stable/tutorials/i18n/internationalizing_games.html#translation-contexts)
86/// in Godot.
87#[macro_export]
88macro_rules! tr_n {
89    ($n:expr; $singular:literal, $plural:literal $(, $($args:tt)*)?) => {
90        <$crate::classes::Engine as $crate::obj::Singleton>::singleton()
91            .tr_n(
92                &format!($singular$(, $($args)*)?),
93                &format!($plural$(, $($args)*)?),
94                $n,
95            )
96    };
97
98    ($n:expr, $context:expr; $singular:literal, $plural:literal $(, $($args:tt)*)?) => {
99        <$crate::classes::Engine as $crate::obj::Singleton>::singleton()
100            .tr_n_ex(
101                &format!($singular$(, $($args)*)?),
102                &format!($plural$(, $($args)*)?),
103                $n,
104            )
105            .context(&format!("{}", $context))
106            .done()
107    };
108}