From 853bde8e6a92d03438975c554ef8004e6e2b37ce Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 13:58:54 +0200 Subject: [PATCH 1/9] Defined an own progress bar --- .../Components/NXProgressBar.Designer.cs | 48 ++++++++++++ .../UI WinForms/Components/NXProgressBar.cs | 73 +++++++++++++++++++ .../UI WinForms/Components/NXProgressBar.resx | 60 +++++++++++++++ 3 files changed, 181 insertions(+) create mode 100644 I18N Commander/UI WinForms/Components/NXProgressBar.Designer.cs create mode 100644 I18N Commander/UI WinForms/Components/NXProgressBar.cs create mode 100644 I18N Commander/UI WinForms/Components/NXProgressBar.resx diff --git a/I18N Commander/UI WinForms/Components/NXProgressBar.Designer.cs b/I18N Commander/UI WinForms/Components/NXProgressBar.Designer.cs new file mode 100644 index 0000000..bc99865 --- /dev/null +++ b/I18N Commander/UI WinForms/Components/NXProgressBar.Designer.cs @@ -0,0 +1,48 @@ +namespace UI_WinForms.Components +{ + sealed partial class NXProgressBar + { + /// + /// Required designer variable. + /// + private System.ComponentModel.IContainer components = null; + + /// + /// Clean up any resources being used. + /// + /// true if managed resources should be disposed; otherwise, false. + protected override void Dispose(bool disposing) + { + if (disposing && (components != null)) + { + components.Dispose(); + } + base.Dispose(disposing); + } + + #region Component Designer generated code + + /// + /// Required method for Designer support - do not modify + /// the contents of this method with the code editor. + /// + private void InitializeComponent() + { + this.SuspendLayout(); + // + // NXProgressBar + // + this.AutoScaleDimensions = new System.Drawing.SizeF(120F, 120F); + this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Dpi; + this.BackColor = System.Drawing.Color.LightSkyBlue; + this.Font = new System.Drawing.Font("Segoe UI", 8F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); + this.Margin = new System.Windows.Forms.Padding(0); + this.Name = "NXProgressBar"; + this.Size = new System.Drawing.Size(702, 41); + this.ResumeLayout(false); + + } + + #endregion + } +} diff --git a/I18N Commander/UI WinForms/Components/NXProgressBar.cs b/I18N Commander/UI WinForms/Components/NXProgressBar.cs new file mode 100644 index 0000000..6b3bc7d --- /dev/null +++ b/I18N Commander/UI WinForms/Components/NXProgressBar.cs @@ -0,0 +1,73 @@ +using System.ComponentModel; +using SolidBrush = System.Drawing.SolidBrush; + +namespace UI_WinForms.Components; + +public sealed partial class NXProgressBar : UserControl +{ + private static readonly SolidBrush BACKGROUND_NOT_FILLED = new(SystemColors.Control); + + private readonly SolidBrush backgroundFilled; + private readonly SolidBrush textBrush; + + public NXProgressBar() + { + this.InitializeComponent(); + this.backgroundFilled = new SolidBrush(this.BackColor); + this.textBrush = new SolidBrush(this.ForeColor); + } + + [Category("Settings"), Description("Text to show inside the progress bar.")] + public string InformationText { get; set; } = string.Empty; + + [Category("Settings"), Description("The current percentage [0,100] of the progress bar.")] + public int PercentInt + { + get => (int) (this.PercentFloat * 100); + set => this.PercentFloat = value / 100f; + } + + [Category("Settings"), Description("The current percentage [0,1] of the progress bar.")] + public float PercentFloat { get; set; } = 0; + + [Category("Settings"), Description("When true, appends the percentage to the text.")] + public bool AppendPercentageToText { get; set; } = true; + + protected override void OnPaintBackground(PaintEventArgs e) + { + // Do not paint the background. + } + + // Draw the progress bar by filling the background of the label with color: + protected override void OnPaint(PaintEventArgs e) + { + base.OnPaint(e); + + var width = (int) MathF.Ceiling((this.Width - this.Margin.Horizontal) * this.PercentFloat); + var height = this.Height - this.Margin.Vertical; + + // Erase the background: + e.Graphics.FillRectangle(BACKGROUND_NOT_FILLED, this.Margin.Left, this.Margin.Top, this.Width - this.Margin.Horizontal, height); + + // Draw the filled background: + e.Graphics.FillRectangle(this.backgroundFilled, this.Margin.Left, this.Margin.Top, width, height); + + // Calculate the text x position by using the margin: + var textX = this.Margin.Left + this.Padding.Left; + + // Calculate the text y position by considering the margin: + var textY = (int) MathF.Ceiling((this.Height - this.Font.Height) / 2f) + this.Margin.Top + this.Padding.Top; + + // Draw the text horizontally at the beginning, and vertically centered: + e.Graphics.DrawString(this.GetTextForRendering(), this.Font, this.textBrush, textX, textY); + } + + private string GetTextForRendering() + { + var text = this.InformationText; + if (this.AppendPercentageToText) + text += $" ({this.PercentInt}%)"; + + return text; + } +} \ No newline at end of file diff --git a/I18N Commander/UI WinForms/Components/NXProgressBar.resx b/I18N Commander/UI WinForms/Components/NXProgressBar.resx new file mode 100644 index 0000000..b5ae26c --- /dev/null +++ b/I18N Commander/UI WinForms/Components/NXProgressBar.resx @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + \ No newline at end of file From 40877241fea05351ae032f93d3e09e4b8368aa91 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 19:19:46 +0200 Subject: [PATCH 2/9] Fixed DeepL translation when using empty text --- I18N Commander/Processor/DeepL.cs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/I18N Commander/Processor/DeepL.cs b/I18N Commander/Processor/DeepL.cs index 49be452..3e7d8fd 100644 --- a/I18N Commander/Processor/DeepL.cs +++ b/I18N Commander/Processor/DeepL.cs @@ -39,6 +39,9 @@ public static class DeepL { if (DEEPL_NOT_AVAILABLE) return string.Empty; + + if (string.IsNullOrWhiteSpace(text)) + return string.Empty; if (await AppSettings.GetDeepLMode() == SettingDeepLMode.DISABLED) return string.Empty; From c8b5dc9b7ad6c80d525d5f14bb4271b119c02282 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 19:24:24 +0200 Subject: [PATCH 3/9] Added method to calculate the overall translation progress --- I18N Commander/Processor/TranslationProcessor.cs | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/I18N Commander/Processor/TranslationProcessor.cs b/I18N Commander/Processor/TranslationProcessor.cs index f2d2494..7e771b6 100644 --- a/I18N Commander/Processor/TranslationProcessor.cs +++ b/I18N Commander/Processor/TranslationProcessor.cs @@ -51,4 +51,15 @@ public static class TranslationProcessor return updateException.ToProcessorResult(); } } + + public static async Task> CalculateTranslationProgress() + { + await using var db = ProcessorMeta.ServiceProvider.GetRequiredService(); + var numCultures = (await AppSettings.GetCultureIndices()).Count; + var numTextElements = await db.TextElements.CountAsync(); + var numTotalTranslations = numCultures * numTextElements; + var numTextElementsTranslated = await db.Translations.CountAsync(n => !string.IsNullOrWhiteSpace(n.Text)); + + return new ProcessorResult(numTextElementsTranslated * 100 / numTotalTranslations); + } } \ No newline at end of file From 1071439348a71c1eec18728d9c5ee4b404b52ec8 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 19:25:09 +0200 Subject: [PATCH 4/9] Added the translation progress component --- .../TranslationProgress.Designer.cs | 65 +++++++++++++++++++ .../Components/TranslationProgress.cs | 38 +++++++++++ .../Components/TranslationProgress.resx | 60 +++++++++++++++++ 3 files changed, 163 insertions(+) create mode 100644 I18N Commander/UI WinForms/Components/TranslationProgress.Designer.cs create mode 100644 I18N Commander/UI WinForms/Components/TranslationProgress.cs create mode 100644 I18N Commander/UI WinForms/Components/TranslationProgress.resx diff --git a/I18N Commander/UI WinForms/Components/TranslationProgress.Designer.cs b/I18N Commander/UI WinForms/Components/TranslationProgress.Designer.cs new file mode 100644 index 0000000..14a037e --- /dev/null +++ b/I18N Commander/UI WinForms/Components/TranslationProgress.Designer.cs @@ -0,0 +1,65 @@ +namespace UI_WinForms.Components +{ + sealed partial class TranslationProgress + { + /// + /// Required designer variable. + /// + private System.ComponentModel.IContainer components = null; + + /// + /// Clean up any resources being used. + /// + /// true if managed resources should be disposed; otherwise, false. + protected override void Dispose(bool disposing) + { + if (disposing && (components != null)) + { + components.Dispose(); + } + base.Dispose(disposing); + } + + #region Component Designer generated code + + /// + /// Required method for Designer support - do not modify + /// the contents of this method with the code editor. + /// + private void InitializeComponent() + { + this.nxProgressBar = new UI_WinForms.Components.NXProgressBar(); + this.SuspendLayout(); + // + // nxProgressBar + // + this.nxProgressBar.AppendPercentageToText = true; + this.nxProgressBar.BackColor = System.Drawing.Color.LightSkyBlue; + this.nxProgressBar.Dock = System.Windows.Forms.DockStyle.Fill; + this.nxProgressBar.Font = new System.Drawing.Font("Segoe UI", 8F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); + this.nxProgressBar.InformationText = "Overall translation progress"; + this.nxProgressBar.Location = new System.Drawing.Point(0, 0); + this.nxProgressBar.Margin = new System.Windows.Forms.Padding(3, 0, 3, 0); + this.nxProgressBar.Name = "nxProgressBar"; + this.nxProgressBar.Padding = new System.Windows.Forms.Padding(3, 0, 0, 0); + this.nxProgressBar.PercentFloat = 0F; + this.nxProgressBar.PercentInt = 0; + this.nxProgressBar.Size = new System.Drawing.Size(832, 68); + this.nxProgressBar.TabIndex = 0; + // + // TranslationProgress + // + this.AutoScaleDimensions = new System.Drawing.SizeF(8F, 20F); + this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; + this.Controls.Add(this.nxProgressBar); + this.Name = "TranslationProgress"; + this.Size = new System.Drawing.Size(832, 68); + this.ResumeLayout(false); + + } + + #endregion + + private NXProgressBar nxProgressBar; + } +} diff --git a/I18N Commander/UI WinForms/Components/TranslationProgress.cs b/I18N Commander/UI WinForms/Components/TranslationProgress.cs new file mode 100644 index 0000000..c7bd9a2 --- /dev/null +++ b/I18N Commander/UI WinForms/Components/TranslationProgress.cs @@ -0,0 +1,38 @@ +using Processor; + +namespace UI_WinForms.Components; + +public sealed partial class TranslationProgress : UserControl +{ + public TranslationProgress() + { + this.InitializeComponent(); + + this.DoubleBuffered = true; + this.Load += this.OnLoad; + AppEvents.WhenTranslationChanged += async (_, _) => await this.TranslationChanged(); + } + + private async void OnLoad(object? sender, EventArgs e) => await this.CalculateTranslationProgress(); + + private async Task TranslationChanged() => await this.CalculateTranslationProgress(); + + private async Task CalculateTranslationProgress() + { + var result = await TranslationProcessor.CalculateTranslationProgress(); + if (this.nxProgressBar.InvokeRequired) + this.nxProgressBar.Invoke(() => SetProgress(result)); + else + SetProgress(result); + + void SetProgress(ProcessorResult resultData) + { + if (resultData.Successful) + this.nxProgressBar.PercentInt = resultData.Result; + else + this.nxProgressBar.PercentInt = 0; + + this.nxProgressBar.Refresh(); + } + } +} \ No newline at end of file diff --git a/I18N Commander/UI WinForms/Components/TranslationProgress.resx b/I18N Commander/UI WinForms/Components/TranslationProgress.resx new file mode 100644 index 0000000..b5ae26c --- /dev/null +++ b/I18N Commander/UI WinForms/Components/TranslationProgress.resx @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + \ No newline at end of file From 6101f49f44a1bd8a06fc5cab4a92386ac3690c05 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 19:25:51 +0200 Subject: [PATCH 5/9] Added an event for a changed translation --- I18N Commander/UI WinForms/AppEvents.cs | 10 ++++++++++ I18N Commander/UI WinForms/Components/Translation.cs | 7 +++++-- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/I18N Commander/UI WinForms/AppEvents.cs b/I18N Commander/UI WinForms/AppEvents.cs index 5cd9ce9..5ba9c0d 100644 --- a/I18N Commander/UI WinForms/AppEvents.cs +++ b/I18N Commander/UI WinForms/AppEvents.cs @@ -23,4 +23,14 @@ internal static class AppEvents internal static void TextElementChanged(TextElement? textElement) => WhenTextElementChanged?.Invoke(null, textElement); #endregion + + #region Translation was changed + + // Translation changed event which can be subscribed: + internal static event EventHandler WhenTranslationChanged; + + // Method to raise the translation changed event: + internal static void TranslationChanged(Translation? translation) => WhenTranslationChanged?.Invoke(null, translation); + + #endregion } \ No newline at end of file diff --git a/I18N Commander/UI WinForms/Components/Translation.cs b/I18N Commander/UI WinForms/Components/Translation.cs index f823876..80cee88 100644 --- a/I18N Commander/UI WinForms/Components/Translation.cs +++ b/I18N Commander/UI WinForms/Components/Translation.cs @@ -124,8 +124,11 @@ public sealed partial class Translation : UserControl private async void SaveChanges(object? sender, ElapsedEventArgs e) { if (this.currentTranslationId > -1) - await TranslationProcessor.SaveChangedTranslation(this.currentTranslationId, this.textBox.Text, this.checkBoxManual.Checked); - + { + var storedTranslation = await TranslationProcessor.SaveChangedTranslation(this.currentTranslationId, this.textBox.Text, this.checkBoxManual.Checked); + AppEvents.TranslationChanged(storedTranslation.Result); + } + if(this.ParentForm is UI_WinForms.Main main) main.RemoveDeferredSaveOperation(this.currentTranslationId); From 8534163e551749a978c9244bab0c6e32855c9308 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 19:26:10 +0200 Subject: [PATCH 6/9] Added the translation progress component --- .../UI WinForms/Components/Main.Designer.cs | 53 +- .../UI WinForms/Components/Main.resx | 622 +++++++++--------- 2 files changed, 344 insertions(+), 331 deletions(-) diff --git a/I18N Commander/UI WinForms/Components/Main.Designer.cs b/I18N Commander/UI WinForms/Components/Main.Designer.cs index b2b353d..8c0dfb1 100644 --- a/I18N Commander/UI WinForms/Components/Main.Designer.cs +++ b/I18N Commander/UI WinForms/Components/Main.Designer.cs @@ -35,12 +35,13 @@ this.sectionTree = new UI_WinForms.Components.SectionTree(); this.splitContainerRTB = new System.Windows.Forms.SplitContainer(); this.textElements = new UI_WinForms.Components.TextElements(); + this.translations = new UI_WinForms.Components.Translations(); + this.translationProgress = new UI_WinForms.Components.TranslationProgress(); this.tabControl = new System.Windows.Forms.TabControl(); this.tabTranslation = new System.Windows.Forms.TabPage(); this.tabSettings = new System.Windows.Forms.TabPage(); this.settings = new UI_WinForms.Components.Settings(); this.imageList = new System.Windows.Forms.ImageList(this.components); - this.translations = new UI_WinForms.Components.Translations(); this.tableLayout.SuspendLayout(); ((System.ComponentModel.ISupportInitialize)(this.splitContainerLR)).BeginInit(); this.splitContainerLR.Panel1.SuspendLayout(); @@ -59,13 +60,14 @@ // this.tableLayout.ColumnCount = 1; this.tableLayout.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 100F)); - this.tableLayout.Controls.Add(this.splitContainerLR, 0, 0); + this.tableLayout.Controls.Add(this.splitContainerLR, 0, 1); + this.tableLayout.Controls.Add(this.translationProgress, 0, 0); this.tableLayout.Dock = System.Windows.Forms.DockStyle.Fill; this.tableLayout.Location = new System.Drawing.Point(3, 3); this.tableLayout.Name = "tableLayout"; - this.tableLayout.RowCount = 1; - this.tableLayout.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F)); + this.tableLayout.RowCount = 2; this.tableLayout.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Absolute, 20F)); + this.tableLayout.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F)); this.tableLayout.Size = new System.Drawing.Size(885, 589); this.tableLayout.TabIndex = 0; // @@ -74,7 +76,7 @@ this.splitContainerLR.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle; this.splitContainerLR.Dock = System.Windows.Forms.DockStyle.Fill; this.splitContainerLR.FixedPanel = System.Windows.Forms.FixedPanel.Panel1; - this.splitContainerLR.Location = new System.Drawing.Point(3, 3); + this.splitContainerLR.Location = new System.Drawing.Point(3, 23); this.splitContainerLR.Name = "splitContainerLR"; // // splitContainerLR.Panel1 @@ -85,7 +87,7 @@ // splitContainerLR.Panel2 // this.splitContainerLR.Panel2.Controls.Add(this.splitContainerRTB); - this.splitContainerLR.Size = new System.Drawing.Size(879, 583); + this.splitContainerLR.Size = new System.Drawing.Size(879, 563); this.splitContainerLR.SplitterDistance = 319; this.splitContainerLR.TabIndex = 1; // @@ -95,7 +97,7 @@ this.sectionTree.Font = new System.Drawing.Font("Segoe UI", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); this.sectionTree.Location = new System.Drawing.Point(0, 0); this.sectionTree.Name = "sectionTree"; - this.sectionTree.Size = new System.Drawing.Size(317, 581); + this.sectionTree.Size = new System.Drawing.Size(317, 561); this.sectionTree.TabIndex = 0; // // splitContainerRTB @@ -115,7 +117,7 @@ // splitContainerRTB.Panel2 // this.splitContainerRTB.Panel2.Controls.Add(this.translations); - this.splitContainerRTB.Size = new System.Drawing.Size(556, 583); + this.splitContainerRTB.Size = new System.Drawing.Size(556, 563); this.splitContainerRTB.SplitterDistance = 340; this.splitContainerRTB.TabIndex = 0; // @@ -128,6 +130,25 @@ this.textElements.Size = new System.Drawing.Size(554, 338); this.textElements.TabIndex = 0; // + // translations + // + this.translations.Dock = System.Windows.Forms.DockStyle.Fill; + this.translations.Enabled = false; + this.translations.Font = new System.Drawing.Font("Segoe UI", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); + this.translations.Location = new System.Drawing.Point(0, 0); + this.translations.Name = "translations"; + this.translations.Size = new System.Drawing.Size(554, 217); + this.translations.TabIndex = 0; + // + // translationProgress + // + this.translationProgress.Dock = System.Windows.Forms.DockStyle.Fill; + this.translationProgress.Location = new System.Drawing.Point(0, 0); + this.translationProgress.Margin = new System.Windows.Forms.Padding(0); + this.translationProgress.Name = "translationProgress"; + this.translationProgress.Size = new System.Drawing.Size(885, 20); + this.translationProgress.TabIndex = 2; + // // tabControl // this.tabControl.Alignment = System.Windows.Forms.TabAlignment.Left; @@ -160,10 +181,10 @@ // this.tabSettings.Controls.Add(this.settings); this.tabSettings.ImageIndex = 0; - this.tabSettings.Location = new System.Drawing.Point(136, 4); + this.tabSettings.Location = new System.Drawing.Point(70, 4); this.tabSettings.Name = "tabSettings"; this.tabSettings.Padding = new System.Windows.Forms.Padding(3); - this.tabSettings.Size = new System.Drawing.Size(60, 92); + this.tabSettings.Size = new System.Drawing.Size(891, 595); this.tabSettings.TabIndex = 1; this.tabSettings.Text = "Settings"; this.tabSettings.UseVisualStyleBackColor = true; @@ -174,7 +195,7 @@ this.settings.Font = new System.Drawing.Font("Segoe UI", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); this.settings.Location = new System.Drawing.Point(3, 3); this.settings.Name = "settings"; - this.settings.Size = new System.Drawing.Size(54, 86); + this.settings.Size = new System.Drawing.Size(885, 589); this.settings.TabIndex = 0; // // imageList @@ -185,15 +206,6 @@ this.imageList.Images.SetKeyName(0, "icons8-settings.svg.png"); this.imageList.Images.SetKeyName(1, "icons8-language-45.png"); // - // translations - // - this.translations.Dock = System.Windows.Forms.DockStyle.Fill; - this.translations.Font = new System.Drawing.Font("Segoe UI", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - this.translations.Location = new System.Drawing.Point(0, 0); - this.translations.Name = "translations"; - this.translations.Size = new System.Drawing.Size(554, 237); - this.translations.TabIndex = 0; - // // Main // this.AutoScaleDimensions = new System.Drawing.SizeF(120F, 120F); @@ -231,5 +243,6 @@ private ImageList imageList; private Settings settings; private Translations translations; + private TranslationProgress translationProgress; } } diff --git a/I18N Commander/UI WinForms/Components/Main.resx b/I18N Commander/UI WinForms/Components/Main.resx index 04561c3..2d9781b 100644 --- a/I18N Commander/UI WinForms/Components/Main.resx +++ b/I18N Commander/UI WinForms/Components/Main.resx @@ -64,324 +64,324 @@ AAEAAAD/////AQAAAAAAAAAMAgAAAEZTeXN0ZW0uV2luZG93cy5Gb3JtcywgQ3VsdHVyZT1uZXV0cmFs LCBQdWJsaWNLZXlUb2tlbj1iNzdhNWM1NjE5MzRlMDg5BQEAAAAmU3lzdGVtLldpbmRvd3MuRm9ybXMu - SW1hZ2VMaXN0U3RyZWFtZXIBAAAABERhdGEHAgIAAAAJAwAAAA8DAAAAUEoAAAJNU0Z0AUkBTAIBAQIB - AAE4AQABOAEAAS0BAAEtAQAE/wEhAQAI/wFCAU0BNgcAATYDAAEoAwABtAMAAS0DAAEBAQABIAUAAZAB + SW1hZ2VMaXN0U3RyZWFtZXIBAAAABERhdGEHAgIAAAAJAwAAAA8DAAAALEoAAAJNU0Z0AUkBTAIBAQIB + AAFQAQABUAEAAS0BAAEtAQAE/wEhAQAI/wFCAU0BNgcAATYDAAEoAwABtAMAAS0DAAEBAQABIAUAAZAB fvoAAw8BFAMTARkEAf8A/wAqAAMnATkDTgGWA1EBoQNRAaEDUQGhA04BlgMnATp8AAMLAQ4CUwFRAaIB - XgFbAVkBxwMlATb/AP8AJgADEQEWA0wB8wE6AjkB/wE9ATwBOwH/AT0BPAE7Af8BPQE8ATsB/wE6AjkB - /wNGAfQDEQEWeAADEgEYAWABXQFaAcwBvAFbARkB/wFnAV4BWQHXAxABFf8A/wAiAAM/AW4BRgFDAUIB - /wHEAa8BpgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AcQBrgGmAf8BRgFDAUIB/wNAAXB4AAMSARgB - YAFdAVoBzAG8AVsBGQH/AbwBWwEZAf8BaAFfAVkB2AMlATcEAf8A/wAaAANYAbcBVwFSAVAB/wHeAcUB - uwH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/Ad4BxQG7Af8BVwFSAU8B/wNYAboEAXQAAxIBGAFgAV0B - WgHMAbsBWwEZAf8BvAFbARkB/wG8AVsBGQH/AWgBXwFaAdUCGgEZASP/APEAAwMBBAMiATEDKQE+AxIB - GBQAAxIBGANcAdsBewFwAWwB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - egFwAWsB/wNcAdsDEwEaFAADEgEXAykBPgMiATEDAwEEUAADEgEYAWABXQFaAcwBuwFbARkB/wG7AVsB - GQH/AbsBWwEZAf8BvAFbARkB/wFmAV0BWwHUAyEBLwQB/wDlAAMCAQMDPQFpA1cB5ANNAe8DWwHQAzYB - WQMEAQUMAAMoATsDVAHsAasBmgGTAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0B - wgH/AaoBmQGSAf8DUgHtAykBPQwAAwMBBAM2AVcDXQHPA00B7wNZAeUDPgFqAwIBA0wAAxIBGAFgAV0B - WgHMAbsBWwEaAf8BuwFbARkB/wG7AVsBGQH/AbsBWwEZAf8BuwFbARkB/wFjAVwBWgHTAyIBMf8A4QAD - AgEDAzQBUwNRAfEBbwFpAWYB/wG3AasBpAH/AV0BWQFXAf8DOgH7A1EBpAMZASIDBAEFAwkBDAM/AW4B - OAI3AfsB3AHIAb4B/wHnAc4BwwH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B2AHAAbYB - /wIwAS8B/ANAAXEDCgENAwMBBAMYASADUQGiATsBOgE5AfsBXgFXAVQB/wG2AaMBmwH/AXABZwFjAf8D - TgHyAzUBVQMCAQNIAAMSARgBYAFdAVoBzAG7AVsBGgH/AbsBWwEaAf8BuwFbARkB/wG7AVsBGQH/AbsB - WwEZAf8BuwFbARkB/wFmAV0BWwHUAxgBIP8A2QADAwEEAz0BaANRAfEBfwF0AW8B/wHjAcwBwQH/AewB - 2gHQAf8B5AHVAcsB/wGnAZ0BlwH/AVMBUAFPAf8DVwHkA04BmANVAbQDVAHsAXgBcgFuAf8B7QHcAdIB - /wHqAdUBywH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wF1AWsBZwH/A1IB - 7QNWAbUDTgGXA1kB4gFTAU4BTAH/AaQBlAGNAf8B3wHGAbsB/wHnAc0BwgH/AeMByQG+Af8BgAF1AXAB - /wNOAfIDPgFqAwMBBEQAAxIBGAFgAV0BWgHMAboBWwEaAf8BuwFbARoB/wG7AVsBGgH/AbsBWwEaAf8B - uwFbARkB/wG7AVsBGQH/AbsBWwEZAf8BZwFcAVkB1gMlATf/ANUAAyEBLwNZAeMBbwFqAWYB/wHjAcwB - wgH/AecBzQHCAf8B6AHQAcUB/wHtAdwB0gH/Ae0B3QHTAf8B6AHZAc8B/wGEAX4BeQH/AzcB/wFOAUwB - SwH/AbcBqwGlAf8B6gHbAdEB/wHtAd0B0wH/Ae0B3QHTAf8B6wHVAcsB/wHnAc0BwgH/AecBzQHCAf8B - 5wHNAcIB/wHnAc0BwgH/AeUBywHAAf8BswGgAZgB/wFNAUoBSAH/ATcCNgH/AYEBdQFxAf8B4wHJAb8B - /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeMByQG+Af8BcAFnAWMB/wNZAeUDIgExJAAD - IQEwA1IBoAJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJYAVYBswGEAWIBSAHuAboB - WwEaAf8BugFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGgH/AbsBWwEZAf8BuwFbARkB - /wF3AV8BVAHlA1UBrQJWAVQBqwJWAVQBqwJWAVQBqwJUAVMBqQJWAVQBqwJWAVQBqwJWAVQBqwJWAVQB - qwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwNSAaADIQEw/wCNAAMoATwD - UgHtAbcBqwGkAf8B7AHbAdAB/wHpAdEBxgH/AecBzQHCAf8B6AHRAcYB/wHsAdoB0AH/Ae0B3QHTAf8B - 7AHcAdIB/wHeAc8BxgH/AewB3AHSAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B - 0wH/AeoB1QHLAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeYBzAHBAf8B - 2AHAAbYB/wHmAcwBwQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0B - wgH/AbEBngGXAf8DTQHvAykBPSAAAyABLgGCAV0BTAHsAbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkB - WgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWgEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB - /wG6AVsBGgH/AboBWwEaAf8BuwFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARkB/wG7AVsBGQH/AbsB - WwEZAf8BuwFbARkB/wG7AVsBGQH/AbwBWwEZAf8BvwF1ASsB/AHsAaQBQgH/AewBpAFCAf8B7AGkAUIB - /wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B6wGkAUIB/wHrAaQBQgH/AesB - pAFCAf8B6wGkAUIB/wGPAXkBWQHrAyABLf8AiQADEAEVA1sBzQFcAVkBVgH/AeMB1AHLAf8B7QHcAdIB - /wHpAdEBxgH/AecBzQHCAf8B6AHQAcUB/wHsAdsB0QH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B - 3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAdwB0gH/AesB1QHKAf8B5wHNAcIB + XQFbAVoBxwMlATb/AP8AJgADEQEWA08B8wE6AjkB/wE9ATwBOwH/AT0BPAE7Af8BPQE8ATsB/wE6AjkB + /wNOAfQDEQEWeAADEgEYA10BzAG8AVsBGQH/AWICXgHXAxABFf8A/wAiAAM/AW4BRgFDAUIB/wHEAa8B + pgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AcQBrgGmAf8BRgFDAUIB/wNAAXB4AAMSARgDXQHMAbwB + WwEZAf8BvAFbARkB/wFjAV8BWwHYAyUBNwQB/wD/ABoAA1gBtwFXAVIBUAH/Ad4BxQG7Af8B5wHNAcIB + /wHnAc0BwgH/AecBzQHCAf8B3gHFAbsB/wFXAVIBTwH/A1gBugQBdAADEgEYA10BzAG7AVsBGQH/AbwB + WwEZAf8BvAFbARkB/wFjAV8BXgHVAhoBGQEj/wDxAAMDAQQDIgExAykBPgMSARgUAAMSARgDXwHbAXsB + cAFsAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AXoBcAFrAf8DXwHbAxMB + GhQAAxIBFwMpAT4DIgExAwMBBFAAAxIBGANdAcwBuwFbARkB/wG7AVsBGQH/AbsBWwEZAf8BvAFbARkB + /wFiAl0B1AMhAS8EAf8A5QADAgEDAz0BaQNbAeQDUwHvA1sB0AM2AVkDBAEFDAADKAE7A1sB7AGrAZoB + kwH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wGqAZkBkgH/A1gB7QMpAT0M + AAMDAQQDNgFXA10BzwNTAe8DXwHlAz4BagMCAQNMAAMSARgDXQHMAbsBWwEaAf8BuwFbARkB/wG7AVsB + GQH/AbsBWwEZAf8BuwFbARkB/wFfAVwBWwHTAyIBMf8A4QADAgEDAzQBUwNWAfEBbwFpAWYB/wG3AasB + pAH/AV0BWQFXAf8DOgH7A1EBpAMZASIDBAEFAwkBDAM/AW4BOAI3AfsB3AHIAb4B/wHnAc4BwwH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B2AHAAbYB/wItASwB/ANAAXEDCgENAwMBBAMYASAD + UQGiATsBOgE5AfsBXgFXAVQB/wG2AaMBmwH/AXABZwFjAf8DVQHyAzUBVQMCAQNIAAMSARgDXQHMAbsB + WwEaAf8BuwFbARoB/wG7AVsBGQH/AbsBWwEZAf8BuwFbARkB/wG7AVsBGQH/AWICXQHUAxgBIP8A2QAD + AwEEAz0BaANWAfEBfwF0AW8B/wHjAcwBwQH/AewB2gHQAf8B5AHVAcsB/wGnAZ0BlwH/AVMBUAFPAf8D + WwHkA04BmANVAbQDWwHsAXgBcgFuAf8B7QHcAdIB/wHqAdUBywH/AecBzQHCAf8B5wHNAcIB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wF1AWsBZwH/A1gB7QNWAbUDTgGXA14B4gFTAU4BTAH/AaQBlAGNAf8B + 3wHGAbsB/wHnAc0BwgH/AeMByQG+Af8BgAF1AXAB/wNVAfIDPgFqAwMBBEQAAxIBGANdAcwBugFbARoB + /wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGQH/AbsBWwEZAf8BuwFbARkB/wFjAlwB1gMlATf/ + ANUAAyEBLwNcAeMBbwFqAWYB/wHjAcwBwgH/AecBzQHCAf8B6AHQAcUB/wHtAdwB0gH/Ae0B3QHTAf8B + 6AHZAc8B/wGEAX4BeQH/AzcB/wFOAUwBSwH/AbcBqwGlAf8B6gHbAdEB/wHtAd0B0wH/Ae0B3QHTAf8B + 6wHVAcsB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeUBywHAAf8BswGgAZgB/wFNAUoB + SAH/ATcCNgH/AYEBdQFxAf8B4wHJAb8B/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeMB + yQG+Af8BcAFnAWMB/wNfAeUDIgExJAADIQEwA1IBoAJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQB + qwJWAVQBqwJYAVYBswF5AWIBUAHuAboBWwEaAf8BugFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB + /wG7AVsBGgH/AbsBWwEZAf8BuwFbARkB/wFuAV8BXAHlA1UBrQJWAVQBqwJWAVQBqwJWAVQBqwJUAVMB + qQJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQBqwJWAVQB + qwJWAVQBqwNSAaADIQEw/wCNAAMoATwDWAHtAbcBqwGkAf8B7AHbAdAB/wHpAdEBxgH/AecBzQHCAf8B + 6AHRAcYB/wHsAdoB0AH/Ae0B3QHTAf8B7AHcAdIB/wHeAc8BxgH/AewB3AHSAf8B7QHdAdMB/wHtAd0B + 0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/AeoB1QHLAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AeYBzAHBAf8B2AHAAbYB/wHmAcwBwQH/AecBzQHCAf8B5wHNAcIB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AbEBngGXAf8DUwHvAykBPSAAAyABLgF3AV0BVAHsAbkB + WgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWgEaAf8BugFbARoB + /wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BuwFbARoB/wG7AVsBGgH/AbsB + WwEaAf8BuwFbARkB/wG7AVsBGQH/AbsBWwEZAf8BuwFbARkB/wG7AVsBGQH/AbwBWwEZAf8BuQF1ASsB + /AHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewB + pAFCAf8B6wGkAUIB/wHrAaQBQgH/AesBpAFCAf8B6wGkAUIB/wF/AXMBXgHrAyABLf8AiQADEAEVA1sB + zQFcAVkBVgH/AeMB1AHLAf8B7QHcAdIB/wHpAdEBxgH/AecBzQHCAf8B6AHQAcUB/wHsAdsB0QH/Ae0B + 3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB + /wHtAdwB0gH/AesB1QHKAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B3QHFAboB + /wFaAVUBUgH/A10BzgMRARYgAAMzAVABiwFgATkB9gG5AVoBGwH/AbkBWgEaAf8BuQFaARoB/wG5AVoB + GgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BugFaARoB/wG6AVsBGgH/AboBWwEaAf8B + ugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsB + GQH/AbsBWwEZAf8BuwFbARkB/wGpAWcBJAH+Ab4BigFAAf0B7QGkAUIB/wHsAaQBQgH/AewBpAFCAf8B + 7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQB + QgH/AesBpAFCAf8BogF9AUgB9gMzAVD/AI0AAzMBUgJMAUsB+gGmAZsBlQH/Ae0B3QHTAf8B7AHbAdAB + /wHpAdEBxgH/AesB1wHQAf8B7AHaAdMB/wHsAdsB0QH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B + 3QHTAf8B7QHdAdMB/wHtAd0B0wH/AeoB2gHQAf8BxgG5AbEB/wHqAdoB0AH/AeoB1QHKAf8B5wHOAcMB /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B3QHFAboB/wFaAVUBUgH/A10BzgMRARYgAAMzAVAB - lAFgATMB9gG5AVoBGwH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoB - GgH/AbkBWgEaAf8BugFaARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8B - ugFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGQH/AbsBWwEZAf8BuwFbARkB/wGvAWQB - IQH+AccBigFAAf0B7QGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B - 7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AesBpAFCAf8BsgGJAUgB9gMzAVD/ - AI0AAzMBUgJHAUYB+gGmAZsBlQH/Ae0B3QHTAf8B7AHbAdAB/wHpAdEBxgH/AesB1wHQAf8B7AHaAdMB - /wHsAdsB0QH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/AeoB - 2gHQAf8BxgG5AbEB/wHqAdoB0AH/AeoB1QHKAf8B5wHOAcMB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB - /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AaEB - kQGLAf8BOgI5AfsDNQFWJAADMwFRAZ4BWwE2AfcBuAFaARsB/wG5AVoBGwH/AbkBWgEbAf8BuQFaARoB - /wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AboBWgEaAf8BugFaARoB/wG6AVoBGgH/AboB - WwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB - /wG7AVsBGQH/AbsBWwEZAf8BtAFqASUB/gHSAZkBQAH9Ae0BpAFCAf8B7QGkAUIB/wHsAaQBQgH/AewB - pAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB - /wHsAaQBQgH/AbIBiQFIAfYDMwFR/wCNAAMDAQQDUAGdAVIBTwFNAf8B5wHXAc0B/wHtAd0B0wH/AfAB - 5AHfAf8B9gHyAfcB/wH1AfEB9QH/Ae0B2wHVAf8B7AHaAdAB/wHtAd0B0wH/AdgBygHBAf8BxgG5AbEB - /wHoAdYBzAH/Ad8BywHBAf8BzwG7AbEB/wFBAj8B/wHPAboBsQH/Ad8BygHAAf8BpAGWAY8B/wGPAYIB - fAH/AeYBzAHBAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - 5wHNAcIB/wHhAcgBvgH/AVABTAFKAf8DUQGiAwMBBCQAAzMBUQGeAVsBNgH3AbgBWgEbAf8BuAFaARsB - /wG4AVoBGwH/AbkBWgEbAf8BuQFaARsB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkB - WgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB - /wG6AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGgH/Ab0BcwErAfwB7AGjAUEB/wHtAaQBQgH/Ae0B - pAFCAf8B7QGkAUIB/wHtAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB - /wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wGyAYkBSAH2AzMBUf8AkQADFwEfA1gB3wF/AXkBdAH/AewB - 3AHSAf8B7QHdAdQB/wH0Au0B/wHwAeQB4gH/AecBzQHCAf8B5QHOAcMB/wG7Aa8BqAH/AUYBRAFDAf8B - TwFLAUkB/wHQAbcBrAH/AdABtwGsAf8BxAGtAaMB/wE4AjcB/wHEAa0BowH/AcMBrAGiAf8BTwFLAUkB - /wFkAVwBWQH/AeIByAG9Af8B5gHMAcEB/wHmAcwBwQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5gHMAcEB/wF+AXQBbgH/A1kB4gMYASAoAAMzAVEBngFbATYB9wG4AVoBGwH/AbgBWgEbAf8B - uAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuQFaARsB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoB - GgH/AbkBWgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWgEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8B - ugFbARoB/wG6AVsBGgH/AboBWwEaAf8BuwFbARoB/wHKAYkBOAH7Ae0BpAFCAf8B7QGkAUIB/wHtAaQB - QgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B - 7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8BsgGJAUgB9gMzAVH/AJEAAwMBBANNAZMDNgH/AdoBygHBAf8B - 7QHdAdMB/wHuAd8B1gH/Ae0B3QHUAf8B5QHOAcMB/wGWAYgBggH/ATgCNwH/AWwBYwFfAf8BtgGhAZgB - /wHQAbcBrAH/AdABtwGsAf8BzAG0AakB/wGcAYsBhAH/AcwBtAGpAf8BtgGiAZgB/wFUAU8BTAH/AaoB - lwGPAf8BzwG2AawB/wGUAYUBgAH/Aa8BngGWAf8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB - /wHZAcABtgH/ATcCNgH/A04BlgMDAQQoAAMzAVEBngFbATYB9wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB - /wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbkBWgEbAf8BuQFaARoB/wG5AVoBGgH/AbkB - WgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BugFaARoB/wG6AVoBGgH/AboBWwEaAf8BugFbARoB - /wG6AVsBGgH/AboBWwEaAf8BtAFmASsB/AHgAZYBSAH+Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0B - pAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/AewBpAFCAf8B7AGkAUIB - /wHsAaQBQgH/AewBpAFCAf8BsgGJAUgB9gMzAVH/AJEAAwkBDANWAbIBSQFGAUUB/wHmAc8BxAH/Ae0B - 3AHSAf8B7QHdAdMB/wHtAd0B0wH/AbwBsAGoAf8COAE3Af8BewFwAWsB/wHOAbUBqgH/AdABtwGsAf8B - 0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/Ac8BtgGrAf8BzAG0AakB/wHPAbYB - qwH/AYQBdwFyAf8DNQH/AZMBhQF/Af8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHmAcwB - wQH/AVABSwFKAf8DVQG0AwkBDCgAAzMBUQGdAVsBNgH3AbcBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbgB - WgEbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG5AVoBGwH/AbkBWgEaAf8BuQFaARoB - /wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AboBWgEaAf8BugFaARoB/wG6AVsBGgH/AboB - WwEaAf8BugFbARoB/wHBAXcBMQH7Ae4BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB - /wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHsAaQBQgH/AewB - pAFCAf8B7AGkAUIB/wGyAYkBSAH2AzMBUf8AiQADEwEaAykBPQNAAXADVgHrAa8BnwGYAf8B5wHNAcIB - /wHpAdEBxgH/AewB2wHQAf8B1gHIAb8B/wFGAUQBQwH/AWsBYgFeAf8BzgG1AaoB/wHQAbcBrAH/Ac4B - tgGrAf8BogGRAYkB/wFoAWABXAH/AUEBPwE+Af8DNQH/AUEBPgE9Af8BaAFfAVsB/wGiAZABiAH/Ac0B - tAGqAf8BlAGFAX4B/wGEAXcBcQH/Ac8BtgGsAf8B4wHJAb4B/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB - /wHnAc0BwgH/AbQBogGaAf8DVgHrAz8BbgMoATwDEwEZIAADMwFRAZ0BWwE2AfcBtwFaARsB/wG3AVoB - GwH/AbgBWgEbAf8BuAFaARsB/wHDAXIBPAH/AcsBhQFWAf8BvwFpATAB/wG4AVoBGwH/AbgBWgEbAf8B - uQFaARsB/wG5AVoBGwH/Ab0BZAEoAf8BywGFAVYB/wHFAXYBQQH/AbkBWgEaAf8BuQFaARoB/wG5AVoB - GgH/AboBWgEaAf8BugFbARoB/wG+AVoBKwH9AdEBlwFAAf0B7gGkAUIB/wHuAaQBQgH/Ad4BlAE6Af8B - 7QGjAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/AesBogFBAf8B3QGTAToB/wHtAaQB - QgH/Ae0BpAFCAf8B7AGkAUIB/wHsAaQBQgH/AbIBiQFIAfYDMwFR/wB9AAMRARYDQAFwA1gBugNcAdsD - UgHtAzAB/AF2AXABbQH/AekB2QHPAf8B6QHRAccB/wHnAc0BwgH/AegB0AHFAf8BhQF9AXcB/wE+ATwB - OwH/AbEBnQGUAf8B0AG3AawB/wHOAbYBqwH/AYIBdQFwAf8BPQI8Af8BSwFgAWcB/wFyAacBugH/AX0B - uwHSAf8BcgGoAbwB/wFMAWEBaAH/AT0CPAH/AYEBdAFvAf8BzQG1AaoB/wHPAbYBqwH/AcABqQGfAf8B - hQF4AXMB/wGgAZABiQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeUBywHAAf8BeQFvAWoB/wI4ATcB - +wNUAewDXAHbA1gBuANAAW8DEQEWFAADMwFRAZ0BWwE2AfcBtwFaARsB/wG3AVoBGwH/AbcBWgEbAf8B - twFaARsB/wHOAYwBYQH/AfsB9QHxAf8B3QGxAZMB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoB - GwH/AdYBoAF8Af8B+wH1AfEB/wHXAaEBfgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8B - uQFaARoB/wG+AWcBMgH9Ad4BkwFHAf4B7gGkAUIB/wHZAY8BOAH/AZYBTAEXAf8BxQF6AS4B/wHsAaMB - QQH/Ae0BpAFCAf8B7QGkAUIB/wHpAaABQAH/AbkBbQEnAf8BmAFKARUB/wHeAZQBOgH/Ae0BpAFCAf8B - 7QGkAUIB/wHtAaQBQgH/AbMBiQFIAfYDMwFR/wB5AAMmATgDTAHzAUYBQwFCAf8BVwFSAU8B/wF5AW8B - agH/AaoBmQGSAf8B2gHGAb0B/wHtAdwB0gH/Ae0B3QHTAf8B7AHbAdEB/wHoAdABxgH/AdYBvgG0Af8B - VwFRAU8B/wFkAVwBWAH/AdABtwGsAf8B0AG3AawB/wGjAZEBiQH/AT0CPAH/AVoBewGIAf8BiwHWAfAB - /wGPAd0B+QH/AY8B3QH5Af8BjwHdAfkB/wGLAdYB8QH/AVsBfAGJAf8BPQI8Af8BogGQAYkB/wHMAbQB - qQH/AU0BSQFHAf8BRwFEAUIB/wGLAX8BegH/AeYBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - 5wHNAcIB/wHdAcQBugH/Aa8BnQGWAf8BfgFzAW8B/wFZAVQBUQH/AUcBRAFDAf8DTAHzAycBORAAAzMB - UQGdAVsBNgH3AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AbcBWgEbAf8BuAFeASAB/wH5AfEB7AH/AfgB - 7gHnAf8ByQGBAVAB/wHJAYEBUAH/AckBgQFQAf8ByQGBAVAB/wH0AeUB3AH/AfsB9gHzAf8BxgF4AUQB - /wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BvwF1ATAB+wHuAaQBQgH/Ae0B - owFCAf8BvAFyASoB/wGNAUIBEgH/AY4BQgESAf8BvwF0ASsB/wHoAZ4BPwH/AdsBkQE5Af8BowFVARsB - /wGOAT8BEAH/AZgBSgEWAf8BzAGCATEB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wGzAYkBSAH2AzMB - Uf8AeQADTgGUAToCOQH/AcIBrQGkAf8B3gHFAbsB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHqAdQB - ygH/Ae0B3QHTAf8B7QHdAdMB/wHsAdsB0QH/AcUBswGqAf8BQwFAAT8B/wGgAY4BhwH/AdABtwGsAf8B - 0AG3AawB/wFqAWEBXQH/AUoBXgFlAf8BiwHWAfAB/wGPAd0B+QH/AY8B3QH5Af8BjwHdAfkB/wGPAd0B - +QH/AY8B3QH5Af8BiwHWAfEB/wFLAWABaAH/AWgBYAFcAf8BzwG2AasB/wGoAZYBjQH/AbgBowGZAf8B - 3QHJAb8B/wHqAdUBygH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0B - wgH/AecBzQHCAf8B4AHHAb0B/wHGAbEBpwH/ATsCOQH/A04BlhAAAzMBUQGbAVsBNgH3AbcBWgEbAf8B - twFaARsB/wG3AVoBGwH/AbcBWgEbAf8BtwFbARwB/wHmAcYBsRn/Ae8B2QHLAf8BvgFnAS0B/wG4AVoB - GwH/AbkBWgEbAf8BuQFaARoB/wG5AVoBGgH/AawBYgEhAf4BzgGFATYB/AHuAaQBQgH/Ae4BpAFCAf8B - 6QGfAT8B/wHHAX0BLwH/AZMBRwEVAf8BjQFBARIB/wGnAVsBHgH/AZkBTAEWAf8BjgFAAREB/wGvAWEB - IQH/AdsBkQE5Af8B7AGjAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wGzAYkBSAH2AzMBUf8AeQAD - UQGiAT0BPAE7Af8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - 6gHUAckB/wHtAd0B0wH/Ae0B3QHTAf8BvQGxAakB/wE3AjYB/wHEAa0BowH/AdABtwGsAf8B0AG3AawB - /wFDAUABPwH/AXABpQG3Af8BjwHdAfkB/wGPAd0B+QH/AWwBnAGtAf8BOgFBAUQB/wFqAZoBqwH/AY8B - 3QH5Af8BjwHdAfkB/wFyAacBugH/AUEBPwE+Af8B0AG3AawB/wHMAbMBqQH/AcQBrQGjAf8BzwG7AbEB - /wHqAdoB0AH/AesB1QHKAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5wHNAcIB/wHnAc0BwgH/AT0BPAE7Af8DUQGhEAADMwFRAZsBWwE3AfcBtgFaARwB/wG3AVoB - GwH/AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AdQBnAF2Af8B/gH9AfwB/wH2AeoB4wH/AeMBwAGoAf8B - 5AHAAacB/wHyAeAB1AX/AeEBuAGcAf8BuAFbARwB/wG4AVoBGwH/AbgBWgEbAf8BuQFaARsB/wG5AVoB - GwH/AawBbgEtAfoB7wGjAUIB/wHvAaMBQgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/Ac0BgwEyAf8B - kAFEARMB/wGMAUABEQH/AY0BPwEQAf8BuAFsASYB/wHsAaIBQQH/Ae4BpAFCAf8B7QGkAUIB/wHtAaQB - QgH/Ae0BpAFCAf8B7QGkAUIB/wGzAYkBSAH2AzMBUf8AeQADUQGiAT0BPAE7Af8B5gHMAcEB/wHnAc0B - wgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHqAdQBygH/Ae0B3AHSAf8B - uAGsAaUB/wMzAf8BzgG1AaoB/wHQAbcBrAH/AdABtwGsAf8BOAI3Af8BfAG5AdAB/wGPAd0B+QH/AY8B - 3QH5Af8BPQFGAUkB/wMzAf8BOwFDAUUB/wGPAd0B+QH/AY8B3QH5Af8BfAG7AdEB/wE2AjUB/wHQAbcB - rAH/AZwBiwGDAf8BOAI3Af8BQQFAAT8B/wHHAboBsgH/Ae0B3AHSAf8B6gHVAcoB/wHnAc0BwgH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AaEBkQGLAf8BOgI5AfsDNQFWJAADMwFRAZIBWwE8AfcBuAFaARsB + /wG5AVoBGwH/AbkBWgEbAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AboB + WgEaAf8BugFaARoB/wG6AVoBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB + /wG7AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGQH/AbsBWwEZAf8BrgFtASgB/gHJAZkBQAH9Ae0B + pAFCAf8B7QGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB + /wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AaIBfQFIAfYDMwFR/wCNAAMDAQQDUAGdAVIB + TwFNAf8B5wHXAc0B/wHtAd0B0wH/AfAB5AHfAf8B9gHyAfcB/wH1AfEB9QH/Ae0B2wHVAf8B7AHaAdAB + /wHtAd0B0wH/AdgBygHBAf8BxgG5AbEB/wHoAdYBzAH/Ad8BywHBAf8BzwG7AbEB/wFBAj8B/wHPAboB + sQH/Ad8BygHAAf8BpAGWAY8B/wGPAYIBfAH/AeYBzAHBAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHhAcgBvgH/AVABTAFKAf8DUQGiAwMBBCQAAzMB + UQGSAVsBPAH3AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbkBWgEbAf8BuQFaARsB/wG5AVoBGgH/AbkB + WgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWwEaAf8BugFbARoB + /wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AbsBWwEaAf8BuwFbARoB/wG7AVsBGgH/AbcB + cwErAfwB7AGjAUEB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/AewBpAFCAf8B7AGkAUIB + /wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wGiAX0BSAH2AzMB + Uf8AkQADFwEfA10B3wF/AXkBdAH/AewB3AHSAf8B7QHdAdQB/wH0Au0B/wHwAeQB4gH/AecBzQHCAf8B + 5QHOAcMB/wG7Aa8BqAH/AUYBRAFDAf8BTwFLAUkB/wHQAbcBrAH/AdABtwGsAf8BxAGtAaMB/wE4AjcB + /wHEAa0BowH/AcMBrAGiAf8BTwFLAUkB/wFkAVwBWQH/AeIByAG9Af8B5gHMAcEB/wHmAcwBwQH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5gHMAcEB/wF+AXQBbgH/A14B4gMYASAoAAMzAVEB + kgFbATwB9wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuQFaARsB/wG5AVoB + GgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG6AVoBGgH/AboBWgEaAf8B + ugFbARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BuwFbARoB/wHBAYYB + OAH7Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B + 7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8BogF9AUgB9gMzAVH/ + AJEAAwMBBANNAZMDNgH/AdoBygHBAf8B7QHdAdMB/wHuAd8B1gH/Ae0B3QHUAf8B5QHOAcMB/wGWAYgB + ggH/ATgCNwH/AWwBYwFfAf8BtgGhAZgB/wHQAbcBrAH/AdABtwGsAf8BzAG0AakB/wGcAYsBhAH/AcwB + tAGpAf8BtgGiAZgB/wFUAU8BTAH/AaoBlwGPAf8BzwG2AawB/wGUAYUBgAH/Aa8BngGWAf8B5gHMAcEB + /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHZAcABtgH/ATcCNgH/A04BlgMDAQQoAAMzAVEBkgFbATwB + 9wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbkB + WgEbAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BugFaARoB + /wG6AVoBGgH/AboBWwEaAf8BugFbARoB/wG6AVsBGgH/AboBWwEaAf8BrgFmASsB/AHaAZABSwH+Ae0B + pAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB + /wHtAaQBQgH/AewBpAFCAf8B7AGkAUIB/wHsAaQBQgH/AewBpAFCAf8BogF9AUgB9gMzAVH/AJEAAwkB + DANWAbIBSQFGAUUB/wHmAc8BxAH/Ae0B3AHSAf8B7QHdAdMB/wHtAd0B0wH/AbwBsAGoAf8COAE3Af8B + ewFwAWsB/wHOAbUBqgH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHQAbcB + rAH/Ac8BtgGrAf8BzAG0AakB/wHPAbYBqwH/AYQBdwFyAf8DNQH/AZMBhQF/Af8B5gHMAcEB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wHmAcwBwQH/AVABSwFKAf8DVQG0AwkBDCgAAzMBUQGRAVsBPAH3AbcB + WgEbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB + /wG5AVoBGwH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AboB + WgEaAf8BugFaARoB/wG6AVsBGgH/AboBWwEaAf8BugFbARoB/wG2AXEBMQH7Ae4BpAFCAf8B7QGkAUIB + /wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0B + pAFCAf8B7QGkAUIB/wHsAaQBQgH/AewBpAFCAf8B7AGkAUIB/wGiAX0BSAH2AzMBUf8AiQADEwEaAykB + PQNAAXADWgHrAa8BnwGYAf8B5wHNAcIB/wHpAdEBxgH/AewB2wHQAf8B1gHIAb8B/wFGAUQBQwH/AWsB + YgFeAf8BzgG1AaoB/wHQAbcBrAH/Ac4BtgGrAf8BogGRAYkB/wFoAWABXAH/AUEBPwE+Af8DNQH/AUEB + PgE9Af8BaAFfAVsB/wGiAZABiAH/Ac0BtAGqAf8BlAGFAX4B/wGEAXcBcQH/Ac8BtgGsAf8B4wHJAb4B + /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AbQBogGaAf8DWgHrAz8BbgMoATwDEwEZIAAD + MwFRAZEBWwE8AfcBtwFaARsB/wG3AVoBGwH/AbgBWgEbAf8BuAFaARsB/wHDAXIBPAH/AcsBhQFWAf8B + vwFpATAB/wG4AVoBGwH/AbgBWgEbAf8BuQFaARsB/wG5AVoBGwH/Ab0BZAEoAf8BywGFAVYB/wHFAXYB + QQH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AboBWgEaAf8BugFbARoB/wG+AVcBMQH9AcgBlwFAAf0B + 7gGkAUIB/wHuAaQBQgH/Ad4BlAE6Af8B7QGjAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQB + QgH/AesBogFBAf8B3QGTAToB/wHtAaQBQgH/Ae0BpAFCAf8B7AGkAUIB/wHsAaQBQgH/AaIBfQFIAfYD + MwFR/wB9AAMRARYDQAFwA1gBugNfAdsDWAHtAy0B/AF2AXABbQH/AekB2QHPAf8B6QHRAccB/wHnAc0B + wgH/AegB0AHFAf8BhQF9AXcB/wE+ATwBOwH/AbEBnQGUAf8B0AG3AawB/wHOAbYBqwH/AYIBdQFwAf8B + PQI8Af8BSwFgAWcB/wFyAacBugH/AX0BuwHSAf8BcgGoAbwB/wFMAWEBaAH/AT0CPAH/AYEBdAFvAf8B + zQG1AaoB/wHPAbYBqwH/AcABqQGfAf8BhQF4AXMB/wGgAZABiQH/AecBzQHCAf8B5wHNAcIB/wHnAc0B + wgH/AeUBywHAAf8BeQFvAWoB/wI4ATcB+wNbAewDXwHbA1gBuANAAW8DEQEWFAADMwFRAZEBWwE8AfcB + twFaARsB/wG3AVoBGwH/AbcBWgEbAf8BtwFaARsB/wHOAYwBYQH/AfsB9QHxAf8B3QGxAZMB/wG4AVoB + GwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AdYBoAF8Af8B+wH1AfEB/wHXAaEBfgH/AbkBWgEaAf8B + uQFaARoB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG+AWQBOAH9AdgBjQFKAf4B7gGkAUIB/wHZAY8B + OAH/AZYBTAEXAf8BxQF6AS4B/wHsAaMBQQH/Ae0BpAFCAf8B7QGkAUIB/wHpAaABQAH/AbkBbQEnAf8B + mAFKARUB/wHeAZQBOgH/Ae0BpAFCAf8B7QGkAUIB/wHtAaQBQgH/AaMBfQFIAfYDMwFR/wB5AAMmATgD + TwHzAUYBQwFCAf8BVwFSAU8B/wF5AW8BagH/AaoBmQGSAf8B2gHGAb0B/wHtAdwB0gH/Ae0B3QHTAf8B + 7AHbAdEB/wHoAdABxgH/AdYBvgG0Af8BVwFRAU8B/wFkAVwBWAH/AdABtwGsAf8B0AG3AawB/wGjAZEB + iQH/AT0CPAH/AVoBewGIAf8BiwHWAfAB/wGPAd0B+QH/AY8B3QH5Af8BjwHdAfkB/wGLAdYB8QH/AVsB + fAGJAf8BPQI8Af8BogGQAYkB/wHMAbQBqQH/AU0BSQFHAf8BRwFEAUIB/wGLAX8BegH/AeYBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHdAcQBugH/Aa8BnQGWAf8BfgFzAW8B/wFZAVQB + UQH/AUcBRAFDAf8DTwHzAycBORAAAzMBUQGRAVsBPAH3AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AbcB + WgEbAf8BuAFeASAB/wH5AfEB7AH/AfgB7gHnAf8ByQGBAVAB/wHJAYEBUAH/AckBgQFQAf8ByQGBAVAB + /wH0AeUB3AH/AfsB9gHzAf8BxgF4AUQB/wG5AVoBGgH/AbkBWgEaAf8BuQFaARoB/wG5AVoBGgH/AbkB + WgEaAf8BswFvATAB+wHuAaQBQgH/Ae0BowFCAf8BvAFyASoB/wGNAUIBEgH/AY4BQgESAf8BvwF0ASsB + /wHoAZ4BPwH/AdsBkQE5Af8BowFVARsB/wGOAT8BEAH/AZgBSgEWAf8BzAGCATEB/wHtAaQBQgH/Ae0B + pAFCAf8B7QGkAUIB/wGjAX0BSAH2AzMBUf8AeQADTgGUAToCOQH/AcIBrQGkAf8B3gHFAbsB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wHqAdQBygH/Ae0B3QHTAf8B7QHdAdMB/wHsAdsB0QH/AcUBswGqAf8B + QwFAAT8B/wGgAY4BhwH/AdABtwGsAf8B0AG3AawB/wFqAWEBXQH/AUoBXgFlAf8BiwHWAfAB/wGPAd0B + +QH/AY8B3QH5Af8BjwHdAfkB/wGPAd0B+QH/AY8B3QH5Af8BiwHWAfEB/wFLAWABaAH/AWgBYAFcAf8B + zwG2AasB/wGoAZYBjQH/AbgBowGZAf8B3QHJAb8B/wHqAdUBygH/AecBzQHCAf8B5wHNAcIB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B4AHHAb0B/wHGAbEBpwH/ATsCOQH/A04B + lhAAAzMBUQGPAVsBPAH3AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AbcBWgEbAf8BtwFbARwB/wHmAcYB + sRn/Ae8B2QHLAf8BvgFnAS0B/wG4AVoBGwH/AbkBWgEbAf8BuQFaARoB/wG5AVoBGgH/AaYBZQEkAf4B + yAF+ATMB/AHuAaQBQgH/Ae4BpAFCAf8B6QGfAT8B/wHHAX0BLwH/AZMBRwEVAf8BjQFBARIB/wGnAVsB + HgH/AZkBTAEWAf8BjgFAAREB/wGvAWEBIQH/AdsBkQE5Af8B7AGjAUIB/wHtAaQBQgH/Ae0BpAFCAf8B + 7QGkAUIB/wGjAX0BSAH2AzMBUf8AeQADUQGiAT0BPAE7Af8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B6gHUAckB/wHtAd0B0wH/Ae0B3QHTAf8BvQGxAakB/wE3AjYB + /wHEAa0BowH/AdABtwGsAf8B0AG3AawB/wFDAUABPwH/AXABpQG3Af8BjwHdAfkB/wGPAd0B+QH/AWwB + nAGtAf8BOgFBAUQB/wFqAZoBqwH/AY8B3QH5Af8BjwHdAfkB/wFyAacBugH/AUEBPwE+Af8B0AG3AawB + /wHMAbMBqQH/AcQBrQGjAf8BzwG7AbEB/wHqAdoB0AH/AesB1QHKAf8B5wHNAcIB/wHnAc0BwgH/AecB zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AT0BPAE7Af8DUQGhEAAD - MwFRAZsBWwE3AfcBtgFaARwB/wG2AVoBHAH/AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AcUBegFHAf8B - +QHyAe0B/wHxAd4B0gH/Ab0BaAEvAf8BugFgASMB/wHoAckBtAX/AcwBiAFbAf8BuAFaARsB/wG4AVoB - GwH/AbgBWgEbAf8BuAFaARsB/wGsAWIBIgH+AcoBigE5AfsB7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B - 7wGkAUIB/wHuAaQBQgH/Ac4BgwEyAf8BkQFFARMB/wGMAUABEQH/AY4BQAERAf8BxQF5AS0B/wHtAaMB - QgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wGzAYkBSAH2AzMBUf8AeQAD + MwFRAY8BWwE9AfcBtgFaARwB/wG3AVoBGwH/AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AdQBnAF2Af8B + /gH9AfwB/wH2AeoB4wH/AeMBwAGoAf8B5AHAAacB/wHyAeAB1AX/AeEBuAGcAf8BuAFbARwB/wG4AVoB + GwH/AbgBWgEbAf8BuQFaARsB/wG5AVoBGwH/AaYBbgEwAfoB7wGjAUIB/wHvAaMBQgH/Ae4BpAFCAf8B + 7gGkAUIB/wHuAaQBQgH/Ac0BgwEyAf8BkAFEARMB/wGMAUABEQH/AY0BPwEQAf8BuAFsASYB/wHsAaIB + QQH/Ae4BpAFCAf8B7QGkAUIB/wHtAaQBQgH/Ae0BpAFCAf8B7QGkAUIB/wGjAX0BSAH2AzMBUf8AeQAD UQGiAT0BPAE7Af8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - 5wHNAcIB/wHnAc0BwgH/AeoB1AHKAf8BvQGxAaoB/wI3ATYB/wHDAawBogH/AdABtwGsAf8B0AG3AawB - /wFDAUEBQAH/AW8BowG2Af8BjwHdAfkB/wGPAd0B+QH/AW4BoAGxAf8BPgFIAUsB/wFtAZ4BrwH/AY8B - 3QH5Af8BjwHdAfkB/wFxAaYBuAH/AUIBQAE+Af8B0AG3AawB/wHMAbQBqQH/AcQBrQGjAf8BzwG7AbEB - /wHqAdoB0AH/Ae0B3QHTAf8B7QHdAdMB/wHrAdUBygH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5wHNAcIB/wHnAc0BwgH/AT0BPAE7Af8DUQGhEAADMwFRAZsBWwE3AfcBtgFaARwB/wG2AVoB - HAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBGwH/AbgBXQEfAf8B8QHfAdIB/wH6AfMB7wH/AccBfwFOAf8B - vgFpATAB/wH2AesB5AH/AfsB9QHyAf8BugFfASEB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoB - GwH/Ab4BYQEwAf0B3wGSAUcB/gHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/AekBnQE/Af8B - lwFLARYB/wGMAUABEQH/AawBYAEgAf8BkQFDARIB/wGVAUYBFAH/AdYBiwE2Af8B7gGkAUIB/wHuAaQB - QgH/Ae4BpAFCAf8B7gGkAUIB/wHtAaQBQgH/AbMBiQFIAfYDMwFR/wB5AANNAZIBOgI5Af8BwgGtAaQB - /wHdAcUBugH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8BxgG0AasB/wFEAUIBQQH/AZ4BjQGFAf8B0AG3AawB/wHQAbcBrAH/AWsBYgFeAf8BSQFcAWQB - /wGLAdUB7wH/AY8B3QH5Af8BjwHdAfkB/wGPAd0B+QH/AY8B3QH5Af8BjwHdAfkB/wGLAdUB8AH/AUoB - XgFlAf8BaQFhAV0B/wHPAbYBqwH/AbYBoQGYAf8BwgGrAaEB/wHgAcwBwQH/Ae0B3QHTAf8B7QHdAdMB - /wHtAd0B0wH/Ae0B3QHTAf8B6gHVAcoB/wHnAc4BwwH/AecBzQHCAf8B5wHNAcIB/wHbAcMBuQH/AcEB - rAGkAf8BOgI5Af8DTgGVEAADMwFRAZsBWwE3AfcBtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB - /wG2AVoBHAH/AbYBWgEbAf8B1gGgAXwF/wHXAaMBgAH/Ac0BjAFfA/8B/gH/Ad0BsAGTAf8BtwFaARsB - /wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AcIBegErAfwB7gGiAUEB/wHvAaMBQgH/Ae8B - owFCAf8B7wGjAUIB/wHvAaMBQgH/AdEBhQEzAf8BmwFQARkB/wG5AW0BKAH/AesBoAFBAf8BuAFsASYB - /wGOAT8BEAH/AagBWwEeAf8B7AGhAUEB/wHuAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/AbMB - iQFIAfYDMwFR/wB5AAMjATMDUAHuAUUBQwFBAf8BVgFRAU8B/wF4AW4BagH/AakBmAGRAf8B2AHAAbYB - /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AdcBvwG1Af8BWAFSAVAB/wFiAVsBVwH/Ac8B - twGsAf8B0AG3AawB/wGkAZIBigH/AT4CPAH/AVkBeAGEAf8BigHVAe8B/wGPAd0B+QH/AY8B3QH5Af8B - jwHdAfkB/wGLAdUB8AH/AVkBegGGAf8BPQI8Af8BowGRAYoB/wHNAbQBqQH/AVYBUQFOAf8BTgFKAUgB - /wGoAZ0BlgH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B7QHcAdIB/wHXAcMBugH/AaUB - lQGOAf8BdQFrAWcB/wFVAVABTgH/AUQBQgFBAf8CUQFQAfEDJQE2EAADMwFRAZsBWwE3AfcBtQFaARwB - /wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BvAFlASsB/wH8AfgB9gH/Ae4B - 2AHIAf8B6QHNAboB/wH9AfoB+AH/Ab8BbQE1Af8BtwFaARsB/wG3AVoBGwH/AbcBWgEbAf8BuAFaARsB - /wG6AVwBHAH/AcoBfgEwAfwB8AGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8B - owFCAf8B4wGXATwB/wHrAZ8BQAH/Ae8BowFCAf8B6QGeAT8B/wGlAVcBHAH/AY8BQAERAf8BxAF4ASwB - /wHuAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/AbQBiQFIAfYDMwFR/wB9AAMMARADPAFmA1YB - sANbAdkDUwHqAkQBQwH6AXIBaQFlAf8B5AHKAb8B/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wGFAXkB - dQH/AT4BPAE7Af8BrwGbAZIB/wHQAbcBrAH/Ac8BtgGrAf8BhQF4AXIB/wE+AT0BPAH/AUkBXAFjAf8B - bwGiAbUB/wF7AbkBzwH/AW8BowG1Af8BSgFdAWQB/wE+AjwB/wGEAXcBcQH/AcwBtAGpAf8BzgG2AasB - /wGtAZoBkQH/AWcBYAFdAf8BoAGWAZEB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHqAdoB0AH/AXMB - bQFqAf8BNwI2AfsDVgHrA10B2gNVAbQDPQFpAw4BEhQAAzMBUQGbAVoBNwH3AbUBWgEcAf8BtQFaARwB - /wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8B6AHJAbUB/wH+Av0B/wH+Af0B - /AH/Ae4B1wHIAf8BuAFdAR8B/wG3AVoBGwH/AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AbABaQEmAf4B - 2QGfAUAB/QHwAaMBQgH/AfABowFCAf8B7wGjAUIB/wG6AW4BKQH/AaYBWwEfAf8BpwFbAR8B/wGnAVsB - HwH/AacBWwEfAf8BpQFYAR0B/wGnAVkBHQH/AaABUgEZAf8BjgE/ARAB/wGQAUEBEQH/AagBWwEdAf8B - zwGEATIB/wHuAaQBQgH/Ae4BpAFCAf8BtAGJAUgB9gMzAVH/AIkAAw8BFAMlATcDPQFpA1MB6QGtAZwB - lAH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AdMBvAGyAf8BSAFFAUQB/wFoAWABXAH/Ac4BtQGqAf8B - 0AG3AawB/wHPAbYBqwH/AaUBkwGLAf8BawFiAV4B/wFEAUIBQAH/AjkBOAH/AUQBQQFAAf8BawFiAV4B - /wGkAZIBigH/Ac0BtAGqAf8BjQF/AXgB/wGAAXMBbgH/Ac4BtwGtAf8B6AHWAcwB/wHtAd0B0wH/Ae0B - 3QHTAf8B7QHdAdMB/wHtAd0B0wH/AbQBqQGiAf8DVgHrAz8BbQMnAToDEQEWIAADMwFRAZsBWgE3AfcB - tQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wHQAZQB - bAH/Af4B/QH8Av8C/gH/AdsBrQGOAf8BtwFbARwB/wG3AVoBGwH/AbcBWgEbAf8BtwFaARsB/wG3AVoB - GwH/AbEBfQE4AfoB8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wGmAVsBHwH/AYsBQAERAf8B - iwFAAREB/wGLAUABEQH/AYwBQAERAf8BjQFAAREB/wGPAT8BEAH/AY0BPwEQAf8BjgE/ARAB/wGOAT8B - EAH/AY8BPwEQAf8BxAF4ASwB/wHuAaQBQgH/Ae4BpAFCAf8BtAGJAUgB9gMzAVH/AJEAAwgBCgNVAa8B - SQFGAUQB/wHlAcsBwAH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AbsBpwGfAf8BOQI4Af8BdAFqAWUB - /wHOAbUBqgH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/AdAB - twGsAf8B0AG3AawB/wHPAbYBqwH/AYUBeAFzAf8DNQH/AZIBhgGBAf8B7AHbAdEB/wHtAd0B0wH/Ae0B - 3QHTAf8B7QHdAdMB/wHrAdsB0QH/AUsBSQFIAf8DVgGzAwkBDCgAAzMBUQGbAVoBNwH3AbUBWQEcAf8B - tQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BwgF1AUIB/wH1AegB - 4AH/AfoB9AHvAf8BygGHAVoB/wG2AVoBHAH/AbYBWgEbAf8BtwFaARsB/wG3AVoBGwH/AasBYgEjAf4B - 0AGXAUYB+wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHvAaMB - QgH/Ae8BowFCAf8B7wGjAUIB/wGNAUABEQH/AaYBWAEcAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B - 7wGjAUIB/wHvAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wG0AYkBSAH2AzMBUf8AkQADAwEEA04BlAM2Af8B - 1gG+AbQB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHkAcoBvwH/AZsBjAGFAf8BOgI5Af8BaAFgAVwB - /wGvAZsBkgH/Ac8BtgGsAf8B0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/AdAB - twGsAf8B0AG3AawB/wHQAbkBrgH/AZkBjAGGAf8BsgGgAZgB/wHoAdABxQH/AewB2wHRAf8B8QHlAeEB - /wHtAd0B1AH/Ad0BzgHFAf8DNwH/A04BlwMDAQQoAAMzAVEBmwFaATcB9wG1AVkBHAH/AbUBWQEcAf8B - tQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG1AVoBHAH/AbcBXQEhAf8BwQFzAT4B/wHDAXYB - QgH/AbgBXwEjAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtwFaARsB/wGxAWQBKAH7AfABowFCAf8B + 5wHNAcIB/wHqAdQBygH/Ae0B3AHSAf8BuAGsAaUB/wMzAf8BzgG1AaoB/wHQAbcBrAH/AdABtwGsAf8B + OAI3Af8BfAG5AdAB/wGPAd0B+QH/AY8B3QH5Af8BPQFGAUkB/wMzAf8BOwFDAUUB/wGPAd0B+QH/AY8B + 3QH5Af8BfAG7AdEB/wE2AjUB/wHQAbcBrAH/AZwBiwGDAf8BOAI3Af8BQQFAAT8B/wHHAboBsgH/Ae0B + 3AHSAf8B6gHVAcoB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB + /wHnAc0BwgH/AT0BPAE7Af8DUQGhEAADMwFRAY8BWwE9AfcBtgFaARwB/wG2AVoBHAH/AbcBWgEbAf8B + twFaARsB/wG3AVoBGwH/AcUBegFHAf8B+QHyAe0B/wHxAd4B0gH/Ab0BaAEvAf8BugFgASMB/wHoAckB + tAX/AcwBiAFbAf8BuAFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wGmAWUBJQH+AcEBhwE5AfsB + 7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGkAUIB/wHuAaQBQgH/Ac4BgwEyAf8BkQFFARMB/wGMAUAB + EQH/AY4BQAERAf8BxQF5AS0B/wHtAaMBQgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/Ae0BpAFCAf8B + 7QGkAUIB/wGjAX0BSAH2AzMBUf8AeQADUQGiAT0BPAE7Af8B5gHMAcEB/wHnAc0BwgH/AecBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeoB1AHKAf8BvQGxAaoB/wI3ATYB + /wHDAawBogH/AdABtwGsAf8B0AG3AawB/wFDAUEBQAH/AW8BowG2Af8BjwHdAfkB/wGPAd0B+QH/AW4B + oAGxAf8BPgFIAUsB/wFtAZ4BrwH/AY8B3QH5Af8BjwHdAfkB/wFxAaYBuAH/AUIBQAE+Af8B0AG3AawB + /wHMAbQBqQH/AcQBrQGjAf8BzwG7AbEB/wHqAdoB0AH/Ae0B3QHTAf8B7QHdAdMB/wHrAdUBygH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AT0BPAE7Af8DUQGhEAAD + MwFRAY8BWwE9AfcBtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBGwH/AbgBXQEfAf8B + 8QHfAdIB/wH6AfMB7wH/AccBfwFOAf8BvgFpATAB/wH2AesB5AH/AfsB9QHyAf8BugFfASEB/wG4AVoB + GwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/Ab4BXgE2Af0B2QGMAUoB/gHvAaMBQgH/Ae8BowFCAf8B + 7wGjAUIB/wHvAaMBQgH/AekBnQE/Af8BlwFLARYB/wGMAUABEQH/AawBYAEgAf8BkQFDARIB/wGVAUYB + FAH/AdYBiwE2Af8B7gGkAUIB/wHuAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wHtAaQBQgH/AaMBfQFIAfYD + MwFR/wB5AANNAZIBOgI5Af8BwgGtAaQB/wHdAcUBugH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8BxgG0AasB/wFEAUIBQQH/AZ4BjQGFAf8B0AG3AawB + /wHQAbcBrAH/AWsBYgFeAf8BSQFcAWQB/wGLAdUB7wH/AY8B3QH5Af8BjwHdAfkB/wGPAd0B+QH/AY8B + 3QH5Af8BjwHdAfkB/wGLAdUB8AH/AUoBXgFlAf8BaQFhAV0B/wHPAbYBqwH/AbYBoQGYAf8BwgGrAaEB + /wHgAcwBwQH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B3QHTAf8B6gHVAcoB/wHnAc4BwwH/AecB + zQHCAf8B5wHNAcIB/wHbAcMBuQH/AcEBrAGkAf8BOgI5Af8DTgGVEAADMwFRAY8BWwE9AfcBtgFaARwB + /wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEbAf8B1gGgAXwF/wHXAaMBgAH/Ac0B + jAFfA/8B/gH/Ad0BsAGTAf8BtwFaARsB/wG4AVoBGwH/AbgBWgEbAf8BuAFaARsB/wG4AVoBGwH/AbwB + egErAfwB7gGiAUEB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/AdEBhQEzAf8BmwFQARkB + /wG5AW0BKAH/AesBoAFBAf8BuAFsASYB/wGOAT8BEAH/AagBWwEeAf8B7AGhAUEB/wHuAaQBQgH/Ae4B + pAFCAf8B7gGkAUIB/wHuAaQBQgH/AaMBfQFIAfYDMwFR/wB5AAMjATMDVgHuAUUBQwFBAf8BVgFRAU8B + /wF4AW4BagH/AakBmAGRAf8B2AHAAbYB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AdcB + vwG1Af8BWAFSAVAB/wFiAVsBVwH/Ac8BtwGsAf8B0AG3AawB/wGkAZIBigH/AT4CPAH/AVkBeAGEAf8B + igHVAe8B/wGPAd0B+QH/AY8B3QH5Af8BjwHdAfkB/wGLAdUB8AH/AVkBegGGAf8BPQI8Af8BowGRAYoB + /wHNAbQBqQH/AVYBUQFOAf8BTgFKAUgB/wGoAZ0BlgH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/Ae0B + 3QHTAf8B7QHcAdIB/wHXAcMBugH/AaUBlQGOAf8BdQFrAWcB/wFVAVABTgH/AUQBQgFBAf8CVgFVAfED + JQE2EAADMwFRAY8BWwE9AfcBtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYB + WgEcAf8BvAFlASsB/wH8AfgB9gH/Ae4B2AHIAf8B6QHNAboB/wH9AfoB+AH/Ab8BbQE1Af8BtwFaARsB + /wG3AVoBGwH/AbcBWgEbAf8BuAFaARsB/wG6AVwBHAH/AcQBfgEtAfwB8AGjAUIB/wHvAaMBQgH/Ae8B + owFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B4wGXATwB/wHrAZ8BQAH/Ae8BowFCAf8B6QGeAT8B + /wGlAVcBHAH/AY8BQAERAf8BxAF4ASwB/wHuAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wHuAaQBQgH/AaQB + fQFIAfYDMwFR/wB9AAMMARADPAFmA1YBsANcAdkDVgHqAkoBSQH6AXIBaQFlAf8B5AHKAb8B/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wGFAXkBdQH/AT4BPAE7Af8BrwGbAZIB/wHQAbcBrAH/Ac8BtgGrAf8B + hQF4AXIB/wE+AT0BPAH/AUkBXAFjAf8BbwGiAbUB/wF7AbkBzwH/AW8BowG1Af8BSgFdAWQB/wE+AjwB + /wGEAXcBcQH/AcwBtAGpAf8BzgG2AasB/wGtAZoBkQH/AWcBYAFdAf8BoAGWAZEB/wHtAd0B0wH/Ae0B + 3QHTAf8B7QHdAdMB/wHqAdoB0AH/AXMBbQFqAf8BNwI2AfsDWgHrA18B2gNVAbQDPQFpAw4BEhQAAzMB + UQGPAVoBPQH3AbUBWgEcAf8BtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYB + WgEcAf8B6AHJAbUB/wH+Av0B/wH+Af0B/AH/Ae4B1wHIAf8BuAFdAR8B/wG3AVoBGwH/AbcBWgEbAf8B + twFaARsB/wG3AVoBGwH/AaoBbAEpAf4B0AGfAUAB/QHwAaMBQgH/AfABowFCAf8B7wGjAUIB/wG6AW4B + KQH/AaYBWwEfAf8BpwFbAR8B/wGnAVsBHwH/AacBWwEfAf8BpQFYAR0B/wGnAVkBHQH/AaABUgEZAf8B + jgE/ARAB/wGQAUEBEQH/AagBWwEdAf8BzwGEATIB/wHuAaQBQgH/Ae4BpAFCAf8BpAF9AUgB9gMzAVH/ + AIkAAw8BFAMlATcDPQFpA1oB6QGtAZwBlAH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AdMBvAGyAf8B + SAFFAUQB/wFoAWABXAH/Ac4BtQGqAf8B0AG3AawB/wHPAbYBqwH/AaUBkwGLAf8BawFiAV4B/wFEAUIB + QAH/AjkBOAH/AUQBQQFAAf8BawFiAV4B/wGkAZIBigH/Ac0BtAGqAf8BjQF/AXgB/wGAAXMBbgH/Ac4B + twGtAf8B6AHWAcwB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHtAd0B0wH/AbQBqQGiAf8DWgHrAz8B + bQMnAToDEQEWIAADMwFRAY8BWgE9AfcBtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoB + HAH/AbYBWgEcAf8BtgFaARwB/wHQAZQBbAH/Af4B/QH8Av8C/gH/AdsBrQGOAf8BtwFbARwB/wG3AVoB + GwH/AbcBWgEbAf8BtwFaARsB/wG3AVoBGwH/AasBfQE+AfoB8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B + 8AGjAUIB/wGmAVsBHwH/AYsBQAERAf8BiwFAAREB/wGLAUABEQH/AYwBQAERAf8BjQFAAREB/wGPAT8B + EAH/AY0BPwEQAf8BjgE/ARAB/wGOAT8BEAH/AY8BPwEQAf8BxAF4ASwB/wHuAaQBQgH/Ae4BpAFCAf8B + pAF9AUgB9gMzAVH/AJEAAwgBCgNVAa8BSQFGAUQB/wHlAcsBwAH/AecBzQHCAf8B5wHNAcIB/wHnAc0B + wgH/AbsBpwGfAf8BOQI4Af8BdAFqAWUB/wHOAbUBqgH/AdABtwGsAf8B0AG3AawB/wHQAbcBrAH/AdAB + twGsAf8B0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHPAbYBqwH/AYUBeAFzAf8DNQH/AZIB + hgGBAf8B7AHbAdEB/wHtAd0B0wH/Ae0B3QHTAf8B7QHdAdMB/wHrAdsB0QH/AUsBSQFIAf8DVgGzAwkB + DCgAAzMBUQGPAVoBPQH3AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoB + HAH/AbYBWgEcAf8BwgF1AUIB/wH1AegB4AH/AfoB9AHvAf8BygGHAVoB/wG2AVoBHAH/AbYBWgEbAf8B + twFaARsB/wG3AVoBGwH/AaUBZQEmAf4BxwGUAUkB+wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMB + QgH/AfABowFCAf8B8AGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wGNAUABEQH/AaYBWAEcAf8B + 7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaQBQgH/Ae4BpAFCAf8B7gGkAUIB/wGkAX0B + SAH2AzMBUf8AkQADAwEEA04BlAM2Af8B1gG+AbQB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHkAcoB + vwH/AZsBjAGFAf8BOgI5Af8BaAFgAVwB/wGvAZsBkgH/Ac8BtgGsAf8B0AG3AawB/wHQAbcBrAH/AdAB + twGsAf8B0AG3AawB/wHQAbcBrAH/AdABtwGsAf8B0AG3AawB/wHQAbkBrgH/AZkBjAGGAf8BsgGgAZgB + /wHoAdABxQH/AewB2wHRAf8B8QHlAeEB/wHtAd0B1AH/Ad0BzgHFAf8DNwH/A04BlwMDAQQoAAMzAVEB + jwFaAT0B9wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG1AVoB + HAH/AbcBXQEhAf8BwQFzAT4B/wHDAXYBQgH/AbgBXwEjAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8B + twFaARsB/wGlAV8BKAH7AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMB + QgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/Ae8BowFCAf8BmwFPARkB/wGxAWMBIgH/Ae8BowFCAf8B + 7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae4BpAFCAf8BpAF9AUgB9gMzAVH/ + AJEAAxgBIANeAeIBfwF0AW8B/wHmAcwBwQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B + 5AHKAb8B/wG+AakBoQH/AUoBRwFFAf8BPgE8ATsB/wFiAVoBVwH/AaYBlAGMAf8B0AG3AawB/wHQAbcB + rAH/AcUBrgGkAf8BngGNAYYB/wGTAYQBfQH/AdkBwwG4Af8B6AHWAcwB/wHsAdwB0QH/AekB0QHGAf8B + 5wHNAcIB/wHsAdgB0gH/AfcB9AH5Af8B8gHoAeQB/wHsAdwB0gH/AYYBfgF6Af8DXAHjAxgBISgAAzMB + UQGPAVoBPQH3AbQBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUB + WQEcAf8BtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB + /wGkAWUBJgH+AcMBfgErAfwB8QGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfAB + owFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHoAZsBPgH/AekBnQE/Af8B7wGjAUIB + /wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wGmAX0BSAH2AzMB + Uf8AjQADAwEEA1EBogFRAUwBSgH/AeEByAG+Af8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB + /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHVAb4BtAH/AYsBfgF4Af8BWgFVAVIB/wFfAVoBVwH/AdsB + xgG7Af8B0QG8AbIB/wFPAUwBSgH/AUYBQwFCAf8BYgFbAVgB/wHsAdsB0QH/Ae0B3QHTAf8B7QHdAdMB + /wHsAdsB0AH/AekB0QHGAf8B5wHNAcIB/wHsAdoB1AH/AewB2wHRAf8B7QHdAdMB/wHpAdkB0AH/AVQB + UgFQAf8DUQGkAwQBBSQAAzMBUQGPAVoBPQH3AbQBWQEcAf8BtAFZARwB/wG1AVkBHAH/AbUBWQEcAf8B + tQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVoBHAH/AbUBWgEcAf8BtgFaARwB/wG2AVoB + HAH/AbYBWgEcAf8BtgFaARwB/wGqAW0BKwH+AcoBlwFAAf0B8QGjAUIB/wHxAaMBQgH/AfABowFCAf8B 8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMB - QgH/Ae8BowFCAf8BmwFPARkB/wGxAWMBIgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B - 7wGjAUIB/wHvAaMBQgH/Ae4BpAFCAf8BtAGJAUgB9gMzAVH/AJEAAxgBIANZAeIBfwF0AW8B/wHmAcwB - wQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5AHKAb8B/wG+AakBoQH/AUoBRwFFAf8B - PgE8ATsB/wFiAVoBVwH/AaYBlAGMAf8B0AG3AawB/wHQAbcBrAH/AcUBrgGkAf8BngGNAYYB/wGTAYQB - fQH/AdkBwwG4Af8B6AHWAcwB/wHsAdwB0QH/AekB0QHGAf8B5wHNAcIB/wHsAdgB0gH/AfcB9AH5Af8B - 8gHoAeQB/wHsAdwB0gH/AYYBfgF6Af8DWQHjAxgBISgAAzMBUQGbAVoBNwH3AbQBWQEcAf8BtQFZARwB - /wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFaARwB/wG2AVoBHAH/AbYB - WgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wGqAWIBIwH+AckBfgEuAfwB8QGjAUIB - /wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfAB - owFCAf8B8AGjAUIB/wHoAZsBPgH/AekBnQE/Af8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB - /wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wG1AYgBSAH2AzMBUf8AjQADAwEEA1EBogFRAUwBSgH/AeEB - yAG+Af8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB - /wHVAb4BtAH/AYsBfgF4Af8BWgFVAVIB/wFfAVoBVwH/AdsBxgG7Af8B0QG8AbIB/wFPAUwBSgH/AUYB - QwFCAf8BYgFbAVgB/wHsAdsB0QH/Ae0B3QHTAf8B7QHdAdMB/wHsAdsB0AH/AekB0QHGAf8B5wHNAcIB - /wHsAdoB1AH/AewB2wHRAf8B7QHdAdMB/wHpAdkB0AH/AVQBUgFQAf8DUQGkAwQBBSQAAzMBUQGbAVoB - NwH3AbQBWQEcAf8BtAFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8B - tQFZARwB/wG1AVoBHAH/AbUBWgEcAf8BtgFaARwB/wG2AVoBHAH/AbYBWgEcAf8BtgFaARwB/wGwAWoB - KAH+AdMBlwFAAf0B8QGjAUIB/wHxAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B - 8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B7wGjAUIB/wHvAaMB - QgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wG1AYgBSAH2AzMBUf8AjQAD - NQFWAToCOQH7AaEBkQGLAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHZAcIBtwH/AdYBwgG5Af8B7QHdAdMB - /wHrAdwB0gH/AckBvQG0Af8ByQG2Aa0B/wHaAcIBuAH/AegB0QHGAf8B7AHbAdAB/wHtAd0B0wH/Ae0B - 3QHTAf8B7QHbAdEB/wHpAdIBxwH/AecBzQHCAf8B6AHQAcUB/wHsAdoB0AH/Ae0B3QHTAf8BqQGeAZgB - /wE7AjoB+wM2AVgkAAMzAVEBmwFaATcB9wG0AVkBHQH/AbQBWQEdAf8BtAFZARwB/wG0AVkBHAH/AbQB - WQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB - /wG2AVoBHAH/AbYBWgEcAf8BuQFwASsB/AHwAaIBQQH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEB - owFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB - /wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8B - owFCAf8BtQGIAUgB9gMzAVH/AIkAAxEBFgNdAc4BWgFVAVIB/wHdAcUBugH/AecBzQHCAf8B5wHNAcIB - /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB - zQHCAf8B5wHNAcIB/wHnAc0BwgH/AeoB1AHKAf8B7QHeAdQB/wHtAd0B0wH/AewB2wHRAf8B6AHQAcUB - /wHnAc0BwgH/AekB0QHGAf8B7QHcAdIB/wHtAd0B0wH/Ae0B3QHTAf8B7AHbAdEB/wHpAdEBxgH/AecB - zQHCAf8B6AHRAcYB/wHtAdwB0gH/AeUB1gHMAf8BYAFcAVkB/wNbAdADEgEXIAADMwFRAZsBWgE3AfcB - tAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZARwB/wG0AVkBHAH/AbQBWQEcAf8BtQFZARwB/wG1AVkB - HAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoBHAH/AckBhAE3AfsB - 8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHwAaMB - QgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B - 8AGjAUIB/wHwAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/AbUBiAFIAfYDMwFR/wCJAAMoATwD - UgHtAa4BnAGVAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B - 5gHMAcEB/wHVAb0BswH/AeQBygHAAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc4B - wwH/AfEB5gHkAf8B8AHkAd4B/wHtAd0B0wH/AewB2wHQAf8B6QHRAcYB/wHnAc0BwgH/AecBzwHEAf8B - 2wHLAcIB/wHsAdwB0gH/Ae0B3QHTAf8B7AHbAdAB/wHpAdEBxgH/AecBzQHCAf8B6AHQAcUB/wHsAdoB - 0AH/AboBrgGmAf8DTQHvAykBPiAAAzMBUQGaAVoBNwH3AbQBWQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQB - WQEdAf8BtAFZAR0B/wG0AVkBHAH/AbQBWQEcAf8BtAFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB - /wG1AVkBHAH/AbUBWQEcAf8BrgFiASsB/AHiAZMBSAH+AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEB + QgH/AfABowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8B + 7wGjAUIB/wGmAX0BSAH2AzMBUf8AjQADNQFWAToCOQH7AaEBkQGLAf8B5wHNAcIB/wHnAc0BwgH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB + /wHZAcIBtwH/AdYBwgG5Af8B7QHdAdMB/wHrAdwB0gH/AckBvQG0Af8ByQG2Aa0B/wHaAcIBuAH/AegB + 0QHGAf8B7AHbAdAB/wHtAd0B0wH/Ae0B3QHTAf8B7QHbAdEB/wHpAdIBxwH/AecBzQHCAf8B6AHQAcUB + /wHsAdoB0AH/Ae0B3QHTAf8BqQGeAZgB/wE7AjoB+wM2AVgkAAMzAVEBjwFaAT0B9wG0AVkBHQH/AbQB + WQEdAf8BtAFZARwB/wG0AVkBHAH/AbQBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB + /wG1AVkBHAH/AbUBWgEcAf8BtQFaARwB/wG2AVoBHAH/AbYBWgEcAf8BswFwASsB/AHwAaIBQQH/AfEB + owFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB + /wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHvAaMBQgH/Ae8B + owFCAf8B7wGjAUIB/wHvAaMBQgH/Ae8BowFCAf8BpgF9AUgB9gMzAVH/AIkAAxEBFgNdAc4BWgFVAVIB + /wHdAcUBugH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecB + zQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeoB1AHKAf8B7QHeAdQB + /wHtAd0B0wH/AewB2wHRAf8B6AHQAcUB/wHnAc0BwgH/AekB0QHGAf8B7QHcAdIB/wHtAd0B0wH/Ae0B + 3QHTAf8B7AHbAdEB/wHpAdEBxgH/AecBzQHCAf8B6AHRAcYB/wHtAdwB0gH/AeUB1gHMAf8BYAFcAVkB + /wNbAdADEgEXIAADMwFRAY8BWgE9AfcBtAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZARwB/wG0AVkB + HAH/AbQBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWgEcAf8B + tQFaARwB/wG2AVoBHAH/AcABgQE3AfsB8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMB + QgH/AfEBowFCAf8B8QGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B + 8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wHvAaMB + QgH/AaYBfQFIAfYDMwFR/wCJAAMoATwDWAHtAa4BnAGVAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B + 5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5gHMAcEB/wHVAb0BswH/AeQBygHAAf8B5wHNAcIB/wHnAc0B + wgH/AecBzQHCAf8B5wHNAcIB/wHnAc4BwwH/AfEB5gHkAf8B8AHkAd4B/wHtAd0B0wH/AewB2wHQAf8B + 6QHRAcYB/wHnAc0BwgH/AecBzwHEAf8B2wHLAcIB/wHsAdwB0gH/Ae0B3QHTAf8B7AHbAdAB/wHpAdEB + xgH/AecBzQHCAf8B6AHQAcUB/wHsAdoB0AH/AboBrgGmAf8DUwHvAykBPiAAAzMBUQGOAVoBPQH3AbQB + WQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZAR0B/wG0AVkBHAH/AbQBWQEcAf8BtAFZARwB + /wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/AbUBWQEcAf8BpwFiASsB/AHcAY0BSwH+AfEB + owFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB + /wHxAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfAB + owFCAf8B8AGjAUIB/wHwAaMBQgH/Ae8BowFCAf8B7wGjAUIB/wGmAX0BSAH2AzMBUf8AiQADIAEuA14B + 4gFpAWIBXgH/AeEByAG9Af8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHhAcgBvQH/AX4B + cwFuAf8DNgH/AUcBRAFDAf8BqwGaAZMB/wHjAcoBvwH/AecBzQHCAf8B5wHNAcIB/wHuAd4B2QH/AfcB + 9gH8Af8B9wH2AfsB/wHwAeMB3QH/Ae0B3QHTAf8B6gHZAc8B/wGxAaEBmgH/AUsBSAFGAf8BNwI2Af8B + fgF3AXMB/wHmAdcBzQH/Ae0B3QHTAf8B7QHcAdIB/wHpAdEBxgH/AecBzQHCAf8B4wHLAcEB/wFtAWcB + YwH/A1sB5AMhATAgAAMzAVEBhwFgAToB9gGzAVkBHQH/AbMBWQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQB + WQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQBWQEcAf8BtAFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB + /wG1AVkBHAH/AbIBawEvAfsB8gGjAUIB/wHyAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEB owFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfABowFCAf8B8AGjAUIB /wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/Ae8B - owFCAf8B7wGjAUIB/wG1AYgBSAH2AzMBUf8AiQADIAEuA1kB4gFpAWIBXgH/AeEByAG9Af8B5wHNAcIB - /wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHhAcgBvQH/AX4BcwFuAf8DNgH/AUcBRAFDAf8BqwGaAZMB - /wHjAcoBvwH/AecBzQHCAf8B5wHNAcIB/wHuAd4B2QH/AfcB9gH8Af8B9wH2AfsB/wHwAeMB3QH/Ae0B - 3QHTAf8B6gHZAc8B/wGxAaEBmgH/AUsBSAFGAf8BNwI2Af8BfgF3AXMB/wHmAdcBzQH/Ae0B3QHTAf8B - 7QHcAdIB/wHpAdEBxgH/AecBzQHCAf8B4wHLAcEB/wFtAWcBYwH/A1cB5AMhATAgAAMzAVEBkQFgATQB - 9gGzAVkBHQH/AbMBWQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQB - WQEcAf8BtAFZARwB/wG1AVkBHAH/AbUBWQEcAf8BtQFZARwB/wG1AVkBHAH/Ab4BcQEvAfsB8gGjAUIB - /wHyAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEB - owFCAf8B8QGjAUIB/wHxAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB - /wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/Ae8BowFCAf8BtQGIAUgB9gMzAVH/AIkAAwIB - AwM7AWQDTwHvAXsBcQFtAf8B4QHIAb0B/wHnAc0BwgH/Ad4BxQG7Af8BogGSAYsB/wFRAUwBSwH/A1oB - 4ANNAZMDVgGwA1MB6QFvAWYBYgH/AecBzQHCAf8B6gHWAc8B/wHzAewB7gH/AfgB9wH+Af8B9wH2Af0B - /wHyAekB6AH/Ae4B3gHWAf8BfAF1AXEB/wNUAeoDVgGwA00BkgNYAd8BUAFNAUwB/wGjAZkBkwH/AeEB - 0gHJAf8B7AHbAdAB/wHjAcwBwQH/AX0BcgFtAf8DUQHxAz0BaAMDAQQgAAMdASgBawFeAVcB3QGzAVkB - HQH/AbMBWQEdAf8BswFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8B - tAFZARwB/wG0AVkBHAH/AbQBWQEcAf8BtQFZARwB/wGsAWUBJQH+AdMBlQFAAf0B8gGjAUIB/wHyAaMB - QgH/AfIBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B - 8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMB - QgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8BdQFpAVsB3QMdASj/AI0ABAIDMgRPAe8B - aQFiAV4B/wGxAZ4BlgH/AVsBVQFTAf8BRwJGAfoDUQGeAxgBIAMDAQQDCQELAz8BbAM2AfsB1AG9AbMB - /wHnAc0BwgH/AegB0AHHAf8B8wHrAe0B/wHvAeEB3wH/AegBzwHFAf8B4AHMAcIB/wMyAfwDPwFuAwkB - CwMDAQQDFgEeA1ABmgNBAfkBWQFWAVQB/wGwAaUBngH/AWwBZwFjAf8DTwHwAzMBUgMCAQMkAAQBAxoB - JAM9AWgCQQFAAXECQQFAAXECQQFAAXECQQFAAXECQQFAAXECQQFAAXECQQFAAXECQQFAAXECQQFAAXEC - QQFAAXECQQFAAXECQQFAAXACQQFAAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXED - QQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQM9AWgDGgEkBAH/AJEABAID - OwFkA1kB4gNSAe0DWwHNAzQBVAMDAQQMAAMnAToDVgHrAaUBlAGOAf8B5wHNAcIB/wHnAc0BwgH/AeoB - 1gHOAf8B6AHOAcQB/wHnAc0BwgH/AbEBnwGXAf8DVAHsAykBPQwAAwIBAwMzAVEDWwHLA1IB7QNZAeMD - PQFnAwIBA/8A/wBaAAMCAQMDIAEtAygBOwMQARUUAAMSARcDXQHaAXQBawFnAf8B5wHNAcIB/wHnAc0B - wgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AYABdQFwAf8DXAHbAxMBGRQAAw8BFAMoATsDIAEuAwIB - A/8A/wCGAANWAbMBVQFQAU4B/wHcAcMBuQH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AeEByAG9Af8B - WgFUAVIB/wNYAbr/AP8ArgADPQFpAUQBQgFBAf8BwAGrAaMB/wHlAcwBwQH/AeUBzAHBAf8B5QHMAcEB - /wHFAbABpwH/AUgBRQFDAf8DQAFx/wD/AK4AAw0BEQJOAUwB8AE6AjkB/wE9AjsB/wE9AjsB/wE9AjsB - /wE6AjkB/wNMAfMDEQEW/wD/ALIAAyQBNANNAZIDUQGiA1EBogNRAaIDTQGTAyUBN/8A/wD/AP8A/wA9 - AAFCAU0BPgcAAT4DAAEoAwABtAMAAS0DAAEBAQABAQUAATgBBBYAA/8BAAf/AccD/wHADAAC/wHgAT8D - /wGHA/8BwAwAAv8BwAEfA/8BgwP/AcAMAAL/AcABHwP/AYAD/wHADAAC/wHAAQ8D/wGAA/8BwAwAAf8B - DwGAAQ8BhwL/AYABPwL/AcAMAAH+AQMBgAEOAQMC/wGAAT8C/wHADAAB/AMAAQEC/wGAAR8C/wHADAAB - +AQAAv8BgAEPAv8BwAwAAfgEAAH/AYADAAEDAcAMAAH4BAAB/wQAAQEBwAwAAfgEAAH/BAABAQHADAAB - /AMAAQEB/wQAAQEBwAwAAfwDAAEBAf8EAAEBAcAMAAH+AwABAwH/BAABAQHADAAB/gMAAQMB/wQAAQEB - wAwAAf4DAAEDAf8EAAEBAcAMAAH4BAAB/wQAAQEBwAwAAcAEAAEfBAABAQHADAABgAQAAQ8EAAEBAcAM - AAGABAABDwQAAQEBwAwAAYAEAAEPBAABAQHADAABgAQAAQ8EAAEBAcAMAAGABAABDwQAAQEBwAwAAYAE - AAEPBAABAQHADAABgAQAAQ8EAAEBAcAMAAHABAABHwQAAQEBwAwAAfgEAAH/BAABAQHADAAB/gMAAQMB - /wQAAQEBwAwAAf4DAAEDAf8EAAEBAcAMAAH+AwABAwH/BAABAQHADAAB/AMAAQEB/wQAAQEBwAwAAfwD - AAEBAf8EAAEBAcAMAAH4BAAB/wQAAQEBwAwAAfgEAAH/BAABAQHADAAB+AQAAf8EAAEBAcAMAAH4BAAB - /wQAAQEBwAwAAfwDAAEBAf8EAAEBAcAMAAH+AQMBgAEOAQMG/wHADAAB/wEPAYABDwGHBv8BwAwAAv8B - wAEfB/8BwAwAAv8BwAEfB/8BwAwAAv8BwAEfB/8BwAwAAv8B4AE/B/8BwAwAC/8BwAwACw== + owFCAf8BpgF9AUgB9gMzAVH/AIkAAwIBAwM7AWQDVQHvAXsBcQFtAf8B4QHIAb0B/wHnAc0BwgH/Ad4B + xQG7Af8BogGSAYsB/wFRAUwBSwH/A18B4ANNAZMDVgGwA1oB6QFvAWYBYgH/AecBzQHCAf8B6gHWAc8B + /wHzAewB7gH/AfgB9wH+Af8B9wH2Af0B/wHyAekB6AH/Ae4B3gHWAf8BfAF1AXEB/wNYAeoDVgGwA00B + kgNdAd8BUAFNAUwB/wGjAZkBkwH/AeEB0gHJAf8B7AHbAdAB/wHjAcwBwQH/AX0BcgFtAf8DVgHxAz0B + aAMDAQQgAAMdASgBZQFeAVsB3QGzAVkBHQH/AbMBWQEdAf8BswFZAR0B/wG0AVkBHQH/AbQBWQEdAf8B + tAFZAR0B/wG0AVkBHQH/AbQBWQEdAf8BtAFZARwB/wG0AVkBHAH/AbQBWQEcAf8BtQFZARwB/wGmAWgB + KAH+AcoBlQFAAf0B8gGjAUIB/wHyAaMBQgH/AfIBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B + 8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHxAaMBQgH/AfEBowFCAf8B8QGjAUIB/wHwAaMB + QgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B8AGjAUIB/wHwAaMBQgH/AfABowFCAf8B + aQFlAV4B3QMdASj/AI0ABAIDMgFPA1UB7wFpAWIBXgH/AbEBngGWAf8BWwFVAVMB/wFMAksB+gNRAZ4D + GAEgAwMBBAMJAQsDPwFsAzYB+wHUAb0BswH/AecBzQHCAf8B6AHQAccB/wHzAesB7QH/Ae8B4QHfAf8B + 6AHPAcUB/wHgAcwBwgH/Ay8B/AM/AW4DCQELAwMBBAMWAR4DUAGaA0EB+QFZAVYBVAH/AbABpQGeAf8B + bAFnAWMB/wNSAfADMwFSAwIBAyQABAEDGgEkAz0BaAJBAUABcQJBAUABcQJBAUABcQJBAUABcQJBAUAB + cQJBAUABcQJBAUABcQJBAUABcQJBAUABcQJBAUABcQJBAUABcQJBAUABcAJBAUABcQNBAXEDQQFxA0EB + cQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EBcQNBAXEDQQFxA0EB + cQNBAXEDQQFxAz0BaAMaASQEAf8AkQAEAgM7AWQDXgHiA1gB7QNbAc0DNAFUAwMBBAwAAycBOgNaAesB + pQGUAY4B/wHnAc0BwgH/AecBzQHCAf8B6gHWAc4B/wHoAc4BxAH/AecBzQHCAf8BsQGfAZcB/wNbAewD + KQE9DAADAgEDAzMBUQNcAcsDWAHtA1wB4wM9AWcDAgED/wD/AFoAAwIBAwMgAS0DKAE7AxABFRQAAxIB + FwNfAdoBdAFrAWcB/wHnAc0BwgH/AecBzQHCAf8B5wHNAcIB/wHnAc0BwgH/AecBzQHCAf8BgAF1AXAB + /wNfAdsDEwEZFAADDwEUAygBOwMgAS4DAgED/wD/AIYAA1YBswFVAVABTgH/AdwBwwG5Af8B5wHNAcIB + /wHnAc0BwgH/AecBzQHCAf8B4QHIAb0B/wFaAVQBUgH/A1gBuv8A/wCuAAM9AWkBRAFCAUEB/wHAAasB + owH/AeUBzAHBAf8B5QHMAcEB/wHlAcwBwQH/AcUBsAGnAf8BSAFFAUMB/wNAAXH/AP8ArgADDQERA1EB + 8AE6AjkB/wE9AjsB/wE9AjsB/wE9AjsB/wE6AjkB/wNPAfMDEQEW/wD/ALIAAyQBNANNAZIDUQGiA1EB + ogNRAaIDTQGTAyUBN/8A/wD/AP8A/wA9AAFCAU0BPgcAAT4DAAEoAwABtAMAAS0DAAEBAQABAQUAATgB + BBYAA/8BAAf/AccD/wHADAAC/wHgAT8D/wGHA/8BwAwAAv8BwAEfA/8BgwP/AcAMAAL/AcABHwP/AYAD + /wHADAAC/wHAAQ8D/wGAA/8BwAwAAf8BDwGAAQ8BhwL/AYABPwL/AcAMAAH+AQMBgAEOAQMC/wGAAT8C + /wHADAAB/AMAAQEC/wGAAR8C/wHADAAB+AQAAv8BgAEPAv8BwAwAAfgEAAH/AYADAAEDAcAMAAH4BAAB + /wQAAQEBwAwAAfgEAAH/BAABAQHADAAB/AMAAQEB/wQAAQEBwAwAAfwDAAEBAf8EAAEBAcAMAAH+AwAB + AwH/BAABAQHADAAB/gMAAQMB/wQAAQEBwAwAAf4DAAEDAf8EAAEBAcAMAAH4BAAB/wQAAQEBwAwAAcAE + AAEfBAABAQHADAABgAQAAQ8EAAEBAcAMAAGABAABDwQAAQEBwAwAAYAEAAEPBAABAQHADAABgAQAAQ8E + AAEBAcAMAAGABAABDwQAAQEBwAwAAYAEAAEPBAABAQHADAABgAQAAQ8EAAEBAcAMAAHABAABHwQAAQEB + wAwAAfgEAAH/BAABAQHADAAB/gMAAQMB/wQAAQEBwAwAAf4DAAEDAf8EAAEBAcAMAAH+AwABAwH/BAAB + AQHADAAB/AMAAQEB/wQAAQEBwAwAAfwDAAEBAf8EAAEBAcAMAAH4BAAB/wQAAQEBwAwAAfgEAAH/BAAB + AQHADAAB+AQAAf8EAAEBAcAMAAH4BAAB/wQAAQEBwAwAAfwDAAEBAf8EAAEBAcAMAAH+AQMBgAEOAQMG + /wHADAAB/wEPAYABDwGHBv8BwAwAAv8BwAEfB/8BwAwAAv8BwAEfB/8BwAwAAv8BwAEfB/8BwAwAAv8B + 4AE/B/8BwAwAC/8BwAwACw== \ No newline at end of file From ebc7a5708b8f4a91ba23e85e451f0e08f3b51802 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 22:05:10 +0200 Subject: [PATCH 7/9] Added progress calculation for sections & texts; covered corner cases --- .../Processor/TranslationProcessor.cs | 48 +++++++++++++++++++ 1 file changed, 48 insertions(+) diff --git a/I18N Commander/Processor/TranslationProcessor.cs b/I18N Commander/Processor/TranslationProcessor.cs index 7e771b6..9de7cb8 100644 --- a/I18N Commander/Processor/TranslationProcessor.cs +++ b/I18N Commander/Processor/TranslationProcessor.cs @@ -60,6 +60,54 @@ public static class TranslationProcessor var numTotalTranslations = numCultures * numTextElements; var numTextElementsTranslated = await db.Translations.CountAsync(n => !string.IsNullOrWhiteSpace(n.Text)); + if(numTextElementsTranslated == 0 && numTotalTranslations == 0) + return new ProcessorResult(100); + + if (numTotalTranslations == 0) + return new ProcessorResult(0); + + if(numTextElementsTranslated > numTotalTranslations) + return new ProcessorResult(100); + + return new ProcessorResult(numTextElementsTranslated * 100 / numTotalTranslations); + } + + public static async Task> CalculateTranslationProgress(Section section) + { + await using var db = ProcessorMeta.ServiceProvider.GetRequiredService(); + var numCultures = (await AppSettings.GetCultureIndices()).Count; + var numTextElements = await db.TextElements.CountAsync(n => n.Section == section); + var numTotalTranslations = numCultures * numTextElements; + var numTextElementsTranslated = await db.Translations.CountAsync(n => !string.IsNullOrWhiteSpace(n.Text) && n.TextElement.Section == section); + + if(numTextElementsTranslated == 0 && numTotalTranslations == 0) + return new ProcessorResult(100); + + if (numTotalTranslations == 0) + return new ProcessorResult(0); + + if(numTextElementsTranslated > numTotalTranslations) + return new ProcessorResult(100); + + return new ProcessorResult(numTextElementsTranslated * 100 / numTotalTranslations); + } + + public static async Task> CalculateTranslationProgress(TextElement textElement) + { + await using var db = ProcessorMeta.ServiceProvider.GetRequiredService(); + var numCultures = (await AppSettings.GetCultureIndices()).Count; + var numTotalTranslations = numCultures; + var numTextElementsTranslated = await db.Translations.CountAsync(n => !string.IsNullOrWhiteSpace(n.Text) && n.TextElement == textElement); + + if(numTextElementsTranslated == 0 && numTotalTranslations == 0) + return new ProcessorResult(100); + + if (numTotalTranslations == 0) + return new ProcessorResult(0); + + if(numTextElementsTranslated > numTotalTranslations) + return new ProcessorResult(100); + return new ProcessorResult(numTextElementsTranslated * 100 / numTotalTranslations); } } \ No newline at end of file From 6c7b5dbadeb3e22181827c75bb4b08aea5ec700e Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 22:07:01 +0200 Subject: [PATCH 8/9] Added translation progress to sections --- .../UI WinForms/Components/SectionTree.cs | 41 +++++++++++++++++-- 1 file changed, 37 insertions(+), 4 deletions(-) diff --git a/I18N Commander/UI WinForms/Components/SectionTree.cs b/I18N Commander/UI WinForms/Components/SectionTree.cs index f7b3db6..d402363 100644 --- a/I18N Commander/UI WinForms/Components/SectionTree.cs +++ b/I18N Commander/UI WinForms/Components/SectionTree.cs @@ -1,4 +1,5 @@ -using Processor; +using DataModel.Database; +using Processor; using UI_WinForms.Dialogs; using UI_WinForms.Resources; @@ -6,6 +7,8 @@ namespace UI_WinForms.Components; public partial class SectionTree : UserControl { + private static readonly Dictionary> NODE_PROGRESS_HANDLERS = new(); + public SectionTree() { this.InitializeComponent(); @@ -46,17 +49,23 @@ public partial class SectionTree : UserControl { foreach (var section in await SectionProcessor.LoadLayer(i)) { + var translationProgress = await TranslationProcessor.CalculateTranslationProgress(section); + // Create the tree node: var node = new TreeNode { Name = section.DataKey, // [sic] name is the key - Text = section.Name, + Text = $"{section.Name} [{translationProgress.Result}%]", StateImageIndex = 1, }; // Cache the node: treeNodes.Add(section.DataKey, node); + // Wire each node to the translation change event to update the translation progress: + NODE_PROGRESS_HANDLERS.Add(node, async (_, translation) => await this.UpdateTranslationProgress(node, section, translation)); + AppEvents.WhenTranslationChanged += NODE_PROGRESS_HANDLERS[node]; + // Is this a root node? if (section.Depth is 0) @@ -107,6 +116,18 @@ public partial class SectionTree : UserControl this.treeView.ExpandAll(); } + private async Task UpdateTranslationProgress(TreeNode node, Section section, DataModel.Database.Translation? translation) + { + if (translation is null || translation.TextElement.Section.DataKey == section.DataKey) + { + var currentTranslationProgress = await TranslationProcessor.CalculateTranslationProgress(section); + if(this.treeView.InvokeRequired) + this.treeView.Invoke(() => node.Text = $"{section.Name} [{currentTranslationProgress.Result}%]"); + else + node.Text = $"{section.Name} [{currentTranslationProgress.Result}%]"; + } + } + private async void buttonAdd_Click(object sender, EventArgs e) { if(this.DesignMode) @@ -135,13 +156,19 @@ public partial class SectionTree : UserControl if(!addedSection.Successful) return; + var translationProgress = await TranslationProcessor.CalculateTranslationProgress(addedSection.Result!); + // Add the new section to the tree control: var node = new TreeNode { Name = addedSection.Result!.DataKey, // [sic] name is the key - Text = addedSection.Result.Name, + Text = $"{addedSection.Result.Name} [{translationProgress.Result}%]", StateImageIndex = 1, }; + + // Wire each node to the translation change event to update the translation progress: + NODE_PROGRESS_HANDLERS.Add(node, async (_, translation) => await this.UpdateTranslationProgress(node, addedSection.Result, translation)); + AppEvents.WhenTranslationChanged += NODE_PROGRESS_HANDLERS[node]; if(!addRootNode && selectedNode is not null) selectedNode.Nodes.Add(node); @@ -171,14 +198,18 @@ public partial class SectionTree : UserControl // Ask the user, if he really wants to remove the section: if(MessageBox.Show(numberChildren > 0 ? $"Are you sure, you want to remove the section '{selectedNode.Text}', its {numberChildren} children and so on?" : $"Are you sure, you want to remove the section '{selectedNode.Text}'?", "Remove section", MessageBoxButtons.YesNo, MessageBoxIcon.Question, MessageBoxDefaultButton.Button2) == DialogResult.No) return; - + // Remove the section from the database: // (notice, that the node's name is its key) await SectionProcessor.RemoveSection(selectedNode.Name); // Remove all nodes from the tree control: this.treeView.Nodes.Clear(); + foreach (var (treeNode, handler) in NODE_PROGRESS_HANDLERS) + AppEvents.WhenTranslationChanged -= handler; + NODE_PROGRESS_HANDLERS.Clear(); + // Reload the tree: this.LoadNodes(this, EventArgs.Empty); @@ -187,6 +218,8 @@ public partial class SectionTree : UserControl // Fire the click event: this.treeView_NodeMouseClick(this, new TreeNodeMouseClickEventArgs(this.treeView.SelectedNode!, MouseButtons.Left, 1, 0, 0)); + + AppEvents.TranslationChanged(null); } private async void treeView_NodeMouseClick(object sender, TreeNodeMouseClickEventArgs e) From 0f732e076659da2798d2ca54c44ed72060aa7ef7 Mon Sep 17 00:00:00 2001 From: Thorsten Sommer Date: Mon, 26 Sep 2022 22:08:30 +0200 Subject: [PATCH 9/9] Added translation progress to text elements --- .../UI WinForms/Components/TextElements.cs | 43 +++++++++++++++++-- 1 file changed, 40 insertions(+), 3 deletions(-) diff --git a/I18N Commander/UI WinForms/Components/TextElements.cs b/I18N Commander/UI WinForms/Components/TextElements.cs index ea31b88..b7dec0e 100644 --- a/I18N Commander/UI WinForms/Components/TextElements.cs +++ b/I18N Commander/UI WinForms/Components/TextElements.cs @@ -55,6 +55,37 @@ public partial class TextElements : UserControl else this.buttonChangeMultiLine.Image = Icons.icons8_align_text_left_512; }; + + AppEvents.WhenTranslationChanged += async (_, translation) => + { + if (translation is null) + return; + + // Check if the translation is in the current text element. + // When this is the case, update the list view item. We want + // to update the progress part. + if (this.currentTextElement?.Translations.Any(n => n.Id == translation.Id) ?? false) + { + // Determine the translation progress: + var progress = await TranslationProcessor.CalculateTranslationProgress(this.currentTextElement); + + if (this.listTextElements.InvokeRequired) + this.listTextElements.Invoke(UpdateListElement); + else + UpdateListElement(); + + void UpdateListElement() + { + // Get the list view item by searching the TAG property: + var item = this.listTextElements.Items.Cast().FirstOrDefault(n => n.Tag is int id && id == this.currentTextElement.Id); + if (item is null) + return; + + // Update the progress text: + item.Text = $"{this.currentTextElement.Name} [{progress.Result}%]"; + } + } + }; } // Loads all the text elements for the current section. @@ -69,11 +100,15 @@ public partial class TextElements : UserControl // Update the list: this.listTextElements.Items.Clear(); foreach (var textElement in textElements) - this.listTextElements.Items.Add(new ListViewItem(textElement.Name, textElement.IsMultiLine ? 1 : 0) + { + // Determine the translation progress: + var progress = await TranslationProcessor.CalculateTranslationProgress(textElement); + this.listTextElements.Items.Add(new ListViewItem($"{textElement.Name} [{progress.Result}%]", textElement.IsMultiLine ? 1 : 0) { Tag = textElement.Id, }); - + } + this.column.AutoResize(ColumnHeaderAutoResizeStyle.ColumnContent); } @@ -107,6 +142,7 @@ public partial class TextElements : UserControl }); this.column.AutoResize(ColumnHeaderAutoResizeStyle.ColumnContent); + AppEvents.TranslationChanged(null); } private async void buttonRemove_Click(object sender, EventArgs e) @@ -118,11 +154,12 @@ public partial class TextElements : UserControl if(MessageBox.Show(this.currentTextElement.Translations.Count > 0 ? $"Are you sure, you want to remove the text element '{this.currentTextElement.Name}', its {this.currentTextElement.Translations.Count} translations and so on?" : $"Are you sure, you want to remove the text element '{this.currentTextElement.Name}'?", "Remove text element", MessageBoxButtons.YesNo, MessageBoxIcon.Question, MessageBoxDefaultButton.Button2) == DialogResult.No) return; - // Remove the text element1 from the database: + // Remove the text element from the database: await TextElementProcessor.DeleteTextElement(this.currentTextElement.Id); // Reload the data: await this.LoadTextElements(); + AppEvents.TranslationChanged(null); } private async void buttonRename_Click(object sender, EventArgs e)