dotnet / docs-maui

This repository contains documentation for .NET Multi-platform App UI (MAUI).
https://docs.microsoft.com/dotnet/maui
Creative Commons Attribution 4.0 International
216 stars 185 forks source link

Example code does not work / compile #2298

Closed Tandry closed 1 week ago

Tandry commented 1 month ago

Type of issue

Code doesn't work

Description

[Enter feedback here] AbsoluteLayout.Add(new BoxView // I've replaced AbsoluteLayout with my own element, but that's not the problem { Color = Colors.Silver }, new Rect(0, 10, 200, 5)); does not compile or run. "CS1501: No overload for method 'Add' takes 2 arguments."

Suggestion: Rather than packing a bunch of statements with implied but not explicit functionality into terse code, it would be FAR more helpful to understand (and see in an example) exactly what elements are being assigned to. Does the rect correspond to AnchorX, AnchorY? There's no way to make heads or tails out of the "equivalent" XAML here. The XAML example tells you explicitly what is being assigned to:

However if I try to do: Rect r = new Rect(0, 10, 200, 15); AbsoluteLayout.LayoutBounds(r); // CS1061: Boxview does not contain a definition for LayoutBounds...

This is VERY frustrating when: a) The official documentation example does not work and b) The naming convention between XAML and the "corresponding" methods don't align and c) Reasonable guesses (which should never be needed in the first place) don't work 

[editing to add this] Here's what DID eventually work: BoxView goldBoxView = new BoxView { Color = Colors.Gold, }; DrawingCanvas.Add(goldBoxView); // DrawingCanvas is my XAML AbsoluteLayout element. Rect r = new Rect(0, 10, 200, 5); DrawingCanvas.SetLayoutBounds(goldBoxView, r); goldBoxView.GestureRecognizers.Add(pointerGestureRecognizer); // Playing around with pointer detection as I learn

        BoxView silverBoxView = new BoxView
        {
            Color = Colors.Silver,
        };
        DrawingCanvas.Add(silverBoxView);
        r = new Rect(0, 20, 200, 5);
        DrawingCanvas.SetLayoutBounds(silverBoxView, r);

        BoxView brownBoxView = new BoxView
        {
            Color = Colors.Brown,
        };
        DrawingCanvas.Add(brownBoxView);
        r = new Rect(10, 0, 5, 65);
        DrawingCanvas.SetLayoutBounds(brownBoxView, r);

        BoxView greenBoxView = new BoxView
        {
            Color = Colors.Green,
        };
        DrawingCanvas.Add(greenBoxView);
        r = new Rect(20, 0, 5, 65);
        DrawingCanvas.SetLayoutBounds(greenBoxView, r);
        greenBoxView.GestureRecognizers.Add(pointerGestureRecognizer);

        BoxView purpleBox = new BoxView
        {
            Color = Colors.Purple,
        };
        DrawingCanvas.Add(purpleBox);
        r = new Rect(100,100,100,100);
        DrawingCanvas.SetLayoutBounds(purpleBox, r);
        purpleBox.GestureRecognizers.Add(pointerGestureRecognizer);

        Label headerLabel = new Label
        {
            TextColor = Colors.Red,
            Text="Stylish Header Demo",
            FontSize=24,
        };
        DrawingCanvas.Add(headerLabel);
        r = new Rect(30, 25, AbsoluteLayout.AutoSize, AbsoluteLayout.AutoSize);
        DrawingCanvas.SetLayoutBounds(headerLabel, r);

Page URL

https://learn.microsoft.com/en-us/dotnet/maui/user-interface/layouts/absolutelayout?view=net-maui-8.0

Content source URL

https://github.com/dotnet/docs-maui/blob/main/docs/user-interface/layouts/absolutelayout.md

Document Version Independent Id

d8aac004-9823-8211-3e9d-aefe7d9c4d95

Article author

@davidbritch

Metadata

  • ID: d8aac004-9823-8211-3e9d-aefe7d9c4d95
  • Service: dotnet-mobile
  • Sub-service: dotnet-maui
davidbritch commented 1 month ago

Hi @Tandry

If you read the paragraph after the code example you've cited, you'll read: "The C# example uses the following Add extension methods to add children to the AbsoluteLayout:" followed by the extension methods you require. Then the code will work.

Tandry commented 1 month ago

I provided working code. .Add does not take two arguments: CS1501: No overload for method 'Add' takes 2 arguments. The corrected code replaces

       absoluteLayout.Add(new BoxView
        {
            Color = Colors.Silver
        }, new Rect(0, 10, 200, 5));

with

BoxView bv = new BoxView { Color = Colors.Silver };
absoluteLayout.Add(bv);
Canvas.SetLayoutBounds(bv, new Rect(0, 10, 200, 5));
davidbritch commented 1 month ago

HI @Tandry

Yes, I get that your code works. But the code in the doc also works, via an Add extension method that does take two arguments. The Add extension method is in the doc, and in the sample the doc links to.

Tandry commented 1 month ago

David, Let's consider the use case of someone new to MAUI who is unfamiliar with its internal workings. That person, my earlier self in this case, is going to expect Microsoft's code to compile as provided. It would be one thing to say, "Here's some code that does the trick - but be aware that it needs this extension in order to work." and THEN provide the code, but that warning is not up front. Instead, the documentation states, "The equivalent C# code is shown below" and a block of code is provided with a copy button. It's natural for that newbie to assume that code works without further reading or inclusion of subsequent blocks of code.

I highly recommend that the documentation support the use case which comes naturally to this user, without modifying or extending "stock" methods on standard objects. What if, for whatever reason, I don't wish to extend .Add()? For one thing, for fear of ripple effects or repercussions down the road since that person is brand new and clueless as to what ripple effects those may be. A best practice here is to provide code that, without extending the objects or adding any functionality - especially completely unnecessary extensions - does the trick. Alas, the simpler example is present - it's in the proportional example near the bottom of the documentation but even that is not called out as different - we get the same "The equivalent C# code is shown below".

Speaking only for my own case, I was not interested in proportional layouts, so I did not look at that example. I was interested in "absolute" and my reasonable expectation was that I could tap that "copy" button so conveniently provided and paste the code into my work, make the needed changes to variable names and...oh..crap...this doesn't compile. This left me to pursue a 2 to 3 hour goose chase through dozens of seemingly applicable but half-decade old Xamarin questions in StackOverflow. If only I could bill Microsoft for my wasted time!

Documentation needs to serve the customer and the customer's use case here is to learn MAUI. The flow of that documentation can strongly affect the customer's frustration level (don't get me started on the reams of pages which are supposed to "document" feature X and all they do is say, "Feature X provides functionality X" - without ever saying what the (&#%(&#% the bloody thing is intended to be used for! This is a struggle I gave up on during my 8 years as a blue badge FTE at Microsoft. But I digress.

As a new learner, I would highly recommend providing the simplest, guaranteed to work solution first, without embellishment and the litmus test for that is "does the copy button provide the ability to splice this code into VS and guarantee working functionality without alterations beyond basic variable name alignment". I've been writing in C# for decades, so lack of knowledge of the language is not the problem.

Once a student understands what's needed - in this case, create the Control, Add the Control to the Layout and THEN set the position - in that order - THEN they can understand how to bend the rules. It turns out that in my case, the presented solution with the extension was not viable either because I'm adding a PointerGestureRecognizer to the BoxView, so I need to capture the return from that constructor. So again, the simple solution is the only one that worked in the long run.

I dearly hope that the team decides to align the documentation around reasonable and expected use cases by those who are clueless enough (such as my earlier self) to need to go to the documentation in the first place.

Cheers,

Steve

davidbritch commented 1 month ago

Hi Steve,

The Add extension method wasn't thrown in for the hell of it. In Xamarin.Forms it was baked into framework and was the preferred way to add to an AbsoluteLayout from C#. But then the extension method was left out of .NET MAUI which means that everyone migrating their apps from Xamarin.Forms to .NET MAUI receive a lot of build errors. Hence making that doc use the extension method, so that when Xamarin.Forms user google AbsoluteLayout, they find the solution to their problems.

We'd love to be so well resourced that we can have docs for users coming to .NET MAUI from Xamarin.Forms, and users who are brand new to .NET MAUI, but that just isn't the case.