Merge branch 'master' into master-ghc8107
This commit is contained in:
commit
0c096e2c89
@ -770,7 +770,7 @@ final class GMember: ObservableObject, Identifiable {
|
||||
}
|
||||
|
||||
struct RemoteCtrlSession {
|
||||
var ctrlAppInfo: CtrlAppInfo
|
||||
var ctrlAppInfo: CtrlAppInfo?
|
||||
var appVersion: String
|
||||
var sessionState: UIRemoteCtrlSessionState
|
||||
|
||||
@ -782,6 +782,10 @@ struct RemoteCtrlSession {
|
||||
if case .connected = sessionState { true } else { false }
|
||||
}
|
||||
|
||||
var discovery: Bool {
|
||||
if case .searching = sessionState { true } else { false }
|
||||
}
|
||||
|
||||
var sessionCode: String? {
|
||||
switch sessionState {
|
||||
case let .pendingConfirmation(_, sessionCode): sessionCode
|
||||
@ -793,6 +797,8 @@ struct RemoteCtrlSession {
|
||||
|
||||
enum UIRemoteCtrlSessionState {
|
||||
case starting
|
||||
case searching
|
||||
case found(remoteCtrl: RemoteCtrlInfo, compatible: Bool)
|
||||
case connecting(remoteCtrl_: RemoteCtrlInfo?)
|
||||
case pendingConfirmation(remoteCtrl_: RemoteCtrlInfo?, sessionCode: String)
|
||||
case connected(remoteCtrl: RemoteCtrlInfo, sessionCode: String)
|
||||
|
@ -919,8 +919,10 @@ func findKnownRemoteCtrl() async throws {
|
||||
try await sendCommandOkResp(.findKnownRemoteCtrl)
|
||||
}
|
||||
|
||||
func confirmRemoteCtrl(_ rcId: Int64) async throws {
|
||||
try await sendCommandOkResp(.confirmRemoteCtrl(remoteCtrlId: rcId))
|
||||
func confirmRemoteCtrl(_ rcId: Int64) async throws -> (RemoteCtrlInfo?, CtrlAppInfo, String) {
|
||||
let r = await chatSendCmd(.confirmRemoteCtrl(remoteCtrlId: rcId))
|
||||
if case let .remoteCtrlConnecting(rc_, ctrlAppInfo, v) = r { return (rc_, ctrlAppInfo, v) }
|
||||
throw r
|
||||
}
|
||||
|
||||
func verifyRemoteCtrlSession(_ sessCode: String) async throws -> RemoteCtrlInfo {
|
||||
@ -1714,9 +1716,17 @@ func processReceivedMsg(_ res: ChatResponse) async {
|
||||
await MainActor.run {
|
||||
m.updateGroupMemberConnectionStats(groupInfo, member, ratchetSyncProgress.connectionStats)
|
||||
}
|
||||
case let .remoteCtrlFound(remoteCtrl):
|
||||
// TODO multicast
|
||||
logger.debug("\(String(describing: remoteCtrl))")
|
||||
case let .remoteCtrlFound(remoteCtrl, ctrlAppInfo_, appVersion, compatible):
|
||||
await MainActor.run {
|
||||
if let sess = m.remoteCtrlSession, case .searching = sess.sessionState {
|
||||
let state = UIRemoteCtrlSessionState.found(remoteCtrl: remoteCtrl, compatible: compatible)
|
||||
m.remoteCtrlSession = RemoteCtrlSession(
|
||||
ctrlAppInfo: ctrlAppInfo_,
|
||||
appVersion: appVersion,
|
||||
sessionState: state
|
||||
)
|
||||
}
|
||||
}
|
||||
case let .remoteCtrlSessionCode(remoteCtrl_, sessionCode):
|
||||
await MainActor.run {
|
||||
let state = UIRemoteCtrlSessionState.pendingConfirmation(remoteCtrl_: remoteCtrl_, sessionCode: sessionCode)
|
||||
@ -1731,8 +1741,13 @@ func processReceivedMsg(_ res: ChatResponse) async {
|
||||
case .remoteCtrlStopped:
|
||||
// This delay is needed to cancel the session that fails on network failure,
|
||||
// e.g. when user did not grant permission to access local network yet.
|
||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) {
|
||||
switchToLocalSession()
|
||||
if let sess = m.remoteCtrlSession {
|
||||
m.remoteCtrlSession = nil
|
||||
if case .connected = sess.sessionState {
|
||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) {
|
||||
switchToLocalSession()
|
||||
}
|
||||
}
|
||||
}
|
||||
default:
|
||||
logger.debug("unsupported event: \(res.responseType)")
|
||||
|
@ -16,12 +16,19 @@ struct ConnectDesktopView: View {
|
||||
var viaSettings = false
|
||||
@AppStorage(DEFAULT_DEVICE_NAME_FOR_REMOTE_ACCESS) private var deviceName = UIDevice.current.name
|
||||
@AppStorage(DEFAULT_CONFIRM_REMOTE_SESSIONS) private var confirmRemoteSessions = false
|
||||
@AppStorage(DEFAULT_CONNECT_REMOTE_VIA_MULTICAST) private var connectRemoteViaMulticast = false
|
||||
@AppStorage(DEFAULT_OFFER_REMOTE_MULTICAST) private var offerRemoteMulticast = true
|
||||
@AppStorage(DEFAULT_CONNECT_REMOTE_VIA_MULTICAST) private var connectRemoteViaMulticast = true
|
||||
@AppStorage(DEFAULT_CONNECT_REMOTE_VIA_MULTICAST_AUTO) private var connectRemoteViaMulticastAuto = true
|
||||
@AppStorage(DEFAULT_DEVELOPER_TOOLS) private var developerTools = false
|
||||
@State private var sessionAddress: String = ""
|
||||
@State private var remoteCtrls: [RemoteCtrlInfo] = []
|
||||
@State private var alert: ConnectDesktopAlert?
|
||||
@State private var showConnectScreen = true
|
||||
@State private var showQRCodeScanner = true
|
||||
@State private var firstAppearance = true
|
||||
|
||||
private var useMulticast: Bool {
|
||||
connectRemoteViaMulticast && !remoteCtrls.isEmpty
|
||||
}
|
||||
|
||||
private enum ConnectDesktopAlert: Identifiable {
|
||||
case unlinkDesktop(rc: RemoteCtrlInfo)
|
||||
@ -67,9 +74,14 @@ struct ConnectDesktopView: View {
|
||||
|
||||
var viewBody: some View {
|
||||
Group {
|
||||
if let session = m.remoteCtrlSession {
|
||||
let discovery = m.remoteCtrlSession?.discovery
|
||||
if discovery == true || (discovery == nil && !showConnectScreen) {
|
||||
searchingDesktopView()
|
||||
} else if let session = m.remoteCtrlSession {
|
||||
switch session.sessionState {
|
||||
case .starting: connectingDesktopView(session, nil)
|
||||
case .searching: searchingDesktopView()
|
||||
case let .found(rc, compatible): foundDesktopView(session, rc, compatible)
|
||||
case let .connecting(rc_): connectingDesktopView(session, rc_)
|
||||
case let .pendingConfirmation(rc_, sessCode):
|
||||
if confirmRemoteSessions || rc_ == nil {
|
||||
@ -81,16 +93,35 @@ struct ConnectDesktopView: View {
|
||||
}
|
||||
case let .connected(rc, _): activeSessionView(session, rc)
|
||||
}
|
||||
} else {
|
||||
// The hack below prevents camera freezing when exiting linked devices view.
|
||||
// Using showQRCodeScanner inside connectDesktopView or passing it as parameter still results in freezing.
|
||||
} else if showQRCodeScanner || firstAppearance {
|
||||
connectDesktopView()
|
||||
} else {
|
||||
connectDesktopView(showScanner: false)
|
||||
}
|
||||
}
|
||||
.onAppear {
|
||||
setDeviceName(deviceName)
|
||||
updateRemoteCtrls()
|
||||
showConnectScreen = !useMulticast
|
||||
if m.remoteCtrlSession != nil {
|
||||
disconnectDesktop()
|
||||
} else if useMulticast {
|
||||
findKnownDesktop()
|
||||
}
|
||||
// The hack below prevents camera freezing when exiting linked devices view.
|
||||
// `firstAppearance` prevents camera flicker when the view first opens.
|
||||
// moving `showQRCodeScanner = false` to `onDisappear` (to avoid `firstAppearance`) does not prevent freeze.
|
||||
showQRCodeScanner = false
|
||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.25) {
|
||||
firstAppearance = false
|
||||
showQRCodeScanner = true
|
||||
}
|
||||
}
|
||||
.onDisappear {
|
||||
if m.remoteCtrlSession != nil {
|
||||
showConnectScreen = false
|
||||
disconnectDesktop()
|
||||
}
|
||||
}
|
||||
@ -134,12 +165,14 @@ struct ConnectDesktopView: View {
|
||||
.interactiveDismissDisabled(m.activeRemoteCtrl)
|
||||
}
|
||||
|
||||
private func connectDesktopView() -> some View {
|
||||
private func connectDesktopView(showScanner: Bool = true) -> some View {
|
||||
List {
|
||||
Section("This device name") {
|
||||
devicesView()
|
||||
}
|
||||
scanDesctopAddressView()
|
||||
if showScanner {
|
||||
scanDesctopAddressView()
|
||||
}
|
||||
if developerTools {
|
||||
desktopAddressView()
|
||||
}
|
||||
@ -167,6 +200,56 @@ struct ConnectDesktopView: View {
|
||||
.navigationTitle("Connecting to desktop")
|
||||
}
|
||||
|
||||
private func searchingDesktopView() -> some View {
|
||||
List {
|
||||
Section("This device name") {
|
||||
devicesView()
|
||||
}
|
||||
Section("Found desktop") {
|
||||
Text("Waiting for desktop...").italic()
|
||||
Button {
|
||||
disconnectDesktop(.dismiss)
|
||||
} label: {
|
||||
Label("Scan QR code", systemImage: "qrcode")
|
||||
}
|
||||
}
|
||||
}
|
||||
.navigationTitle("Connecting to desktop")
|
||||
}
|
||||
|
||||
@ViewBuilder private func foundDesktopView(_ session: RemoteCtrlSession, _ rc: RemoteCtrlInfo, _ compatible: Bool) -> some View {
|
||||
let v = List {
|
||||
Section("This device name") {
|
||||
devicesView()
|
||||
}
|
||||
Section("Found desktop") {
|
||||
ctrlDeviceNameText(session, rc)
|
||||
ctrlDeviceVersionText(session)
|
||||
if !compatible {
|
||||
Text("Not compatible!").foregroundColor(.red)
|
||||
} else if !connectRemoteViaMulticastAuto {
|
||||
Button {
|
||||
confirmKnownDesktop(rc)
|
||||
} label: {
|
||||
Label("Connect", systemImage: "checkmark")
|
||||
}
|
||||
}
|
||||
}
|
||||
if !compatible && !connectRemoteViaMulticastAuto {
|
||||
Section {
|
||||
disconnectButton("Cancel")
|
||||
}
|
||||
}
|
||||
}
|
||||
.navigationTitle("Found desktop")
|
||||
|
||||
if compatible && connectRemoteViaMulticastAuto {
|
||||
v.onAppear { confirmKnownDesktop(rc) }
|
||||
} else {
|
||||
v
|
||||
}
|
||||
}
|
||||
|
||||
private func verifySessionView(_ session: RemoteCtrlSession, _ rc: RemoteCtrlInfo?, _ sessCode: String) -> some View {
|
||||
List {
|
||||
Section("Connected to desktop") {
|
||||
@ -191,7 +274,7 @@ struct ConnectDesktopView: View {
|
||||
}
|
||||
|
||||
private func ctrlDeviceNameText(_ session: RemoteCtrlSession, _ rc: RemoteCtrlInfo?) -> Text {
|
||||
var t = Text(rc?.deviceViewName ?? session.ctrlAppInfo.deviceName)
|
||||
var t = Text(rc?.deviceViewName ?? session.ctrlAppInfo?.deviceName ?? "")
|
||||
if (rc == nil) {
|
||||
t = t + Text(" ") + Text("(new)").italic()
|
||||
}
|
||||
@ -199,8 +282,8 @@ struct ConnectDesktopView: View {
|
||||
}
|
||||
|
||||
private func ctrlDeviceVersionText(_ session: RemoteCtrlSession) -> Text {
|
||||
let v = session.ctrlAppInfo.appVersionRange.maxVersion
|
||||
var t = Text("v\(v)")
|
||||
let v = session.ctrlAppInfo?.appVersionRange.maxVersion
|
||||
var t = Text("v\(v ?? "")")
|
||||
if v != session.appVersion {
|
||||
t = t + Text(" ") + Text("(this device v\(session.appVersion))").italic()
|
||||
}
|
||||
@ -301,7 +384,10 @@ struct ConnectDesktopView: View {
|
||||
|
||||
Section("Linked desktop options") {
|
||||
Toggle("Verify connections", isOn: $confirmRemoteSessions)
|
||||
Toggle("Discover on network", isOn: $connectRemoteViaMulticast).disabled(true)
|
||||
Toggle("Discover via local network", isOn: $connectRemoteViaMulticast)
|
||||
if connectRemoteViaMulticast {
|
||||
Toggle("Connect automatically", isOn: $connectRemoteViaMulticastAuto)
|
||||
}
|
||||
}
|
||||
}
|
||||
.navigationTitle("Linked desktops")
|
||||
@ -335,10 +421,42 @@ struct ConnectDesktopView: View {
|
||||
}
|
||||
}
|
||||
|
||||
private func connectDesktopAddress(_ addr: String) {
|
||||
private func findKnownDesktop() {
|
||||
Task {
|
||||
do {
|
||||
let (rc_, ctrlAppInfo, v) = try await connectRemoteCtrl(desktopAddress: addr)
|
||||
try await findKnownRemoteCtrl()
|
||||
await MainActor.run {
|
||||
m.remoteCtrlSession = RemoteCtrlSession(
|
||||
ctrlAppInfo: nil,
|
||||
appVersion: "",
|
||||
sessionState: .searching
|
||||
)
|
||||
showConnectScreen = true
|
||||
}
|
||||
} catch let e {
|
||||
await MainActor.run {
|
||||
errorAlert(e)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private func confirmKnownDesktop(_ rc: RemoteCtrlInfo) {
|
||||
connectDesktop_ {
|
||||
try await confirmRemoteCtrl(rc.remoteCtrlId)
|
||||
}
|
||||
}
|
||||
|
||||
private func connectDesktopAddress(_ addr: String) {
|
||||
connectDesktop_ {
|
||||
try await connectRemoteCtrl(desktopAddress: addr)
|
||||
}
|
||||
}
|
||||
|
||||
private func connectDesktop_(_ connect: @escaping () async throws -> (RemoteCtrlInfo?, CtrlAppInfo, String)) {
|
||||
Task {
|
||||
do {
|
||||
let (rc_, ctrlAppInfo, v) = try await connect()
|
||||
await MainActor.run {
|
||||
sessionAddress = ""
|
||||
m.remoteCtrlSession = RemoteCtrlSession(
|
||||
@ -380,11 +498,11 @@ struct ConnectDesktopView: View {
|
||||
}
|
||||
}
|
||||
|
||||
private func disconnectButton() -> some View {
|
||||
private func disconnectButton(_ label: LocalizedStringKey = "Disconnect") -> some View {
|
||||
Button {
|
||||
disconnectDesktop(.dismiss)
|
||||
} label: {
|
||||
Label("Disconnect", systemImage: "multiply")
|
||||
Label(label, systemImage: "multiply")
|
||||
}
|
||||
}
|
||||
|
||||
@ -393,7 +511,11 @@ struct ConnectDesktopView: View {
|
||||
do {
|
||||
try await stopRemoteCtrl()
|
||||
await MainActor.run {
|
||||
switchToLocalSession()
|
||||
if case .connected = m.remoteCtrlSession?.sessionState {
|
||||
switchToLocalSession()
|
||||
} else {
|
||||
m.remoteCtrlSession = nil
|
||||
}
|
||||
switch action {
|
||||
case .back: dismiss()
|
||||
case .dismiss: dismiss()
|
||||
|
@ -56,7 +56,7 @@ let DEFAULT_SHOW_UNREAD_AND_FAVORITES = "showUnreadAndFavorites"
|
||||
let DEFAULT_DEVICE_NAME_FOR_REMOTE_ACCESS = "deviceNameForRemoteAccess"
|
||||
let DEFAULT_CONFIRM_REMOTE_SESSIONS = "confirmRemoteSessions"
|
||||
let DEFAULT_CONNECT_REMOTE_VIA_MULTICAST = "connectRemoteViaMulticast"
|
||||
let DEFAULT_OFFER_REMOTE_MULTICAST = "offerRemoteMulticast"
|
||||
let DEFAULT_CONNECT_REMOTE_VIA_MULTICAST_AUTO = "connectRemoteViaMulticastAuto"
|
||||
|
||||
let appDefaults: [String: Any] = [
|
||||
DEFAULT_SHOW_LA_NOTICE: false,
|
||||
@ -91,8 +91,8 @@ let appDefaults: [String: Any] = [
|
||||
DEFAULT_CUSTOM_DISAPPEARING_MESSAGE_TIME: 300,
|
||||
DEFAULT_SHOW_UNREAD_AND_FAVORITES: false,
|
||||
DEFAULT_CONFIRM_REMOTE_SESSIONS: false,
|
||||
DEFAULT_CONNECT_REMOTE_VIA_MULTICAST: false,
|
||||
DEFAULT_OFFER_REMOTE_MULTICAST: true
|
||||
DEFAULT_CONNECT_REMOTE_VIA_MULTICAST: true,
|
||||
DEFAULT_CONNECT_REMOTE_VIA_MULTICAST_AUTO: true,
|
||||
]
|
||||
|
||||
enum SimpleXLinkMode: String, Identifiable {
|
||||
|
@ -1172,6 +1172,10 @@
|
||||
<target>Свързване</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Свързване инкогнито</target>
|
||||
@ -1862,8 +1866,8 @@ This cannot be undone!</source>
|
||||
<target>Открийте и се присъединете към групи</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2499,6 +2503,10 @@ This cannot be undone!</source>
|
||||
<target>За конзолата</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Френски интерфейс</target>
|
||||
@ -3449,6 +3457,10 @@ This is your link for group %@!</source>
|
||||
<target>Няма получени или изпратени файлове</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Известия</target>
|
||||
@ -5396,6 +5408,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>Гласово съобщение…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Изчаква се получаването на файла</target>
|
||||
@ -5926,6 +5942,10 @@ SimpleX сървърите не могат да видят вашия профи
|
||||
<target>аудио разговор (не е e2e криптиран)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>лошо ID на съобщението</target>
|
||||
|
@ -1172,6 +1172,10 @@
|
||||
<target>Připojit</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Spojit se inkognito</target>
|
||||
@ -1862,8 +1866,8 @@ This cannot be undone!</source>
|
||||
<target>Objevte a připojte skupiny</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2499,6 +2503,10 @@ This cannot be undone!</source>
|
||||
<target>Pro konzoli</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Francouzské rozhraní</target>
|
||||
@ -3449,6 +3457,10 @@ This is your link for group %@!</source>
|
||||
<target>Žádné přijaté ani odeslané soubory</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Oznámení</target>
|
||||
@ -5396,6 +5408,10 @@ Chcete-li se připojit, požádejte svůj kontakt o vytvoření dalšího odkazu
|
||||
<target>Hlasová zpráva…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Čekání na soubor</target>
|
||||
@ -5926,6 +5942,10 @@ Servery SimpleX nevidí váš profil.</target>
|
||||
<target>zvukový hovor (nešifrovaný e2e)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>špatné ID zprávy</target>
|
||||
|
@ -299,10 +299,12 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="(new)" xml:space="preserve">
|
||||
<source>(new)</source>
|
||||
<target>(Neu)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="(this device v%@)" xml:space="preserve">
|
||||
<source>(this device v%@)</source>
|
||||
<target>(Dieses Gerät hat v%@)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id=")" xml:space="preserve">
|
||||
@ -397,6 +399,9 @@
|
||||
<source>- optionally notify deleted contacts.
|
||||
- profile names with spaces.
|
||||
- and more!</source>
|
||||
<target>- Optionale Benachrichtigung von gelöschten Kontakten.
|
||||
- Profilnamen mit Leerzeichen.
|
||||
- Und mehr!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="- voice messages up to 5 minutes. - custom time to disappear. - editing history." xml:space="preserve">
|
||||
@ -885,6 +890,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad desktop address" xml:space="preserve">
|
||||
<source>Bad desktop address</source>
|
||||
<target>Falsche Desktop-Adresse</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad message ID" xml:space="preserve">
|
||||
@ -899,6 +905,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Better groups" xml:space="preserve">
|
||||
<source>Better groups</source>
|
||||
<target>Bessere Gruppen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Better messages" xml:space="preserve">
|
||||
@ -913,6 +920,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Block group members" xml:space="preserve">
|
||||
<source>Block group members</source>
|
||||
<target>Gruppenmitglieder blockieren</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member" xml:space="preserve">
|
||||
@ -1186,6 +1194,10 @@
|
||||
<target>Verbinden</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Inkognito verbinden</target>
|
||||
@ -1193,6 +1205,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to desktop" xml:space="preserve">
|
||||
<source>Connect to desktop</source>
|
||||
<target>Mit dem Desktop verbinden</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to yourself?" xml:space="preserve">
|
||||
@ -1241,10 +1254,12 @@ Das ist Ihr eigener Einmal-Link!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected desktop" xml:space="preserve">
|
||||
<source>Connected desktop</source>
|
||||
<target>Verbundener Desktop</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected to desktop" xml:space="preserve">
|
||||
<source>Connected to desktop</source>
|
||||
<target>Mit dem Desktop verbunden</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting server…" xml:space="preserve">
|
||||
@ -1259,6 +1274,7 @@ Das ist Ihr eigener Einmal-Link!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting to desktop" xml:space="preserve">
|
||||
<source>Connecting to desktop</source>
|
||||
<target>Mit dem Desktop verbinden</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection" xml:space="preserve">
|
||||
@ -1283,6 +1299,7 @@ Das ist Ihr eigener Einmal-Link!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection terminated" xml:space="preserve">
|
||||
<source>Connection terminated</source>
|
||||
<target>Verbindung beendet</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection timeout" xml:space="preserve">
|
||||
@ -1367,6 +1384,7 @@ Das ist Ihr eigener Einmal-Link!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create a group using a random profile." xml:space="preserve">
|
||||
<source>Create a group using a random profile.</source>
|
||||
<target>Erstellen Sie eine Gruppe mit einem zufälligen Profil.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create an address to let people connect with you." xml:space="preserve">
|
||||
@ -1781,14 +1799,17 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop address" xml:space="preserve">
|
||||
<source>Desktop address</source>
|
||||
<target>Desktop-Adresse</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop app version %@ is not compatible with this app." xml:space="preserve">
|
||||
<source>Desktop app version %@ is not compatible with this app.</source>
|
||||
<target>Desktop App-Version %@ ist mit dieser App nicht kompatibel.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop devices" xml:space="preserve">
|
||||
<source>Desktop devices</source>
|
||||
<target>Desktop-Geräte</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Develop" xml:space="preserve">
|
||||
@ -1883,6 +1904,7 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Disconnect desktop?" xml:space="preserve">
|
||||
<source>Disconnect desktop?</source>
|
||||
<target>Desktop-Verbindung trennen?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover and join groups" xml:space="preserve">
|
||||
@ -1890,8 +1912,8 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
<target>Gruppen entdecken und ihnen beitreten</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2066,10 +2088,12 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation error" xml:space="preserve">
|
||||
<source>Encryption re-negotiation error</source>
|
||||
<target>Fehler bei der Neuverhandlung der Verschlüsselung</target>
|
||||
<note>message decrypt error item</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation failed." xml:space="preserve">
|
||||
<source>Encryption re-negotiation failed.</source>
|
||||
<target>Neuverhandlung der Verschlüsselung fehlgeschlagen.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter Passcode" xml:space="preserve">
|
||||
@ -2104,6 +2128,7 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter this device name…" xml:space="preserve">
|
||||
<source>Enter this device name…</source>
|
||||
<target>Geben Sie diesen Gerätenamen ein…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter welcome message…" xml:space="preserve">
|
||||
@ -2433,6 +2458,7 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Faster joining and more reliable messages." xml:space="preserve">
|
||||
<source>Faster joining and more reliable messages.</source>
|
||||
<target>Schnellerer Gruppenbeitritt und zuverlässigere Nachrichtenzustellung.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Favorite" xml:space="preserve">
|
||||
@ -2530,6 +2556,10 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
<target>Für Konsole</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Französische Bedienoberfläche</target>
|
||||
@ -2857,6 +2887,7 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito groups" xml:space="preserve">
|
||||
<source>Incognito groups</source>
|
||||
<target>Inkognito-Gruppen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito mode" xml:space="preserve">
|
||||
@ -2891,6 +2922,7 @@ Das kann nicht rückgängig gemacht werden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incompatible version" xml:space="preserve">
|
||||
<source>Incompatible version</source>
|
||||
<target>Inkompatible Version</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incorrect passcode" xml:space="preserve">
|
||||
@ -3065,6 +3097,7 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep the app open to use it from desktop" xml:space="preserve">
|
||||
<source>Keep the app open to use it from desktop</source>
|
||||
<target>Die App muss geöffnet bleiben, um sie vom Desktop aus nutzen zu können</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep your connections" xml:space="preserve">
|
||||
@ -3129,14 +3162,17 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Link mobile and desktop apps! 🔗" xml:space="preserve">
|
||||
<source>Link mobile and desktop apps! 🔗</source>
|
||||
<target>Verknüpfe Mobiltelefon- und Desktop-Apps! 🔗</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktop options" xml:space="preserve">
|
||||
<source>Linked desktop options</source>
|
||||
<target>Verknüpfte Desktop-Optionen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktops" xml:space="preserve">
|
||||
<source>Linked desktops</source>
|
||||
<target>Verknüpfte Desktops</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Live message!" xml:space="preserve">
|
||||
@ -3489,6 +3525,10 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
<target>Keine empfangenen oder gesendeten Dateien</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Benachrichtigungen</target>
|
||||
@ -3710,6 +3750,7 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste desktop address" xml:space="preserve">
|
||||
<source>Paste desktop address</source>
|
||||
<target>Desktop-Adresse einfügen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste image" xml:space="preserve">
|
||||
@ -4309,6 +4350,7 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan QR code from desktop" xml:space="preserve">
|
||||
<source>Scan QR code from desktop</source>
|
||||
<target>Den QR-Code vom Desktop scannen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan code" xml:space="preserve">
|
||||
@ -4533,6 +4575,7 @@ Das ist Ihr Link für die Gruppe %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Session code" xml:space="preserve">
|
||||
<source>Session code</source>
|
||||
<target>Sitzungscode</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Set 1 day" xml:space="preserve">
|
||||
@ -5034,6 +5077,7 @@ Dies kann passieren, wenn es einen Fehler gegeben hat oder die Verbindung kompro
|
||||
</trans-unit>
|
||||
<trans-unit id="This device name" xml:space="preserve">
|
||||
<source>This device name</source>
|
||||
<target>Dieser Gerätename</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="This group has over %lld members, delivery receipts are not sent." xml:space="preserve">
|
||||
@ -5073,6 +5117,7 @@ Dies kann passieren, wenn es einen Fehler gegeben hat oder die Verbindung kompro
|
||||
</trans-unit>
|
||||
<trans-unit id="To hide unwanted messages." xml:space="preserve">
|
||||
<source>To hide unwanted messages.</source>
|
||||
<target>Um unerwünschte Nachrichten zu verbergen.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="To make a new connection" xml:space="preserve">
|
||||
@ -5236,10 +5281,12 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink" xml:space="preserve">
|
||||
<source>Unlink</source>
|
||||
<target>Entkoppeln</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink desktop?" xml:space="preserve">
|
||||
<source>Unlink desktop?</source>
|
||||
<target>Desktop entkoppeln?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlock" xml:space="preserve">
|
||||
@ -5334,6 +5381,7 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
</trans-unit>
|
||||
<trans-unit id="Use from desktop" xml:space="preserve">
|
||||
<source>Use from desktop</source>
|
||||
<target>Vom Desktop aus nutzen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Use iOS call interface" xml:space="preserve">
|
||||
@ -5368,10 +5416,12 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify code with desktop" xml:space="preserve">
|
||||
<source>Verify code with desktop</source>
|
||||
<target>Code mit dem Desktop überprüfen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection" xml:space="preserve">
|
||||
<source>Verify connection</source>
|
||||
<target>Verbindung überprüfen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection security" xml:space="preserve">
|
||||
@ -5381,6 +5431,7 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connections" xml:space="preserve">
|
||||
<source>Verify connections</source>
|
||||
<target>Verbindungen überprüfen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify security code" xml:space="preserve">
|
||||
@ -5395,6 +5446,7 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
</trans-unit>
|
||||
<trans-unit id="Via secure quantum resistant protocol." xml:space="preserve">
|
||||
<source>Via secure quantum resistant protocol.</source>
|
||||
<target>Über ein sicheres quantenbeständiges Protokoll.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Video call" xml:space="preserve">
|
||||
@ -5447,6 +5499,10 @@ Bitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um s
|
||||
<target>Sprachnachrichten…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Warte auf Datei</target>
|
||||
@ -5992,6 +6048,10 @@ SimpleX-Server können Ihr Profil nicht einsehen.</target>
|
||||
<target>Audioanruf (nicht E2E verschlüsselt)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>Ungültige Nachrichten-ID</target>
|
||||
@ -6576,6 +6636,7 @@ SimpleX-Server können Ihr Profil nicht einsehen.</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@" xml:space="preserve">
|
||||
<source>v%@</source>
|
||||
<target>v%@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@ (%@)" xml:space="preserve">
|
||||
@ -6717,6 +6778,7 @@ SimpleX-Server können Ihr Profil nicht einsehen.</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="NSLocalNetworkUsageDescription" xml:space="preserve">
|
||||
<source>SimpleX uses local network access to allow using user chat profile via desktop app on the same network.</source>
|
||||
<target>SimpleX nutzt den lokalen Netzwerkzugriff, um die Nutzung von Benutzer-Chatprofilen über eine Desktop-App im gleichen Netzwerk zu erlauben.</target>
|
||||
<note>Privacy - Local Network Usage Description</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="NSMicrophoneUsageDescription" xml:space="preserve">
|
||||
|
@ -1194,6 +1194,11 @@
|
||||
<target>Connect</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<target>Connect automatically</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Connect incognito</target>
|
||||
@ -1908,9 +1913,9 @@ This cannot be undone!</target>
|
||||
<target>Discover and join groups</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<target>Discover on network</target>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<target>Discover via local network</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2553,6 +2558,11 @@ This cannot be undone!</target>
|
||||
<target>For console</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<target>Found desktop</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>French interface</target>
|
||||
@ -3518,6 +3528,11 @@ This is your link for group %@!</target>
|
||||
<target>No received or sent files</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<target>Not compatible!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Notifications</target>
|
||||
@ -5488,6 +5503,11 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>Voice message…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<target>Waiting for desktop...</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Waiting for file</target>
|
||||
@ -6033,6 +6053,11 @@ SimpleX servers cannot see your profile.</target>
|
||||
<target>audio call (not e2e encrypted)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<target>author</target>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>bad message ID</target>
|
||||
|
@ -1172,6 +1172,10 @@
|
||||
<target>Conectar</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Conectar incognito</target>
|
||||
@ -1862,8 +1866,8 @@ This cannot be undone!</source>
|
||||
<target>Descubre y únete a grupos</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2499,6 +2503,10 @@ This cannot be undone!</source>
|
||||
<target>Para consola</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Interfaz en francés</target>
|
||||
@ -3449,6 +3457,10 @@ This is your link for group %@!</source>
|
||||
<target>Sin archivos recibidos o enviados</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Notificaciones</target>
|
||||
@ -5397,6 +5409,10 @@ Para conectarte, pide a tu contacto que cree otro enlace de conexión y comprueb
|
||||
<target>Mensaje de voz…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Esperando archivo</target>
|
||||
@ -5927,6 +5943,10 @@ Los servidores de SimpleX no pueden ver tu perfil.</target>
|
||||
<target>llamada (sin cifrar)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>ID de mensaje erróneo</target>
|
||||
|
@ -1167,6 +1167,10 @@
|
||||
<target>Yhdistä</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Yhdistä Incognito</target>
|
||||
@ -1857,8 +1861,8 @@ This cannot be undone!</source>
|
||||
<target>Löydä ryhmiä ja liity niihin</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2491,6 +2495,10 @@ This cannot be undone!</source>
|
||||
<target>Konsoliin</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Ranskalainen käyttöliittymä</target>
|
||||
@ -3440,6 +3448,10 @@ This is your link for group %@!</source>
|
||||
<target>Ei vastaanotettuja tai lähetettyjä tiedostoja</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Ilmoitukset</target>
|
||||
@ -5383,6 +5395,10 @@ Jos haluat muodostaa yhteyden, pyydä kontaktiasi luomaan toinen yhteyslinkki ja
|
||||
<target>Ääniviesti…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Odottaa tiedostoa</target>
|
||||
@ -5913,6 +5929,10 @@ SimpleX-palvelimet eivät näe profiiliasi.</target>
|
||||
<target>äänipuhelu (ei e2e-salattu)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>virheellinen viestin tunniste</target>
|
||||
|
@ -299,10 +299,12 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="(new)" xml:space="preserve">
|
||||
<source>(new)</source>
|
||||
<target>(nouveau)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="(this device v%@)" xml:space="preserve">
|
||||
<source>(this device v%@)</source>
|
||||
<target>(cet appareil v%@)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id=")" xml:space="preserve">
|
||||
@ -397,6 +399,9 @@
|
||||
<source>- optionally notify deleted contacts.
|
||||
- profile names with spaces.
|
||||
- and more!</source>
|
||||
<target>- option pour notifier les contacts supprimés.
|
||||
- noms de profil avec espaces.
|
||||
- et plus encore !</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="- voice messages up to 5 minutes. - custom time to disappear. - editing history." xml:space="preserve">
|
||||
@ -885,6 +890,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad desktop address" xml:space="preserve">
|
||||
<source>Bad desktop address</source>
|
||||
<target>Mauvaise adresse de bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad message ID" xml:space="preserve">
|
||||
@ -899,6 +905,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Better groups" xml:space="preserve">
|
||||
<source>Better groups</source>
|
||||
<target>Des groupes plus performants</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Better messages" xml:space="preserve">
|
||||
@ -913,6 +920,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Block group members" xml:space="preserve">
|
||||
<source>Block group members</source>
|
||||
<target>Bloquer des membres d'un groupe</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member" xml:space="preserve">
|
||||
@ -1186,6 +1194,10 @@
|
||||
<target>Se connecter</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Se connecter incognito</target>
|
||||
@ -1193,6 +1205,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to desktop" xml:space="preserve">
|
||||
<source>Connect to desktop</source>
|
||||
<target>Se connecter au bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to yourself?" xml:space="preserve">
|
||||
@ -1241,10 +1254,12 @@ Il s'agit de votre propre lien unique !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected desktop" xml:space="preserve">
|
||||
<source>Connected desktop</source>
|
||||
<target>Bureau connecté</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected to desktop" xml:space="preserve">
|
||||
<source>Connected to desktop</source>
|
||||
<target>Connecté au bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting server…" xml:space="preserve">
|
||||
@ -1259,6 +1274,7 @@ Il s'agit de votre propre lien unique !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting to desktop" xml:space="preserve">
|
||||
<source>Connecting to desktop</source>
|
||||
<target>Connexion au bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection" xml:space="preserve">
|
||||
@ -1283,6 +1299,7 @@ Il s'agit de votre propre lien unique !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection terminated" xml:space="preserve">
|
||||
<source>Connection terminated</source>
|
||||
<target>Connexion terminée</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection timeout" xml:space="preserve">
|
||||
@ -1367,6 +1384,7 @@ Il s'agit de votre propre lien unique !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create a group using a random profile." xml:space="preserve">
|
||||
<source>Create a group using a random profile.</source>
|
||||
<target>Création de groupes via un profil aléatoire.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create an address to let people connect with you." xml:space="preserve">
|
||||
@ -1781,14 +1799,17 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop address" xml:space="preserve">
|
||||
<source>Desktop address</source>
|
||||
<target>Adresse de bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop app version %@ is not compatible with this app." xml:space="preserve">
|
||||
<source>Desktop app version %@ is not compatible with this app.</source>
|
||||
<target>La version de l'application de bureau %@ n'est pas compatible avec cette application.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop devices" xml:space="preserve">
|
||||
<source>Desktop devices</source>
|
||||
<target>Appareils de bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Develop" xml:space="preserve">
|
||||
@ -1883,6 +1904,7 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Disconnect desktop?" xml:space="preserve">
|
||||
<source>Disconnect desktop?</source>
|
||||
<target>Déconnecter le bureau ?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover and join groups" xml:space="preserve">
|
||||
@ -1890,8 +1912,8 @@ Cette opération ne peut être annulée !</target>
|
||||
<target>Découvrir et rejoindre des groupes</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2066,10 +2088,12 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation error" xml:space="preserve">
|
||||
<source>Encryption re-negotiation error</source>
|
||||
<target>Erreur lors de la renégociation du chiffrement</target>
|
||||
<note>message decrypt error item</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation failed." xml:space="preserve">
|
||||
<source>Encryption re-negotiation failed.</source>
|
||||
<target>La renégociation du chiffrement a échoué.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter Passcode" xml:space="preserve">
|
||||
@ -2104,6 +2128,7 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter this device name…" xml:space="preserve">
|
||||
<source>Enter this device name…</source>
|
||||
<target>Entrez le nom de l'appareil…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter welcome message…" xml:space="preserve">
|
||||
@ -2433,6 +2458,7 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Faster joining and more reliable messages." xml:space="preserve">
|
||||
<source>Faster joining and more reliable messages.</source>
|
||||
<target>Connexion plus rapide et messages plus fiables.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Favorite" xml:space="preserve">
|
||||
@ -2530,6 +2556,10 @@ Cette opération ne peut être annulée !</target>
|
||||
<target>Pour la console</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Interface en français</target>
|
||||
@ -2857,6 +2887,7 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito groups" xml:space="preserve">
|
||||
<source>Incognito groups</source>
|
||||
<target>Groupes incognito</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito mode" xml:space="preserve">
|
||||
@ -2891,6 +2922,7 @@ Cette opération ne peut être annulée !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incompatible version" xml:space="preserve">
|
||||
<source>Incompatible version</source>
|
||||
<target>Version incompatible</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incorrect passcode" xml:space="preserve">
|
||||
@ -3065,6 +3097,7 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep the app open to use it from desktop" xml:space="preserve">
|
||||
<source>Keep the app open to use it from desktop</source>
|
||||
<target>Garder l'application ouverte pour l'utiliser depuis le bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep your connections" xml:space="preserve">
|
||||
@ -3129,14 +3162,17 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Link mobile and desktop apps! 🔗" xml:space="preserve">
|
||||
<source>Link mobile and desktop apps! 🔗</source>
|
||||
<target>Liez vos applications mobiles et de bureau ! 🔗</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktop options" xml:space="preserve">
|
||||
<source>Linked desktop options</source>
|
||||
<target>Options de bureau lié</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktops" xml:space="preserve">
|
||||
<source>Linked desktops</source>
|
||||
<target>Bureaux liés</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Live message!" xml:space="preserve">
|
||||
@ -3489,6 +3525,10 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
<target>Aucun fichier reçu ou envoyé</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Notifications</target>
|
||||
@ -3710,6 +3750,7 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste desktop address" xml:space="preserve">
|
||||
<source>Paste desktop address</source>
|
||||
<target>Coller l'adresse du bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste image" xml:space="preserve">
|
||||
@ -4309,6 +4350,7 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan QR code from desktop" xml:space="preserve">
|
||||
<source>Scan QR code from desktop</source>
|
||||
<target>Scanner le code QR du bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan code" xml:space="preserve">
|
||||
@ -4533,6 +4575,7 @@ Voici votre lien pour le groupe %@ !</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Session code" xml:space="preserve">
|
||||
<source>Session code</source>
|
||||
<target>Code de session</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Set 1 day" xml:space="preserve">
|
||||
@ -5034,6 +5077,7 @@ Cela peut se produire en raison d'un bug ou lorsque la connexion est compromise.
|
||||
</trans-unit>
|
||||
<trans-unit id="This device name" xml:space="preserve">
|
||||
<source>This device name</source>
|
||||
<target>Ce nom d'appareil</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="This group has over %lld members, delivery receipts are not sent." xml:space="preserve">
|
||||
@ -5073,6 +5117,7 @@ Cela peut se produire en raison d'un bug ou lorsque la connexion est compromise.
|
||||
</trans-unit>
|
||||
<trans-unit id="To hide unwanted messages." xml:space="preserve">
|
||||
<source>To hide unwanted messages.</source>
|
||||
<target>Pour cacher les messages indésirables.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="To make a new connection" xml:space="preserve">
|
||||
@ -5236,10 +5281,12 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink" xml:space="preserve">
|
||||
<source>Unlink</source>
|
||||
<target>Délier</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink desktop?" xml:space="preserve">
|
||||
<source>Unlink desktop?</source>
|
||||
<target>Délier le bureau ?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlock" xml:space="preserve">
|
||||
@ -5334,6 +5381,7 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
</trans-unit>
|
||||
<trans-unit id="Use from desktop" xml:space="preserve">
|
||||
<source>Use from desktop</source>
|
||||
<target>Utilisation depuis le bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Use iOS call interface" xml:space="preserve">
|
||||
@ -5368,10 +5416,12 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify code with desktop" xml:space="preserve">
|
||||
<source>Verify code with desktop</source>
|
||||
<target>Vérifier le code avec le bureau</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection" xml:space="preserve">
|
||||
<source>Verify connection</source>
|
||||
<target>Vérifier la connexion</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection security" xml:space="preserve">
|
||||
@ -5381,6 +5431,7 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connections" xml:space="preserve">
|
||||
<source>Verify connections</source>
|
||||
<target>Vérifier les connexions</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify security code" xml:space="preserve">
|
||||
@ -5395,6 +5446,7 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
</trans-unit>
|
||||
<trans-unit id="Via secure quantum resistant protocol." xml:space="preserve">
|
||||
<source>Via secure quantum resistant protocol.</source>
|
||||
<target>Via un protocole sécurisé de cryptographie post-quantique.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Video call" xml:space="preserve">
|
||||
@ -5447,6 +5499,10 @@ Pour vous connecter, veuillez demander à votre contact de créer un autre lien
|
||||
<target>Message vocal…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>En attente du fichier</target>
|
||||
@ -5992,6 +6048,10 @@ Les serveurs SimpleX ne peuvent pas voir votre profil.</target>
|
||||
<target>appel audio (sans chiffrement)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>ID de message incorrecte</target>
|
||||
@ -6576,6 +6636,7 @@ Les serveurs SimpleX ne peuvent pas voir votre profil.</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@" xml:space="preserve">
|
||||
<source>v%@</source>
|
||||
<target>v%@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@ (%@)" xml:space="preserve">
|
||||
@ -6717,6 +6778,7 @@ Les serveurs SimpleX ne peuvent pas voir votre profil.</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="NSLocalNetworkUsageDescription" xml:space="preserve">
|
||||
<source>SimpleX uses local network access to allow using user chat profile via desktop app on the same network.</source>
|
||||
<target>SimpleX utilise un accès au réseau local pour permettre l'utilisation du profil de chat de l'utilisateur via l'application de bureau au sein de ce même réseau.</target>
|
||||
<note>Privacy - Local Network Usage Description</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="NSMicrophoneUsageDescription" xml:space="preserve">
|
||||
|
@ -399,6 +399,9 @@
|
||||
<source>- optionally notify deleted contacts.
|
||||
- profile names with spaces.
|
||||
- and more!</source>
|
||||
<target>- avvisa facoltativamente i contatti eliminati.
|
||||
- nomi del profilo con spazi.
|
||||
- e molto altro!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="- voice messages up to 5 minutes. - custom time to disappear. - editing history." xml:space="preserve">
|
||||
@ -902,6 +905,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Better groups" xml:space="preserve">
|
||||
<source>Better groups</source>
|
||||
<target>Gruppi migliorati</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Better messages" xml:space="preserve">
|
||||
@ -916,6 +920,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Block group members" xml:space="preserve">
|
||||
<source>Block group members</source>
|
||||
<target>Blocca i membri dei gruppi</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member" xml:space="preserve">
|
||||
@ -1189,6 +1194,10 @@
|
||||
<target>Connetti</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Connetti in incognito</target>
|
||||
@ -1375,6 +1384,7 @@ Questo è il tuo link una tantum!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create a group using a random profile." xml:space="preserve">
|
||||
<source>Create a group using a random profile.</source>
|
||||
<target>Crea un gruppo usando un profilo casuale.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create an address to let people connect with you." xml:space="preserve">
|
||||
@ -1902,9 +1912,8 @@ Non è reversibile!</target>
|
||||
<target>Scopri ed unisciti ai gruppi</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<target>Trova nella rete</target>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2449,6 +2458,7 @@ Non è reversibile!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Faster joining and more reliable messages." xml:space="preserve">
|
||||
<source>Faster joining and more reliable messages.</source>
|
||||
<target>Ingresso più veloce e messaggi più affidabili.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Favorite" xml:space="preserve">
|
||||
@ -2546,6 +2556,10 @@ Non è reversibile!</target>
|
||||
<target>Per console</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Interfaccia francese</target>
|
||||
@ -2873,6 +2887,7 @@ Non è reversibile!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito groups" xml:space="preserve">
|
||||
<source>Incognito groups</source>
|
||||
<target>Gruppi in incognito</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito mode" xml:space="preserve">
|
||||
@ -3147,6 +3162,7 @@ Questo è il tuo link per il gruppo %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Link mobile and desktop apps! 🔗" xml:space="preserve">
|
||||
<source>Link mobile and desktop apps! 🔗</source>
|
||||
<target>Collega le app mobile e desktop! 🔗</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktop options" xml:space="preserve">
|
||||
@ -3509,6 +3525,10 @@ Questo è il tuo link per il gruppo %@!</target>
|
||||
<target>Nessun file ricevuto o inviato</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Notifiche</target>
|
||||
@ -5097,6 +5117,7 @@ Può accadere a causa di qualche bug o quando la connessione è compromessa.</ta
|
||||
</trans-unit>
|
||||
<trans-unit id="To hide unwanted messages." xml:space="preserve">
|
||||
<source>To hide unwanted messages.</source>
|
||||
<target>Per nascondere messaggi indesiderati.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="To make a new connection" xml:space="preserve">
|
||||
@ -5425,6 +5446,7 @@ Per connetterti, chiedi al tuo contatto di creare un altro link di connessione e
|
||||
</trans-unit>
|
||||
<trans-unit id="Via secure quantum resistant protocol." xml:space="preserve">
|
||||
<source>Via secure quantum resistant protocol.</source>
|
||||
<target>Tramite protocollo sicuro resistente alla quantistica.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Video call" xml:space="preserve">
|
||||
@ -5477,6 +5499,10 @@ Per connetterti, chiedi al tuo contatto di creare un altro link di connessione e
|
||||
<target>Messaggio vocale…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>In attesa del file</target>
|
||||
@ -6022,6 +6048,10 @@ I server di SimpleX non possono vedere il tuo profilo.</target>
|
||||
<target>chiamata audio (non crittografata e2e)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>ID messaggio errato</target>
|
||||
|
@ -1169,6 +1169,10 @@
|
||||
<target>接続</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>シークレットモードで接続</target>
|
||||
@ -1859,8 +1863,8 @@ This cannot be undone!</source>
|
||||
<target>グループを見つけて参加する</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2494,6 +2498,10 @@ This cannot be undone!</source>
|
||||
<target>コンソール</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>フランス語UI</target>
|
||||
@ -3443,6 +3451,10 @@ This is your link for group %@!</source>
|
||||
<target>送受信済みのファイルがありません</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>通知</target>
|
||||
@ -5379,6 +5391,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>音声メッセージ…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>ファイル待ち</target>
|
||||
@ -5909,6 +5925,10 @@ SimpleX サーバーはあなたのプロファイルを参照できません。
|
||||
<target>音声通話 (エンドツーエンド暗号化なし)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>メッセージ ID が正しくありません</target>
|
||||
|
@ -399,6 +399,9 @@
|
||||
<source>- optionally notify deleted contacts.
|
||||
- profile names with spaces.
|
||||
- and more!</source>
|
||||
<target>- optioneel verwijderde contacten op de hoogte stellen.
|
||||
- profielnamen met spaties.
|
||||
- en meer!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="- voice messages up to 5 minutes. - custom time to disappear. - editing history." xml:space="preserve">
|
||||
@ -902,6 +905,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Better groups" xml:space="preserve">
|
||||
<source>Better groups</source>
|
||||
<target>Betere groepen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Better messages" xml:space="preserve">
|
||||
@ -916,6 +920,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Block group members" xml:space="preserve">
|
||||
<source>Block group members</source>
|
||||
<target>Groepsleden blokkeren</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member" xml:space="preserve">
|
||||
@ -1189,6 +1194,10 @@
|
||||
<target>Verbind</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Verbind incognito</target>
|
||||
@ -1375,6 +1384,7 @@ Dit is uw eigen eenmalige link!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create a group using a random profile." xml:space="preserve">
|
||||
<source>Create a group using a random profile.</source>
|
||||
<target>Maak een groep met een willekeurig profiel.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create an address to let people connect with you." xml:space="preserve">
|
||||
@ -1902,9 +1912,8 @@ Dit kan niet ongedaan gemaakt worden!</target>
|
||||
<target>Ontdek en sluit je aan bij groepen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<target>Ontdek via netwerk</target>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2449,6 +2458,7 @@ Dit kan niet ongedaan gemaakt worden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Faster joining and more reliable messages." xml:space="preserve">
|
||||
<source>Faster joining and more reliable messages.</source>
|
||||
<target>Snellere deelname en betrouwbaardere berichten.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Favorite" xml:space="preserve">
|
||||
@ -2546,6 +2556,10 @@ Dit kan niet ongedaan gemaakt worden!</target>
|
||||
<target>Voor console</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Franse interface</target>
|
||||
@ -2873,6 +2887,7 @@ Dit kan niet ongedaan gemaakt worden!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito groups" xml:space="preserve">
|
||||
<source>Incognito groups</source>
|
||||
<target>Incognitogroepen</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito mode" xml:space="preserve">
|
||||
@ -3147,6 +3162,7 @@ Dit is jouw link voor groep %@!</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="Link mobile and desktop apps! 🔗" xml:space="preserve">
|
||||
<source>Link mobile and desktop apps! 🔗</source>
|
||||
<target>Koppel mobiele en desktop-apps! 🔗</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktop options" xml:space="preserve">
|
||||
@ -3509,6 +3525,10 @@ Dit is jouw link voor groep %@!</target>
|
||||
<target>Geen ontvangen of verzonden bestanden</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Meldingen</target>
|
||||
@ -5097,6 +5117,7 @@ Het kan gebeuren vanwege een bug of wanneer de verbinding is aangetast.</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="To hide unwanted messages." xml:space="preserve">
|
||||
<source>To hide unwanted messages.</source>
|
||||
<target>Om ongewenste berichten te verbergen.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="To make a new connection" xml:space="preserve">
|
||||
@ -5425,6 +5446,7 @@ Om verbinding te maken, vraagt u uw contact om een andere verbinding link te mak
|
||||
</trans-unit>
|
||||
<trans-unit id="Via secure quantum resistant protocol." xml:space="preserve">
|
||||
<source>Via secure quantum resistant protocol.</source>
|
||||
<target>Via een beveiligd kwantumbestendig protocol.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Video call" xml:space="preserve">
|
||||
@ -5477,6 +5499,10 @@ Om verbinding te maken, vraagt u uw contact om een andere verbinding link te mak
|
||||
<target>Spraakbericht…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Wachten op bestand</target>
|
||||
@ -6022,6 +6048,10 @@ SimpleX servers kunnen uw profiel niet zien.</target>
|
||||
<target>audio oproep (niet e2e versleuteld)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>Onjuiste bericht-ID</target>
|
||||
|
@ -1186,6 +1186,10 @@
|
||||
<target>Połącz</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Połącz incognito</target>
|
||||
@ -1890,8 +1894,8 @@ To nie może być cofnięte!</target>
|
||||
<target>Odkrywaj i dołączaj do grup</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2530,6 +2534,10 @@ To nie może być cofnięte!</target>
|
||||
<target>Dla konsoli</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Francuski interfejs</target>
|
||||
@ -3489,6 +3497,10 @@ To jest twój link do grupy %@!</target>
|
||||
<target>Brak odebranych lub wysłanych plików</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Powiadomienia</target>
|
||||
@ -5447,6 +5459,10 @@ Aby się połączyć, poproś Twój kontakt o utworzenie kolejnego linku połąc
|
||||
<target>Wiadomość głosowa…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Oczekiwanie na plik</target>
|
||||
@ -5992,6 +6008,10 @@ Serwery SimpleX nie mogą zobaczyć Twojego profilu.</target>
|
||||
<target>połączenie audio (nie szyfrowane e2e)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>zły identyfikator wiadomości</target>
|
||||
|
@ -89,6 +89,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="%@ and %@" xml:space="preserve">
|
||||
<source>%@ and %@</source>
|
||||
<target>%@ и %@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%@ and %@ connected" xml:space="preserve">
|
||||
@ -103,6 +104,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="%@ connected" xml:space="preserve">
|
||||
<source>%@ connected</source>
|
||||
<target>%@ соединен(а)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%@ is connected!" xml:space="preserve">
|
||||
@ -132,6 +134,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="%@, %@ and %lld members" xml:space="preserve">
|
||||
<source>%@, %@ and %lld members</source>
|
||||
<target>%@, %@ и %lld членов группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%@, %@ and %lld other members connected" xml:space="preserve">
|
||||
@ -201,6 +204,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld group events" xml:space="preserve">
|
||||
<source>%lld group events</source>
|
||||
<target>%lld событий</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld members" xml:space="preserve">
|
||||
@ -210,14 +214,17 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld messages blocked" xml:space="preserve">
|
||||
<source>%lld messages blocked</source>
|
||||
<target>%lld сообщений заблокировано</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld messages marked deleted" xml:space="preserve">
|
||||
<source>%lld messages marked deleted</source>
|
||||
<target>%lld сообщений помечено удалёнными</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld messages moderated by %@" xml:space="preserve">
|
||||
<source>%lld messages moderated by %@</source>
|
||||
<target>%lld сообщений модерировано членом %@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="%lld minutes" xml:space="preserve">
|
||||
@ -292,10 +299,12 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="(new)" xml:space="preserve">
|
||||
<source>(new)</source>
|
||||
<target>(новое)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="(this device v%@)" xml:space="preserve">
|
||||
<source>(this device v%@)</source>
|
||||
<target>(это устройство v%@)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id=")" xml:space="preserve">
|
||||
@ -390,6 +399,9 @@
|
||||
<source>- optionally notify deleted contacts.
|
||||
- profile names with spaces.
|
||||
- and more!</source>
|
||||
<target>- опционально уведомляйте удалённые контакты.
|
||||
- имена профилей с пробелами.
|
||||
- и прочее!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="- voice messages up to 5 minutes. - custom time to disappear. - editing history." xml:space="preserve">
|
||||
@ -408,6 +420,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="0 sec" xml:space="preserve">
|
||||
<source>0 sec</source>
|
||||
<target>0 сек</target>
|
||||
<note>time to disappear</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="0s" xml:space="preserve">
|
||||
@ -637,6 +650,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="All new messages from %@ will be hidden!" xml:space="preserve">
|
||||
<source>All new messages from %@ will be hidden!</source>
|
||||
<target>Все новые сообщения от %@ будут скрыты!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="All your contacts will remain connected." xml:space="preserve">
|
||||
@ -746,10 +760,12 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Already connecting!" xml:space="preserve">
|
||||
<source>Already connecting!</source>
|
||||
<target>Уже соединяется!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Already joining the group!" xml:space="preserve">
|
||||
<source>Already joining the group!</source>
|
||||
<target>Вступление в группу уже начато!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Always use relay" xml:space="preserve">
|
||||
@ -874,6 +890,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad desktop address" xml:space="preserve">
|
||||
<source>Bad desktop address</source>
|
||||
<target>Неверный адрес компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Bad message ID" xml:space="preserve">
|
||||
@ -888,6 +905,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Better groups" xml:space="preserve">
|
||||
<source>Better groups</source>
|
||||
<target>Улучшенные группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Better messages" xml:space="preserve">
|
||||
@ -897,18 +915,22 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Block" xml:space="preserve">
|
||||
<source>Block</source>
|
||||
<target>Заблокировать</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block group members" xml:space="preserve">
|
||||
<source>Block group members</source>
|
||||
<target>Блокируйте членов группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member" xml:space="preserve">
|
||||
<source>Block member</source>
|
||||
<target>Заблокировать члена группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Block member?" xml:space="preserve">
|
||||
<source>Block member?</source>
|
||||
<target>Заблокировать члена группы?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Both you and your contact can add message reactions." xml:space="preserve">
|
||||
@ -1172,6 +1194,10 @@
|
||||
<target>Соединиться</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Соединиться Инкогнито</target>
|
||||
@ -1179,24 +1205,31 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to desktop" xml:space="preserve">
|
||||
<source>Connect to desktop</source>
|
||||
<target>Подключиться к компьютеру</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to yourself?" xml:space="preserve">
|
||||
<source>Connect to yourself?</source>
|
||||
<target>Соединиться с самим собой?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to yourself? This is your own SimpleX address!" xml:space="preserve">
|
||||
<source>Connect to yourself?
|
||||
This is your own SimpleX address!</source>
|
||||
<target>Соединиться с самим собой?
|
||||
Это ваш собственный адрес SimpleX!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect to yourself? This is your own one-time link!" xml:space="preserve">
|
||||
<source>Connect to yourself?
|
||||
This is your own one-time link!</source>
|
||||
<target>Соединиться с самим собой?
|
||||
Это ваша собственная одноразовая ссылка!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect via contact address" xml:space="preserve">
|
||||
<source>Connect via contact address</source>
|
||||
<target>Соединиться через адрес</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect via link" xml:space="preserve">
|
||||
@ -1216,14 +1249,17 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect with %@" xml:space="preserve">
|
||||
<source>Connect with %@</source>
|
||||
<target>Соединиться с %@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected desktop" xml:space="preserve">
|
||||
<source>Connected desktop</source>
|
||||
<target>Подключенный компьютер</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connected to desktop" xml:space="preserve">
|
||||
<source>Connected to desktop</source>
|
||||
<target>Компьютер подключен</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting server…" xml:space="preserve">
|
||||
@ -1238,6 +1274,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connecting to desktop" xml:space="preserve">
|
||||
<source>Connecting to desktop</source>
|
||||
<target>Подключение к компьютеру</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection" xml:space="preserve">
|
||||
@ -1262,6 +1299,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection terminated" xml:space="preserve">
|
||||
<source>Connection terminated</source>
|
||||
<target>Подключение прервано</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connection timeout" xml:space="preserve">
|
||||
@ -1331,6 +1369,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Correct name to %@?" xml:space="preserve">
|
||||
<source>Correct name to %@?</source>
|
||||
<target>Исправить имя на %@?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create" xml:space="preserve">
|
||||
@ -1345,6 +1384,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create a group using a random profile." xml:space="preserve">
|
||||
<source>Create a group using a random profile.</source>
|
||||
<target>Создайте группу, используя случайный профиль.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create an address to let people connect with you." xml:space="preserve">
|
||||
@ -1359,6 +1399,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create group" xml:space="preserve">
|
||||
<source>Create group</source>
|
||||
<target>Создать группу</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create group link" xml:space="preserve">
|
||||
@ -1383,6 +1424,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create profile" xml:space="preserve">
|
||||
<source>Create profile</source>
|
||||
<target>Создать профиль</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Create queue" xml:space="preserve">
|
||||
@ -1545,6 +1587,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Delete %lld messages?" xml:space="preserve">
|
||||
<source>Delete %lld messages?</source>
|
||||
<target>Удалить %lld сообщений?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Delete Contact" xml:space="preserve">
|
||||
@ -1574,6 +1617,7 @@ This is your own one-time link!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Delete and notify contact" xml:space="preserve">
|
||||
<source>Delete and notify contact</source>
|
||||
<target>Удалить и уведомить контакт</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Delete archive" xml:space="preserve">
|
||||
@ -1609,6 +1653,8 @@ This is your own one-time link!</source>
|
||||
<trans-unit id="Delete contact? This cannot be undone!" xml:space="preserve">
|
||||
<source>Delete contact?
|
||||
This cannot be undone!</source>
|
||||
<target>Удалить контакт?
|
||||
Это не может быть отменено!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Delete database" xml:space="preserve">
|
||||
@ -1753,14 +1799,17 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop address" xml:space="preserve">
|
||||
<source>Desktop address</source>
|
||||
<target>Адрес компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop app version %@ is not compatible with this app." xml:space="preserve">
|
||||
<source>Desktop app version %@ is not compatible with this app.</source>
|
||||
<target>Версия настольного приложения %@ несовместима с этим приложением.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Desktop devices" xml:space="preserve">
|
||||
<source>Desktop devices</source>
|
||||
<target>Компьютеры</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Develop" xml:space="preserve">
|
||||
@ -1855,6 +1904,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Disconnect desktop?" xml:space="preserve">
|
||||
<source>Disconnect desktop?</source>
|
||||
<target>Отключить компьютер?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover and join groups" xml:space="preserve">
|
||||
@ -1862,8 +1912,8 @@ This cannot be undone!</source>
|
||||
<target>Найдите и вступите в группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2038,10 +2088,12 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation error" xml:space="preserve">
|
||||
<source>Encryption re-negotiation error</source>
|
||||
<target>Ошибка нового соглашения о шифровании</target>
|
||||
<note>message decrypt error item</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Encryption re-negotiation failed." xml:space="preserve">
|
||||
<source>Encryption re-negotiation failed.</source>
|
||||
<target>Ошибка нового соглашения о шифровании.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter Passcode" xml:space="preserve">
|
||||
@ -2056,6 +2108,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter group name…" xml:space="preserve">
|
||||
<source>Enter group name…</source>
|
||||
<target>Введите имя группы…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter passphrase…" xml:space="preserve">
|
||||
@ -2075,6 +2128,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter this device name…" xml:space="preserve">
|
||||
<source>Enter this device name…</source>
|
||||
<target>Введите имя этого устройства…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter welcome message…" xml:space="preserve">
|
||||
@ -2089,6 +2143,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Enter your name…" xml:space="preserve">
|
||||
<source>Enter your name…</source>
|
||||
<target>Введите ваше имя…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Error" xml:space="preserve">
|
||||
@ -2148,6 +2203,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Error creating member contact" xml:space="preserve">
|
||||
<source>Error creating member contact</source>
|
||||
<target>Ошибка создания контакта с членом группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Error creating profile!" xml:space="preserve">
|
||||
@ -2282,6 +2338,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Error sending member contact invitation" xml:space="preserve">
|
||||
<source>Error sending member contact invitation</source>
|
||||
<target>Ошибка отправки приглашения члену группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Error sending message" xml:space="preserve">
|
||||
@ -2366,6 +2423,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Expand" xml:space="preserve">
|
||||
<source>Expand</source>
|
||||
<target>Раскрыть</target>
|
||||
<note>chat item action</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Export database" xml:space="preserve">
|
||||
@ -2400,6 +2458,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Faster joining and more reliable messages." xml:space="preserve">
|
||||
<source>Faster joining and more reliable messages.</source>
|
||||
<target>Быстрое вступление и надежная доставка сообщений.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Favorite" xml:space="preserve">
|
||||
@ -2497,6 +2556,10 @@ This cannot be undone!</source>
|
||||
<target>Для консоли</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Французский интерфейс</target>
|
||||
@ -2519,6 +2582,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Fully decentralized – visible only to members." xml:space="preserve">
|
||||
<source>Fully decentralized – visible only to members.</source>
|
||||
<target>Группа полностью децентрализована – она видна только членам.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Fully re-implemented - work in background!" xml:space="preserve">
|
||||
@ -2543,10 +2607,12 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Group already exists" xml:space="preserve">
|
||||
<source>Group already exists</source>
|
||||
<target>Группа уже существует</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Group already exists!" xml:space="preserve">
|
||||
<source>Group already exists!</source>
|
||||
<target>Группа уже существует!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Group display name" xml:space="preserve">
|
||||
@ -2821,6 +2887,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito groups" xml:space="preserve">
|
||||
<source>Incognito groups</source>
|
||||
<target>Инкогнито группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incognito mode" xml:space="preserve">
|
||||
@ -2855,6 +2922,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incompatible version" xml:space="preserve">
|
||||
<source>Incompatible version</source>
|
||||
<target>Несовместимая версия</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Incorrect passcode" xml:space="preserve">
|
||||
@ -2906,6 +2974,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Invalid name!" xml:space="preserve">
|
||||
<source>Invalid name!</source>
|
||||
<target>Неверное имя!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Invalid server address!" xml:space="preserve">
|
||||
@ -3001,6 +3070,7 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Join group?" xml:space="preserve">
|
||||
<source>Join group?</source>
|
||||
<target>Вступить в группу?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Join incognito" xml:space="preserve">
|
||||
@ -3010,11 +3080,14 @@ This cannot be undone!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Join with current profile" xml:space="preserve">
|
||||
<source>Join with current profile</source>
|
||||
<target>Вступить с активным профилем</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Join your group? This is your link for group %@!" xml:space="preserve">
|
||||
<source>Join your group?
|
||||
This is your link for group %@!</source>
|
||||
<target>Вступить в вашу группу?
|
||||
Это ваша ссылка на группу %@!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Joining group" xml:space="preserve">
|
||||
@ -3024,6 +3097,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep the app open to use it from desktop" xml:space="preserve">
|
||||
<source>Keep the app open to use it from desktop</source>
|
||||
<target>Оставьте приложение открытым, чтобы использовать его с компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Keep your connections" xml:space="preserve">
|
||||
@ -3088,14 +3162,17 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Link mobile and desktop apps! 🔗" xml:space="preserve">
|
||||
<source>Link mobile and desktop apps! 🔗</source>
|
||||
<target>Свяжите мобильное и настольное приложения! 🔗</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktop options" xml:space="preserve">
|
||||
<source>Linked desktop options</source>
|
||||
<target>Опции связанных компьютеров</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Linked desktops" xml:space="preserve">
|
||||
<source>Linked desktops</source>
|
||||
<target>Связанные компьютеры</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Live message!" xml:space="preserve">
|
||||
@ -3250,6 +3327,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Messages from %@ will be shown!" xml:space="preserve">
|
||||
<source>Messages from %@ will be shown!</source>
|
||||
<target>Сообщения от %@ будут показаны!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Migrating database archive…" xml:space="preserve">
|
||||
@ -3447,6 +3525,10 @@ This is your link for group %@!</source>
|
||||
<target>Нет полученных или отправленных файлов</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Уведомления</target>
|
||||
@ -3583,6 +3665,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Open" xml:space="preserve">
|
||||
<source>Open</source>
|
||||
<target>Открыть</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Open Settings" xml:space="preserve">
|
||||
@ -3602,6 +3685,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Open group" xml:space="preserve">
|
||||
<source>Open group</source>
|
||||
<target>Открыть группу</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Open user profiles" xml:space="preserve">
|
||||
@ -3666,6 +3750,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste desktop address" xml:space="preserve">
|
||||
<source>Paste desktop address</source>
|
||||
<target>Вставить адрес компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Paste image" xml:space="preserve">
|
||||
@ -3815,10 +3900,12 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Profile name" xml:space="preserve">
|
||||
<source>Profile name</source>
|
||||
<target>Имя профиля</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Profile name:" xml:space="preserve">
|
||||
<source>Profile name:</source>
|
||||
<target>Имя профиля:</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Profile password" xml:space="preserve">
|
||||
@ -4068,10 +4155,12 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Repeat connection request?" xml:space="preserve">
|
||||
<source>Repeat connection request?</source>
|
||||
<target>Повторить запрос на соединение?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Repeat join request?" xml:space="preserve">
|
||||
<source>Repeat join request?</source>
|
||||
<target>Повторить запрос на вступление?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Reply" xml:space="preserve">
|
||||
@ -4261,6 +4350,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan QR code from desktop" xml:space="preserve">
|
||||
<source>Scan QR code from desktop</source>
|
||||
<target>Сканировать QR код с компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Scan code" xml:space="preserve">
|
||||
@ -4345,6 +4435,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Send direct message to connect" xml:space="preserve">
|
||||
<source>Send direct message to connect</source>
|
||||
<target>Отправьте сообщение чтобы соединиться</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Send disappearing message" xml:space="preserve">
|
||||
@ -4484,6 +4575,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Session code" xml:space="preserve">
|
||||
<source>Session code</source>
|
||||
<target>Код сессии</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Set 1 day" xml:space="preserve">
|
||||
@ -4798,6 +4890,7 @@ This is your link for group %@!</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Tap to Connect" xml:space="preserve">
|
||||
<source>Tap to Connect</source>
|
||||
<target>Нажмите чтобы соединиться</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Tap to activate profile." xml:space="preserve">
|
||||
@ -4984,6 +5077,7 @@ It can happen because of some bug or when the connection is compromised.</source
|
||||
</trans-unit>
|
||||
<trans-unit id="This device name" xml:space="preserve">
|
||||
<source>This device name</source>
|
||||
<target>Имя этого устройства</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="This group has over %lld members, delivery receipts are not sent." xml:space="preserve">
|
||||
@ -4998,10 +5092,12 @@ It can happen because of some bug or when the connection is compromised.</source
|
||||
</trans-unit>
|
||||
<trans-unit id="This is your own SimpleX address!" xml:space="preserve">
|
||||
<source>This is your own SimpleX address!</source>
|
||||
<target>Это ваш собственный адрес SimpleX!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="This is your own one-time link!" xml:space="preserve">
|
||||
<source>This is your own one-time link!</source>
|
||||
<target>Это ваша собственная одноразовая ссылка!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="This setting applies to messages in your current chat profile **%@**." xml:space="preserve">
|
||||
@ -5021,6 +5117,7 @@ It can happen because of some bug or when the connection is compromised.</source
|
||||
</trans-unit>
|
||||
<trans-unit id="To hide unwanted messages." xml:space="preserve">
|
||||
<source>To hide unwanted messages.</source>
|
||||
<target>Чтобы скрыть нежелательные сообщения.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="To make a new connection" xml:space="preserve">
|
||||
@ -5107,14 +5204,17 @@ You will be prompted to complete authentication before this feature is enabled.<
|
||||
</trans-unit>
|
||||
<trans-unit id="Unblock" xml:space="preserve">
|
||||
<source>Unblock</source>
|
||||
<target>Разблокировать</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unblock member" xml:space="preserve">
|
||||
<source>Unblock member</source>
|
||||
<target>Разблокировать члена группы</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unblock member?" xml:space="preserve">
|
||||
<source>Unblock member?</source>
|
||||
<target>Разблокировать члена группы?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unexpected error: %@" xml:space="preserve">
|
||||
@ -5181,10 +5281,12 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink" xml:space="preserve">
|
||||
<source>Unlink</source>
|
||||
<target>Забыть</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlink desktop?" xml:space="preserve">
|
||||
<source>Unlink desktop?</source>
|
||||
<target>Забыть компьютер?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Unlock" xml:space="preserve">
|
||||
@ -5279,6 +5381,7 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="Use from desktop" xml:space="preserve">
|
||||
<source>Use from desktop</source>
|
||||
<target>Использовать с компьютера</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Use iOS call interface" xml:space="preserve">
|
||||
@ -5313,10 +5416,12 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify code with desktop" xml:space="preserve">
|
||||
<source>Verify code with desktop</source>
|
||||
<target>Сверьте код с компьютером</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection" xml:space="preserve">
|
||||
<source>Verify connection</source>
|
||||
<target>Проверить соединение</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connection security" xml:space="preserve">
|
||||
@ -5326,6 +5431,7 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify connections" xml:space="preserve">
|
||||
<source>Verify connections</source>
|
||||
<target>Проверять соединения</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Verify security code" xml:space="preserve">
|
||||
@ -5340,6 +5446,7 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="Via secure quantum resistant protocol." xml:space="preserve">
|
||||
<source>Via secure quantum resistant protocol.</source>
|
||||
<target>Через безопасный квантово-устойчивый протокол.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Video call" xml:space="preserve">
|
||||
@ -5392,6 +5499,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>Голосовое сообщение…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Ожидается прием файла</target>
|
||||
@ -5494,31 +5605,39 @@ To connect, please ask your contact to create another connection link and check
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already connecting to %@." xml:space="preserve">
|
||||
<source>You are already connecting to %@.</source>
|
||||
<target>Вы уже соединяетесь с %@.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already connecting via this one-time link!" xml:space="preserve">
|
||||
<source>You are already connecting via this one-time link!</source>
|
||||
<target>Вы уже соединяетесь по этой одноразовой ссылке!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already in group %@." xml:space="preserve">
|
||||
<source>You are already in group %@.</source>
|
||||
<target>Вы уже состоите в группе %@.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already joining the group %@." xml:space="preserve">
|
||||
<source>You are already joining the group %@.</source>
|
||||
<target>Вы уже вступаете в группу %@.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already joining the group via this link!" xml:space="preserve">
|
||||
<source>You are already joining the group via this link!</source>
|
||||
<target>Вы уже вступаете в группу по этой ссылке!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already joining the group via this link." xml:space="preserve">
|
||||
<source>You are already joining the group via this link.</source>
|
||||
<target>Вы уже вступаете в группу по этой ссылке.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are already joining the group! Repeat join request?" xml:space="preserve">
|
||||
<source>You are already joining the group!
|
||||
Repeat join request?</source>
|
||||
<target>Вы уже вступаете в группу!
|
||||
Повторить запрос на вступление?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You are connected to the server used to receive messages from this contact." xml:space="preserve">
|
||||
@ -5618,11 +5737,14 @@ Repeat join request?</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="You have already requested connection via this address!" xml:space="preserve">
|
||||
<source>You have already requested connection via this address!</source>
|
||||
<target>Вы уже запросили соединение через этот адрес!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You have already requested connection! Repeat connection request?" xml:space="preserve">
|
||||
<source>You have already requested connection!
|
||||
Repeat connection request?</source>
|
||||
<target>Вы уже запросили соединение!
|
||||
Повторить запрос?</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You have no chats" xml:space="preserve">
|
||||
@ -5677,6 +5799,7 @@ Repeat connection request?</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="You will be connected when group link host's device is online, please wait or check later!" xml:space="preserve">
|
||||
<source>You will be connected when group link host's device is online, please wait or check later!</source>
|
||||
<target>Соединение будет установлено, когда владелец ссылки группы будет онлайн. Пожалуйста, подождите или проверьте позже!</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You will be connected when your connection request is accepted, please wait or check later!" xml:space="preserve">
|
||||
@ -5696,6 +5819,7 @@ Repeat connection request?</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="You will connect to all group members." xml:space="preserve">
|
||||
<source>You will connect to all group members.</source>
|
||||
<target>Вы соединитесь со всеми членами группы.</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="You will still receive calls and notifications from muted profiles when they are active." xml:space="preserve">
|
||||
@ -5819,6 +5943,7 @@ You can change it in Settings.</source>
|
||||
</trans-unit>
|
||||
<trans-unit id="Your profile" xml:space="preserve">
|
||||
<source>Your profile</source>
|
||||
<target>Ваш профиль</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Your profile **%@** will be shared." xml:space="preserve">
|
||||
@ -5915,6 +6040,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="and %lld other events" xml:space="preserve">
|
||||
<source>and %lld other events</source>
|
||||
<target>и %lld других событий</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="audio call (not e2e encrypted)" xml:space="preserve">
|
||||
@ -5922,6 +6048,10 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
<target>аудиозвонок (не e2e зашифрованный)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>ошибка ID сообщения</target>
|
||||
@ -5934,6 +6064,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="blocked" xml:space="preserve">
|
||||
<source>blocked</source>
|
||||
<target>заблокировано</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bold" xml:space="preserve">
|
||||
@ -6008,6 +6139,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="connected directly" xml:space="preserve">
|
||||
<source>connected directly</source>
|
||||
<target>соединен(а) напрямую</target>
|
||||
<note>rcv group event chat item</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="connecting" xml:space="preserve">
|
||||
@ -6107,6 +6239,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="deleted contact" xml:space="preserve">
|
||||
<source>deleted contact</source>
|
||||
<target>удалил(а) контакт</target>
|
||||
<note>rcv direct event chat item</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="deleted group" xml:space="preserve">
|
||||
@ -6473,6 +6606,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="send direct message" xml:space="preserve">
|
||||
<source>send direct message</source>
|
||||
<target>отправьте сообщение</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="starting…" xml:space="preserve">
|
||||
@ -6502,6 +6636,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@" xml:space="preserve">
|
||||
<source>v%@</source>
|
||||
<target>v%@</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="v%@ (%@)" xml:space="preserve">
|
||||
@ -6643,6 +6778,7 @@ SimpleX серверы не могут получить доступ к Ваше
|
||||
</trans-unit>
|
||||
<trans-unit id="NSLocalNetworkUsageDescription" xml:space="preserve">
|
||||
<source>SimpleX uses local network access to allow using user chat profile via desktop app on the same network.</source>
|
||||
<target>SimpleX использует доступ к локальной сети, чтобы разрешить использование профиля чата через компьютер в той же сети.</target>
|
||||
<note>Privacy - Local Network Usage Description</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="NSMicrophoneUsageDescription" xml:space="preserve">
|
||||
|
@ -1159,6 +1159,10 @@
|
||||
<target>เชื่อมต่อ</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
@ -1844,8 +1848,8 @@ This cannot be undone!</source>
|
||||
<source>Discover and join groups</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2476,6 +2480,10 @@ This cannot be undone!</source>
|
||||
<target>สำหรับคอนโซล</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>อินเทอร์เฟซภาษาฝรั่งเศส</target>
|
||||
@ -3421,6 +3429,10 @@ This is your link for group %@!</source>
|
||||
<target>ไม่มีไฟล์ที่ได้รับหรือส่ง</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>การแจ้งเตือน</target>
|
||||
@ -5354,6 +5366,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>ข้อความเสียง…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>กำลังรอไฟล์</target>
|
||||
@ -5882,6 +5898,10 @@ SimpleX servers cannot see your profile.</source>
|
||||
<target>การโทรด้วยเสียง (ไม่ได้ encrypt จากต้นจนจบ)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>ID ข้อความที่ไม่ดี</target>
|
||||
|
@ -1166,6 +1166,10 @@
|
||||
<target>Підключіться</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>Підключайтеся інкогніто</target>
|
||||
@ -1854,8 +1858,8 @@ This cannot be undone!</source>
|
||||
<source>Discover and join groups</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2486,6 +2490,10 @@ This cannot be undone!</source>
|
||||
<target>Для консолі</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>Французький інтерфейс</target>
|
||||
@ -3435,6 +3443,10 @@ This is your link for group %@!</source>
|
||||
<target>Немає отриманих або відправлених файлів</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>Сповіщення</target>
|
||||
@ -5378,6 +5390,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>Голосове повідомлення…</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>Очікування файлу</target>
|
||||
@ -5908,6 +5924,10 @@ SimpleX servers cannot see your profile.</source>
|
||||
<target>аудіовиклик (без шифрування e2e)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>невірний ідентифікатор повідомлення</target>
|
||||
|
@ -1172,6 +1172,10 @@
|
||||
<target>连接</target>
|
||||
<note>server test step</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect automatically" xml:space="preserve">
|
||||
<source>Connect automatically</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Connect incognito" xml:space="preserve">
|
||||
<source>Connect incognito</source>
|
||||
<target>在隐身状态下连接</target>
|
||||
@ -1862,8 +1866,8 @@ This cannot be undone!</source>
|
||||
<target>发现和加入群组</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Discover on network" xml:space="preserve">
|
||||
<source>Discover on network</source>
|
||||
<trans-unit id="Discover via local network" xml:space="preserve">
|
||||
<source>Discover via local network</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Do NOT use SimpleX for emergency calls." xml:space="preserve">
|
||||
@ -2499,6 +2503,10 @@ This cannot be undone!</source>
|
||||
<target>用于控制台</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Found desktop" xml:space="preserve">
|
||||
<source>Found desktop</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="French interface" xml:space="preserve">
|
||||
<source>French interface</source>
|
||||
<target>法语界面</target>
|
||||
@ -3449,6 +3457,10 @@ This is your link for group %@!</source>
|
||||
<target>未收到或发送文件</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Not compatible!" xml:space="preserve">
|
||||
<source>Not compatible!</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Notifications" xml:space="preserve">
|
||||
<source>Notifications</source>
|
||||
<target>通知</target>
|
||||
@ -5396,6 +5408,10 @@ To connect, please ask your contact to create another connection link and check
|
||||
<target>语音消息……</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for desktop..." xml:space="preserve">
|
||||
<source>Waiting for desktop...</source>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="Waiting for file" xml:space="preserve">
|
||||
<source>Waiting for file</source>
|
||||
<target>等待文件中</target>
|
||||
@ -5926,6 +5942,10 @@ SimpleX 服务器无法看到您的资料。</target>
|
||||
<target>语音通话(非端到端加密)</target>
|
||||
<note>No comment provided by engineer.</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="author" xml:space="preserve">
|
||||
<source>author</source>
|
||||
<note>member role</note>
|
||||
</trans-unit>
|
||||
<trans-unit id="bad message ID" xml:space="preserve">
|
||||
<source>bad message ID</source>
|
||||
<target>错误消息 ID</target>
|
||||
|
@ -609,7 +609,7 @@ public enum ChatResponse: Decodable, Error {
|
||||
case contactConnectionDeleted(user: UserRef, connection: PendingContactConnection)
|
||||
// remote desktop responses/events
|
||||
case remoteCtrlList(remoteCtrls: [RemoteCtrlInfo])
|
||||
case remoteCtrlFound(remoteCtrl: RemoteCtrlInfo)
|
||||
case remoteCtrlFound(remoteCtrl: RemoteCtrlInfo, ctrlAppInfo_: CtrlAppInfo?, appVersion: String, compatible: Bool)
|
||||
case remoteCtrlConnecting(remoteCtrl_: RemoteCtrlInfo?, ctrlAppInfo: CtrlAppInfo, appVersion: String)
|
||||
case remoteCtrlSessionCode(remoteCtrl_: RemoteCtrlInfo?, sessionCode: String)
|
||||
case remoteCtrlConnected(remoteCtrl: RemoteCtrlInfo)
|
||||
@ -903,7 +903,7 @@ public enum ChatResponse: Decodable, Error {
|
||||
case let .newContactConnection(u, connection): return withUser(u, String(describing: connection))
|
||||
case let .contactConnectionDeleted(u, connection): return withUser(u, String(describing: connection))
|
||||
case let .remoteCtrlList(remoteCtrls): return String(describing: remoteCtrls)
|
||||
case let .remoteCtrlFound(remoteCtrl): return String(describing: remoteCtrl)
|
||||
case let .remoteCtrlFound(remoteCtrl, ctrlAppInfo_, appVersion, compatible): return "remoteCtrl:\n\(String(describing: remoteCtrl))\nctrlAppInfo_:\n\(String(describing: ctrlAppInfo_))\nappVersion: \(appVersion)\ncompatible: \(compatible)"
|
||||
case let .remoteCtrlConnecting(remoteCtrl_, ctrlAppInfo, appVersion): return "remoteCtrl_:\n\(String(describing: remoteCtrl_))\nctrlAppInfo:\n\(String(describing: ctrlAppInfo))\nappVersion: \(appVersion)"
|
||||
case let .remoteCtrlSessionCode(remoteCtrl_, sessionCode): return "remoteCtrl_:\n\(String(describing: remoteCtrl_))\nsessionCode: \(sessionCode)"
|
||||
case let .remoteCtrlConnected(remoteCtrl): return String(describing: remoteCtrl)
|
||||
@ -1546,6 +1546,7 @@ public struct RemoteCtrlInfo: Decodable {
|
||||
|
||||
public enum RemoteCtrlSessionState: Decodable {
|
||||
case starting
|
||||
case searching
|
||||
case connecting
|
||||
case pendingConfirmation(sessionCode: String)
|
||||
case connected(sessionCode: String)
|
||||
|
@ -25,6 +25,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"- more stable message delivery.\n- a bit better groups.\n- and more!" = "- stabilere Zustellung von Nachrichten.\n- ein bisschen verbesserte Gruppen.\n- und mehr!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- optionally notify deleted contacts.\n- profile names with spaces.\n- and more!" = "- Optionale Benachrichtigung von gelöschten Kontakten.\n- Profilnamen mit Leerzeichen.\n- Und mehr!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- voice messages up to 5 minutes.\n- custom time to disappear.\n- editing history." = "- Bis zu 5 Minuten lange Sprachnachrichten.\n- Zeitdauer für verschwindende Nachrichten anpassen.\n- Nachrichten-Historie bearbeiten.";
|
||||
|
||||
@ -43,6 +46,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"(" = "(";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(new)" = "(Neu)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(this device v%@)" = "(Dieses Gerät hat v%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
")" = ")";
|
||||
|
||||
@ -548,6 +557,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Back" = "Zurück";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Bad desktop address" = "Falsche Desktop-Adresse";
|
||||
|
||||
/* integrity error chat item */
|
||||
"bad message hash" = "Ungültiger Nachrichten-Hash";
|
||||
|
||||
@ -560,12 +572,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Bad message ID" = "Falsche Nachrichten-ID";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better groups" = "Bessere Gruppen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better messages" = "Verbesserungen bei Nachrichten";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block" = "Blockieren";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block group members" = "Gruppenmitglieder blockieren";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member" = "Mitglied blockieren";
|
||||
|
||||
@ -771,6 +789,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connect incognito" = "Inkognito verbinden";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to desktop" = "Mit dem Desktop verbinden";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connect to SimpleX Chat developers." = "Mit den SimpleX Chat-Entwicklern verbinden.";
|
||||
|
||||
@ -801,9 +822,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"connected" = "Verbunden";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected desktop" = "Verbundener Desktop";
|
||||
|
||||
/* rcv group event chat item */
|
||||
"connected directly" = "Direkt miteinander verbunden";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected to desktop" = "Mit dem Desktop verbunden";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connecting" = "verbinde";
|
||||
|
||||
@ -828,6 +855,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting server… (error: %@)" = "Mit dem Server verbinden… (Fehler: %@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting to desktop" = "Mit dem Desktop verbinden";
|
||||
|
||||
/* chat list item title */
|
||||
"connecting…" = "Verbinde…";
|
||||
|
||||
@ -846,6 +876,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connection request sent!" = "Verbindungsanfrage wurde gesendet!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection terminated" = "Verbindung beendet";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection timeout" = "Verbindungszeitüberschreitung";
|
||||
|
||||
@ -900,6 +933,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Create" = "Erstellen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create a group using a random profile." = "Erstellen Sie eine Gruppe mit einem zufälligen Profil.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create an address to let people connect with you." = "Erstellen Sie eine Adresse, damit sich Personen mit Ihnen verbinden können.";
|
||||
|
||||
@ -1173,6 +1209,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Description" = "Beschreibung";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop address" = "Desktop-Adresse";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop app version %@ is not compatible with this app." = "Desktop App-Version %@ ist mit dieser App nicht kompatibel.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop devices" = "Desktop-Geräte";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Develop" = "Entwicklung";
|
||||
|
||||
@ -1236,6 +1281,9 @@
|
||||
/* server test step */
|
||||
"Disconnect" = "Trennen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Disconnect desktop?" = "Desktop-Verbindung trennen?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Discover and join groups" = "Gruppen entdecken und ihnen beitreten";
|
||||
|
||||
@ -1374,6 +1422,12 @@
|
||||
/* chat item text */
|
||||
"encryption re-negotiation allowed for %@" = "Neuaushandlung der Verschlüsselung von %@ erlaubt";
|
||||
|
||||
/* message decrypt error item */
|
||||
"Encryption re-negotiation error" = "Fehler bei der Neuverhandlung der Verschlüsselung";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Encryption re-negotiation failed." = "Neuverhandlung der Verschlüsselung fehlgeschlagen.";
|
||||
|
||||
/* chat item text */
|
||||
"encryption re-negotiation required" = "Neuaushandlung der Verschlüsselung notwendig";
|
||||
|
||||
@ -1404,6 +1458,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Enter server manually" = "Geben Sie den Server manuell ein";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter this device name…" = "Geben Sie diesen Gerätenamen ein…";
|
||||
|
||||
/* placeholder */
|
||||
"Enter welcome message…" = "Geben Sie eine Begrüßungsmeldung ein …";
|
||||
|
||||
@ -1605,6 +1662,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Fast and no wait until the sender is online!" = "Schnell und ohne warten auf den Absender, bis er online ist!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Faster joining and more reliable messages." = "Schnellerer Gruppenbeitritt und zuverlässigere Nachrichtenzustellung.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Favorite" = "Favorit";
|
||||
|
||||
@ -1866,6 +1926,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito" = "Inkognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito groups" = "Inkognito-Gruppen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito mode" = "Inkognito-Modus";
|
||||
|
||||
@ -1893,6 +1956,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible database version" = "Inkompatible Datenbank-Version";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible version" = "Inkompatible Version";
|
||||
|
||||
/* PIN entry */
|
||||
"Incorrect passcode" = "Zugangscode ist falsch";
|
||||
|
||||
@ -2028,6 +2094,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Joining group" = "Der Gruppe beitreten";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep the app open to use it from desktop" = "Die App muss geöffnet bleiben, um sie vom Desktop aus nutzen zu können";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep your connections" = "Ihre Verbindungen beibehalten";
|
||||
|
||||
@ -2064,6 +2133,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Limitations" = "Einschränkungen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Link mobile and desktop apps! 🔗" = "Verknüpfe Mobiltelefon- und Desktop-Apps! 🔗";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktop options" = "Verknüpfte Desktop-Optionen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktops" = "Verknüpfte Desktops";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"LIVE" = "LIVE";
|
||||
|
||||
@ -2462,6 +2540,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Paste" = "Einfügen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste desktop address" = "Desktop-Adresse einfügen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste image" = "Bild einfügen";
|
||||
|
||||
@ -2846,6 +2927,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code" = "QR-Code scannen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code from desktop" = "Den QR-Code vom Desktop scannen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan security code from your contact's app." = "Scannen Sie den Sicherheitscode von der App Ihres Kontakts.";
|
||||
|
||||
@ -2990,6 +3074,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Servers" = "Server";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Session code" = "Sitzungscode";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Set 1 day" = "Einen Tag festlegen";
|
||||
|
||||
@ -3299,6 +3386,9 @@
|
||||
/* notification title */
|
||||
"this contact" = "Dieser Kontakt";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This device name" = "Dieser Gerätename";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This group has over %lld members, delivery receipts are not sent." = "Es werden keine Empfangsbestätigungen gesendet, da diese Gruppe über %lld Mitglieder hat.";
|
||||
|
||||
@ -3320,6 +3410,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"To connect, your contact can scan QR code or use the link in the app." = "Um eine Verbindung herzustellen, kann Ihr Kontakt den QR-Code scannen oder den Link in der App verwenden.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To hide unwanted messages." = "Um unerwünschte Nachrichten zu verbergen.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To make a new connection" = "Um eine Verbindung mit einem neuen Kontakt zu erstellen";
|
||||
|
||||
@ -3416,6 +3509,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Unless your contact deleted the connection or this link was already used, it might be a bug - please report it.\nTo connect, please ask your contact to create another connection link and check that you have a stable network connection." = "Entweder hat Ihr Kontakt die Verbindung gelöscht, oder dieser Link wurde bereits verwendet, es könnte sich um einen Fehler handeln - Bitte melden Sie es uns.\nBitten Sie Ihren Kontakt darum einen weiteren Verbindungs-Link zu erzeugen, um sich neu verbinden zu können und stellen Sie sicher, dass Sie eine stabile Netzwerk-Verbindung haben.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink" = "Entkoppeln";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink desktop?" = "Desktop entkoppeln?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlock" = "Entsperren";
|
||||
|
||||
@ -3470,6 +3569,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Use for new connections" = "Für neue Verbindungen nutzen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use from desktop" = "Vom Desktop aus nutzen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use iOS call interface" = "iOS Anrufschnittstelle nutzen";
|
||||
|
||||
@ -3491,12 +3593,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Using SimpleX Chat servers." = "Verwendung von SimpleX-Chat-Servern.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@" = "v%@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@ (%@)" = "v%@ (%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify code with desktop" = "Code mit dem Desktop überprüfen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection" = "Verbindung überprüfen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection security" = "Sicherheit der Verbindung überprüfen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connections" = "Verbindungen überprüfen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify security code" = "Sicherheitscode überprüfen";
|
||||
|
||||
@ -3515,6 +3629,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"via relay" = "über Relais";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Via secure quantum resistant protocol." = "Über ein sicheres quantenbeständiges Protokoll.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Video call" = "Videoanruf";
|
||||
|
||||
|
@ -7,6 +7,9 @@
|
||||
/* Privacy - Face ID Usage Description */
|
||||
"NSFaceIDUsageDescription" = "Face ID wird von SimpleX für die lokale Authentifizierung genutzt";
|
||||
|
||||
/* Privacy - Local Network Usage Description */
|
||||
"NSLocalNetworkUsageDescription" = "SimpleX nutzt den lokalen Netzwerkzugriff, um die Nutzung von Benutzer-Chatprofilen über eine Desktop-App im gleichen Netzwerk zu erlauben.";
|
||||
|
||||
/* Privacy - Microphone Usage Description */
|
||||
"NSMicrophoneUsageDescription" = "SimpleX benötigt Zugriff auf das Mikrofon, um Audio- und Videoanrufe und die Aufnahme von Sprachnachrichten zu ermöglichen.";
|
||||
|
||||
|
@ -25,6 +25,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"- more stable message delivery.\n- a bit better groups.\n- and more!" = "- une diffusion plus stable des messages.\n- des groupes un peu plus performants.\n- et bien d'autres choses encore !";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- optionally notify deleted contacts.\n- profile names with spaces.\n- and more!" = "- option pour notifier les contacts supprimés.\n- noms de profil avec espaces.\n- et plus encore !";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- voice messages up to 5 minutes.\n- custom time to disappear.\n- editing history." = "- messages vocaux pouvant durer jusqu'à 5 minutes.\n- délai personnalisé de disparition.\n- l'historique de modification.";
|
||||
|
||||
@ -43,6 +46,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"(" = "(";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(new)" = "(nouveau)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(this device v%@)" = "(cet appareil v%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
")" = ")";
|
||||
|
||||
@ -548,6 +557,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Back" = "Retour";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Bad desktop address" = "Mauvaise adresse de bureau";
|
||||
|
||||
/* integrity error chat item */
|
||||
"bad message hash" = "hash de message incorrect";
|
||||
|
||||
@ -560,12 +572,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Bad message ID" = "Mauvais ID de message";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better groups" = "Des groupes plus performants";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better messages" = "Meilleurs messages";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block" = "Bloquer";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block group members" = "Bloquer des membres d'un groupe";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member" = "Bloquer ce membre";
|
||||
|
||||
@ -771,6 +789,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connect incognito" = "Se connecter incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to desktop" = "Se connecter au bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connect to SimpleX Chat developers." = "se connecter aux developpeurs de SimpleX Chat.";
|
||||
|
||||
@ -801,9 +822,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"connected" = "connecté";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected desktop" = "Bureau connecté";
|
||||
|
||||
/* rcv group event chat item */
|
||||
"connected directly" = "s'est connecté.e de manière directe";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected to desktop" = "Connecté au bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connecting" = "connexion";
|
||||
|
||||
@ -828,6 +855,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting server… (error: %@)" = "Connexion au serveur… (erreur : %@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting to desktop" = "Connexion au bureau";
|
||||
|
||||
/* chat list item title */
|
||||
"connecting…" = "connexion…";
|
||||
|
||||
@ -846,6 +876,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connection request sent!" = "Demande de connexion envoyée !";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection terminated" = "Connexion terminée";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection timeout" = "Délai de connexion";
|
||||
|
||||
@ -900,6 +933,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Create" = "Créer";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create a group using a random profile." = "Création de groupes via un profil aléatoire.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create an address to let people connect with you." = "Créez une adresse pour permettre aux gens de vous contacter.";
|
||||
|
||||
@ -1173,6 +1209,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Description" = "Description";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop address" = "Adresse de bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop app version %@ is not compatible with this app." = "La version de l'application de bureau %@ n'est pas compatible avec cette application.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop devices" = "Appareils de bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Develop" = "Développer";
|
||||
|
||||
@ -1236,6 +1281,9 @@
|
||||
/* server test step */
|
||||
"Disconnect" = "Se déconnecter";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Disconnect desktop?" = "Déconnecter le bureau ?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Discover and join groups" = "Découvrir et rejoindre des groupes";
|
||||
|
||||
@ -1374,6 +1422,12 @@
|
||||
/* chat item text */
|
||||
"encryption re-negotiation allowed for %@" = "renégociation de chiffrement autorisée pour %@";
|
||||
|
||||
/* message decrypt error item */
|
||||
"Encryption re-negotiation error" = "Erreur lors de la renégociation du chiffrement";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Encryption re-negotiation failed." = "La renégociation du chiffrement a échoué.";
|
||||
|
||||
/* chat item text */
|
||||
"encryption re-negotiation required" = "renégociation de chiffrement requise";
|
||||
|
||||
@ -1404,6 +1458,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Enter server manually" = "Entrer un serveur manuellement";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter this device name…" = "Entrez le nom de l'appareil…";
|
||||
|
||||
/* placeholder */
|
||||
"Enter welcome message…" = "Entrez un message de bienvenue…";
|
||||
|
||||
@ -1605,6 +1662,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Fast and no wait until the sender is online!" = "Rapide et ne nécessitant pas d'attendre que l'expéditeur soit en ligne !";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Faster joining and more reliable messages." = "Connexion plus rapide et messages plus fiables.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Favorite" = "Favoris";
|
||||
|
||||
@ -1866,6 +1926,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito" = "Incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito groups" = "Groupes incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito mode" = "Mode Incognito";
|
||||
|
||||
@ -1893,6 +1956,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible database version" = "Version de la base de données incompatible";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible version" = "Version incompatible";
|
||||
|
||||
/* PIN entry */
|
||||
"Incorrect passcode" = "Code d'accès erroné";
|
||||
|
||||
@ -2028,6 +2094,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Joining group" = "Entrain de rejoindre le groupe";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep the app open to use it from desktop" = "Garder l'application ouverte pour l'utiliser depuis le bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep your connections" = "Conserver vos connexions";
|
||||
|
||||
@ -2064,6 +2133,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Limitations" = "Limitations";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Link mobile and desktop apps! 🔗" = "Liez vos applications mobiles et de bureau ! 🔗";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktop options" = "Options de bureau lié";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktops" = "Bureaux liés";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"LIVE" = "LIVE";
|
||||
|
||||
@ -2462,6 +2540,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Paste" = "Coller";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste desktop address" = "Coller l'adresse du bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste image" = "Coller l'image";
|
||||
|
||||
@ -2846,6 +2927,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code" = "Scanner un code QR";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code from desktop" = "Scanner le code QR du bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan security code from your contact's app." = "Scannez le code de sécurité depuis l'application de votre contact.";
|
||||
|
||||
@ -2990,6 +3074,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Servers" = "Serveurs";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Session code" = "Code de session";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Set 1 day" = "Définir 1 jour";
|
||||
|
||||
@ -3299,6 +3386,9 @@
|
||||
/* notification title */
|
||||
"this contact" = "ce contact";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This device name" = "Ce nom d'appareil";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This group has over %lld members, delivery receipts are not sent." = "Ce groupe compte plus de %lld membres, les accusés de réception ne sont pas envoyés.";
|
||||
|
||||
@ -3320,6 +3410,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"To connect, your contact can scan QR code or use the link in the app." = "Pour se connecter, votre contact peut scanner le code QR ou utiliser le lien dans l'application.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To hide unwanted messages." = "Pour cacher les messages indésirables.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To make a new connection" = "Pour établir une nouvelle connexion";
|
||||
|
||||
@ -3416,6 +3509,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Unless your contact deleted the connection or this link was already used, it might be a bug - please report it.\nTo connect, please ask your contact to create another connection link and check that you have a stable network connection." = "A moins que votre contact ait supprimé la connexion ou que ce lien ait déjà été utilisé, il peut s'agir d'un bug - veuillez le signaler.\nPour vous connecter, veuillez demander à votre contact de créer un autre lien de connexion et vérifiez que vous disposez d'une connexion réseau stable.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink" = "Délier";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink desktop?" = "Délier le bureau ?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlock" = "Déverrouiller";
|
||||
|
||||
@ -3470,6 +3569,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Use for new connections" = "Utiliser pour les nouvelles connexions";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use from desktop" = "Utilisation depuis le bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use iOS call interface" = "Utiliser l'interface d'appel d'iOS";
|
||||
|
||||
@ -3491,12 +3593,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Using SimpleX Chat servers." = "Utilisation des serveurs SimpleX Chat.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@" = "v%@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@ (%@)" = "v%@ (%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify code with desktop" = "Vérifier le code avec le bureau";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection" = "Vérifier la connexion";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection security" = "Vérifier la sécurité de la connexion";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connections" = "Vérifier les connexions";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify security code" = "Vérifier le code de sécurité";
|
||||
|
||||
@ -3515,6 +3629,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"via relay" = "via relais";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Via secure quantum resistant protocol." = "Via un protocole sécurisé de cryptographie post-quantique.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Video call" = "Appel vidéo";
|
||||
|
||||
|
@ -7,6 +7,9 @@
|
||||
/* Privacy - Face ID Usage Description */
|
||||
"NSFaceIDUsageDescription" = "SimpleGroup not found!X utilise Face ID pour l'authentification locale";
|
||||
|
||||
/* Privacy - Local Network Usage Description */
|
||||
"NSLocalNetworkUsageDescription" = "SimpleX utilise un accès au réseau local pour permettre l'utilisation du profil de chat de l'utilisateur via l'application de bureau au sein de ce même réseau.";
|
||||
|
||||
/* Privacy - Microphone Usage Description */
|
||||
"NSMicrophoneUsageDescription" = "SimpleX a besoin d'un accès au microphone pour les appels audio et vidéo ainsi que pour enregistrer des messages vocaux.";
|
||||
|
||||
|
@ -25,6 +25,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"- more stable message delivery.\n- a bit better groups.\n- and more!" = "- recapito dei messaggi più stabile.\n- gruppi un po' migliorati.\n- e altro ancora!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- optionally notify deleted contacts.\n- profile names with spaces.\n- and more!" = "- avvisa facoltativamente i contatti eliminati.\n- nomi del profilo con spazi.\n- e molto altro!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- voice messages up to 5 minutes.\n- custom time to disappear.\n- editing history." = "- messaggi vocali fino a 5 minuti.\n- tempo di scomparsa personalizzato.\n- cronologia delle modifiche.";
|
||||
|
||||
@ -569,12 +572,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Bad message ID" = "ID del messaggio errato";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better groups" = "Gruppi migliorati";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better messages" = "Messaggi migliorati";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block" = "Blocca";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block group members" = "Blocca i membri dei gruppi";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member" = "Blocca membro";
|
||||
|
||||
@ -924,6 +933,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Create" = "Crea";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create a group using a random profile." = "Crea un gruppo usando un profilo casuale.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create an address to let people connect with you." = "Crea un indirizzo per consentire alle persone di connettersi con te.";
|
||||
|
||||
@ -1275,9 +1287,6 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Discover and join groups" = "Scopri ed unisciti ai gruppi";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Discover on network" = "Trova nella rete";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Do it later" = "Fallo dopo";
|
||||
|
||||
@ -1653,6 +1662,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Fast and no wait until the sender is online!" = "Veloce e senza aspettare che il mittente sia in linea!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Faster joining and more reliable messages." = "Ingresso più veloce e messaggi più affidabili.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Favorite" = "Preferito";
|
||||
|
||||
@ -1914,6 +1926,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito" = "Incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito groups" = "Gruppi in incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito mode" = "Modalità incognito";
|
||||
|
||||
@ -2118,6 +2133,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Limitations" = "Limitazioni";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Link mobile and desktop apps! 🔗" = "Collega le app mobile e desktop! 🔗";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktop options" = "Opzioni del desktop collegato";
|
||||
|
||||
@ -3392,6 +3410,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"To connect, your contact can scan QR code or use the link in the app." = "Per connettervi, il tuo contatto può scansionare il codice QR o usare il link nell'app.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To hide unwanted messages." = "Per nascondere messaggi indesiderati.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To make a new connection" = "Per creare una nuova connessione";
|
||||
|
||||
@ -3608,6 +3629,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"via relay" = "via relay";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Via secure quantum resistant protocol." = "Tramite protocollo sicuro resistente alla quantistica.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Video call" = "Videochiamata";
|
||||
|
||||
|
@ -25,6 +25,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"- more stable message delivery.\n- a bit better groups.\n- and more!" = "- stabielere berichtbezorging.\n- een beetje betere groepen.\n- en meer!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- optionally notify deleted contacts.\n- profile names with spaces.\n- and more!" = "- optioneel verwijderde contacten op de hoogte stellen.\n- profielnamen met spaties.\n- en meer!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- voice messages up to 5 minutes.\n- custom time to disappear.\n- editing history." = "- spraakberichten tot 5 minuten.\n- aangepaste tijd om te verdwijnen.\n- bewerkingsgeschiedenis.";
|
||||
|
||||
@ -569,12 +572,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Bad message ID" = "Onjuiste bericht-ID";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better groups" = "Betere groepen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better messages" = "Betere berichten";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block" = "Blokkeren";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block group members" = "Groepsleden blokkeren";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member" = "Lid blokkeren";
|
||||
|
||||
@ -924,6 +933,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Create" = "Maak";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create a group using a random profile." = "Maak een groep met een willekeurig profiel.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create an address to let people connect with you." = "Maak een adres aan zodat mensen contact met je kunnen opnemen.";
|
||||
|
||||
@ -1275,9 +1287,6 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Discover and join groups" = "Ontdek en sluit je aan bij groepen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Discover on network" = "Ontdek via netwerk";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Do it later" = "Doe het later";
|
||||
|
||||
@ -1653,6 +1662,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Fast and no wait until the sender is online!" = "Snel en niet wachten tot de afzender online is!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Faster joining and more reliable messages." = "Snellere deelname en betrouwbaardere berichten.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Favorite" = "Favoriet";
|
||||
|
||||
@ -1914,6 +1926,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito" = "Incognito";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito groups" = "Incognitogroepen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito mode" = "Incognito modus";
|
||||
|
||||
@ -2118,6 +2133,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Limitations" = "Beperkingen";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Link mobile and desktop apps! 🔗" = "Koppel mobiele en desktop-apps! 🔗";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktop options" = "Gekoppelde desktop opties";
|
||||
|
||||
@ -3392,6 +3410,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"To connect, your contact can scan QR code or use the link in the app." = "Om verbinding te maken, kan uw contact de QR-code scannen of de link in de app gebruiken.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To hide unwanted messages." = "Om ongewenste berichten te verbergen.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To make a new connection" = "Om een nieuwe verbinding te maken";
|
||||
|
||||
@ -3608,6 +3629,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"via relay" = "via relais";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Via secure quantum resistant protocol." = "Via een beveiligd kwantumbestendig protocol.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Video call" = "video oproep";
|
||||
|
||||
|
@ -25,6 +25,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"- more stable message delivery.\n- a bit better groups.\n- and more!" = "- более стабильная доставка сообщений.\n- немного улучшенные группы.\n- и прочее!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- optionally notify deleted contacts.\n- profile names with spaces.\n- and more!" = "- опционально уведомляйте удалённые контакты.\n- имена профилей с пробелами.\n- и прочее!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"- voice messages up to 5 minutes.\n- custom time to disappear.\n- editing history." = "- голосовые сообщения до 5 минут.\n- настройка времени исчезающих сообщений.\n- история редактирования.";
|
||||
|
||||
@ -43,6 +46,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"(" = "(";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(new)" = "(новое)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"(this device v%@)" = "(это устройство v%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
")" = ")";
|
||||
|
||||
@ -118,12 +127,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"%@ %@" = "%@ %@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%@ and %@" = "%@ и %@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%@ and %@ connected" = "%@ и %@ соединены";
|
||||
|
||||
/* copied message info, <sender> at <time> */
|
||||
"%@ at %@:" = "%1$@ в %2$@:";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%@ connected" = "%@ соединен(а)";
|
||||
|
||||
/* notification title */
|
||||
"%@ is connected!" = "Установлено соединение с %@!";
|
||||
|
||||
@ -139,6 +154,9 @@
|
||||
/* notification title */
|
||||
"%@ wants to connect!" = "%@ хочет соединиться!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%@, %@ and %lld members" = "%@, %@ и %lld членов группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%@, %@ and %lld other members connected" = "%@, %@ и %lld других членов соединены";
|
||||
|
||||
@ -178,9 +196,21 @@
|
||||
/* No comment provided by engineer. */
|
||||
"%lld file(s) with total size of %@" = "%lld файл(ов) общим размером %@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld group events" = "%lld событий";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld members" = "Членов группы: %lld";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld messages blocked" = "%lld сообщений заблокировано";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld messages marked deleted" = "%lld сообщений помечено удалёнными";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld messages moderated by %@" = "%lld сообщений модерировано членом %@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"%lld minutes" = "%lld минуты";
|
||||
|
||||
@ -229,6 +259,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"~strike~" = "\\~зачеркнуть~";
|
||||
|
||||
/* time to disappear */
|
||||
"0 sec" = "0 сек";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"0s" = "0с";
|
||||
|
||||
@ -371,6 +404,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"All messages will be deleted - this cannot be undone! The messages will be deleted ONLY for you." = "Все сообщения будут удалены - это действие нельзя отменить! Сообщения будут удалены только для Вас.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"All new messages from %@ will be hidden!" = "Все новые сообщения от %@ будут скрыты!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"All your contacts will remain connected." = "Все контакты, которые соединились через этот адрес, сохранятся.";
|
||||
|
||||
@ -434,6 +470,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Already connected?" = "Соединение уже установлено?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Already connecting!" = "Уже соединяется!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Already joining the group!" = "Вступление в группу уже начато!";
|
||||
|
||||
/* pref value */
|
||||
"always" = "всегда";
|
||||
|
||||
@ -443,6 +485,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"An empty chat profile with the provided name is created, and the app opens as usual." = "Будет создан пустой профиль чата с указанным именем, и приложение откроется в обычном режиме.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"and %lld other events" = "и %lld других событий";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Answer call" = "Принять звонок";
|
||||
|
||||
@ -512,6 +557,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Back" = "Назад";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Bad desktop address" = "Неверный адрес компьютера";
|
||||
|
||||
/* integrity error chat item */
|
||||
"bad message hash" = "ошибка хэш сообщения";
|
||||
|
||||
@ -524,9 +572,27 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Bad message ID" = "Ошибка ID сообщения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better groups" = "Улучшенные группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Better messages" = "Улучшенные сообщения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block" = "Заблокировать";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block group members" = "Блокируйте членов группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member" = "Заблокировать члена группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Block member?" = "Заблокировать члена группы?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"blocked" = "заблокировано";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"bold" = "жирный";
|
||||
|
||||
@ -723,9 +789,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connect incognito" = "Соединиться Инкогнито";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to desktop" = "Подключиться к компьютеру";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connect to SimpleX Chat developers." = "соединитесь с разработчиками.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to yourself?" = "Соединиться с самим собой?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to yourself?\nThis is your own one-time link!" = "Соединиться с самим собой?\nЭто ваша собственная одноразовая ссылка!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect to yourself?\nThis is your own SimpleX address!" = "Соединиться с самим собой?\nЭто ваш собственный адрес SimpleX!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect via contact address" = "Соединиться через адрес";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect via link" = "Соединиться через ссылку";
|
||||
|
||||
@ -735,9 +816,21 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connect via one-time link" = "Соединиться через одноразовую ссылку";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connect with %@" = "Соединиться с %@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connected" = "соединение установлено";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected desktop" = "Подключенный компьютер";
|
||||
|
||||
/* rcv group event chat item */
|
||||
"connected directly" = "соединен(а) напрямую";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connected to desktop" = "Компьютер подключен";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"connecting" = "соединяется";
|
||||
|
||||
@ -762,6 +855,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting server… (error: %@)" = "Устанавливается соединение с сервером… (ошибка: %@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connecting to desktop" = "Подключение к компьютеру";
|
||||
|
||||
/* chat list item title */
|
||||
"connecting…" = "соединяется…";
|
||||
|
||||
@ -780,6 +876,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Connection request sent!" = "Запрос на соединение отправлен!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection terminated" = "Подключение прервано";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Connection timeout" = "Превышено время соединения";
|
||||
|
||||
@ -828,15 +927,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Core version: v%@" = "Версия ядра: v%@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Correct name to %@?" = "Исправить имя на %@?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create" = "Создать";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create a group using a random profile." = "Создайте группу, используя случайный профиль.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create an address to let people connect with you." = "Создайте адрес, чтобы можно было соединиться с вами.";
|
||||
|
||||
/* server test step */
|
||||
"Create file" = "Создание файла";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create group" = "Создать группу";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create group link" = "Создать ссылку группы";
|
||||
|
||||
@ -849,6 +957,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Create one-time invitation link" = "Создать ссылку-приглашение";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Create profile" = "Создать профиль";
|
||||
|
||||
/* server test step */
|
||||
"Create queue" = "Создание очереди";
|
||||
|
||||
@ -963,6 +1074,9 @@
|
||||
/* chat item action */
|
||||
"Delete" = "Удалить";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete %lld messages?" = "Удалить %lld сообщений?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete address" = "Удалить адрес";
|
||||
|
||||
@ -975,6 +1089,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Delete all files" = "Удалить все файлы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete and notify contact" = "Удалить и уведомить контакт";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete archive" = "Удалить архив";
|
||||
|
||||
@ -996,6 +1113,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Delete Contact" = "Удалить контакт";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete contact?\nThis cannot be undone!" = "Удалить контакт?\nЭто не может быть отменено!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Delete database" = "Удалить данные чата";
|
||||
|
||||
@ -1071,6 +1191,9 @@
|
||||
/* copied message info */
|
||||
"Deleted at: %@" = "Удалено: %@";
|
||||
|
||||
/* rcv direct event chat item */
|
||||
"deleted contact" = "удалил(а) контакт";
|
||||
|
||||
/* rcv group event chat item */
|
||||
"deleted group" = "удалил(а) группу";
|
||||
|
||||
@ -1086,6 +1209,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Description" = "Описание";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop address" = "Адрес компьютера";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop app version %@ is not compatible with this app." = "Версия настольного приложения %@ несовместима с этим приложением.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Desktop devices" = "Компьютеры";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Develop" = "Для разработчиков";
|
||||
|
||||
@ -1149,6 +1281,9 @@
|
||||
/* server test step */
|
||||
"Disconnect" = "Разрыв соединения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Disconnect desktop?" = "Отключить компьютер?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Discover and join groups" = "Найдите и вступите в группы";
|
||||
|
||||
@ -1287,6 +1422,12 @@
|
||||
/* chat item text */
|
||||
"encryption re-negotiation allowed for %@" = "новое соглашение о шифровании разрешено для %@";
|
||||
|
||||
/* message decrypt error item */
|
||||
"Encryption re-negotiation error" = "Ошибка нового соглашения о шифровании";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Encryption re-negotiation failed." = "Ошибка нового соглашения о шифровании.";
|
||||
|
||||
/* chat item text */
|
||||
"encryption re-negotiation required" = "требуется новое соглашение о шифровании";
|
||||
|
||||
@ -1302,6 +1443,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Enter correct passphrase." = "Введите правильный пароль.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter group name…" = "Введите имя группы…";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter Passcode" = "Введите Код";
|
||||
|
||||
@ -1314,12 +1458,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Enter server manually" = "Ввести сервер вручную";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter this device name…" = "Введите имя этого устройства…";
|
||||
|
||||
/* placeholder */
|
||||
"Enter welcome message…" = "Введите приветственное сообщение…";
|
||||
|
||||
/* placeholder */
|
||||
"Enter welcome message… (optional)" = "Введите приветственное сообщение... (опционально)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Enter your name…" = "Введите ваше имя…";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"error" = "ошибка";
|
||||
|
||||
@ -1356,6 +1506,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Error creating group link" = "Ошибка при создании ссылки группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Error creating member contact" = "Ошибка создания контакта с членом группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Error creating profile!" = "Ошибка создания профиля!";
|
||||
|
||||
@ -1434,6 +1587,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Error sending email" = "Ошибка отправки email";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Error sending member contact invitation" = "Ошибка отправки приглашения члену группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Error sending message" = "Ошибка при отправке сообщения";
|
||||
|
||||
@ -1485,6 +1641,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Exit without saving" = "Выйти без сохранения";
|
||||
|
||||
/* chat item action */
|
||||
"Expand" = "Раскрыть";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Export database" = "Экспорт архива чата";
|
||||
|
||||
@ -1503,6 +1662,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Fast and no wait until the sender is online!" = "Быстрые и не нужно ждать, когда отправитель онлайн!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Faster joining and more reliable messages." = "Быстрое вступление и надежная доставка сообщений.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Favorite" = "Избранный";
|
||||
|
||||
@ -1572,6 +1734,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Full name:" = "Полное имя:";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Fully decentralized – visible only to members." = "Группа полностью децентрализована – она видна только членам.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Fully re-implemented - work in background!" = "Полностью обновлены - работают в фоне!";
|
||||
|
||||
@ -1584,6 +1749,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Group" = "Группа";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Group already exists" = "Группа уже существует";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Group already exists!" = "Группа уже существует!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"group deleted" = "группа удалена";
|
||||
|
||||
@ -1755,6 +1926,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito" = "Инкогнито";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito groups" = "Инкогнито группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incognito mode" = "Режим Инкогнито";
|
||||
|
||||
@ -1782,6 +1956,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible database version" = "Несовместимая версия базы данных";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Incompatible version" = "Несовместимая версия";
|
||||
|
||||
/* PIN entry */
|
||||
"Incorrect passcode" = "Неправильный код";
|
||||
|
||||
@ -1821,6 +1998,9 @@
|
||||
/* invalid chat item */
|
||||
"invalid data" = "ошибка данных";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Invalid name!" = "Неверное имя!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Invalid server address!" = "Ошибка в адресе сервера!";
|
||||
|
||||
@ -1899,12 +2079,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Join group" = "Вступить в группу";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Join group?" = "Вступить в группу?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Join incognito" = "Вступить инкогнито";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Join with current profile" = "Вступить с активным профилем";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Join your group?\nThis is your link for group %@!" = "Вступить в вашу группу?\nЭто ваша ссылка на группу %@!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Joining group" = "Вступление в группу";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep the app open to use it from desktop" = "Оставьте приложение открытым, чтобы использовать его с компьютера";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Keep your connections" = "Сохраните Ваши соединения";
|
||||
|
||||
@ -1941,6 +2133,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Limitations" = "Ограничения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Link mobile and desktop apps! 🔗" = "Свяжите мобильное и настольное приложения! 🔗";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktop options" = "Опции связанных компьютеров";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Linked desktops" = "Связанные компьютеры";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"LIVE" = "LIVE";
|
||||
|
||||
@ -2046,6 +2247,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Messages & files" = "Сообщения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Messages from %@ will be shown!" = "Сообщения от %@ будут показаны!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Migrating database archive…" = "Данные чата перемещаются…";
|
||||
|
||||
@ -2288,12 +2492,18 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Only your contact can send voice messages." = "Только Ваш контакт может отправлять голосовые сообщения.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Open" = "Открыть";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Open chat" = "Открыть чат";
|
||||
|
||||
/* authentication reason */
|
||||
"Open chat console" = "Открыть консоль";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Open group" = "Открыть группу";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Open Settings" = "Открыть Настройки";
|
||||
|
||||
@ -2330,6 +2540,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Paste" = "Вставить";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste desktop address" = "Вставить адрес компьютера";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Paste image" = "Вставить изображение";
|
||||
|
||||
@ -2426,6 +2639,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Profile image" = "Аватар";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Profile name" = "Имя профиля";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Profile name:" = "Имя профиля:";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Profile password" = "Пароль профиля";
|
||||
|
||||
@ -2591,6 +2810,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Renegotiate encryption?" = "Пересогласовать шифрование?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Repeat connection request?" = "Повторить запрос на соединение?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Repeat join request?" = "Повторить запрос на вступление?";
|
||||
|
||||
/* chat item action */
|
||||
"Reply" = "Ответить";
|
||||
|
||||
@ -2702,6 +2927,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code" = "Сканировать QR код";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan QR code from desktop" = "Сканировать QR код с компьютера";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Scan security code from your contact's app." = "Сканируйте код безопасности из приложения контакта.";
|
||||
|
||||
@ -2756,9 +2984,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Send delivery receipts to" = "Отправка отчётов о доставке";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"send direct message" = "отправьте сообщение";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Send direct message" = "Отправить сообщение";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Send direct message to connect" = "Отправьте сообщение чтобы соединиться";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Send disappearing message" = "Отправить исчезающее сообщение";
|
||||
|
||||
@ -2840,6 +3074,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Servers" = "Серверы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Session code" = "Код сессии";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Set 1 day" = "Установить 1 день";
|
||||
|
||||
@ -3026,6 +3263,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Tap to activate profile." = "Нажмите, чтобы сделать профиль активным.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Tap to Connect" = "Нажмите чтобы соединиться";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Tap to join" = "Нажмите, чтобы вступить";
|
||||
|
||||
@ -3146,12 +3386,21 @@
|
||||
/* notification title */
|
||||
"this contact" = "этот контакт";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This device name" = "Имя этого устройства";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This group has over %lld members, delivery receipts are not sent." = "В группе более %lld членов, отчёты о доставке выключены.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This group no longer exists." = "Эта группа больше не существует.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This is your own one-time link!" = "Это ваша собственная одноразовая ссылка!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This is your own SimpleX address!" = "Это ваш собственный адрес SimpleX!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"This setting applies to messages in your current chat profile **%@**." = "Эта настройка применяется к сообщениям в Вашем текущем профиле чата **%@**.";
|
||||
|
||||
@ -3161,6 +3410,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"To connect, your contact can scan QR code or use the link in the app." = "Чтобы соединиться с Вами, Ваш контакт может отсканировать QR-код или использовать ссылку в приложении.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To hide unwanted messages." = "Чтобы скрыть нежелательные сообщения.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"To make a new connection" = "Чтобы соединиться";
|
||||
|
||||
@ -3209,6 +3461,15 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Unable to record voice message" = "Невозможно записать голосовое сообщение";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unblock" = "Разблокировать";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unblock member" = "Разблокировать члена группы";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unblock member?" = "Разблокировать члена группы?";
|
||||
|
||||
/* item status description */
|
||||
"Unexpected error: %@" = "Неожиданная ошибка: %@";
|
||||
|
||||
@ -3248,6 +3509,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Unless your contact deleted the connection or this link was already used, it might be a bug - please report it.\nTo connect, please ask your contact to create another connection link and check that you have a stable network connection." = "Возможно, Ваш контакт удалил ссылку, или она уже была использована. Если это не так, то это может быть ошибкой - пожалуйста, сообщите нам об этом.\nЧтобы установить соединение, попросите Ваш контакт создать еще одну ссылку и проверьте Ваше соединение с сетью.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink" = "Забыть";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlink desktop?" = "Забыть компьютер?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Unlock" = "Разблокировать";
|
||||
|
||||
@ -3302,6 +3569,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Use for new connections" = "Использовать для новых соединений";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use from desktop" = "Использовать с компьютера";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Use iOS call interface" = "Использовать интерфейс iOS для звонков";
|
||||
|
||||
@ -3323,12 +3593,24 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Using SimpleX Chat servers." = "Используются серверы, предоставленные SimpleX Chat.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@" = "v%@";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"v%@ (%@)" = "v%@ (%@)";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify code with desktop" = "Сверьте код с компьютером";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection" = "Проверить соединение";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connection security" = "Проверить безопасность соединения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify connections" = "Проверять соединения";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Verify security code" = "Подтвердить код безопасности";
|
||||
|
||||
@ -3347,6 +3629,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"via relay" = "через relay сервер";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Via secure quantum resistant protocol." = "Через безопасный квантово-устойчивый протокол.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Video call" = "Видеозвонок";
|
||||
|
||||
@ -3455,6 +3740,27 @@
|
||||
/* No comment provided by engineer. */
|
||||
"You are already connected to %@." = "Вы уже соединены с контактом %@.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already connecting to %@." = "Вы уже соединяетесь с %@.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already connecting via this one-time link!" = "Вы уже соединяетесь по этой одноразовой ссылке!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already in group %@." = "Вы уже состоите в группе %@.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already joining the group %@." = "Вы уже вступаете в группу %@.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already joining the group via this link!" = "Вы уже вступаете в группу по этой ссылке!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already joining the group via this link." = "Вы уже вступаете в группу по этой ссылке.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are already joining the group!\nRepeat join request?" = "Вы уже вступаете в группу!\nПовторить запрос на вступление?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You are connected to the server used to receive messages from this contact." = "Установлено соединение с сервером, через который Вы получаете сообщения от этого контакта.";
|
||||
|
||||
@ -3530,6 +3836,12 @@
|
||||
/* No comment provided by engineer. */
|
||||
"You could not be verified; please try again." = "Верификация не удалась; пожалуйста, попробуйте ещё раз.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You have already requested connection via this address!" = "Вы уже запросили соединение через этот адрес!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You have already requested connection!\nRepeat connection request?" = "Вы уже запросили соединение!\nПовторить запрос?";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You have no chats" = "У Вас нет чатов";
|
||||
|
||||
@ -3572,6 +3884,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"You will be connected to group when the group host's device is online, please wait or check later!" = "Соединение с группой будет установлено, когда хост группы будет онлайн. Пожалуйста, подождите или проверьте позже!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You will be connected when group link host's device is online, please wait or check later!" = "Соединение будет установлено, когда владелец ссылки группы будет онлайн. Пожалуйста, подождите или проверьте позже!";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You will be connected when your connection request is accepted, please wait or check later!" = "Соединение будет установлено, когда Ваш запрос будет принят. Пожалуйста, подождите или проверьте позже!";
|
||||
|
||||
@ -3581,6 +3896,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"You will be required to authenticate when you start or resume the app after 30 seconds in background." = "Вы будете аутентифицированы при запуске и возобновлении приложения, которое было 30 секунд в фоновом режиме.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You will connect to all group members." = "Вы соединитесь со всеми членами группы.";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"You will still receive calls and notifications from muted profiles when they are active." = "Вы все равно получите звонки и уведомления в профилях без звука, когда они активные.";
|
||||
|
||||
@ -3644,6 +3962,9 @@
|
||||
/* No comment provided by engineer. */
|
||||
"Your privacy" = "Конфиденциальность";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Your profile" = "Ваш профиль";
|
||||
|
||||
/* No comment provided by engineer. */
|
||||
"Your profile **%@** will be shared." = "Будет отправлен Ваш профиль **%@**.";
|
||||
|
||||
|
@ -7,6 +7,9 @@
|
||||
/* Privacy - Face ID Usage Description */
|
||||
"NSFaceIDUsageDescription" = "SimpleX использует Face ID для аутентификации";
|
||||
|
||||
/* Privacy - Local Network Usage Description */
|
||||
"NSLocalNetworkUsageDescription" = "SimpleX использует доступ к локальной сети, чтобы разрешить использование профиля чата через компьютер в той же сети.";
|
||||
|
||||
/* Privacy - Microphone Usage Description */
|
||||
"NSMicrophoneUsageDescription" = "SimpleX использует микрофон для аудио и видео звонков, и для записи голосовых сообщений.";
|
||||
|
||||
|
@ -4,6 +4,7 @@ import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.painter.Painter
|
||||
import com.google.accompanist.insets.navigationBarsWithImePadding
|
||||
import java.io.File
|
||||
|
||||
actual fun Modifier.navigationBarsWithImePadding(): Modifier = navigationBarsWithImePadding()
|
||||
|
||||
@ -19,7 +20,7 @@ actual fun ProvideWindowInsets(
|
||||
@Composable
|
||||
actual fun Modifier.desktopOnExternalDrag(
|
||||
enabled: Boolean,
|
||||
onFiles: (List<String>) -> Unit,
|
||||
onFiles: (List<File>) -> Unit,
|
||||
onImage: (Painter) -> Unit,
|
||||
onText: (String) -> Unit
|
||||
): Modifier = this
|
||||
|
@ -71,7 +71,7 @@ actual class VideoPlayer actual constructor(
|
||||
private fun start(seek: Long? = null, onProgressUpdate: (position: Long?, state: TrackState) -> Unit): Boolean {
|
||||
val filepath = getAppFilePath(uri)
|
||||
if (filepath == null || !File(filepath).exists()) {
|
||||
Log.e(TAG, "No such file: $uri")
|
||||
Log.e(TAG, "No such file: $filepath")
|
||||
brokenVideo.value = true
|
||||
return false
|
||||
}
|
||||
|
@ -65,7 +65,7 @@ fun MainScreen() {
|
||||
!chatModel.controller.appPrefs.laNoticeShown.get()
|
||||
&& showAdvertiseLAAlert
|
||||
&& chatModel.controller.appPrefs.onboardingStage.get() == OnboardingStage.OnboardingComplete
|
||||
&& chatModel.chats.isNotEmpty()
|
||||
&& chatModel.chats.count() > 1
|
||||
&& chatModel.activeCallInvitation.value == null
|
||||
) {
|
||||
AppLock.showLANotice(ChatModel.controller.appPrefs.laNoticeShown) }
|
||||
|
@ -3,6 +3,7 @@ package chat.simplex.common.model
|
||||
import androidx.compose.material.*
|
||||
import androidx.compose.runtime.*
|
||||
import androidx.compose.runtime.snapshots.SnapshotStateList
|
||||
import androidx.compose.runtime.snapshots.SnapshotStateMap
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.text.SpanStyle
|
||||
import androidx.compose.ui.text.font.*
|
||||
@ -27,7 +28,6 @@ import kotlinx.serialization.encoding.Encoder
|
||||
import kotlinx.serialization.json.*
|
||||
import java.io.File
|
||||
import java.net.URI
|
||||
import java.net.URLDecoder
|
||||
import java.time.format.DateTimeFormatter
|
||||
import java.time.format.FormatStyle
|
||||
import java.util.*
|
||||
@ -113,7 +113,7 @@ object ChatModel {
|
||||
val currentRemoteHost = mutableStateOf<RemoteHostInfo?>(null)
|
||||
val remoteHostId: Long? @Composable get() = remember { currentRemoteHost }.value?.remoteHostId
|
||||
fun remoteHostId(): Long? = currentRemoteHost.value?.remoteHostId
|
||||
val newRemoteHostPairing = mutableStateOf<Pair<RemoteHostInfo?, RemoteHostSessionState>?>(null)
|
||||
val remoteHostPairing = mutableStateOf<Pair<RemoteHostInfo?, RemoteHostSessionState>?>(null)
|
||||
val remoteCtrlSession = mutableStateOf<RemoteCtrlSession?>(null)
|
||||
|
||||
fun getUser(userId: Long): User? = if (currentUser.value?.userId == userId) {
|
||||
@ -638,6 +638,9 @@ data class User(
|
||||
|
||||
val addressShared: Boolean = profile.contactLink != null
|
||||
|
||||
fun updateRemoteHostId(rh: Long?): User =
|
||||
if (rh == null) this else this.copy(remoteHostId = rh)
|
||||
|
||||
companion object {
|
||||
val sampleData = User(
|
||||
remoteHostId = null,
|
||||
@ -2301,7 +2304,7 @@ data class CIFile(
|
||||
sent = fileStatus.sent,
|
||||
fileSource = fileSource
|
||||
)
|
||||
cachedRemoteFileRequests.add(fileSource)
|
||||
cachedRemoteFileRequests[fileSource] = false
|
||||
val showAlert = fileSize > 5_000_000 && allowToShowAlert
|
||||
if (showAlert) {
|
||||
AlertManager.shared.showAlertMsgWithProgress(
|
||||
@ -2310,7 +2313,7 @@ data class CIFile(
|
||||
)
|
||||
}
|
||||
val res = chatModel.controller.getRemoteFile(rh.remoteHostId, rf)
|
||||
cachedRemoteFileRequests.remove(fileSource)
|
||||
cachedRemoteFileRequests[fileSource] = res
|
||||
if (showAlert) {
|
||||
AlertManager.shared.hideAlert()
|
||||
}
|
||||
@ -2327,7 +2330,7 @@ data class CIFile(
|
||||
): CIFile =
|
||||
CIFile(fileId = fileId, fileName = fileName, fileSize = fileSize, fileSource = if (filePath == null) null else CryptoFile.plain(filePath), fileStatus = fileStatus, fileProtocol = FileProtocol.XFTP)
|
||||
|
||||
val cachedRemoteFileRequests = SnapshotStateList<CryptoFile>()
|
||||
val cachedRemoteFileRequests = SnapshotStateMap<CryptoFile, Boolean>()
|
||||
}
|
||||
}
|
||||
|
||||
@ -2360,7 +2363,7 @@ data class CryptoFile(
|
||||
companion object {
|
||||
fun plain(f: String): CryptoFile = CryptoFile(f, null)
|
||||
|
||||
fun desktopPlain(f: URI): CryptoFile = CryptoFile(URLDecoder.decode(f.rawPath, "UTF-8"), null)
|
||||
fun desktopPlain(f: URI): CryptoFile = CryptoFile(f.toFile().absolutePath, null)
|
||||
}
|
||||
}
|
||||
|
||||
@ -2918,7 +2921,7 @@ enum class NotificationPreviewMode {
|
||||
}
|
||||
|
||||
data class RemoteCtrlSession(
|
||||
val ctrlAppInfo: CtrlAppInfo,
|
||||
val ctrlAppInfo: CtrlAppInfo?,
|
||||
val appVersion: String,
|
||||
val sessionState: UIRemoteCtrlSessionState
|
||||
) {
|
||||
@ -2936,14 +2939,17 @@ data class RemoteCtrlSession(
|
||||
@Serializable
|
||||
sealed class RemoteCtrlSessionState {
|
||||
@Serializable @SerialName("starting") object Starting: RemoteCtrlSessionState()
|
||||
@Serializable @SerialName("searching") object Searching: RemoteCtrlSessionState()
|
||||
@Serializable @SerialName("connecting") object Connecting: RemoteCtrlSessionState()
|
||||
@Serializable @SerialName("pendingConfirmation") data class PendingConfirmation(val sessionCode: String): RemoteCtrlSessionState()
|
||||
@Serializable @SerialName("connected") data class Connected(val sessionCode: String): RemoteCtrlSessionState()
|
||||
}
|
||||
|
||||
sealed class UIRemoteCtrlSessionState {
|
||||
@Serializable @SerialName("starting") object Starting: UIRemoteCtrlSessionState()
|
||||
@Serializable @SerialName("connecting") data class Connecting(val remoteCtrl_: RemoteCtrlInfo? = null): UIRemoteCtrlSessionState()
|
||||
@Serializable @SerialName("pendingConfirmation") data class PendingConfirmation(val remoteCtrl_: RemoteCtrlInfo? = null, val sessionCode: String): UIRemoteCtrlSessionState()
|
||||
@Serializable @SerialName("connected") data class Connected(val remoteCtrl: RemoteCtrlInfo, val sessionCode: String): UIRemoteCtrlSessionState()
|
||||
object Starting: UIRemoteCtrlSessionState()
|
||||
object Searching: UIRemoteCtrlSessionState()
|
||||
data class Found(val remoteCtrl: RemoteCtrlInfo, val compatible: Boolean): UIRemoteCtrlSessionState()
|
||||
data class Connecting(val remoteCtrl_: RemoteCtrlInfo? = null): UIRemoteCtrlSessionState()
|
||||
data class PendingConfirmation(val remoteCtrl_: RemoteCtrlInfo? = null, val sessionCode: String): UIRemoteCtrlSessionState()
|
||||
data class Connected(val remoteCtrl: RemoteCtrlInfo, val sessionCode: String): UIRemoteCtrlSessionState()
|
||||
}
|
||||
|
@ -170,6 +170,7 @@ class AppPreferences {
|
||||
|
||||
val confirmRemoteSessions = mkBoolPreference(SHARED_PREFS_CONFIRM_REMOTE_SESSIONS, false)
|
||||
val connectRemoteViaMulticast = mkBoolPreference(SHARED_PREFS_CONNECT_REMOTE_VIA_MULTICAST, false)
|
||||
val connectRemoteViaMulticastAuto = mkBoolPreference(SHARED_PREFS_CONNECT_REMOTE_VIA_MULTICAST_AUTO, true)
|
||||
val offerRemoteMulticast = mkBoolPreference(SHARED_PREFS_OFFER_REMOTE_MULTICAST, true)
|
||||
|
||||
private fun mkIntPreference(prefName: String, default: Int) =
|
||||
@ -314,6 +315,7 @@ class AppPreferences {
|
||||
private const val SHARED_PREFS_DEVICE_NAME_FOR_REMOTE_ACCESS = "DeviceNameForRemoteAccess"
|
||||
private const val SHARED_PREFS_CONFIRM_REMOTE_SESSIONS = "ConfirmRemoteSessions"
|
||||
private const val SHARED_PREFS_CONNECT_REMOTE_VIA_MULTICAST = "ConnectRemoteViaMulticast"
|
||||
private const val SHARED_PREFS_CONNECT_REMOTE_VIA_MULTICAST_AUTO = "ConnectRemoteViaMulticastAuto"
|
||||
private const val SHARED_PREFS_OFFER_REMOTE_MULTICAST = "OfferRemoteMulticast"
|
||||
}
|
||||
}
|
||||
@ -468,7 +470,7 @@ object ChatController {
|
||||
|
||||
suspend fun apiGetActiveUser(rh: Long?): User? {
|
||||
val r = sendCmd(rh, CC.ShowActiveUser())
|
||||
if (r is CR.ActiveUser) return r.user
|
||||
if (r is CR.ActiveUser) return r.user.updateRemoteHostId(rh)
|
||||
Log.d(TAG, "apiGetActiveUser: ${r.responseType} ${r.details}")
|
||||
chatModel.userCreated.value = false
|
||||
return null
|
||||
@ -476,7 +478,7 @@ object ChatController {
|
||||
|
||||
suspend fun apiCreateActiveUser(rh: Long?, p: Profile?, sameServers: Boolean = false, pastTimestamp: Boolean = false): User? {
|
||||
val r = sendCmd(rh, CC.CreateActiveUser(p, sameServers = sameServers, pastTimestamp = pastTimestamp))
|
||||
if (r is CR.ActiveUser) return r.user
|
||||
if (r is CR.ActiveUser) return r.user.updateRemoteHostId(rh)
|
||||
else if (
|
||||
r is CR.ChatCmdError && r.chatError is ChatError.ChatErrorStore && r.chatError.storeError is StoreError.DuplicateName ||
|
||||
r is CR.ChatCmdError && r.chatError is ChatError.ChatErrorChat && r.chatError.errorType is ChatErrorType.UserExists
|
||||
@ -501,7 +503,7 @@ object ChatController {
|
||||
|
||||
suspend fun apiSetActiveUser(rh: Long?, userId: Long, viewPwd: String?): User {
|
||||
val r = sendCmd(rh, CC.ApiSetActiveUser(userId, viewPwd))
|
||||
if (r is CR.ActiveUser) return if (rh == null) r.user else r.user.copy(remoteHostId = rh)
|
||||
if (r is CR.ActiveUser) return r.user.updateRemoteHostId(rh)
|
||||
Log.d(TAG, "apiSetActiveUser: ${r.responseType} ${r.details}")
|
||||
throw Exception("failed to set the user as active ${r.responseType} ${r.details}")
|
||||
}
|
||||
@ -538,7 +540,7 @@ object ChatController {
|
||||
|
||||
private suspend fun setUserPrivacy(rh: Long?, cmd: CC): User {
|
||||
val r = sendCmd(rh, cmd)
|
||||
if (r is CR.UserPrivacy) return if (rh == null) r.updatedUser else r.updatedUser.copy(remoteHostId = rh)
|
||||
if (r is CR.UserPrivacy) return r.updatedUser.updateRemoteHostId(rh)
|
||||
else throw Exception("Failed to change user privacy: ${r.responseType} ${r.details}")
|
||||
}
|
||||
|
||||
@ -989,7 +991,7 @@ object ChatController {
|
||||
val userId = try { currentUserId("apiSetProfileAddress") } catch (e: Exception) { return null }
|
||||
return when (val r = sendCmd(rh, CC.ApiSetProfileAddress(userId, on))) {
|
||||
is CR.UserProfileNoChange -> null
|
||||
is CR.UserProfileUpdated -> r.user
|
||||
is CR.UserProfileUpdated -> r.user.updateRemoteHostId(rh)
|
||||
else -> throw Exception("failed to set profile address: ${r.responseType} ${r.details}")
|
||||
}
|
||||
}
|
||||
@ -1032,7 +1034,7 @@ object ChatController {
|
||||
suspend fun apiDeleteUserAddress(rh: Long?): User? {
|
||||
val userId = try { currentUserId("apiDeleteUserAddress") } catch (e: Exception) { return null }
|
||||
val r = sendCmd(rh, CC.ApiDeleteMyAddress(userId))
|
||||
if (r is CR.UserContactLinkDeleted) return r.user
|
||||
if (r is CR.UserContactLinkDeleted) return r.user.updateRemoteHostId(rh)
|
||||
Log.e(TAG, "apiDeleteUserAddress bad response: ${r.responseType} ${r.details}")
|
||||
return null
|
||||
}
|
||||
@ -1392,7 +1394,7 @@ object ChatController {
|
||||
chatModel.remoteHosts.addAll(hosts)
|
||||
}
|
||||
|
||||
suspend fun startRemoteHost(rhId: Long?, multicast: Boolean = false): Triple<RemoteHostInfo?, String, String>? {
|
||||
suspend fun startRemoteHost(rhId: Long?, multicast: Boolean = true): Triple<RemoteHostInfo?, String, String>? {
|
||||
val r = sendCmd(null, CC.StartRemoteHost(rhId, multicast))
|
||||
if (r is CR.RemoteHostStarted) return Triple(r.remoteHost_, r.invitation, r.ctrlPort)
|
||||
apiErrorAlert("startRemoteHost", generalGetString(MR.strings.error_alert_title), r)
|
||||
@ -1428,18 +1430,29 @@ object ChatController {
|
||||
return null
|
||||
}
|
||||
|
||||
suspend fun getRemoteFile(rhId: Long, file: RemoteFile): Boolean = sendCommandOkResp(null, CC.GetRemoteFile(rhId, file))
|
||||
suspend fun getRemoteFile(rhId: Long, file: RemoteFile): Boolean = sendCmd(null, CC.GetRemoteFile(rhId, file)) is CR.CmdOk
|
||||
|
||||
suspend fun connectRemoteCtrl(desktopAddress: String): Pair<SomeRemoteCtrl?, CR.ChatCmdError?> {
|
||||
val r = sendCmd(null, CC.ConnectRemoteCtrl(desktopAddress))
|
||||
if (r is CR.RemoteCtrlConnecting) return SomeRemoteCtrl(r.remoteCtrl_, r.ctrlAppInfo, r.appVersion) to null
|
||||
else if (r is CR.ChatCmdError) return null to r
|
||||
else throw Exception("connectRemoteCtrl error: ${r.responseType} ${r.details}")
|
||||
return if (r is CR.RemoteCtrlConnecting) SomeRemoteCtrl(r.remoteCtrl_, r.ctrlAppInfo, r.appVersion) to null
|
||||
else if (r is CR.ChatCmdError) null to r
|
||||
else {
|
||||
apiErrorAlert("connectRemoteCtrl", generalGetString(MR.strings.error_alert_title), r)
|
||||
null to null
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun findKnownRemoteCtrl(): Boolean = sendCommandOkResp(null, CC.FindKnownRemoteCtrl())
|
||||
|
||||
suspend fun confirmRemoteCtrl(rcId: Long): Boolean = sendCommandOkResp(null, CC.ConfirmRemoteCtrl(rcId))
|
||||
suspend fun confirmRemoteCtrl(rcId: Long): Pair<SomeRemoteCtrl?, CR.ChatCmdError?> {
|
||||
val r = sendCmd(null, CC.ConfirmRemoteCtrl(remoteCtrlId = rcId))
|
||||
return if (r is CR.RemoteCtrlConnecting) SomeRemoteCtrl(r.remoteCtrl_, r.ctrlAppInfo, r.appVersion) to null
|
||||
else if (r is CR.ChatCmdError) null to r
|
||||
else {
|
||||
apiErrorAlert("confirmRemoteCtrl", generalGetString(MR.strings.error_alert_title), r)
|
||||
null to null
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun verifyRemoteCtrlSession(sessionCode: String): RemoteCtrlInfo? {
|
||||
val r = sendCmd(null, CC.VerifyRemoteCtrlSession(sessionCode))
|
||||
@ -1836,7 +1849,7 @@ object ChatController {
|
||||
is CR.GroupMemberRatchetSync ->
|
||||
chatModel.updateGroupMemberConnectionStats(rhId, r.groupInfo, r.member, r.ratchetSyncProgress.connectionStats)
|
||||
is CR.RemoteHostSessionCode -> {
|
||||
chatModel.newRemoteHostPairing.value = r.remoteHost_ to RemoteHostSessionState.PendingConfirmation(r.sessionCode)
|
||||
chatModel.remoteHostPairing.value = r.remoteHost_ to RemoteHostSessionState.PendingConfirmation(r.sessionCode)
|
||||
}
|
||||
is CR.RemoteHostConnected -> {
|
||||
// TODO needs to update it instead in sessions
|
||||
@ -1845,7 +1858,7 @@ object ChatController {
|
||||
}
|
||||
is CR.RemoteHostStopped -> {
|
||||
val disconnectedHost = chatModel.remoteHosts.firstOrNull { it.remoteHostId == r.remoteHostId_ }
|
||||
chatModel.newRemoteHostPairing.value = null
|
||||
chatModel.remoteHostPairing.value = null
|
||||
if (disconnectedHost != null) {
|
||||
showToast(
|
||||
generalGetString(MR.strings.remote_host_was_disconnected_toast).format(disconnectedHost.hostDeviceName.ifEmpty { disconnectedHost.remoteHostId.toString() })
|
||||
@ -1857,8 +1870,15 @@ object ChatController {
|
||||
}
|
||||
}
|
||||
is CR.RemoteCtrlFound -> {
|
||||
// TODO multicast
|
||||
Log.d(TAG, "RemoteCtrlFound: ${r.remoteCtrl}")
|
||||
val sess = chatModel.remoteCtrlSession.value
|
||||
if (sess != null && sess.sessionState is UIRemoteCtrlSessionState.Searching) {
|
||||
val state = UIRemoteCtrlSessionState.Found(remoteCtrl = r.remoteCtrl, compatible = r.compatible)
|
||||
chatModel.remoteCtrlSession.value = RemoteCtrlSession(
|
||||
ctrlAppInfo = r.ctrlAppInfo_,
|
||||
appVersion = r.appVersion,
|
||||
sessionState = state
|
||||
)
|
||||
}
|
||||
}
|
||||
is CR.RemoteCtrlSessionCode -> {
|
||||
val state = UIRemoteCtrlSessionState.PendingConfirmation(remoteCtrl_ = r.remoteCtrl_, sessionCode = r.sessionCode)
|
||||
@ -1870,7 +1890,13 @@ object ChatController {
|
||||
chatModel.remoteCtrlSession.value = chatModel.remoteCtrlSession.value?.copy(sessionState = state)
|
||||
}
|
||||
is CR.RemoteCtrlStopped -> {
|
||||
switchToLocalSession()
|
||||
val sess = chatModel.remoteCtrlSession.value
|
||||
if (sess != null) {
|
||||
chatModel.remoteCtrlSession.value = null
|
||||
if (sess.sessionState is UIRemoteCtrlSessionState.Connected) {
|
||||
switchToLocalSession()
|
||||
}
|
||||
}
|
||||
}
|
||||
else ->
|
||||
Log.d(TAG , "unsupported event: ${r.responseType}")
|
||||
@ -2322,7 +2348,7 @@ sealed class CC {
|
||||
is DeleteRemoteHost -> "/delete remote host $remoteHostId"
|
||||
is StoreRemoteFile ->
|
||||
"/store remote file $remoteHostId " +
|
||||
(if (storeEncrypted == null) "" else " encrypt=${onOff(storeEncrypted)} ") +
|
||||
(if (storeEncrypted == null) "" else "encrypt=${onOff(storeEncrypted)} ") +
|
||||
localPath
|
||||
is GetRemoteFile -> "/get remote file $remoteHostId ${json.encodeToString(file)}"
|
||||
is ConnectRemoteCtrl -> "/connect remote ctrl $xrcpInvitation"
|
||||
@ -3782,7 +3808,7 @@ sealed class CR {
|
||||
@Serializable @SerialName("remoteFileStored") class RemoteFileStored(val remoteHostId: Long, val remoteFileSource: CryptoFile): CR()
|
||||
// remote events (mobile)
|
||||
@Serializable @SerialName("remoteCtrlList") class RemoteCtrlList(val remoteCtrls: List<RemoteCtrlInfo>): CR()
|
||||
@Serializable @SerialName("remoteCtrlFound") class RemoteCtrlFound(val remoteCtrl: RemoteCtrlInfo): CR()
|
||||
@Serializable @SerialName("remoteCtrlFound") class RemoteCtrlFound(val remoteCtrl: RemoteCtrlInfo, val ctrlAppInfo_: CtrlAppInfo?, val appVersion: String, val compatible: Boolean): CR()
|
||||
@Serializable @SerialName("remoteCtrlConnecting") class RemoteCtrlConnecting(val remoteCtrl_: RemoteCtrlInfo?, val ctrlAppInfo: CtrlAppInfo, val appVersion: String): CR()
|
||||
@Serializable @SerialName("remoteCtrlSessionCode") class RemoteCtrlSessionCode(val remoteCtrl_: RemoteCtrlInfo?, val sessionCode: String): CR()
|
||||
@Serializable @SerialName("remoteCtrlConnected") class RemoteCtrlConnected(val remoteCtrl: RemoteCtrlInfo): CR()
|
||||
@ -4080,7 +4106,11 @@ sealed class CR {
|
||||
is RemoteHostStopped -> "remote host ID: $remoteHostId_"
|
||||
is RemoteFileStored -> "remote host ID: $remoteHostId\nremoteFileSource:\n" + json.encodeToString(remoteFileSource)
|
||||
is RemoteCtrlList -> json.encodeToString(remoteCtrls)
|
||||
is RemoteCtrlFound -> json.encodeToString(remoteCtrl)
|
||||
is RemoteCtrlFound -> "remote ctrl: " + json.encodeToString(remoteCtrl) +
|
||||
"\nctrlAppInfo: " +
|
||||
(if (ctrlAppInfo_ == null) "null" else json.encodeToString(ctrlAppInfo_)) +
|
||||
"\nappVersion: $appVersion" +
|
||||
"\ncompatible: $compatible"
|
||||
is RemoteCtrlConnecting ->
|
||||
"remote ctrl: " +
|
||||
(if (remoteCtrl_ == null) "null" else json.encodeToString(remoteCtrl_)) +
|
||||
|
@ -7,6 +7,8 @@ import chat.simplex.common.views.helpers.generalGetString
|
||||
import chat.simplex.res.MR
|
||||
import java.io.*
|
||||
import java.net.URI
|
||||
import java.net.URLDecoder
|
||||
import java.net.URLEncoder
|
||||
|
||||
expect val dataDir: File
|
||||
expect val tmpDir: File
|
||||
@ -28,6 +30,10 @@ expect val remoteHostsDir: File
|
||||
|
||||
expect fun desktopOpenDatabaseDir()
|
||||
|
||||
fun createURIFromPath(absolutePath: String): URI = URI.create(URLEncoder.encode(absolutePath, "UTF-8"))
|
||||
|
||||
fun URI.toFile(): File = File(URLDecoder.decode(rawPath, "UTF-8").removePrefix("file:"))
|
||||
|
||||
fun copyFileToFile(from: File, to: URI, finally: () -> Unit) {
|
||||
try {
|
||||
to.outputStream().use { stream ->
|
||||
@ -92,7 +98,7 @@ fun getLoadedFileSource(file: CIFile?): CryptoFile? {
|
||||
|
||||
private fun fileReady(file: CIFile, filePath: String) =
|
||||
File(filePath).exists() &&
|
||||
!CIFile.cachedRemoteFileRequests.contains(file.fileSource)
|
||||
CIFile.cachedRemoteFileRequests[file.fileSource] != false
|
||||
&& File(filePath).length() >= file.fileSize
|
||||
|
||||
/**
|
||||
|
@ -3,6 +3,7 @@ package chat.simplex.common.platform
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.painter.Painter
|
||||
import java.io.File
|
||||
|
||||
expect fun Modifier.navigationBarsWithImePadding(): Modifier
|
||||
|
||||
@ -16,7 +17,7 @@ expect fun ProvideWindowInsets(
|
||||
@Composable
|
||||
expect fun Modifier.desktopOnExternalDrag(
|
||||
enabled: Boolean = true,
|
||||
onFiles: (List<String>) -> Unit = {},
|
||||
onFiles: (List<File>) -> Unit = {},
|
||||
onImage: (Painter) -> Unit = {},
|
||||
onText: (String) -> Unit = {}
|
||||
): Modifier
|
||||
|
@ -43,16 +43,13 @@ object VideoPlayerHolder {
|
||||
): VideoPlayer =
|
||||
players.getOrPut(uri to gallery) { VideoPlayer(uri, gallery, defaultPreview, defaultDuration, soundEnabled) }
|
||||
|
||||
fun enableSound(enable: Boolean, fileName: String?, gallery: Boolean): Boolean =
|
||||
player(fileName, gallery)?.enableSound(enable) == true
|
||||
|
||||
private fun player(fileName: String?, gallery: Boolean): VideoPlayer? {
|
||||
fileName ?: return null
|
||||
return players.values.firstOrNull { player -> player.uri.path?.endsWith(fileName) == true && player.gallery == gallery }
|
||||
private fun player(uri: URI?, gallery: Boolean): VideoPlayer? {
|
||||
uri ?: return null
|
||||
return players.values.firstOrNull { player -> player.uri == uri && player.gallery == gallery }
|
||||
}
|
||||
|
||||
fun release(uri: URI, gallery: Boolean, remove: Boolean) =
|
||||
player(uri.path, gallery)?.release(remove).run { }
|
||||
player(uri, gallery)?.release(remove).run { }
|
||||
|
||||
fun stopAll() {
|
||||
players.values.forEach { it.stop() }
|
||||
|
@ -501,7 +501,7 @@ fun ChatLayout(
|
||||
.fillMaxWidth()
|
||||
.desktopOnExternalDrag(
|
||||
enabled = !attachmentDisabled.value && rememberUpdatedState(chat.userCanSend).value,
|
||||
onFiles = { paths -> composeState.onFilesAttached(paths.map { URI.create(it) }) },
|
||||
onFiles = { paths -> composeState.onFilesAttached(paths.map { it.toURI() }) },
|
||||
onImage = {
|
||||
// TODO: file is not saved anywhere?!
|
||||
val tmpFile = File.createTempFile("image", ".bmp", tmpDir)
|
||||
|
@ -850,6 +850,7 @@ fun ComposeView(
|
||||
deleteUnusedFiles()
|
||||
}
|
||||
chatModel.removeLiveDummy()
|
||||
CIFile.cachedRemoteFileRequests.clear()
|
||||
}
|
||||
|
||||
val timedMessageAllowed = remember(chat.chatInfo) { chat.chatInfo.featureEnabled(ChatFeature.TimedMessages) }
|
||||
|
@ -133,7 +133,7 @@ fun ChatItemView(
|
||||
}
|
||||
|
||||
fun deleteMessageQuestionText(): String {
|
||||
return if (fullDeleteAllowed) {
|
||||
return if (!sent || fullDeleteAllowed) {
|
||||
generalGetString(MR.strings.delete_message_cannot_be_undone_warning)
|
||||
} else {
|
||||
generalGetString(MR.strings.delete_message_mark_deleted_warning)
|
||||
@ -195,7 +195,7 @@ fun ChatItemView(
|
||||
}
|
||||
val clipboard = LocalClipboardManager.current
|
||||
val cachedRemoteReqs = remember { CIFile.cachedRemoteFileRequests }
|
||||
val copyAndShareAllowed = cItem.file == null || !chatModel.connectedToRemote() || getLoadedFilePath(cItem.file) != null || !cachedRemoteReqs.contains(cItem.file.fileSource)
|
||||
val copyAndShareAllowed = cItem.file == null || !chatModel.connectedToRemote() || getLoadedFilePath(cItem.file) != null || cachedRemoteReqs[cItem.file.fileSource] != false
|
||||
if (copyAndShareAllowed) {
|
||||
ItemAction(stringResource(MR.strings.share_verb), painterResource(MR.images.ic_share), onClick = {
|
||||
var fileSource = getLoadedFileSource(cItem.file)
|
||||
@ -221,7 +221,7 @@ fun ChatItemView(
|
||||
showMenu.value = false
|
||||
})
|
||||
}
|
||||
if ((cItem.content.msgContent is MsgContent.MCImage || cItem.content.msgContent is MsgContent.MCVideo || cItem.content.msgContent is MsgContent.MCFile || cItem.content.msgContent is MsgContent.MCVoice) && (getLoadedFilePath(cItem.file) != null || (chatModel.connectedToRemote() && !cachedRemoteReqs.contains(cItem.file?.fileSource)))) {
|
||||
if ((cItem.content.msgContent is MsgContent.MCImage || cItem.content.msgContent is MsgContent.MCVideo || cItem.content.msgContent is MsgContent.MCFile || cItem.content.msgContent is MsgContent.MCVoice) && (getLoadedFilePath(cItem.file) != null || (chatModel.connectedToRemote() && cachedRemoteReqs[cItem.file?.fileSource] != false))) {
|
||||
SaveContentItemAction(cItem, saveFileLauncher, showMenu)
|
||||
}
|
||||
if (cItem.meta.editable && cItem.content.msgContent !is MsgContent.MCVoice && !live) {
|
||||
|
@ -40,6 +40,7 @@ fun DatabaseView(
|
||||
m: ChatModel,
|
||||
showSettingsModal: (@Composable (ChatModel) -> Unit) -> (() -> Unit)
|
||||
) {
|
||||
val currentRemoteHost by remember { chatModel.currentRemoteHost }
|
||||
val progressIndicator = remember { mutableStateOf(false) }
|
||||
val prefs = m.controller.appPrefs
|
||||
val useKeychain = remember { mutableStateOf(prefs.storeDBPassphrase.get()) }
|
||||
@ -68,6 +69,7 @@ fun DatabaseView(
|
||||
val user = m.currentUser.value
|
||||
val rhId = user?.remoteHostId
|
||||
DatabaseLayout(
|
||||
currentRemoteHost = currentRemoteHost,
|
||||
progressIndicator.value,
|
||||
remember { m.chatRunning }.value != false,
|
||||
m.chatDbChanged.value,
|
||||
@ -119,6 +121,7 @@ fun DatabaseView(
|
||||
|
||||
@Composable
|
||||
fun DatabaseLayout(
|
||||
currentRemoteHost: RemoteHostInfo?,
|
||||
progressIndicator: Boolean,
|
||||
runChat: Boolean,
|
||||
chatDbChanged: Boolean,
|
||||
@ -165,103 +168,107 @@ fun DatabaseLayout(
|
||||
}
|
||||
}
|
||||
)
|
||||
SectionDividerSpaced(maxTopPadding = true)
|
||||
|
||||
SectionView(stringResource(MR.strings.run_chat_section)) {
|
||||
RunChatSetting(runChat, stopped, startChat, stopChatAlert)
|
||||
}
|
||||
SectionTextFooter(
|
||||
if (stopped) {
|
||||
stringResource(MR.strings.you_must_use_the_most_recent_version_of_database)
|
||||
} else {
|
||||
stringResource(MR.strings.stop_chat_to_enable_database_actions)
|
||||
if (currentRemoteHost == null) {
|
||||
SectionDividerSpaced(maxTopPadding = true)
|
||||
|
||||
SectionView(stringResource(MR.strings.run_chat_section)) {
|
||||
RunChatSetting(runChat, stopped, startChat, stopChatAlert)
|
||||
}
|
||||
)
|
||||
SectionDividerSpaced()
|
||||
|
||||
SectionView(stringResource(MR.strings.chat_database_section)) {
|
||||
val unencrypted = chatDbEncrypted == false
|
||||
SettingsActionItem(
|
||||
if (unencrypted) painterResource(MR.images.ic_lock_open_right) else if (useKeyChain) painterResource(MR.images.ic_vpn_key_filled)
|
||||
else painterResource(MR.images.ic_lock),
|
||||
stringResource(MR.strings.database_passphrase),
|
||||
click = showSettingsModal() { DatabaseEncryptionView(it) },
|
||||
iconColor = if (unencrypted || (appPlatform.isDesktop && passphraseSaved)) WarningOrange else MaterialTheme.colors.secondary,
|
||||
disabled = operationsDisabled
|
||||
SectionTextFooter(
|
||||
if (stopped) {
|
||||
stringResource(MR.strings.you_must_use_the_most_recent_version_of_database)
|
||||
} else {
|
||||
stringResource(MR.strings.stop_chat_to_enable_database_actions)
|
||||
}
|
||||
)
|
||||
if (appPlatform.isDesktop && developerTools) {
|
||||
SectionDividerSpaced()
|
||||
|
||||
SectionView(stringResource(MR.strings.chat_database_section)) {
|
||||
val unencrypted = chatDbEncrypted == false
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_folder_open),
|
||||
stringResource(MR.strings.open_database_folder),
|
||||
::desktopOpenDatabaseDir,
|
||||
if (unencrypted) painterResource(MR.images.ic_lock_open_right) else if (useKeyChain) painterResource(MR.images.ic_vpn_key_filled)
|
||||
else painterResource(MR.images.ic_lock),
|
||||
stringResource(MR.strings.database_passphrase),
|
||||
click = showSettingsModal() { DatabaseEncryptionView(it) },
|
||||
iconColor = if (unencrypted || (appPlatform.isDesktop && passphraseSaved)) WarningOrange else MaterialTheme.colors.secondary,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
if (appPlatform.isDesktop && developerTools) {
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_folder_open),
|
||||
stringResource(MR.strings.open_database_folder),
|
||||
::desktopOpenDatabaseDir,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
}
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_ios_share),
|
||||
stringResource(MR.strings.export_database),
|
||||
click = {
|
||||
if (initialRandomDBPassphrase.get()) {
|
||||
exportProhibitedAlert()
|
||||
} else {
|
||||
exportArchive()
|
||||
}
|
||||
},
|
||||
textColor = MaterialTheme.colors.primary,
|
||||
iconColor = MaterialTheme.colors.primary,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_download),
|
||||
stringResource(MR.strings.import_database),
|
||||
{ withApi { importArchiveLauncher.launch("application/zip") } },
|
||||
textColor = Color.Red,
|
||||
iconColor = Color.Red,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
val chatArchiveNameVal = chatArchiveName.value
|
||||
val chatArchiveTimeVal = chatArchiveTime.value
|
||||
val chatLastStartVal = chatLastStart.value
|
||||
if (chatArchiveNameVal != null && chatArchiveTimeVal != null && chatLastStartVal != null) {
|
||||
val title = chatArchiveTitle(chatArchiveTimeVal, chatLastStartVal)
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_inventory_2),
|
||||
title,
|
||||
click = showSettingsModal { ChatArchiveView(it, title, chatArchiveNameVal, chatArchiveTimeVal) },
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
}
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_delete_forever),
|
||||
stringResource(MR.strings.delete_database),
|
||||
deleteChatAlert,
|
||||
textColor = Color.Red,
|
||||
iconColor = Color.Red,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
}
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_ios_share),
|
||||
stringResource(MR.strings.export_database),
|
||||
click = {
|
||||
if (initialRandomDBPassphrase.get()) {
|
||||
exportProhibitedAlert()
|
||||
} else {
|
||||
exportArchive()
|
||||
}
|
||||
},
|
||||
textColor = MaterialTheme.colors.primary,
|
||||
iconColor = MaterialTheme.colors.primary,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_download),
|
||||
stringResource(MR.strings.import_database),
|
||||
{ withApi { importArchiveLauncher.launch("application/zip") }},
|
||||
textColor = Color.Red,
|
||||
iconColor = Color.Red,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
val chatArchiveNameVal = chatArchiveName.value
|
||||
val chatArchiveTimeVal = chatArchiveTime.value
|
||||
val chatLastStartVal = chatLastStart.value
|
||||
if (chatArchiveNameVal != null && chatArchiveTimeVal != null && chatLastStartVal != null) {
|
||||
val title = chatArchiveTitle(chatArchiveTimeVal, chatLastStartVal)
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_inventory_2),
|
||||
title,
|
||||
click = showSettingsModal { ChatArchiveView(it, title, chatArchiveNameVal, chatArchiveTimeVal) },
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
}
|
||||
SettingsActionItem(
|
||||
painterResource(MR.images.ic_delete_forever),
|
||||
stringResource(MR.strings.delete_database),
|
||||
deleteChatAlert,
|
||||
textColor = Color.Red,
|
||||
iconColor = Color.Red,
|
||||
disabled = operationsDisabled
|
||||
)
|
||||
}
|
||||
SectionDividerSpaced(maxTopPadding = true)
|
||||
SectionDividerSpaced(maxTopPadding = true)
|
||||
|
||||
SectionView(stringResource(MR.strings.files_and_media_section).uppercase()) {
|
||||
val deleteFilesDisabled = operationsDisabled || appFilesCountAndSize.value.first == 0
|
||||
SectionItemView(
|
||||
deleteAppFilesAndMedia,
|
||||
disabled = deleteFilesDisabled
|
||||
) {
|
||||
Text(
|
||||
stringResource(if (users.size > 1) MR.strings.delete_files_and_media_for_all_users else MR.strings.delete_files_and_media_all),
|
||||
color = if (deleteFilesDisabled) MaterialTheme.colors.secondary else Color.Red
|
||||
)
|
||||
SectionView(stringResource(MR.strings.files_and_media_section).uppercase()) {
|
||||
val deleteFilesDisabled = operationsDisabled || appFilesCountAndSize.value.first == 0
|
||||
SectionItemView(
|
||||
deleteAppFilesAndMedia,
|
||||
disabled = deleteFilesDisabled
|
||||
) {
|
||||
Text(
|
||||
stringResource(if (users.size > 1) MR.strings.delete_files_and_media_for_all_users else MR.strings.delete_files_and_media_all),
|
||||
color = if (deleteFilesDisabled) MaterialTheme.colors.secondary else Color.Red
|
||||
)
|
||||
}
|
||||
}
|
||||
val (count, size) = appFilesCountAndSize.value
|
||||
SectionTextFooter(
|
||||
if (count == 0) {
|
||||
stringResource(MR.strings.no_received_app_files)
|
||||
} else {
|
||||
String.format(stringResource(MR.strings.total_files_count_and_size), count, formatBytes(size))
|
||||
}
|
||||
)
|
||||
}
|
||||
val (count, size) = appFilesCountAndSize.value
|
||||
SectionTextFooter(
|
||||
if (count == 0) {
|
||||
stringResource(MR.strings.no_received_app_files)
|
||||
} else {
|
||||
String.format(stringResource(MR.strings.total_files_count_and_size), count, formatBytes(size))
|
||||
}
|
||||
)
|
||||
|
||||
SectionBottomSpacer()
|
||||
}
|
||||
}
|
||||
@ -666,6 +673,7 @@ private fun operationEnded(m: ChatModel, progressIndicator: MutableState<Boolean
|
||||
fun PreviewDatabaseLayout() {
|
||||
SimpleXTheme {
|
||||
DatabaseLayout(
|
||||
currentRemoteHost = null,
|
||||
progressIndicator = false,
|
||||
runChat = true,
|
||||
chatDbChanged = false,
|
||||
|
@ -125,7 +125,7 @@ fun DefaultConfigurableTextField(
|
||||
keyboardType: KeyboardType = KeyboardType.Text,
|
||||
dependsOn: State<Any?>? = null,
|
||||
) {
|
||||
var valid by remember { mutableStateOf(validKey(state.value.text)) }
|
||||
var valid by remember { mutableStateOf(isValid(state.value.text)) }
|
||||
var showKey by remember { mutableStateOf(false) }
|
||||
val icon = if (valid) {
|
||||
if (showKey) painterResource(MR.images.ic_visibility_off_filled) else painterResource(MR.images.ic_visibility_filled)
|
||||
|
@ -67,7 +67,7 @@ fun CreateLinkView(m: ChatModel, rh: RemoteHostInfo?, initialSelection: CreateLi
|
||||
AddContactView(m, rh,connReqInvitation.value ?: "", contactConnection)
|
||||
}
|
||||
CreateLinkTab.LONG_TERM -> {
|
||||
UserAddressView(m, rh?.remoteHostId, viaCreateLinkView = true, close = {})
|
||||
UserAddressView(m, viaCreateLinkView = true, close = {})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -21,6 +21,7 @@ import androidx.compose.ui.platform.LocalClipboardManager
|
||||
import androidx.compose.ui.text.AnnotatedString
|
||||
import androidx.compose.ui.text.TextStyle
|
||||
import androidx.compose.ui.text.font.FontFamily
|
||||
import androidx.compose.ui.text.font.FontStyle
|
||||
import androidx.compose.ui.text.input.TextFieldValue
|
||||
import androidx.compose.ui.unit.dp
|
||||
import androidx.compose.ui.unit.sp
|
||||
@ -37,6 +38,7 @@ import chat.simplex.common.views.newchat.QRCodeScanner
|
||||
import chat.simplex.common.views.usersettings.PreferenceToggle
|
||||
import chat.simplex.common.views.usersettings.SettingsActionItem
|
||||
import chat.simplex.res.MR
|
||||
import dev.icerock.moko.resources.ImageResource
|
||||
import dev.icerock.moko.resources.compose.painterResource
|
||||
import dev.icerock.moko.resources.compose.stringResource
|
||||
|
||||
@ -69,15 +71,21 @@ fun ConnectDesktopView(close: () -> Unit) {
|
||||
|
||||
@Composable
|
||||
private fun ConnectDesktopLayout(deviceName: String, close: () -> Unit) {
|
||||
val showConnectScreen = remember { mutableStateOf(true) }
|
||||
val sessionAddress = remember { mutableStateOf("") }
|
||||
val remoteCtrls = remember { mutableStateListOf<RemoteCtrlInfo>() }
|
||||
val session = remember { chatModel.remoteCtrlSession }.value
|
||||
Column(
|
||||
Modifier.fillMaxWidth().verticalScroll(rememberScrollState()),
|
||||
) {
|
||||
if (session != null) {
|
||||
val discovery = if (session == null) null else session.sessionState is UIRemoteCtrlSessionState.Searching
|
||||
if (discovery == true || (discovery == null && !showConnectScreen.value)) {
|
||||
SearchingDesktop(deviceName, remoteCtrls)
|
||||
} else if (session != null) {
|
||||
when (session.sessionState) {
|
||||
is UIRemoteCtrlSessionState.Starting -> ConnectingDesktop(session, null)
|
||||
is UIRemoteCtrlSessionState.Searching -> SearchingDesktop(deviceName, remoteCtrls)
|
||||
is UIRemoteCtrlSessionState.Found -> FoundDesktop(session, session.sessionState.remoteCtrl, session.sessionState.compatible, remember { controller.appPrefs.connectRemoteViaMulticastAuto.state }, deviceName, remoteCtrls, sessionAddress)
|
||||
is UIRemoteCtrlSessionState.Connecting -> ConnectingDesktop(session, session.sessionState.remoteCtrl_)
|
||||
is UIRemoteCtrlSessionState.PendingConfirmation -> {
|
||||
if (controller.appPrefs.confirmRemoteSessions.get() || session.sessionState.remoteCtrl_ == null) {
|
||||
@ -97,11 +105,21 @@ private fun ConnectDesktopLayout(deviceName: String, close: () -> Unit) {
|
||||
}
|
||||
SectionBottomSpacer()
|
||||
}
|
||||
DisposableEffect(Unit) {
|
||||
LaunchedEffect(Unit) {
|
||||
setDeviceName(deviceName)
|
||||
updateRemoteCtrls(remoteCtrls)
|
||||
val useMulticast = useMulticast(remoteCtrls)
|
||||
showConnectScreen.value = !useMulticast
|
||||
if (chatModel.remoteCtrlSession.value != null) {
|
||||
disconnectDesktop()
|
||||
} else if (useMulticast) {
|
||||
findKnownDesktop(showConnectScreen)
|
||||
}
|
||||
}
|
||||
DisposableEffect(Unit) {
|
||||
onDispose {
|
||||
if (chatModel.remoteCtrlSession.value != null) {
|
||||
showConnectScreen.value = false
|
||||
disconnectDesktop()
|
||||
}
|
||||
}
|
||||
@ -146,7 +164,75 @@ private fun ConnectingDesktop(session: RemoteCtrlSession, rc: RemoteCtrlInfo?) {
|
||||
SectionSpacer()
|
||||
|
||||
SectionView {
|
||||
DisconnectButton(::disconnectDesktop)
|
||||
DisconnectButton(onClick = ::disconnectDesktop)
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun SearchingDesktop(deviceName: String, remoteCtrls: SnapshotStateList<RemoteCtrlInfo>) {
|
||||
AppBarTitle(stringResource(MR.strings.connecting_to_desktop))
|
||||
SectionView(stringResource(MR.strings.this_device_name).uppercase()) {
|
||||
DevicesView(deviceName, remoteCtrls) {
|
||||
if (it != "") {
|
||||
setDeviceName(it)
|
||||
controller.appPrefs.deviceNameForRemoteAccess.set(it)
|
||||
}
|
||||
}
|
||||
}
|
||||
SectionDividerSpaced()
|
||||
SectionView(stringResource(MR.strings.found_desktop).uppercase(), padding = PaddingValues(horizontal = DEFAULT_PADDING)) {
|
||||
Text(stringResource(MR.strings.waiting_for_desktop), fontStyle = FontStyle.Italic)
|
||||
}
|
||||
SectionSpacer()
|
||||
DisconnectButton(stringResource(MR.strings.scan_QR_code).replace('\n', ' '), MR.images.ic_qr_code, ::disconnectDesktop)
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun FoundDesktop(
|
||||
session: RemoteCtrlSession,
|
||||
rc: RemoteCtrlInfo,
|
||||
compatible: Boolean,
|
||||
connectRemoteViaMulticastAuto: State<Boolean>,
|
||||
deviceName: String,
|
||||
remoteCtrls: SnapshotStateList<RemoteCtrlInfo>,
|
||||
sessionAddress: MutableState<String>,
|
||||
) {
|
||||
AppBarTitle(stringResource(MR.strings.found_desktop))
|
||||
SectionView(stringResource(MR.strings.this_device_name).uppercase()) {
|
||||
DevicesView(deviceName, remoteCtrls) {
|
||||
if (it != "") {
|
||||
setDeviceName(it)
|
||||
controller.appPrefs.deviceNameForRemoteAccess.set(it)
|
||||
}
|
||||
}
|
||||
}
|
||||
SectionDividerSpaced()
|
||||
SectionView(stringResource(MR.strings.found_desktop).uppercase(), padding = PaddingValues(horizontal = DEFAULT_PADDING)) {
|
||||
CtrlDeviceNameText(session, rc)
|
||||
CtrlDeviceVersionText(session)
|
||||
if (!compatible) {
|
||||
Text(stringResource(MR.strings.not_compatible), color = MaterialTheme.colors.error)
|
||||
}
|
||||
}
|
||||
|
||||
SectionSpacer()
|
||||
|
||||
if (compatible) {
|
||||
SectionItemView({ confirmKnownDesktop(sessionAddress, rc) }) {
|
||||
Icon(painterResource(MR.images.ic_check), generalGetString(MR.strings.connect_button), tint = MaterialTheme.colors.secondary)
|
||||
TextIconSpaced(false)
|
||||
Text(generalGetString(MR.strings.connect_button))
|
||||
}
|
||||
}
|
||||
|
||||
if (!compatible || !connectRemoteViaMulticastAuto.value) {
|
||||
DisconnectButton(stringResource(MR.strings.cancel_verb), onClick = ::disconnectDesktop)
|
||||
}
|
||||
|
||||
if (compatible && connectRemoteViaMulticastAuto.value) {
|
||||
LaunchedEffect(Unit) {
|
||||
confirmKnownDesktop(sessionAddress, rc)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -174,7 +260,7 @@ private fun VerifySession(session: RemoteCtrlSession, rc: RemoteCtrlInfo?, sessC
|
||||
}
|
||||
|
||||
SectionView {
|
||||
DisconnectButton(::disconnectDesktop)
|
||||
DisconnectButton(onClick = ::disconnectDesktop)
|
||||
}
|
||||
}
|
||||
|
||||
@ -182,7 +268,7 @@ private fun VerifySession(session: RemoteCtrlSession, rc: RemoteCtrlInfo?, sessC
|
||||
private fun CtrlDeviceNameText(session: RemoteCtrlSession, rc: RemoteCtrlInfo?) {
|
||||
val newDesktop = annotatedStringResource(MR.strings.new_desktop)
|
||||
val text = remember(rc) {
|
||||
var t = AnnotatedString(rc?.deviceViewName ?: session.ctrlAppInfo.deviceName)
|
||||
var t = AnnotatedString(rc?.deviceViewName ?: session.ctrlAppInfo?.deviceName ?: "")
|
||||
if (rc == null) {
|
||||
t = t + AnnotatedString(" ") + newDesktop
|
||||
}
|
||||
@ -195,7 +281,7 @@ private fun CtrlDeviceNameText(session: RemoteCtrlSession, rc: RemoteCtrlInfo?)
|
||||
private fun CtrlDeviceVersionText(session: RemoteCtrlSession) {
|
||||
val thisDeviceVersion = annotatedStringResource(MR.strings.this_device_version, session.appVersion)
|
||||
val text = remember(session) {
|
||||
val v = AnnotatedString(session.ctrlAppInfo.appVersionRange.maxVersion)
|
||||
val v = AnnotatedString(session.ctrlAppInfo?.appVersionRange?.maxVersion ?: "")
|
||||
var t = AnnotatedString("v$v")
|
||||
if (v.text != session.appVersion) {
|
||||
t = t + AnnotatedString(" ") + thisDeviceVersion
|
||||
@ -243,7 +329,8 @@ private fun SessionCodeText(code: String) {
|
||||
private fun DevicesView(deviceName: String, remoteCtrls: SnapshotStateList<RemoteCtrlInfo>, updateDeviceName: (String) -> Unit) {
|
||||
DeviceNameField(deviceName) { updateDeviceName(it) }
|
||||
if (remoteCtrls.isNotEmpty()) {
|
||||
SectionItemView({ ModalManager.start.showModal { LinkedDesktopsView(remoteCtrls) } }) {
|
||||
SectionItemView({ ModalManager.start.showModal { LinkedDesktopsView(remoteCtrls) }
|
||||
}) {
|
||||
Text(generalGetString(MR.strings.linked_desktops))
|
||||
}
|
||||
}
|
||||
@ -336,8 +423,13 @@ private fun LinkedDesktopsView(remoteCtrls: SnapshotStateList<RemoteCtrlInfo>) {
|
||||
PreferenceToggle(stringResource(MR.strings.verify_connections), remember { controller.appPrefs.confirmRemoteSessions.state }.value) {
|
||||
controller.appPrefs.confirmRemoteSessions.set(it)
|
||||
}
|
||||
PreferenceToggle(stringResource(MR.strings.discover_on_network), remember { controller.appPrefs.connectRemoteViaMulticast.state }.value && false) {
|
||||
controller.appPrefs.confirmRemoteSessions.set(it)
|
||||
PreferenceToggle(stringResource(MR.strings.discover_on_network), remember { controller.appPrefs.connectRemoteViaMulticast.state }.value) {
|
||||
controller.appPrefs.connectRemoteViaMulticast.set(it)
|
||||
}
|
||||
if (remember { controller.appPrefs.connectRemoteViaMulticast.state }.value) {
|
||||
PreferenceToggle(stringResource(MR.strings.multicast_connect_automatically), remember { controller.appPrefs.connectRemoteViaMulticastAuto.state }.value) {
|
||||
controller.appPrefs.connectRemoteViaMulticastAuto.set(it)
|
||||
}
|
||||
}
|
||||
}
|
||||
SectionBottomSpacer()
|
||||
@ -355,13 +447,11 @@ private fun setDeviceName(name: String) {
|
||||
}
|
||||
}
|
||||
|
||||
private fun updateRemoteCtrls(remoteCtrls: SnapshotStateList<RemoteCtrlInfo>) {
|
||||
withBGApi {
|
||||
val res = controller.listRemoteCtrls()
|
||||
if (res != null) {
|
||||
remoteCtrls.clear()
|
||||
remoteCtrls.addAll(res)
|
||||
}
|
||||
private suspend fun updateRemoteCtrls(remoteCtrls: SnapshotStateList<RemoteCtrlInfo>) {
|
||||
val res = controller.listRemoteCtrls()
|
||||
if (res != null) {
|
||||
remoteCtrls.clear()
|
||||
remoteCtrls.addAll(res)
|
||||
}
|
||||
}
|
||||
|
||||
@ -369,9 +459,34 @@ private fun processDesktopQRCode(sessionAddress: MutableState<String>, resp: Str
|
||||
connectDesktopAddress(sessionAddress, resp)
|
||||
}
|
||||
|
||||
private fun connectDesktopAddress(sessionAddress: MutableState<String>, addr: String) {
|
||||
private fun findKnownDesktop(showConnectScreen: MutableState<Boolean>) {
|
||||
withBGApi {
|
||||
val res = controller.connectRemoteCtrl(desktopAddress = addr)
|
||||
if (controller.findKnownRemoteCtrl()) {
|
||||
chatModel.remoteCtrlSession.value = RemoteCtrlSession(
|
||||
ctrlAppInfo = null,
|
||||
appVersion = "",
|
||||
sessionState = UIRemoteCtrlSessionState.Searching
|
||||
)
|
||||
showConnectScreen.value = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun confirmKnownDesktop(sessionAddress: MutableState<String>, rc: RemoteCtrlInfo) {
|
||||
connectDesktop(sessionAddress) {
|
||||
controller.confirmRemoteCtrl(rc.remoteCtrlId)
|
||||
}
|
||||
}
|
||||
|
||||
private fun connectDesktopAddress(sessionAddress: MutableState<String>, addr: String) {
|
||||
connectDesktop(sessionAddress) {
|
||||
controller.connectRemoteCtrl(addr)
|
||||
}
|
||||
}
|
||||
|
||||
private fun connectDesktop(sessionAddress: MutableState<String>, connect: suspend () -> Pair<SomeRemoteCtrl?, CR.ChatCmdError?>) {
|
||||
withBGApi {
|
||||
val res = connect()
|
||||
if (res.first != null) {
|
||||
val (rc_, ctrlAppInfo, v) = res.first!!
|
||||
sessionAddress.value = ""
|
||||
@ -409,18 +524,25 @@ private fun verifyDesktopSessionCode(remoteCtrls: SnapshotStateList<RemoteCtrlIn
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun DisconnectButton(onClick: () -> Unit) {
|
||||
private fun DisconnectButton(label: String = generalGetString(MR.strings.disconnect_remote_host), icon: ImageResource = MR.images.ic_close, onClick: () -> Unit) {
|
||||
SectionItemView(onClick) {
|
||||
Icon(painterResource(MR.images.ic_close), generalGetString(MR.strings.disconnect_remote_host), tint = MaterialTheme.colors.secondary)
|
||||
Icon(painterResource(icon), label, tint = MaterialTheme.colors.secondary)
|
||||
TextIconSpaced(false)
|
||||
Text(generalGetString(MR.strings.disconnect_remote_host))
|
||||
Text(label)
|
||||
}
|
||||
}
|
||||
|
||||
private fun useMulticast(remoteCtrls: List<RemoteCtrlInfo>): Boolean =
|
||||
controller.appPrefs.connectRemoteViaMulticast.get() && remoteCtrls.isNotEmpty()
|
||||
|
||||
private fun disconnectDesktop(close: (() -> Unit)? = null) {
|
||||
withBGApi {
|
||||
controller.stopRemoteCtrl()
|
||||
switchToLocalSession()
|
||||
if (chatModel.remoteCtrlSession.value?.sessionState is UIRemoteCtrlSessionState.Connected) {
|
||||
switchToLocalSession()
|
||||
} else {
|
||||
chatModel.remoteCtrlSession.value = null
|
||||
}
|
||||
close?.invoke()
|
||||
}
|
||||
}
|
||||
|
@ -30,6 +30,7 @@ import chat.simplex.common.views.chat.item.ItemAction
|
||||
import chat.simplex.common.views.chatlist.*
|
||||
import chat.simplex.common.views.helpers.*
|
||||
import chat.simplex.common.views.newchat.QRCode
|
||||
import chat.simplex.common.views.usersettings.PreferenceToggle
|
||||
import chat.simplex.common.views.usersettings.SettingsActionItemWithContent
|
||||
import chat.simplex.res.MR
|
||||
import dev.icerock.moko.resources.compose.painterResource
|
||||
@ -90,6 +91,9 @@ fun ConnectMobileLayout(
|
||||
SectionView(generalGetString(MR.strings.this_device_name).uppercase()) {
|
||||
DeviceNameField(deviceName.value ?: "") { updateDeviceName(it) }
|
||||
SectionTextFooter(generalGetString(MR.strings.this_device_name_shared_with_mobile))
|
||||
PreferenceToggle(stringResource(MR.strings.multicast_discoverable_via_local_network), remember { controller.appPrefs.offerRemoteMulticast.state }.value) {
|
||||
controller.appPrefs.offerRemoteMulticast.set(it)
|
||||
}
|
||||
SectionDividerSpaced(maxBottomPadding = false)
|
||||
}
|
||||
SectionView(stringResource(MR.strings.devices).uppercase()) {
|
||||
@ -235,7 +239,7 @@ private fun showAddingMobileDevice(connecting: MutableState<Boolean>) {
|
||||
ModalManager.start.showModalCloseable { close ->
|
||||
val invitation = rememberSaveable { mutableStateOf<String?>(null) }
|
||||
val port = rememberSaveable { mutableStateOf<String?>(null) }
|
||||
val pairing = remember { chatModel.newRemoteHostPairing }
|
||||
val pairing = remember { chatModel.remoteHostPairing }
|
||||
val sessionCode = when (val state = pairing.value?.second) {
|
||||
is RemoteHostSessionState.PendingConfirmation -> state.sessionCode
|
||||
else -> null
|
||||
@ -266,11 +270,12 @@ private fun showAddingMobileDevice(connecting: MutableState<Boolean>) {
|
||||
}
|
||||
DisposableEffect(Unit) {
|
||||
withBGApi {
|
||||
val r = chatModel.controller.startRemoteHost(null)
|
||||
val r = chatModel.controller.startRemoteHost(null, controller.appPrefs.offerRemoteMulticast.get())
|
||||
if (r != null) {
|
||||
connecting.value = true
|
||||
invitation.value = r.second
|
||||
port.value = r.third
|
||||
chatModel.remoteHostPairing.value = null to RemoteHostSessionState.Starting
|
||||
}
|
||||
}
|
||||
onDispose {
|
||||
@ -279,7 +284,7 @@ private fun showAddingMobileDevice(connecting: MutableState<Boolean>) {
|
||||
chatController.stopRemoteHost(null)
|
||||
}
|
||||
}
|
||||
chatModel.newRemoteHostPairing.value = null
|
||||
chatModel.remoteHostPairing.value = null
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -287,7 +292,7 @@ private fun showAddingMobileDevice(connecting: MutableState<Boolean>) {
|
||||
|
||||
private fun showConnectMobileDevice(rh: RemoteHostInfo, connecting: MutableState<Boolean>) {
|
||||
ModalManager.start.showModalCloseable { close ->
|
||||
val pairing = remember { chatModel.newRemoteHostPairing }
|
||||
val pairing = remember { chatModel.remoteHostPairing }
|
||||
val invitation = rememberSaveable { mutableStateOf<String?>(null) }
|
||||
val port = rememberSaveable { mutableStateOf<String?>(null) }
|
||||
val sessionCode = when (val state = pairing.value?.second) {
|
||||
@ -308,13 +313,14 @@ private fun showConnectMobileDevice(rh: RemoteHostInfo, connecting: MutableState
|
||||
)
|
||||
var remoteHostId by rememberSaveable { mutableStateOf<Long?>(null) }
|
||||
LaunchedEffect(Unit) {
|
||||
val r = chatModel.controller.startRemoteHost(rh.remoteHostId)
|
||||
val r = chatModel.controller.startRemoteHost(rh.remoteHostId, controller.appPrefs.offerRemoteMulticast.get())
|
||||
if (r != null) {
|
||||
val (rh_, inv) = r
|
||||
connecting.value = true
|
||||
remoteHostId = rh_?.remoteHostId
|
||||
invitation.value = inv
|
||||
port.value = r.third
|
||||
chatModel.remoteHostPairing.value = null to RemoteHostSessionState.Starting
|
||||
}
|
||||
}
|
||||
LaunchedEffect(remember { chatModel.currentRemoteHost }.value) {
|
||||
@ -334,7 +340,7 @@ private fun showConnectMobileDevice(rh: RemoteHostInfo, connecting: MutableState
|
||||
chatController.stopRemoteHost(remoteHostId)
|
||||
}
|
||||
}
|
||||
chatModel.newRemoteHostPairing.value = null
|
||||
chatModel.remoteHostPairing.value = null
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -28,7 +28,6 @@ import chat.simplex.common.model.*
|
||||
import chat.simplex.common.ui.theme.*
|
||||
import chat.simplex.common.views.chat.item.ClickableText
|
||||
import chat.simplex.common.views.helpers.*
|
||||
import chat.simplex.common.model.*
|
||||
import chat.simplex.common.views.helpers.annotatedStringResource
|
||||
import chat.simplex.res.MR
|
||||
|
||||
@ -39,6 +38,7 @@ fun NetworkAndServersView(
|
||||
showSettingsModal: (@Composable (ChatModel) -> Unit) -> (() -> Unit),
|
||||
showCustomModal: (@Composable (ChatModel, () -> Unit) -> Unit) -> (() -> Unit),
|
||||
) {
|
||||
val currentRemoteHost by remember { chatModel.currentRemoteHost }
|
||||
// It's not a state, just a one-time value. Shouldn't be used in any state-related situations
|
||||
val netCfg = remember { chatModel.controller.getNetCfg() }
|
||||
val networkUseSocksProxy: MutableState<Boolean> = remember { mutableStateOf(netCfg.useSocksProxy) }
|
||||
@ -52,6 +52,7 @@ fun NetworkAndServersView(
|
||||
|
||||
val proxyPort = remember { derivedStateOf { chatModel.controller.appPrefs.networkProxyHostPort.state.value?.split(":")?.lastOrNull()?.toIntOrNull() ?: 9050 } }
|
||||
NetworkAndServersLayout(
|
||||
currentRemoteHost = currentRemoteHost,
|
||||
developerTools = developerTools,
|
||||
networkUseSocksProxy = networkUseSocksProxy,
|
||||
onionHosts = onionHosts,
|
||||
@ -150,6 +151,7 @@ fun NetworkAndServersView(
|
||||
}
|
||||
|
||||
@Composable fun NetworkAndServersLayout(
|
||||
currentRemoteHost: RemoteHostInfo?,
|
||||
developerTools: Boolean,
|
||||
networkUseSocksProxy: MutableState<Boolean>,
|
||||
onionHosts: MutableState<OnionHosts>,
|
||||
@ -172,14 +174,16 @@ fun NetworkAndServersView(
|
||||
|
||||
SettingsActionItem(painterResource(MR.images.ic_dns), stringResource(MR.strings.xftp_servers), showCustomModal { m, close -> ProtocolServersView(m, m.remoteHostId, ServerProtocol.XFTP, close) })
|
||||
|
||||
UseSocksProxySwitch(networkUseSocksProxy, proxyPort, toggleSocksProxy, showSettingsModal)
|
||||
UseOnionHosts(onionHosts, networkUseSocksProxy, showSettingsModal, useOnion)
|
||||
if (developerTools) {
|
||||
SessionModePicker(sessionMode, showSettingsModal, updateSessionMode)
|
||||
if (currentRemoteHost == null) {
|
||||
UseSocksProxySwitch(networkUseSocksProxy, proxyPort, toggleSocksProxy, showSettingsModal)
|
||||
UseOnionHosts(onionHosts, networkUseSocksProxy, showSettingsModal, useOnion)
|
||||
if (developerTools) {
|
||||
SessionModePicker(sessionMode, showSettingsModal, updateSessionMode)
|
||||
}
|
||||
SettingsActionItem(painterResource(MR.images.ic_cable), stringResource(MR.strings.network_settings), showSettingsModal { AdvancedNetworkSettingsView(it) })
|
||||
}
|
||||
SettingsActionItem(painterResource(MR.images.ic_cable), stringResource(MR.strings.network_settings), showSettingsModal { AdvancedNetworkSettingsView(it) })
|
||||
}
|
||||
if (networkUseSocksProxy.value) {
|
||||
if (currentRemoteHost == null && networkUseSocksProxy.value) {
|
||||
SectionCustomFooter {
|
||||
Column {
|
||||
Text(annotatedStringResource(MR.strings.disable_onion_hosts_when_not_supported))
|
||||
@ -448,6 +452,7 @@ private fun showUpdateNetworkSettingsDialog(
|
||||
fun PreviewNetworkAndServersLayout() {
|
||||
SimpleXTheme {
|
||||
NetworkAndServersLayout(
|
||||
currentRemoteHost = null,
|
||||
developerTools = true,
|
||||
networkUseSocksProxy = remember { mutableStateOf(true) },
|
||||
proxyPort = remember { mutableStateOf(9050) },
|
||||
|
@ -21,7 +21,10 @@ import chat.simplex.res.MR
|
||||
fun PreferencesView(m: ChatModel, user: User, close: () -> Unit,) {
|
||||
var preferences by rememberSaveable(stateSaver = serializableSaver()) { mutableStateOf(user.fullPreferences) }
|
||||
var currentPreferences by rememberSaveable(stateSaver = serializableSaver()) { mutableStateOf(preferences) }
|
||||
|
||||
val u = remember { m.currentUser }
|
||||
KeyChangeEffect(u.value?.remoteHostId, u.value?.userId) {
|
||||
close()
|
||||
}
|
||||
fun savePrefs(afterSave: () -> Unit = {}) {
|
||||
withApi {
|
||||
val newProfile = user.profile.toProfile().copy(preferences = preferences.toPreferences())
|
||||
|
@ -155,7 +155,7 @@ fun SettingsLayout(
|
||||
}
|
||||
val profileHidden = rememberSaveable { mutableStateOf(false) }
|
||||
SettingsActionItem(painterResource(MR.images.ic_manage_accounts), stringResource(MR.strings.your_chat_profiles), { withAuth(generalGetString(MR.strings.auth_open_chat_profiles), generalGetString(MR.strings.auth_log_in_using_credential)) { showSettingsModalWithSearch { it, search -> UserProfilesView(it, search, profileHidden) } } }, disabled = stopped, extraPadding = true)
|
||||
SettingsActionItem(painterResource(MR.images.ic_qr_code), stringResource(MR.strings.your_simplex_contact_address), showCustomModal { it, close -> UserAddressView(it, it.currentUser.value?.remoteHostId, shareViaProfile = it.currentUser.value!!.addressShared, close = close) }, disabled = stopped, extraPadding = true)
|
||||
SettingsActionItem(painterResource(MR.images.ic_qr_code), stringResource(MR.strings.your_simplex_contact_address), showCustomModal { it, close -> UserAddressView(it, shareViaProfile = it.currentUser.value!!.addressShared, close = close) }, disabled = stopped, extraPadding = true)
|
||||
ChatPreferencesItem(showCustomModal, stopped = stopped)
|
||||
if (appPlatform.isDesktop) {
|
||||
SettingsActionItem(painterResource(MR.images.ic_smartphone), stringResource(if (remember { chatModel.remoteHosts }.isEmpty()) MR.strings.link_a_mobile else MR.strings.linked_mobiles), showModal { ConnectMobileView() }, disabled = stopped, extraPadding = true)
|
||||
|
@ -33,7 +33,6 @@ import chat.simplex.res.MR
|
||||
@Composable
|
||||
fun UserAddressView(
|
||||
chatModel: ChatModel,
|
||||
rhId: Long?,
|
||||
viaCreateLinkView: Boolean = false,
|
||||
shareViaProfile: Boolean = false,
|
||||
close: () -> Unit
|
||||
@ -42,12 +41,15 @@ fun UserAddressView(
|
||||
val shareViaProfile = remember { mutableStateOf(shareViaProfile) }
|
||||
var progressIndicator by remember { mutableStateOf(false) }
|
||||
val onCloseHandler: MutableState<(close: () -> Unit) -> Unit> = remember { mutableStateOf({ _ -> }) }
|
||||
|
||||
val user = remember { chatModel.currentUser }
|
||||
KeyChangeEffect(user.value?.remoteHostId, user.value?.userId) {
|
||||
close()
|
||||
}
|
||||
fun setProfileAddress(on: Boolean) {
|
||||
progressIndicator = true
|
||||
withBGApi {
|
||||
try {
|
||||
val u = chatModel.controller.apiSetProfileAddress(rhId, on)
|
||||
val u = chatModel.controller.apiSetProfileAddress(user?.value?.remoteHostId, on)
|
||||
if (u != null) {
|
||||
chatModel.updateUser(u)
|
||||
}
|
||||
@ -63,14 +65,14 @@ fun UserAddressView(
|
||||
val uriHandler = LocalUriHandler.current
|
||||
val showLayout = @Composable {
|
||||
UserAddressLayout(
|
||||
user = user.value,
|
||||
userAddress = userAddress.value,
|
||||
shareViaProfile,
|
||||
rhId,
|
||||
onCloseHandler,
|
||||
createAddress = {
|
||||
withApi {
|
||||
progressIndicator = true
|
||||
val connReqContact = chatModel.controller.apiCreateUserAddress(rhId)
|
||||
val connReqContact = chatModel.controller.apiCreateUserAddress(user?.value?.remoteHostId)
|
||||
if (connReqContact != null) {
|
||||
chatModel.userAddress.value = UserContactLinkRec(connReqContact)
|
||||
|
||||
@ -115,7 +117,7 @@ fun UserAddressView(
|
||||
onConfirm = {
|
||||
progressIndicator = true
|
||||
withApi {
|
||||
val u = chatModel.controller.apiDeleteUserAddress(rhId)
|
||||
val u = chatModel.controller.apiDeleteUserAddress(user?.value?.remoteHostId)
|
||||
if (u != null) {
|
||||
chatModel.userAddress.value = null
|
||||
chatModel.updateUser(u)
|
||||
@ -129,7 +131,7 @@ fun UserAddressView(
|
||||
},
|
||||
saveAas = { aas: AutoAcceptState, savedAAS: MutableState<AutoAcceptState> ->
|
||||
withBGApi {
|
||||
val address = chatModel.controller.userAddressAutoAccept(rhId, aas.autoAccept)
|
||||
val address = chatModel.controller.userAddressAutoAccept(user?.value?.remoteHostId, aas.autoAccept)
|
||||
if (address != null) {
|
||||
chatModel.userAddress.value = address
|
||||
savedAAS.value = aas
|
||||
@ -168,9 +170,9 @@ fun UserAddressView(
|
||||
|
||||
@Composable
|
||||
private fun UserAddressLayout(
|
||||
user: User?,
|
||||
userAddress: UserContactLinkRec?,
|
||||
shareViaProfile: MutableState<Boolean>,
|
||||
rhId: Long?,
|
||||
onCloseHandler: MutableState<(close: () -> Unit) -> Unit>,
|
||||
createAddress: () -> Unit,
|
||||
learnMore: () -> Unit,
|
||||
@ -183,7 +185,7 @@ private fun UserAddressLayout(
|
||||
Column(
|
||||
Modifier.verticalScroll(rememberScrollState()),
|
||||
) {
|
||||
AppBarTitle(stringResource(MR.strings.simplex_address), hostDevice(rhId), withPadding = false)
|
||||
AppBarTitle(stringResource(MR.strings.simplex_address), hostDevice(user?.remoteHostId), withPadding = false)
|
||||
Column(
|
||||
Modifier.fillMaxWidth().padding(bottom = DEFAULT_PADDING_HALF),
|
||||
horizontalAlignment = Alignment.CenterHorizontally,
|
||||
@ -432,6 +434,7 @@ private fun SaveAASButton(disabled: Boolean, onClick: () -> Unit) {
|
||||
fun PreviewUserAddressLayoutNoAddress() {
|
||||
SimpleXTheme {
|
||||
UserAddressLayout(
|
||||
user = User.sampleData,
|
||||
userAddress = null,
|
||||
createAddress = {},
|
||||
share = { _ -> },
|
||||
@ -440,7 +443,6 @@ fun PreviewUserAddressLayoutNoAddress() {
|
||||
setProfileAddress = { _ -> },
|
||||
learnMore = {},
|
||||
shareViaProfile = remember { mutableStateOf(false) },
|
||||
rhId = null,
|
||||
onCloseHandler = remember { mutableStateOf({}) },
|
||||
sendEmail = {},
|
||||
)
|
||||
@ -466,6 +468,7 @@ private fun showUnsavedChangesAlert(save: () -> Unit, revert: () -> Unit) {
|
||||
fun PreviewUserAddressLayoutAddressCreated() {
|
||||
SimpleXTheme {
|
||||
UserAddressLayout(
|
||||
user = User.sampleData,
|
||||
userAddress = UserContactLinkRec("https://simplex.chat/contact#/?v=1&smp=smp%3A%2F%2FPQUV2eL0t7OStZOoAsPEV2QYWt4-xilbakvGUGOItUo%3D%40smp6.simplex.im%2FK1rslx-m5bpXVIdMZg9NLUZ_8JBm8xTt%23MCowBQYDK2VuAyEALDeVe-sG8mRY22LsXlPgiwTNs9dbiLrNuA7f3ZMAJ2w%3D"),
|
||||
createAddress = {},
|
||||
share = { _ -> },
|
||||
@ -474,7 +477,6 @@ fun PreviewUserAddressLayoutAddressCreated() {
|
||||
setProfileAddress = { _ -> },
|
||||
learnMore = {},
|
||||
shareViaProfile = remember { mutableStateOf(false) },
|
||||
rhId = null,
|
||||
onCloseHandler = remember { mutableStateOf({}) },
|
||||
sendEmail = {},
|
||||
)
|
||||
|
@ -29,7 +29,11 @@ import java.net.URI
|
||||
|
||||
@Composable
|
||||
fun UserProfileView(chatModel: ChatModel, close: () -> Unit) {
|
||||
val user = chatModel.currentUser.value
|
||||
val u = remember {chatModel.currentUser}
|
||||
val user = u.value
|
||||
KeyChangeEffect(u.value?.remoteHostId, u.value?.userId) {
|
||||
close()
|
||||
}
|
||||
if (user != null) {
|
||||
var profile by remember { mutableStateOf(user.profile.toProfile()) }
|
||||
UserProfileLayout(
|
||||
|
@ -1404,4 +1404,12 @@
|
||||
<string name="v5_3_simpler_incognito_mode_descr">فعّل وضع التخفي عند الاتصال.</string>
|
||||
<string name="member_contact_send_direct_message">أرسل رسالة مباشرة</string>
|
||||
<string name="rcv_group_event_member_created_contact">متصل مباشرةً</string>
|
||||
<string name="connect_plan_already_connecting">جارٍ الاتصال بالفعل!</string>
|
||||
<string name="v5_4_better_groups">مجموعات أفضل</string>
|
||||
<string name="rcv_group_and_other_events">و%d أحداث أخرى</string>
|
||||
<string name="connect_plan_already_joining_the_group">جارٍ انضمام بالفعل إلى المجموعة!</string>
|
||||
<string name="block_member_confirmation">حجب</string>
|
||||
<string name="bad_desktop_address">عنوان سطح المكتب غير صالح</string>
|
||||
<string name="block_member_desc">سيتم إخفاء كافة الرسائل الجديدة من %s!</string>
|
||||
<string name="blocked_item_description">محجوب</string>
|
||||
</resources>
|
@ -1670,6 +1670,8 @@
|
||||
<string name="desktop_connection_terminated">Connection terminated</string>
|
||||
<string name="session_code">Session code</string>
|
||||
<string name="connecting_to_desktop">Connecting to desktop</string>
|
||||
<string name="waiting_for_desktop">Waiting for desktop…</string>
|
||||
<string name="found_desktop">Found desktop</string>
|
||||
<string name="connect_to_desktop">Connect to desktop</string>
|
||||
<string name="connected_to_desktop">Connected to desktop</string>
|
||||
<string name="connected_desktop">Connected desktop</string>
|
||||
@ -1681,9 +1683,12 @@
|
||||
<string name="scan_qr_code_from_desktop">Scan QR code from desktop</string>
|
||||
<string name="desktop_address">Desktop address</string>
|
||||
<string name="verify_connections">Verify connections</string>
|
||||
<string name="discover_on_network">Discover on network</string>
|
||||
<string name="discover_on_network">Discover via local network</string>
|
||||
<string name="multicast_discoverable_via_local_network">Discoverable via local network</string>
|
||||
<string name="multicast_connect_automatically">Connect automatically</string>
|
||||
<string name="paste_desktop_address">Paste desktop address</string>
|
||||
<string name="desktop_device">Desktop</string>
|
||||
<string name="not_compatible">Not compatible!</string>
|
||||
|
||||
<!-- Under development -->
|
||||
<string name="in_developing_title">Coming soon!</string>
|
||||
|
@ -1542,4 +1542,67 @@
|
||||
<string name="blocked_item_description">blockiert</string>
|
||||
<string name="encryption_renegotiation_error">Fehler bei der Neuverhandlung der Verschlüsselung</string>
|
||||
<string name="alert_text_encryption_renegotiation_failed">Neuverhandlung der Verschlüsselung fehlgeschlagen</string>
|
||||
<string name="v5_4_block_group_members">Gruppenmitglieder blockieren</string>
|
||||
<string name="v5_4_incognito_groups_descr">Erstellen Sie eine Gruppe mit einem zufälligen Profil.</string>
|
||||
<string name="connected_desktop">Verbundener Desktop</string>
|
||||
<string name="desktop_address">Desktop-Adresse</string>
|
||||
<string name="v5_4_better_groups">Bessere Gruppen</string>
|
||||
<string name="discover_on_network">Lokales Netzwerk durchsuchen</string>
|
||||
<string name="desktop_device">Desktop</string>
|
||||
<string name="connected_to_desktop">Mit dem Desktop verbunden</string>
|
||||
<string name="connecting_to_desktop">Mit dem Desktop verbinden</string>
|
||||
<string name="desktop_devices">Desktop-Geräte</string>
|
||||
<string name="connected_mobile">Verbundenes Mobiltelefon</string>
|
||||
<string name="desktop_connection_terminated">Verbindung beendet</string>
|
||||
<string name="enter_this_device_name">Geben Sie diesen Gerätenamen ein…</string>
|
||||
<string name="error">Fehler</string>
|
||||
<string name="connect_to_desktop">Mit dem Desktop verbinden</string>
|
||||
<string name="disconnect_remote_host">Trenne Verbindung</string>
|
||||
<string name="group_member_role_author">Autor</string>
|
||||
<string name="connected_to_mobile">Mit dem Mobiltelefon verbunden</string>
|
||||
<string name="bad_desktop_address">Falsche Desktop-Adresse</string>
|
||||
<string name="devices">Geräte</string>
|
||||
<string name="disconnect_desktop_question">Desktop-Verbindung trennen?</string>
|
||||
<string name="desktop_app_version_is_incompatible">Desktop-App-Version %s ist mit dieser App nicht kompatibel.</string>
|
||||
<string name="new_mobile_device">Neues Mobiltelefon-Gerät</string>
|
||||
<string name="only_one_device_can_work_at_the_same_time">Nur ein Gerät kann gleichzeitig genutzt werden</string>
|
||||
<string name="v5_4_link_mobile_desktop">Verknüpfe Mobiltelefon- und Desktop-Apps! 🔗</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">Über ein sicheres quantenbeständiges Protokoll</string>
|
||||
<string name="open_on_mobile_and_scan_qr_code"><![CDATA[Öffnen Sie in den Einstellungen der Mobiltelefon-App <i>Vom Desktop aus nutzen</i> und scannen Sie den QR-Code.]]></string>
|
||||
<string name="v5_4_block_group_members_descr">Um unerwünschte Nachrichten zu verbergen.</string>
|
||||
<string name="desktop_incompatible_version">Inkompatible Version</string>
|
||||
<string name="new_desktop"><![CDATA[<i>(Neu)</i>]]></string>
|
||||
<string name="unlink_desktop_question">Desktop entkoppeln?</string>
|
||||
<string name="linked_desktop_options">Verknüpfte Desktop-Optionen</string>
|
||||
<string name="linked_desktops">Verknüpfte Desktops</string>
|
||||
<string name="v5_4_incognito_groups">Inkognito-Gruppen</string>
|
||||
<string name="this_device">Dieses Gerät</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[Mobiltelefon <b>%s</b> wurde getrennt]]></string>
|
||||
<string name="v5_4_better_groups_descr">Schnellerer Gruppenbeitritt und zuverlässigere Nachrichtenzustellung.</string>
|
||||
<string name="linked_mobiles">Verknüpfte Mobiltelefone</string>
|
||||
<string name="this_device_name">Dieser Gerätename</string>
|
||||
<string name="waiting_for_mobile_to_connect_on_port"><![CDATA[Auf die Mobiltelefonverbindung über Port <i>%s</i> warten]]></string>
|
||||
<string name="loading_remote_file_title">Laden der Datei</string>
|
||||
<string name="link_a_mobile">Zu einem Mobiltelefon verbinden</string>
|
||||
<string name="settings_section_title_use_from_desktop">Vom Desktop aus nutzen</string>
|
||||
<string name="session_code">Sitzungscode</string>
|
||||
<string name="this_device_version"><![CDATA[<i>(Dieses Gerät hat v%s)</i>]]></string>
|
||||
<string name="unlink_desktop">Entkoppeln</string>
|
||||
<string name="this_device_name_shared_with_mobile">Der Gerätename wird mit dem verbundenen Mobiltelefon-Client geteilt.</string>
|
||||
<string name="verify_code_on_mobile">Code auf dem Mobiltelefon überprüfen</string>
|
||||
<string name="paste_desktop_address">Desktop-Adresse einfügen</string>
|
||||
<string name="verify_code_with_desktop">Code mit dem Desktop überprüfen</string>
|
||||
<string name="scan_qr_code_from_desktop">Den QR-Code vom Desktop scannen</string>
|
||||
<string name="v5_4_more_things_descr">- Optionale Benachrichtigung von gelöschten Kontakten.
|
||||
\n- Profilnamen mit Leerzeichen.
|
||||
\n- Und mehr!</string>
|
||||
<string name="scan_from_mobile">Vom Mobiltelefon scannen</string>
|
||||
<string name="verify_connections">Verbindungen überprüfen</string>
|
||||
<string name="loading_remote_file_desc">Bitte warten Sie, solange die Datei von dem verknüpften Mobiltelefon geladen wird</string>
|
||||
<string name="verify_connection">Verbindung überprüfen</string>
|
||||
<string name="multicast_connect_automatically">Automatisch verbinden</string>
|
||||
<string name="waiting_for_desktop">Auf Desktop warten…</string>
|
||||
<string name="found_desktop">Gefundener Desktop</string>
|
||||
<string name="not_compatible">Nicht kompatibel!</string>
|
||||
<string name="multicast_discoverable_via_local_network">Über das lokale Netzwerk auffindbar</string>
|
||||
</resources>
|
@ -1461,4 +1461,62 @@
|
||||
<string name="blocked_item_description">blocké</string>
|
||||
<string name="encryption_renegotiation_error">Erreur lors de la renégociation du chiffrement</string>
|
||||
<string name="alert_text_encryption_renegotiation_failed">La renégociation du chiffrement a échoué.</string>
|
||||
<string name="v5_4_block_group_members">Bloquer des membres d\'un groupe</string>
|
||||
<string name="v5_4_incognito_groups_descr">Création de groupes via un profil aléatoire.</string>
|
||||
<string name="connected_desktop">Bureau connecté</string>
|
||||
<string name="new_mobile_device">Nouvel appareil mobile</string>
|
||||
<string name="desktop_address">Adresse de bureau</string>
|
||||
<string name="only_one_device_can_work_at_the_same_time">Un seul appareil peut fonctionner en même temps</string>
|
||||
<string name="v5_4_link_mobile_desktop">Liez vos applications mobiles et de bureau ! 🔗</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">Via un protocole sécurisé de cryptographie post-quantique.</string>
|
||||
<string name="open_on_mobile_and_scan_qr_code"><![CDATA[Ouvrez <i>Utiliser depuis le bureau</i> dans l\'application mobile et scannez le code QR.]]></string>
|
||||
<string name="v5_4_block_group_members_descr">Pour cacher les messages indésirables.</string>
|
||||
<string name="desktop_incompatible_version">Version incompatible</string>
|
||||
<string name="new_desktop"><![CDATA[<i>(nouveau)</i>]]></string>
|
||||
<string name="unlink_desktop_question">Délier le bureau ?</string>
|
||||
<string name="v5_4_better_groups">Des groupes plus performants</string>
|
||||
<string name="linked_desktop_options">Options de bureau lié</string>
|
||||
<string name="linked_desktops">Bureaux liés</string>
|
||||
<string name="discover_on_network">Rechercher sur le réseau</string>
|
||||
<string name="v5_4_incognito_groups">Groupes incognito</string>
|
||||
<string name="this_device">Cet appareil</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[Le mobile <b>%s</b> a été déconnecté]]></string>
|
||||
<string name="v5_4_better_groups_descr">Connexion plus rapide et messages plus fiables.</string>
|
||||
<string name="linked_mobiles">Mobiles liés</string>
|
||||
<string name="desktop_device">Bureau</string>
|
||||
<string name="connected_to_desktop">Connecté au bureau</string>
|
||||
<string name="this_device_name">Ce nom d\'appareil</string>
|
||||
<string name="waiting_for_mobile_to_connect_on_port"><![CDATA[En attente d\'une connexion mobile sur le port <i>%s</i>]]></string>
|
||||
<string name="loading_remote_file_title">Chargement du fichier</string>
|
||||
<string name="connecting_to_desktop">Connexion au bureau</string>
|
||||
<string name="desktop_devices">Appareils de bureau</string>
|
||||
<string name="link_a_mobile">Lier un portable</string>
|
||||
<string name="settings_section_title_use_from_desktop">Utilisation depuis le bureau</string>
|
||||
<string name="connected_mobile">Mobile connecté</string>
|
||||
<string name="session_code">Code de session</string>
|
||||
<string name="desktop_connection_terminated">Connexion terminée</string>
|
||||
<string name="this_device_version"><![CDATA[<i>(cet appareil v%s)</i>]]></string>
|
||||
<string name="unlink_desktop">Délier</string>
|
||||
<string name="this_device_name_shared_with_mobile">Le nom de l\'appareil sera partagé avec le client mobile connecté.</string>
|
||||
<string name="verify_code_on_mobile">Vérifier le code sur le mobile</string>
|
||||
<string name="enter_this_device_name">Entrez le nom de l\'appareil…</string>
|
||||
<string name="error">Erreur</string>
|
||||
<string name="connect_to_desktop">Se connecter au bureau</string>
|
||||
<string name="disconnect_remote_host">Se déconnecter</string>
|
||||
<string name="group_member_role_author">auteur</string>
|
||||
<string name="connected_to_mobile">Connecté au portable</string>
|
||||
<string name="bad_desktop_address">Mauvaise adresse de bureau</string>
|
||||
<string name="paste_desktop_address">Coller l\'adresse du bureau</string>
|
||||
<string name="verify_code_with_desktop">Vérifier le code avec le bureau</string>
|
||||
<string name="scan_qr_code_from_desktop">Scanner le code QR du bureau</string>
|
||||
<string name="devices">Appareils</string>
|
||||
<string name="v5_4_more_things_descr">- option pour notifier les contacts supprimés.
|
||||
\n- noms de profil avec espaces.
|
||||
\n- et plus encore !</string>
|
||||
<string name="scan_from_mobile">Numériser depuis un mobile</string>
|
||||
<string name="verify_connections">Vérifier les connexions</string>
|
||||
<string name="disconnect_desktop_question">Déconnecter le bureau ?</string>
|
||||
<string name="loading_remote_file_desc">Veuillez patienter le temps que le fichier soit chargé depuis le mobile lié.</string>
|
||||
<string name="desktop_app_version_is_incompatible">La version de l\'application de bureau %s n\'est pas compatible avec cette application.</string>
|
||||
<string name="verify_connection">Vérifier la connexion</string>
|
||||
</resources>
|
@ -0,0 +1,359 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<resources>
|
||||
<string name="alert_text_decryption_error_n_messages_failed_to_decrypt">%1$d az üzenetek visszafejtése sikertelen</string>
|
||||
<string name="alert_text_decryption_error_too_many_skipped">%1$d üzenetek kihagyva.</string>
|
||||
<string name="integrity_msg_skipped">%1$d kihagyott üzenet(ek)</string>
|
||||
<string name="group_info_section_title_num_members">%1$s TAGOK</string>
|
||||
<string name="chat_item_ttl_month">1 hónap</string>
|
||||
<string name="chat_item_ttl_week">1 hét</string>
|
||||
<string name="v5_3_new_interface_languages">6 új kezelőfelület nyelv</string>
|
||||
<string name="send_disappearing_message_5_minutes">5 perc</string>
|
||||
<string name="send_disappearing_message_1_minute">1 perc</string>
|
||||
<string name="learn_more_about_address">A SimpleX azonosítóról</string>
|
||||
<string name="abort_switch_receiving_address_question">Címváltoztatás megszakítása?</string>
|
||||
<string name="abort_switch_receiving_address_confirm">Megszakítás</string>
|
||||
<string name="send_disappearing_message_30_seconds">30 másodperc</string>
|
||||
<string name="one_time_link_short">Egyszer használatos link</string>
|
||||
<string name="contact_wants_to_connect_via_call">%1$s szeretne kapcsolatba lépni veled</string>
|
||||
<string name="about_simplex_chat">A SimpleX chatről</string>
|
||||
<string name="chat_item_ttl_day">1 nap</string>
|
||||
<string name="abort_switch_receiving_address">Címváltoztatás megszakítása</string>
|
||||
<string name="about_simplex">A SimpleX-ről</string>
|
||||
<string name="color_primary">Kiemelőszín</string>
|
||||
<string name="callstatus_accepted">elfogadott hívás</string>
|
||||
<string name="network_enable_socks_info">Kapcsolódás a szerverekhez SOCKS proxy segítségével a %d? porton? A proxyt el kell indítani mielőtt bekapcsolná ezt az opciót.</string>
|
||||
<string name="accept_feature">Elfogad</string>
|
||||
<string name="accept_call_on_lock_screen">Elfogad</string>
|
||||
<string name="above_then_preposition_continuation">felül, majd pedig:</string>
|
||||
<string name="accept_contact_incognito_button">Elfogadás inkognítóban</string>
|
||||
<string name="accept_connection_request__question">Elfogadod a kapcsolatfelvételt?</string>
|
||||
<string name="accept_contact_button">Elfogad</string>
|
||||
<string name="accept">Elfogad</string>
|
||||
<string name="add_address_to_your_profile">Add hozzá az azonosítót a profilodhoz, így a kapcsolataid megosztatják azt más emberekkel. A profilod változtatásai így frissítésre kerülnek a kapcsolataidnál is!</string>
|
||||
<string name="color_primary_variant">További kiemelőszín</string>
|
||||
<string name="callstatus_error">hiba a hívásban</string>
|
||||
<string name="v5_4_block_group_members">Csoporttagok blokkolása</string>
|
||||
<string name="la_authenticate">Hitelesítés</string>
|
||||
<string name="empty_chat_profile_is_created">Egy üres chat profil létre lett hozva a megadott névvel és az app normál módon megnyílik.</string>
|
||||
<string name="feature_cancelled_item">megszakítva %s</string>
|
||||
<string name="smp_servers_preset_add">Adj hozzá egyedi szervereket</string>
|
||||
<string name="calls_prohibited_with_this_contact">Hang-/videóhívások megtiltva.</string>
|
||||
<string name="network_session_mode_entity_description">Külön TCP kapcsolat (és SOCKS bejelentkezési adatok) lesznek használva <b>minden ismerősre és csoport tagra</b>
|
||||
\n<b>Tudnivaló</b>: ha sok ismerősöd van, az akkumulátor- és adat használatod jelentősen megnőhet és néhány kapcsolódási kísérlet sikertelen lehet.</string>
|
||||
<string name="icon_descr_cancel_link_preview">URL link előnézet megszakítása</string>
|
||||
<string name="network_session_mode_user_description"><![CDATA[Külön TCP kapcsolat (és SOCKS bejelentkezési adatok) lesznek használva <b>minden chat profilodra az appban</b>.]]></string>
|
||||
<string name="both_you_and_your_contact_can_send_disappearing">Mindketten, te és az ismerősöd is küldhettek eltűnő üzeneteket.</string>
|
||||
<string name="keychain_is_storing_securely">Az Android Keystore-t jelmondat biztonságos tárolására használják - lehetővé teszi az értesítési szolgáltatás működését.</string>
|
||||
<string name="scan_QR_code_to_connect_to_contact_who_shows_QR_code"><![CDATA[<b>QR-kód beolvasása</b>: kapcsolódás ismerőshöz a megmutatott QR-kódja alapján]]></string>
|
||||
<string name="alert_title_msg_bad_hash">Téves üzenet hash</string>
|
||||
<string name="cant_delete_user_profile">Felhasználói profil törlése nem lehetséges!</string>
|
||||
<string name="color_background">Háttér</string>
|
||||
<string name="socks_proxy_setting_limitations"><![CDATA[<b>Tudnivaló</b>: az üzenet- és fájl relay szerverek SOCKS proxy által vannak kapcsolatban. A hívások és URL link előnézetek közvetlen kapcsolatot használnak.]]></string>
|
||||
<string name="full_backup">App adatmentés</string>
|
||||
<string name="database_initialization_error_title">Adatbázis inicializálása nem lehetséges</string>
|
||||
<string name="all_your_contacts_will_remain_connected_update_sent">A kapcsolat megmarad az összes Ismerősöddel. Profil változtatások frissítésre kerülnek az ismerőseidnél.</string>
|
||||
<string name="v4_5_transport_isolation_descr">Chat profile (alap beállítás) avagy kapcsolat által (BÉTA).</string>
|
||||
<string name="connect__a_new_random_profile_will_be_shared">Egy új véletlenszerű profil lesz megosztva.</string>
|
||||
<string name="allow_voice_messages_only_if">Hangüzenetek küldésének engedélyezése kizárólag az esetre ha a másik fél is engedélyezi.</string>
|
||||
<string name="app_version_code">App build: %s</string>
|
||||
<string name="audio_video_calls">Hang-/videóhívások</string>
|
||||
<string name="network_settings">Haladó hálózati beállítások</string>
|
||||
<string name="allow_your_contacts_to_send_voice_messages">Ismerősök küldhetnek hangüzeneteket engedélyezése.</string>
|
||||
<string name="settings_audio_video_calls">Hang- és videóhívások</string>
|
||||
<string name="v5_3_encrypt_local_files_descr">Az app titkosítja a helyi fájlokat (a videók kivételével).</string>
|
||||
<string name="answer_call">Hívás fogadása</string>
|
||||
<string name="allow_your_contacts_to_send_disappearing_messages">Ismerősök küldhetnek eltűnő üzeneteket engedélyezve.</string>
|
||||
<string name="connect_plan_already_connecting">Már kapcsolódik!</string>
|
||||
<string name="cannot_receive_file">Fájl fogadás nem lehetséges</string>
|
||||
<string name="auth_unavailable">Hitelesítés elérhetetlen</string>
|
||||
<string name="app_version_title">App verzió</string>
|
||||
<string name="button_add_welcome_message">Üdvözlőszöveg hozzáadása</string>
|
||||
<string name="snd_conn_event_ratchet_sync_started">titkosítás egyeztetése %s számára…</string>
|
||||
<string name="available_in_v51">"
|
||||
\nElérhető a v5.1-ben"</string>
|
||||
<string name="both_you_and_your_contacts_can_delete">Mindketten, te és az ismerősöd is visszaállíthatatlanul törölhettek elküldött üzeneteket.</string>
|
||||
<string name="v5_4_better_groups">Jobb csoportok</string>
|
||||
<string name="clear_chat_warning">Minden üzenet törlésre kerül - ez visszafordíthatatlan! Az üzenetek csak NÁLAD törlődnek.</string>
|
||||
<string name="icon_descr_call_ended">Hívás befejeződött</string>
|
||||
<string name="settings_section_title_calls">HÍVÁSOK</string>
|
||||
<string name="rcv_group_and_other_events">és %d egyéb események</string>
|
||||
<string name="address_section_title">Azonosító</string>
|
||||
<string name="connect_plan_already_joining_the_group">Már csatlakozik a csoporthoz!</string>
|
||||
<string name="auto_accept_contact">Automatikus elfogadás</string>
|
||||
<string name="notifications_mode_service_desc">Háttérszolgáltatás mindig fut - az értesítések azonnal megjelennek, amint üzenetek vannak.</string>
|
||||
<string name="allow_to_delete_messages">Elküldött üzenetek visszafordíthatatlan törlésének engedélyezése.</string>
|
||||
<string name="both_you_and_your_contact_can_send_voice">Mindketten, te és az ismerősöd is küldhettek hangüzeneteket.</string>
|
||||
<string name="alert_title_msg_bad_id">Téves üzenet ID</string>
|
||||
<string name="allow_your_contacts_adding_message_reactions">Üzenet rakciók -emojik- engedélyezése az ismerősei számára.</string>
|
||||
<string name="allow_to_send_voice">Hangüzenetek küldésének engedélyezése.</string>
|
||||
<string name="allow_message_reactions_only_if">Üzenet reakciók -emojik- engedélyezése kizárólag az esetre ha a másik fél is engedélyezi.</string>
|
||||
<string name="back">Vissza</string>
|
||||
<string name="it_can_disabled_via_settings_notifications_still_shown"><![CDATA[<b>Kikapcsolható a beállításokban</b> – az értesítések továbbra is megjelenítésre kerülnek amíg az app fut.]]></string>
|
||||
<string name="v4_2_group_links_desc">Adminok létrehozhatnak linkeket csoporthoz való csatlakozáshoz.</string>
|
||||
<string name="call_on_lock_screen">Hívások a lezárási képernyőn:</string>
|
||||
<string name="conn_event_ratchet_sync_started">titkosítás egyeztetése…</string>
|
||||
<string name="invite_prohibited">Ismerős meghívása sikertelen!</string>
|
||||
<string name="integrity_msg_bad_id">téves üzenet ID</string>
|
||||
<string name="v4_2_auto_accept_contact_requests">Ismerősnek jelölések automatikus elfogadása</string>
|
||||
<string name="impossible_to_recover_passphrase"><![CDATA[<b>Tudnivaló</b>: NEM fogod tudni helyreállítani vagy megváltoztatni a jelmondatot az esetben ha elveszíted.]]></string>
|
||||
<string name="callstatus_calling">hívás…</string>
|
||||
<string name="color_secondary_variant">További másodlagos</string>
|
||||
<string name="smp_servers_add_to_another_device">Hozzáadás másik eszközhöz</string>
|
||||
<string name="allow_message_reactions">Üzenet reakciók -emojik- engedélyezése.</string>
|
||||
<string name="icon_descr_cancel_file_preview">Fájl előnézet megszakítása</string>
|
||||
<string name="all_group_members_will_remain_connected">Minden csoporttag kapcsolatban marad.</string>
|
||||
<string name="onboarding_notifications_mode_service_desc"><![CDATA[<b>Több akkumulátort használ</b>! Háttérszolgáltatás mindig fut - értesítések megjelennek azonnal, ahogy új üzenetek érkeznek.]]></string>
|
||||
<string name="block_member_confirmation">Blokkolás</string>
|
||||
<string name="group_member_role_admin">admin</string>
|
||||
<string name="icon_descr_cancel_image_preview">Fénykép előnézet megszakítása</string>
|
||||
<string name="v5_1_self_destruct_passcode_descr">Minden adat törlődik amint bevitelre kerül.</string>
|
||||
<string name="icon_descr_video_asked_to_receive">Kérte a videó elfogadását</string>
|
||||
<string name="block_member_button">Tag blokkolása</string>
|
||||
<string name="v5_2_more_things">Néhány további dolog</string>
|
||||
<string name="authentication_cancelled">Hitelesítés megszakítva</string>
|
||||
<string name="allow_to_send_files">Fájlok és fotók/videók küldésének engedélyezése.</string>
|
||||
<string name="users_delete_all_chats_deleted">Minden chat illetve az összes üzenet törlésre kerül - ez visszafordíthatatlan!</string>
|
||||
<string name="icon_descr_audio_call">hanghívás</string>
|
||||
<string name="bold_text">vastagított</string>
|
||||
<string name="app_passcode_replaced_with_self_destruct">Az app számkód helyettesítésre kerül egy önmegsemmisítő számkóddal.</string>
|
||||
<string name="v5_3_new_interface_languages_descr">Arab, bulgár, finn, héber, thai és ukrán - köszönet a felhasználóknak és a Weblate-nek!</string>
|
||||
<string name="add_new_contact_to_create_one_time_QR_code"><![CDATA[<b>Új ismerős hozzáadása</b>: egyszer használatos QR-kód készítése az ismerős számára.]]></string>
|
||||
<string name="allow_voice_messages_question">Hangüzenetek engedélyezése?</string>
|
||||
<string name="always_use_relay">Mindig használt relay szervert</string>
|
||||
<string name="chat_preferences_always">mindig</string>
|
||||
<string name="call_already_ended">A hívás már befejeződött!</string>
|
||||
<string name="turn_off_battery_optimization_button">Engedélyez</string>
|
||||
<string name="all_your_contacts_will_remain_connected">A kapcsolat megmarad az összes Ismerősöddel.</string>
|
||||
<string name="icon_descr_cancel_live_message">Élő chat üzenet megszakítása</string>
|
||||
<string name="allow_irreversible_message_deletion_only_if">Helyreállíthatatlan üzenet törlés engedélyezése kizárólag az esetre ha a másik fél is engedélyezi.</string>
|
||||
<string name="v4_6_audio_video_calls">Hang- és videóhívások</string>
|
||||
<string name="integrity_msg_bad_hash">téves üzenet hash</string>
|
||||
<string name="notifications_mode_service">Mindig bekapcsolva</string>
|
||||
<string name="keychain_allows_to_receive_ntfs">Az Android Keystore fogja biztonságosan tárolni a jelmondatot app újraindítás vagy jelmondat változtatás után - lehetővé téve az értesítések fogadását.</string>
|
||||
<string name="all_app_data_will_be_cleared">Minden app adat törölve.</string>
|
||||
<string name="onboarding_notifications_mode_off_desc"><![CDATA[<b>Legjobb akkumulátoridő</b>. Kizárólag akkor kapsz értesítéseket amikor fut az app (NINCS háttérszolgáltatás).]]></string>
|
||||
<string name="appearance_settings">Megjelenés</string>
|
||||
<string name="turning_off_service_and_periodic">Akkumulátor optimizáció aktív, a háttérszolgáltatás és a rendszeres új üzenet ellenőrzés kikapcsolva. Újra bekapcsolhatod ezeket a beállításokban.</string>
|
||||
<string name="block_member_question">Tag blokkolása?</string>
|
||||
<string name="callstatus_ended">hívás befejeződött %1$s</string>
|
||||
<string name="onboarding_notifications_mode_periodic_desc"><![CDATA[<b>Jó akkumulátoridő</b>. A háttérszolgáltatás ellenőrzi az új üzeneteket 10 percenként. Hívásokról és fontos üzenetekről maradhatsz le.]]></string>
|
||||
<string name="group_member_role_author">szerző</string>
|
||||
<string name="allow_your_contacts_irreversibly_delete">Ismerősök visszafordíthatatlanul törölhetnek elküldött üzeneteket engedélyezve.</string>
|
||||
<string name="cancel_verb">Megszakítás</string>
|
||||
<string name="notifications_mode_off_desc">Az app csak akkor tud értesítéseket fogadni amikor fut, héttérszolgáltatás nem kerül elindításra.</string>
|
||||
<string name="v5_1_better_messages">Jobb üzenetek</string>
|
||||
<string name="abort_switch_receiving_address_desc">A cím változtatás megszakításra kerül. A régi fogadó cím marad használatban.</string>
|
||||
<string name="allow_verb">Engedélyez</string>
|
||||
<string name="bad_desktop_address">Rossz asztal cím</string>
|
||||
<string name="users_add">Adj hozzá profilt</string>
|
||||
<string name="attach">Csatolás</string>
|
||||
<string name="v5_0_app_passcode">App számkód</string>
|
||||
<string name="icon_descr_asked_to_receive">Kérte, hogy fogfaja a képet</string>
|
||||
<string name="use_camera_button">Fényképező</string>
|
||||
<string name="cannot_access_keychain">A Keystore-hoz nem sikerül hozzáférni az adatbázis jelszó elmentése végett</string>
|
||||
<string name="callstatus_in_progress">hívás folyamatban</string>
|
||||
<string name="auto_accept_images">Fényképek automatiklus elfogadása</string>
|
||||
<string name="allow_your_contacts_to_call">Hang- és videóhívás engedélyezése az ismerősei számára.</string>
|
||||
<string name="settings_section_title_icon">APP IKON</string>
|
||||
<string name="v4_3_improved_server_configuration_desc">Szerver hozzáadása QR kód befotózásával.</string>
|
||||
<string name="allow_to_send_disappearing">Eltünő üzenetek küldésének engedélyezése.</string>
|
||||
<string name="allow_disappearing_messages_only_if">Eltűnő üzenetek engedélyezése kizárólag az esetre ha a másik fél is engedélyezi.</string>
|
||||
<string name="icon_descr_audio_off">Hang kikapcsolva</string>
|
||||
<string name="allow_direct_messages">Közvetlen üzenetküldés tagok számára engedélyezett.</string>
|
||||
<string name="settings_section_title_app">APP</string>
|
||||
<string name="icon_descr_call_progress">Hívás folyamatban</string>
|
||||
<string name="both_you_and_your_contact_can_add_message_reactions">Mindketten, te és az ismerősöd is használhattok üzenet reakciókat (emojik).</string>
|
||||
<string name="both_you_and_your_contact_can_make_calls">Mindketten, te és az ismerősöd is tudok hívásokat indítani.</string>
|
||||
<string name="la_auth_failed">Hitelesítés sikertelen</string>
|
||||
<string name="block_member_desc">Minden új üzenet %s -tól/től elrejtésre kerül.</string>
|
||||
<string name="app_version_name">App verzió: v%s</string>
|
||||
<string name="allow_calls_only_if">Hívások engedélyezése kizárólag az esetre ha a másik fél is engedélyezi.</string>
|
||||
<string name="smp_servers_add">Szerver hozzáadása…</string>
|
||||
<string name="icon_descr_audio_on">Hang bekapcsolva</string>
|
||||
<string name="audio_call_no_encryption">hanghívás (nem e2e titkosított)</string>
|
||||
<string name="blocked_item_description">blokkolva</string>
|
||||
<string name="change_database_passphrase_question">Adatbázis jelmondat megváltoztatása?</string>
|
||||
<string name="callstate_connected">kapcsolódva</string>
|
||||
<string name="la_change_app_passcode">Számkód megváltoztatása</string>
|
||||
<string name="rcv_group_event_changed_member_role">%s to %s megváltozott szerepköre</string>
|
||||
<string name="switch_receiving_address">Fogadó szerver cím megváltoztatása</string>
|
||||
<string name="change_verb">Változtatás</string>
|
||||
<string name="confirm_passcode">Számkód megerősítése</string>
|
||||
<string name="confirm_password">Jelszó megerősítése</string>
|
||||
<string name="change_member_role_question">Csoport szerepkör megváltoztatása?</string>
|
||||
<string name="change_lock_mode">Lezárási mód megváltoztatása</string>
|
||||
<string name="notification_contact_connected">Kapcsolódva</string>
|
||||
<string name="rcv_group_event_member_connected">kapcsolódva</string>
|
||||
<string name="connect_via_link_verb">Kapcsolódás</string>
|
||||
<string name="group_member_status_connected">kapcsolódva</string>
|
||||
<string name="connected_mobile">Összekapcsolt telefon</string>
|
||||
<string name="server_connected">kapcsolódva</string>
|
||||
<string name="change_role">Szerepkör megváltoztatása</string>
|
||||
<string name="icon_descr_server_status_connected">Kapcsolódva</string>
|
||||
<string name="auth_confirm_credential">Belépési adatok megerősítése</string>
|
||||
<string name="switch_receiving_address_question">Fogadó szerver cím megváltoztatása</string>
|
||||
<string name="rcv_conn_event_switch_queue_phase_completed">megváltozott azonosító számodra</string>
|
||||
<string name="change_self_destruct_mode">Önmegsemmisítő mód megváltoztatása</string>
|
||||
<string name="rcv_group_event_changed_your_role">a szerepköröd megváltoztatva %s-ra(-re)</string>
|
||||
<string name="connect_button">Kapcsolódás</string>
|
||||
<string name="connect_via_member_address_alert_title">Kapcsolódás közvetlenül?</string>
|
||||
<string name="smp_server_test_connect">Kapcsolódás</string>
|
||||
<string name="rcv_group_event_member_created_contact">közvetlenül kapcsolódva</string>
|
||||
<string name="connection_local_display_name">kapcsolat %1$d</string>
|
||||
<string name="status_contact_has_e2e_encryption">az ismerősnél az e2e titkosítás elérhető</string>
|
||||
<string name="v5_4_incognito_groups_descr">Csoport létrehozása véletlenszerűen létrehozott profillal.</string>
|
||||
<string name="delete_contact_all_messages_deleted_cannot_undo_warning">Az ismerős és az összes üzenet törlésre kerül - ez visszafordíthatatlan!</string>
|
||||
<string name="contacts_can_mark_messages_for_deletion">Ismerősök megjelölhetik az üzeneteket törlendőként; de láthatod azokat.</string>
|
||||
<string name="connect_via_invitation_link">Kapcsolódás egy Egyszer használatos linkkel?</string>
|
||||
<string name="connect_via_link_or_qr">Kapcsolódás egy link / QR-kód által</string>
|
||||
<string name="connection_error_auth">Kapcsolódási hiba (AUTH)</string>
|
||||
<string name="notification_preview_mode_contact">Ismerős neve</string>
|
||||
<string name="connect_via_contact_link">Kapcsolódás ismerős azonosítója által?</string>
|
||||
<string name="create_address">Azonosító létrehozása</string>
|
||||
<string name="copy_verb">Másolás</string>
|
||||
<string name="continue_to_next_step">Folytatás</string>
|
||||
<string name="connect_plan_connect_via_link">Kapcsolódás egy linken keresztül?</string>
|
||||
<string name="contact_already_exists">Az ismerős már létezik</string>
|
||||
<string name="core_version">Fő verzió: v%s</string>
|
||||
<string name="icon_descr_contact_checked">Ismerős ellenőrizve</string>
|
||||
<string name="connect_plan_connect_to_yourself">Kapcsolódás saját magához?</string>
|
||||
<string name="copied">Kimásolva a vágólapra</string>
|
||||
<string name="connection_request_sent">Kapcsolódási kérés elküldve!</string>
|
||||
<string name="connecting_to_desktop">Kapcsolódás az asztalhoz</string>
|
||||
<string name="network_session_mode_entity">Kapcsolat</string>
|
||||
<string name="correct_name_to">Név helyesbítése erre: %s?</string>
|
||||
<string name="connection_timeout">Kapcsolat időtúllépés</string>
|
||||
<string name="connect_with_contact_name_question">Kapcsolódás %1$s által?</string>
|
||||
<string name="create_profile_button">Létrehozás</string>
|
||||
<string name="contact_preferences">Ismerős beállításai</string>
|
||||
<string name="info_row_connection">Kapcsolat</string>
|
||||
<string name="desktop_connection_terminated">Kapcsolat megszakítva</string>
|
||||
<string name="display_name_connection_established">Kapcsolat létrehozva</string>
|
||||
<string name="status_contact_has_no_e2e_encryption">az ismerősnél az e2e titkosítás nem elérhető</string>
|
||||
<string name="chat_preferences_contact_allows">Az ismerős engedélyezi</string>
|
||||
<string name="notification_preview_somebody">Ismerős elrejtve:</string>
|
||||
<string name="connect_to_desktop">Kapcsolódás az asztalhoz</string>
|
||||
<string name="icon_descr_context">Kontextus ikon</string>
|
||||
<string name="connect_via_link">Kapcsolódás egy linken keresztül</string>
|
||||
<string name="receipts_section_contacts">Ismerősök</string>
|
||||
<string name="connection_error">Kapcsolódási hiba</string>
|
||||
<string name="alert_title_contact_connection_pending">Az ismerős még nem kapcsolódott!</string>
|
||||
<string name="v5_3_discover_join_groups_descr">- kapcsolódás könyvtár szolgáltatáshoz (BÉTA)!
|
||||
\n- kézbesítési igazolások (20 tagig).
|
||||
\n- gyorsabb és stabilabb</string>
|
||||
<string name="contribute">Hozzájárulás</string>
|
||||
<string name="group_member_status_intro_invitation">kapcsolódás (meghívás bemutatkozásra)</string>
|
||||
<string name="create_simplex_address">SimpleX azonosító létrehozása</string>
|
||||
<string name="rcv_direct_event_contact_deleted">törölt ismerős</string>
|
||||
<string name="delete_member_message__question">Tag üzenetének törlése?</string>
|
||||
<string name="chat_is_running">A chat szolgáltatás működik (fut)</string>
|
||||
<string name="share_one_time_link">Egyszer használatos meghívó link létrehozása</string>
|
||||
<string name="delete_link">Link törlése</string>
|
||||
<string name="notifications_mode_periodic_desc">Új üzenetek ellenőrzése 10 percenként, legfeljebb 1 percen keresztül.</string>
|
||||
<string name="delete_database">Adatbázis törlése</string>
|
||||
<string name="create_group_button">Csoport létrehozása</string>
|
||||
<string name="network_session_mode_user">Chat profil</string>
|
||||
<string name="create_another_profile_button">Profil létrehozása</string>
|
||||
<string name="connected_desktop">Csatlakoztatott asztal</string>
|
||||
<string name="share_text_deleted_at">Törölve ekkor: %s</string>
|
||||
<string name="info_row_deleted_at">Törölve ekkor</string>
|
||||
<string name="v4_6_chinese_spanish_interface">Kínai és spanyol kezelőfelület.</string>
|
||||
<string name="alert_title_cant_invite_contacts">Ismerősök meghívása nem lehetséges!</string>
|
||||
<string name="chat_is_stopped_indication">A chat szolgáltatás leállt (nem fut)</string>
|
||||
<string name="theme_dark">Sötét</string>
|
||||
<string name="create_profile">Profil létrehozása</string>
|
||||
<string name="rcv_group_event_group_deleted">törölt csoport</string>
|
||||
<string name="full_deletion">Törlés mindenkinek</string>
|
||||
<string name="button_create_group_link">Link létrehozása</string>
|
||||
<string name="chat_preferences">Chat beállítások</string>
|
||||
<string name="chat_archive_header">Chat archívum</string>
|
||||
<string name="delete_profile">Profil törlése</string>
|
||||
<string name="la_current_app_passcode">Jelenlegi Számkód</string>
|
||||
<string name="group_member_status_connecting">kapcsolódás</string>
|
||||
<string name="confirm_new_passphrase">Új jelmondat megerősítése…</string>
|
||||
<string name="group_connection_pending">kapcsolódás…</string>
|
||||
<string name="delete_chat_profile">Chat profil törlés</string>
|
||||
<string name="custom_time_picker_custom">egyedi</string>
|
||||
<string name="callstatus_connecting">hívás kapcsolódik…</string>
|
||||
<string name="customize_theme_title">Színséma személyreszabása</string>
|
||||
<string name="maximum_supported_file_size">Jelenleg támogatott legnagyobb fájl méret: %1$s.</string>
|
||||
<string name="smp_server_test_delete_file">Fájl törlése</string>
|
||||
<string name="in_developing_title">Hamarosan!</string>
|
||||
<string name="snd_conn_event_switch_queue_phase_changing_for_member">azonosító megváltoztatása %s számára…</string>
|
||||
<string name="chat_database_imported">Chat adatbázis importálva</string>
|
||||
<string name="chat_archive_section">CHAT ARCHÍVUM</string>
|
||||
<string name="delete_messages">Üzenetek törlése?</string>
|
||||
<string name="clear_chat_menu_action">Kiürítés</string>
|
||||
<string name="icon_descr_close_button">Bezárás gomb</string>
|
||||
<string name="chat_is_stopped">A chat szolgáltatás leállt (nem fut)</string>
|
||||
<string name="item_info_current">(jelenlegi)</string>
|
||||
<string name="v5_1_custom_themes_descr">Színsémák személyreszabása és megosztása</string>
|
||||
<string name="delete_chat_profile_question">Chat profil törlése?</string>
|
||||
<string name="create_group">Titkos csoport létrehozása</string>
|
||||
<string name="connected_to_desktop">Kapcsolódva az asztalhoz</string>
|
||||
<string name="configure_ICE_servers">ICE sezrverek beállítása</string>
|
||||
<string name="button_delete_group">Csoport törlése</string>
|
||||
<string name="clear_verification">Chat hitelesításe</string>
|
||||
<string name="group_member_status_creator">szerző</string>
|
||||
<string name="confirm_verb">Megerősítés</string>
|
||||
<string name="for_me_only">Törlés nálam</string>
|
||||
<string name="delete_messages__question">%d üzenet törlése?</string>
|
||||
<string name="v5_1_custom_themes">Egyedi színsémák</string>
|
||||
<string name="group_member_status_accepted">kapcsolódás (elfogadva)</string>
|
||||
<string name="smp_servers_check_address">Szerver cím ellenőrzése és újrapróbálkozás.</string>
|
||||
<string name="delete_group_question">Csoport törlése?</string>
|
||||
<string name="confirm_database_upgrades">Adatbázis frissítés megerősítése</string>
|
||||
<string name="create_your_profile">Saját profil létrehozása</string>
|
||||
<string name="snd_conn_event_switch_queue_phase_changing">azonosító megváltoztatása…</string>
|
||||
<string name="display_name_connecting">kapcsolódás…</string>
|
||||
<string name="icon_descr_call_connecting">Hívás kapcsolása</string>
|
||||
<string name="delete_files_and_media_question">Fájlok illetve fotók/videók törlése?</string>
|
||||
<string name="group_member_status_complete">befejezve</string>
|
||||
<string name="chat_database_section">CHAT ADATBÁZIS</string>
|
||||
<string name="change_self_destruct_passcode">Önmegsemmisító számkód megváltoztatása</string>
|
||||
<string name="smp_server_test_create_queue">Várólista létrehozása</string>
|
||||
<string name="colored_text">színes</string>
|
||||
<string name="callstate_connecting">kapcsolódás…</string>
|
||||
<string name="dark_theme">Sötét színséma</string>
|
||||
<string name="deleted_description">törölve</string>
|
||||
<string name="users_delete_question">Chat profil törlése?</string>
|
||||
<string name="chat_with_developers">Chat a SimpleX fejlesztőivel</string>
|
||||
<string name="delete_link_question">Link törlése?</string>
|
||||
<string name="server_connecting">kapcsolódás</string>
|
||||
<string name="send_disappearing_message_custom_time">Személyreszabott idő</string>
|
||||
<string name="connect_via_link_incognito">Inkognítóban csatlakozva</string>
|
||||
<string name="settings_section_title_chats">CHATEK</string>
|
||||
<string name="v5_3_new_desktop_app_descr">Új profil létrehozása a számítógépen futó appban. 💻</string>
|
||||
<string name="group_member_status_announced">kapcsolódás (bejelentve)</string>
|
||||
<string name="contact_connection_pending">kapcsolódás…</string>
|
||||
<string name="chat_database_deleted">Chat adatbázis törölve</string>
|
||||
<string name="group_member_status_introduced">kapcsolódás (bejelentve)</string>
|
||||
<string name="create_group_link">Csoporthoz link létrehozása</string>
|
||||
<string name="chat_console">Chat konzol</string>
|
||||
<string name="delete_files_and_media_for_all_users">Fájlok törlése minden chat profil alatt</string>
|
||||
<string name="smp_server_test_delete_queue">Várólista törlése</string>
|
||||
<string name="button_delete_contact">Ismerős törlése</string>
|
||||
<string name="archive_created_on_ts">Létrehozva: %1$s</string>
|
||||
<string name="rcv_conn_event_switch_queue_phase_changing">azonosító megváltoztatása…</string>
|
||||
<string name="connected_to_mobile">Kapcsolódva a mobilhoz</string>
|
||||
<string name="current_passphrase">Jelenlegi jelmondat…</string>
|
||||
<string name="choose_file_title">Fájl választása</string>
|
||||
<string name="create_one_time_link">Egyszer használatos meghívó link létrehozása</string>
|
||||
<string name="delete_image">Kép törlése</string>
|
||||
<string name="smp_server_test_create_file">Fájl létrehozása</string>
|
||||
<string name="create_secret_group_title">Tikos csoport létrehozása</string>
|
||||
<string name="clear_contacts_selection_button">Kiürítés</string>
|
||||
<string name="delete_contact_question">Ismerős törlése?</string>
|
||||
<string name="clear_verb">Kiürítés</string>
|
||||
<string name="create_address_and_let_people_connect">Hozz létre egy azonosítót, hogy az ismerősök kapcsolatba léphessenek veled.</string>
|
||||
<string name="v4_4_verify_connection_security_desc">Biztonsági kódok ösezhasonlítása az ismerősökkel.</string>
|
||||
<string name="smp_server_test_compare_file">Fájl összehasonlítása</string>
|
||||
<string name="your_chats">Chatek</string>
|
||||
<string name="delete_message__question">Üzenet törlése?</string>
|
||||
<string name="delete_pending_connection__question">Függő kapcsolatfelvételi kérés törlése?</string>
|
||||
<string name="database_encrypted">Adatbázis titkosítva!</string>
|
||||
<string name="clear_chat_question">Chat kiürítése?</string>
|
||||
<string name="database_downgrade">Adatbázis downgrade?</string>
|
||||
<string name="clear_chat_button">Chat kiürítése</string>
|
||||
<string name="database_passphrase_will_be_updated">Adatbázis titkosítási jelmondat meg lesz változtatva.</string>
|
||||
</resources>
|
@ -1505,4 +1505,18 @@
|
||||
<string name="loading_remote_file_desc">Si prega di attendere mentre il file viene caricato dal cellulare collegato</string>
|
||||
<string name="desktop_app_version_is_incompatible">La versione dell\'app desktop %s non è compatibile con questa app.</string>
|
||||
<string name="verify_connection">Verifica la connessione</string>
|
||||
<string name="v5_4_block_group_members">Blocca i membri dei gruppi</string>
|
||||
<string name="v5_4_incognito_groups_descr">Crea un gruppo usando un profilo casuale.</string>
|
||||
<string name="v5_4_link_mobile_desktop">Collega le app mobile e desktop! 🔗</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">Tramite protocollo sicuro resistente alla quantistica.</string>
|
||||
<string name="v5_4_block_group_members_descr">Per nascondere messaggi indesiderati.</string>
|
||||
<string name="v5_4_better_groups">Gruppi migliorati</string>
|
||||
<string name="v5_4_incognito_groups">Gruppi in incognito</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[Il cellulare <b>%s</b> è stato disconnesso]]></string>
|
||||
<string name="v5_4_better_groups_descr">Ingresso più veloce e messaggi più affidabili.</string>
|
||||
<string name="v5_4_more_things_descr">- avvisa facoltativamente i contatti eliminati.
|
||||
\n- nomi del profilo con spazi.
|
||||
\n- e molto altro!</string>
|
||||
<string name="waiting_for_mobile_to_connect_on_port"><![CDATA[In attesa che il cellulare si connetta alla porta <i>%s</i>]]></string>
|
||||
<string name="group_member_role_author">autore</string>
|
||||
</resources>
|
@ -1469,7 +1469,7 @@
|
||||
<string name="unlink_desktop_question">Desktop ontkoppelen?</string>
|
||||
<string name="linked_desktop_options">Gekoppelde desktop opties</string>
|
||||
<string name="linked_desktops">Gelinkte desktops</string>
|
||||
<string name="discover_on_network">Ontdek via netwerk</string>
|
||||
<string name="discover_on_network">Ontdek via het lokale netwerk</string>
|
||||
<string name="this_device">Dit apparaat</string>
|
||||
<string name="linked_mobiles">Gekoppelde mobiele apparaten</string>
|
||||
<string name="desktop_device">Desktop</string>
|
||||
@ -1503,4 +1503,23 @@
|
||||
<string name="loading_remote_file_desc">Wacht terwijl het bestand wordt geladen vanaf de gekoppelde mobiele telefoon</string>
|
||||
<string name="desktop_app_version_is_incompatible">Desktop-app-versie %s is niet compatibel met deze app.</string>
|
||||
<string name="verify_connection">Controleer de verbinding</string>
|
||||
<string name="v5_4_block_group_members">Groepsleden blokkeren</string>
|
||||
<string name="v5_4_incognito_groups_descr">Maak een groep met een willekeurig profiel.</string>
|
||||
<string name="v5_4_link_mobile_desktop">Koppel mobiele en desktop-apps! 🔗</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">Via een beveiligd kwantumbestendig protocol.</string>
|
||||
<string name="v5_4_block_group_members_descr">Om ongewenste berichten te verbergen.</string>
|
||||
<string name="v5_4_better_groups">Betere groepen</string>
|
||||
<string name="v5_4_incognito_groups">Incognitogroepen</string>
|
||||
<string name="v5_4_better_groups_descr">Snellere deelname en betrouwbaardere berichten.</string>
|
||||
<string name="v5_4_more_things_descr">- optioneel verwijderde contacten op de hoogte stellen.
|
||||
\n- profielnamen met spaties.
|
||||
\n- en meer!</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[Mobiele verbinding <b>%s</b> is verbroken]]></string>
|
||||
<string name="group_member_role_author">auteur</string>
|
||||
<string name="waiting_for_mobile_to_connect_on_port"><![CDATA[Wachten tot mobiel verbinding maakt op poort <i>%s</i>]]></string>
|
||||
<string name="multicast_connect_automatically">Automatisch verbinden</string>
|
||||
<string name="waiting_for_desktop">Wachten op desktop…</string>
|
||||
<string name="found_desktop">Desktop gevonden</string>
|
||||
<string name="not_compatible">Niet compatibel!</string>
|
||||
<string name="multicast_discoverable_via_local_network">Vindbaar via lokaal netwerk</string>
|
||||
</resources>
|
@ -3,11 +3,11 @@
|
||||
<string name="app_name">SimpleX</string>
|
||||
<string name="thousand_abbreviation">т</string>
|
||||
<!-- Connect via Link - MainActivity.kt -->
|
||||
<string name="connect_via_contact_link">Соединиться через ссылку-контакт?</string>
|
||||
<string name="connect_via_invitation_link">Соединиться через ссылку-приглашение?</string>
|
||||
<string name="connect_via_group_link">Соединиться через ссылку группы?</string>
|
||||
<string name="connect_via_contact_link">Соединиться через адрес?</string>
|
||||
<string name="connect_via_invitation_link">Соединиться через одноразовую ссылку?</string>
|
||||
<string name="connect_via_group_link">Вступить в группу?</string>
|
||||
<string name="profile_will_be_sent_to_contact_sending_link">Ваш профиль будет отправлен контакту, от которого Вы получили эту ссылку.</string>
|
||||
<string name="you_will_join_group">Вы вступите в группу, на которую ссылается эта ссылка.</string>
|
||||
<string name="you_will_join_group">Вы соединитесь со всеми членами группы.</string>
|
||||
<string name="connect_via_link_verb">Соединиться</string>
|
||||
<!-- Server info - ChatModel.kt -->
|
||||
<string name="server_connected">соединено</string>
|
||||
@ -435,7 +435,7 @@
|
||||
<string name="your_profile_is_stored_on_your_device">Ваш профиль, контакты и доставленные сообщения хранятся на Вашем устройстве.</string>
|
||||
<string name="profile_is_only_shared_with_your_contacts">Профиль отправляется только Вашим контактам.</string>
|
||||
<string name="display_name_cannot_contain_whitespace">Имя профиля не может содержать пробелы.</string>
|
||||
<string name="display_name">Имя профиля</string>
|
||||
<string name="display_name">Введите ваше имя:</string>
|
||||
<string name="create_profile_button">Создать</string>
|
||||
<string name="about_simplex">О SimpleX</string>
|
||||
<!-- markdown demo - MarkdownHelpView.kt -->
|
||||
@ -818,8 +818,8 @@
|
||||
<string name="switch_receiving_address">Переключить адрес получения</string>
|
||||
<!-- AddGroupView.kt -->
|
||||
<string name="create_secret_group_title">Создать скрытую группу</string>
|
||||
<string name="group_is_decentralized">Группа полностью децентрализована — она видна только членам.</string>
|
||||
<string name="group_display_name_field">Имя группы:</string>
|
||||
<string name="group_is_decentralized">Группа полностью децентрализована – она видна только членам.</string>
|
||||
<string name="group_display_name_field">Введите имя группы:</string>
|
||||
<string name="group_full_name_field">Полное имя:</string>
|
||||
<string name="group_main_profile_sent">Ваш профиль чата будет отправлен членам группы</string>
|
||||
<!-- GroupProfileView.kt -->
|
||||
@ -1489,4 +1489,114 @@
|
||||
<string name="error_sending_message_contact_invitation">Ошибка отправки приглашения</string>
|
||||
<string name="member_contact_send_direct_message">Послать прямое сообщение</string>
|
||||
<string name="rcv_group_event_member_created_contact">соединен напрямую</string>
|
||||
<string name="expand_verb">Раскрыть</string>
|
||||
<string name="v5_4_block_group_members">Блокируйте членов группы</string>
|
||||
<string name="connect_plan_repeat_connection_request">Повторить запрос на соединение?</string>
|
||||
<string name="encryption_renegotiation_error">Ошибка нового соглашения о шифровании</string>
|
||||
<string name="rcv_direct_event_contact_deleted">удалил(а) контакт</string>
|
||||
<string name="error_alert_title">Ошибка</string>
|
||||
<string name="v5_4_incognito_groups_descr">Создайте группу, используя случайный профиль.</string>
|
||||
<string name="create_group_button">Создать группу</string>
|
||||
<string name="create_another_profile_button">Создать профиль</string>
|
||||
<string name="connected_desktop">Подключенный компьютер</string>
|
||||
<string name="group_members_2">%s и %s</string>
|
||||
<string name="new_mobile_device">Новое мобильное устройство</string>
|
||||
<string name="desktop_address">Адрес компьютера</string>
|
||||
<string name="only_one_device_can_work_at_the_same_time">Одновременно может работать только одно устройство</string>
|
||||
<string name="connect_plan_join_your_group">Вступить в вашу группу?</string>
|
||||
<string name="v5_4_link_mobile_desktop">Свяжите мобильное и настольное приложения! 🔗</string>
|
||||
<string name="marked_deleted_items_description">%d сообщений помечено удалёнными</string>
|
||||
<string name="connect_plan_group_already_exists">Группа уже существует!</string>
|
||||
<string name="open_on_mobile_and_scan_qr_code"><![CDATA[Откройте <i>Использовать с компьютера</i> в мобильном приложении и сосканируйте QR код]]></string>
|
||||
<string name="connect_plan_already_connecting">Уже соединяется!</string>
|
||||
<string name="desktop_incompatible_version">Несовместимая версия</string>
|
||||
<string name="new_desktop"><![CDATA[<i>(новое)</i>]]></string>
|
||||
<string name="v5_4_better_groups">Улучшенные группы</string>
|
||||
<string name="linked_desktop_options">Опции связанных компьютеров</string>
|
||||
<string name="linked_desktops">Связанные компьютеры</string>
|
||||
<string name="discover_on_network">Обнаружение по локальной сети</string>
|
||||
<string name="rcv_group_and_other_events">и %d других событий</string>
|
||||
<string name="connect_plan_connect_via_link">Соединиться через ссылку?</string>
|
||||
<string name="v5_4_incognito_groups">Инкогнито группы</string>
|
||||
<string name="connect_plan_already_joining_the_group">Вступление в группу уже начато!</string>
|
||||
<string name="moderated_items_description">%d сообщений модерировано членом %s</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[Удаленный хост был отключен: <b>%s</b>]]></string>
|
||||
<string name="v5_4_better_groups_descr">Быстрое вступление и надежная доставка сообщений.</string>
|
||||
<string name="connect_plan_connect_to_yourself">Соединиться с самим собой?</string>
|
||||
<string name="linked_mobiles">Связанные мобильные</string>
|
||||
<string name="desktop_device">Компьютер</string>
|
||||
<string name="connected_to_desktop">Компьютер подключен</string>
|
||||
<string name="loading_remote_file_title">Загрузка файла</string>
|
||||
<string name="connecting_to_desktop">Подключение к компьютеру</string>
|
||||
<string name="alert_text_encryption_renegotiation_failed">Ошибка нового соглашения о шифровании</string>
|
||||
<string name="desktop_devices">Компьютеры</string>
|
||||
<string name="correct_name_to">Исправить имя на %s?</string>
|
||||
<string name="delete_messages__question">Удалить %d сообщений?</string>
|
||||
<string name="link_a_mobile">Связать мобильный</string>
|
||||
<string name="connect_with_contact_name_question">Соединиться с %1$s?</string>
|
||||
<string name="remove_member_button">Удалить члена группы</string>
|
||||
<string name="block_member_confirmation">Заблокировать</string>
|
||||
<string name="blocked_items_description">%d сообщений заблокировано</string>
|
||||
<string name="block_member_button">Заблокировать члена группы</string>
|
||||
<string name="connected_mobile">Подключенный мобильный</string>
|
||||
<string name="connect_plan_repeat_join_request">Повторить запрос на вступление?</string>
|
||||
<string name="button_remove_member_question">Удалить члена группы?</string>
|
||||
<string name="delete_and_notify_contact">Удалить и уведомить контакт</string>
|
||||
<string name="connect_plan_open_group">Открыть группу</string>
|
||||
<string name="desktop_connection_terminated">Подключение прервано</string>
|
||||
<string name="this_device_version"><![CDATA[<i>(это устройство v%s)</i>]]></string>
|
||||
<string name="unblock_member_desc">Сообщения от %s будут показаны!</string>
|
||||
<string name="enter_this_device_name">Введите имя этого устройства…</string>
|
||||
<string name="error">Ошибка</string>
|
||||
<string name="connect_to_desktop">Подключиться к компьютеру</string>
|
||||
<string name="disconnect_remote_host">Отключить</string>
|
||||
<string name="block_member_question">Заблокировать члена группы?</string>
|
||||
<string name="rcv_group_events_count">%d событий</string>
|
||||
<string name="invalid_name">Неверное имя!</string>
|
||||
<string name="connected_to_mobile">Мобильный подключен</string>
|
||||
<string name="bad_desktop_address">Неверный адрес компьютера</string>
|
||||
<string name="paste_desktop_address">Вставить адрес компьютера</string>
|
||||
<string name="devices">Устройства</string>
|
||||
<string name="v5_4_more_things_descr">- опционально уведомляйте удалённые контакты.
|
||||
\n- имена профилей с пробелами.
|
||||
\n- и прочее!</string>
|
||||
<string name="non_content_uri_alert_title">Неверный путь к файлу</string>
|
||||
<string name="scan_from_mobile">Сканируйте с мобильного</string>
|
||||
<string name="disconnect_desktop_question">Отключить компьютер?</string>
|
||||
<string name="loading_remote_file_desc">Пожалуйста, подождите, пока файл загружается со связанного мобильного устройства.</string>
|
||||
<string name="block_member_desc">Все новые сообщения от %s будут скрыты!</string>
|
||||
<string name="desktop_app_version_is_incompatible">Версия настольного приложения %s несовместима с этим приложением.</string>
|
||||
<string name="blocked_item_description">заблокировано</string>
|
||||
<string name="connect_plan_you_are_already_connecting_to_vName">Вы уже соединяетесь с %1$s.</string>
|
||||
<string name="connect_plan_you_are_already_joining_the_group_via_this_link">Вы уже вступаете в группу по этой ссылке.</string>
|
||||
<string name="connect_plan_you_are_already_joining_the_group_vName">Вы уже вступаете в группу %1$s.</string>
|
||||
<string name="connect_plan_this_is_your_own_one_time_link">Это ваша собственная одноразовая ссылка!</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">Через безопасный квантово-устойчивый протокол.</string>
|
||||
<string name="v5_4_block_group_members_descr">Чтобы скрыть нежелательные сообщения.</string>
|
||||
<string name="unlink_desktop_question">Забыть компьютер?</string>
|
||||
<string name="video_decoding_exception_desc">Видео невозможно декодировать. Пожалуйста, попробуйте другое видео или свяжитесь с разработчиками.</string>
|
||||
<string name="rcv_group_event_1_member_connected">%@ соединен(а)</string>
|
||||
<string name="group_members_n">%s, %s и %d членов группы</string>
|
||||
<string name="this_device">Это устройство</string>
|
||||
<string name="unblock_member_button">Разблокировать члена группы</string>
|
||||
<string name="contact_tap_to_connect">Нажмите чтобы соединиться</string>
|
||||
<string name="this_device_name">Имя этого устройства</string>
|
||||
<string name="connect_plan_you_are_already_in_group_vName">Вы уже состоите в группе %1$s.</string>
|
||||
<string name="connect_plan_this_is_your_own_simplex_address">Это ваш собственный адрес SimpleX!</string>
|
||||
<string name="unblock_member_question">Разблокировать члена группы?</string>
|
||||
<string name="settings_section_title_use_from_desktop">Использовать с компьютера</string>
|
||||
<string name="session_code">Код сессии</string>
|
||||
<string name="connect_plan_you_are_already_connecting_via_this_one_time_link">Вы уже соединяетесь по этой одноразовой ссылке!</string>
|
||||
<string name="unlink_desktop">Забыть</string>
|
||||
<string name="this_device_name_shared_with_mobile">Имя устройства будет доступно подключенному мобильному клиенту.</string>
|
||||
<string name="verify_code_on_mobile">Сверьте код на мобильном</string>
|
||||
<string name="non_content_uri_alert_text">Указан неверный путь к файлу. Сообщите о проблеме разработчикам приложения.</string>
|
||||
<string name="connect_plan_this_is_your_link_for_group_vName">Это ваша ссылка на группу %1$s!</string>
|
||||
<string name="verify_code_with_desktop">Сверьте код с компьютером</string>
|
||||
<string name="scan_qr_code_from_desktop">Сканировать QR код с компьютера</string>
|
||||
<string name="unblock_member_confirmation">Разблокировать</string>
|
||||
<string name="connect_plan_you_have_already_requested_connection_via_this_address">Вы уже запросили соединение через этот адрес!</string>
|
||||
<string name="terminal_always_visible">Показывать консоль в новом окне</string>
|
||||
<string name="verify_connections">Проверять соединения</string>
|
||||
<string name="verify_connection">Проверить соединение</string>
|
||||
</resources>
|
@ -1048,4 +1048,27 @@
|
||||
<string name="users_delete_data_only">Sadece yerel profil verisi</string>
|
||||
<string name="info_row_local_name">Yerel ad</string>
|
||||
<string name="only_you_can_add_message_reactions">Sadece sen mesaj tepkileri ekleyebilirsin.</string>
|
||||
<string name="stop_file__confirm">Durdur</string>
|
||||
<string name="stop_file__action">Dosyayı durdur</string>
|
||||
<string name="error_alert_title">Hata</string>
|
||||
<string name="create_another_profile_button">ProfilProfil oluştur</string>
|
||||
<string name="stop_chat_to_enable_database_actions">Veri tabanı eylemlerini etkinleştirmek için sohbeti durdur.</string>
|
||||
<string name="stop_snd_file__title">Dosya göndermeyi durdur?</string>
|
||||
<string name="auth_stop_chat">Sohbeti durdur</string>
|
||||
<string name="connect_use_current_profile">Mevcut profili kullan</string>
|
||||
<string name="la_mode_system">Sistem</string>
|
||||
<string name="settings_section_title_support">SIMPLEX CHAT\'İ DESTEKLE</string>
|
||||
<string name="stop_chat_to_export_import_or_delete_chat_database">Sohbet veri tabanını dışa aktarmak, içe aktarmak veya silmek için sohbeti durdur. Sohbet durdurulduğunda mesaj alamaz ve gönderemezsiniz.</string>
|
||||
<string name="desktop_device">Masaüstü</string>
|
||||
<string name="contact_tap_to_connect">Bağlanmak için dokun</string>
|
||||
<string name="block_member_confirmation">Engelle</string>
|
||||
<string name="tap_to_activate_profile">Profili etkinleştirmek için dokun.</string>
|
||||
<string name="stop_chat_confirmation">Durdur</string>
|
||||
<string name="stop_sharing_address">Adres paylaşmayı durdur?</string>
|
||||
<string name="send_receipts_disabled">kapalı</string>
|
||||
<string name="turn_off_battery_optimization_button">İzin ver</string>
|
||||
<string name="error">Hata</string>
|
||||
<string name="stop_sharing">Paylaşmayı durdur</string>
|
||||
<string name="stop_rcv_file__title">Dosya almayı durdur?</string>
|
||||
<string name="stop_chat_question">Sohbeti durdur?</string>
|
||||
</resources>
|
@ -1471,7 +1471,7 @@
|
||||
<string name="unlink_desktop_question">取消链接桌面端?</string>
|
||||
<string name="linked_desktop_options">已链接桌面选项</string>
|
||||
<string name="linked_desktops">已链接桌面</string>
|
||||
<string name="discover_on_network">网络发现</string>
|
||||
<string name="discover_on_network">通过本地网络发现</string>
|
||||
<string name="this_device">此设备</string>
|
||||
<string name="linked_mobiles">已链接的移动设备</string>
|
||||
<string name="desktop_device">桌面</string>
|
||||
@ -1505,4 +1505,23 @@
|
||||
<string name="loading_remote_file_desc">从已链接移动设备加载文件时请稍候片刻</string>
|
||||
<string name="desktop_app_version_is_incompatible">桌面应用版本 %s 不兼容此应用。</string>
|
||||
<string name="verify_connection">验证连接</string>
|
||||
<string name="v5_4_block_group_members">屏蔽群组成员</string>
|
||||
<string name="v5_4_incognito_groups_descr">使用随机身份创建群组</string>
|
||||
<string name="v5_4_link_mobile_desktop">连接移动端和桌面端应用程序!🔗</string>
|
||||
<string name="v5_4_link_mobile_desktop_descr">通过安全的、抗量子计算机破解的协议。</string>
|
||||
<string name="v5_4_block_group_members_descr">隐藏不需要的信息。</string>
|
||||
<string name="v5_4_better_groups">更佳的群组</string>
|
||||
<string name="v5_4_incognito_groups">匿名群组</string>
|
||||
<string name="remote_host_was_disconnected_toast"><![CDATA[远程主机 <b>%s</b> 已断开连接]]></string>
|
||||
<string name="v5_4_better_groups_descr">加入速度更快、信息更可靠。</string>
|
||||
<string name="v5_4_more_things_descr">- 可选择通知已删除的联系人。
|
||||
\n- 带空格的个人资料名称。
|
||||
\n- 以及更多!</string>
|
||||
<string name="waiting_for_mobile_to_connect_on_port"><![CDATA[正等待移动设备在端口 <i>%s</i> 进行连接]]></string>
|
||||
<string name="group_member_role_author">作者</string>
|
||||
<string name="multicast_connect_automatically">自动连接</string>
|
||||
<string name="waiting_for_desktop">等待桌面中…</string>
|
||||
<string name="found_desktop">找到了桌面</string>
|
||||
<string name="not_compatible">不兼容!</string>
|
||||
<string name="multicast_discoverable_via_local_network">可通过本地网络发现</string>
|
||||
</resources>
|
@ -104,5 +104,5 @@ private fun fileFilterDescription(input: String): String = when(input) {
|
||||
else -> ""
|
||||
}
|
||||
|
||||
actual fun URI.inputStream(): InputStream? = File(URI("file:" + toString().removePrefix("file:"))).inputStream()
|
||||
actual fun URI.outputStream(): OutputStream = File(URI("file:" + toString().removePrefix("file:"))).outputStream()
|
||||
actual fun URI.inputStream(): InputStream? = toFile().inputStream()
|
||||
actual fun URI.outputStream(): OutputStream = toFile().outputStream()
|
||||
|
@ -157,7 +157,7 @@ actual fun ImageBitmap.scale(width: Int, height: Int): ImageBitmap {
|
||||
|
||||
// LALAL
|
||||
actual fun isImage(uri: URI): Boolean {
|
||||
val path = uri.path.lowercase()
|
||||
val path = uri.toFile().path.lowercase()
|
||||
return path.endsWith(".gif") ||
|
||||
path.endsWith(".webp") ||
|
||||
path.endsWith(".png") ||
|
||||
@ -166,7 +166,7 @@ actual fun isImage(uri: URI): Boolean {
|
||||
}
|
||||
|
||||
actual fun isAnimImage(uri: URI, drawable: Any?): Boolean {
|
||||
val path = uri.path.lowercase()
|
||||
val path = uri.toFile().path.lowercase()
|
||||
return path.endsWith(".gif") || path.endsWith(".webp")
|
||||
}
|
||||
|
||||
|
@ -4,6 +4,8 @@ import androidx.compose.foundation.contextMenuOpenDetector
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.*
|
||||
import androidx.compose.ui.graphics.painter.Painter
|
||||
import java.io.File
|
||||
import java.net.URI
|
||||
|
||||
actual fun Modifier.navigationBarsWithImePadding(): Modifier = this
|
||||
|
||||
@ -19,13 +21,15 @@ actual fun ProvideWindowInsets(
|
||||
@Composable
|
||||
actual fun Modifier.desktopOnExternalDrag(
|
||||
enabled: Boolean,
|
||||
onFiles: (List<String>) -> Unit,
|
||||
onFiles: (List<File>) -> Unit,
|
||||
onImage: (Painter) -> Unit,
|
||||
onText: (String) -> Unit
|
||||
): Modifier =
|
||||
onExternalDrag(enabled) {
|
||||
when(val data = it.dragData) {
|
||||
is DragData.FilesList -> onFiles(data.readFiles())
|
||||
// data.readFiles() returns filePath in URI format (where spaces replaces with %20). But it's an error-prone idea to work later
|
||||
// with such format when everywhere we use absolutePath in File() format
|
||||
is DragData.FilesList -> onFiles(data.readFiles().map { URI.create(it).toFile() })
|
||||
is DragData.Image -> onImage(data.readImage())
|
||||
is DragData.Text -> onText(data.readText())
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ actual object AudioPlayer: AudioPlayerInterface {
|
||||
|
||||
// Returns real duration of the track
|
||||
private fun start(fileSource: CryptoFile, seek: Int? = null, onProgressUpdate: (position: Int?, state: TrackState) -> Unit): Int? {
|
||||
val absoluteFilePath = if (fileSource.isAbsolutePath) fileSource.filePath else getAppFilePath(fileSource.filePath)
|
||||
val absoluteFilePath = if (fileSource.isAbsolutePath) fileSource.filePath else getAppFilePath(fileSource.filePath)
|
||||
if (!File(absoluteFilePath).exists()) {
|
||||
Log.e(TAG, "No such file: ${fileSource.filePath}")
|
||||
return null
|
||||
@ -46,16 +46,16 @@ actual object AudioPlayer: AudioPlayerInterface {
|
||||
VideoPlayerHolder.stopAll()
|
||||
RecorderInterface.stopRecording?.invoke()
|
||||
val current = currentlyPlaying.value
|
||||
if (current == null || current.first != fileSource) {
|
||||
if (current == null || current.first != fileSource || !player.status().isPlayable) {
|
||||
stopListener()
|
||||
player.stop()
|
||||
runCatching {
|
||||
if (fileSource.cryptoArgs != null) {
|
||||
val tmpFile = fileSource.createTmpFileIfNeeded()
|
||||
decryptCryptoFile(absoluteFilePath, fileSource.cryptoArgs, tmpFile.absolutePath)
|
||||
player.media().prepare(tmpFile.toURI().toString().replaceFirst("file:", "file://"))
|
||||
player.media().prepare(tmpFile.absolutePath)
|
||||
} else {
|
||||
player.media().prepare(File(absoluteFilePath).toURI().toString().replaceFirst("file:", "file://"))
|
||||
player.media().prepare(absoluteFilePath)
|
||||
}
|
||||
}.onFailure {
|
||||
Log.e(TAG, it.stackTraceToString())
|
||||
@ -171,7 +171,7 @@ actual object AudioPlayer: AudioPlayerInterface {
|
||||
var res: Int? = null
|
||||
try {
|
||||
val helperPlayer = AudioPlayerComponent().mediaPlayer()
|
||||
helperPlayer.media().startPaused(File(unencryptedFilePath).toURI().toString().replaceFirst("file:", "file://"))
|
||||
helperPlayer.media().startPaused(unencryptedFilePath)
|
||||
res = helperPlayer.duration
|
||||
helperPlayer.stop()
|
||||
helperPlayer.release()
|
||||
|
@ -4,6 +4,7 @@ import androidx.compose.ui.platform.ClipboardManager
|
||||
import androidx.compose.ui.platform.UriHandler
|
||||
import androidx.compose.ui.text.AnnotatedString
|
||||
import chat.simplex.common.model.*
|
||||
import chat.simplex.common.views.helpers.generalGetString
|
||||
import chat.simplex.common.views.helpers.withApi
|
||||
import java.io.File
|
||||
import java.net.URI
|
||||
@ -25,14 +26,16 @@ actual fun shareFile(text: String, fileSource: CryptoFile) {
|
||||
withApi {
|
||||
FileChooserLauncher(false) { to: URI? ->
|
||||
if (to != null) {
|
||||
val absolutePath = if (fileSource.isAbsolutePath) fileSource.filePath else getAppFilePath(fileSource.filePath)
|
||||
if (fileSource.cryptoArgs != null) {
|
||||
try {
|
||||
decryptCryptoFile(getAppFilePath(fileSource.filePath), fileSource.cryptoArgs, to.path)
|
||||
decryptCryptoFile(absolutePath, fileSource.cryptoArgs, to.toFile().absolutePath)
|
||||
showToast(generalGetString(MR.strings.file_saved))
|
||||
} catch (e: Exception) {
|
||||
Log.e(TAG, "Unable to decrypt crypto file: " + e.stackTraceToString())
|
||||
}
|
||||
} else {
|
||||
copyFileToFile(File(fileSource.filePath), to) {}
|
||||
copyFileToFile(File(absolutePath), to) {}
|
||||
}
|
||||
}
|
||||
}.launch(fileSource.filePath)
|
||||
|
@ -52,7 +52,7 @@ actual class VideoPlayer actual constructor(
|
||||
private fun start(seek: Long? = null, onProgressUpdate: (position: Long?, state: TrackState) -> Unit): Boolean {
|
||||
val filepath = getAppFilePath(uri)
|
||||
if (filepath == null || !File(filepath).exists()) {
|
||||
Log.e(TAG, "No such file: $uri")
|
||||
Log.e(TAG, "No such file: $filepath")
|
||||
brokenVideo.value = true
|
||||
return false
|
||||
}
|
||||
@ -62,10 +62,9 @@ actual class VideoPlayer actual constructor(
|
||||
}
|
||||
AudioPlayer.stop()
|
||||
VideoPlayerHolder.stopAll()
|
||||
val playerFilePath = uri.toString().replaceFirst("file:", "file://")
|
||||
if (listener.value == null) {
|
||||
runCatching {
|
||||
player.media().prepare(playerFilePath)
|
||||
player.media().prepare(uri.toFile().absolutePath)
|
||||
if (seek != null) {
|
||||
player.seekTo(seek.toInt())
|
||||
}
|
||||
@ -217,12 +216,12 @@ actual class VideoPlayer actual constructor(
|
||||
suspend fun getBitmapFromVideo(defaultPreview: ImageBitmap?, uri: URI?, withAlertOnException: Boolean = true): VideoPlayerInterface.PreviewAndDuration = withContext(playerThread.asCoroutineDispatcher()) {
|
||||
val mediaComponent = getOrCreateHelperPlayer()
|
||||
val player = mediaComponent.mediaPlayer()
|
||||
if (uri == null || !File(uri.rawPath).exists()) {
|
||||
if (uri == null || !uri.toFile().exists()) {
|
||||
if (withAlertOnException) showVideoDecodingException()
|
||||
|
||||
return@withContext VideoPlayerInterface.PreviewAndDuration(preview = defaultPreview, timestamp = 0L, duration = 0L)
|
||||
}
|
||||
player.media().startPaused(uri.toString().replaceFirst("file:", "file://"))
|
||||
player.media().startPaused(uri.toFile().absolutePath)
|
||||
val start = System.currentTimeMillis()
|
||||
var snap: BufferedImage? = null
|
||||
while (snap == null && start + 5000 > System.currentTimeMillis()) {
|
||||
|
@ -3,7 +3,7 @@ package chat.simplex.common.platform
|
||||
import java.net.URI
|
||||
|
||||
fun isVideo(uri: URI): Boolean {
|
||||
val path = uri.path.lowercase()
|
||||
val path = uri.toFile().path.lowercase()
|
||||
return path.endsWith(".mov") ||
|
||||
path.endsWith(".avi") ||
|
||||
path.endsWith(".mp4") ||
|
||||
|
@ -8,14 +8,12 @@ import androidx.compose.ui.unit.Density
|
||||
import chat.simplex.common.model.*
|
||||
import chat.simplex.common.platform.*
|
||||
import chat.simplex.common.simplexWindowState
|
||||
import chat.simplex.res.MR
|
||||
import java.io.ByteArrayInputStream
|
||||
import java.io.File
|
||||
import java.net.URI
|
||||
import javax.imageio.ImageIO
|
||||
import kotlin.io.encoding.Base64
|
||||
import kotlin.io.encoding.ExperimentalEncodingApi
|
||||
import kotlin.io.path.toPath
|
||||
|
||||
private val bStyle = SpanStyle(fontWeight = FontWeight.Bold)
|
||||
private val iStyle = SpanStyle(fontStyle = FontStyle.Italic)
|
||||
@ -90,9 +88,9 @@ actual fun escapedHtmlToAnnotatedString(text: String, density: Density): Annotat
|
||||
actual fun getAppFileUri(fileName: String): URI {
|
||||
val rh = chatModel.currentRemoteHost.value
|
||||
return if (rh == null) {
|
||||
URI(appFilesDir.toURI().toString() + "/" + fileName)
|
||||
createURIFromPath(appFilesDir.absolutePath + "/" + fileName)
|
||||
} else {
|
||||
URI(dataDir.absolutePath + "/remote_hosts/" + rh.storePath + "/simplex_v1_files/" + fileName)
|
||||
createURIFromPath(dataDir.absolutePath + "/remote_hosts/" + rh.storePath + "/simplex_v1_files/" + fileName)
|
||||
}
|
||||
}
|
||||
|
||||
@ -116,11 +114,11 @@ actual suspend fun getLoadedImage(file: CIFile?): Pair<ImageBitmap, ByteArray>?
|
||||
}
|
||||
}
|
||||
|
||||
actual fun getFileName(uri: URI): String? = uri.toPath().toFile().name
|
||||
actual fun getFileName(uri: URI): String? = uri.toFile().name
|
||||
|
||||
actual fun getAppFilePath(uri: URI): String? = uri.path
|
||||
actual fun getAppFilePath(uri: URI): String? = uri.toFile().absolutePath
|
||||
|
||||
actual fun getFileSize(uri: URI): Long? = uri.toPath().toFile().length()
|
||||
actual fun getFileSize(uri: URI): Long? = uri.toFile().length()
|
||||
|
||||
actual fun getBitmapFromUri(uri: URI, withAlertOnException: Boolean): ImageBitmap? =
|
||||
try {
|
||||
|
@ -1,5 +1,5 @@
|
||||
name: simplex-chat
|
||||
version: 5.4.0.5
|
||||
version: 5.4.0.6
|
||||
#synopsis:
|
||||
#description:
|
||||
homepage: https://github.com/simplex-chat/simplex-chat#readme
|
||||
|
@ -5,7 +5,7 @@ cabal-version: 1.12
|
||||
-- see: https://github.com/sol/hpack
|
||||
|
||||
name: simplex-chat
|
||||
version: 5.4.0.5
|
||||
version: 5.4.0.6
|
||||
category: Web, System, Services, Cryptography
|
||||
homepage: https://github.com/simplex-chat/simplex-chat#readme
|
||||
author: simplex.chat
|
||||
|
@ -6066,8 +6066,9 @@ chatCommandP =
|
||||
("/help groups" <|> "/help group" <|> "/hg") $> ChatHelp HSGroups,
|
||||
("/help contacts" <|> "/help contact" <|> "/hc") $> ChatHelp HSContacts,
|
||||
("/help address" <|> "/ha") $> ChatHelp HSMyAddress,
|
||||
"/help incognito" $> ChatHelp HSIncognito,
|
||||
("/help incognito" <|> "/hi") $> ChatHelp HSIncognito,
|
||||
("/help messages" <|> "/hm") $> ChatHelp HSMessages,
|
||||
("/help remote" <|> "/hr") $> ChatHelp HSRemote,
|
||||
("/help settings" <|> "/hs") $> ChatHelp HSSettings,
|
||||
("/help db" <|> "/hd") $> ChatHelp HSDatabase,
|
||||
("/help" <|> "/h") $> ChatHelp HSMain,
|
||||
@ -6174,7 +6175,6 @@ chatCommandP =
|
||||
"/set disappear " *> (SetUserTimedMessages <$> (("yes" $> True) <|> ("no" $> False))),
|
||||
("/incognito" <* optional (A.space *> onOffP)) $> ChatHelp HSIncognito,
|
||||
"/set device name " *> (SetLocalDeviceName <$> textP),
|
||||
-- "/create remote host" $> CreateRemoteHost,
|
||||
"/list remote hosts" $> ListRemoteHosts,
|
||||
"/switch remote host " *> (SwitchRemoteHost <$> ("local" $> Nothing <|> (Just <$> A.decimal))),
|
||||
"/start remote host " *> (StartRemoteHost <$> ("new" $> Nothing <|> (Just <$> ((,) <$> A.decimal <*> (" multicast=" *> onOffP <|> pure False))))),
|
||||
|
@ -203,7 +203,7 @@ data ChatController = ChatController
|
||||
contactMergeEnabled :: TVar Bool
|
||||
}
|
||||
|
||||
data HelpSection = HSMain | HSFiles | HSGroups | HSContacts | HSMyAddress | HSIncognito | HSMarkdown | HSMessages | HSSettings | HSDatabase
|
||||
data HelpSection = HSMain | HSFiles | HSGroups | HSContacts | HSMyAddress | HSIncognito | HSMarkdown | HSMessages | HSRemote | HSSettings | HSDatabase
|
||||
deriving (Show)
|
||||
|
||||
data ChatCommand
|
||||
@ -662,14 +662,14 @@ data ChatResponse
|
||||
| CRRemoteHostSessionCode {remoteHost_ :: Maybe RemoteHostInfo, sessionCode :: Text}
|
||||
| CRNewRemoteHost {remoteHost :: RemoteHostInfo}
|
||||
| CRRemoteHostConnected {remoteHost :: RemoteHostInfo}
|
||||
| CRRemoteHostStopped {remoteHostId_ :: Maybe RemoteHostId}
|
||||
| CRRemoteHostStopped {remoteHostId_ :: Maybe RemoteHostId, rhsState :: RemoteHostSessionState, rhStopReason :: RemoteHostStopReason}
|
||||
| CRRemoteFileStored {remoteHostId :: RemoteHostId, remoteFileSource :: CryptoFile}
|
||||
| CRRemoteCtrlList {remoteCtrls :: [RemoteCtrlInfo]}
|
||||
| CRRemoteCtrlFound {remoteCtrl :: RemoteCtrlInfo, ctrlAppInfo_ :: Maybe CtrlAppInfo, appVersion :: AppVersion, compatible :: Bool}
|
||||
| CRRemoteCtrlConnecting {remoteCtrl_ :: Maybe RemoteCtrlInfo, ctrlAppInfo :: CtrlAppInfo, appVersion :: AppVersion}
|
||||
| CRRemoteCtrlSessionCode {remoteCtrl_ :: Maybe RemoteCtrlInfo, sessionCode :: Text}
|
||||
| CRRemoteCtrlConnected {remoteCtrl :: RemoteCtrlInfo}
|
||||
| CRRemoteCtrlStopped
|
||||
| CRRemoteCtrlStopped {rcsState :: RemoteCtrlSessionState, rcStopReason :: RemoteCtrlStopReason}
|
||||
| CRSQLResult {rows :: [Text]}
|
||||
| CRSlowSQLQueries {chatQueries :: [SlowSQLQuery], agentQueries :: [SlowSQLQuery]}
|
||||
| CRDebugLocks {chatLockName :: Maybe String, agentLocks :: AgentLocks}
|
||||
@ -700,14 +700,14 @@ allowRemoteEvent = \case
|
||||
CRRemoteHostSessionCode {} -> False
|
||||
CRNewRemoteHost _ -> False
|
||||
CRRemoteHostConnected _ -> False
|
||||
CRRemoteHostStopped _ -> False
|
||||
CRRemoteHostStopped {} -> False
|
||||
CRRemoteFileStored {} -> False
|
||||
CRRemoteCtrlList _ -> False
|
||||
CRRemoteCtrlFound {} -> False
|
||||
CRRemoteCtrlConnecting {} -> False
|
||||
CRRemoteCtrlSessionCode {} -> False
|
||||
CRRemoteCtrlConnected _ -> False
|
||||
CRRemoteCtrlStopped -> False
|
||||
CRRemoteCtrlStopped {} -> False
|
||||
CRSQLResult _ -> False
|
||||
CRSlowSQLQueries {} -> False
|
||||
_ -> True
|
||||
@ -1083,6 +1083,12 @@ data RemoteHostError
|
||||
| RHEProtocolError RemoteProtocolError
|
||||
deriving (Show, Exception)
|
||||
|
||||
data RemoteHostStopReason
|
||||
= RHSRConnectionFailed ChatError
|
||||
| RHSRCrashed ChatError
|
||||
| RHSRDisconnected
|
||||
deriving (Show, Exception)
|
||||
|
||||
-- TODO review errors, some of it can be covered by HTTP2 errors
|
||||
data RemoteCtrlError
|
||||
= RCEInactive -- ^ No session is running
|
||||
@ -1098,6 +1104,13 @@ data RemoteCtrlError
|
||||
| RCEProtocolError {protocolError :: RemoteProtocolError}
|
||||
deriving (Show, Exception)
|
||||
|
||||
data RemoteCtrlStopReason
|
||||
= RCSRDiscoveryFailed ChatError
|
||||
| RCSRConnectionFailed ChatError
|
||||
| RCSRSetupFailed ChatError
|
||||
| RCSRDisconnected
|
||||
deriving (Show, Exception)
|
||||
|
||||
data ArchiveError
|
||||
= AEImport {chatError :: ChatError}
|
||||
| AEImportFile {file :: String, chatError :: ChatError}
|
||||
@ -1323,6 +1336,10 @@ $(JQ.deriveJSON (sumTypeJSON $ dropPrefix "RCS") ''RemoteCtrlSessionState)
|
||||
|
||||
$(JQ.deriveJSON defaultJSON ''RemoteCtrlInfo)
|
||||
|
||||
$(JQ.deriveJSON (sumTypeJSON $ dropPrefix "RCSR") ''RemoteCtrlStopReason)
|
||||
|
||||
$(JQ.deriveJSON (sumTypeJSON $ dropPrefix "RHSR") ''RemoteHostStopReason)
|
||||
|
||||
$(JQ.deriveJSON (sumTypeJSON $ dropPrefix "CR") ''ChatResponse)
|
||||
|
||||
$(JQ.deriveFromJSON defaultJSON ''ArchiveConfig)
|
||||
|
@ -10,6 +10,7 @@ module Simplex.Chat.Help
|
||||
myAddressHelpInfo,
|
||||
incognitoHelpInfo,
|
||||
messagesHelpInfo,
|
||||
remoteHelpInfo,
|
||||
markdownInfo,
|
||||
settingsInfo,
|
||||
databaseHelpInfo,
|
||||
@ -87,7 +88,7 @@ chatHelpInfo =
|
||||
green "Create your address: " <> highlight "/address",
|
||||
"",
|
||||
green "Other commands:",
|
||||
indent <> highlight "/help <topic> " <> " - help on: " <> listHighlight ["groups", "contacts", "messages", "files", "address", "settings", "db"],
|
||||
indent <> highlight "/help <topic> " <> " - help on: " <> listHighlight ["groups", "contacts", "messages", "files", "address", "incognito", "remote", "settings", "db"],
|
||||
indent <> highlight "/profile " <> " - show / update user profile",
|
||||
indent <> highlight "/delete <contact>" <> " - delete contact and all messages with them",
|
||||
indent <> highlight "/chats " <> " - most recent chats",
|
||||
@ -272,6 +273,34 @@ messagesHelpInfo =
|
||||
indent <> highlight "! #team (hi) <new msg> " <> " - to edit your message in the group #team"
|
||||
]
|
||||
|
||||
remoteHelpInfo :: [StyledString]
|
||||
remoteHelpInfo =
|
||||
map
|
||||
styleMarkdown
|
||||
[ green "Remote control",
|
||||
"You can use CLI as a remote controller for a mobile app or as a remote host for a desktop app (or another CLI).",
|
||||
"For example, you can run CLI on a server and use it from a desktop computer, connecting via SSH port forwarding.",
|
||||
"",
|
||||
indent <> highlight "/set device name <name> " <> " - set CLI name for remote connections",
|
||||
"",
|
||||
green "Using as remote controller",
|
||||
indent <> highlight "/start remote host new " <> " - pair and connect a new remote host",
|
||||
indent <> highlight "/start remote host <id> [multicast=on] " <> " - start connection with a known (paired) remote host",
|
||||
indent <> highlight "/stop remote host new " <> " - cancel pairing with a new remote host",
|
||||
indent <> highlight "/stop remote host <id> " <> " - stop connection with connected remote host",
|
||||
indent <> highlight "/switch remote host local " <> " - switch to using local database",
|
||||
indent <> highlight "/switch remote host <id> " <> " - switch to connected remote host",
|
||||
indent <> highlight "/list remote hosts " <> " - list known remote hosts",
|
||||
indent <> highlight "/delete remote host <id> " <> " - delete (unpair) known remote hosts - also deletes all host files from controller",
|
||||
"",
|
||||
green "Using as remote host",
|
||||
indent <> highlight "/connect remote ctrl <session_address> " <> " - connect to remote controller via the adress from /start remote host",
|
||||
indent <> highlight "/stop remote ctrl " <> " - stop connection with remote controller",
|
||||
indent <> highlight "/find remote ctrl " <> " - find known remote controller on the local network (it should be started with multicast=on)",
|
||||
indent <> highlight "/list remote ctrls " <> " - list known remote controllers",
|
||||
indent <> highlight "/delete remote ctrl <id> " <> " - delete known remote controller"
|
||||
]
|
||||
|
||||
markdownInfo :: [StyledString]
|
||||
markdownInfo =
|
||||
map
|
||||
|
@ -169,12 +169,12 @@ startRemoteHost rh_ = do
|
||||
handleConnectError :: ChatMonad m => RHKey -> SessionSeq -> m a -> m a
|
||||
handleConnectError rhKey sessSeq action = action `catchChatError` \err -> do
|
||||
logError $ "startRemoteHost.rcConnectHost crashed: " <> tshow err
|
||||
cancelRemoteHostSession (Just sessSeq) rhKey
|
||||
cancelRemoteHostSession (Just (sessSeq, RHSRConnectionFailed err)) rhKey
|
||||
throwError err
|
||||
handleHostError :: ChatMonad m => SessionSeq -> TVar RHKey -> m () -> m ()
|
||||
handleHostError sessSeq rhKeyVar action = action `catchChatError` \err -> do
|
||||
logError $ "startRemoteHost.waitForHostSession crashed: " <> tshow err
|
||||
readTVarIO rhKeyVar >>= cancelRemoteHostSession (Just sessSeq)
|
||||
readTVarIO rhKeyVar >>= cancelRemoteHostSession (Just (sessSeq, RHSRCrashed err))
|
||||
waitForHostSession :: ChatMonad m => Maybe RemoteHostInfo -> RHKey -> SessionSeq -> TVar RHKey -> RCStepTMVar (ByteString, TLS, RCStepTMVar (RCHostSession, RCHostHello, RCHostPairing)) -> m ()
|
||||
waitForHostSession remoteHost_ rhKey sseq rhKeyVar vars = do
|
||||
(sessId, tls, vars') <- timeoutThrow (ChatErrorRemoteHost rhKey RHETimeout) 60000000 $ takeRCStep vars
|
||||
@ -220,7 +220,7 @@ startRemoteHost rh_ = do
|
||||
onDisconnected :: ChatMonad m => RHKey -> SessionSeq -> m ()
|
||||
onDisconnected rhKey sseq = do
|
||||
logDebug $ "HTTP2 client disconnected: " <> tshow (rhKey, sseq)
|
||||
cancelRemoteHostSession (Just sseq) rhKey
|
||||
cancelRemoteHostSession (Just (sseq, RHSRDisconnected)) rhKey
|
||||
pollEvents :: ChatMonad m => RemoteHostId -> RemoteHostClient -> m ()
|
||||
pollEvents rhId rhClient = do
|
||||
oq <- asks outputQ
|
||||
@ -246,24 +246,25 @@ closeRemoteHost rhKey = do
|
||||
logNote $ "Closing remote host session for " <> tshow rhKey
|
||||
cancelRemoteHostSession Nothing rhKey
|
||||
|
||||
cancelRemoteHostSession :: ChatMonad m => Maybe SessionSeq -> RHKey -> m ()
|
||||
cancelRemoteHostSession sseq_ rhKey = do
|
||||
cancelRemoteHostSession :: ChatMonad m => Maybe (SessionSeq, RemoteHostStopReason) -> RHKey -> m ()
|
||||
cancelRemoteHostSession handlerInfo_ rhKey = do
|
||||
sessions <- asks remoteHostSessions
|
||||
crh <- asks currentRemoteHost
|
||||
deregistered <- atomically $
|
||||
TM.lookup rhKey sessions >>= \case
|
||||
Nothing -> pure Nothing
|
||||
Just (sessSeq, _) | maybe False (/= sessSeq) sseq_ -> pure Nothing -- ignore cancel from a ghost session handler
|
||||
Just (sessSeq, _) | maybe False (/= sessSeq) (fst <$> handlerInfo_) -> pure Nothing -- ignore cancel from a ghost session handler
|
||||
Just (_, rhs) -> do
|
||||
TM.delete rhKey sessions
|
||||
modifyTVar' crh $ \cur -> if (RHId <$> cur) == Just rhKey then Nothing else cur -- only wipe the closing RH
|
||||
pure $ Just rhs
|
||||
forM_ deregistered $ \session -> do
|
||||
liftIO $ cancelRemoteHost handlingError session `catchAny` (logError . tshow)
|
||||
when handlingError $ toView $ CRRemoteHostStopped rhId_
|
||||
forM_ (snd <$> handlerInfo_) $ \rhStopReason ->
|
||||
toView $ CRRemoteHostStopped {remoteHostId_, rhsState = rhsSessionState session, rhStopReason}
|
||||
where
|
||||
handlingError = isJust sseq_
|
||||
rhId_ = case rhKey of
|
||||
handlingError = isJust handlerInfo_
|
||||
remoteHostId_ = case rhKey of
|
||||
RHNew -> Nothing
|
||||
RHId rhId -> Just rhId
|
||||
|
||||
@ -395,7 +396,7 @@ findKnownRemoteCtrl = do
|
||||
sseq <- startRemoteCtrlSession
|
||||
foundCtrl <- newEmptyTMVarIO
|
||||
cmdOk <- newEmptyTMVarIO
|
||||
action <- async $ handleCtrlError sseq "findKnownRemoteCtrl.discover" $ do
|
||||
action <- async $ handleCtrlError sseq RCSRDiscoveryFailed "findKnownRemoteCtrl.discover" $ do
|
||||
atomically $ takeTMVar cmdOk
|
||||
(RCCtrlPairing {ctrlFingerprint}, inv@(RCVerifiedInvitation RCInvitation {app})) <-
|
||||
timeoutThrow (ChatErrorRemoteCtrl RCETimeout) discoveryTimeout . withAgent $ \a -> rcDiscoverCtrl a pairings
|
||||
@ -441,7 +442,7 @@ startRemoteCtrlSession = do
|
||||
Right sseq <$ writeTVar session (Just (sseq, RCSessionStarting))
|
||||
|
||||
connectRemoteCtrl :: ChatMonad m => RCVerifiedInvitation -> SessionSeq -> m (Maybe RemoteCtrlInfo, CtrlAppInfo)
|
||||
connectRemoteCtrl verifiedInv@(RCVerifiedInvitation inv@RCInvitation {ca, app}) sseq = handleCtrlError sseq "connectRemoteCtrl" $ do
|
||||
connectRemoteCtrl verifiedInv@(RCVerifiedInvitation inv@RCInvitation {ca, app}) sseq = handleCtrlError sseq RCSRConnectionFailed "connectRemoteCtrl" $ do
|
||||
ctrlInfo@CtrlAppInfo {deviceName = ctrlDeviceName} <- parseCtrlAppInfo app
|
||||
v <- checkAppVersion ctrlInfo
|
||||
rc_ <- withStore' $ \db -> getRemoteCtrlByFingerprint db ca
|
||||
@ -452,7 +453,7 @@ connectRemoteCtrl verifiedInv@(RCVerifiedInvitation inv@RCInvitation {ca, app})
|
||||
cmdOk <- newEmptyTMVarIO
|
||||
rcsWaitSession <- async $ do
|
||||
atomically $ takeTMVar cmdOk
|
||||
handleCtrlError sseq "waitForCtrlSession" $ waitForCtrlSession rc_ ctrlDeviceName rcsClient vars
|
||||
handleCtrlError sseq RCSRConnectionFailed "waitForCtrlSession" $ waitForCtrlSession rc_ ctrlDeviceName rcsClient vars
|
||||
updateRemoteCtrlSession sseq $ \case
|
||||
RCSessionStarting -> Right RCSessionConnecting {remoteCtrlId_ = remoteCtrlId' <$> rc_, rcsClient, rcsWaitSession}
|
||||
_ -> Left $ ChatErrorRemoteCtrl RCEBadState
|
||||
@ -602,7 +603,7 @@ verifyRemoteCtrlSession execChatCommand sessCode' = do
|
||||
Nothing -> throwError $ ChatErrorRemoteCtrl RCEInactive
|
||||
Just (sseq, RCSessionPendingConfirmation {rcsClient, ctrlDeviceName = ctrlName, sessionCode, rcsWaitConfirmation}) -> pure (sseq, rcsClient, ctrlName, sessionCode, rcsWaitConfirmation)
|
||||
_ -> throwError $ ChatErrorRemoteCtrl RCEBadState
|
||||
handleCtrlError sseq "verifyRemoteCtrlSession" $ do
|
||||
handleCtrlError sseq RCSRSetupFailed "verifyRemoteCtrlSession" $ do
|
||||
let verified = sameVerificationCode sessCode' sessionCode
|
||||
timeoutThrow (ChatErrorRemoteCtrl RCETimeout) networkIOTimeout . liftIO $ confirmCtrlSession client verified -- signal verification result before crashing
|
||||
unless verified $ throwError $ ChatErrorRemoteCtrl $ RCEProtocolError PRESessionCode
|
||||
@ -630,31 +631,32 @@ verifyRemoteCtrlSession execChatCommand sessCode' = do
|
||||
monitor sseq server = do
|
||||
res <- waitCatch server
|
||||
logInfo $ "HTTP2 server stopped: " <> tshow res
|
||||
cancelActiveRemoteCtrl (Just sseq)
|
||||
cancelActiveRemoteCtrl $ Just (sseq, RCSRDisconnected)
|
||||
|
||||
stopRemoteCtrl :: ChatMonad m => m ()
|
||||
stopRemoteCtrl = cancelActiveRemoteCtrl Nothing
|
||||
|
||||
handleCtrlError :: ChatMonad m => SessionSeq -> Text -> m a -> m a
|
||||
handleCtrlError sseq name action =
|
||||
handleCtrlError :: ChatMonad m => SessionSeq -> (ChatError -> RemoteCtrlStopReason) -> Text -> m a -> m a
|
||||
handleCtrlError sseq mkReason name action =
|
||||
action `catchChatError` \e -> do
|
||||
logError $ name <> " remote ctrl error: " <> tshow e
|
||||
cancelActiveRemoteCtrl (Just sseq)
|
||||
cancelActiveRemoteCtrl $ Just (sseq, mkReason e)
|
||||
throwError e
|
||||
|
||||
-- | Stop session controller, unless session update key is present but stale
|
||||
cancelActiveRemoteCtrl :: ChatMonad m => Maybe SessionSeq -> m ()
|
||||
cancelActiveRemoteCtrl sseq_ = handleAny (logError . tshow) $ do
|
||||
cancelActiveRemoteCtrl :: ChatMonad m => Maybe (SessionSeq, RemoteCtrlStopReason) -> m ()
|
||||
cancelActiveRemoteCtrl handlerInfo_ = handleAny (logError . tshow) $ do
|
||||
var <- asks remoteCtrlSession
|
||||
session_ <- atomically $ readTVar var >>= \case
|
||||
Nothing -> pure Nothing
|
||||
Just (oldSeq, _) | maybe False (/= oldSeq) sseq_ -> pure Nothing
|
||||
Just (oldSeq, _) | maybe False (/= oldSeq) (fst <$> handlerInfo_) -> pure Nothing
|
||||
Just (_, s) -> Just s <$ writeTVar var Nothing
|
||||
forM_ session_ $ \session -> do
|
||||
liftIO $ cancelRemoteCtrl handlingError session
|
||||
when handlingError $ toView CRRemoteCtrlStopped
|
||||
forM_ (snd <$> handlerInfo_) $ \rcStopReason ->
|
||||
toView CRRemoteCtrlStopped {rcsState = rcsSessionState session, rcStopReason}
|
||||
where
|
||||
handlingError = isJust sseq_
|
||||
handlingError = isJust handlerInfo_
|
||||
|
||||
cancelRemoteCtrl :: Bool -> RemoteCtrlSession -> IO ()
|
||||
cancelRemoteCtrl handlingError = \case
|
||||
|
@ -58,13 +58,15 @@ runInputLoop ct@ChatTerminal {termState, liveMessageState} cc = forever $ do
|
||||
rh' = if either (const False) allowRemoteCommand cmd then rh else Nothing
|
||||
unless (isMessage cmd) $ echo s
|
||||
r <- runReaderT (execChatCommand rh' bs) cc
|
||||
processResp s cmd r
|
||||
processResp s cmd rh r
|
||||
printRespToTerminal ct cc False rh r
|
||||
startLiveMessage cmd r
|
||||
where
|
||||
echo s = printToTerminal ct [plain s]
|
||||
processResp s cmd = \case
|
||||
CRActiveUser _ -> setActive ct ""
|
||||
processResp s cmd rh = \case
|
||||
CRActiveUser u -> case rh of
|
||||
Nothing -> setActive ct ""
|
||||
Just rhId -> updateRemoteUser ct u rhId
|
||||
CRChatItems u chatName_ _ -> whenCurrUser cc u $ mapM_ (setActive ct . chatActiveTo) chatName_
|
||||
CRNewChatItem u (AChatItem _ SMDSnd cInfo _) -> whenCurrUser cc u $ setActiveChat ct cInfo
|
||||
CRChatItemUpdated u (AChatItem _ SMDSnd cInfo _) -> whenCurrUser cc u $ setActiveChat ct cInfo
|
||||
|
@ -10,6 +10,8 @@
|
||||
module Simplex.Chat.Terminal.Output where
|
||||
|
||||
import Control.Concurrent (ThreadId)
|
||||
import Control.Logger.Simple
|
||||
import Control.Monad
|
||||
import Control.Monad.Catch (MonadMask)
|
||||
import Control.Monad.Except
|
||||
import Control.Monad.Reader
|
||||
@ -18,21 +20,23 @@ import Data.Text (Text)
|
||||
import qualified Data.Text as T
|
||||
import Data.Time.Clock (getCurrentTime)
|
||||
import Data.Time.LocalTime (getCurrentTimeZone)
|
||||
import Simplex.Chat (processChatCommand)
|
||||
import Simplex.Chat (execChatCommand, processChatCommand)
|
||||
import Simplex.Chat.Controller
|
||||
import Simplex.Chat.Markdown
|
||||
import Simplex.Chat.Messages
|
||||
import Simplex.Chat.Messages.CIContent (CIContent(..), SMsgDirection (..))
|
||||
import Simplex.Chat.Options
|
||||
import Simplex.Chat.Protocol (MsgContent (..), msgContentText)
|
||||
import Simplex.Chat.Remote.Types (RemoteHostId)
|
||||
import Simplex.Chat.Remote.Types (RHKey (..), RemoteHostId, RemoteHostInfo (..), RemoteHostSession (..))
|
||||
import Simplex.Chat.Styled
|
||||
import Simplex.Chat.Terminal.Notification (Notification (..), initializeNotifications)
|
||||
import Simplex.Chat.Types
|
||||
import Simplex.Chat.View
|
||||
import Simplex.Messaging.Agent.Protocol
|
||||
import Simplex.Messaging.Encoding.String
|
||||
import Simplex.Messaging.Util (safeDecodeUtf8)
|
||||
import Simplex.Messaging.TMap (TMap)
|
||||
import qualified Simplex.Messaging.TMap as TM
|
||||
import Simplex.Messaging.Util (safeDecodeUtf8, tshow)
|
||||
import System.Console.ANSI.Types
|
||||
import System.IO (IOMode (..), hPutStrLn, withFile)
|
||||
import System.Mem.Weak (Weak)
|
||||
@ -48,7 +52,8 @@ data ChatTerminal = ChatTerminal
|
||||
nextMessageRow :: TVar Int,
|
||||
termLock :: TMVar (),
|
||||
sendNotification :: Maybe (Notification -> IO ()),
|
||||
activeTo :: TVar String
|
||||
activeTo :: TVar String,
|
||||
currentRemoteUsers :: TMap RemoteHostId User
|
||||
}
|
||||
|
||||
data TerminalState = TerminalState
|
||||
@ -103,6 +108,7 @@ newChatTerminal t opts = do
|
||||
nextMessageRow <- newTVarIO lastRow
|
||||
sendNotification <- if muteNotifications opts then pure Nothing else Just <$> initializeNotifications
|
||||
activeTo <- newTVarIO ""
|
||||
currentRemoteUsers <- newTVarIO mempty
|
||||
-- threadDelay 500000 -- this delay is the same as timeout in getTerminalSize
|
||||
pure
|
||||
ChatTerminal
|
||||
@ -113,7 +119,8 @@ newChatTerminal t opts = do
|
||||
nextMessageRow,
|
||||
termLock,
|
||||
sendNotification,
|
||||
activeTo
|
||||
activeTo,
|
||||
currentRemoteUsers
|
||||
}
|
||||
|
||||
mkTermState :: TerminalState
|
||||
@ -142,12 +149,14 @@ runTerminalOutput ct cc@ChatController {outputQ, showLiveItems, logFilePath} = d
|
||||
case r of
|
||||
CRNewChatItem u ci -> markChatItemRead u ci
|
||||
CRChatItemUpdated u ci -> markChatItemRead u ci
|
||||
CRRemoteHostConnected {remoteHost = RemoteHostInfo {remoteHostId}} -> getRemoteUser remoteHostId
|
||||
CRRemoteHostStopped {remoteHostId_} -> mapM_ removeRemoteUser remoteHostId_
|
||||
_ -> pure ()
|
||||
let printResp = case logFilePath of
|
||||
Just path -> if logResponseToFile r then logResponse path else printToTerminal ct
|
||||
_ -> printToTerminal ct
|
||||
liveItems <- readTVarIO showLiveItems
|
||||
responseString cc liveItems outputRH r >>= printResp
|
||||
responseString ct cc liveItems outputRH r >>= printResp
|
||||
responseNotification ct cc r
|
||||
where
|
||||
markChatItemRead u (AChatItem _ _ chat ci@ChatItem {chatDir, meta = CIMeta {itemStatus}}) =
|
||||
@ -158,6 +167,10 @@ runTerminalOutput ct cc@ChatController {outputQ, showLiveItems, logFilePath} = d
|
||||
void $ runReaderT (runExceptT $ processChatCommand (APIChatRead chatRef (Just (itemId, itemId)))) cc
|
||||
_ -> pure ()
|
||||
logResponse path s = withFile path AppendMode $ \h -> mapM_ (hPutStrLn h . unStyle) s
|
||||
getRemoteUser rhId = runReaderT (execChatCommand (Just rhId) "/user") cc >>= \case
|
||||
CRActiveUser {user} -> updateRemoteUser ct user rhId
|
||||
cr -> logError $ "Unexpected reply while getting remote user: " <> tshow cr
|
||||
removeRemoteUser rhId = atomically $ TM.delete rhId (currentRemoteUsers ct)
|
||||
|
||||
responseNotification :: ChatTerminal -> ChatController -> ChatResponse -> IO ()
|
||||
responseNotification t@ChatTerminal {sendNotification} cc = \case
|
||||
@ -254,15 +267,29 @@ whenCurrUser cc u a = do
|
||||
sameUser User {userId = uId} = maybe False $ \User {userId} -> userId == uId
|
||||
|
||||
printRespToTerminal :: ChatTerminal -> ChatController -> Bool -> Maybe RemoteHostId -> ChatResponse -> IO ()
|
||||
printRespToTerminal ct cc liveItems outputRH r = responseString cc liveItems outputRH r >>= printToTerminal ct
|
||||
printRespToTerminal ct cc liveItems outputRH r = responseString ct cc liveItems outputRH r >>= printToTerminal ct
|
||||
|
||||
responseString :: ChatController -> Bool -> Maybe RemoteHostId -> ChatResponse -> IO [StyledString]
|
||||
responseString cc liveItems outputRH r = do
|
||||
currentRH <- readTVarIO $ currentRemoteHost cc
|
||||
user <- readTVarIO $ currentUser cc -- XXX: local user, should be subsumed by remote when connected
|
||||
responseString :: ChatTerminal -> ChatController -> Bool -> Maybe RemoteHostId -> ChatResponse -> IO [StyledString]
|
||||
responseString ct cc liveItems outputRH r = do
|
||||
cu <- getCurrentUser ct cc
|
||||
ts <- getCurrentTime
|
||||
tz <- getCurrentTimeZone
|
||||
pure $ responseToView (currentRH, user) (config cc) liveItems ts tz outputRH r
|
||||
pure $ responseToView cu (config cc) liveItems ts tz outputRH r
|
||||
|
||||
updateRemoteUser :: ChatTerminal -> User -> RemoteHostId -> IO ()
|
||||
updateRemoteUser ct user rhId = atomically $ TM.insert rhId user (currentRemoteUsers ct)
|
||||
|
||||
getCurrentUser :: ChatTerminal -> ChatController -> IO (Maybe RemoteHostId, Maybe User)
|
||||
getCurrentUser ct cc = atomically $ do
|
||||
localUser_ <- readTVar (currentUser cc)
|
||||
readTVar (currentRemoteHost cc) >>= \case
|
||||
Nothing -> pure (Nothing, localUser_)
|
||||
Just rhId ->
|
||||
TM.lookup (RHId rhId) (remoteHostSessions cc) >>= \case
|
||||
Just (_, RHSessionConnected {}) -> do
|
||||
hostUser_ <- TM.lookup rhId (currentRemoteUsers ct)
|
||||
pure (Just rhId, hostUser_)
|
||||
_ -> pure (Nothing, localUser_)
|
||||
|
||||
printToTerminal :: ChatTerminal -> [StyledString] -> IO ()
|
||||
printToTerminal ct s =
|
||||
|
@ -135,6 +135,7 @@ responseToView hu@(currentRH, user_) ChatConfig {logLevel, showReactions, showRe
|
||||
HSIncognito -> incognitoHelpInfo
|
||||
HSMessages -> messagesHelpInfo
|
||||
HSMarkdown -> markdownInfo
|
||||
HSRemote -> remoteHelpInfo
|
||||
HSSettings -> settingsInfo
|
||||
HSDatabase -> databaseHelpInfo
|
||||
CRWelcome user -> chatWelcome user
|
||||
@ -298,8 +299,8 @@ responseToView hu@(currentRH, user_) ChatConfig {logLevel, showReactions, showRe
|
||||
]
|
||||
CRNewRemoteHost RemoteHostInfo {remoteHostId = rhId, hostDeviceName} -> ["new remote host " <> sShow rhId <> " added: " <> plain hostDeviceName]
|
||||
CRRemoteHostConnected RemoteHostInfo {remoteHostId = rhId} -> ["remote host " <> sShow rhId <> " connected"]
|
||||
CRRemoteHostStopped rhId_ ->
|
||||
[ maybe "new remote host" (mappend "remote host " . sShow) rhId_ <> " stopped"
|
||||
CRRemoteHostStopped {remoteHostId_} ->
|
||||
[ maybe "new remote host" (mappend "remote host " . sShow) remoteHostId_ <> " stopped"
|
||||
]
|
||||
CRRemoteFileStored rhId (CryptoFile filePath cfArgs_) ->
|
||||
[plain $ "file " <> filePath <> " stored on remote host " <> show rhId]
|
||||
@ -309,8 +310,9 @@ responseToView hu@(currentRH, user_) ChatConfig {logLevel, showReactions, showRe
|
||||
[ "remote controller " <> sShow remoteCtrlId <> " found: "
|
||||
<> maybe (deviceName <> "not compatible") (\info -> viewRemoteCtrl info appVersion compatible) ctrlAppInfo_
|
||||
]
|
||||
<> [ "use " <> highlight ("/confirm remote ctrl " <> show remoteCtrlId) <> " to connect" | isJust ctrlAppInfo_ && compatible]
|
||||
where
|
||||
deviceName = if T.null ctrlDeviceName then "" else plain ctrlDeviceName <> ", "
|
||||
deviceName = if T.null ctrlDeviceName then "" else plain ctrlDeviceName <> ", "
|
||||
CRRemoteCtrlConnecting {remoteCtrl_, ctrlAppInfo, appVersion} ->
|
||||
[ (maybe "connecting new remote controller" (\RemoteCtrlInfo {remoteCtrlId} -> "connecting remote controller " <> sShow remoteCtrlId) remoteCtrl_ <> ": ")
|
||||
<> viewRemoteCtrl ctrlAppInfo appVersion True
|
||||
@ -322,7 +324,7 @@ responseToView hu@(currentRH, user_) ChatConfig {logLevel, showReactions, showRe
|
||||
]
|
||||
CRRemoteCtrlConnected RemoteCtrlInfo {remoteCtrlId = rcId, ctrlDeviceName} ->
|
||||
["remote controller " <> sShow rcId <> " session started with " <> plain ctrlDeviceName]
|
||||
CRRemoteCtrlStopped -> ["remote controller stopped"]
|
||||
CRRemoteCtrlStopped {} -> ["remote controller stopped"]
|
||||
CRSQLResult rows -> map plain rows
|
||||
CRSlowSQLQueries {chatQueries, agentQueries} ->
|
||||
let viewQuery SlowSQLQuery {query, queryStats = SlowQueryStats {count, timeMax, timeAvg}} =
|
||||
|
@ -44,6 +44,7 @@ remoteTests = describe "Remote" $ do
|
||||
it "should send files from CLI without /store" remoteCLIFileTest
|
||||
it "switches remote hosts" switchRemoteHostTest
|
||||
it "indicates remote hosts" indicateRemoteHostTest
|
||||
it "works with multiple profiles" multipleProfilesTest
|
||||
|
||||
-- * Chat commands
|
||||
|
||||
@ -416,6 +417,55 @@ indicateRemoteHostTest = testChat4 aliceProfile aliceDesktopProfile bobProfile c
|
||||
desktop <##> cath
|
||||
cath <##> desktop
|
||||
|
||||
multipleProfilesTest :: FilePath -> IO ()
|
||||
multipleProfilesTest = testChat4 aliceProfile aliceDesktopProfile bobProfile cathProfile $ \mobile desktop bob cath -> do
|
||||
connectUsers desktop cath
|
||||
|
||||
desktop ##> "/create user desk_bottom"
|
||||
desktop <## "user profile: desk_bottom"
|
||||
desktop <## "use /p <display name> to change it"
|
||||
desktop <## "(the updated profile will be sent to all your contacts)"
|
||||
desktop ##> "/users"
|
||||
desktop <## "alice_desktop (Alice Desktop)"
|
||||
desktop <## "desk_bottom (active)"
|
||||
|
||||
startRemote mobile desktop
|
||||
contactBob desktop bob
|
||||
desktop ##> "/users"
|
||||
desktop <## "alice (Alice) (active)"
|
||||
|
||||
desktop ##> "/create user alt_alice"
|
||||
desktop <## "user profile: alt_alice"
|
||||
desktop <## "use /p <display name> to change it"
|
||||
desktop <## "(the updated profile will be sent to all your contacts)"
|
||||
|
||||
desktop ##> "/users"
|
||||
desktop <## "alice (Alice)"
|
||||
desktop <## "alt_alice (active)"
|
||||
|
||||
desktop ##> "/user"
|
||||
desktop <## "user profile: alt_alice"
|
||||
desktop <## "use /p <display name> to change it"
|
||||
desktop <## "(the updated profile will be sent to all your contacts)"
|
||||
|
||||
bob #> "@alice hi"
|
||||
(desktop, "[user: alice] ") ^<# "bob> hi"
|
||||
|
||||
cath #> "@alice_desktop hello"
|
||||
(desktop, "[local, user: alice_desktop] ") ^<# "cath> hello"
|
||||
|
||||
desktop ##> "/switch remote host local"
|
||||
desktop <## "Using local profile"
|
||||
desktop ##> "/user"
|
||||
desktop <## "user profile: desk_bottom"
|
||||
desktop <## "use /p <display name> to change it"
|
||||
desktop <## "(the updated profile will be sent to all your contacts)"
|
||||
|
||||
bob #> "@alice hey"
|
||||
(desktop, "[remote: 1, user: alice] ") ^<# "bob> hey"
|
||||
|
||||
stopDesktop mobile desktop
|
||||
|
||||
-- * Utils
|
||||
|
||||
startRemote :: TestCC -> TestCC -> IO ()
|
||||
@ -460,6 +510,7 @@ startRemoteDiscover mobile desktop = do
|
||||
mobile ##> "/find remote ctrl"
|
||||
mobile <## "ok"
|
||||
mobile <## ("remote controller 1 found: My desktop, v" <> versionNumber)
|
||||
mobile <## "use /confirm remote ctrl 1 to connect"
|
||||
mobile ##> "/confirm remote ctrl 1"
|
||||
|
||||
mobile <## ("connecting remote controller 1: My desktop, v" <> versionNumber)
|
||||
|
@ -164,7 +164,7 @@
|
||||
"simplex-unique-card-3-p-1": "يخزن SimpleX جميع بيانات المستخدم على الأجهزة العميلة<strong> بتنسيق قاعدة بيانات محمولة مشفرة — </strong>يمكن نقله إلى جهاز آخر.",
|
||||
"simplex-unique-card-4-p-1": "شبكة SimpleX لا مركزية بالكامل ومستقلة عن أي عملة مشفرة أو أي منصة أخرى، بخلاف الإنترنت.",
|
||||
"simplex-unique-card-4-p-2": "يمكنك<strong> استخدام SimpleX مع خوادمك الخاصة </strong> أو مع الخوادم التي نوفرها — ولا يزال الاتصال ممكن بأي مستخدم.",
|
||||
"join": "انضم الى",
|
||||
"join": "انضم إلى",
|
||||
"we-invite-you-to-join-the-conversation": "نحن ندعوك للانضمام إلى محادثة",
|
||||
"join-the-REDDIT-community": "انضم إلى مجتمع REDDIT",
|
||||
"join-us-on-GitHub": "انضم إلينا على GitHub",
|
||||
|
Loading…
Reference in New Issue
Block a user