2024-05-22 05:58:12 +00:00
{{ template "header" . }}
2023-06-24 18:40:57 +00:00
< main >
2023-09-10 11:57:22 +00:00
<!-- Need to do this custom selector thingy since <select> cant submit on click -->
< div class = "custom-select" >
2024-05-22 05:58:12 +00:00
{{ range $key, $value := .enginesNames }} {{ if eq $.Engine $key }}Translate
with: < a href = "#" class = "selected-option" > {{$value}}< / a > {{ end }} {{ end }}
2023-09-10 11:57:22 +00:00
< ul class = "options" >
2024-05-22 05:58:12 +00:00
{{ range $key, $value := .enginesNames }}
2023-09-11 02:15:52 +00:00
< a href = "/?engine={{$key}}" >
< li > {{$value}}< / li >
2023-09-10 13:41:45 +00:00
< / a >
2024-05-22 05:58:12 +00:00
{{ end }}
2023-09-10 11:57:22 +00:00
< / ul >
< / div >
2024-05-22 05:58:12 +00:00
< br / >
< br / >
2024-08-27 17:06:11 +00:00
{{ if eq .Engine "some" }}
< form action = "/" method = "get" id = "enginesForm" >
< select name = "engines" aria-label = "Engines you want to use" id = "engines" multiple >
{{ range $key, $value := .enginesNames}}
< option value = "{{ $key }}" { { contains $ . SomeEngines $ key " selected " } } >
{{ $value }}
< / option >
{{end}}
< / select >
< button type = "submit" > Select Engines< / button >
{{ end }}
2024-05-22 05:58:12 +00:00
< form action = "/" method = "post" id = "translation-form" >
2023-10-05 13:29:22 +00:00
<!-- This hidden input is so that the engine gets sent in the request even though its not declared here -->
2023-09-10 11:57:22 +00:00
< input name = "engine" value = "{{.Engine}}" type = "hidden" / >
2024-08-27 17:06:11 +00:00
{{ if eq .Engine "some" }}
< input name = "engines" value = "{{.EnginesNamesStr}}" type = "hidden" / >
{{ end }}
2023-11-29 15:28:26 +00:00
< div class = "wrap languages center-area" >
2023-09-10 11:57:22 +00:00
< div class = "language" >
2023-09-10 14:52:51 +00:00
< select name = "from" aria-label = "Source language" id = "sourceLanguage" >
2024-06-27 14:33:04 +00:00
{{ range $key, $value := .SourceLanguages }} {{ if eq $.From "" }}
2024-06-27 15:08:29 +00:00
< option value = "{{ .Id }}" { { if eq . Id $ . defaultLang } } selected { { end } } >
2023-09-10 11:57:22 +00:00
{{ .Name }}
< / option >
2024-05-22 05:58:12 +00:00
{{ else }}
2024-06-27 15:08:29 +00:00
< option value = "{{ .Id }}" { { if eq $ . From . Id } } selected { { end } } >
2023-09-10 13:41:45 +00:00
{{ .Name }}
< / option >
2024-05-22 05:58:12 +00:00
{{ end }} {{ end }}
2023-09-10 11:57:22 +00:00
< / select >
< / div >
< div class = "switch_languages" >
2024-05-22 05:58:12 +00:00
< button id = "switchbutton"
aria-label="Switch languages"
formaction="/switchlanguages?engine={{ .Engine }}"
type="submit">
2023-09-20 10:34:20 +00:00
<!-- https://icon - sets.iconify.design/ci/arrow - left - right/ -->
2024-05-22 05:58:12 +00:00
< svg xmlns = "http://www.w3.org/2000/svg"
width="24"
height="24"
viewBox="0 0 24 24">
< path fill = "none" stroke = "currentColor" stroke-linecap = "round" stroke-linejoin = "round" stroke-width = "2" d = "m16 13l3 3m0 0l-3 3m3-3H5m3-5L5 8m0 0l3-3M5 8h14" / >
2023-09-20 10:34:20 +00:00
< / svg >
2023-09-10 11:57:22 +00:00
< / button >
< / div >
< div class = "language" >
2023-09-10 14:52:51 +00:00
< select name = "to" aria-label = "Target language" id = "targetLanguage" >
2024-05-22 05:58:12 +00:00
{{ range $key, $value := .TargetLanguages }} {{ if $.To }}
< option value = "{{ .Id }}" { { if eq $ . To . Id } } selected { { end } } >
2023-09-10 11:57:22 +00:00
{{ .Name }}
< / option >
2024-05-22 05:58:12 +00:00
{{ else }}
< option value = "{{ .Id }}" { { if eq . Id $ . defaultLangTarget } } selected { { end } } >
2023-10-20 10:19:51 +00:00
{{ .Name }}
< / option >
2024-05-22 05:58:12 +00:00
{{ end }} {{ end }}
2023-09-10 11:57:22 +00:00
< / select >
< / div >
< / div >
2023-11-29 15:28:26 +00:00
< div class = "center-area2 item-wrapper" >
Source Text:
2023-09-20 10:34:20 +00:00
< textarea autofocus class = "item" id = "input" name = "text" dir = "auto" placeholder = "Enter Text Here" >
{{ .OriginalText }}< / textarea >
2024-05-22 05:58:12 +00:00
{{ if .Translation.SourceTransliteration }}
< br >
Transliteration: {{ newlinetobr .Translation.SourceTransliteration }}{{ end }}
{{ if .TtsFrom }}
2023-11-29 15:28:26 +00:00
< br >
2023-09-20 10:34:20 +00:00
< audio controls >
< source type = "audio/mpeg" src = "{{ .TtsFrom }}" / >
< / audio >
2024-05-22 05:58:12 +00:00
{{ end }}
2023-11-29 15:28:26 +00:00
< br >
2023-09-20 10:34:20 +00:00
< / div >
2024-08-27 17:06:11 +00:00
{{ if .TranslateMany }}
{{ range $key, $value := .TranslateMany }}
2023-10-13 13:00:41 +00:00
< div class = "item-wrapper center-area2" >
2023-09-20 10:34:20 +00:00
Engine: {{.Engine}}
2023-10-13 07:03:57 +00:00
< textarea class = "translation item" dir = "auto" placeholder = "Translation" id = "output" readonly >
2023-09-20 10:34:20 +00:00
{{.OutputText}}< / textarea >
2024-05-22 05:58:12 +00:00
{{ if .AutoDetect }}
< br >
Detected Language: {{.AutoDetect}}{{ end }}
{{ if .TargetTransliteration }}
< br >
Transliteration: {{ newlinetobr .TargetTransliteration }}{{ end }}
{{ if $.TtsTo }}
2023-11-29 15:28:26 +00:00
< br >
2023-09-20 10:34:20 +00:00
< audio controls >
< source type = "audio/mpeg" src = "{{ $.TtsTo }}" / >
< / audio >
2024-05-22 05:58:12 +00:00
{{ end }}
2023-11-29 15:28:26 +00:00
< br >
2023-09-10 11:57:22 +00:00
< / div >
2024-05-22 05:58:12 +00:00
{{ end }}
{{ else }} {{ if .TranslationExists }}
2023-10-13 13:00:41 +00:00
< div class = "item-wrapper center-area2" >
2023-10-13 07:03:57 +00:00
< textarea class = "translation item" dir = "auto" placeholder = "Translation" id = "output" readonly >
2023-09-20 10:34:20 +00:00
{{.Translation.OutputText}}< / textarea >
2024-05-22 05:58:12 +00:00
{{ if .Translation.AutoDetect }}
< br >
Detected Language: {{.Translation.AutoDetect}}{{ end }}
{{ if .Translation.TargetTransliteration }}
< br >
Transliteration: {{ newlinetobr .Translation.TargetTransliteration }}{{ end }}
{{ if .TtsTo }}
2023-11-29 15:28:26 +00:00
< br >
2023-09-20 10:34:20 +00:00
< audio controls >
< source type = "audio/mpeg" src = "{{ .TtsTo }}" / >
< / audio >
2024-05-22 05:58:12 +00:00
{{ end }}
2023-11-29 15:28:26 +00:00
< br >
2024-05-22 05:58:12 +00:00
{{ end }}
{{ end }}
< div style = "display:flex;
justify-content:space-around;
align-items:center">
{{ if .TranslationExists }}
< button class = "wrap" type = "button" onclick = "copyToClipboard()" > Copy the translation< / button >
{{ end }}
{{ if and .Engine .From .To .OriginalText }}
< p >
< a id = "url"
class="button"
onclick="copyLinkToClipboard(event)"
href="/?engine={{.Engine}}& from={{.From}}& to={{.To}}& text={{.OriginalText}}">Copy translation link< / a >
< / p >
{{ end }}
{{ if .TranslationExists }}
< button class = "wrap" type = "submit" > Translate!< / button >
{{ else }}
< button class = "wrap"
style="margin-left:auto;
position:relative;
left:-10%;
margin-top: 1%"
type="submit">Translate!< / button >
{{ end }}
2023-11-29 15:28:26 +00:00
< / div >
2024-05-22 05:58:12 +00:00
< / div >
2024-05-22 12:06:52 +00:00
{{ if eq .Engine "yandex" }}
{{ template "yandex_extras" . }}
{{ end }}
2024-05-23 07:15:47 +00:00
{{ if eq .Engine "reverso" }}
{{ template "reverso_extras" . }}
{{ end }}
2024-05-27 10:12:20 +00:00
{{ if eq .Engine "google" }}
{{ template "google_extras" . }}
{{ end }}
2023-09-10 11:57:22 +00:00
< / form >
2023-09-10 13:41:45 +00:00
< script >
// @license magnet:?xt=urn:btih:0b31508aeb0634b347b8270c7bee4d411b5d4109& dn=agpl-3.0.txt AGPL-3.0
// this code submits the translation form when pressing Ctrl/Meta+Enter while focussed on the input text field
document
.getElementById("input")
.addEventListener("keydown", function (event) {
if (event.keyCode === 13 & & (event.metaKey || event.ctrlKey)) {
document.getElementById("translation-form").submit();
}
});
2023-09-20 10:34:20 +00:00
// This code makes the select language menu searchable if js is enabled
2023-09-10 14:52:51 +00:00
var options = { searchable: true };
NiceSelect.bind(document.getElementById("targetLanguage"), options);
NiceSelect.bind(document.getElementById("sourceLanguage"), options);
2023-10-13 07:03:57 +00:00
// This function allows to copy the translated text to the clipboard
function copyToClipboard() {
var copyText = document.getElementById("output");
copyText.select();
copyText.setSelectionRange(0, 99999); // This is for mobile devices.
document.execCommand("copy");
}
2024-04-04 05:41:35 +00:00
function copyLinkToClipboard(event) {
// Get the text of the link based on the id.
var copyText = document.getElementById("url");
var text = copyText.href;
// Create an input element, set the value to the link, append it to the body, select the text, copy it to the clipboard, then remove the input element.
// This is the only way to copy text to the clipboard in a browser, you could consider this a hack but yeah... it works.
var input = document.createElement("input");
input.value = text;
document.body.appendChild(input);
input.select();
document.execCommand("copy");
document.body.removeChild(input);
event.preventDefault();
// If failed to copy to clipboard, alert the user
if (!document.execCommand("copy")) {
alert("Failed to copy the link to the clipboard");
}
// Otherwise, let the user know it successfully copied with a small css animation by switching to green bg then back to the original color.
else {
copyText.style.backgroundColor = "#4CAF50";
// Change the text to "Copied!" for a second"
copyText.innerText = "Copied!";
setTimeout(function () {
copyText.style.backgroundColor = "#f57c00";
// Change the text back to "Copy translation link" after a second
copyText.innerText = "Copy translation link";
}, 1000);
}
}
2023-09-10 13:41:45 +00:00
< / script >
2023-06-24 18:40:57 +00:00
< / main >
2024-05-22 05:58:12 +00:00
{{ template "footer" . }}