From 3c491ad833cc966ade79873beb53a012a0a4fc3d Mon Sep 17 00:00:00 2001 From: Qiutong Shen Date: Thu, 21 May 2026 13:40:36 +0800 Subject: [PATCH] =?UTF-8?q?fix(develop):=20UWP=E2=86=92WinAppSDK=20link=20?= =?UTF-8?q?migration=20=E2=80=94=20win2d,=20migration=20guides=20&=20misc?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- hub/apps/develop/data/drag-and-drop.md | 52 +++++++++---------- .../develop/motion/storyboarded-animations.md | 6 +-- .../push-notifications/wns-overview.md | 2 +- .../win2d/choosing-control-resolution.md | 2 +- .../using-win2d-without-built-in-controls.md | 2 +- .../case-study-1.md | 2 +- .../case-study-2.md | 2 +- .../guides/threading.md | 2 +- .../guides/winui3.md | 2 +- 9 files changed, 36 insertions(+), 36 deletions(-) diff --git a/hub/apps/develop/data/drag-and-drop.md b/hub/apps/develop/data/drag-and-drop.md index 3d66a40297..0ec13676b4 100644 --- a/hub/apps/develop/data/drag-and-drop.md +++ b/hub/apps/develop/data/drag-and-drop.md @@ -11,7 +11,7 @@ ms.localizationpriority: medium Drag and drop is an intuitive way to transfer data within an application or between applications on the Windows desktop. Drag and drop lets the user transfer data between applications or within an application using a standard gesture (press-hold-and-pan with the finger or press-and-pan with a mouse or a stylus). -> **Important APIs**: [CanDrag property](/uwp/api/windows.ui.xaml.uielement.candrag), [AllowDrop property](/uwp/api/windows.ui.xaml.uielement.allowdrop) +> **Important APIs**: [CanDrag property](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.candrag), [AllowDrop property](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.allowdrop) The drag source, which is the application or area where the drag gesture is triggered, provides the data to be transferred by filling a data package object that can contain standard data formats, including text, RTF, HTML, bitmaps, storage items or custom data formats. The source also indicates the kind of operations it supports: copy, move or link. When the pointer is released, drop occurs. The drop target, which is the application or area underneath the pointer, processes the data package and returns the type of operation it performed. @@ -22,7 +22,7 @@ Drag and drop allows data transfer between or within any kind of application, in Here's an overview of what you need to do to enable drag and drop in your app: 1. Enable dragging on an element by setting its **CanDrag** property to true. -2. Build the data package. The system handles images and text automatically, but for other content, you'll need to handle the [**DragStarting**](/uwp/api/windows.ui.xaml.uielement.dragstarting) and [**DropCompleted**](/uwp/api/windows.ui.xaml.uielement.dropcompleted) events and use them to construct your own data package. +2. Build the data package. The system handles images and text automatically, but for other content, you'll need to handle the [**DragStarting**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dragstarting) and [**DropCompleted**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dropcompleted) events and use them to construct your own data package. 3. Enable dropping by setting the **AllowDrop** property to **true** on all the elements that can receive dropped content. 4. Handle the **DragOver** event to let the system know what type of drag operations the element can receive. 5. Process the **Drop** event to receive the dropped content. @@ -31,11 +31,11 @@ Here's an overview of what you need to do to enable drag and drop in your app: ## Enable dragging -To enable dragging on an element, set its [**CanDrag**](/uwp/api/windows.ui.xaml.uielement.candrag) property to **true**. This make the element—and the elements it contains, in the case of collections like ListView—draggable. +To enable dragging on an element, set its [**CanDrag**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.candrag) property to **true**. This make the element—and the elements it contains, in the case of collections like ListView—draggable. Be specific about what's draggable. Users won't want to drag everything in your app, only certain items, such as images or text. -Here's how to set [**CanDrag**](/uwp/api/windows.ui.xaml.uielement.candrag). +Here's how to set [**CanDrag**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.candrag). ```xaml @@ -49,11 +49,11 @@ In most cases, the system will construct a data package for you. The system auto - Images - Text -For other content, you'll need to handle the [**DragStarting**](/uwp/api/windows.ui.xaml.uielement.dragstarting) and [**DropCompleted**](/uwp/api/windows.ui.xaml.uielement.dropcompleted) events and use them to construct your own [DataPackage](/uwp/api/windows.applicationmodel.datatransfer.datapackage). +For other content, you'll need to handle the [**DragStarting**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dragstarting) and [**DropCompleted**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dropcompleted) events and use them to construct your own [DataPackage](/uwp/api/windows.applicationmodel.datatransfer.datapackage). ## Enable dropping -The following markup shows how the [**AllowDrop**](/uwp/api/windows.ui.xaml.uielement.allowdrop) property can be used to specify that an area of the app is a valid drop target for a dragged item (the specified area must not have a null background, it must be able to receive pointer input, and the item cannot be dropped anywhere other than the specified area). +The following markup shows how the [**AllowDrop**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.allowdrop) property can be used to specify that an area of the app is a valid drop target for a dragged item (the specified area must not have a null background, it must be able to receive pointer input, and the item cannot be dropped anywhere other than the specified area). > [!NOTE] > Typically, a UI element has a null background by default. If you want users to be able to drop an item anywhere within your app, the app background cannot be null (set `Background="Transparent"` if the background should not be visible). @@ -67,7 +67,7 @@ The following markup shows how the [**AllowDrop**](/uwp/api/windows.ui.xaml.uiel ## Handle the DragOver event -The [**DragOver**](/uwp/api/windows.ui.xaml.uielement.dragover) event fires when a user has dragged an item over your app, but not yet dropped it. In this handler, you need to specify what kind of operations your app supports by using the [**AcceptedOperation**](/uwp/api/windows.ui.xaml.drageventargs.acceptedoperation) property. Copy is the most common. +The [**DragOver**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dragover) event fires when a user has dragged an item over your app, but not yet dropped it. In this handler, you need to specify what kind of operations your app supports by using the [**AcceptedOperation**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.acceptedoperation) property. Copy is the most common. ```csharp private void Grid_DragOver(object sender, DragEventArgs e) @@ -78,7 +78,7 @@ private void Grid_DragOver(object sender, DragEventArgs e) ## Process the Drop event -The [**Drop**](/uwp/api/windows.ui.xaml.uielement.drop) event occurs when the user releases items in a valid drop area. Process them by using the [**DataView**](/uwp/api/windows.ui.xaml.drageventargs.dataview) property. +The [**Drop**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.drop) event occurs when the user releases items in a valid drop area. Process them by using the [**DataView**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.dataview) property. For simplicity in the example below, we'll assume the user dropped a single photo and access it directly. In reality, users can drop multiple items of varying formats simultaneously. Your app should handle this possibility by checking what types of files were dropped and how many there are, and process each accordingly. You should also consider notifying the user if they're trying to do something your app doesn't support. @@ -102,7 +102,7 @@ private async void Grid_Drop(object sender, DragEventArgs e) ## Customize the UI -The system provides a default UI for dragging and dropping. However, you can also choose to customize various parts of the UI by setting custom captions and glyphs, or by opting not to show a UI at all. To customize the UI, use the [**DragEventArgs.DragUIOverride**](/uwp/api/windows.ui.xaml.drageventargs.draguioverride) property. +The system provides a default UI for dragging and dropping. However, you can also choose to customize various parts of the UI by setting custom captions and glyphs, or by opting not to show a UI at all. To customize the UI, use the [**DragEventArgs.DragUIOverride**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.draguioverride) property. ```csharp private void Grid_DragOverCustomized(object sender, DragEventArgs e) @@ -121,7 +121,7 @@ private void Grid_DragOverCustomized(object sender, DragEventArgs e) ## Open a context menu on an item you can drag with touch -When using touch, dragging a [**UIElement**](/uwp/api/Windows.UI.Xaml.UIElement) and opening its context menu share similar touch gestures; each begins with a press and hold. Here's how the system disambiguates between the two actions for elements in your app that support both: +When using touch, dragging a [**UIElement**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement) and opening its context menu share similar touch gestures; each begins with a press and hold. Here's how the system disambiguates between the two actions for elements in your app that support both: - If a user presses and holds an item and begins dragging it within 500 milliseconds, the item is dragged and the context menu is not shown. - If the user presses and holds but does not drag within 500 milliseconds, the context menu is opened. @@ -129,37 +129,37 @@ When using touch, dragging a [**UIElement**](/uwp/api/Windows.UI.Xaml.UIElement) ## Designate an item in a ListView or GridView as a folder -You can specify a [**ListViewItem**](/uwp/api/Windows.UI.Xaml.Controls.ListViewItem) or [**GridViewItem**](/uwp/api/Windows.UI.Xaml.Controls.GridViewItem) as a folder. This is particularly useful for TreeView and File Explorer scenarios. To do so, explicitly set the [**AllowDrop**](/uwp/api/windows.ui.xaml.uielement.allowdrop) property to **True** on that item. +You can specify a [**ListViewItem**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.listviewitem) or [**GridViewItem**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.gridviewitem) as a folder. This is particularly useful for TreeView and File Explorer scenarios. To do so, explicitly set the [**AllowDrop**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.allowdrop) property to **True** on that item. -The system will automatically show the appropriate animations for dropping into a folder versus a non-folder item. Your app code must continue to handle the [**Drop**](/uwp/api/windows.ui.xaml.uielement.drop) event on the folder item (as well as on the non-folder item) in order to update the data source and add the dropped item to the target folder. +The system will automatically show the appropriate animations for dropping into a folder versus a non-folder item. Your app code must continue to handle the [**Drop**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.drop) event on the folder item (as well as on the non-folder item) in order to update the data source and add the dropped item to the target folder. ## Enable drag and drop reordering within ListViews -[**ListView**](/uwp/api/Windows.UI.Xaml.Controls.ListView)s support drag-based reordering out of the box, using an API very similar to the **CanDrop** API described in this article. At minimum, you add the **AllowDrop** and **CanReorderItems** properties. +[**ListView**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.listview)s support drag-based reordering out of the box, using an API very similar to the **CanDrop** API described in this article. At minimum, you add the **AllowDrop** and **CanReorderItems** properties. -See [**ListViewBase.CanReorderItems**](/uwp/api/windows.ui.xaml.controls.listviewbase.canreorderitems) for more information. +See [**ListViewBase.CanReorderItems**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.listviewbase.canreorderitems) for more information. ## Implementing custom drag and drop -The [UIElement](/uwp/api/windows.ui.xaml.uielement) class does most of the work of implementing drag-and-drop for you. But if you want, you can implement your own version by using the APIs below. +The [UIElement](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement) class does most of the work of implementing drag-and-drop for you. But if you want, you can implement your own version by using the APIs below. | Functionality | Windows App SDK
Microsoft.UI.Input.DragDrop namespace | | --- | --- | | DragPrimitive | [DragOperation](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.dragoperation) | | Create a data package | [DataPackage](/uwp/api/windows.applicationmodel.datatransfer.datapackage) | | Hand off drag to the shell |[DragOperation.StartAsync](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.dragoperation) | -| Receive drop from the shell | [DragDropManager.TargetRequested](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.dragdropmanager)
[ICoreDropOperationTarget](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.dragoperation) | +| Receive drop from the shell | [DragDropManager.TargetRequested](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.dragdropmanager)
[IDropOperationTarget](/windows/windows-app-sdk/api/winrt/microsoft.ui.input.dragdrop.idropoperationtarget) | ## See also - [App-to-app communication](../../design/input/index.md) -- [AllowDrop](/uwp/api/windows.ui.xaml.uielement.allowdrop) -- [CanDrag](/uwp/api/windows.ui.xaml.uielement.candrag) -- [DragOver](/uwp/api/windows.ui.xaml.uielement.dragover) -- [AcceptedOperation](/uwp/api/windows.ui.xaml.drageventargs.acceptedoperation) -- [DataView](/uwp/api/windows.ui.xaml.drageventargs.dataview) -- [DragUIOverride](/uwp/api/windows.ui.xaml.drageventargs.draguioverride) -- [Drop](/uwp/api/windows.ui.xaml.uielement.drop) -- [IsDragSource](/uwp/api/windows.ui.xaml.controls.listviewbase.isdragsource) -- [**DragStarting**](/uwp/api/windows.ui.xaml.uielement.dragstarting) -- [**DropCompleted**](/uwp/api/windows.ui.xaml.uielement.dropcompleted) +- [AllowDrop](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.allowdrop) +- [CanDrag](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.candrag) +- [DragOver](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dragover) +- [AcceptedOperation](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.acceptedoperation) +- [DataView](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.dataview) +- [DragUIOverride](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.drageventargs.draguioverride) +- [Drop](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.drop) +- [IsDragSource](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.listviewbase.isdragsource) +- [**DragStarting**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dragstarting) +- [**DropCompleted**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.uielement.dropcompleted) diff --git a/hub/apps/develop/motion/storyboarded-animations.md b/hub/apps/develop/motion/storyboarded-animations.md index bd7de7bb51..77a2b9c052 100644 --- a/hub/apps/develop/motion/storyboarded-animations.md +++ b/hub/apps/develop/motion/storyboarded-animations.md @@ -213,7 +213,7 @@ You also put your animations within a [**Storyboard**](/windows/windows-app-sdk/ ## Dependent and independent animations -At this point we need to introduce some important points about how the animation system works. In particular, animation interacts fundamentally with how a Windows Runtime app renders to the screen, and how that rendering uses processing threads. A Windows Runtime app always has a main UI thread, and this thread is responsible for updating the screen with current information. In addition, a Windows Runtime app has a composition thread, which is used for precalculating layouts immediately before they are shown. When you animate the UI, there's potential to cause a lot of work for the UI thread. The system must redraw large areas of the screen using fairly short time intervals between each refresh. This is necessary for capturing the latest property value of the animated property. If you're not careful, there's risk that an animation can make the UI less responsive, or will impact performance of other app features that are also on the same UI thread. +At this point we need to introduce some important points about how the animation system works. In particular, animation interacts fundamentally with how a WinUI 3 app renders to the screen, and how that rendering uses processing threads. A WinUI 3 app always has a main UI thread, and this thread is responsible for updating the screen with current information. In addition, a WinUI 3 app has a composition thread, which is used for precalculating layouts immediately before they are shown. When you animate the UI, there's potential to cause a lot of work for the UI thread. The system must redraw large areas of the screen using fairly short time intervals between each refresh. This is necessary for capturing the latest property value of the animated property. If you're not careful, there's risk that an animation can make the UI less responsive, or will impact performance of other app features that are also on the same UI thread. The variety of animation that is determined to have some risk of slowing down the UI thread is called a *dependent animation*. An animation not subject to this risk is an *independent animation*. The distinction between dependent and independent animations isn't just determined by animation types ([**DoubleAnimation**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.Media.Animation.DoubleAnimation) and so on) as we described earlier. Instead, it's determined by which specific properties you are animating, and other factors like inheritance and composition of controls. There are circumstances where even if an animation does change UI, the animation can have minimal impact to the UI thread, and can instead be handled by the composition thread as an independent animation. @@ -308,11 +308,11 @@ Up to now, we've shown the custom animations that are animating between two valu If you are familiar with Windows Presentation Foundation (WPF), read this section; otherwise, you can skip it. -In general, creating storyboarded animations in a Windows Runtime app is like WPF. But there are a number of important differences: +In general, creating storyboarded animations in a WinUI 3 app is like WPF. But there are a number of important differences: - Storyboarded animations are not the only way to visually animate a UI, nor are they necessarily the easiest way for app developers to do so. Rather than using storyboarded animations it's often a better design practice to use theme animations and transition animations. These can quickly create recommended UI animations without getting into the intricacies of animation property targeting. For more info see [Animations in XAML](xaml-animation.md). - In the Windows Runtime, many XAML controls include theme animations and transition animations as part of their built-in behavior. For the most part, WPF controls didn't have a default animation behavior. -- Not all custom animations you create can run by default in a Windows Runtime app, if the animation system determines that the animation might cause bad performance in your UI. Animations where the system determines there could be a performance impact are called *dependent animations*. It's dependent because the clocking of your animation is directly working against the UI thread, which is also where active user input and other updates are trying to apply the runtime changes to UI. A dependent animation that's consuming extensive system resources on the UI thread can make the app appear unresponsive in certain situations. If your animation causes a layout change or otherwise has the potential to impact performance on the UI thread, you often need to explicitly enable the animation to see it run. That's what the **EnableDependentAnimation** property on specific animation classes is for. See [Dependent and independent animations](./storyboarded-animations.md#dependent-and-independent-animations) for more info. +- Not all custom animations you create can run by default in a WinUI 3 app, if the animation system determines that the animation might cause bad performance in your UI. Animations where the system determines there could be a performance impact are called *dependent animations*. It's dependent because the clocking of your animation is directly working against the UI thread, which is also where active user input and other updates are trying to apply the runtime changes to UI. A dependent animation that's consuming extensive system resources on the UI thread can make the app appear unresponsive in certain situations. If your animation causes a layout change or otherwise has the potential to impact performance on the UI thread, you often need to explicitly enable the animation to see it run. That's what the **EnableDependentAnimation** property on specific animation classes is for. See [Dependent and independent animations](./storyboarded-animations.md#dependent-and-independent-animations) for more info. - Custom easing functions are not currently supported in the Windows Runtime. ## Related topics diff --git a/hub/apps/develop/notifications/push-notifications/wns-overview.md b/hub/apps/develop/notifications/push-notifications/wns-overview.md index c2e6559c70..986913c287 100644 --- a/hub/apps/develop/notifications/push-notifications/wns-overview.md +++ b/hub/apps/develop/notifications/push-notifications/wns-overview.md @@ -226,7 +226,7 @@ using namespace winrt::Windows::System; using namespace winrt::Windows::System::Power; using namespace winrt::Microsoft::UI::Xaml; using namespace winrt::Microsoft::UI::Xaml::Controls; -using namespace winrt::Windows::UI::Xaml::Navigation; +using namespace winrt::Microsoft::UI::Xaml::Navigation; ... winrt::fire_and_forget CheckForEnergySaving() { diff --git a/hub/apps/develop/win2d/choosing-control-resolution.md b/hub/apps/develop/win2d/choosing-control-resolution.md index 47a6b47760..455454aaf8 100644 --- a/hub/apps/develop/win2d/choosing-control-resolution.md +++ b/hub/apps/develop/win2d/choosing-control-resolution.md @@ -41,7 +41,7 @@ This scenario may arise, for instance, on a 2D sprite game that should always re Solving this doesn't strictly require writing any new Win2D code at all. -The [`Viewbox`](/uwp/api/Windows.UI.Xaml.Controls.Viewbox) XAML object lets you constrain the sizes of its child visual elements, automatically adding scaling, with letterboxing or pillarboxing to preserve aspect ratios as necessary. +The [`Viewbox`](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.viewbox) XAML object lets you constrain the sizes of its child visual elements, automatically adding scaling, with letterboxing or pillarboxing to preserve aspect ratios as necessary. Simply ensure your `CanvasControl`, `CanvasVirtualControl` or `CanvasAnimatedControl` is a child element of a `ViewBox`, and restrict the size of that control. diff --git a/hub/apps/develop/win2d/using-win2d-without-built-in-controls.md b/hub/apps/develop/win2d/using-win2d-without-built-in-controls.md index fdc8be0a55..e20f4e7e39 100644 --- a/hub/apps/develop/win2d/using-win2d-without-built-in-controls.md +++ b/hub/apps/develop/win2d/using-win2d-without-built-in-controls.md @@ -107,7 +107,7 @@ The application decides on the frequency of redrawing. In the same manner as usi ```csharp canvasSwapChainPanel.SizeChanged += canvasSwapChainPanel_SizeChanged; -void canvasSwapChainPanel_SizeChanged(object sender, Windows.UI.Xaml.SizeChangedEventArgs e) +void canvasSwapChainPanel_SizeChanged(object sender, Microsoft.UI.Xaml.SizeChangedEventArgs e) { canvasSwapChainPanel.SwapChain.ResizeBuffers(e.NewSize); } diff --git a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-1.md b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-1.md index bb447e3ded..f58e13aacf 100644 --- a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-1.md +++ b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-1.md @@ -127,7 +127,7 @@ public partial class App : Application ## Migrate the LoadedImageBrush model -**LoadedImageBrush** is a specialization of [**XamlCompositionBrushBase**](/uwp/api/windows.ui.xaml.media.xamlcompositionbrushbase). The *PhotoLab* sample app uses the **LoadedImageBrush** class to apply effects to photos. +**LoadedImageBrush** is a specialization of [**XamlCompositionBrushBase**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.media.xamlcompositionbrushbase). The *PhotoLab* sample app uses the **LoadedImageBrush** class to apply effects to photos. ### Reference the Win2D NuGet package diff --git a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-2.md b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-2.md index e1c2eea9a7..3a659feb3a 100644 --- a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-2.md +++ b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/case-study-2.md @@ -324,7 +324,7 @@ The two changes in this section are necessary due to a threading model differenc ### MainPage -**MainPage** loads image files from your **Pictures** folder, calls [**StorageItemContentProperties.GetImagePropertiesAsync**](/uwp/api/windows.storage.fileproperties.storageitemcontentproperties.getimagepropertiesasync) to get the image file's properties, creates a **Photo** model object for each image file (saving those same properties in a data member), and adds that **Photo** object to a collection. The collection of **Photo** objects is data-bound to a **GridView** in the UI. On behalf of that **GridView**, **MainPage** handles the [**ContainerContentChanging**](/uwp/api/windows.ui.xaml.controls.listviewbase.containercontentchanging) event, and for phase 1 that handler calls into a coroutine that calls [**StorageFile.GetThumbnailAsync**](/uwp/api/windows.storage.storagefile.getthumbnailasync). This call to **GetThumbnailAsync** results in messages being pumped (it doesn't return immediately, and do *all* of its work async), and that causes reentrancy. The result is that the **GridView** has its **Items** collection changed while layout is taking place, and that causes a crash. +**MainPage** loads image files from your **Pictures** folder, calls [**StorageItemContentProperties.GetImagePropertiesAsync**](/uwp/api/windows.storage.fileproperties.storageitemcontentproperties.getimagepropertiesasync) to get the image file's properties, creates a **Photo** model object for each image file (saving those same properties in a data member), and adds that **Photo** object to a collection. The collection of **Photo** objects is data-bound to a **GridView** in the UI. On behalf of that **GridView**, **MainPage** handles the [**ContainerContentChanging**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.listviewbase.containercontentchanging) event, and for phase 1 that handler calls into a coroutine that calls [**StorageFile.GetThumbnailAsync**](/uwp/api/windows.storage.storagefile.getthumbnailasync). This call to **GetThumbnailAsync** results in messages being pumped (it doesn't return immediately, and do *all* of its work async), and that causes reentrancy. The result is that the **GridView** has its **Items** collection changed while layout is taking place, and that causes a crash. If we comment out the call to **StorageItemContentProperties::GetImagePropertiesAsync**, then we don't get the crash. But the real fix is to make the **StorageFile.GetThumbnailAsync** call be explicitly async by cooperatively awaiting **wil::resume_foreground** immediately before calling **GetThumbnailAsync**. This works because **wil::resume_foreground** schedules the code that follows it to be a task on the **DispatcherQueue**. diff --git a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/threading.md b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/threading.md index f760d60216..3dfd34284c 100644 --- a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/threading.md +++ b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/threading.md @@ -123,7 +123,7 @@ void MainPage::NotifyUser(std::wstring strMessage) } ``` -In your Windows App SDK app, use the [Microsoft.UI.Dispatching.DispatcherQueue.TryEnqueue](/windows/windows-app-sdk/api/winrt/microsoft.ui.dispatching.dispatcherqueue.tryenqueue)) method instead. It adds to the [**Microsoft.UI.Dispatching.DispatcherQueue**](/windows/windows-app-sdk/api/winrt/microsoft.ui.dispatching.dispatcherqueue) a task that will be executed on the thread associated with the **DispatcherQueue**. +In your Windows App SDK app, use the [Microsoft.UI.Dispatching.DispatcherQueue.TryEnqueue](/windows/windows-app-sdk/api/winrt/microsoft.ui.dispatching.dispatcherqueue.tryenqueue) method instead. It adds to the [**Microsoft.UI.Dispatching.DispatcherQueue**](/windows/windows-app-sdk/api/winrt/microsoft.ui.dispatching.dispatcherqueue) a task that will be executed on the thread associated with the **DispatcherQueue**. ```csharp // MainPage.xaml.cs in a Windows App SDK app diff --git a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/winui3.md b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/winui3.md index ede9b53a82..3751c234d0 100644 --- a/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/winui3.md +++ b/hub/apps/windows-app-sdk/migrate-to-windows-app-sdk/guides/winui3.md @@ -93,7 +93,7 @@ In your UWP app, if you use certain types from the [**Windows.UI.Popups**](/uwp/ The steps that you have to follow in a desktop app are described in [Display WinRT UI objects that depend on CoreWindow](../../../develop/ui-input/display-ui-objects.md). > [!NOTE] -> For new apps, we recommend using the [**ContentDialog**](/uwp/api/windows.ui.xaml.controls.contentdialog) control instead of [**MessageDialog**](/uwp/api/windows.ui.popups.messagedialog). For more info, see the [ContentDialog, and Popup](#contentdialog-and-popup) section below. +> For new apps, we recommend using the [**ContentDialog**](/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.controls.contentdialog) control instead of [**MessageDialog**](/uwp/api/windows.ui.popups.messagedialog). For more info, see the [ContentDialog, and Popup](#contentdialog-and-popup) section below. Here's some typical UWP code to display a [**MessageDialog**](/uwp/api/windows.ui.popups.messagedialog).