Maui: [Spec] Slim Renderer 架构

创建于 2020-05-19  ·  56评论  ·  资料来源: dotnet/maui

警告:这个规范仍然是一个 WIP,我们仍在试验这个概念

描述

Slim 渲染器架构受益于多目标和单项目功能。

例子

入口渲染器.cs

public partial class EntryRenderer {
   public static PropertyMapper<IView> ViewMapper = new PropertyMapper<IView> {

     // Add your own method to map to any property         
     [nameof(IView.BackgroundColor)] = MapBackgroundColor

   };
}

入口渲染器.iOS.cs

// You don’t need to register a new renderer.
public partial class EntryRenderer
{
     // You know what method to call because you named it!
   public static void MapBackgroundColor (IViewRenderer renderer, IView view)
     {
        // You don’t need to call any base methods here or worry about order.

        // Every renderer is consistent; you know where the native view is.
          var nativeView = (NativeView)renderer.NativeView;
          var color = view.BackgroundColor;

          if (color != null) {

            // Phew! That was easy!         
            nativeView.BackgroundColor = UIColor.FromRGB (204, 153, 255);
          }
     }
}

渲染器的标准化

所有默认渲染器都将移植到此架构,适用于所有平台

渲染器的注册

rendererRegistrar 将存在于依赖服务上并由serviceCollection.Get<IRendererRegistrar>() ,允许控制哪个渲染器关联到哪个控件

渲染器接口

映射器概念

属性映射器负责触发响应属性更改的操作。 纤薄渲染器本身不订阅属性更改,但会执行一些声明的操作以响应更改。

控件的属性映射器属性为public static ,可以通过用户代码进行扩展。

属性映射器在反馈循环中不起作用(单击按钮,输入文本)

TODO:讨论映射器键的用途。 stringobject ? 如果我们可以比较引用(在 BindableProperties 的情况下),最好避免字符串比较

如何使用旧版自定义渲染器

如何根据旧渲染器使用第三方控件

如何补充现有的渲染器

此架构的新可扩展性模型基于属性映射器。 当您要添加对新属性的支持时,只需要映射新属性。 为了使属性存在,子类化控件是必要的,但子类化渲染器不是。

向后兼容

我们是否要保持与现有自定义渲染器的向后兼容性,或者旧渲染器的子类将影响此架构

难度:非常高

proposal-open slim renderer

最有用的评论

请不要试图不惜一切代价保持向后兼容。 这是新的东西。 它不必与 XF 兼容。 你可以做出更好的东西。

所有56条评论

Xamarin 形式的 wpf 渲染器和一些 android 渲染器如 ButtonRenderer 是快速的,我们知道这里的“快速”是什么意思。
这些渲染器会很快吗?
提前致谢。

@ysmoradi 是的! 这些新的渲染器将遵循快速渲染器模式(即主视图周围没有包装视图)。 我们计划为所有平台执行此操作,而不仅仅是 Android 和 WPF。

请不要试图不惜一切代价保持向后兼容。 这是新的东西。 它不必与 XF 兼容。 你可以做出更好的东西。

为什么不使用自己的一组控件制作 UI 框架,而无需完全用 C# 编写的任何类型的映射和行为逻辑,这些映射和行为逻辑将使用 Skia 图形库呈现? 由于人们使用高度定制的设计,因此无需尝试匹配平台设计指南。 唯一的需要是灵活定制的可能性。 如果我遗漏了一些东西,请纠正我,但我不明白为什么好处超过渲染器架构。

使用这种方法,是否可以编写跨平台渲染器而不是特定于平台的渲染器? 就像用skia-sharp control映射Button控件一样。

平台渲染器是一个糟糕的设计。 如您所见,由于平台限制,有很多 xamarin 控件库不支持 UWP。
举个例子,UWP 中的阴影。 您无法从角按钮获得角阴影(当然,您可以更改按钮模板来执行此操作,但那是另一回事)。

我知道构建跨平台渲染非常困难。 但是 flutter 告诉我们这是可行的。 从长远来看,跨平台渲染器是最好的解决方案。

我认为将整个应用程序渲染为自定义 2d 画布可能可以无缝地用于移动应用程序。

但它可能不适用于桌面应用程序或复杂的应用程序,因为有很多用户操作需要重新实现,例如拖放、文本选择、操作文本的键盘快捷键等等。

为什么不使用自己的一组控件制作 UI 框架,而无需完全用 C# 编写的任何类型的映射和行为逻辑,这些映射和行为逻辑将使用 Skia 图形库呈现? 由于人们使用高度定制的设计,因此无需尝试匹配平台设计指南。 唯一的需要是灵活定制的可能性。 如果我遗漏了一些东西,请纠正我,但我不明白为什么好处超过渲染器架构。

我认为将整个应用程序渲染为自定义 2d 画布可能可以无缝地用于移动应用程序。

但它可能不适用于桌面应用程序或复杂的应用程序,因为有很多用户操作需要重新实现,例如拖放、文本选择、操作文本的键盘快捷键等等。

为什么不使用自己的一组控件制作 UI 框架,而无需完全用 C# 编写的任何类型的映射和行为逻辑,这些映射和行为逻辑将使用 Skia 图形库呈现? 由于人们使用高度定制的设计,因此无需尝试匹配平台设计指南。 唯一的需要是灵活定制的可能性。 如果我遗漏了一些东西,请纠正我,但我不明白为什么好处超过渲染器架构。

你对所有这些东西都是完全正确的,但团队并没有被迫选择唯一的一种方法。 我认为这都是因为时间不够。 我的意思是他们只需要在一年内与 .net 6 一起发布一个“全新的”完全跨平台的 ui 框架。而且以经过时间考验的旧框架作为基础的风险要小得多。 没关系,它应该是。 但我相信,从长远来看,自定义 2d 画布渲染有更多的好处,真的值得被称为“跨平台”。 Xamarin 表单确实是一件好事,它在今天取得了巨大的进步。 但是是时候继续前进了。 微软和 xamarin 团队有非常聪明的工程师,他们可能正在考虑这种方法,甚至可能与http://avaloniaui.net/有一些联系作为王牌

为什么不使用自己的一组控件制作 UI 框架,而无需完全用 C# 编写的任何类型的映射和行为逻辑,这些映射和行为逻辑将使用 Skia 图形库呈现? 由于人们使用高度定制的设计,因此无需尝试匹配平台设计指南。 唯一的需要是灵活定制的可能性。 如果我遗漏了一些东西,请纠正我,但我不明白为什么好处超过渲染器架构。

为 Skia 开发人员设置 4 次渲染默认灰色可能很酷,它将 100% 更改它以确保提供丰富的设计,
对于后面的可梳理性,将保留这 3 个原样,但添加“亲爱的开发人员自己绘制”_skia_render 并为开发人员承担 90% 的责任。

如果要保持渲染器的概念,是否可以考虑通过INotifyPropertyChanged和事件处理程序消除共享 UI 代码和渲染器之间的桥梁? IE

  • 不是在共享控件上设置 _property_ 并传播PropertyChanged事件,而是可以直接在平台渲染器上映射和设置属性吗?
  • 除了在共享控件上调用 _method_ 以及由渲染器触发和处理的事件,是否可以直接在平台渲染器上映射和涉及该方法?

INotifyPropertyChanged非常适合 MVVM 设计和松散耦合的视图模型,但作为共享 UI 代码和平台渲染器之间的桥梁机制,它总是让人觉得笨拙。 这反过来会导致更好的性能,共享 UI 和渲染器层之间更少的“闲聊”以及更好的开发人员体验。

这很长,但值得在毛伊岛观看一些“内部棒球”。
https://www.youtube.com/watch?v=_MGh3xipWm4

听起来 Maui 的架构将同时支持平台渲染控件和画布绘制控件,而且高贵的@Clancey将继续为 Maui 开发基于skia 的渲染集,它不仅适用于 MVU 风格毛伊岛,但也适用于 MVVM 模式。

乍一看,Maui 似乎是对 Forms 的重新命名,但仔细观察,它是对 Forms 架构的重构,以使其各层更加松散耦合,从而支持我们在此线程中提出的许多问题。 未来的欢乐时光。

这有点偏离主题,但我想问的只是因为它与这个确切的事情相关:

记忆如何与SKCanvasView (或一般的 Skia)一起工作? 每一个是否总是与其大小成正比地占用内存? 如果它与其他人重叠,这会改变吗?

例如,如果我有一个渐变控件(用 Skia 编写的渲染器)并且在它的顶部我有一个半透明按钮(用 Skia 编写的渲染器)会占用两倍的内存,还是图形上下文以某种方式共享? 如果 Skia 控件与非 Skia 控件重叠会怎样?

我之前考虑过使用 Skia 在 Forms 中实现一些花哨的图形控件,但不了解内存的工作方式总是引起足够的关注,我还没有。

@GalaxiaGuy我认为使用重叠在非skia控件上的skia控件,就像托管在wpf控件上的winform控件一样。 你可以这样做,但不是最好的。
如果您有两个由SKCanvasView呈现的控件,则不会共享图形上下文。 最好的方法是将渲染的两个合成并在单个画布上绘制。
在我的测试中,如果你只是做一些静态的事情, SkiaSharp性能并没有那么糟糕。 我试着做一些动画,我的笔记本电脑的 CPU 使用率有点高。

为什么这么多人沉迷于Skia? 一个好的渲染规范对于低级别使用的渲染引擎是不可知的。 如果特定平台渲染器想要使用 Skia(或 Direct2D 或 OpenGL 或其他),则应用层不必担心。

很久以前,XAML 和 WPF 的最大承诺是Lookless Controls的想法,
我认为我们不需要对各种操作系统和框架中现有组件的另一组接口和抽象,而是需要基于 XAML 的真正无外观的控件 - 使用与平台无关的视觉原语和特定于平台的图形渲染后端进行模板化。 当然,默认模板也可能是实际的本机控件,但圣杯是定义一次使用无处不在的图形模板。

很久以前,XAML 和 WPF 的最大承诺是 Lookless Controls 的想法,其中控件的实际图形被推迟到模板。 Xamarin Forms 使用 XAML 时没有这种能力,这是它的最弱点,几年后才被绘图规范部分修复。

同意! 并且您确实需要非常少量的渲染原语来完成应用程序所需的大约 99% 的所有内容:

  • 边框(包括阴影和圆角边缘的选项)
  • 线/椭圆/矩形
  • 纯文本渲染
  • 纯文本输入
  • 富文本渲染
  • 富文本输入
  • HTML 渲染
  • 图片展示
  • 音频/视频演示者
  • 实体和线性/径向渐变画笔

XF 渲染平台变得如此臃肿,因为每当向框架添加新类型的控件时,它都是使用新的渲染器完成的,而不是构建在框架内的现有基元之上。

是的,必须将更多的逻辑移入框架层,最具挑战性的是项目控件( VirtualizingStackPanel对于拥有可扩展的项目查看器至关重要,但据我所知从未有效地移植到外部WPF,因为它太复杂了)。 但是随着 WPF 是开源的,现在很多都可以移植到 MAUI 中,我认为这终于应该开始发生了。

您确实需要非常少量的渲染原语来完成应用程序所需的大约 99% 的所有内容。

Uno 平台正在使用这种方法。

@速度系统

除了在共享控件上设置属性和传播的 PropertyChanged 事件之外,是否可以直接在平台渲染器上映射和设置属性?

这也是这次变革的一个大目标。 一旦我们站在这些变化的另一边,渲染器将不知道 BindableObject 或 INPC 意味着什么

这也是这次变革的一个大目标。 一旦我们站在这些变化的另一边,渲染器将不知道 BindableObject 或 INPC 意味着什么

因此,只要BindableProperty值发生变化,渲染器上的方法就会被框架调用,而不是渲染器必须订阅PropertyChanged

@legistek

这基本上反转了依赖关系

所以渲染器将只针对 IButton 工作。

然后 System.Maui 将添加对渲染器项目的引用,而不是渲染器现在如何引用 Xamarin.Forms.Core

我检查了我们这里有一个尖峰
https://github.com/dotnet/maui/pull/66

所以你可以看到这可能是什么样子

我将在今天太平洋夏令时间 3:30 与@davidortinau 进行直播,我们将讨论超薄渲染器

https://www.twitch.tv/microsoftdeveloper

加入我们! 一探究竟! 并提出问题!

@PureWeen不幸的是我错过了。 YouTube 上会提供录音吗?

这也是这次变革的一个大目标。 一旦我们处于这些更改的另一端,渲染器将不知道 BindableObject 或 INPC 的含义。

这是巨大的,真正的实质性改进。 毫无疑问,随着迁移到 Maui,许多渲染器中使用的复杂继承模型将被删除,以支持更组合的方法?

今天要复习#66。

查看#66,很高兴看到使用“诱饵和开关”而不是使用反射来构建和调用纤薄的渲染器。 只是一些想法:

  • Slim 渲染器是否会解决 GC 问题,尤其是在托管和本机控件生命周期不匹配的 Android 上? 这在导致可怕的ObjectDisposedException虚拟化布局中的子视图中尤为明显。
  • Slim 渲染器会导致Effect被弃用吗? 效果可能很有用,但最终它们会增加复杂性,并增加布局生命周期的潜在延迟。
  • “双向”属性如何与新的渲染器设计配合使用? 例如,假设我有一个MediaElement和一个 Position ( TimeSpan ) 属性。 Setter 更新当前位置,getter 从本机媒体播放器检索当前位置,即AVPlayerMediaPlayer 。 是否有将 _getter_ 映射到纤薄渲染器的设计?

Slim 渲染器是否会解决 GC 问题,尤其是在托管和本机控件生命周期不匹配的 Android 上? 这在导致可怕的 ObjectDisposedException 的虚拟化布局中的子视图中尤为明显。

我们在这里确实有一些想法!! 我们想稍微修改处理策略,以希望解决大多数(如果不是全部)ODE 异常。 现在我们非常积极地处理 android/iOS 中的所有内容,但我相当肯定我们可以依靠 GC 来完成 GC 所做的事情。 如果我们确保取消引用所有内容并让 GC 完成在很多情况下应该有帮助的工作

Slim 渲染器会导致弃用 Effect 吗? 效果可能很有用,但最终它们会增加复杂性,并增加布局生命周期的潜在延迟。

随着我们发展这个想法,这绝对是一件值得研究的事情。 一旦我们完成所有这些的最终设计,我们将看看效果。 但是,是的,我可以看到效果已经过时,因为它们旨在作为一种无需使用完整渲染器即可利用原生元素的方式。 映射器基本上过时的效果

“双向”属性如何与新的渲染器设计配合使用? 例如,假设我有一个带有 Position (TimeSpan) 属性的 MediaElement。 Setter 更新当前位置,getter 从本机媒体播放器即 AVPlayer、MediaPlayer 检索当前位置。 是否有将 getter 映射到纤薄渲染器的设计?

我们仍在努力解决这个问题。 如果我错了,请纠正我@Clancey但 ActionMapper 是我们目前的方法,是吗? https://github.com/dotnet/maui/blob/slim-renderers/Maui.Core/PropertyMapper.cs#L91

“双向”属性如何与新的渲染器设计配合使用? 例如,假设我有一个带有 Position (TimeSpan) 属性的 MediaElement。 Setter 更新当前位置,getter 从本机媒体播放器即 AVPlayer、MediaPlayer 检索当前位置。 是否有将 getter 映射到纤薄渲染器的设计?

我们仍在努力解决这个问题。 如果我错了,请纠正我@Clancey但 ActionMapper 是我们目前的方法,是吗? https://github.com/dotnet/maui/blob/slim-renderers/Maui.Core/PropertyMapper.cs#L91

不完全是。 所以 ActionMapper 与 PropertyMapper 是一样的,除了它们在 SetElement 阶段不被调用。 所以,对于像 WebView、GoBack 这样的东西。 你不想在初始化期间调用它,但它仍然是你需要与渲染器通信的东西。

我们已经支持 2 路映射。 即条目。 当文本值出现在条目上时。 IEntry 有一个string Text {get;set;} ,我们只需设置该值。 因此,对于媒体元素,您有 2 个选择。 一种是简单地在位置/时间发生变化时将其回退。 如果你想让它成为你查询的东西。 你可以这样做。 xplat 视图可以访问渲染器。 view.Renderer.NativeView as NativeMediaView您现在可以购买您想要的任何属性!

以下是我们在构建期间的流中的一些视频

@Clancey在这里会更深入
https://www.youtube.com/watch?v=_MGh3xipWm4

我在这里和大卫谈了一点
https://www.youtube.com/watch?v=lAmwjfZY1IM

“双向”属性如何与新的渲染器设计配合使用? 例如,假设我有一个带有 Position (TimeSpan) 属性的 MediaElement。 Setter 更新当前位置,getter 从本机媒体播放器即 AVPlayer、MediaPlayer 检索当前位置。 是否有将 getter 映射到纤薄渲染器的设计?

我们仍在努力解决这个问题。 如果我错了,请纠正我@Clancey但 ActionMapper 是我们目前的方法,是吗? https://github.com/dotnet/maui/blob/slim-renderers/Maui.Core/PropertyMapper.cs#L91

不完全是。 所以 ActionMapper 与 PropertyMapper 是一样的,除了它们在 SetElement 阶段不被调用。 所以,对于像 WebView、GoBack 这样的东西。 你不想在初始化期间调用它,但它仍然是你需要与渲染器通信的东西。

我们已经支持 2 路映射。 即条目。 当文本值出现在条目上时。 IEntry 有一个string Text {get;set;} ,我们只需设置该值。 因此,对于媒体元素,您有 2 个选择。 一种是简单地在位置/时间发生变化时将其回退。 如果你想让它成为你查询的东西。 你可以这样做。 xplat 视图可以访问渲染器。 view.Renderer.NativeView as NativeMediaView您现在可以购买您想要的任何属性!

这里要考虑的另一件事是 C#9 中的 Records。 特殊之处在于它们是不可变的并且具有init属性访问器。 因此,为了使它们在双向绑定中可用,映射器需要能够使用with运算符返回一个新实例。

我真的希望视图可以绑定到记录,因为这让纯 MVVM 甚至纯 MVU 的事情变得更容易。

问题:您发布的图表具有由Windows.UI.*呈现的 Windows 控件,但据我了解,现在正在弃用并且不会看到任何更新:对流畅设计呈现的所有改进都是作为 WinUI 项目的一部分发生在Microsoft.UI.*中。 你能对此发表评论吗?

我认为映射到本机控件是一个很大的错误,这是 Xamarin.Forms 的可怕部分,您无法轻松制作独特而美观的布局,您必须遵循 WPF 和 Flutter 控件的概念和方法,而无需渲染使用 OpenGL / DirectX / Metal 用 C++ 编写的引擎,因为除了不依赖于不断变化的平台结构之外,这还促进了可移植性、性能和灵活性。

问题是在这里讨论新的架构/属性映射器。 不是他们映射的对象。 只是为了重新迭代。 Slim Render Architecture for native 并不意味着我们永远、也永远不能做一个绘制控件的方法。 但这确实允许我们混合和匹配原生与非原生控件,如果你纯粹绘制,那就更难了。 我计划继续研究基于 Skia 的控件,这些控件遵循相同的 Slim Renderer 架构,包括绘图层。 https://github.com/Clancey/Comet/tree/dev/src/Comet.Skia/Handlers。

我在这个渲染器上的 2 美分(我承认我不完全理解,TBH):

我有一个关于如何使用相同控件类实现平台渲染控件(例如包装 UIButton)和无外观控件(a la WPF)的想法。 老实说,这很简单:让 Maui Button 类使用控件模板,并从中删除所有特定于平台的渲染器代码。 然后,为包含 ButtonRenderer 的 Button 提供一个内置模板。 ButtonRenderer 是与 Cocoa/UIKit/UWP/etc 对话的对象,为每个 UI 工具包提供特定于平台的代码,应用程序开发人员使用的 Button 类只是将其属性转发给它。 如果用户想要使用自定义绘制的按钮,那么他们可以简单地覆盖模板并使用绘图类(无论最终看起来像什么)而不是 ButtonRenderer,就像我们在 WPF 中所做的那样。 老实说,我不知道今天在毛伊岛这是否已经可能(甚至已经使用),因为我从来没有像我理解 WPF 那样花时间深入理解 Xamarin.Forms。

告诉我你的想法!

我试图了解 Slim 渲染器对不同应用程序模型(MVVM、MVU 等)的意义。

最初的图表似乎表明每个不同的应用程序模型都有自己的一组渲染器。
但在我看来,最好为每种渲染类型设置一组渲染器(例如,渲染到 XF 等本机控件、渲染到画布等)。
渲染器不需要知道应用程序模型,它只需要知道什么值映射到哪个属性,以便它可以将正确的更新应用到底层控件。
对于每个应用程序模型,只有IButton会以不同的方式实现,并负责调用其渲染器的映射函数。

这很重要,因为像 Fabulous 这样的 3rd 方库不会有 Microsoft 的人力来为每个平台上的每个控件实现(伴随着所有错误)所有适当的渲染器。

另一点是:控制接口( IButton )应该是 getter-only 供渲染器使用。
渲染器不设置值,每个应用程序模型都会以不同的方式塑造控件(BindableProperty、BindingObject 等)。
例如,Fabulous 将拥有不可变的视图。 只有在内部,才会被授权将突变设置为IButton的实例。

这样,Fabulous 可以直接使用IButton接口作为其内部字典的阅读器视图,以便渲染器可以工作。

// This is the type used by our users, sort of a Builder that return a new instance each time
// and append the set value to an internal list 
public struct Button
{
     public Button Text(string value) => (...);

     internal ReadOnlyDictionary<string, obj> Build() { ... }
}

// This will be an implementation of IButton, hidden from our users
internal class FabulousButton : IButton
{
    private ReadOnlyDictionary<string, obj> _properties;
    FabulousButton(ReadOnlyDictionary<string, obj> properties)
    {
        _properties = properties;
    }

    void Update(ReadOnlyDictionary<string, obj> properties)
    {
        var previousProperties = _properties;
        _properties = properties;

        // Diffing of the 2 dictionaries to determine what changed
        // and which mapped functions inside the renderer should be called
        (...)
    }

    public string Text => _properties["Text"];
}

@TimLariviere你所说的一切都是它的工作原理:-)

就渲染器而言,那里的绘图令人困惑。

您需要关心的唯一部分是 Fabulous Button,然后我们会处理其他所有事情

大多数情况下,接口是只读的

这是按钮使用的界面
https://github.com/dotnet/maui/blob/slim-renderer-samples/Maui.Core/Views/IText.cs

您真正需要做的事情(就渲染器而言)是向渲染器发出信号,表明它应该重新使用 IButton

例如,在所有这些的 BindableObject 版本上,我们只是在此处调用 Renderer 的 updateproperty 方法

https://github.com/dotnet/maui/blob/slim-renderer-samples/System.Maui.Core/VisualElement.cs#L1132

某个时候(很快?) @Clancey将会有一个 Comet 的公共版本,你可以看看他是怎么做的。

我会检查
https://github.com/dotnet/maui/blob/slim-renderer-samples

您可以将自己的 Fabulous.Core 头添加到其中,然后开始向接口添加实现

@PureWeen哦酷。 谢谢,我会尝试使用您链接的示例,看看效果如何。

@PureWeen @Clancey我相信 Maui 团队会全力以赴,但请新的 Slim 渲染器更喜欢合成而不是继承。 继承很有用,但不幸的是,在 XF 中,它使一些渲染器层次结构极其复杂且难以维护。

@PureWeen
这个网址
https://github.com/dotnet/maui/blob/slim-renderer-samples

给404,是私有的吗?

@Rand-随机

https://github.com/dotnet/maui/tree/slim-renderer-samples

@速度系统

我相信 Maui 团队会全力以赴,但请新的 Slim 渲染器更喜欢合成而不是继承。 继承很有用,但不幸的是,在 XF 中,它使一些渲染器层次结构极其复杂且难以维护。

它们就是这样建造的。 有一个非常瘦的基类,它直接从好的 ol' System.Object继承

https://github.com/dotnet/maui/blob/slim-renderer-samples/Maui.Core/Renderers/View/AbstractViewRenderer.Android.cs

并且没有本土关系。

从那里开始,整个事情通过基本上是一个字典来定义

https://github.com/dotnet/maui/blob/slim-renderer-samples/Maui.Core/Renderers/View/AbstractViewRenderer.cs#L31

它基本上像装饰器一样运行。

您可以使用额外的映射器来装饰映射器,并且可以注入自己的 func 等。

我们的目标是通过将您自己的 Func 添加到映射器或直接访问本机元素来覆盖 95% 的用户场景,因为它们都是多目标的

@PureWeen在您的示例中讨论这些超薄渲染器的实现的最合适的渠道是什么?

我有一些问题,例如:

  • 默认值会在一个集中的地方定义吗? 在 XF 中,它们当前是在创建 BindableProperty 字段时定义的,但根据应用程序模型,这些字段不会出现。
  • Application 类也会成为(部分)接口吗? 它定义了许多 UI 行为(资源、菜单、主页),并且以不同的方式实现会很棒。
  • Measure/Arrange/etc 是否会从控制界面中提取? 我认为应用程序模型以不同的方式实现它们真的没有意义。

默认值会在一个集中的地方定义吗? 在 XF 中,它们当前是在创建 BindableProperty 字段时定义的,但根据应用程序模型,这些字段不会出现。

这是一个很好的问题。 @克兰西? 不确定我们是否已经定义了这个。 有一个初始设置阶段,所有映射器都使用属性的当前值(默认值)被调用,但我不确定我们是否有默认值的计划以及如何推广这些

Application 类也会成为(部分)接口吗? 它定义了许多 UI 行为(资源、菜单、主页),并且以不同的方式实现会很棒。

是的! 我们希望将所有应用程序类(本机和 xplat)合并为一个应用程序类。 你为什么问这个? 我只是好奇你在这里的用例,所以我们可以确保解决

Measure/Arrange/etc 是否会从控制界面中提取? 我认为应用程序模型以不同的方式实现它们真的没有意义。

这就是计划。 这个想法是将我们所有的布局代码提取出来,这样它们都不依赖于 BindableObject/Property .. 这样 Blazor/Comet/other 可以只使用 StackLayout 并且结果将是相同的。

你为什么问这个? 我只是好奇你在这里的用例,所以我们可以确保解决

我还不完全确定我想要什么。 但是在 Fabulous 中,我们目前没有一个很好的故事来定义全局样式和主菜单(例如 macOS)。 由于我们让用户自己对 Application 类进行子类化,因此我们基本上告诉他们像在经典 Xamarin.Forms 中那样定义资源/菜单。

所以理想情况下,Application 的所有 UI 相关属性也将成为视图的一部分,这样我们也可以在其上应用我们的视图差异逻辑。

类似的东西

public interface IAppRoot
{
    IEnumerable<object> Resources { get; }
    IMenu MainMenu { get; }
    IPage MainPage { get; }
}

public class Application
{
    /// Bootstrapping and other logic of MAUI

   public IAppRoot Root { get; set; } // Replaces MainPage, which is typed for pages only
}

@PureWeen另一个问题:谁将负责触发TextChangedToggled等事件? 控件还是渲染器?

我认为可以大大简化其他应用程序模型的实现的一件事是,当更改为编程时,可能不会触发状态更改事件。

例如,今天,当用户写东西或我们做MyEntry.Text = "New value";时,Entry 上的TextChanged被触发。
我认为对程序化更改做出反应并不是很有用,而且是隐含的,这不利于代码的推理。

这也导致了 Android 上的无限循环,因为该平台以轻微的延迟触发其事件,并迫使 Fabulous 失去同步,不可能再回来。
我们找到的唯一解决方法是在设置值之前先取消订阅事件,然后重新订阅...

一个好奇的问题。 当 MAUI 与架构无关时,为什么控件以架构名称命名? 例如在上图中,我们有毛伊岛。 Mvvm .ButtonRenderer.Android? @PureWeen @Clancey

XF 有一种叫做 Compressed Layouts 的东西(有问题)
我们在毛伊岛有这样的东西吗(肯定没有错误!)?

我看到人们在这个帖子中对使用 Flutter/Skia 方法渲染 UI 的反应如何,我基本同意他们的看法。
我真的很高兴 MAUI 可能会支持自定义/非本机控件和渲染。
但是,我不得不说,使用原生 UI 的能力在事物的政治方面确保了框架的安全。
是的,我指的是苹果。 由于最新消息,如果在某个时间点出于某种原因使用 Flutter 会被视为“利用非文档化/受限功能”或“不遵循 Apple UI 指南”等,我不会感到惊讶。

我看到人们在这个帖子中对使用 Flutter/Skia 方法渲染 UI 的反应如何,我基本同意他们的看法。
我很高兴在 MAUI 中可能会支持自定义/非本机控件和渲染。
但是,我不得不说,使用原生 UI 的能力在事物的政治方面确保了框架的安全。
是的,我指的是苹果。 由于最新消息,如果在某个时间点出于某种原因使用 Flutter 会被视为“利用非文档化/受限功能”或“不遵循 Apple UI 指南”等,我不会感到惊讶。

如果 MAUI 支持 Web(如 Flitter),那么我们总是可以渲染到 WebView 中。
Apple 不太可能敢阻止基于 WebView 的应用程序,因为一些大公司在 AppStore 中仅通过 WebView 表示

我看到人们在这个帖子中对使用 Flutter/Skia 方法渲染 UI 的反应如何,我基本同意他们的看法。
我很高兴在 MAUI 中可能会支持自定义/非本机控件和渲染。
但是,我不得不说,使用原生 UI 的能力在事物的政治方面确保了框架的安全。
是的,我指的是苹果。 由于最新消息,如果在某个时间点出于某种原因使用 Flutter 会被视为“利用非文档化/受限功能”或“不遵循 Apple UI 指南”等,我不会感到惊讶。

如果 MAUI 支持 Web(如 Flitter),那么我们总是可以渲染到 WebView 中。
Apple 不太可能敢阻止基于 WebView 的应用程序,因为一些大公司在 AppStore 中仅通过 WebView 表示

这已经违反了指导方针 - https://developer.apple.com/app-store/review/guidelines/#minimum -functionality

在仔细阅读了 MAUI 的这个全新世界似乎是什么之后,请对所有神圣的热爱实际上写一次使用无处不在的渲染引擎,如 SKIA 或其他多平台渲染引擎,必须实现自定义每个平台上的 UI 就像在 Xamarin Forms 中一样感觉陈旧,就像它是在地狱第七圈中创建的解决方案。

如果向后兼容性是必须的“只是”使新的和现代的渲染支持成为渲染旧组件的一种方式,我已经看到其他平台对此有很好的解决方案,我最近使用的一个是在统一的 UI 引擎中新的现代 UXML 有一个 IMGUI 渲染。

@jackie0100
我完全同意

必须像在 Xamarin Forms 中那样在每个平台上实现自定义 UI 感觉很旧,就像它是在地狱第七圈中创建的解决方案。

至于渲染器的实现,IView IS A native view(而不是 IView HAS A native view)的想法呢? 即继承而不是组合? 这将导致“表单开销”绝对为零的最快、最精简的架构。 您基本上是在使用纯原生视图,而且只是一个通用界面。

然后你可以做这样的事情,在 iOS 领域,只需将你的视图转换为 UIView,然后向它添加一个本机子项(你想要的任何类型),因为 IView 是一个 UIView。 同样,如果您想进行“原生嵌入”,这很容易,因为 IView 是 UIView,您只需将其中一个 IView 添加到您的原生视图中,因为它们是相同的。 这将大规模启用本机 <-> maui 互操作性,并具有最高级别的性能和最低的内存消耗。

我有点想自己制作原型。 也许是周末/晚上的项目...

image

如果 MAUI 支持 Web(如 Flitter),那么我们总是可以渲染到 WebView 中。

iOS 上不需要 WebView:可以直接在OpenGLMetal 中渲染。

或者在下面使用带有 OpenGL 或 Metal 的 Skia。

使用原生 UI 的能力在事物的政治方面确保了框架的安全。 [苹果]

在某些时候,Apple 从他们的书面政策中删除了使用原生 UI 小部件的要求。 我看不出他们有任何实际方法可以将政策逆转为限制性。

无论如何,_能够_使用本机控件是一个不错的选择。

@legistek

为什么这么多人沉迷于Skia? 一个好的渲染规范对于渲染引擎来说是不可知的......

虽然我完全同意“不可知论”,但必须实现很多细节才能呈现任何交互式 UI - 如果您直接转到 OpenGL/Metal/Vulkan/任何低级渲染引擎。 人们对 Skia 很着迷,因为它是应用程序的 UI 问题和实际渲染引擎之间的一个有效的_中间层_:如果你只有裸机,Skia 会处理_很多_必须设计和实现的内容。 没有理由重新发明这项工作。 虽然它不应该是 _only_ 目标,但它是一个非常有价值和成熟的目标,这将使从 OpenGL 迁移到 Vulkan 变得更加容易。

我还怀疑,与 Xamarin Forms 维护两个并行小部件层次结构(跨平台小部件和本机小部件)相比,以 Skia 为目标目标要简单得多。

Skia 甚至可能会加速 .Net Maui 在浏览器中具有高性能的那一天。 同样,因为渲染不是从低级构建,而是从适当的中级抽象开始。 那将是一个巨大的胜利。

看过最近的 maui 视频,除非我弄错了,否则似乎有更多风格的控件出现了漂移,原生控件与在平台独立方面完成的绘图重叠。 无论是它的skia 还是某种与原生画布绘图的批处理互操作,我都希望这种方法被采用! 具有讽刺意味的是,XF 平台渲染器模型对 Microsoft UI 平台的伤害最大,使用最少。

我还会让控件明确没有本机组件和布局合成器检测到这一点的能力,它可能允许自动减少创建的本机视图(即,如果容器中的所有控件都是用毛伊标签绘制的Skia,它可以使容器成为 SkView 并只调用标签子控件上的绘制操作),在 Android 上,这将提高诸如具有大量图像 + 文本控件的列表元素之类的事物的速度。

我不明白渲染器是什么。
如果把吸收目标视觉差异的程序叫做渲染器,那应该是被Xamarin和MAUI一并吸收的,如果不是,我觉得就是一个未完成的Xamarin和MAUI,永远不会完成。
我认为应用程序编程应该更独立于目标环境的差异。

我不明白渲染器是什么。
如果将吸收目标视觉差异的程序称为渲染器,则它应该被 Xamarin 和 MAUI 一起吸收。如果没有,我认为这是未完成的 Xamarin 和 MAUI。它永远不会完成。
我认为应用程序编程应该更独立于目标环境的差异。

此页面是否有帮助?
0 / 5 - 0 等级

相关问题

PureWeen picture PureWeen  ·  21评论

sim756 picture sim756  ·  16评论

PureWeen picture PureWeen  ·  9评论

jsuarezruiz picture jsuarezruiz  ·  3评论

jsuarezruiz picture jsuarezruiz  ·  7评论