diff --git a/CHANGELOG.md b/CHANGELOG.md
index a1607125bd..aa0ca63858 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -5,6 +5,7 @@
### Next version
* Added slider to change message column width
+* Added option for formal/informal DeepL translation
* Small improvements and minor bug fixes
### [Epidexipteryx](https://en.wikipedia.org/wiki/Epidexipteryx)
diff --git a/app/src/main/assets/CHANGELOG.md b/app/src/main/assets/CHANGELOG.md
index a1607125bd..aa0ca63858 100644
--- a/app/src/main/assets/CHANGELOG.md
+++ b/app/src/main/assets/CHANGELOG.md
@@ -5,6 +5,7 @@
### Next version
* Added slider to change message column width
+* Added option for formal/informal DeepL translation
* Small improvements and minor bug fixes
### [Epidexipteryx](https://en.wikipedia.org/wiki/Epidexipteryx)
diff --git a/app/src/main/java/eu/faircode/email/DeepL.java b/app/src/main/java/eu/faircode/email/DeepL.java
index 49874d4975..db887b852f 100644
--- a/app/src/main/java/eu/faircode/email/DeepL.java
+++ b/app/src/main/java/eu/faircode/email/DeepL.java
@@ -60,6 +60,7 @@ import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
+import java.util.Objects;
import javax.net.ssl.HttpsURLConnection;
@@ -100,6 +101,7 @@ public class DeepL {
JSONObject jlanguage = jlanguages.getJSONObject(i);
String name = jlanguage.getString("name");
String target = jlanguage.getString("language");
+ boolean formality = jlanguage.optBoolean("supports_formality");
Locale locale = Locale.forLanguageTag(target);
if (locale != null)
@@ -110,7 +112,7 @@ public class DeepL {
String resname = "language_" + target.toLowerCase().replace('-', '_');
int resid = res.getIdentifier(resname, "drawable", pkg);
- languages.add(new Language(name, target,
+ languages.add(new Language(name, target, formality,
resid == 0 ? null : resid,
favorites && frequency > 0));
frequencies.put(target, frequency);
@@ -188,11 +190,28 @@ public class DeepL {
}
public static Translation translate(String text, String target, Context context) throws IOException, JSONException {
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+ boolean formality = prefs.getBoolean("deepl_formal", true);
+ return translate(text, target, formality, context);
+ }
+
+ public static Translation translate(String text, String target, boolean formality, Context context) throws IOException, JSONException {
// https://www.deepl.com/docs-api/translating-text/request/
String request =
"text=" + URLEncoder.encode(text, StandardCharsets.UTF_8.name()) +
"&target_lang=" + URLEncoder.encode(target, StandardCharsets.UTF_8.name());
+ ensureLanguages(context);
+ for (int i = 0; i < jlanguages.length(); i++) {
+ JSONObject jlanguage = jlanguages.getJSONObject(i);
+ if (Objects.equals(target, jlanguage.getString("language"))) {
+ boolean supports_formality = jlanguage.optBoolean("supports_formality");
+ if (supports_formality)
+ request += "&formality=" + (formality ? "more" : "less");
+ break;
+ }
+ }
+
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
String key = prefs.getString("deepl_key", null);
@@ -289,12 +308,14 @@ public class DeepL {
public static class Language {
public String name;
public String target;
+ public boolean formality;
public Integer icon;
public boolean favorite;
- private Language(String name, String target, Integer icon, boolean favorit) {
+ private Language(String name, String target, boolean formality, Integer icon, boolean favorit) {
this.name = name;
this.target = target;
+ this.formality = formality;
this.icon = icon;
this.favorite = favorit;
}
@@ -319,12 +340,15 @@ public class DeepL {
final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
String key = prefs.getString("deepl_key", null);
boolean pro = prefs.getBoolean("deepl_pro", false);
+ boolean formal = prefs.getBoolean("deepl_formal", true);
boolean small = prefs.getBoolean("deepl_small", false);
View view = LayoutInflater.from(context).inflate(R.layout.dialog_deepl, null);
final ImageButton ibInfo = view.findViewById(R.id.ibInfo);
final EditText etKey = view.findViewById(R.id.etKey);
final CheckBox cbPro = view.findViewById(R.id.cbPro);
+ final CheckBox cbFormal = view.findViewById(R.id.cbFormal);
+ final TextView tvFormal = view.findViewById(R.id.tvFormal);
final CheckBox cbSmall = view.findViewById(R.id.cbSmall);
final TextView tvUsage = view.findViewById(R.id.tvUsage);
final TextView tvPrivacy = view.findViewById(R.id.tvPrivacy);
@@ -353,6 +377,19 @@ public class DeepL {
etKey.setText(key);
cbPro.setChecked(pro);
+ cbFormal.setChecked(formal);
+
+ try {
+ List formals = new ArrayList<>();
+ for (Language lang : getTargetLanguages(context, false))
+ if (lang.formality)
+ formals.add(lang.name);
+
+ tvFormal.setText(TextUtils.join(", ", formals));
+ } catch (Throwable ex) {
+ tvFormal.setText(Log.formatThrowable(ex, false));
+ }
+
cbSmall.setChecked(small);
tvUsage.setVisibility(View.GONE);
@@ -396,6 +433,7 @@ public class DeepL {
else
editor.putString("deepl_key", key);
editor.putBoolean("deepl_pro", cbPro.isChecked());
+ editor.putBoolean("deepl_formal", cbFormal.isChecked());
editor.putBoolean("deepl_small", cbSmall.isChecked());
editor.apply();
}
diff --git a/app/src/main/res/layout/dialog_deepl.xml b/app/src/main/res/layout/dialog_deepl.xml
index 924f6da4a4..55bae02795 100644
--- a/app/src/main/res/layout/dialog_deepl.xml
+++ b/app/src/main/res/layout/dialog_deepl.xml
@@ -62,6 +62,25 @@
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/etKey" />
+
+
+
+
+ app:layout_constraintTop_toBottomOf="@id/tvFormal" />
Configure …
Enter key
Translating …
+ Use formal form
Use a small font for the source text
Usage: %1$s / %2$s (%3$d %%)
Tap the text to be translated
diff --git a/metadata/en-US/changelogs/1830.txt b/metadata/en-US/changelogs/1830.txt
index a1607125bd..aa0ca63858 100644
--- a/metadata/en-US/changelogs/1830.txt
+++ b/metadata/en-US/changelogs/1830.txt
@@ -5,6 +5,7 @@
### Next version
* Added slider to change message column width
+* Added option for formal/informal DeepL translation
* Small improvements and minor bug fixes
### [Epidexipteryx](https://en.wikipedia.org/wiki/Epidexipteryx)