自定义组件

大多数情况下,默认的 ft 组件(例如 DivPH1 等)就足以满足您的所有需求。

预备知识

如果您不了解 ft 组件是什么,应首先阅读关于 ft 组件的说明

然而,在许多情况下,您需要一个自定义的 ft 组件来创建独特的 HTML 标签(例如 <zero-md></zero-md>)。FastHTML 提供了多种方法来实现这一点,本节将逐一介绍。通常,您应该选择能满足需求的最高级选项。

真实世界示例

这篇外部教程通过一个实际场景,讲解了您可能需要使用自定义 ft 组件创建自定义 HTML 标签的情况。通过真实世界的示例,可以很好地理解本指南内容的用处。

NotStr

第一种方法是使用 NotStr 类将 HTML 标签作为字符串使用。这种方法适用于一次性使用,但随着复杂度的增加,会变得难以处理。不过,我们可以看到,使用 NotStr 和使用开箱即用的组件可以生成相同的 XML。

from fasthtml.common import NotStr,Div, to_xml
div_NotStr = NotStr('<div></div>') 
print(div_NotStr)
<div></div>

自动创建

下一个(也是更好的)方法是让 FastHTML 为您生成组件函数。正如您在我们的 assert 中所见,这将创建一个函数,该函数会生成我们想要的 HTML。尽管在 fasthtml.components 源代码中并没有一个名为 Some_never_before_used_tag 的函数,但这依然有效(您可以通过查看源代码自行验证)。

提示

通常,需要这些标签是因为某个 CSS 或 Javascript 库创建了一个新的 XML 标签,而这个标签并非标准的 HTML。例如,zero-md Javascript 库会寻找 <zero-md></zero-md> 标签,以便知道在哪个元素上运行其 Javascript 代码。大多数 CSS 库通过基于 class 属性创建样式来工作,但它们也可以将样式应用于它们自己定义的任意 HTML 标签。

from fasthtml.components import Some_never_before_used_tag

Some_never_before_used_tag()
<some-never-before-used-tag></some-never-before-used-tag>

手动创建

自动创建并非魔法。它只是调用了一个 Python 函数 __getattr__,您也可以自己调用它来获得相同的结果。

import fasthtml

auto_called = fasthtml.components.Some_never_before_used_tag()
manual_called = fasthtml.components.__getattr__('Some_never_before_used_tag')()

# Proving they generate the same xml
assert to_xml(auto_called) == to_xml(manual_called)

知道了这一点,我们便明白,通过修改 __getattr__ 函数创建组件的方式,可以创建一个与 FastHTML 默认行为不同的函数!这只需要几行代码,阅读这些代码是更深入地理解组件的好方法。

提示

双下划线(Dunder)方法和函数是名称前后都有双下划线的特殊函数。它们在 Python 的特定时刻被调用,因此您可以使用它们来实现符合特定用例的自定义行为。如果您不了解 Python 的工作原理,它们可能看起来像魔法,但它们在修改 Python 默认行为方面非常常用(__init__ 可能是最常见的一个)。

在一个模块中,__getattr__ 被调用以获取一个属性。在 fasthtml.components 中,它被定义为为您自动创建组件。

例如,如果您想要一个创建 <path></path> 的组件,并且不与 pathlib.Path 的名称冲突,您可以做到这一点。FastHTML 会自动创建具有一对一映射和一致名称的新组件,这几乎总是您想要的。但在某些情况下,您可能希望自定义这种行为,您可以使用 ft_hx 函数来实现与默认方式不同的操作。

from fasthtml.common import ft_hx

def ft_path(*c, target_id=None, **kwargs): 
    return ft_hx('path', *c, target_id=target_id, **kwargs)

ft_path()
<path></path>

我们可以在该函数中添加任何我们需要的行为,因此,让我们来看一些您在项目中可能需要的、逐步复杂的示例。

标签中的下划线

既然我们了解了 FastHTML 如何生成组件,我们就可以用各种方式创建自己的组件。例如,也许我们需要一个使用下划线的奇怪 HTML 标签。FastHTML 会将标签中的 _ 替换为 -,因为标签中使用下划线非常不常见,而且很少是您想要的结果,尽管这种情况偶尔也会出现。

def tag_with_underscores(*c, target_id=None, **kwargs): 
    return ft_hx('tag_with_underscores', *c, target_id=target_id, **kwargs)

tag_with_underscores()
<tag_with_underscores></tag_with_underscores>

标签中的符号(如 @)

有时,您可能需要使用一个包含 Python 函数名中不允许的字符的标签(同样,这非常不寻常)。

def tag_with_AtSymbol(*c, target_id=None, **kwargs): 
    return ft_hx('tag-with-@symbol', *c, target_id=target_id, **kwargs)

tag_with_AtSymbol()
<tag-with-@symbol></tag-with-@symbol>

标签属性中的符号(如 @)

也可能出现 HTML 标签中的某个参数使用了 Python 参数中不能使用的字符。为了处理这些情况,您可以使用字典来定义这些参数。

Div(normal_arg='normal stuff',**{'notNormal:arg:with_varing@symbols!':'123'})
<div normal-arg="normal stuff" notnormal:arg:with_varing@symbols!="123"></div>