Skip to content

Commit 8edf3f0

Browse files
committed
compose: Support save snippets
We sort the saved snippets by title to be consistent with the web implementation. A subtle nuance of having a compose box in a modal bottom sheet is that the message list page behind will shift when the keyboard is expanded, even though its compose box is not visible anyway. An UX improvement would be preserving the inputs on the saved snippet compose box after the user has navigated away. Fixes: #863
1 parent 820db6e commit 8edf3f0

15 files changed

+1270
-0
lines changed

assets/l10n/app_en.arb

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -393,6 +393,54 @@
393393
"@composeBoxAttachFromCameraTooltip": {
394394
"description": "Tooltip for compose box icon to attach an image from the camera to the message."
395395
},
396+
"composeBoxShowSavedSnippetsTooltip": "Show saved snippets",
397+
"@composeBoxShowSavedSnippetsTooltip": {
398+
"description": "Tooltip for compose box icon to show a list of saved snippets."
399+
},
400+
"noSavedSnippets": "No saved snippets",
401+
"@noSavedSnippets": {
402+
"description": "Text to show on the saved snippets bottom sheet when there are no saved snippets."
403+
},
404+
"savedSnippetsTitle": "Saved snippets",
405+
"@savedSnippetsTitle": {
406+
"description": "Title for the bottom sheet to display saved snippets."
407+
},
408+
"newSavedSnippetButton": "New",
409+
"@newSavedSnippetButton": {
410+
"description": "Label for adding a new saved snippet."
411+
},
412+
"newSavedSnippetTitle": "New snippet",
413+
"@newSavedSnippetTitle": {
414+
"description": "Title for the bottom sheet to add a new saved snippet."
415+
},
416+
"newSavedSnippetTitleHint": "Title",
417+
"@newSavedSnippetTitleHint": {
418+
"description": "Hint text for the title input when adding a new saved snippet."
419+
},
420+
"newSavedSnippetContentHint": "Content",
421+
"@newSavedSnippetContentHint": {
422+
"description": "Hint text for the content input when adding a new saved snippet."
423+
},
424+
"errorFailedToCreateSavedSnippetTitle": "Failed to create saved snippet",
425+
"@errorFailedToCreateSavedSnippetTitle": {
426+
"description": "Error title when the saved snippet failed to be created."
427+
},
428+
"savedSnippetTitleValidationErrorEmpty": "Title cannot be empty.",
429+
"@savedSnippetTitleValidationErrorEmpty": {
430+
"description": "Validation error message when the title of the saved snippet is empty."
431+
},
432+
"savedSnippetTitleValidationErrorTooLong": "Title length shouldn't be greater than 60 characters.",
433+
"@savedSnippetTitleValidationErrorTooLong": {
434+
"description": "Validation error message when the title of the saved snippet is too long."
435+
},
436+
"savedSnippetContentValidationErrorEmpty": "Content cannot be empty.",
437+
"@savedSnippetContentValidationErrorEmpty": {
438+
"description": "Validation error message when the content of the saved snippet is empty."
439+
},
440+
"savedSnippetContentValidationErrorTooLong": "Content length shouldn't be greater than 10000 characters.",
441+
"@savedSnippetContentValidationErrorTooLong": {
442+
"description": "Validation error message when the content of the saved snippet is too long."
443+
},
396444
"composeBoxGenericContentHint": "Type a message",
397445
"@composeBoxGenericContentHint": {
398446
"description": "Hint text for content input when sending a message."

lib/generated/l10n/zulip_localizations.dart

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -652,6 +652,78 @@ abstract class ZulipLocalizations {
652652
/// **'Take a photo'**
653653
String get composeBoxAttachFromCameraTooltip;
654654

655+
/// Tooltip for compose box icon to show a list of saved snippets.
656+
///
657+
/// In en, this message translates to:
658+
/// **'Show saved snippets'**
659+
String get composeBoxShowSavedSnippetsTooltip;
660+
661+
/// Text to show on the saved snippets bottom sheet when there are no saved snippets.
662+
///
663+
/// In en, this message translates to:
664+
/// **'No saved snippets'**
665+
String get noSavedSnippets;
666+
667+
/// Title for the bottom sheet to display saved snippets.
668+
///
669+
/// In en, this message translates to:
670+
/// **'Saved snippets'**
671+
String get savedSnippetsTitle;
672+
673+
/// Label for adding a new saved snippet.
674+
///
675+
/// In en, this message translates to:
676+
/// **'New'**
677+
String get newSavedSnippetButton;
678+
679+
/// Title for the bottom sheet to add a new saved snippet.
680+
///
681+
/// In en, this message translates to:
682+
/// **'New snippet'**
683+
String get newSavedSnippetTitle;
684+
685+
/// Hint text for the title input when adding a new saved snippet.
686+
///
687+
/// In en, this message translates to:
688+
/// **'Title'**
689+
String get newSavedSnippetTitleHint;
690+
691+
/// Hint text for the content input when adding a new saved snippet.
692+
///
693+
/// In en, this message translates to:
694+
/// **'Content'**
695+
String get newSavedSnippetContentHint;
696+
697+
/// Error title when the saved snippet failed to be created.
698+
///
699+
/// In en, this message translates to:
700+
/// **'Failed to create saved snippet'**
701+
String get errorFailedToCreateSavedSnippetTitle;
702+
703+
/// Validation error message when the title of the saved snippet is empty.
704+
///
705+
/// In en, this message translates to:
706+
/// **'Title cannot be empty.'**
707+
String get savedSnippetTitleValidationErrorEmpty;
708+
709+
/// Validation error message when the title of the saved snippet is too long.
710+
///
711+
/// In en, this message translates to:
712+
/// **'Title length shouldn\'t be greater than 60 characters.'**
713+
String get savedSnippetTitleValidationErrorTooLong;
714+
715+
/// Validation error message when the content of the saved snippet is empty.
716+
///
717+
/// In en, this message translates to:
718+
/// **'Content cannot be empty.'**
719+
String get savedSnippetContentValidationErrorEmpty;
720+
721+
/// Validation error message when the content of the saved snippet is too long.
722+
///
723+
/// In en, this message translates to:
724+
/// **'Content length shouldn\'t be greater than 10000 characters.'**
725+
String get savedSnippetContentValidationErrorTooLong;
726+
655727
/// Hint text for content input when sending a message.
656728
///
657729
/// In en, this message translates to:

lib/generated/l10n/zulip_localizations_ar.dart

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,46 @@ class ZulipLocalizationsAr extends ZulipLocalizations {
330330
@override
331331
String get composeBoxAttachFromCameraTooltip => 'Take a photo';
332332

333+
@override
334+
String get composeBoxShowSavedSnippetsTooltip => 'Show saved snippets';
335+
336+
@override
337+
String get noSavedSnippets => 'No saved snippets';
338+
339+
@override
340+
String get savedSnippetsTitle => 'Saved snippets';
341+
342+
@override
343+
String get newSavedSnippetButton => 'New';
344+
345+
@override
346+
String get newSavedSnippetTitle => 'New snippet';
347+
348+
@override
349+
String get newSavedSnippetTitleHint => 'Title';
350+
351+
@override
352+
String get newSavedSnippetContentHint => 'Content';
353+
354+
@override
355+
String get errorFailedToCreateSavedSnippetTitle =>
356+
'Failed to create saved snippet';
357+
358+
@override
359+
String get savedSnippetTitleValidationErrorEmpty => 'Title cannot be empty.';
360+
361+
@override
362+
String get savedSnippetTitleValidationErrorTooLong =>
363+
'Title length shouldn\'t be greater than 60 characters.';
364+
365+
@override
366+
String get savedSnippetContentValidationErrorEmpty =>
367+
'Content cannot be empty.';
368+
369+
@override
370+
String get savedSnippetContentValidationErrorTooLong =>
371+
'Content length shouldn\'t be greater than 10000 characters.';
372+
333373
@override
334374
String get composeBoxGenericContentHint => 'Type a message';
335375

lib/generated/l10n/zulip_localizations_en.dart

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,46 @@ class ZulipLocalizationsEn extends ZulipLocalizations {
330330
@override
331331
String get composeBoxAttachFromCameraTooltip => 'Take a photo';
332332

333+
@override
334+
String get composeBoxShowSavedSnippetsTooltip => 'Show saved snippets';
335+
336+
@override
337+
String get noSavedSnippets => 'No saved snippets';
338+
339+
@override
340+
String get savedSnippetsTitle => 'Saved snippets';
341+
342+
@override
343+
String get newSavedSnippetButton => 'New';
344+
345+
@override
346+
String get newSavedSnippetTitle => 'New snippet';
347+
348+
@override
349+
String get newSavedSnippetTitleHint => 'Title';
350+
351+
@override
352+
String get newSavedSnippetContentHint => 'Content';
353+
354+
@override
355+
String get errorFailedToCreateSavedSnippetTitle =>
356+
'Failed to create saved snippet';
357+
358+
@override
359+
String get savedSnippetTitleValidationErrorEmpty => 'Title cannot be empty.';
360+
361+
@override
362+
String get savedSnippetTitleValidationErrorTooLong =>
363+
'Title length shouldn\'t be greater than 60 characters.';
364+
365+
@override
366+
String get savedSnippetContentValidationErrorEmpty =>
367+
'Content cannot be empty.';
368+
369+
@override
370+
String get savedSnippetContentValidationErrorTooLong =>
371+
'Content length shouldn\'t be greater than 10000 characters.';
372+
333373
@override
334374
String get composeBoxGenericContentHint => 'Type a message';
335375

lib/generated/l10n/zulip_localizations_ja.dart

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,46 @@ class ZulipLocalizationsJa extends ZulipLocalizations {
330330
@override
331331
String get composeBoxAttachFromCameraTooltip => 'Take a photo';
332332

333+
@override
334+
String get composeBoxShowSavedSnippetsTooltip => 'Show saved snippets';
335+
336+
@override
337+
String get noSavedSnippets => 'No saved snippets';
338+
339+
@override
340+
String get savedSnippetsTitle => 'Saved snippets';
341+
342+
@override
343+
String get newSavedSnippetButton => 'New';
344+
345+
@override
346+
String get newSavedSnippetTitle => 'New snippet';
347+
348+
@override
349+
String get newSavedSnippetTitleHint => 'Title';
350+
351+
@override
352+
String get newSavedSnippetContentHint => 'Content';
353+
354+
@override
355+
String get errorFailedToCreateSavedSnippetTitle =>
356+
'Failed to create saved snippet';
357+
358+
@override
359+
String get savedSnippetTitleValidationErrorEmpty => 'Title cannot be empty.';
360+
361+
@override
362+
String get savedSnippetTitleValidationErrorTooLong =>
363+
'Title length shouldn\'t be greater than 60 characters.';
364+
365+
@override
366+
String get savedSnippetContentValidationErrorEmpty =>
367+
'Content cannot be empty.';
368+
369+
@override
370+
String get savedSnippetContentValidationErrorTooLong =>
371+
'Content length shouldn\'t be greater than 10000 characters.';
372+
333373
@override
334374
String get composeBoxGenericContentHint => 'Type a message';
335375

lib/generated/l10n/zulip_localizations_nb.dart

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,46 @@ class ZulipLocalizationsNb extends ZulipLocalizations {
330330
@override
331331
String get composeBoxAttachFromCameraTooltip => 'Take a photo';
332332

333+
@override
334+
String get composeBoxShowSavedSnippetsTooltip => 'Show saved snippets';
335+
336+
@override
337+
String get noSavedSnippets => 'No saved snippets';
338+
339+
@override
340+
String get savedSnippetsTitle => 'Saved snippets';
341+
342+
@override
343+
String get newSavedSnippetButton => 'New';
344+
345+
@override
346+
String get newSavedSnippetTitle => 'New snippet';
347+
348+
@override
349+
String get newSavedSnippetTitleHint => 'Title';
350+
351+
@override
352+
String get newSavedSnippetContentHint => 'Content';
353+
354+
@override
355+
String get errorFailedToCreateSavedSnippetTitle =>
356+
'Failed to create saved snippet';
357+
358+
@override
359+
String get savedSnippetTitleValidationErrorEmpty => 'Title cannot be empty.';
360+
361+
@override
362+
String get savedSnippetTitleValidationErrorTooLong =>
363+
'Title length shouldn\'t be greater than 60 characters.';
364+
365+
@override
366+
String get savedSnippetContentValidationErrorEmpty =>
367+
'Content cannot be empty.';
368+
369+
@override
370+
String get savedSnippetContentValidationErrorTooLong =>
371+
'Content length shouldn\'t be greater than 10000 characters.';
372+
333373
@override
334374
String get composeBoxGenericContentHint => 'Type a message';
335375

lib/generated/l10n/zulip_localizations_pl.dart

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -337,6 +337,46 @@ class ZulipLocalizationsPl extends ZulipLocalizations {
337337
@override
338338
String get composeBoxAttachFromCameraTooltip => 'Zrób zdjęcie';
339339

340+
@override
341+
String get composeBoxShowSavedSnippetsTooltip => 'Show saved snippets';
342+
343+
@override
344+
String get noSavedSnippets => 'No saved snippets';
345+
346+
@override
347+
String get savedSnippetsTitle => 'Saved snippets';
348+
349+
@override
350+
String get newSavedSnippetButton => 'New';
351+
352+
@override
353+
String get newSavedSnippetTitle => 'New snippet';
354+
355+
@override
356+
String get newSavedSnippetTitleHint => 'Title';
357+
358+
@override
359+
String get newSavedSnippetContentHint => 'Content';
360+
361+
@override
362+
String get errorFailedToCreateSavedSnippetTitle =>
363+
'Failed to create saved snippet';
364+
365+
@override
366+
String get savedSnippetTitleValidationErrorEmpty => 'Title cannot be empty.';
367+
368+
@override
369+
String get savedSnippetTitleValidationErrorTooLong =>
370+
'Title length shouldn\'t be greater than 60 characters.';
371+
372+
@override
373+
String get savedSnippetContentValidationErrorEmpty =>
374+
'Content cannot be empty.';
375+
376+
@override
377+
String get savedSnippetContentValidationErrorTooLong =>
378+
'Content length shouldn\'t be greater than 10000 characters.';
379+
340380
@override
341381
String get composeBoxGenericContentHint => 'Wpisz wiadomość';
342382

0 commit comments

Comments
 (0)