dotnet/wpf · error · InvalidOperationException

SR.Visual_CannotTransformPoint

Error message

SR.Visual_CannotTransformPoint

What it means

Visual.PointToScreen throws InvalidOperationException(SR.Visual_CannotTransformPoint) when the GeneralTransform produced by TransformToAncestor(RootVisual) is null or TryTransform fails, i.e. the point could not be mapped from the visual's coordinates to root-visual coordinates.

Solutions

  1. Ensure ancestor transforms are invertible (non-zero scale, valid matrix) at the time of the call
  2. Retry the conversion after transforms/animations settle
  3. Prefer PointToClient/point mapping via TryTransform with a fallback when transforms are transiently degenerate

Example fix

// before
scaleTransform.ScaleX = 0; // degenerate
var pt = inner.PointToScreen(new Point(1, 1)); // throws
// after
scaleTransform.ScaleX = 1; // keep transforms non-degenerate
var pt = inner.PointToScreen(new Point(1, 1));
Defensive patterns

Strategy: try-catch

Validate before calling

var g = visual.TransformToAncestor(root); if (g == null || !g.TryTransform(point, out _)) return; // degenerate transform

Type guard

bool CanTransformPoint(Visual v, Point p) { var src = PresentationSource.FromVisual(v); if (src == null) return false; var g = v.TransformToAncestor(src.RootVisual); return g != null && g.TryTransform(p, out _); }

Try / catch

try { var p = visual.PointToScreen(point); } catch (InvalidOperationException) { /* transform degenerate; retry after layout settles */ }

Prevention

When it happens

Trigger: TransformToAncestor returns a transform that cannot invert/apply for the given point (e.g. singular/degenerate transforms from scale 0 or extreme animations), so TryTransform returns false.

Common situations: Elements under an active degenerate ScaleTransform/MatrixTransform (zero scale); transforms mid-animation producing non-invertible matrices.

Related errors


AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14). Data as JSON: /api/errors/ca68069aafe0e0c5. Report an issue: GitHub.

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/PresentationCore/System/Windows/Media/Visual.cs:4730

        /// This method converts a point in the current Visual's coordinate
        /// system into a point in screen coordinates.
        /// </summary>
        public Point PointToScreen(Point point)
        {
            VerifyAPIReadOnly();

            PresentationSource inputSource = PresentationSource.FromVisual(this);

            if (inputSource == null)
            {
                throw new InvalidOperationException(SR.Visual_NoPresentationSource);
            }

            // Translate the point from the visual to the root.
            GeneralTransform gUp = this.TransformToAncestor(inputSource.RootVisual);
            if (gUp == null || !gUp.TryTransform(point, out point))
            {
                throw new InvalidOperationException(SR.Visual_CannotTransformPoint);
            }

            // Translate the point from the root to the screen
            point = PointUtil.RootToClient(point, inputSource);
            point = PointUtil.ClientToScreen(point, inputSource);

            return point;
        }

        /// <summary>
        /// This method converts a point in screen coordinates into a point
        /// in the current Visual's coordinate system.
        /// </summary>
        public Point PointFromScreen(Point point)
        {
            VerifyAPIReadOnly();

            PresentationSource inputSource = PresentationSource.FromVisual(this);

View on GitHub (pinned to 81131a70a4)