Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,8 @@ jobs:
backend:
- "macOS-x86_64"
- "macOS-arm64"
- "windows"
- "windows-x86_64"
- "windows-arm64"
- "linux-x11-gtk3"
- "linux-wayland-gtk3"
- "linux-wayland-gtk4"
Expand Down Expand Up @@ -489,11 +490,16 @@ jobs:
briefcase-run-args: --config 'requires=["toga-core", "toga-textual"]' --config 'console_app=true'
app-user-data-path: '$HOME\AppData\Local\Tiberius Yak\Toga Testbed\Data'

- backend: "windows"
- backend: "windows-x86_64"
platform: "windows"
runs-on: "windows-latest"
app-user-data-path: '$HOME\AppData\Local\Tiberius Yak\Toga Testbed\Data'

- backend: "windows-arm64"
platform: "windows"
runs-on: "windows-11-arm"
app-user-data-path: '$HOME\AppData\Local\Tiberius Yak\Toga Testbed\Data'

- backend: "iOS"
platform: "iOS"
runs-on: "macos-latest"
Expand Down
1 change: 1 addition & 0 deletions changes/2782.feature.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Toga's WinForms backend can now be used on ARM64 machines with a native ARM64 Python interpreter.
8 changes: 5 additions & 3 deletions docs/en/reference/platforms/windows.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,13 @@ The Toga backend for Windows is [`toga-winforms`](https://github.com/beeware/tog

`toga-winforms` requires Python 3.10+, and Windows 10 or newer.

/// note | Note
Toga requires the use of either .NET Framework 4.x, or .NET Core 10.

Toga uses the [Python.NET](https://pythonnet.github.io) library to access the underlying Winforms GUI toolkit on Windows. Unfortunately, Python.NET doesn't always keep up with the release schedule of Python itself, and as a result, may not be compatible with recently-released versions of Python (i.e., a Python release with a version number of 3.X.0 or 3.X.1). If you experience problems installing Toga, and you're using a recently-released version of Python, try downgrading to the previous minor release (e.g. 3.13.9 instead of 3.14.0).
If you're on an x86-64 machine, .NET Framework 4.x is installed by default on Windows 10 and 11. Toga will use .NET Core 10 if it is installed.

If you're using an ARM64 machine, and you're using a native ARM64 Python interpreter, you *must* use .NET Core 10. The [.NET Desktop Runtime can be downloaded from the .NET website](https://dotnet.microsoft.com/en-us/download/dotnet/10.0). If you're using an x86-64 interpreter on an ARM64 machine, Toga can use the .NET Framework install that is provided by default.

///
Toga uses the [Python.NET](https://pythonnet.github.io) library to access the underlying Winforms GUI toolkit on Windows. Unfortunately, Python.NET doesn't always keep up with the release schedule of Python itself, and as a result, may not be compatible with recently-released versions of Python (i.e., a Python release with a version number of 3.X.0 or 3.X.1). If you experience problems installing Toga, and you're using a recently-released version of Python, try downgrading to the previous minor release (e.g. 3.13.9 instead of 3.14.0).

If you are using Windows 10 and want to use a WebView to display web content, you will also need to install the [Edge WebView2 Evergreen Runtime.](https://developer.microsoft.com/en-us/microsoft-edge/webview2/#download) Windows 11 has this runtime installed by default.

Expand Down
61 changes: 61 additions & 0 deletions winforms/src/toga_winforms/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,58 @@
import platform
from pathlib import Path

import clr_loader
from pythonnet import set_runtime

try:
####################################################################################
# Toga Winforms requires the use of .NET; either .NET Framework 4.x, or .NET Core.
#
# .NET Framework 4.x is available by default on Windows 10 and 11. However, on
# Windows on ARM64, it is an x86-64 binary, so it can't be used by a native ARM64
# Python interpreter.
#
# However, it *can* be used if you have an x86-64 Python interpreter - which is what
# you get if you run `py install -3.13` or `py install -3.14`. This will apparently
# change with Python 3.15.
#
# Using .NET Core requires a separate install - but it will be present on a lot
# of systems.
#
# So - try to load .NET Core; if it succeeds, use it. If the load fails, fall back
# to .NET Framework. If we're on ARM64, check to see if the interpreter is running
# in emulation mode. If it is, we're OK; if we're not, stop the interpreter; the
# .NET gives instructions on how to install .NET
####################################################################################

# runtime.json defines the .NET version. .NET 10 is the current LTS release.
set_runtime(
clr_loader.get_coreclr(
runtime_config=Path(__file__).parent / "resources/runtime.json"
)
)

# .NET Core load succeeded
_use_dotnet_core = True
except (clr_loader.util.clr_error.ClrError, RuntimeError):
# .NET Core load failed.
if platform.machine() == "ARM64" and "ARM64" in platform.python_compiler():
# A native ARM64 machine running an ARM64 Python.
# .NET Framework 4.x isn't an option.
raise RuntimeError("""

On Windows, Toga requires .NET Core 10. Please visit:

https://dotnet.microsoft.com/en-us/download/dotnet/10.0

and install the .NET Desktop Runtime.""") from None
else:
# Either a native x86_64 machine, or an ARM64 machine with
# and x86_64 Python interpreter in emulation mode. We can
# use .NET Framework 4.x
_use_dotnet_core = False


import clr
import travertino

Expand All @@ -9,6 +64,12 @@
# Add a reference to the Winforms assembly
clr.AddReference("System.Windows.Forms")

# .NET Core requires some other explicit assemblies
if _use_dotnet_core:
clr.AddReference("Microsoft.Win32.SystemEvents")
clr.AddReference("System.Windows.Extensions")


# Add a reference to the WindowsBase assembly. This is needed to access
# System.Windows.Threading.Dispatcher.
#
Expand Down
15 changes: 15 additions & 0 deletions winforms/src/toga_winforms/resources/runtime.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"runtimeOptions": {
"tfm": "net10.0-windows",
"frameworks": [
{
"name": "Microsoft.NETCore.App",
"version": "10.0.0"
},
{
"name": "Microsoft.WindowsDesktop.App",
"version": "10.0.0"
}
]
}
}
Loading