php laravel管理员相关类库
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了php laravel管理员相关类库相关的知识,希望对你有一定的参考价值。
# laravel-admin的代码片段
## laravel的switch
修改form下的开关为中文文案
SwitchField.php
其中动态修改单个值,通过:
```php
$form->switch('charge_type', '房间属性')->states([
'on.text' => '计费', // 1
'off.text' => '免费', // 0
]);
```
## 一个按钮,点击复制值
LongUrl.php
## Form
> AsyncRender
## column
> ExpandRow
## laravel-admin生成控制器代码
有4个文件:
> controller.stub
> controller.show.stub
> MakeTemplateControllerCommand.php
> ResourceGenerator.php
<?php
namespace App\Admin\Extensions\Grid;
use Encore\Admin\Grid\Displayers\AbstractDisplayer;
use Qiniu\Processing\ImageUrlBuilder;
/**
* laravel-admin里显示小图片
* 可以用来显示多个小图片
* 图片基于七牛
* 需要继承
*
* Class ShowSmallImage
* @package App\Admin\Extensions\Grid
*/
abstract class ShowSmallImageBase extends AbstractDisplayer
{
protected $width = 80;
protected $height = 60;
protected $model = 2;
/**
* 图片地址的分割符
*
* @var string
*/
protected $delimiter = ',';
/**
* 配置filesystems.disk里的key
* 需定义
*
* @abstract
* @var string|null
*/
protected $disk = null;
/**
* 显示七牛小图
*
* $grid->column('img', '图片')->showSmallImage();
*
* @return array|mixed|string
*/
public function display()
{
$args = func_get_args();
$this->model = $args[0] ?? $this->model;
$this->width = $args[1] ?? $this->width; // 可改为small类型
$this->height = $args[2] ?? $this->height;
$value = $this->value;
if (empty($value)) {
return '';
}
if (is_string($value)) {
$value = explode($this->delimiter, $value);
}
$html = '';
foreach ($value as $image) {
$html .= $this->imgHtml($image);
}
return $html;
}
protected function imgHtml($image)
{
if (empty($image)) {
return '';
}
if (!ifStartHttp($image)) { // 不自带域名
$image = $this->handleNotStartHttp($image);
}
$image = $this->handleQiNiu($image);
return "<img src=\"{$image}\" width=\"{$this->width}\" height=\"{$this->height}\" />";
}
protected function ifQiNiuPic($image)
{
$domain = getStorageConfig('domain', $this->disk);
$domain = parse_url($domain, PHP_URL_HOST);
return ifStartHttp($image, $domain);
}
protected function handleQiNiu($image)
{
if (!$this->ifQiNiuPic($image)) {
return $image;
}
return (new ImageUrlBuilder())->thumbnail($image, $this->model, $this->width, $this->height);
}
abstract protected function handleNotStartHttp($image);
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2018/3/5
* Time: 下午2:54
*/
namespace App\Admin\Extensions\Form;
class SwitchField extends \Encore\Admin\Form\Field\SwitchField
{
protected $states = [
'on' => ['value' => 1, 'text' => '是', 'color' => 'success'],
'off' => ['value' => 0, 'text' => '否', 'color' => 'danger'],
];
}
<?php
namespace App\Admin\Extensions\Grid;
/**
* 修改默认开关的文案(改为中文)
*
* @package App\Admin\Extensions\Form
*/
class SwitchDisplay extends \Encore\Admin\Grid\Displayers\SwitchDisplay
{
protected $states = [
'on' => ['value' => 1, 'text' => '是', 'color' => 'success'],
'off' => ['value' => 0, 'text' => '否', 'color' => 'danger'],
];
}
<?php
namespace App\Admin\Extensions\Grid;
use Encore\Admin\Grid\Displayers\AbstractDisplayer;
class SelectText extends AbstractDisplayer
{
/**
* 在数组中显示对应值的文案
*
* $grid->column('type', '类型')->selectText($typeArr);
*
* @return array|mixed|string
*/
public function display()
{
$data = current(func_get_args());
$value = $this->value;
if (!isset($value)) {
return '';
}
return $data[$value]??'';
}
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2018/3/5
* Time: 下午3:02
*/
namespace App\Admin\Extensions\Grid;
use Encore\Admin\Admin;
use Encore\Admin\Grid\Displayers\AbstractDisplayer;
/**
* 一个按钮,点击复制值
*
* Class longUrl
* @package App\Admin\Extensions\Grid
*/
class LongUrl extends AbstractDisplayer
{
const ID_CLIPBOARD_JS = 'id-clipboard-js';
public function display()
{
$name = $this->column->getName();
$class = "grid-long-url-{$name}";
$jsId = self::ID_CLIPBOARD_JS;
$script = <<<EOT
if (window['Clipboard']){
new Clipboard('.{$class}')
}else{
$('#{$jsId}').ready(function (){
setTimeout(function (){
if (window['Clipboard']){
new Clipboard('.{$class}')
}else{
console.error('还是没有Clipboard');
}
}, 0);
});
}
EOT;
// 一定要在\Encore\Admin\Layout\Content中添加row,一个script,否则异步的pjax就会过滤掉js加载
// \Encore\Admin\Admin::js('https://cdn.staticfile.org/clipboard.js/1.5.16/clipboard.min.js');
Admin::script($script);
return <<<EOT
<button class="{$class} btn btn-default" data-clipboard-text="{$this->value}" title="{$this->value}">复制</button>
EOT;
}
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2019/4/3
* Time: 17:23
*/
namespace App\Admin\Extensions\Form;
/**
* 解决null值保存,强制转换为string
*/
class Text extends \Encore\Admin\Form\Field\Text
{
public function prepare($value)
{
return (string)parent::prepare($value);
}
}
<!-- 放在resources/views/vendor/laravel-admin-logs/logs.blade.php中 -->
<script data-exec-on-popstate>
$(function () {
LA.intervalIds = [];
LA.addIntervalId = function (intervalId, persist) {
this.intervalIds.push({id:intervalId, persist:persist});
};
LA.clearIntervalId = function (intervalId) {
for (var id in this.intervalIds) {
if (intervalId == this.intervalIds[id].id && !this.intervalIds[id].persist) {
clearInterval(intervalId);
this.intervalIds.splice(id, 1);
}
}
};
LA.cleanIntervalId = function () {
for (var id in this.intervalIds) {
if (!this.intervalIds[id].persist) {
clearInterval(this.intervalIds[id].id);
this.intervalIds.splice(id, 1);
}
}
};
$(document).on('pjax:complete', function(xhr) {
$.admin.cleanIntervalId();
});
$('.log-refresh').on('click', function() {
$.pjax.reload('#pjax-container');
});
var pos = {{ $end }};
function changePos(offset){
pos = offset;
}
// 此处修改,增加fetch结束的变量
var fetchWait = 1;
function fetch() {
if (fetchWait){
fetchWait = 0;
}else{
return;
}
$.ajax({
url:'{{ $tailPath }}',
method: 'get',
data : {offset : pos},
success:function(data) {
fetchWait = 1;
for (var i in data.logs) {
$('table > tbody > tr:first').before(data.logs[i]);
}
changePos(data.pos);
}
});
}
var refreshIntervalId = null;
$('.log-live').click(function() {
$("i", this).toggleClass("fa-play fa-pause");
if (refreshIntervalId) {
$.admin.clearIntervalId(refreshIntervalId);
refreshIntervalId = null;
} else {
refreshIntervalId = setInterval(function() {
fetch();
}, 2000);
$.admin.addIntervalId(refreshIntervalId, false);
}
});
});
</script>
<div class="row">
<!-- /.col -->
<div class="col-md-10">
<div class="box box-primary">
<div class="box-header with-border">
<button type="button" class="btn btn-primary btn-sm log-refresh"><i class="fa fa-refresh"></i> {{ trans('admin.refresh') }}</button>
<button type="button" class="btn btn-default btn-sm log-live"><i class="fa fa-play"></i> </button>
<div class="pull-right">
<div class="btn-group">
@if ($prevUrl)
<a href="{{ $prevUrl }}" class="btn btn-default btn-sm"><i class="fa fa-chevron-left"></i></a>
@endif
@if ($nextUrl)
<a href="{{ $nextUrl }}" class="btn btn-default btn-sm"><i class="fa fa-chevron-right"></i></a>
@endif
</div>
<!-- /.btn-group -->
</div>
<!-- /.box-tools -->
</div>
<!-- /.box-header -->
<div class="box-body no-padding">
<div class="table-responsive">
<table class="table table-hover">
<thead>
<tr>
<th>Level</th>
<th>Env</th>
<th>Time</th>
<th>Message</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach($logs as $index => $log)
<tr>
<td><span class="label bg-{{\Encore\Admin\LogViewer\LogViewer::$levelColors[$log['level']]}}">{{ $log['level'] }}</span></td>
<td><strong>{{ $log['env'] }}</strong></td>
<td style="width:150px;">{{ $log['time'] }}</td>
<td><code style="word-break: break-all;">{{ $log['info'] }}</code></td>
<td>
@if(!empty($log['trace']))
<a class="btn btn-primary btn-xs" data-toggle="collapse" data-target=".trace-{{$index}}"><i class="fa fa-info"></i> Exception</a>
@endif
</td>
</tr>
@if (!empty($log['trace']))
<tr class="collapse trace-{{$index}}">
<td colspan="5"><div style="white-space: pre-wrap;background: #333;color: #fff; padding: 10px;">{{ $log['trace'] }}</div></td>
</tr>
@endif
@endforeach
</tbody>
</table>
<!-- /.table -->
</div>
<!-- /.mail-box-messages -->
</div>
<!-- /.box-body -->
</div>
<!-- /. box -->
</div>
<div class="col-md-2">
<div class="box box-solid">
<div class="box-header with-border">
<h3 class="box-title">Files</h3>
</div>
<div class="box-body no-padding">
<ul class="nav nav-pills nav-stacked">
@foreach($logFiles as $logFile)
<li @if($logFile == $fileName)class="active"@endif>
<a href="{{ route('log-viewer-file', ['file' => $logFile]) }}"><i class="fa fa-{{ ($logFile == $fileName) ? 'folder-open' : 'folder' }}"></i>{{ $logFile }}</a>
</li>
@endforeach
</ul>
</div>
<!-- /.box-body -->
</div>
<div class="box box-solid">
<div class="box-header with-border">
<h3 class="box-title">Info</h3>
</div>
<div class="box-body no-padding">
<ul class="nav nav-pills nav-stacked">
<li class="margin: 10px;">
<a>Size: {{ $size }}</a>
</li>
<li class="margin: 10px;">
<a>Updated at: {{ date('Y-m-d H:i:s', filectime($filePath)) }}</a>
</li>
</ul>
</div>
<!-- /.box-body -->
</div>
<!-- /.box -->
</div>
<!-- /.col -->
</div>
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2019/4/3
* Time: 10:48
*/
namespace App\Admin\Controllers;
use Encore\Admin\Layout\Content;
use Encore\Admin\Form;
use Encore\Admin\Grid;
use \App\User as Model;
abstract class AdminTemplateController extends AdminController
{
/**
* 页名
*
* @var string
*/
protected $headerText = '';
/**
* Index interface.
*
* @param Content $content
* @return Content
*/
public function index(Content $content)
{
return $content
->header('列表')
->description($this->headerText . '的列表')
->body($this->grid());
}
/**
* Edit interface.
*
* @param mixed $id
* @param Content $content
* @return Content
*/
public function edit($id, Content $content)
{
return $content
->header('编辑')
->description($this->headerText . '的编辑')
->body($this->form()->edit($id));
}
/**
* Create interface.
*
* @param Content $content
* @return Content
*/
public function create(Content $content)
{
return $content
->header('创建')
->description($this->headerText . '的创建')
->body($this->form());
}
/**
* 覆盖
* demo
*
* @return Grid
*/
protected function grid()
{
$model = new Model;
$grid = new Grid($model);
$grid->id('ID')->sortable();
$grid->created_at('创建时间');
$grid->updated_at('更新时间');
return $grid;
}
/**
* 覆盖
* demo
*
* @return Form
*/
protected function form()
{
$model = new Model;
$form = new Form($model);
$form->display('id', 'ID');
$form->display(Model::CREATED_AT, '创建时间');
$form->display(Model::UPDATED_AT, '更新时间');
return $form;
}
}
<?php
namespace DummyNamespace;
use App\Admin\Controllers\AdminTemplateController;
use DummyModelNamespace as Model;
use Encore\Admin\Form;
use Encore\Admin\Grid;
class DummyClass extends AdminTemplateController
{
DummyProtected
protected function grid()
{
$model = new Model;
$grid = new Grid($model);
DummyGrid
return $grid;
}
protected function form()
{
$model = new Model;
$form = new Form($model);
DummyForm
return $form;
}
}
<?php
namespace DummyNamespace;
use App\Admin\Controllers\AdminTemplateController;
use DummyModelNamespace as Model;
use Encore\Admin\Grid;
class DummyClass extends AdminTemplateController
{
DummyProtected
protected function grid()
{
$model = new Model;
$grid = new Grid($model);
DummyGrid
return $grid;
}
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2019/4/22
* Time: 18:18
*/
namespace App\Helper\Vendor\LaravelAdmin;
/**
* 添加到:\App\Console\Kernel::$commands
*
* @example php artisan admin:make:template_controller UserFriend
* @example php artisan admin:make:template_controller UserFriend --disSave
*/
class MakeTemplateControllerCommand extends \Encore\Admin\Console\MakeCommand
{
/**
* @var \App\Helper\Vendor\LaravelAdmin\ResourceGenerator
*/
protected $generator;
/**
* The console command name.
*
* @var string
*/
protected $signature = 'admin:make:template_controller {name}
{--model=}
{--stub= : Path to the custom stub file. }
{--O|output}
{--disSave}
{--disEdit}';
/**
* The console command description.
*
* @var string
*/
protected $description = '创建Laravel-Admin的后台控制器,根据后台模板控制器';
/**
* 入口
*
* @return void|bool
*/
public function handle()
{
$this->handleModelNull();
return parent::handle();
}
/**
* 处理model的参数为空的情况
*
* @param null $nameRec
*/
protected function handleModelNull($nameRec = null)
{
$nameArg = $this->argument('name');
if (is_null($this->option('model'))) { // 处理默认model
$name = $this->rootNamespace() . 'Models\\' . ($nameRec ?? $nameArg);
if (class_exists($name) && is_subclass_of($name, \Illuminate\Database\Eloquent\Model::class)) {
$this->input->setOption('model', $name);
}else if (is_null($nameRec)){ // 递归查(名称 + Model)的字符串
$this->handleModelNull($nameArg . 'Model');
}
}
}
/**
* 覆盖generator属性
*
* @param string $modelName
*/
protected function output($modelName)
{
$this->initResourceGenerator($modelName);
parent::output($modelName);
$this->info($this->generator->generateProtected());
}
/**
* 覆盖generator属性
*
* @param string $stub
* @param string $name
* @return string
*/
protected function replaceClass($stub, $name)
{
$this->initResourceGenerator($this->option('model'));
$stub = parent::replaceClass($stub, $name);
return str_replace(
[
'DummyProtected',
],
[
$this->indentCodes($this->generator->generateProtected()),
],
$stub
);
}
protected function initResourceGenerator($modelName)
{
$this->generator = new ResourceGenerator($modelName);
$this->generator->setDisEditBool(!!$this->option('disEdit'));
$this->generator->setDisSaveBool(!!$this->option('disSave'));
}
/**
* Get the desired class name from the input.
*
* @return string
*/
protected function getNameInput()
{
$name = trim($this->argument('name')) . 'AdminController';
$this->type = $this->qualifyClass($name);
return $name;
}
/**
* Get the stub file for the generator.
*
* @return string
*/
protected function getStub()
{
if ($stub = $this->option('stub')) {
return $stub;
}
if ($this->option('model')) {
if (!!$this->option('disSave')){ // 不需要form
return __DIR__ . '/controller.show.stub';
}
return __DIR__ . '/controller.stub';
}
return __DIR__.'/stubs/blank.stub';
}
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2019/4/22
* Time: 19:52
*/
namespace App\Helper\Vendor\LaravelAdmin;
/**
* 留意在idea中必须\r的换行符
*/
class ResourceGenerator extends \Encore\Admin\Console\ResourceGenerator
{
/**
* @var array
*/
protected $formats = [
'form_field' => "\$form->%s('%s', '%s')",
'show_field' => "\$show->%s('%s')",
'grid_column' => "\$grid->column('%s', '%s')",
'grid_filter' => "\$filter->%s('%s', '%s')", // grid的filter
'grid_filter_equal' => "\$filter->equal('%s', '%s')->%s(%s)", // 上面的特殊情况,要equal来打头
];
/**
* grid的filter的string的映射
*
* @var array
*/
protected $gridFilterFieldStringTypeMapping = [
'ip' => 'ip',
'email' => 'email|mail',
'url' => 'url|link|src|href',
'mobile' => 'mobile|phone',
];
/**
* grid的filter需要跳出的数组
*
* @var array
*/
protected $gridFilterFieldContinue = [
'password|pwd',
'image|img|avatar|pic|picture|cover',
'file|attachment',
];
/**
* 不允许编辑,可以新建
*
* @var bool
*/
protected $disEditBool = false;
/**
* 不允许保存,(不允许编辑和创建)
*
* @var bool
*/
protected $disSaveBool = false;
/**
* 用字段描述做label
*
* @param \Doctrine\DBAL\Schema\Column $column
* @return string|null
*/
protected function getFormatLabel($column)
{
return $this->handleDefaultFieldComment($column);
}
/**
* 处理comment是默认字段时没有写comment,则根据代码配置的返回
*
* @param \Doctrine\DBAL\Schema\Column $column
* @return mixed|string|null
*/
protected function handleDefaultFieldComment($column)
{
$label = $column->getComment();
$name = $column->getName();
if (empty($label) && array_key_exists($name, $this->getReservedColumnsMap())) {
return $this->getReservedColumnsMap()[$name];
}
return $label;
}
/**
* 字段对应的中文
*
* @see \Encore\Admin\Console\ResourceGenerator::getReservedColumns
* @return array
*/
protected function getReservedColumnsMap($datetimeBool = false)
{
if ($datetimeBool){ // 只返回时间
return [
$this->model->getCreatedAtColumn() => trans('admin.created_at'),
$this->model->getUpdatedAtColumn() => trans('admin.updated_at'),
'deleted_at' => '删除时间',
];
}
return [
$this->model->getKeyName() => '主键',
$this->model->getCreatedAtColumn() => trans('admin.created_at'),
$this->model->getUpdatedAtColumn() => trans('admin.updated_at'),
'deleted_at' => '删除时间',
];
}
/**
* grid的action的模板
*
* @return string
*/
protected function generateGridActions()
{
$output = " \$actions->disableView();";
$output .= $this->isDisEditBool() ? "\r\n \$actions->disableEdit();" : '';
return <<<CODE
\$grid->actions(function (Grid\Displayers\Actions \$actions){
{$output}
});
CODE;
}
/**
* grid的filter的模板
*
* @return string
* @throws \Exception
*/
protected function generateGridFilter()
{
$eol = "\r\n"; // 会特别在后面加8个空格
// 用于column
$filterColumnArr = $rowArr = [];
$sysDatetimeFilterColumnKeyIterator = new \InfiniteIterator(new \ArrayIterator(['left', 'right']));
$sysDatetimeFilterColumnBoth = 0;
foreach ($this->getTableColumns() as $column) {
$columnName = $column->getName();
$type = $column->getType()->getName();
$labelArg = $this->getFormatLabel($column);
$otherArg = '';
$fieldFormat = 'grid_filter_equal';
$fieldType = 'equal';
$filterColumnKey = 'first';
// set column fieldType and defaultValue
switch ($type) {
case 'boolean':
case 'bool':
$fieldType = 'select';
break;
case 'json': // 暂不过滤json
continue;
case 'string': // 字符串
// 跳出
foreach ($this->gridFilterFieldContinue as $regex) {
if (preg_match("/^($regex)$/i", $columnName) !== 0) {
continue;
}
}
// 根据字段名,来匹配类型
$matchBool = false;
foreach ($this->gridFilterFieldStringTypeMapping as $type => $regex) {
if (preg_match("/^($regex)$/i", $columnName) !== 0) {
$matchBool = true;
$fieldType = $type;
break;
}
}
$fieldFormat = $matchBool ? 'grid_filter_equal' : 'grid_filter';
break;
case 'integer':
case 'bigint':
case 'smallint':
case 'timestamp':
$fieldType = 'integer';
break;
case 'decimal':
case 'float':
case 'real': // 实数
$fieldType = 'decimal';
break;
case 'datetime':
if (array_key_exists($columnName, $this->getReservedColumnsMap(true))){ // 系统默认时间
$filterColumnKey = $sysDatetimeFilterColumnKeyIterator->current();
$sysDatetimeFilterColumnKeyIterator->next();
$rowArr[$filterColumnKey] = 2;
++$sysDatetimeFilterColumnBoth;
}
$fieldType = 'datetime';
break;
case 'date':
$fieldType = 'date';
break;
case 'time':
$fieldType = 'time';
break;
case 'text':
case 'blob':
$fieldType = 'textarea';
break;
}
if ($fieldFormat === 'grid_filter_equal'){
$row = ' ' . sprintf($this->formats[$fieldFormat], $columnName, $labelArg, $fieldType, $otherArg) . ";{$eol}";
}else{
$row = ' ' . sprintf($this->formats[$fieldFormat], $fieldType, $columnName, $labelArg) . ";{$eol}";
}
// 处理column,所有
$filterColumnArr[$filterColumnKey][] = $row;
} // foreach结束
$filterCode = '';
// 拼接column
foreach ($filterColumnArr as $key => $filterColumnItemArr) {
if ($sysDatetimeFilterColumnBoth < 2){ // 时间搜索不够2个,就不用column
$filterCode .= join('', $filterColumnItemArr);
continue;
}
$width = isset($rowArr[$key]) ? '1/' . $rowArr[$key] : 12; // 整行的时候要设置为12
$filterCode .= $this->generateGridFilterColumn($width, trim(join(' ', $filterColumnItemArr), $eol));
}
if ($sysDatetimeFilterColumnBoth < 2){
$filterCode = rtrim($filterCode, $eol);
}
// 留意空格对齐
$output = <<<CODE
\$grid->filter(function (Grid\Filter \$filter){
\$filter->disableIdFilter();
{$filterCode}
});
CODE;
return $output;
}
protected function generateGridFilterColumn($width, $filterColumnString)
{
return <<<CODE
\$filter->column({$width}, function (Grid\Filter \$filter){
{$filterColumnString}
});
CODE;
}
/**
* grid的代码
*
* @return string
* @throws \Exception
*/
public function generateGrid()
{
$output = '';
// 处理禁用创建按钮
if ($this->isDisSaveBool()){
$output .= "\$grid->disableCreateButton();\r\n";
}
$output .= $this->generateGridActions();
$output .= $this->generateGridFilter();
$output .= "\r\n";
foreach ($this->getTableColumns() as $column) {
$name = $column->getName();
$output .= sprintf($this->formats['grid_column'], $name, $this->getFormatLabel($column));
$output .= ";\r\n";
}
return $output;
}
/**
* form的代码
*
* @return string
* @throws \Exception
*/
public function generateForm()
{
$reservedColumns = $this->getReservedColumns();
$output = '';
foreach ($this->getTableColumns() as $column) {
$name = $column->getName();
$type = $column->getType()->getName();
$default = $column->getDefault();
// 默认元素只显示不修改
if (in_array($name, $reservedColumns)) {
$type = 'display';
}
$defaultValue = '';
// set column fieldType and defaultValue
switch ($type) {
case 'display': // 只显示
$fieldType = 'display';
break;
case 'boolean':
case 'bool':
$fieldType = 'switch';
break;
case 'json':
if (\Encore\Admin\Form::findFieldClass('json')) { // 支持json输出
$fieldType = 'json';
break;
}
$fieldType = 'text';
break;
case 'array':
case 'object':
$fieldType = 'text';
break;
case 'string':
$fieldType = 'text';
foreach ($this->fieldTypeMapping as $type => $regex) {
if (preg_match("/^($regex)$/i", $name) !== 0) {
$fieldType = $type;
break;
}
}
$defaultValue = "'{$default}'";
break;
case 'integer':
case 'bigint':
case 'smallint':
case 'timestamp':
$fieldType = 'number';
break;
case 'decimal':
case 'float':
case 'real':
$fieldType = 'decimal';
break;
case 'datetime':
$fieldType = 'datetime';
$defaultValue = "date('Y-m-d H:i:s')";
break;
case 'date':
$fieldType = 'date';
$defaultValue = "date('Y-m-d')";
break;
case 'time':
$fieldType = 'time';
$defaultValue = "date('H:i:s')";
break;
case 'text':
case 'blob':
$fieldType = 'textarea';
break;
default:
$fieldType = 'text';
$defaultValue = "'{$default}'";
}
$defaultValue = $defaultValue ?: $default;
$output .= sprintf($this->formats['form_field'], $fieldType, $name, $this->getFormatLabel($column));
if (trim($defaultValue, "'\"")) {
$output .= "->default({$defaultValue})";
}
$output .= ";\r\n";
}
return $output;
}
/**
* 返回类属性
*
* @return string
*/
public function generateProtected()
{
$output = <<<CODE
/**
*
* 页名
*
* @var string
*/
protected \$headerText = '';
CODE;
return $output;
}
/**
* @return bool
*/
public function isDisEditBool(): bool
{
return $this->disEditBool;
}
/**
* @param bool $disEditBool
* @return ResourceGenerator
*/
public function setDisEditBool(bool $disEditBool = true)
{
$this->disEditBool = $disEditBool;
return $this;
}
/**
* @param bool $disSaveBool
* @return ResourceGenerator
*/
public function setDisSaveBool(bool $disSaveBool): ResourceGenerator
{
$this->disSaveBool = $disSaveBool;
if ($disSaveBool) { // 也同时禁用create
$this->setDisEditBool($disSaveBool);
}
return $this;
}
/**
* @return bool
*/
public function isDisSaveBool(): bool
{
return $this->disSaveBool;
}
}
<?php
/**
* Created by PhpStorm.
* User: code
* Date: 2019/4/24
* Time: 14:49
*/
namespace App\Admin\Extensions\Form;
/**
* @example
$form->asyncRender('async-json', function (Form $form)use($tinyint){
$output = '';
if ($form->builder()->isEditing()) { // 编辑
$output .= $form->hidden('type', '分类')->default($data['type'])->render()->render();
}else{ // 创建
$output .= $form->hidden('type', '分类')->default($type)->render()->render();
}
return $output;
});
rules好像是失效了
*/
/**
* 传递匿名函数,实现后续render
* 用于解决在控制器判断创建和编辑的问题
*/
class AsyncRender extends \Encore\Admin\Form\Field
{
protected $callback;
public function __construct($column, $arguments = [])
{
$this->column = $column;
$this->id = $this->formatId($column);
// 第一个参数为回调函数,第二个为form对象
$callback = $arguments[0];
/** @var \Encore\Admin\Form $form */
$form = $arguments[1];
// 处理无法识别编辑的问题
$form->saving(function (\Encore\Admin\Form $form){
if ($form->model()->getKey()) { // 指定id是编辑
$form->model()->exists = true;
}
});
if ($callback && $callback instanceof \Closure) {
$this->with($callback);
}
}
public function with(\Closure $callback)
{
$this->callback = $callback;
}
public function render()
{
if ($this->callback instanceof \Closure) {
return call_user_func($this->callback, $this->form);
}
return '';
}
}
<?php
namespace App\Admin\Extensions\Column;
use Encore\Admin\Admin;
use Encore\Admin\Grid\Displayers\AbstractDisplayer;
/**
* 官方示例
* 用于覆盖原有laravel-admin里的expand,原有的只有一个下箭头,这个多个文案
* 留意第一个参数的匿名函数,没有参数,$this为当前model
*/
class ExpandRow extends AbstractDisplayer
{
public function display(\Closure $callback = null, $btn = '查看')
{
$callback = $callback->bindTo($this->row);
$html = call_user_func($callback);
$script = <<<EOT
$('.grid-expand').on('click', function () {
if ($(this).data('inserted') == '0') {
var key = $(this).data('key');
var row = $(this).closest('tr');
var html = $('template.grid-expand-'+key).html();
row.after("<tr><td></td><td colspan='"+(row.find('td').length-1)+"' style='padding:0 !important; border:0px;'>"+html+"</td></tr>");
$(this).data('inserted', 1);
}
$("i", this).toggleClass("fa-caret-right fa-caret-down");
});
EOT;
Admin::script($script);
$btn = $btn ?: $this->column->getName();
$key = $this->getKey();
return <<<EOT
<a class="btn btn-xs btn-default grid-expand" data-inserted="0" data-key="{$key}" data-toggle="collapse" data-target="#grid-collapse-{$key}">
<i class="fa fa-caret-right"></i> $btn
</a>
<template class="grid-expand-{$key}">
<div id="grid-collapse-{$key}" class="collapse">$html</div>
</template>
EOT;
}
}
<?php
if (!function_exists('getAdminStorageFullUrl')) {
/**
* 获取laravel-admin的图片完整路径
*
* @param string $path 路径
* @return string
*/
function getAdminStorageFullUrl($path)
{
if (empty($path)) {
return '';
}
return \Illuminate\Support\Facades\Storage::disk(config('admin.upload.disk'))->url($path);
}
}
以上是关于php laravel管理员相关类库的主要内容,如果未能解决你的问题,请参考以下文章