Kenric Nugteren 1 рік тому
батько
коміт
83c68ba4fa

+ 2 - 0
prs.desktop/Panels/DataEntry/DataEntryList.xaml

@@ -76,6 +76,8 @@
                                             <MenuItem x:Name="_Explode" Header="Regroup Pages" Click="_Explode_OnClick"/>
                                             <MenuItem x:Name="_ShowImage" Header="View Image" Click="_ShowImage_Click"
                                                       ToolTip="Show this image in a separate window." Tag="{Binding}"/>
+                                            <MenuItem x:Name="_RotateImage" Header="Rotate Document" Click="_RotateImage_Click"
+                                                      ToolTip="Rotate this document 90° clockwise" Tag="{Binding}"/>
                                         </ContextMenu.Items>
                                     </ContextMenu>
                                 </ItemsControl.ContextMenu>

+ 102 - 11
prs.desktop/Panels/DataEntry/DataEntryList.xaml.cs

@@ -35,6 +35,7 @@ using PRSDesktop.Panels.DataEntry;
 using InABox.Wpf.Editors;
 using System.Timers;
 using Microsoft.Win32;
+using javax.xml.crypto;
 
 namespace PRSDesktop;
 
@@ -98,6 +99,8 @@ public partial class DataEntryList : UserControl, ICorePanel, IDockPanel
     public event DateEntrySelectionHandler? SelectionChanged;
 
     private readonly object _viewListLock = new object();
+
+    private List<Tuple<ImageSource, DataEntryDocument>> ViewDocuments { get; } = new();
     public ObservableCollection<ImageSource> ViewList { get; init; } = new();
 
     private List<DataEntryDocumentWindow> OpenWindows = new();
@@ -173,14 +176,15 @@ public partial class DataEntryList : UserControl, ICorePanel, IDockPanel
         return images;
     }
 
-    private void UpdateViewList()
+    private void UpdateViewList(bool force = false)
     {
         var selected = _dataEntryGrid.SelectedRows.Select(x => x.ToObject<DataEntryDocument>()).ToList();
-        if (selected.Count == SelectedScans.Count && !selected.Any(x => SelectedScans.All(y => x.ID != y.ID)))
+        if (!force && selected.Count == SelectedScans.Count && !selected.Any(x => SelectedScans.All(y => x.ID != y.ID)))
             return;
 
         SelectedScans = selected;
         ViewList.Clear();
+        ViewDocuments.Clear();
 
         Task.Run(() =>
         {
@@ -251,20 +255,26 @@ public partial class DataEntryList : UserControl, ICorePanel, IDockPanel
                 list.Add(image);
             }
         }
-        lock (_viewListLock)
+        ViewDocuments.Clear();
+        foreach (var scan in SelectedScans)
         {
-            ViewList.Clear();
-            foreach (var scan in SelectedScans)
+            if (bitmaps.TryGetValue(scan.Document.ID, out var list))
             {
-                if (bitmaps.TryGetValue(scan.Document.ID, out var list))
+                foreach (var bitmap in list)
                 {
-                    foreach (var bitmap in list)
-                    {
-                        ViewList.Add(bitmap);
-                    }
+                    ViewDocuments.Add(new(bitmap, scan));
                 }
             }
         }
+
+        lock (_viewListLock)
+        {
+            ViewList.Clear();
+            foreach(var (image, _) in ViewDocuments)
+            {
+                ViewList.Add(image);
+            }
+        }
     }
 
     #endregion
@@ -350,7 +360,7 @@ public partial class DataEntryList : UserControl, ICorePanel, IDockPanel
 
     private void _documents_OnSelectItem(object sender, DynamicGridSelectionEventArgs e)
     {
-        UpdateViewList();
+        UpdateViewList(false);
 
         DoSelect(e.Rows);
     }
@@ -607,4 +617,85 @@ public partial class DataEntryList : UserControl, ICorePanel, IDockPanel
 
         OpenImageWindow(image);
     }
+
+    private void RotateDocument(Document doc)
+    {
+        var extension = Path.GetExtension(doc.FileName).ToLower();
+        if (extension == ".pdf")
+        {
+            var loadeddoc = new PdfLoadedDocument(doc.Data);
+            foreach (var page in loadeddoc.GetPages())
+            {
+                var rotation = (int)page.Rotation;
+                rotation = (rotation + 1) % 4;
+                page.Rotation = (PdfPageRotateAngle)rotation;
+            }
+
+            doc.Data = loadeddoc.SaveToBytes();
+        }
+        else if (extension == ".jpg" || extension == ".jpeg" || extension == ".png" || extension == ".bmp")
+        {
+            using var stream = new MemoryStream(doc.Data);
+            var bitmap = Bitmap.FromStream(stream);
+            bitmap.RotateFlip(RotateFlipType.Rotate90FlipNone);
+            using var outStream = new MemoryStream();
+            bitmap.Save(outStream, extension switch
+            {
+                ".jpg" or ".jpeg" => ImageFormat.Jpeg,
+                ".png" => ImageFormat.Png,
+                _ => ImageFormat.Bmp
+            });
+            doc.Data = outStream.ToArray();
+        }
+        else
+        {
+            using var stream = new MemoryStream(doc.Data);
+            var loadeddoc = DataEntryReGroupWindow.RenderToPDF(doc.FileName, stream);
+
+            foreach (var page in loadeddoc.GetPages())
+            {
+                var rotation = (int)page.Rotation;
+                rotation = (rotation + 1) % 4;
+                page.Rotation = (PdfPageRotateAngle)rotation;
+            }
+
+            doc.Data = loadeddoc.SaveToBytes();
+        }
+    }
+
+    private void _RotateImage_Click(object sender, RoutedEventArgs e)
+    {
+        if (sender is not MenuItem item || item.Tag is not ImageSource image) return;
+
+        var document = ViewDocuments.FirstOrDefault(x => x.Item1 == image)?.Item2;
+        if (document is null)
+        {
+            MessageWindow.ShowError("An error occurred", "Document does not exist in ViewDocuments list");
+            return;
+        }
+
+        var doc = DataEntryCache.Cache.LoadDocuments(CoreUtils.One(document.Document.ID), checkTimestamp: true).First();
+        try
+        {
+            RotateDocument(doc);
+        }
+        catch(Exception err)
+        {
+            MessageWindow.ShowError("Something went wrong while trying to rotate this document.", err);
+            return;
+        }
+
+        Client.Save(doc, "Rotated by user.");
+
+        if (Path.GetExtension(doc.FileName) == ".pdf")
+        {
+            document.Thumbnail = ImageUtils.GetPDFThumbnail(doc.Data, 256, 256);
+        }
+
+        new Client<DataEntryDocument>().Save(document, "");
+
+        DataEntryCache.Cache.Add(new DataEntryCachedDocument(doc));
+
+        UpdateViewList(true);
+    }
 }