bscheshirwork/yii2-trello-like-jui-sortable

将面板从一列移动到另一列的端口

dev-master 2018-04-23 13:28 UTC

This package is auto-updated.

Last update: 2024-09-08 07:18:09 UTC


README

这是一个小部件,用于在面板中显示您的数据并将其在列之间移动。

每次成功的移动都会向您的后端产生请求。

安装

将以下内容添加到您的 require 部分 composer.json

"bscheshirwork/yii2-trello-like-jui-sortable": "*",

使用方法

示例:您有一个bindStatus连接表。您希望按状态排序。

将列和内容添加到 index-drag-and-drop 视图文件(views/board/index-drag-and-drop)中。

    <?php
    TrelloLikeSortable::begin([
        'targetAction' => '/board/drop-finish',
    ]);
    ?>

    <?php foreach ($columns as $columnModel):?>

    <div class="column" id="column<?= $columnModel->id ?>">
        <div class="column-header"><?= $columnModel->name ?></div>
        <?php foreach (array_key_exists($columnModel->id, $dataProviders) ? $dataProviders[$columnModel->id]->models ?? [] : [] as $model):?>
        <div class="portlet" id="item<?= $model->id ?>">
            <div class="portlet-header"><?=$model->name?></div>
            <div class="portlet-content"><?=$model->description?></div>
        </div>

        <?php endforeach;?>
    </div>
    <?php endforeach;?>


    <?php
    TrelloLikeSortable::end();
    ?>

BoardController 中添加 index-drag-and-drop 动作以显示网格,并添加 drop-finish

    /**
     * Lists all Lead models.
     * @return mixed
     */
    public function actionIndexDragAndDrop()
    {
        $searchModel = new BoardSearch();
        $dataProvider = $searchModel->search(Yii::$app->request->queryParams);
        $columns = Status::find()->active()->indexBy('id')->all();
        $dataProviders = $searchModel->dataProviderByStatusList($dataProvider, $columns);

        return $this->render('index-drag-and-drop', [
            'searchModel' => $searchModel,
            'dataProviders' => $dataProviders,
            'columns' => $columns,
        ]);
    }

    /**
     * Accept result of drag-and-drop event TrelloLikeSortable
     * @return bool
     */
    public function actionDropFinish() {
        $model = (new \yii\base\DynamicModel(['item' => null, 'column' => null, 'next' => null]))
            ->addRule('item', 'filter', ['filter' => function ($value) { return strtr($value, ['item' => '']); }])
            ->addRule('column', 'filter', ['filter' => function ($value) { return strtr($value, ['column' => '']); }])
            ->addRule('next', 'filter', ['filter' => function ($value) { return strtr($value, ['item' => '']); }])
            ->addRule('item', 'integer')
            ->addRule('column', 'integer')
            ->addRule('next', 'integer');
        $result = $model->load(Yii::$app->request->post(), '');
        $result &= $model->validate();
        /** todo: add buiseness logic here */

        return (bool) $result;
    }

将搜索模型 BoardSearch 添加到其中

    /**
     * Add new $dataProvider list by all active statuses
     * @param ActiveDataProvider $dataProvider
     * @param Status[] $statusList
     * @return ActiveDataProvider[]
     */
    public function dataProviderByStatusList(ActiveDataProvider $dataProvider, array $statusList = []): array
    {
        foreach ($statusList ?? [] as $id => $column) {
            $result[$id] = $this->dataProviderByStatus($dataProvider, $column);
        }

        return $result ?? [];
    }

    /**
     * Add new clone of $dataProvider with additional condition: last of binding status for passed status
     * @param ActiveDataProvider $dataProvider
     * @param Status $status
     * @return ActiveDataProvider
     */
    public function dataProviderByStatus(ActiveDataProvider $dataProvider, Status $status): ActiveDataProvider
    {
        $dataProviderItem = clone $dataProvider;
        /** @var ActiveQuery $query */
        $query = $dataProviderItem->query = clone $dataProviderItem->query;
        $query->joinWith([
            'bindStatuses' => function (\common\models\BindStatusQuery $query) {
                $query->lastBy('leadId');
            },
        ])->andWhere([\common\models\BindStatus::tableName() . '.statusId' => $status->id]);

        return $dataProviderItem;
    }

将ActiveQuery类添加到连接表 / 添加到特性中

    /**
     * Add to query latest by time
     * SELECT id, createdAt, updatedAt From bind_status where GREATEST(createdAt, updatedAt) =
     * ( select max(GREATEST(createdAt, updatedAt)) from bind_status as i where i.leadId=bind_status.leadId )
     * @param $group string the group field of junction table. Group by relation to main table.
     * @throws \yii\base\InvalidConfigException
     */
    public function lastBy($group) {
        /** @var ActiveQuery $subquery */
        $subquery = \Yii::createObject(static::class, [$this->modelClass]);
        $mainAlias = $this->getPrimaryTableName();
        $alias = strtr($subquery->getPrimaryTableName(), [ '{{%' => '{{%inner_']);
        $subquery->alias($alias)
        ->select('max(GREATEST(' . $alias . '.`createdAt`, ' . $alias . '.`updatedAt`))')
        ->andWhere($alias . '.`' . $group . '` = '. $mainAlias . '.`' . $group . '` ');

        $this->andWhere(['=', 'GREATEST('. $mainAlias . '.`createdAt`, '. $mainAlias . '.`updatedAt`)', $subquery]);
    }