private bool InsertFrames(bool after, double screenScale) { try { //Sizes. var left = NewList[0].Path.SourceFrom(); var right = CurrentList[0].Path.SourceFrom(); //The image should be displayed based on the scale of the project. var scaleLeft = left.DpiX / 96d; var scaleRight = right.DpiX / 96d; //Math.Round(right.DpiX / 96d, 2); var scaleDiffLeft = screenScale / scaleLeft; var scaleDiffRight = screenScale / scaleRight; #region Current frames //If the canvas size changed. if (Math.Abs(RightCanvas.ActualWidth - _rightWidth) > 0.1 || Math.Abs(RightCanvas.ActualHeight - _rightHeight) > 0.1 || Math.Abs(RightImage.ActualWidth - _rightWidth) > 0.1 || Math.Abs(RightImage.ActualHeight - _rightHeight) > 0.1) { StartProgress(CurrentList.Count, FindResource("S.Editor.UpdatingFrames").ToString()); //Saves the state before resizing the images. ActionStack.SaveState(ActionStack.EditAction.ImageAndProperties, CurrentList, Util.Other.ListOfIndexes(0, CurrentList.Count)); foreach (var frameInfo in CurrentList) { #region Resize Images //Draws the images into a DrawingVisual component. var drawingVisual = new DrawingVisual(); using (var context = drawingVisual.RenderOpen()) { //The back canvas. context.DrawRectangle(new SolidColorBrush(UserSettings.All.InsertFillColor), null, new Rect(new Point(0, 0), new Point(Math.Round(RightCanvas.ActualWidth, MidpointRounding.AwayFromZero), Math.Round(RightCanvas.ActualHeight, MidpointRounding.AwayFromZero)))); var topPoint = Dispatcher.Invoke <double>(() => Canvas.GetTop(RightImage)) * scaleDiffRight; var leftPoint = Dispatcher.Invoke <double>(() => Canvas.GetLeft(RightImage)) * scaleDiffRight; //The image. context.DrawImage(frameInfo.Path.SourceFrom(), new Rect(leftPoint, topPoint, RightImage.ActualWidth * scaleDiffRight, RightImage.ActualHeight * scaleDiffRight)); //context.DrawText(new FormattedText("Hi!", CultureInfo.InvariantCulture, FlowDirection.LeftToRight, new Typeface("Segoe UI"), 32, Brushes.Black), new Point(0, 0)); } //Converts the Visual (DrawingVisual) into a BitmapSource. var bmp = new RenderTargetBitmap((int)Math.Round(RightCanvas.ActualWidth * screenScale, MidpointRounding.AwayFromZero), (int)Math.Round(RightCanvas.ActualHeight * screenScale, MidpointRounding.AwayFromZero), right.DpiX, right.DpiX, PixelFormats.Pbgra32); bmp.Render(drawingVisual); #endregion #region Save //Creates a PngBitmapEncoder and adds the BitmapSource to the frames of the encoder var encoder = new PngBitmapEncoder(); encoder.Frames.Add(BitmapFrame.Create(bmp)); //Saves the image into a file using the encoder using (Stream stream = File.Create(frameInfo.Path)) encoder.Save(stream); #endregion if (_isCancelled) { return(false); } UpdateProgress(CurrentList.IndexOf(frameInfo)); } } #endregion #region New frames StartProgress(CurrentList.Count, FindResource("S.Editor.ImportingFrames").ToString()); var folder = Path.GetDirectoryName(CurrentList[0].Path); var insertFolder = Path.GetDirectoryName(NewList[0].Path); //If the canvas size changed. if (Math.Abs(LeftCanvas.ActualWidth - _leftWidth) > 0.1 || Math.Abs(LeftCanvas.ActualHeight - _leftHeight) > 0.1 || Math.Abs(LeftImage.ActualWidth - _leftWidth) > 0.1 || Math.Abs(LeftImage.ActualHeight - _leftHeight) > 0.1 || Math.Abs(left.DpiX - right.DpiX) > 0.1) { foreach (var frameInfo in NewList) { #region Resize Images //Draws the images into a DrawingVisual component. var drawingVisual = new DrawingVisual(); using (var context = drawingVisual.RenderOpen()) { //The back canvas. context.DrawRectangle(new SolidColorBrush(UserSettings.All.InsertFillColor), null, new Rect(new Point(0, 0), new Point(Math.Round(RightCanvas.ActualWidth * scaleDiffRight, MidpointRounding.AwayFromZero), Math.Round(RightCanvas.ActualHeight * scaleDiffRight, MidpointRounding.AwayFromZero)))); var topPoint = Dispatcher.Invoke <double>(() => Canvas.GetTop(LeftImage)) * scaleDiffRight; var leftPoint = Dispatcher.Invoke <double>(() => Canvas.GetLeft(LeftImage)) * scaleDiffRight; //The front image. context.DrawImage(frameInfo.Path.SourceFrom(), new Rect(leftPoint, topPoint, LeftImage.ActualWidth * scaleDiffRight, LeftImage.ActualHeight * scaleDiffRight)); // * scaleDiffLeft } //Converts the Visual (DrawingVisual) into a BitmapSource. Using the actual frame dpi. var bmp = new RenderTargetBitmap((int)Math.Round(LeftCanvas.ActualWidth * screenScale, MidpointRounding.AwayFromZero), (int)Math.Round(LeftCanvas.ActualHeight * screenScale, MidpointRounding.AwayFromZero), right.DpiX, right.DpiX, PixelFormats.Pbgra32); bmp.Render(drawingVisual); #endregion #region Save //Creates a PngBitmapEncoder and adds the BitmapSource to the frames of the encoder. var encoder = new PngBitmapEncoder(); encoder.Frames.Add(BitmapFrame.Create(bmp)); File.Delete(frameInfo.Path); var fileName = Path.Combine(folder, $"{_insertIndex}-{NewList.IndexOf(frameInfo)} {DateTime.Now:hh-mm-ss}.png"); //Saves the image into a file using the encoder. using (Stream stream = File.Create(fileName)) encoder.Save(stream); frameInfo.Path = fileName; #endregion if (_isCancelled) { return(false); } UpdateProgress(NewList.IndexOf(frameInfo)); } } else { foreach (var frameInfo in NewList) { #region Move var fileName = Path.Combine(folder, $"{_insertIndex}-{NewList.IndexOf(frameInfo)} {DateTime.Now:hh-mm-ss}.png"); File.Move(frameInfo.Path, fileName); frameInfo.Path = fileName; #endregion if (_isCancelled) { return(false); } UpdateProgress(NewList.IndexOf(frameInfo)); } } Directory.Delete(insertFolder, true); #endregion if (_isCancelled) { return(false); } #region Merge the lists if (after) { _insertIndex++; } //Saves the state before inserting the images. This was removed because it was causing a crash when applying undo twice. //ActionStack.SaveState(ActionStack.EditAction.Add, _insertIndex, NewList.Count); CurrentList.InsertRange(_insertIndex, NewList); #endregion return(true); } catch (Exception ex) { LogWriter.Log(ex, "Insert Error"); Dispatcher.Invoke(() => ErrorDialog.Ok("Insert Error", "Something Wrong Happened", ex.Message, ex)); return(false); } }