Jelajahi Sumber

Merge remote-tracking branch 'origin/master'

igb 6 bulan lalu
induk
melakukan
03e0e065fb

+ 0 - 5
app/Admin/Controllers/BaseProductController.php

@@ -3,7 +3,6 @@
 namespace App\Admin\Controllers;
 namespace App\Admin\Controllers;
 
 
 use App\Admin\Repositories\BaseProduct;
 use App\Admin\Repositories\BaseProduct;
-use App\Models\BaseProduct as baseProductModel;
 use Dcat\Admin\Admin;
 use Dcat\Admin\Admin;
 use Dcat\Admin\Form;
 use Dcat\Admin\Form;
 use Dcat\Admin\Form\NestedForm;
 use Dcat\Admin\Form\NestedForm;
@@ -55,8 +54,6 @@ class BaseProductController extends AdminController
         });
         });
     }
     }
 
 
-
-
     /**
     /**
      * Make a show builder.
      * Make a show builder.
      *
      *
@@ -89,7 +86,6 @@ class BaseProductController extends AdminController
                     $table .= '</table>';
                     $table .= '</table>';
                     return $table;
                     return $table;
                 }
                 }
-
                 return ''; // 当没有数组数据时
                 return ''; // 当没有数组数据时
             })->unescape();
             })->unescape();
             $show->field('images')->as(function ($images) {
             $show->field('images')->as(function ($images) {
@@ -144,7 +140,6 @@ class BaseProductController extends AdminController
                     return $paths;
                     return $paths;
                 });
                 });
             $form->editor('content');
             $form->editor('content');
-            //$form->number('order');
             $form->switch('is_pinned')->default(0);
             $form->switch('is_pinned')->default(0);
             $form->switch('enabled')->default(1);
             $form->switch('enabled')->default(1);
             //插入JS
             //插入JS

+ 3 - 4
app/Admin/Controllers/BaseVideoController.php

@@ -32,7 +32,7 @@ class BaseVideoController extends AdminController
      */
      */
     protected function grid()
     protected function grid()
     {
     {
-        return Grid::make(new BaseVideo(), function (Grid $grid) {
+        return Grid::make(BaseVideo::with(['baseVideoCategory']), function (Grid $grid) {
             $grid->column('id')->sortable();
             $grid->column('id')->sortable();
             $grid->column('title');
             $grid->column('title');
             $grid->column('base_video_category.name','Category Name');
             $grid->column('base_video_category.name','Category Name');
@@ -52,7 +52,7 @@ class BaseVideoController extends AdminController
                 ]);
                 ]);
             });
             });
             //排序
             //排序
-           // $grid->orderby->()->orderBy("order",'asc');
+            $grid->model()->orderBy("is_pinned",'desc')->orderBy("order",'desc');
             //按钮
             //按钮
         });
         });
     }
     }
@@ -66,7 +66,7 @@ class BaseVideoController extends AdminController
      */
      */
     protected function detail($id)
     protected function detail($id)
     {
     {
-        return Show::make($id, BaseVideo::with(['']), function (Show $show) {
+        return Show::make($id, BaseVideo::with(['baseVideoCategory']), function (Show $show) {
             $show->field('id');
             $show->field('id');
             $show->field('title');
             $show->field('title');
             $show->field('base_video_category.name','Category Name');
             $show->field('base_video_category.name','Category Name');
@@ -97,7 +97,6 @@ class BaseVideoController extends AdminController
             $form->editor('remark');
             $form->editor('remark');
             $form->switch('is_pinned')->default(0);
             $form->switch('is_pinned')->default(0);
             $form->switch('enabled')->default(1);
             $form->switch('enabled')->default(1);
-
         });
         });
     }
     }
 }
 }

+ 3 - 0
app/Admin/Repositories/BaseVideo.php

@@ -13,4 +13,7 @@ class BaseVideo extends EloquentRepository
      * @var string
      * @var string
      */
      */
     protected $eloquentClass = Model::class;
     protected $eloquentClass = Model::class;
+
+
+
 }
 }

+ 3 - 1
app/Models/BaseProduct.php

@@ -2,6 +2,7 @@
 
 
 namespace App\Models;
 namespace App\Models;
 
 
+use App\Traits\SortableTraitPinned;
 use Dcat\Admin\Traits\HasDateTimeFormatter;
 use Dcat\Admin\Traits\HasDateTimeFormatter;
 
 
 use Dcat\Admin\Traits\ModelTree;
 use Dcat\Admin\Traits\ModelTree;
@@ -12,7 +13,7 @@ use Spatie\EloquentSortable\SortableTrait;
 class BaseProduct extends Model implements Sortable
 class BaseProduct extends Model implements Sortable
 {
 {
     use HasDateTimeFormatter;
     use HasDateTimeFormatter;
-    use SortableTrait;
+    use SortableTraitPinned;
 
 
     protected $table = 'base_product';
     protected $table = 'base_product';
 
 
@@ -38,4 +39,5 @@ class BaseProduct extends Model implements Sortable
     {
     {
         return $this->hasMany(BaseProductImage::class, 'product_id');
         return $this->hasMany(BaseProductImage::class, 'product_id');
     }
     }
+
 }
 }

+ 2 - 1
app/Models/BaseVideo.php

@@ -7,11 +7,12 @@ use Dcat\Admin\Traits\HasDateTimeFormatter;
 use Illuminate\Database\Eloquent\Model;
 use Illuminate\Database\Eloquent\Model;
 use Spatie\EloquentSortable\Sortable;
 use Spatie\EloquentSortable\Sortable;
 use Spatie\EloquentSortable\SortableTrait;
 use Spatie\EloquentSortable\SortableTrait;
+use App\Traits\SortableTraitPinned;
 
 
 class BaseVideo extends Model implements Sortable
 class BaseVideo extends Model implements Sortable
 {
 {
 	use HasDateTimeFormatter;
 	use HasDateTimeFormatter;
-    use SortableTrait;
+    use SortableTraitPinned;
     protected $table = 'base_video';
     protected $table = 'base_video';
 
 
     // 可选:你可以在这里自定义排序配置
     // 可选:你可以在这里自定义排序配置

+ 17 - 1
app/Providers/AppServiceProvider.php

@@ -2,6 +2,8 @@
 
 
 namespace App\Providers;
 namespace App\Providers;
 
 
+use Illuminate\Support\Facades\DB;
+use Illuminate\Support\Facades\Log;
 use Illuminate\Support\ServiceProvider;
 use Illuminate\Support\ServiceProvider;
 
 
 class AppServiceProvider extends ServiceProvider
 class AppServiceProvider extends ServiceProvider
@@ -24,6 +26,20 @@ class AppServiceProvider extends ServiceProvider
      */
      */
     public function boot()
     public function boot()
     {
     {
-        //
+        //把SQL输出到日志中
+        if ($this->app->environment('local')) { // 仅在本地环境启用
+            DB::listen(function ($query) {
+                // 格式化 SQL 语句
+                $sql = $query->sql;
+                foreach ($query->bindings as $binding) {
+                    $sql = preg_replace('/\?/', "'" . addslashes($binding) . "'", $sql, 1);
+                }
+                // 输出到控制台
+                //dump($sql . ' [' . $query->time . 'ms]');
+                //输出到log
+                Log::info($sql . ' [' . $query->time . 'ms]');
+            });
+        }
+
     }
     }
 }
 }

+ 227 - 0
app/Traits/SortableTraitPinned.php

@@ -0,0 +1,227 @@
+<?php
+
+namespace App\Traits;
+
+use ArrayAccess;
+use Illuminate\Database\Eloquent\Builder;
+use Illuminate\Database\Eloquent\SoftDeletingScope;
+use Illuminate\Support\Facades\Event;
+use InvalidArgumentException;
+use Spatie\EloquentSortable\EloquentModelSortedEvent;
+use Spatie\EloquentSortable\Sortable;
+
+/*
+ * 列表排序is_pinned desc,order desc时用这个trait
+ */
+trait SortableTraitPinned
+{
+    public static function bootSortableTraitPinned()
+    {
+        static::creating(function ($model) {
+            if ($model instanceof Sortable && $model->shouldSortWhenCreating()) {
+                $model->setHighestOrderNumber();
+            }
+        });
+    }
+
+    public function setHighestOrderNumber(): void
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+
+        $this->$orderColumnName = $this->getHighestOrderNumber() + 1;
+    }
+
+    public function getHighestOrderNumber(): int
+    {
+        return (int)$this->buildSortQuery()->max($this->determineOrderColumnName());
+    }
+
+    public function getLowestOrderNumber(): int
+    {
+        return (int)$this->buildSortQuery()->min($this->determineOrderColumnName());
+    }
+
+    public function scopeOrdered(Builder $query, string $direction = 'asc')
+    {
+        return $query->orderBy($this->determineOrderColumnName(), $direction);
+    }
+
+    public static function setNewOrder(
+        $ids,
+        int $startOrder = 1,
+        string $primaryKeyColumn = null,
+        callable $modifyQuery = null
+    ): void {
+        if (! is_array($ids) && ! $ids instanceof ArrayAccess) {
+            throw new InvalidArgumentException('You must pass an array or ArrayAccess object to setNewOrder');
+        }
+
+        $model = new static();
+
+        $orderColumnName = $model->determineOrderColumnName();
+
+        if (is_null($primaryKeyColumn)) {
+            $primaryKeyColumn = $model->getQualifiedKeyName();
+        }
+
+        if (config('eloquent-sortable.ignore_timestamps', false)) {
+            static::$ignoreTimestampsOn = array_values(array_merge(static::$ignoreTimestampsOn, [static::class]));
+        }
+
+        foreach ($ids as $id) {
+            static::withoutGlobalScope(SoftDeletingScope::class)
+                ->when(is_callable($modifyQuery), function ($query) use ($modifyQuery) {
+                    return $modifyQuery($query);
+                })
+                ->where($primaryKeyColumn, $id)
+                ->update([$orderColumnName => $startOrder++]);
+        }
+
+        Event::dispatch(new EloquentModelSortedEvent(static::class));
+
+        if (config('eloquent-sortable.ignore_timestamps', false)) {
+            static::$ignoreTimestampsOn = array_values(array_diff(static::$ignoreTimestampsOn, [static::class]));
+        }
+    }
+
+    public static function setNewOrderByCustomColumn(string $primaryKeyColumn, $ids, int $startOrder = 1)
+    {
+        self::setNewOrder($ids, $startOrder, $primaryKeyColumn);
+    }
+
+    public function determineOrderColumnName(): string
+    {
+        return $this->sortable['order_column_name'] ?? config('eloquent-sortable.order_column_name', 'order_column');
+    }
+
+    /**
+     * Determine if the order column should be set when saving a new model instance.
+     */
+    public function shouldSortWhenCreating(): bool
+    {
+        return $this->sortable['sort_when_creating'] ?? config('eloquent-sortable.sort_when_creating', true);
+    }
+
+    /*
+     * 由于排序在order desc时会出错,所以这里重写了 SortableTrait 中 moveOrderDown 和 moveOrderUp方法
+     */
+    public function moveOrderDown(): static
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+        $swapWithModel = $this->buildSortQuery()->limit(1)
+            ->orderBy('is_pinned', 'desc')->orderBy('order', 'desc')
+            ->where($orderColumnName, '<', $this->$orderColumnName)
+            ->first();
+
+        if (! $swapWithModel) {
+            return $this;
+        }
+
+        if (($this->is_pinned == 1 && $swapWithModel->is_pinned == 0)
+            || ($this->is_pinned == 0 && $swapWithModel->is_pinned == 1)) {
+            throw new \Exception('No sorting allowed');
+        }
+        return $this->swapOrderWithModel($swapWithModel);
+    }
+    public function moveOrderUp(): static
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+
+        $swapWithModel = $this->buildSortQuery()->limit(1)
+            ->orderBy('is_pinned', 'asc')->orderBy('order', 'asc')
+            ->where($orderColumnName, '>', $this->$orderColumnName)
+            ->first();
+
+        if (! $swapWithModel) {
+            return $this;
+        }
+
+        if (($this->is_pinned == 1 && $swapWithModel->is_pinned == 0)
+            || ($this->is_pinned == 0 && $swapWithModel->is_pinned == 1)) {
+            throw new \Exception('No sorting allowed');
+        }
+        return $this->swapOrderWithModel($swapWithModel);
+    }
+    public function swapOrderWithModel(Sortable $otherModel): static
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+
+        $oldOrderOfOtherModel = $otherModel->$orderColumnName;
+
+        $otherModel->$orderColumnName = $this->$orderColumnName;
+        $otherModel->save();
+
+        $this->$orderColumnName = $oldOrderOfOtherModel;
+        $this->save();
+
+        return $this;
+    }
+
+    public static function swapOrder(Sortable $model, Sortable $otherModel): void
+    {
+        $model->swapOrderWithModel($otherModel);
+    }
+
+    public function moveToStart(): static
+    {
+        $firstModel = $this->buildSortQuery()->limit(1)
+            ->ordered()
+            ->first();
+
+        if ($firstModel->getKey() === $this->getKey()) {
+            return $this;
+        }
+
+        $orderColumnName = $this->determineOrderColumnName();
+
+        $this->$orderColumnName = $firstModel->$orderColumnName;
+        $this->save();
+
+        $this->buildSortQuery()->where($this->getQualifiedKeyName(), '!=', $this->getKey())->increment(
+            $orderColumnName
+        );
+
+        return $this;
+    }
+
+    public function moveToEnd(): static
+    {
+        $maxOrder = $this->getHighestOrderNumber();
+
+        $orderColumnName = $this->determineOrderColumnName();
+
+        if ($this->$orderColumnName === $maxOrder) {
+            return $this;
+        }
+
+        $oldOrder = $this->$orderColumnName;
+
+        $this->$orderColumnName = $maxOrder;
+        $this->save();
+
+        $this->buildSortQuery()->where($this->getQualifiedKeyName(), '!=', $this->getKey())
+            ->where($orderColumnName, '>', $oldOrder)
+            ->decrement($orderColumnName);
+
+        return $this;
+    }
+
+    public function isLastInOrder(): bool
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+
+        return (int)$this->$orderColumnName === $this->getHighestOrderNumber();
+    }
+
+    public function isFirstInOrder(): bool
+    {
+        $orderColumnName = $this->determineOrderColumnName();
+
+        return (int)$this->$orderColumnName === $this->getLowestOrderNumber();
+    }
+
+    public function buildSortQuery(): Builder
+    {
+        return static::query();
+    }
+}