microweber-deps/livewire-modal

Laravel Livewire 模态组件

dev-main 2023-07-21 07:39 UTC

This package is auto-updated.

Last update: 2024-09-21 10:12:21 UTC


README

Build Status Total Downloads Total Downloads Latest Stable Version License

关于 Wire Elements Modal

Wire Elements Modal 是一个 Livewire 组件,它提供了一个支持多个子模态并保持状态的模态框。

安装

点击上面的图片阅读关于使用 Wire Elements modal 包的完整文章,或者按照下面的说明操作。

要开始使用,通过 Composer 需求此包

composer require wire-elements/modal

Livewire 指令

将 Livewire 指令 @livewire('livewire-ui-modal') 添加到您的模板中。

<html>
<body>
    <!-- content -->

    @livewire('livewire-ui-modal')
</body>
</html>

Alpine

Wire Elements Modal 需要 Alpine 和插件 Focus。您可以使用官方 CDN 快速包含 Alpine。

<!-- Alpine v3 -->
<script defer src="https://unpkg.com/alpinejs@3.x.x/dist/cdn.min.js"></script>

<!-- Focus plugin -->
<script defer src="https://unpkg.com/@alpinejs/focus@3.x.x/dist/cdn.min.js"></script>

TailwindCSS

基础模态框使用 TailwindCSS 制作。如果您使用不同的 CSS 框架,我建议您发布模态模板并更改标记以包含您 CSS 框架所需的类。

php artisan vendor:publish --tag=livewire-ui-modal-views

创建模态框

您可以通过运行 php artisan make:livewire EditUser 创建初始 Livewire 组件。打开您的组件类并确保它扩展了 ModalComponent 类。

<?php

namespace App\Http\Livewire;

use LivewireUI\Modal\ModalComponent;

class EditUser extends ModalComponent
{
    public function render()
    {
        return view('livewire.edit-user');
    }
}

打开模态框

要打开模态框,您需要发出一个事件。例如,要打开 EditUser 模态框

<!-- Outside of any Livewire component -->
<button onclick="Livewire.emit('openModal', 'edit-user')">Edit User</button>

<!-- Inside existing Livewire component -->
<button wire:click="$emit('openModal', 'edit-user')">Edit User</button>

<!-- Taking namespace into account for component Admin/Actions/EditUser -->
<button wire:click="$emit('openModal', 'admin.actions.edit-user')">Edit User</button>

传递参数

要为特定用户打开 EditUser 模态框,我们可以传递用户 ID

<!-- Outside of any Livewire component -->
<button onclick="Livewire.emit('openModal', 'edit-user', {{ json_encode(['user' => $user->id]) }})">Edit User</button>

<!-- Inside existing Livewire component -->
<button wire:click="$emit('openModal', 'edit-user', {{ json_encode(['user' => $user->id]) }})">Edit User</button>

<!-- If you use a different primaryKey (e.g. email), adjust accordingly -->
<button wire:click="$emit('openModal', 'edit-user', {{ json_encode(['user' => $user->email]) }})">Edit User</button>

<!-- Example of passing multiple parameters -->
<button wire:click="$emit('openModal', 'edit-user', {{ json_encode([$user->id, $isAdmin]) }})">Edit User</button>

参数被注入到模态组件中,并且如果已定义类型,将自动从数据库中获取模型。

<?php

namespace App\Http\Livewire;

use App\Models\User;
use LivewireUI\Modal\ModalComponent;

class EditUser extends ModalComponent
{
    // This will inject just the ID
    // public int $user;

    public User $user;

    public function mount()
    {
        Gate::authorize('update', $this->user);
    }

    public function render()
    {
        return view('livewire.edit-user');
    }
}

参数也被传递到模态组件上的 mount 方法。

打开子模态框

从现有的模态框中,您可以使用完全相同的事件创建子模态框。

<!-- Edit User Modal -->

<!-- Edit Form -->

<button wire:click='$emit("openModal", "delete-user", {{ json_encode(["user" => $user->id]) }})'>Delete User</button>

关闭(子)模态框

例如,如果用户点击“删除”按钮,将打开一个确认对话框,您可以通过发出 closeModal 事件取消删除并返回到编辑用户模态框。这将打开之前的模态框。如果没有之前的模态框,则整个模态组件将被关闭并重置状态。

<button wire:click="$emit('closeModal')">No, do not delete</button>

您还可以在模态组件类内部关闭模态框。

<?php

namespace App\Http\Livewire;

use App\Models\User;
use LivewireUI\Modal\ModalComponent;

class EditUser extends ModalComponent
{
    public User $user;

    public function mount()
    {
        Gate::authorize('update', $this->user);
    }

    public function update()
    {
        Gate::authorize('update', $this->user);

        $this->user->update($data);

        $this->closeModal();
    }

    public function render()
    {
        return view('livewire.edit-user');
    }
}

如果您不想回到上一个模态框但想关闭整个模态组件,您可以使用 forceClose 方法。

public function update()
{
    Gate::authorize('update', $this->user);

    $this->user->update($data);

    $this->forceClose()->closeModal();
}

通常,当更改发生后,您会希望更新其他 Livewire 组件。例如,当用户更新时,更新用户概览。您可以使用 closeModalWithEvents 方法来实现这一点。

public function update()
{
    Gate::authorize('update', $this->user);

    $this->user->update($data);

    $this->closeModalWithEvents([
        UserOverview::getName() => 'userModified',
    ]);
}

您也可以向事件添加参数

public function update()
{
    $this->user->update($data);

    $this->closeModalWithEvents([
        UserOverview::getName() => ['userModified', [$this->user->id]],
    ]);
}

更改模态属性

您可以通过在模态组件类中覆盖静态 modalMaxWidth 方法来更改模态框的宽度(默认值 '2xl')。

/**
 * Supported: 'sm', 'md', 'lg', 'xl', '2xl', '3xl', '4xl', '5xl', '6xl', '7xl'
 */
public static function modalMaxWidth(): string
{
    return 'xl';
}

默认情况下,当您按下 escape 键时,模态框将关闭。如果您想禁用此行为,例如防止意外关闭模态框,您可以通过覆盖静态 closeModalOnEscape 方法并使其返回 false 来实现。

public static function closeModalOnEscape(): bool
{
    return false;
}

默认情况下,当您点击模态框外部时,模态框将关闭。如果您想禁用此行为,例如防止意外关闭模态框,您可以通过覆盖静态 closeModalOnClickAway 方法并使其返回 false 来实现。

public static function closeModalOnClickAway(): bool
{
    return false;
}

默认情况下,通过按Esc键关闭模态框会强制关闭所有模态框。如果您想禁用此行为,例如,允许按Esc键显示上一个模态框,您可以重写静态方法 closeModalOnEscapeIsForceful 并使其返回 false

public static function closeModalOnEscapeIsForceful(): bool
{
    return false;
}

当一个模态框关闭时,您可以选择启用 modalClosed 事件。此事件会在调用 closeModal 时触发,当按下Esc键或您点击模态框外部时。关闭组件的名称将作为参数提供;

public static function dispatchCloseEvent(): bool
{
    return true;
}

默认情况下,当关闭子模态框时,如果再次打开相同的模态框组件,关闭组件的状态仍然可用。如果您希望在关闭组件时销毁组件,可以重写静态方法 destroyOnClose 并使其返回 true。当再次打开已销毁的模态框时,其状态将被重置。

public static function destroyOnClose(): bool
{
    return true;
}

跳过上一个模态框

在某些情况下,您可能想跳过上一个模态框。例如

  1. 团队概览模态框
  2. -> 编辑团队
  3. -> 删除团队

在这种情况下,当团队被删除时,您不想返回到第2步,而是返回到概览页。您可以使用 skipPreviousModal 方法实现这一点。默认情况下,它将跳过上一个模态框。如果您想跳过更多,可以传递要跳过的模态框数量 skipPreviousModals(2)

<?php

namespace App\Http\Livewire;

use App\Models\Team;
use LivewireUI\Modal\ModalComponent;

class DeleteTeam extends ModalComponent
{
    public Team $team;

    public function mount(Team $team)
    {
        $this->team = $team;
    }

    public function delete()
    {
        Gate::authorize('delete', $this->team);

        $this->team->delete();

        $this->skipPreviousModal()->closeModalWithEvents([
            TeamOverview::getName() => 'teamDeleted'
        ]);
    }

    public function render()
    {
        return view('livewire.delete-team');
    }
}

您还可以选择调用 destroySkippedModals() 方法销毁跳过的模态框,这样如果再次打开它们,它们的状态将被重置

为生产构建 Tailwind CSS

要清除包中使用的类,请将以下行添加到您的 tailwind.config.js 中的 purge 数组

'./vendor/wire-elements/modal/resources/views/*.blade.php',
'./storage/framework/views/*.php',

由于一些类是动态构建的,您应该将一些类添加到 purge 安全列表中,因此您的 tailwind.config.js 应该看起来像这样

module.exports = {
  purge: {
    content: [
      './vendor/wire-elements/modal/resources/views/*.blade.php',
      './storage/framework/views/*.php',
      './resources/views/**/*.blade.php',
    ],
    options: {
      safelist: [
        'sm:max-w-2xl'
      ]
    }
  },
  darkMode: false, // or 'media' or 'class'
  theme: {
    extend: {},
  },
  variants: {
    extend: {},
  },
  plugins: [],
}

配置

您可以通过 livewire-ui-modal.php 配置文件来自定义模态框。这包括一些额外的选项,例如,如果您不使用 TailwindCSS 为您的应用程序,则包含CSS,以及默认模态框属性。

要发布配置,请运行 vendor:publish 命令

php artisan vendor:publish --tag=livewire-ui-modal-config
<?php

return [

    /*
    |--------------------------------------------------------------------------
    | Include CSS
    |--------------------------------------------------------------------------
    |
    | The modal uses TailwindCSS, if you don't use TailwindCSS you will need
    | to set this parameter to true. This includes the modern-normalize css.
    |
    */
    'include_css' => false,


    /*
    |--------------------------------------------------------------------------
    | Include JS
    |--------------------------------------------------------------------------
    |
    | Livewire UI will inject the required Javascript in your blade template.
    | If you want to bundle the required Javascript you can set this to false
    | and add `require('vendor/wire-elements/modal/resources/js/modal');`
    | to your script bundler like webpack.
    |
    */
    'include_js' => true,


    /*
    |--------------------------------------------------------------------------
    | Modal Component Defaults
    |--------------------------------------------------------------------------
    |
    | Configure the default properties for a modal component.
    |
    | Supported modal_max_width
    | 'sm', 'md', 'lg', 'xl', '2xl', '3xl', '4xl', '5xl', '6xl', '7xl'
    */
    'component_defaults' => [
        'modal_max_width' => '2xl',

        'close_modal_on_click_away' => true,

        'close_modal_on_escape' => true,

        'close_modal_on_escape_is_forceful' => true,

        'dispatch_close_event' => false,

        'destroy_on_close' => false,
    ],
];

安全

如果您是 Livewire 新手,我建议您查看 安全细节。简而言之,这 非常重要,因为所有信息都必须经过验证,Livewire 在客户端存储这些信息,换句话说,这些数据可以被操纵。像上面示例中那样,使用 Gate 门面来授权操作。

鸣谢

许可协议

WireElements 是开源软件,许可协议为 MIT 协议

使用 Livewire 精心制作的美丽组件