Localize email components (#820)

This commit is contained in:
Leendert de Borst
2025-07-04 12:17:59 +02:00
committed by Leendert de Borst
parent 67d4a0b8ff
commit e7644dc3fb
9 changed files with 663 additions and 38 deletions

View File

@@ -3,12 +3,15 @@
@using AliasVault.Shared.Core;
@using AliasVault.Client.Main.Components.Layout
@using AliasVault.RazorComponents.Services
@using Microsoft.Extensions.Localization
@using AliasVault.Client.Resources
@inject JsInteropService JsInteropService
@inject GlobalNotificationService GlobalNotificationService
@inject IHttpClientFactory HttpClientFactory
@inject EmailService EmailService
@inject HttpClient HttpClient
@inject ConfirmModalService ConfirmModalService
@inject IStringLocalizerFactory LocalizerFactory
<ClickOutsideHandler OnClose="OnClose" ContentId="emailModal">
<ModalWrapper OnEnter="Close">
@@ -35,12 +38,12 @@
<!-- 2-column layout for email details -->
<div class="grid grid-cols-1 sm:grid-cols-2 gap-4 text-sm text-gray-500 dark:text-gray-400">
<div class="space-y-1">
<p>From: @(Email?.FromLocal)@@@(Email?.FromDomain)</p>
<p>To: @(Email?.ToLocal)@@@(Email?.ToDomain)</p>
<p>@Localizer["FromLabel"] @(Email?.FromLocal)@@@(Email?.FromDomain)</p>
<p>@Localizer["ToLabel"] @(Email?.ToLocal)@@@(Email?.ToDomain)</p>
</div>
<div class="space-y-1">
<p>Date: @Email?.DateSystem</p>
<p>Actions: <button @onclick="ShowDeleteConfirmation" class="text-red-500 hover:text-red-700 text-sm">Delete</button></p>
<p>@Localizer["DateLabel"] @Email?.DateSystem</p>
<p>@Localizer["ActionsLabel"] <button @onclick="ShowDeleteConfirmation" class="text-red-500 hover:text-red-700 text-sm">@Localizer["DeleteButton"]</button></p>
</div>
</div>
</div>
@@ -57,7 +60,7 @@
@if (Email?.Attachments?.Any() == true)
{
<div class="border-t border-gray-200 dark:border-gray-600 pt-4">
<h3 class="text-sm font-medium text-gray-500 dark:text-gray-400 mb-2">Attachments:</h3>
<h3 class="text-sm font-medium text-gray-500 dark:text-gray-400 mb-2">@Localizer["AttachmentsLabel"]</h3>
<div class="grid grid-cols-1 sm:grid-cols-2 md:grid-cols-3 gap-4">
@foreach (var attachment in Email.Attachments)
{
@@ -76,7 +79,7 @@
}
</div>
<div class="mt-6 flex justify-end space-x-4">
<button id="close-email-modal" @onclick="Close" class="px-4 py-2 bg-blue-500 text-white rounded hover:bg-blue-600">Close</button>
<button id="close-email-modal" @onclick="Close" class="px-4 py-2 bg-blue-500 text-white rounded hover:bg-blue-600">@Localizer["CloseButton"]</button>
</div>
</div>
</div>
@@ -84,6 +87,8 @@
</ClickOutsideHandler>
@code {
private IStringLocalizer Localizer => LocalizerFactory.Create("Components.Main.Email.EmailModal", "AliasVault.Client");
/// <summary>
/// The email to show in the modal.
/// </summary>
@@ -124,8 +129,8 @@
}
var result = await ConfirmModalService.ShowConfirmation(
"Delete Email",
"Are you sure you want to delete this email? This action cannot be undone."
Localizer["DeleteEmailTitle"],
Localizer["DeleteEmailConfirmation"]
);
if (result)
@@ -185,18 +190,18 @@
if (response.IsSuccessStatusCode)
{
await OnEmailDeleted.InvokeAsync(Email.Id);
GlobalNotificationService.AddSuccessMessage("Email deleted successfully", true);
GlobalNotificationService.AddSuccessMessage(Localizer["EmailDeletedSuccess"], true);
await Close();
}
else
{
var errorMessage = await response.Content.ReadAsStringAsync();
GlobalNotificationService.AddErrorMessage($"Failed to delete email: {errorMessage}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["EmailDeleteFailed"]}: {errorMessage}", true);
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"An error occurred: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["GenericError"]}: {ex.Message}", true);
}
}
@@ -216,16 +221,16 @@
if (response.IsSuccessStatusCode)
{
await OnEmailDeleted.InvokeAsync(Email.Id);
GlobalNotificationService.AddSuccessMessage($"Email deleted successfully.", true);
GlobalNotificationService.AddSuccessMessage(Localizer["EmailDeletedSuccess"], true);
}
else
{
GlobalNotificationService.AddErrorMessage($"Failed to delete email.", true);
GlobalNotificationService.AddErrorMessage(Localizer["EmailDeleteFailed"], true);
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"Failed to delete email: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["EmailDeleteFailed"]}: {ex.Message}", true);
}
}
@@ -251,7 +256,7 @@
else
{
// No HTML and no plain text available
EmailBody = "[This email has no body.]";
EmailBody = Localizer["NoEmailBody"];
}
}
}
@@ -278,7 +283,7 @@
}
else
{
GlobalNotificationService.AddErrorMessage("Failed to download attachment", true);
GlobalNotificationService.AddErrorMessage(Localizer["AttachmentDownloadFailed"], true);
}
}
else
@@ -301,13 +306,13 @@
}
else
{
GlobalNotificationService.AddErrorMessage("Failed to download attachment", true);
GlobalNotificationService.AddErrorMessage(Localizer["AttachmentDownloadFailed"], true);
}
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"Error downloading attachment: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["AttachmentDownloadError"]}: {ex.Message}", true);
}
}
}

View File

@@ -3,12 +3,14 @@
@using AliasVault.Shared.Core;
@using AliasVault.Client.Main.Components.Layout
@using AliasVault.RazorComponents.Services
@using Microsoft.Extensions.Localization
@inject JsInteropService JsInteropService
@inject GlobalNotificationService GlobalNotificationService
@inject IHttpClientFactory HttpClientFactory
@inject EmailService EmailService
@inject HttpClient HttpClient
@inject ConfirmModalService ConfirmModalService
@inject IStringLocalizerFactory LocalizerFactory
<div class="h-full flex flex-col bg-white border-l border-gray-200 dark:border-gray-700 rounded-l-lg">
@if (Email != null)
@@ -35,14 +37,14 @@
<!-- 2-column layout for email details -->
<div class="grid grid-cols-1 sm:grid-cols-2 gap-4 text-sm text-gray-600 dark:text-gray-300">
<div class="space-y-1">
<p><span class="font-medium">From:</span> @(Email.FromLocal)@@@(Email.FromDomain)</p>
<p><span class="font-medium">To:</span> @(Email.ToLocal)@@@(Email.ToDomain)</p>
<p><span class="font-medium">@Localizer["FromLabel"]</span> @(Email.FromLocal)@@@(Email.FromDomain)</p>
<p><span class="font-medium">@Localizer["ToLabel"]</span> @(Email.ToLocal)@@@(Email.ToDomain)</p>
</div>
<div class="space-y-1">
<p><span class="font-medium">Date:</span> @Email.DateSystem</p>
<p><span class="font-medium">@Localizer["DateLabel"]</span> @Email.DateSystem</p>
@if (!string.IsNullOrEmpty(CredentialName) && CredentialId != Guid.Empty)
{
<p><span class="font-medium">Credential:</span>
<p><span class="font-medium">@Localizer["CredentialLabel"]</span>
<button @onclick="@(() => OnCredentialClick.InvokeAsync(CredentialId))"
class="text-blue-600 hover:underline dark:text-blue-400 cursor-pointer">
@CredentialName
@@ -51,7 +53,7 @@
}
else
{
<p><span class="font-medium">Credential:</span> <span class="text-gray-400 dark:text-gray-500">None</span></p>
<p><span class="font-medium">@Localizer["CredentialLabel"]</span> <span class="text-gray-400 dark:text-gray-500">@Localizer["NoneValue"]</span></p>
}
</div>
</div>
@@ -71,7 +73,7 @@
{
<!-- Attachments Section - Fixed height -->
<div class="border-t border-gray-200 dark:border-gray-600 p-4 bg-gray-50 dark:bg-gray-800">
<h3 class="text-sm font-medium text-gray-500 dark:text-gray-400 mb-2">Attachments:</h3>
<h3 class="text-sm font-medium text-gray-500 dark:text-gray-400 mb-2">@Localizer["AttachmentsLabel"]</h3>
<div class="grid grid-cols-1 gap-2 max-h-32 overflow-y-auto">
@foreach (var attachment in Email.Attachments)
{
@@ -97,13 +99,14 @@
<svg class="mx-auto h-12 w-12 text-gray-300 dark:text-gray-600" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 8l7.89 4.26a2 2 0 002.22 0L21 8M5 19h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v10a2 2 0 002 2z"/>
</svg>
<p class="mt-2 text-sm">Select an email to view its contents</p>
<p class="mt-2 text-sm">@Localizer["SelectEmailMessage"]</p>
</div>
</div>
}
</div>
@code {
private IStringLocalizer Localizer => LocalizerFactory.Create("Components.Main.Email.EmailPreview", "AliasVault.Client");
/// <summary>
/// The email to show in the preview.
/// </summary>
@@ -156,8 +159,8 @@
}
var result = await ConfirmModalService.ShowConfirmation(
"Delete Email",
"Are you sure you want to delete this email? This action cannot be undone."
Localizer["DeleteEmailTitle"],
Localizer["DeleteEmailConfirmation"]
);
if (result)
@@ -208,17 +211,17 @@
if (response.IsSuccessStatusCode)
{
await OnEmailDeleted.InvokeAsync(Email.Id);
GlobalNotificationService.AddSuccessMessage("Email deleted successfully", true);
GlobalNotificationService.AddSuccessMessage(Localizer["EmailDeletedSuccess"], true);
}
else
{
var errorMessage = await response.Content.ReadAsStringAsync();
GlobalNotificationService.AddErrorMessage($"Failed to delete email: {errorMessage}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["EmailDeleteFailed"]}: {errorMessage}", true);
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"An error occurred: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["GenericError"]}: {ex.Message}", true);
}
}
@@ -238,16 +241,16 @@
if (response.IsSuccessStatusCode)
{
await OnEmailDeleted.InvokeAsync(Email.Id);
GlobalNotificationService.AddSuccessMessage($"Email deleted successfully.", true);
GlobalNotificationService.AddSuccessMessage(Localizer["EmailDeletedSuccess"], true);
}
else
{
GlobalNotificationService.AddErrorMessage($"Failed to delete email.", true);
GlobalNotificationService.AddErrorMessage(Localizer["EmailDeleteFailed"], true);
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"Failed to delete email: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["EmailDeleteFailed"]}: {ex.Message}", true);
}
}
@@ -272,7 +275,7 @@
else
{
// No HTML and no plain text available
EmailBody = "[This email has no body.]";
EmailBody = Localizer["NoEmailBody"];
}
}
}
@@ -299,7 +302,7 @@
}
else
{
GlobalNotificationService.AddErrorMessage("Failed to download attachment", true);
GlobalNotificationService.AddErrorMessage(Localizer["AttachmentDownloadFailed"], true);
}
}
else
@@ -322,13 +325,13 @@
}
else
{
GlobalNotificationService.AddErrorMessage("Failed to download attachment", true);
GlobalNotificationService.AddErrorMessage(Localizer["AttachmentDownloadFailed"], true);
}
}
}
catch (Exception ex)
{
GlobalNotificationService.AddErrorMessage($"Error downloading attachment: {ex.Message}", true);
GlobalNotificationService.AddErrorMessage($"{Localizer["AttachmentDownloadError"]}: {ex.Message}", true);
}
}
}

View File

@@ -1,4 +1,6 @@
@using AliasVault.Client.Main.Pages.Emails.Models
@using Microsoft.Extensions.Localization
@inject IStringLocalizerFactory LocalizerFactory
<li class="@($"hover:bg-gray-50 dark:hover:bg-gray-600 transition duration-150 ease-in-out cursor-pointer {(IsSelected ? "bg-primary-50 dark:bg-primary-900/30 border-l-4 border-primary-500" : "")}")">
<div @onclick="@(() => OnEmailClick.InvokeAsync(Email.Id))" class="p-4 flex justify-start items-start">
@@ -19,7 +21,7 @@
}
@if (IsNewEmail)
{
<div class="w-2 h-2 ml-1 bg-yellow-500 rounded-full animate-pulse flex-shrink-0" title="New email"></div>
<div class="w-2 h-2 ml-1 bg-yellow-500 rounded-full animate-pulse flex-shrink-0" title="@Localizer["NewEmailTooltip"]"></div>
}
</div>
<!-- Subject (smaller, below from) -->
@@ -41,6 +43,7 @@
</li>
@code {
private IStringLocalizer Localizer => LocalizerFactory.Create("Components.Main.Email.EmailRow", "AliasVault.Client");
/// <summary>
/// The email model.
/// </summary>

View File

@@ -0,0 +1,121 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="FromLabel" xml:space="preserve">
<value>From:</value>
<comment>Email sender field label</comment>
</data>
<data name="ToLabel" xml:space="preserve">
<value>To:</value>
<comment>Email recipient field label</comment>
</data>
<data name="DateLabel" xml:space="preserve">
<value>Date:</value>
<comment>Email date field label</comment>
</data>
<data name="ActionsLabel" xml:space="preserve">
<value>Actions:</value>
<comment>Email actions section label</comment>
</data>
<data name="DeleteButton" xml:space="preserve">
<value>Delete</value>
<comment>Delete email button text</comment>
</data>
<data name="AttachmentsLabel" xml:space="preserve">
<value>Attachments:</value>
<comment>Email attachments section header</comment>
</data>
<data name="CloseButton" xml:space="preserve">
<value>Close</value>
<comment>Close modal button text</comment>
</data>
<data name="DeleteEmailTitle" xml:space="preserve">
<value>Delete Email</value>
<comment>Delete email confirmation dialog title</comment>
</data>
<data name="DeleteEmailConfirmation" xml:space="preserve">
<value>Are you sure you want to delete this email? This action cannot be undone.</value>
<comment>Delete email confirmation message</comment>
</data>
<data name="EmailDeletedSuccess" xml:space="preserve">
<value>Email deleted successfully</value>
<comment>Success message when email is deleted</comment>
</data>
<data name="EmailDeleteFailed" xml:space="preserve">
<value>Failed to delete email</value>
<comment>Error message when email deletion fails</comment>
</data>
<data name="GenericError" xml:space="preserve">
<value>An error occurred</value>
<comment>Generic error message</comment>
</data>
<data name="NoEmailBody" xml:space="preserve">
<value>[This email has no body.]</value>
<comment>Message shown when email has no content</comment>
</data>
<data name="AttachmentDownloadFailed" xml:space="preserve">
<value>Failed to download attachment</value>
<comment>Error message when attachment download fails</comment>
</data>
<data name="AttachmentDownloadError" xml:space="preserve">
<value>Error downloading attachment</value>
<comment>Error message for attachment download error</comment>
</data>
</root>

View File

@@ -0,0 +1,121 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="FromLabel" xml:space="preserve">
<value>Van:</value>
<comment>Email sender field label</comment>
</data>
<data name="ToLabel" xml:space="preserve">
<value>Aan:</value>
<comment>Email recipient field label</comment>
</data>
<data name="DateLabel" xml:space="preserve">
<value>Datum:</value>
<comment>Email date field label</comment>
</data>
<data name="ActionsLabel" xml:space="preserve">
<value>Acties:</value>
<comment>Email actions section label</comment>
</data>
<data name="DeleteButton" xml:space="preserve">
<value>Verwijderen</value>
<comment>Delete email button text</comment>
</data>
<data name="AttachmentsLabel" xml:space="preserve">
<value>Bijlagen:</value>
<comment>Email attachments section header</comment>
</data>
<data name="CloseButton" xml:space="preserve">
<value>Sluiten</value>
<comment>Close modal button text</comment>
</data>
<data name="DeleteEmailTitle" xml:space="preserve">
<value>E-mail verwijderen</value>
<comment>Delete email confirmation dialog title</comment>
</data>
<data name="DeleteEmailConfirmation" xml:space="preserve">
<value>Weet u zeker dat u deze e-mail wilt verwijderen? Deze actie kan niet ongedaan worden gemaakt.</value>
<comment>Delete email confirmation message</comment>
</data>
<data name="EmailDeletedSuccess" xml:space="preserve">
<value>E-mail succesvol verwijderd</value>
<comment>Success message when email is deleted</comment>
</data>
<data name="EmailDeleteFailed" xml:space="preserve">
<value>Verwijderen van e-mail mislukt</value>
<comment>Error message when email deletion fails</comment>
</data>
<data name="GenericError" xml:space="preserve">
<value>Er is een fout opgetreden</value>
<comment>Generic error message</comment>
</data>
<data name="NoEmailBody" xml:space="preserve">
<value>[Deze e-mail heeft geen inhoud.]</value>
<comment>Message shown when email has no content</comment>
</data>
<data name="AttachmentDownloadFailed" xml:space="preserve">
<value>Downloaden van bijlage mislukt</value>
<comment>Error message when attachment download fails</comment>
</data>
<data name="AttachmentDownloadError" xml:space="preserve">
<value>Fout bij downloaden bijlage</value>
<comment>Error message for attachment download error</comment>
</data>
</root>

View File

@@ -0,0 +1,121 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="FromLabel" xml:space="preserve">
<value>From:</value>
<comment>Email sender field label</comment>
</data>
<data name="ToLabel" xml:space="preserve">
<value>To:</value>
<comment>Email recipient field label</comment>
</data>
<data name="DateLabel" xml:space="preserve">
<value>Date:</value>
<comment>Email date field label</comment>
</data>
<data name="CredentialLabel" xml:space="preserve">
<value>Credential:</value>
<comment>Email credential field label</comment>
</data>
<data name="NoneValue" xml:space="preserve">
<value>None</value>
<comment>No credential assigned value</comment>
</data>
<data name="AttachmentsLabel" xml:space="preserve">
<value>Attachments:</value>
<comment>Email attachments section header</comment>
</data>
<data name="SelectEmailMessage" xml:space="preserve">
<value>Select an email to view its contents</value>
<comment>Empty state message when no email is selected</comment>
</data>
<data name="DeleteEmailTitle" xml:space="preserve">
<value>Delete Email</value>
<comment>Delete email confirmation dialog title</comment>
</data>
<data name="DeleteEmailConfirmation" xml:space="preserve">
<value>Are you sure you want to delete this email? This action cannot be undone.</value>
<comment>Delete email confirmation message</comment>
</data>
<data name="EmailDeletedSuccess" xml:space="preserve">
<value>Email deleted successfully</value>
<comment>Success message when email is deleted</comment>
</data>
<data name="EmailDeleteFailed" xml:space="preserve">
<value>Failed to delete email</value>
<comment>Error message when email deletion fails</comment>
</data>
<data name="GenericError" xml:space="preserve">
<value>An error occurred</value>
<comment>Generic error message</comment>
</data>
<data name="NoEmailBody" xml:space="preserve">
<value>[This email has no body.]</value>
<comment>Message shown when email has no content</comment>
</data>
<data name="AttachmentDownloadFailed" xml:space="preserve">
<value>Failed to download attachment</value>
<comment>Error message when attachment download fails</comment>
</data>
<data name="AttachmentDownloadError" xml:space="preserve">
<value>Error downloading attachment</value>
<comment>Error message for attachment download error</comment>
</data>
</root>

View File

@@ -0,0 +1,121 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="FromLabel" xml:space="preserve">
<value>Van:</value>
<comment>Email sender field label</comment>
</data>
<data name="ToLabel" xml:space="preserve">
<value>Aan:</value>
<comment>Email recipient field label</comment>
</data>
<data name="DateLabel" xml:space="preserve">
<value>Datum:</value>
<comment>Email date field label</comment>
</data>
<data name="CredentialLabel" xml:space="preserve">
<value>Inloggegevens:</value>
<comment>Email credential field label</comment>
</data>
<data name="NoneValue" xml:space="preserve">
<value>Geen</value>
<comment>No credential assigned value</comment>
</data>
<data name="AttachmentsLabel" xml:space="preserve">
<value>Bijlagen:</value>
<comment>Email attachments section header</comment>
</data>
<data name="SelectEmailMessage" xml:space="preserve">
<value>Selecteer een e-mail om de inhoud te bekijken</value>
<comment>Empty state message when no email is selected</comment>
</data>
<data name="DeleteEmailTitle" xml:space="preserve">
<value>E-mail verwijderen</value>
<comment>Delete email confirmation dialog title</comment>
</data>
<data name="DeleteEmailConfirmation" xml:space="preserve">
<value>Weet u zeker dat u deze e-mail wilt verwijderen? Deze actie kan niet ongedaan worden gemaakt.</value>
<comment>Delete email confirmation message</comment>
</data>
<data name="EmailDeletedSuccess" xml:space="preserve">
<value>E-mail succesvol verwijderd</value>
<comment>Success message when email is deleted</comment>
</data>
<data name="EmailDeleteFailed" xml:space="preserve">
<value>Verwijderen van e-mail mislukt</value>
<comment>Error message when email deletion fails</comment>
</data>
<data name="GenericError" xml:space="preserve">
<value>Er is een fout opgetreden</value>
<comment>Generic error message</comment>
</data>
<data name="NoEmailBody" xml:space="preserve">
<value>[Deze e-mail heeft geen inhoud.]</value>
<comment>Message shown when email has no content</comment>
</data>
<data name="AttachmentDownloadFailed" xml:space="preserve">
<value>Downloaden van bijlage mislukt</value>
<comment>Error message when attachment download fails</comment>
</data>
<data name="AttachmentDownloadError" xml:space="preserve">
<value>Fout bij downloaden bijlage</value>
<comment>Error message for attachment download error</comment>
</data>
</root>

View File

@@ -0,0 +1,65 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="NewEmailTooltip" xml:space="preserve">
<value>New email</value>
<comment>Tooltip text for new email indicator</comment>
</data>
</root>

View File

@@ -0,0 +1,65 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<data name="NewEmailTooltip" xml:space="preserve">
<value>Nieuwe e-mail</value>
<comment>Tooltip text for new email indicator</comment>
</data>
</root>