@@ -44,6 +44,8 @@ public class InfiniteCanvasViewModel : BaseCanvasViewModel
4444 {
4545 #region Private Members
4646
47+ private bool _isPasting ;
48+
4749 private CanvasItem ? _lastPastedItem ;
4850
4951 private FilesystemChangeWatcher2 _filesystemChangeWatcher ;
@@ -98,120 +100,136 @@ public InfiniteCanvasViewModel(IBaseCanvasPreviewControlView view, BaseContentTy
98100 public override async Task < SafeWrapperResult > TryPasteData ( DataPackageView dataPackage , CancellationToken cancellationToken )
99101 {
100102 _lastPastedItem = null ;
103+ _isPasting = true ;
101104 this . cancellationToken = cancellationToken ;
102105 SafeWrapperResult fetchDataToViewResult = SafeWrapperResult . SUCCESS ;
103106
104- RaiseOnPasteInitiatedEvent ( this , new PasteInitiatedEventArgs ( false , null , ContentType , AssociatedCollection ) ) ;
105-
106- // First, set Infinite Canvas folder
107- SafeWrapperResult initializeInfiniteCanvasFolderResult = await InitializeInfiniteCanvasFolder ( ) ;
108- if ( ! AssertNoError ( initializeInfiniteCanvasFolderResult ) ) // Default AssertNoError
109- {
110- return initializeInfiniteCanvasFolderResult ;
111- }
112-
113- if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
107+ try
114108 {
115- DiscardData ( ) ;
116- return SafeWrapperResult . CANCEL ;
117- }
118-
119- // Get content type from data package
120- BaseContentTypeModel pastedItemContentType = await BaseContentTypeModel . GetContentTypeFromDataPackage ( dataPackage ) ;
109+ RaiseOnPasteInitiatedEvent ( this ,
110+ new PasteInitiatedEventArgs ( false , null , ContentType , AssociatedCollection ) ) ;
121111
122- if ( pastedItemContentType is InvalidContentTypeDataModel invalidContentType )
123- {
124- if ( invalidContentType . error == ( OperationErrorCode . InvalidOperation | OperationErrorCode . NotAFile ) )
125- {
126- // This error code means user tried pasting a folder with Reference Files setting *disabled*
127- AssertNoErrorInfiniteCanvas ( invalidContentType . error ) ; // Only for notification
128- }
129- else
112+ // First, set Infinite Canvas folder
113+ SafeWrapperResult initializeInfiniteCanvasFolderResult = await InitializeInfiniteCanvasFolder ( ) ;
114+ if ( ! AssertNoError ( initializeInfiniteCanvasFolderResult ) ) // Default AssertNoError
130115 {
131- return invalidContentType . error ;
116+ return initializeInfiniteCanvasFolderResult ;
132117 }
133- }
134- else
135- {
136- // Get correct IPasteModel from contentType
137- IPasteModel canvasPasteModel = CanvasHelpers . GetPasteModelFromContentType ( pastedItemContentType , _infiniteCanvasFileReceiver , new StatusCenterOperationReceiver ( ) ) ;
138118
139119 if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
140120 {
141121 DiscardData ( ) ;
142122 return SafeWrapperResult . CANCEL ;
143123 }
144124
145- if ( canvasPasteModel == null )
125+ // Get content type from data package
126+ BaseContentTypeModel pastedItemContentType =
127+ await BaseContentTypeModel . GetContentTypeFromDataPackage ( dataPackage ) ;
128+
129+ if ( pastedItemContentType is InvalidContentTypeDataModel invalidContentType )
146130 {
147- return BaseContentTypeModel . CannotDisplayContentForTypeResult ;
131+ if ( invalidContentType . error == ( OperationErrorCode . InvalidOperation | OperationErrorCode . NotAFile ) )
132+ {
133+ // This error code means user tried pasting a folder with Reference Files setting *disabled*
134+ AssertNoErrorInfiniteCanvas ( invalidContentType . error ) ; // Only for notification
135+ }
136+ else
137+ {
138+ return invalidContentType . error ;
139+ }
148140 }
141+ else
142+ {
143+ // Get correct IPasteModel from contentType
144+ IPasteModel canvasPasteModel = CanvasHelpers . GetPasteModelFromContentType ( pastedItemContentType ,
145+ _infiniteCanvasFileReceiver , new StatusCenterOperationReceiver ( ) ) ;
146+
147+ if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
148+ {
149+ DiscardData ( ) ;
150+ return SafeWrapperResult . CANCEL ;
151+ }
149152
150- // Paste data
151- SafeWrapper < CanvasItem > pastedItem = await canvasPasteModel . PasteData ( dataPackage , UserSettings . AlwaysPasteFilesAsReference , cancellationToken ) ;
152- _lastPastedItem = pastedItem . Result ;
153+ if ( canvasPasteModel == null )
154+ {
155+ return BaseContentTypeModel . CannotDisplayContentForTypeResult ;
156+ }
153157
154- // We don't need IPasteModel anymore, so dispose it
155- canvasPasteModel . Dispose ( ) ;
158+ // Paste data
159+ SafeWrapper < CanvasItem > pastedItem = await canvasPasteModel . PasteData ( dataPackage ,
160+ UserSettings . AlwaysPasteFilesAsReference , cancellationToken ) ;
161+ _lastPastedItem = pastedItem . Result ;
156162
157- if ( ! pastedItem )
158- {
159- return pastedItem ;
160- }
163+ // We don't need IPasteModel anymore, so dispose it
164+ canvasPasteModel . Dispose ( ) ;
161165
162- // Add new object to Infinite Canvas
163- var interactableCanvasControlItem = await InteractableCanvasControlModel . AddItem ( AssociatedCollection , pastedItemContentType , pastedItem , _infiniteCanvasFileReceiver , cancellationToken ) ;
166+ if ( ! pastedItem )
167+ {
168+ return pastedItem ;
169+ }
170+
171+ // Add new object to Infinite Canvas
172+ var interactableCanvasControlItem = await InteractableCanvasControlModel . AddItem (
173+ AssociatedCollection , pastedItemContentType , pastedItem , _infiniteCanvasFileReceiver ,
174+ cancellationToken ) ;
175+
176+ if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
177+ {
178+ DiscardData ( ) ;
179+ return SafeWrapperResult . CANCEL ;
180+ }
181+
182+ // Wait for control to load
183+ await Task . Delay ( Constants . UI . CONTROL_LOAD_DELAY ) ;
184+
185+ // Update item position based on datapackage
186+ InteractableCanvasControlModel . UpdateItemPositionFromDataPackage ( dataPackage ,
187+ interactableCanvasControlItem ) ;
188+
189+ // Save data after pasting
190+ SafeWrapperResult saveDataResult = await SaveConfigurationModel ( ) ;
191+
192+ // Notify paste succeeded
193+ await OnPasteSucceeded ( pastedItem ) ;
194+
195+ if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
196+ {
197+ DiscardData ( ) ;
198+ return SafeWrapperResult . CANCEL ;
199+ }
200+
201+ AssertNoErrorInfiniteCanvas ( saveDataResult ) ; // Only for notification
202+
203+ // Fetch data to view
204+ fetchDataToViewResult = await interactableCanvasControlItem . LoadContent ( ) ;
205+ }
164206
165207 if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
166208 {
167209 DiscardData ( ) ;
168210 return SafeWrapperResult . CANCEL ;
169211 }
170212
171- // Wait for control to load
172- await Task . Delay ( Constants . UI . CONTROL_LOAD_DELAY ) ;
173-
174- // Update item position based on datapackage
175- InteractableCanvasControlModel . UpdateItemPositionFromDataPackage ( dataPackage , interactableCanvasControlItem ) ;
176-
177- // Save data after pasting
178- SafeWrapperResult saveDataResult = await SaveConfigurationModel ( ) ;
179-
180- // Notify paste succeeded
181- await OnPasteSucceeded ( pastedItem ) ;
213+ // Start filesystem change tracker
214+ await StartFilesystemChangeWatcher ( ( await InfiniteCanvasItem . SourceItem ) as StorageFolder ) ;
182215
183216 if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
184217 {
185218 DiscardData ( ) ;
186219 return SafeWrapperResult . CANCEL ;
187220 }
188221
189- AssertNoErrorInfiniteCanvas ( saveDataResult ) ; // Only for notification
222+ RefreshContextMenuItems ( ) ;
190223
191- // Fetch data to view
192- fetchDataToViewResult = await interactableCanvasControlItem . LoadContent ( ) ;
193- }
224+ RaiseOnContentLoadedEvent ( this ,
225+ new ContentLoadedEventArgs ( pastedItemContentType , false , false , CanPasteReference ) ) ;
194226
195- if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
196- {
197- DiscardData ( ) ;
198- return SafeWrapperResult . CANCEL ;
227+ return fetchDataToViewResult ;
199228 }
200-
201- // Start filesystem change tracker
202- await StartFilesystemChangeWatcher ( ( await InfiniteCanvasItem . SourceItem ) as StorageFolder ) ;
203-
204- if ( cancellationToken . IsCancellationRequested ) // Check if it's canceled
229+ finally
205230 {
206- DiscardData ( ) ;
207- return SafeWrapperResult . CANCEL ;
231+ _isPasting = false ;
208232 }
209-
210- RefreshContextMenuItems ( ) ;
211-
212- RaiseOnContentLoadedEvent ( this , new ContentLoadedEventArgs ( pastedItemContentType , false , false , CanPasteReference ) ) ;
213-
214- return fetchDataToViewResult ;
215233 }
216234
217235 public override async Task < SafeWrapperResult > TryLoadExistingData ( CanvasItem canvasItem , BaseContentTypeModel contentType , CancellationToken cancellationToken )
@@ -494,9 +512,7 @@ await MainWindow.Instance.DispatcherQueue.EnqueueAsync(async () =>
494512 {
495513 case WatcherChangeTypes . Created :
496514 {
497- if ( changedItem == null ||
498- InteractableCanvasControlModel . ContainsItem (
499- InteractableCanvasControlModel . FindItem ( changedItem . Path ) ) )
515+ if ( changedItem == null || _isPasting || InteractableCanvasControlModel . FindItem ( changedItem . Path ) is not null )
500516 {
501517 return ;
502518 }
0 commit comments