From b4bb28ef19bf3a4dd64cadcb37598dd9959aef93 Mon Sep 17 00:00:00 2001 From: yflory Date: Mon, 8 Nov 2021 12:44:45 +0100 Subject: [PATCH 01/12] Fix type error in calendar import --- www/calendar/export.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/www/calendar/export.js b/www/calendar/export.js index 5967e2027..307abad33 100644 --- a/www/calendar/export.js +++ b/www/calendar/export.js @@ -188,7 +188,7 @@ define([ hidden.push(al.toString()); } var trigger = al.getFirstPropertyValue('trigger'); - var minutes = trigger ? (-trigger.toSeconds() / 60) : 0; + var minutes = trigger && trigger.toSeconds ? (-trigger.toSeconds() / 60) : 0; if (reminders.indexOf(minutes) === -1) { reminders.push(minutes); } }); From ca0bde068e2c44534f1dd0648a3ace74fb1867ac Mon Sep 17 00:00:00 2001 From: yflory Date: Mon, 8 Nov 2021 12:45:20 +0100 Subject: [PATCH 02/12] Fix issue with Choice grids in forms (#827) --- www/form/inner.js | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/www/form/inner.js b/www/form/inner.js index c3835f934..2f7cdf7b1 100644 --- a/www/form/inner.js +++ b/www/form/inner.js @@ -1815,7 +1815,7 @@ define([ defaultOpts: { items: [1,2].map(function (i) { return { - uid: Util.uid(), + //uid: Util.uid(), v: Messages._getKey('form_defaultItem', [i]) }; }), @@ -1831,6 +1831,10 @@ define([ if (!opts) { opts = Util.clone(TYPES.multiradio.defaultOpts); } if (!Array.isArray(opts.items) || !Array.isArray(opts.values)) { return; } var lines = opts.items.map(function (itemData) { + if (!itemData.uid) { + itemData.uid = Util.uid(); + if (APP.isEditor) { APP.framework.localChange(); } + } var name = itemData.uid; var item = itemData.v; var els = extractValues(opts.values).map(function (data, i) { @@ -3340,9 +3344,11 @@ define([ // Make sure we can't create a section inside another one if (type === 'section' && arr !== content.order) { return; } + var model = TYPES[type] || STATIC_TYPES[type]; + if (!model) { return; } content.form[_uid] = { //q: Messages.form_default, - //opts: opts + opts: Util.clone(model.defaultOpts), type: type, }; if (full || inSection) { From 9d4368e8cd2f8deb6f4dd3f83f2c590ebb19b967 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Benqu=C3=A9?= Date: Mon, 8 Nov 2021 15:04:50 +0000 Subject: [PATCH 03/12] Display full text of Form responses --- www/form/app-form.less | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/www/form/app-form.less b/www/form/app-form.less index 7a8e1ece1..43e534e63 100644 --- a/www/form/app-form.less +++ b/www/form/app-form.less @@ -854,6 +854,13 @@ } } } + &.cp-text-table { + .cp-charts-row { + .cp-value { + white-space: normal; + } + } + } } .cp-form-results-contained { From 528fd4ff9723826bfd2cfcad54b183c5625ee71c Mon Sep 17 00:00:00 2001 From: yflory Date: Tue, 9 Nov 2021 13:47:20 +0100 Subject: [PATCH 04/12] Update form anonymity options --- www/form/app-form.less | 8 +++- www/form/inner.js | 101 +++++++++++++++++++++++++---------------- 2 files changed, 68 insertions(+), 41 deletions(-) diff --git a/www/form/app-form.less b/www/form/app-form.less index 43e534e63..d1ca4da88 100644 --- a/www/form/app-form.less +++ b/www/form/app-form.less @@ -477,13 +477,19 @@ .cp-form-anon-answer { text-align: center; margin: 20px 0 30px 0; + .cp-form-required-radio.cp-radio-required { + background: fade(@cryptpad_text_col, 15%); + padding: 3px; + border: 2px solid @cryptpad_color_red; + color: @cp_form-invalid; + } .cp-form-anon-answer-input { - margin-top: 20px; display: flex; white-space: nowrap; align-items: center; input { margin-left: 10px; + display: inline-block; } } .cp-form-anon-answer-registered { diff --git a/www/form/inner.js b/www/form/inner.js index 2f7cdf7b1..e6e2af133 100644 --- a/www/form/inner.js +++ b/www/form/inner.js @@ -2723,7 +2723,7 @@ define([ var answer = obj.msg; var date = new Date(obj.time).toLocaleString(); var text, warning, badge; - if (!answer._userdata || !answer._userdata.name) { + if (!answer._userdata || (!answer._userdata.name && !answer._userdata.curvePublic)) { text = Messages._getKey('form_answerAnonymous', [date]); } else { var ud = answer._userdata; @@ -3022,69 +3022,81 @@ define([ if (!loggedIn && !content.answers.anonymous) { return; } - var cbox; - var anonName, $anonName; - cbox = UI.createCheckbox('cp-form-anonymous', - Messages.form_anonymousBox, true, {}); - var $cbox = $(cbox); - var $anonBox = $cbox.find('input'); + var $anonName; + var anonRadioOn = UI.createRadio('cp-form-anon', 'cp-form-anon-on', + Messages.form_anonymousBox, false, { + input: { value: 1 }, + }); + var anonOffContent = h('span'); + var anonRadioOff = UI.createRadio('cp-form-anon', 'cp-form-anon-off', + anonOffContent, false, { + input: { value: 0 }, + }); + var radioContainer = h('div.cp-form-required-radio', [ + anonRadioOn, + anonRadioOff, + ]); + var $radio = $(radioContainer); + + if (content.answers.makeAnonymous) { // If we make all answers anonymous, hide the checkbox and display a message - $cbox.hide(); - $anonBox.attr('disabled', 'disabled').prop('checked', true); + $radio.hide(); + $(anonRadioOn).find('input').prop('checked', true); setTimeout(function () { // We need to wait for cbox to be added into the DOM before using .after() - $cbox.after(h('div.alert.alert-info', Messages.form_anonAnswer)); + $radio.after(h('div.alert.alert-info', Messages.form_anonAnswer)); }); } else if (content.answers.anonymous) { // Answers aren't anonymous and guests are allowed // Guests can set a username and logged in users can answer anonymously - var $anon; if (!loggedIn) { - anonName = h('div.cp-form-anon-answer-input', [ + $(anonOffContent).append(h('span.cp-form-anon-answer-input', [ Messages.form_answerAs, h('input', { value: user.name || '', placeholder: Messages.form_anonName }) - ]); - $anonName = $(anonName).hide(); + ])); + $anonName = $(anonOffContent).find('input'); + var $off = $(anonRadioOff).find('input[type="radio"]'); + $anonName.on('click input', function () { + if (!Util.isChecked($off)) { $off.prop('checked', true); } + }); } else if (APP.cantAnon) { // You've already answered with your credentials - $cbox.hide(); - $anonBox.attr('disabled', 'disabled').prop('checked', false); + $(anonRadioOn).find('input').attr('disabled', 'disabled'); + $(anonRadioOff).find('input[type="radio"]').prop('checked', true); } - if (!anonName) { - anonName = h('div.cp-form-anon-answer-input', [ + if (!$anonName) { + $(anonOffContent).append(h('div.cp-form-anon-answer-input', [ Messages.form_answerAs, h('span.cp-form-anon-answer-registered', user.name || Messages.anonymous) - ]); + ])); } - if (!APP.cantAnon) { - $anon = $(anonName).hide(); - $anonBox.on('change', function () { - if (Util.isChecked($anonBox)) { $anon.hide(); } - else { $anon.show(); } + if (!$radio.find('input[type="radio"]:checked').length) { + $radio.addClass('cp-radio-required'); + $radio.find('input[type="radio"]').on('change', function () { + $radio.removeClass('cp-radio-required'); }); } } else { // Answers don't have to be anonymous and only logged in users can answer // ==> they have to answer with their keys so we know their name too - $cbox.hide(); - $anonBox.attr('disabled', 'disabled').prop('checked', false); + $(anonRadioOn).find('input').attr('disabled', 'disabled'); + $(anonRadioOff).find('input[type="radio"]').prop('checked', true); setTimeout(function () { // We need to wait for cbox to be added into the DOM before using .after() if (content.answers.cantEdit) { return; } - $cbox.after(h('div.alert.alert-info', Messages.form_authAnswer)); + $radio.after(h('div.alert.alert-info', Messages.form_authAnswer)); }); - anonName = h('div.cp-form-anon-answer-input', [ + $(anonOffContent).append(h('div.cp-form-anon-answer-input', [ Messages.form_answerAs, h('span.cp-form-anon-answer-registered', user.name || Messages.anonymous) - ]); + ])); } if (APP.hasAnswered && content.answers.cantEdit || APP.isClosed) { - $cbox.hide(); - anonName = undefined; + $radio.hide(); } var send = h('button.cp-open.btn.btn-primary', APP.hasAnswered ? Messages.form_update : Messages.form_submit); @@ -3098,12 +3110,18 @@ define([ evOnChange.fire(); }); var $send = $(send).click(function () { + if (!$radio.find('input[type="radio"]:checked').length) { + return UI.warn(Messages.error); + } + $send.attr('disabled', 'disabled'); var results = getFormResults(); if (!results) { return; } + var wantName = Util.isChecked($(anonRadioOff).find('input[type="radio"]')); + var user = metadataMgr.getUserData(); - if (!Util.isChecked($anonBox) && !content.answers.makeAnonymous) { + if (wantName && !content.answers.makeAnonymous) { results._userdata = loggedIn ? { avatar: user.avatar, name: user.name, @@ -3111,7 +3129,7 @@ define([ curvePublic: user.curvePublic, profile: user.profile } : { - name: $anonName ? $anonName.find('input').val() : user.name + name: $anonName ? $anonName.val() : user.name }; } @@ -3120,7 +3138,7 @@ define([ mailbox: content.answers, results: results, anonymous: content.answers.makeAnonymous || !loggedIn - || (Util.isChecked($anonBox) && !APP.cantAnon) // use ephemeral keys + || (!wantName && !APP.cantAnon) // use ephemeral keys }, function (err, data) { $send.attr('disabled', 'disabled'); if (err || (data && data.error)) { @@ -3130,6 +3148,11 @@ define([ console.error(err || data.error); return void UI.warn(Messages.error); } + if (results._userdata && loggedIn) { + $(anonRadioOn).find('input').attr('disabled', 'disabled'); + $(anonRadioOff).find('input[type="radio"]').prop('checked', true); + APP.cantAnon = true; + } evOnChange.fire(false, true); window.onbeforeunload = undefined; @@ -3139,8 +3162,7 @@ define([ APP.answeredInForm = false; showAnsweredPage(framework, content, { '_time': +new Date() }); if (content.answers.cantEdit) { - $cbox.hide(); - if ($anonName) { $anonName.hide(); } + $(radioContainer).hide(); } }); }); @@ -3248,10 +3270,9 @@ define([ return h('div.cp-form-send-container', [ invalid, errors, - cbox ? h('div.cp-form-anon-answer', [ - cbox, - anonName - ]) : undefined, + h('div.cp-form-anon-answer', [ + radioContainer + ]), reset, send ]); }; From 97cafa6e46283269366173578c31fc1df0b4e7af Mon Sep 17 00:00:00 2001 From: Weblate Date: Tue, 9 Nov 2021 16:25:05 +0100 Subject: [PATCH 05/12] Translated using Weblate (French) Currently translated at 100.0% (1425 of 1425 strings) Translation: CryptPad/App Translate-URL: http://weblate.cryptpad.fr/projects/cryptpad/app/fr/ --- www/common/translations/messages.fr.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/www/common/translations/messages.fr.json b/www/common/translations/messages.fr.json index d78a7e018..a972426b4 100644 --- a/www/common/translations/messages.fr.json +++ b/www/common/translations/messages.fr.json @@ -1424,5 +1424,6 @@ "fc_openIn": "Ouvrir avec {0}", "creation_new": "Créer : {0}", "premiumAccess": "En tant qu'abonné sur {0}, vous pouvez créer de nouveaux documents dans cette application en accès restreint. Veuillez noter qu'elle est expérimentale et qu'il n'est pas recommandé d'y stocker des données importantes.", - "form_exportSheet": "Exporter vers Tableur" + "form_exportSheet": "Exporter vers Tableur", + "form_answerChoice": "Veuillez choisir comment vous souhaitez répondre à ce formulaire :" } From f702e7160d6cff62a3227da82b927d5b3e6dbfcc Mon Sep 17 00:00:00 2001 From: Weblate Date: Tue, 9 Nov 2021 16:25:05 +0100 Subject: [PATCH 06/12] Translated using Weblate (German) Currently translated at 100.0% (1424 of 1424 strings) Translation: CryptPad/App Translate-URL: http://weblate.cryptpad.fr/projects/cryptpad/app/de/ --- www/common/translations/messages.de.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/www/common/translations/messages.de.json b/www/common/translations/messages.de.json index 317f9dad2..3435a2520 100644 --- a/www/common/translations/messages.de.json +++ b/www/common/translations/messages.de.json @@ -1423,5 +1423,6 @@ "fc_openIn": "In {0} öffnen", "premiumOnly": "Die Erstellung neuer Dokumente in dieser Anwendung ist derzeit nur für Abonnenten auf {0} möglich. Dies ist eine experimentelle Anwendung für Testzwecke. Sie wird bald für jeden Benutzer auf {0} verfügbar sein.", "premiumAccess": "Als Abonnent auf {0} kannst du in dieser Anwendung neue Dokumente erstellen. Bitte beachte, dass es sich um eine experimentelle Anwendung handelt, der man noch keine wichtigen Daten anvertrauen sollte.", - "earlyAccessBlocked": "Diese Anwendung ist auf dieser Instanz noch nicht verfügbar" + "earlyAccessBlocked": "Diese Anwendung ist auf dieser Instanz noch nicht verfügbar", + "form_exportSheet": "In Tabelle exportieren" } From 415dafc2128ced2b3f727ac9f64442e6f02becc0 Mon Sep 17 00:00:00 2001 From: Weblate Date: Tue, 9 Nov 2021 16:25:05 +0100 Subject: [PATCH 07/12] Translated using Weblate (English) Currently translated at 100.0% (1425 of 1425 strings) Translation: CryptPad/App Translate-URL: http://weblate.cryptpad.fr/projects/cryptpad/app/en/ --- www/common/translations/messages.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/www/common/translations/messages.json b/www/common/translations/messages.json index 29631bff3..bfad627d7 100644 --- a/www/common/translations/messages.json +++ b/www/common/translations/messages.json @@ -1424,5 +1424,6 @@ "premiumOnly": "Creating new documents in this application is currently limited to subscribers on {0}. This is an early-access experimental application for testing purposes. It will soon become available to everyone on {0}.", "earlyAccessBlocked": "This application is not available yet on this instance", "premiumAccess": "As a subscriber on {0}, you can create new documents in this early-access application. Please be aware that it is experimental and should not yet be trusted with important data.", - "form_exportSheet": "Export to Sheet" + "form_exportSheet": "Export to Sheet", + "form_answerChoice": "Please choose how you would like to answer this form:" } From e6073c5684713d34aad1ed91ad6bced338204308 Mon Sep 17 00:00:00 2001 From: yflory Date: Tue, 9 Nov 2021 16:26:27 +0100 Subject: [PATCH 08/12] Update version --- customize.dist/pages.js | 2 +- package-lock.json | 2 +- package.json | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/customize.dist/pages.js b/customize.dist/pages.js index c53a7a78a..a493f8997 100644 --- a/customize.dist/pages.js +++ b/customize.dist/pages.js @@ -105,7 +105,7 @@ define([ var imprintUrl = AppConfig.imprint && (typeof(AppConfig.imprint) === "boolean" ? '/imprint.html' : AppConfig.imprint); - Pages.versionString = "v4.12.0"; + Pages.versionString = "v4.12.1"; // used for the about menu diff --git a/package-lock.json b/package-lock.json index 4e31acb53..5697225c2 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "cryptpad", - "version": "4.12.0", + "version": "4.12.1", "lockfileVersion": 1, "requires": true, "dependencies": { diff --git a/package.json b/package.json index 343353bb6..39bb0a312 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "cryptpad", "description": "realtime collaborative visual editor with zero knowlege server", - "version": "4.12.0", + "version": "4.12.1", "license": "AGPL-3.0+", "repository": { "type": "git", From 40d92a5423e279233eb8ffbee09d74a7e89c8c2b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Benqu=C3=A9?= Date: Tue, 9 Nov 2021 15:11:43 +0000 Subject: [PATCH 09/12] Adjust UI for anon/name answer choice in forms --- customize.dist/src/less2/include/colortheme.less | 2 +- www/form/app-form.less | 7 +++---- www/form/inner.js | 4 +++- 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/customize.dist/src/less2/include/colortheme.less b/customize.dist/src/less2/include/colortheme.less index dd6115ea1..8817f9312 100644 --- a/customize.dist/src/less2/include/colortheme.less +++ b/customize.dist/src/less2/include/colortheme.less @@ -447,6 +447,6 @@ @cp_form-poll-yes: fade(@cryptpad_color_light_green, 75%); @cp_form-poll-maybe: @cryptpad_color_grey_300; @cp_form-poll-yes-color: @cryptpad_color_green; -@cp_form-invalid: @cryptpad_color_red; +@cp_form-invalid: @cp_alerts-danger-text; @cp_form-palette: @cp_palette; @cp_form-palette2: @cp_palette-dark; diff --git a/www/form/app-form.less b/www/form/app-form.less index d1ca4da88..4e873575e 100644 --- a/www/form/app-form.less +++ b/www/form/app-form.less @@ -477,10 +477,10 @@ .cp-form-anon-answer { text-align: center; margin: 20px 0 30px 0; + .cp-radio { + margin-top: 10px; + } .cp-form-required-radio.cp-radio-required { - background: fade(@cryptpad_text_col, 15%); - padding: 3px; - border: 2px solid @cryptpad_color_red; color: @cp_form-invalid; } .cp-form-anon-answer-input { @@ -575,7 +575,6 @@ flex: 1; } .cp-form-required-tag { - background: fade(@cryptpad_text_col, 15%); padding: 5px; margin-top: -10px; margin-right: -10px; diff --git a/www/form/inner.js b/www/form/inner.js index e6e2af133..d9e731937 100644 --- a/www/form/inner.js +++ b/www/form/inner.js @@ -3032,7 +3032,9 @@ define([ anonOffContent, false, { input: { value: 0 }, }); + Messages.form_answerChoice = "Please choose how you would like to answer this form: "; // XXX var radioContainer = h('div.cp-form-required-radio', [ + Messages.form_answerChoice, anonRadioOn, anonRadioOff, ]); @@ -3268,8 +3270,8 @@ define([ } return h('div.cp-form-send-container', [ - invalid, errors, + invalid, h('div.cp-form-anon-answer', [ radioContainer ]), From 0b78295460114c9398bd5792d7b8037e51e7079d Mon Sep 17 00:00:00 2001 From: yflory Date: Wed, 10 Nov 2021 14:06:15 +0100 Subject: [PATCH 10/12] Update changelog --- CHANGELOG.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 639b82ee9..902ecad68 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,13 @@ +# 4.12.1 + +This minor release contains a few bug fixes based on feedback we received and adjustments to prepare for the update to OnlyOffice 6.4. + +* We noticed that charts and tables in the Document and Presentation (early access) applications cause conflicts with the upcoming OnlyOffice update. They are now disabled until the next release. +* We found that the button to export form results to a CryptPad sheet was empty so we added the missing text. +* Several issues were reported with the Forms application and are now fixed. This patch will prevent conditional sections from losing their content (questions and conditions) while editing the form. The "max options" selector won't be displayed anymore when converting "checkbox" questions to other types. The first two lines of a "choice grid" weren't always registered when submitting a form and this patch fixes it for newly created choice grids. +* Some calendars created with external tools couldn't be imported in CryptPad due to notifications settings. We've changed the "import" script to make sure the event could still be imported but without the problematic notification. +* We've received conflicting feedback about the privacy settings in forms. In the existing system, the users had to untick a box to submit with their name but, depending on the context, it's not always a good solution to make a form result anonymous by default. Similarly submitting form results with the username by default isn't privacy-friendly. We implemented a new system to prompt users to choose between submitting anonymously or with their name (unless one of the options is disabled). + # 4.12.0 ## Goals From fcd416b0f64bc7ecd6070b312dd3e9d3d36fcd57 Mon Sep 17 00:00:00 2001 From: Weblate Date: Tue, 9 Nov 2021 18:25:34 +0100 Subject: [PATCH 11/12] Translated using Weblate (German) Currently translated at 100.0% (1425 of 1425 strings) Translation: CryptPad/App Translate-URL: http://weblate.cryptpad.fr/projects/cryptpad/app/de/ --- www/common/translations/messages.de.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/www/common/translations/messages.de.json b/www/common/translations/messages.de.json index 3435a2520..9db594195 100644 --- a/www/common/translations/messages.de.json +++ b/www/common/translations/messages.de.json @@ -1424,5 +1424,6 @@ "premiumOnly": "Die Erstellung neuer Dokumente in dieser Anwendung ist derzeit nur für Abonnenten auf {0} möglich. Dies ist eine experimentelle Anwendung für Testzwecke. Sie wird bald für jeden Benutzer auf {0} verfügbar sein.", "premiumAccess": "Als Abonnent auf {0} kannst du in dieser Anwendung neue Dokumente erstellen. Bitte beachte, dass es sich um eine experimentelle Anwendung handelt, der man noch keine wichtigen Daten anvertrauen sollte.", "earlyAccessBlocked": "Diese Anwendung ist auf dieser Instanz noch nicht verfügbar", - "form_exportSheet": "In Tabelle exportieren" + "form_exportSheet": "In Tabelle exportieren", + "form_answerChoice": "Bitte wähle aus, wie du dieses Formular beantworten möchtest:" } From 09fb604c3baacf9b626359abe1abcf73037b7815 Mon Sep 17 00:00:00 2001 From: ansuz Date: Tue, 16 Nov 2021 14:07:14 +0530 Subject: [PATCH 12/12] remove hardcoded translation --- www/form/inner.js | 1 - 1 file changed, 1 deletion(-) diff --git a/www/form/inner.js b/www/form/inner.js index d9e731937..a8a5a603a 100644 --- a/www/form/inner.js +++ b/www/form/inner.js @@ -3032,7 +3032,6 @@ define([ anonOffContent, false, { input: { value: 0 }, }); - Messages.form_answerChoice = "Please choose how you would like to answer this form: "; // XXX var radioContainer = h('div.cp-form-required-radio', [ Messages.form_answerChoice, anonRadioOn,