Compare commits

..
10 Commits
Author SHA1 Message Date
vd ee6454a296 support vdpr url 2026-10-09 02:01:43 +02:00
Marlon Erler 8a275ab51a Delete ; 2026-10-04 22:16:20 +02:00
marlon-erler 4bd9dc25f2 typo 2026-10-04 22:14:32 +02:00
marlon-erler 3d523d5e38 update translations 2026-10-04 22:14:04 +02:00
Marlon Erler 71c454980f Update README.md 2026-10-04 22:11:41 +02:00
marlon-erler 5184d21d13 update readme 2026-10-04 22:06:00 +02:00
marlon-erler f05e5f8f00 add dialog to confirm chat deletion 2026-10-02 18:32:22 +02:00
marlon-erler 6ec3355aeb dist 2026-10-01 22:17:04 +02:00
marlon-erler df99b485a4 fix ribbon overflow 2026-10-01 22:16:53 +02:00
marlon-erler a17cec9a79 fix greetings 2026-10-01 21:27:43 +02:00
10 changed files with 156 additions and 34 deletions
+32 -11
View File
@@ -1,16 +1,37 @@
# udn-comms
# CT
UDN-Comms is a messenger built for [UDN](https://github.com/marlon-erler/universal-decentralized-network).
> [!NOTE]
> **LOCAL DEVELOPMENT**
>
> This project is developed on a locally run git service.
>
> This repository gets updated for public releases and announcements only.
# Features
CT is a messenger and task management application built for [UDN](https://github.com/marlon-erler/udn).
- Offline support
- Encryption
- Secondary channels
# Core Features
# Getting Started
- Offline support, updates download in background
- Messaging including reactions, inline replies, and message-replies-only view
- Task management with Kanban and Status Grid view
- Calendar for tasks
- Data transfer and export/import for identity, connections, and chats
1. Use or install the web app [here](https://udn-comms.onrender.com/)
2. Enter your name
3. Connect to your server
4. Create a chat and start messaging
# Update Cycle
- Updates are published monthly
- Version numbers are a combination of year and months, e.g. 2610 for October 2026
- Specific release dates and notes are published within two weeks of the release
# Changes
## 2610 - Scheduled for October 11th, 2026: Initial Release
This application is a rebrand of Comms, whose development started in July 2024. Changelogs or versioning have not been present initially and were never standardized. The CT repository is a fork of Comms. Changes made between the lastest iteration of Comms and CT 2610 include:
- Account and chat identity
- Use a randomized UUID to identify users instead of manually entered names
- Integrate a contacts model to keep track of who sent messages, and to reflect name changes
- Replace primary channels and namespaces with randomized UUIDs and chat names, sync chat settings (name, color, secondary channels)
- UI improvements:
- Show how much storage is used and remaining in storage management view
- Show data transfer progress
- Layout improvements
+1 -1
View File
@@ -445,7 +445,7 @@ body[showing-chat] #chat-page-wrapper {
justify-content: space-between;
}
#chat-page > div > #ribbon > span {
overflow-y: auto;
overflowx: hidden;
flex-direction: column;
justify-content: end;
}
+37 -11
View File
@@ -348,7 +348,7 @@
greeting: (name) => `Hi ${name}`,
///
serverAddress: "Server address",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "connect to server",
disconnectAudioLabel: "disconnect from server",
manageConnectionsAudioLabel: "manage connections",
@@ -480,7 +480,9 @@
showEncryptionKey: "Show encryption key",
randomizeKey: "Randomize",
setColorButtonAudioLabel: "set color",
deleteChatButton: "Delete entire chat"
deleteChatButton: "Delete entire chat",
deleteChatHeadline: "Delete chat?",
deleteChatDescription: "This will delete all messages, tasks, and other data related to this chat from device."
},
message: {
messagesHeadline: "Messages",
@@ -619,9 +621,9 @@
},
homePage: {
appName: "Coordination Tool",
greeting: (name) => `Hi ${name}!`,
greeting: (name) => `Hallo ${name}`,
serverAddress: "Serveradresse",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "mit Server verbinden",
disconnectAudioLabel: "vom Server trennen",
manageConnectionsAudioLabel: "Verbindungen verwalten",
@@ -746,7 +748,9 @@
showEncryptionKey: "Schl\xFCssel anzeigen",
randomizeKey: "Zuf\xE4llig generieren",
setColorButtonAudioLabel: "Farbe festlegen",
deleteChatButton: "Gesamten Chat l\xF6schen"
deleteChatButton: "Gesamten Chat l\xF6schen",
deleteChatHeadline: "Gesamten Chat l\xF6schen?",
deleteChatDescription: "Dies l\xF6scht alle Nachrichten, Aufgaben und alle anderen Daten, die zu diesem Chat geh\xF6ren."
},
message: {
messagesHeadline: "Nachrichten",
@@ -872,9 +876,9 @@
},
homePage: {
appName: "Coordination Tool",
greeting: (name) => `Hola ${name}!`,
greeting: (name) => `Hola ${name}`,
serverAddress: "Direcci\xF3n del servidor",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "conectar al servidor",
disconnectAudioLabel: "desconectar del servidor",
manageConnectionsAudioLabel: "gestionar conexiones",
@@ -999,7 +1003,9 @@
showEncryptionKey: "Mostrar clave de encriptaci\xF3n",
randomizeKey: "Aleatorizar",
setColorButtonAudioLabel: "establecer color",
deleteChatButton: "Eliminar todo el chat"
deleteChatButton: "Eliminar todo el chat",
deleteChatHeadline: "\xBFEliminar chat?",
deleteChatDescription: "\xBFQuieres borrar todas las mensajes, tareas y otros datos que pertenecen a este chat?"
},
message: {
messagesHeadline: "Mensajes",
@@ -6700,6 +6706,18 @@
);
}
// src/View/Components/confirmationDialog.tsx
function ConfirmationDialog(coreViewModel2, buttonLabel, icon, headline, description, action) {
const isModalOpen = new State(false);
function openModal() {
isModalOpen.value = true;
}
function closeModal() {
isModalOpen.value = false;
}
return /* @__PURE__ */ createElement("div", null, /* @__PURE__ */ createElement("button", { class: "danger width-100", "on:click": openModal }, /* @__PURE__ */ createElement("span", null, buttonLabel), /* @__PURE__ */ createElement("span", { class: "icon" }, icon)), /* @__PURE__ */ createElement("div", { class: "modal", "toggle:open": isModalOpen }, /* @__PURE__ */ createElement("div", null, /* @__PURE__ */ createElement("main", null, /* @__PURE__ */ createElement("h2", null, headline), /* @__PURE__ */ createElement("p", { class: "secondary" }, description)), /* @__PURE__ */ createElement("div", { class: "flex-row" }, /* @__PURE__ */ createElement("button", { class: "standard width-50", "on:click": closeModal }, coreViewModel2.translations.general.cancelButton), /* @__PURE__ */ createElement("button", { class: "danger width-50", "on:click": action }, /* @__PURE__ */ createElement("span", null, buttonLabel), /* @__PURE__ */ createElement("span", { class: "icon" }, icon))))));
}
// src/View/ChatPages/settingsPage.tsx
function SettingsPage(coreViewModel2, settingsPageViewModel) {
settingsPageViewModel.loadData();
@@ -6796,10 +6814,12 @@
},
coreViewModel2.translations.general.setButton,
/* @__PURE__ */ createElement("span", { class: "icon" }, "check")
)), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("div", { class: "width-input" }, DangerousActionButton(
)), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("div", { class: "width-input" }, ConfirmationDialog(
coreViewModel2,
coreViewModel2.translations.chatPage.settings.deleteChatButton,
"chat_error",
"delete_forever",
coreViewModel2.translations.chatPage.settings.deleteChatHeadline,
coreViewModel2.translations.chatPage.settings.deleteChatDescription,
settingsPageViewModel.remove
))))));
}
@@ -8237,7 +8257,13 @@
OptionConverter
]
}
), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("h3", null, coreViewModel2.translations.dataTransferModal.chatsHeadline), /* @__PURE__ */ createElement("div", { "children:set": chatList }), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("label", { class: "inline" }, /* @__PURE__ */ createElement("input", { type: "checkbox", "bind:checked": fileTransferViewModel2.allOptionsSelected }), coreViewModel2.translations.general.selectAllLabel));
), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("h3", null, coreViewModel2.translations.dataTransferModal.chatsHeadline), /* @__PURE__ */ createElement("div", { "children:set": chatList }), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("label", { class: "inline" }, /* @__PURE__ */ createElement(
"input",
{
type: "checkbox",
"bind:checked": fileTransferViewModel2.allOptionsSelected
}
), coreViewModel2.translations.general.selectAllLabel));
}
function DirectionSelectionModal(coreViewModel2, connectionViewModel2, fileTransferViewModel2) {
const isPresented = createProxyState(
Vendored
+1 -1
View File
@@ -1,4 +1,4 @@
const VERSION = "2610 Beta 21.17"
const VERSION = "2610 Beta 22"
function processUrl(event) {
const url = event.request.url;
+1 -1
View File
@@ -1 +1 @@
2610 Beta 21.17
2610 Beta 22
+7 -3
View File
@@ -1,5 +1,5 @@
import { DeletableListItem } from "../Components/deletableListItem";
import { DangerousActionButton } from "../Components/dangerousActionButton";
import { ConfirmationDialog } from "../Components/confirmationDialog";
import { ColorPicker } from "../Components/colorPicker";
import * as React from "../../react";
import SettingsPageViewModel from "../../ViewModel/Pages/settingsPageViewModel";
@@ -203,11 +203,15 @@ export function SettingsPage(
<hr></hr>
<div class="width-input">
{DangerousActionButton(
{ConfirmationDialog(
coreViewModel,
coreViewModel.translations.chatPage.settings
.deleteChatButton,
"chat_error",
"delete_forever",
coreViewModel.translations.chatPage.settings
.deleteChatHeadline,
coreViewModel.translations.chatPage.settings
.deleteChatDescription,
settingsPageViewModel.remove,
)}
</div>
@@ -0,0 +1,47 @@
import * as React from "../../react";
import CoreViewModel from "../../ViewModel/Global/coreViewModel";
export function ConfirmationDialog(
coreViewModel: CoreViewModel,
buttonLabel: string,
icon: string,
headline: string,
description: string,
action: () => void,
) {
const isModalOpen = new React.State(false);
function openModal() {
isModalOpen.value = true;
}
function closeModal() {
isModalOpen.value = false;
}
return (
<div>
<button class="danger width-100" on:click={openModal}>
<span>{buttonLabel}</span>
<span class="icon">{icon}</span>
</button>
<div class="modal" toggle:open={isModalOpen}>
<div>
<main>
<h2>{headline}</h2>
<p class="secondary">{description}</p>
</main>
<div class="flex-row">
<button class="standard width-50" on:click={closeModal}>
{coreViewModel.translations.general.cancelButton}
</button>
<button class="danger width-50" on:click={action}>
<span>{buttonLabel}</span>
<span class="icon">{icon}</span>
</button>
</div>
</div>
</div>
</div>
);
}
+1 -1
View File
@@ -137,7 +137,7 @@ body[showing-chat] #chat-page-wrapper {
}
#chat-page > div > #ribbon > span {
overflow-y: auto;
overflow-x: hidden;
flex-direction: column;
justify-content: end;
}
+14 -5
View File
@@ -61,7 +61,7 @@ const englishTranslations = {
///
serverAddress: "Server address",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "connect to server",
disconnectAudioLabel: "disconnect from server",
manageConnectionsAudioLabel: "manage connections",
@@ -244,6 +244,9 @@ const englishTranslations = {
setColorButtonAudioLabel: "set color",
deleteChatButton: "Delete entire chat",
deleteChatHeadline: "Delete chat?",
deleteChatDescription:
"This will delete all messages, tasks, and other data related to this chat from device.",
},
message: {
@@ -440,10 +443,10 @@ export const allTranslations: {
homePage: {
appName: "Coordination Tool",
greeting: (name: string) => `Hi ${name}!`,
greeting: (name: string) => `Hallo ${name}`,
serverAddress: "Serveradresse",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "mit Server verbinden",
disconnectAudioLabel: "vom Server trennen",
manageConnectionsAudioLabel: "Verbindungen verwalten",
@@ -618,6 +621,9 @@ export const allTranslations: {
setColorButtonAudioLabel: "Farbe festlegen",
deleteChatButton: "Gesamten Chat löschen",
deleteChatHeadline: "Gesamten Chat löschen?",
deleteChatDescription:
"Dies löscht alle Nachrichten, Aufgaben und alle anderen Daten, die zu diesem Chat gehören.",
},
message: {
@@ -787,10 +793,10 @@ export const allTranslations: {
homePage: {
appName: "Coordination Tool",
greeting: (name: string) => `Hola ${name}!`,
greeting: (name: string) => `Hola ${name}`,
serverAddress: "Dirección del servidor",
serverAddressPlaceholder: "wss://192.168.0.69:3000",
serverAddressPlaceholder: "wss://udn-s1.onrender.com",
connectAudioLabel: "conectar al servidor",
disconnectAudioLabel: "desconectar del servidor",
manageConnectionsAudioLabel: "gestionar conexiones",
@@ -965,6 +971,9 @@ export const allTranslations: {
setColorButtonAudioLabel: "establecer color",
deleteChatButton: "Eliminar todo el chat",
deleteChatHeadline: "¿Eliminar chat?",
deleteChatDescription:
"¿Quieres borrar todas las mensajes, tareas y otros datos que pertenecen a este chat?",
},
message: {
Executable
+15
View File
@@ -0,0 +1,15 @@
#!/bin/bash
url=""
case $1 in
vd)
url=https://viridian.vd/VDMDI/CT
;;
pr)
url=https://vdpr.org/VDMDI/CT
;;
esac
git remote set-url origin $url
git remote get-url origin