trych/kirby-field-composer

Kirby插件,提供智能处理字段值以组合复杂字符串的方法。

1.3.1 2024-09-16 20:48 UTC

This package is auto-updated.

Last update: 2024-09-16 20:50:28 UTC


README

Kirby Field Composer是一个插件,简化了Kirby中的复杂字段操作。它提供合并字段、应用条件逻辑和操作字符串的方法,智能处理字段值以避免不希望的格式化问题。这使得处理简单和复杂的结构内容变得更加容易。

功能

  • 🧪 字段方法:一组用于操作和组合字段值的方法。
  • 🌐 全局辅助函数field()f(),方便字段组合。
  • 🧬 灵活合并:使用自定义分隔符和位置组合多个字段。
  • 🏷️ 智能处理空字段:当字段为空时,不插入分隔符。
  • 🚦 条件字段处理:应用条件进行字段渲染。
  • 🔡 字符串操作:直接将Kirby的Str类方法应用于字段。

概述

简单的用例包括将多个字段合并到一个字段值中……

$page->title()->merge($page->author(), $page->year());
// => Chasing Starlight, Jane Doe, 2008

……条件性地使用特定值作为字段的前缀……

$page->publisher()->prefix('Publisher: ');
// => Publisher: Kirby Press

……或更多。但要了解插件如何真正有用,看看一个复杂示例会很有帮助:假设在我们的网站上我们需要显示一系列绘画的数字博物馆标签。我们可能需要按照以下模式组合字符串

{Artist Name}, {Year of Birth}-{Year of Death}, {Birth Place}; {Title of the Artwork}, {Year of Creation}; {Material} ({Width} × {Height} cm); {Collection}; {Description}

起初这看起来很简单,但当你深入细节时,它会迅速变得复杂:有由分号分隔的子组,而子组条目本身通常由逗号分隔。当数据缺失时,不应留下废弃的分隔符,如果宽度没有给出,高度也不应显示,如果标题为空,应替换为Untitled,如果艺术家仍然健在,其出生年份前应有*,等等。

通常这需要大量使用条件语句、implode命令等。

该插件提供了使此过程显著简化的方法。以下是代码可能的样子,利用了一些插件的字段方法

// assuming we have two variables $artwork and $artist holding content on both
field(
  [
    $artist->name()->or('Unknown'),
    field($artist->born(), $artist->died(), '-')
      ->prefix('*', when: $artist->died()->isEmpty()),
    $artist->birthplace()
  ],
  [
    $artwork->title()->or('Untitled'),
    $artwork->year()
  ],
  [
    $artwork->material(),
    $artwork->width()->merge($artwork->height(), ' × ')
      ->when($artwork->width(), $artwork->height())
      ->suffix(' cm')
      ->wrap('(', ')'),
    ''
  ],
  $artwork->collection(),
  $artwork->description(),
  '; '
);

结果可能看起来像这样

Edward McDoe, 1856-1936, Scotland; Solitude, 1881; Oil on canvas (56 × 82 cm); Summerfield Collection; An impressionistic depiction of a lone farmer in the fields.

由于此设置将灵活处理空字段,对于另一个缺少艺术品标题、尺寸和收藏且艺术家仍然健在的内容文件,结果可能如下

Jil Nash ,*1982, Ireland; Untitled, 1994; Acrylic on wood; An abstract color explosion.

此外,我们可以将字段包装在标签中以便于样式化,根据条件更改字段等。下面是可用字段方法的详细列表。

安装

下载

下载并将此存储库复制到/site/plugins/field-composer

Git子模块

git submodule add https://github.com/trych/kirby-field-composer.git site/plugins/field-composer

Composer

composer require trych/kirby-field-composer

使用方法

在查看字段方法时,假设我们有一个包含以下内容的页面,用于描述一幅画

Title: Haze
----
Artist: Jil Nash
----
Year: 2014
----
Width: 48.2
----
Height: 67
----
Depth:
----
Description: Faint shapes lost in mist.
----
Info:
----
Museum: Tate

字段方法

插件中的每个字段方法都返回一个字段,因此所有方法都可以用于链式调用多个字段方法。

$field->merge(...$args)

将字段值与给定的参数合并。`merge()` 方法是插件的核心,允许对多个字段和字符串进行复杂的组合。

  • $args: 一个或多个参数(字段、字符串、数字、数组),它们将被合并到单个字段值中。

在其最简单形式中,它可以合并原始字段的值与一个或多个给定参数。默认分隔符是 ,

$page->title()->merge($page->year());
// => Haze, 2014

还可以将其他字段方法链接到 `merge()` 方法上。

$page->title()->merge($page->artist())->upper();
// => HAZE, JIL NASH

字符串也可以合并。

$page->title()->merge($page->artist(), 'Oil on canvas', $page->year());
// => Haze, Jil Nash, Oil on canvas, 2014

空字段将被简单地省略,不会引入重复的分隔符。

$page->title()->merge($page->artist(), $page->info(), $page->year());
// => Haze, Jil Nash, 2014

如果使用字符串作为最后一个参数,它将被解释为放置在各个部分之间的分隔符。否则将使用默认分隔符(', ' 或通过 mergeSeparator 选项设置的分隔符)。

$page->title()->merge($page->artist(), $page->year(), ' / ');
// => Haze / Jil Nash / 2014

如果您想将字符串作为最后一个参数合并,请记住即使它与默认分隔符匹配,也必须显式设置分隔符,否则最后合并的字符串将被解释为分隔符。

// 🚫 this will use the string 'Sold' as a separator
$page->title()->merge($page->artist(), $page->year(), 'Sold');
// => HazeSoldJil NashSold2014

// ✅ pass the separator explicitly as the last argument instead
$page->title()->merge($page->artist(), $page->year(), 'Sold', ', ');
// => Haze, Jil Nash, 2014, Sold

如果原始字段的值不应该合并到第一个位置,可以使用整数作为最后一个参数来指定值应该合并的位置。

$page->title()->upper()->merge($page->year(), $page->artist(), $page->museum(), 2);
// => 2014, Jil Nash, HAZE, Tate

也可以使用负整数,从列表的末尾开始计数。

$page->title()->upper()->merge($page->year(), $page->artist(), $page->museum(), -1);
// => 2014, Jil Nash, Tate, HAZE

如果最后一个参数设置为 false,则原始值将不会合并,而是只合并给定的参数。这在更复杂的场景中很有用,其中原始值是字符串中“子组”的一部分(请参见以下与数组的 `merge()` 方法使用)。

$page->title()->merge($page->year(), $page->artist(), $page->museum(), false);
// => 2014, Jil Nash, Tate

如果使用最后一个参数指定位置,分隔符字符串可以作为 倒数第二个 参数提供。

$page->title()->upper()->merge($page->artist(), $page->year(), $page->museum(), ' / ', 2);
// => Jil Nash / 2014 / HAZE / Tate

如果其中一个参数是数组,其条目将按照相同的规则合并,除了没有传递原始字段值,因此也没有位置选项。这允许在结果字符串中有多个“子组”时进行复杂的合并,这些“子组”可能有不同的分隔符。

$page->title()->upper()->merge(
  [$page->artist(), $page->year()], // arguments will be merged separated by the default by ', '
  [$page->description(), $page->info(), $page->museum(), ' | '], // arguments will be merged separated by ' | '
  'Sold',
  '; ' // separator, top level arguments will be merged separated by `; `
);
// => HAZE; Jil Nash, 2014; Faint shapes lost in mist | Tate; Sold

$field->prefix($prefix, $separator, $when)

向字段的值添加前缀。如果字段为空或条件不满足,则不添加前缀。如果传递空字段作为前缀,则不会添加前缀和分隔符,因此字段保留其原始值。

  • $prefix: 要添加的前缀(可以是字段或字符串)。
  • $separator: 可选的,前缀和字段值之间的分隔符。
  • $when: 可选条件,用于确定是否添加前缀。默认为 true
$page->title()->prefix('Title: ');
// => Title: Haze

$page->info()->prefix('Additional info: ');
// => [returns an empty field, as the info field is also empty]

$page->title()->prefix($page->artist(), ': ');
// => Jil Nash: Haze

$artist->born()->prefix('*', '', $artist->died()->isEmpty());
// => *1982

// if you do not like to pass redundant arguments or like to be explicit
// you can also pass named arguments
$artist->born()->prefix('*', when: $artist->died()->isEmpty());
// => *1982

$field->suffix($suffix, $separator, $when)

向字段的值添加后缀。如果字段为空或条件不满足,则不添加后缀。如果传递空字段作为后缀,则不会添加后缀和分隔符,因此字段保留其原始值。

  • $suffix: 要添加的后缀(可以是字段或字符串)。
  • $separator: 可选的,字段值和后缀之间的分隔符。
  • $when: 可选条件,用于确定是否添加后缀。默认为 true
$page->width()->suffix(' cm');
// => 48.2 cm
$page->width()->merge($page->height(), $page->depth(), ' × ')
  ->prefix('Dimensions: ')
  ->suffix(' cm');
// => Dimensions: 48.2 × 67 cm

在上面的示例中,如果所有字段 widthheightdepth 都为空,则 `merge` 的结果将是空字段,并且不会应用 `prefix` 或 `suffix` 值。

$field->wrap($before, $after, $separator, $when)

用指定的字符串或字段值包裹字段的值。如果字段为空或条件不满足,则不会添加包裹字符串。

  • $before: 预先添加到字段值的字符串或字段。
  • $after: 添加到字段值的字符串或字段。如果为null,则使用$before
  • $separator: 字段值和包装字符串之间的可选分隔符。
  • $when: 可选条件,用于确定是否包装字段。默认为true
$page->title()->wrap('»', '«');
// => »Haze«

如果向beforeafter传递空字段,则不会添加任何字符串,也不会插入分隔符。

$page->artist()->wrap($page->title(), $page->info(), ' | ');
// => Haze | Jil Nash

$field->tag($tag, $attr, $indent, $level, $when)

将字段值包装在HTML标签中。如果字段为空或条件不满足,则不添加标签。

  • $tag: 包装字段值的HTML标签。
  • $attr: 标签的HTML属性关联数组。
  • $indent: 缩进字符串,或为null表示无缩进。
  • $level: 缩进级别。默认为0
  • $when: 可选条件,用于确定是否在标签中包装字段。默认为true
$page->title()->tag('h1');
// => <h1>Haze</h1>

$page->description()->tag('p', ['class' => 'description']);
// => <p class="description">Faint shapes lost in mist.</p>

$field->when(...$conditions)

如果所有条件都有效,则返回原始字段,否则返回空字段。如果字段作为条件之一传递,则它在字段为空时评估为false

  • $conditions: 要检查的条件变量数量。
// just pass the dimensions, if both the `width` and the `height` are given
$page->width()->merge($page->height(), ' × ')->suffix(' cm')
  ->when($page->width(), $page->height());
// => 48.2 × 67 cm

$field->whenAny(...$conditions)

如果任何条件有效,则返回原始字段,否则返回空字段。如果字段作为条件之一传递,则它在字段为空时评估为false

  • $conditions: 要检查的条件变量数量。
// just pass the museum, if either `artist` or `info` are given
$page->museum()->prefix('Gallery: ', '')->whenAny($page->artist(), $page->info());
// => Gallery: Tate

$field->notWhen(...$conditions)

如果所有条件都有效,则返回空字段,否则返回原始字段。如果字段作为条件之一传递,则它在字段为空时评估为false

  • $conditions: 要检查的条件变量数量。
// shows the `description` only if `info` is empty
$page->description()->notWhen($page->info());
// => Faint shapes lost in mist.

$field->notWhenAny(...$conditions)

如果任何条件有效,则返回空字段,否则返回原始字段。如果字段作为条件之一传递,则它在字段为空时评估为false

  • $conditions: 要检查的条件变量数量。
// do not pass museum if either `artist` or `info` are given
$page->museum()->notWhenAny($page->artist(), $page->info());
// => [empty, as `artist` is given]

$field->whenAll(...$conditions)

当所有条件都有效时,是when()的别名。返回字段。

$field->whenNone(...$conditions)

notWhenAny()的别名。如果没有条件有效,则返回字段。

$field->format($callback)

将自定义格式化函数应用于字段值。

这与Kirby的本地 $field->callback() 方法非常相似,但为了方便,将字段值用作回调函数的第一个参数(字段本身为第二个参数),并且只需要返回一个字符串,自动将重新包装到字段中。直接返回带有新值的字段也将正常工作。

  • $callback: 一个闭包,它接受字段值和字段对象作为参数,并返回新的格式化值。值将被自动重新包装在字段中。
// remove all vowels from a string
$page->description()->format(function($value) {
  return preg_replace('/[aeiou]/i', '', $value);
});
// => Fnt shps lst n mst.

$field->str($method, ...$args)

Kirby Str类方法应用于字段值。

  • $method: 要应用Str类的名称方法。
  • $args: 要传递给Str方法的额外参数。
// Change the field's value to camel case
$page->artist()->str('camel');
// => jilNash

// Adds -1 to the field's value or increments the ending number to allow -2, -3, etc.
$page->title()->lower()->str('increment');
// => haze-1

辅助工具

该插件提供了一个全局辅助函数field()以及一个快捷别名f()

field(...$args)

字段辅助工具允许您从给定的值中组合一个字段。然后可以使用该字段与其他字段方法链接。这些参数的作用方式与上面描述的$field->merge()字段方法中的参数相同:您可以传递字段、字符串或数字,并将它们合并到新字段的值中。

field($page->title(), $page->artist(), 'sold', ', ')->upper()
// => HAZE, JIL NASH, SOLD

如果传递了一个数组,它将根据相同的规则将其值合并到一个字段中。如果最后一个给定的参数是一个字符串,它将被解释为分隔符。与$field->merge()方法不同,最后一个参数不能用作位置参数,因为没有初始字段值被传递到field()辅助函数中。

字段辅助函数特别有用,如果您需要组合一个字段,其中第一个值是“子组”的一部分,或者如果您需要将更多的字段方法链接到这样的子组中,如下面的示例所示。

field(
  [$page->title()->tag('em'), $page->year()],
  $page->artist(),
  field($page->width(), $page->height(), ' × ')->suffix(' cm')
    ->when($page->width(), $page->height()),
  $page->description()->prefix('Subject: '),
  $page->info()->prefix('Info: '),
  '; ' // separator for the top level
);
// => <em>Haze</em>, 2014; Jil Nash; 48.2 × 67 cm; Subject: Faint shapes lost in mist.

f(...$args)

field()的别名。

您可以通过在index.php中将各自的常量设置为false来禁用一个或两个辅助函数,如在Kirby辅助函数文档中所述

// /index.php

<?php

define('KIRBY_HELPER_FIELD', false);
define('KIRBY_HELPER_F', false);

require __DIR__ . '/kirby/bootstrap.php';

echo (new Kirby)->render();

选项

该插件有两个选项,分别是mergeSeparatoraffixSeparator

mergeSeparator$field->merge()以及field()辅助函数设置了默认分隔符。其默认值是一个逗号后跟一个空格:', '

affixSeparator为字段方法$field->prefix()$field->suffix()$field->wrap()(“affix”是“prefix”和“suffix”的总称)设置了默认分隔符。其默认值是一个空字符串:''

您可以在config.php文件中更改这两个默认值。

// /site/config/config.php

return [
  'trych.field-composer' => [
    'mergeSeparator' => ' | ',
    'affixSeparator' => ' '
  ]
];

如果在一个提到的字段方法的调用中明确提供了一个分隔符,它将覆盖这些选项以执行特定操作。

贡献

如果您遇到任何问题或有建议,请创建一个新的问题

许可证

MIT许可证© 2024 Timo Rychert