Browse Source

tmp

wechat_public_accounts
blobt 5 years ago
parent
commit
c1a1f00da3
  1. 269
      vendor/blobt/assets/bootstrap-daterangepicker/css/daterangepicker.css
  2. 1653
      vendor/blobt/assets/bootstrap-daterangepicker/js/daterangepicker.js
  3. 203
      vendor/blobt/grid/ActionColumn.php
  4. 162
      vendor/blobt/grid/CheckboxColumn.php
  5. 40
      vendor/blobt/grid/Column.php
  6. 71
      vendor/blobt/grid/DataColumn.php
  7. 641
      vendor/blobt/grid/GridView.php
  8. 0
      vendor/blobt/web/AlertifyAsset.php
  9. 0
      vendor/blobt/web/DatePickerAsset.php
  10. 0
      vendor/blobt/web/DateRangePickerAsset.php
  11. 51
      vendor/blobt/web/DaterangeBootstrapAsset.php
  12. 0
      vendor/blobt/web/GridViewAsset.php
  13. 0
      vendor/blobt/web/Select2Asset.php
  14. 163
      vendor/blobt/widgets/DatePicker.php
  15. 277
      vendor/blobt/widgets/DateRangePicker.php
  16. 332
      vendor/blobt/widgets/Menu.php
  17. 101
      vendor/blobt/widgets/Select2.php

269
vendor/blobt/assets/bootstrap-daterangepicker/css/daterangepicker.css

@ -0,0 +1,269 @@
.daterangepicker {
position: absolute;
color: inherit;
background-color: #fff;
border-radius: 4px;
width: 278px;
padding: 4px;
margin-top: 1px;
top: 100px;
left: 20px;
/* Calendars */ }
.daterangepicker:before, .daterangepicker:after {
position: absolute;
display: inline-block;
border-bottom-color: rgba(0, 0, 0, 0.2);
content: ''; }
.daterangepicker:before {
top: -7px;
border-right: 7px solid transparent;
border-left: 7px solid transparent;
border-bottom: 7px solid #ccc; }
.daterangepicker:after {
top: -6px;
border-right: 6px solid transparent;
border-bottom: 6px solid #fff;
border-left: 6px solid transparent; }
.daterangepicker.opensleft:before {
right: 9px; }
.daterangepicker.opensleft:after {
right: 10px; }
.daterangepicker.openscenter:before {
left: 0;
right: 0;
width: 0;
margin-left: auto;
margin-right: auto; }
.daterangepicker.openscenter:after {
left: 0;
right: 0;
width: 0;
margin-left: auto;
margin-right: auto; }
.daterangepicker.opensright:before {
left: 9px; }
.daterangepicker.opensright:after {
left: 10px; }
.daterangepicker.dropup {
margin-top: -5px; }
.daterangepicker.dropup:before {
top: initial;
bottom: -7px;
border-bottom: initial;
border-top: 7px solid #ccc; }
.daterangepicker.dropup:after {
top: initial;
bottom: -6px;
border-bottom: initial;
border-top: 6px solid #fff; }
.daterangepicker.dropdown-menu {
max-width: none;
z-index: 3001; }
.daterangepicker.single .ranges, .daterangepicker.single .calendar {
float: none; }
.daterangepicker.show-calendar .calendar {
display: block; }
.daterangepicker .calendar {
display: none;
max-width: 270px;
margin: 4px; }
.daterangepicker .calendar.single .calendar-table {
border: none; }
.daterangepicker .calendar th, .daterangepicker .calendar td {
white-space: nowrap;
text-align: center;
min-width: 32px; }
.daterangepicker .calendar-table {
border: 1px solid #fff;
padding: 4px;
border-radius: 4px;
background-color: #fff; }
.daterangepicker table {
width: 100%;
margin: 0; }
.daterangepicker td, .daterangepicker th {
text-align: center;
width: 20px;
height: 20px;
border-radius: 4px;
border: 1px solid transparent;
white-space: nowrap;
cursor: pointer; }
.daterangepicker td.available:hover, .daterangepicker th.available:hover {
background-color: #eee;
border-color: transparent;
color: inherit; }
.daterangepicker td.week, .daterangepicker th.week {
font-size: 80%;
color: #ccc; }
.daterangepicker td.off, .daterangepicker td.off.in-range, .daterangepicker td.off.start-date, .daterangepicker td.off.end-date {
background-color: #fff;
border-color: transparent;
color: #999; }
.daterangepicker td.in-range {
background-color: #ebf4f8;
border-color: transparent;
color: #000;
border-radius: 0; }
.daterangepicker td.start-date {
border-radius: 4px 0 0 4px; }
.daterangepicker td.end-date {
border-radius: 0 4px 4px 0; }
.daterangepicker td.start-date.end-date {
border-radius: 4px; }
.daterangepicker td.active, .daterangepicker td.active:hover {
background-color: #357ebd;
border-color: transparent;
color: #fff; }
.daterangepicker th.month {
width: auto; }
.daterangepicker td.disabled, .daterangepicker option.disabled {
color: #999;
cursor: not-allowed;
text-decoration: line-through; }
.daterangepicker select.monthselect, .daterangepicker select.yearselect {
font-size: 12px;
padding: 1px;
height: auto;
margin: 0;
cursor: default; }
.daterangepicker select.monthselect {
margin-right: 2%;
width: 56%; }
.daterangepicker select.yearselect {
width: 40%; }
.daterangepicker select.hourselect, .daterangepicker select.minuteselect, .daterangepicker select.secondselect, .daterangepicker select.ampmselect {
width: 50px;
margin-bottom: 0; }
.daterangepicker .input-mini {
border: 1px solid #ccc;
border-radius: 4px;
color: #555;
height: 30px;
line-height: 30px;
display: block;
vertical-align: middle;
margin: 0 0 5px 0;
padding: 0 6px 0 28px;
width: 100%; }
.daterangepicker .input-mini.active {
border: 1px solid #08c;
border-radius: 4px; }
.daterangepicker .daterangepicker_input {
position: relative; }
.daterangepicker .daterangepicker_input i {
position: absolute;
left: 8px;
top: 8px; }
.daterangepicker.rtl .input-mini {
padding-right: 28px;
padding-left: 6px; }
.daterangepicker.rtl .daterangepicker_input i {
left: auto;
right: 8px; }
.daterangepicker .calendar-time {
text-align: center;
margin: 5px auto;
line-height: 30px;
position: relative;
padding-left: 28px; }
.daterangepicker .calendar-time select.disabled {
color: #ccc;
cursor: not-allowed; }
.ranges {
font-size: 11px;
float: none;
margin: 4px;
text-align: left; }
.ranges ul {
list-style: none;
margin: 0 auto;
padding: 0;
width: 100%; }
.ranges li {
font-size: 13px;
background-color: #f5f5f5;
border: 1px solid #f5f5f5;
border-radius: 4px;
color: #08c;
padding: 3px 12px;
margin-bottom: 8px;
cursor: pointer; }
.ranges li:hover {
background-color: #08c;
border: 1px solid #08c;
color: #fff; }
.ranges li.active {
background-color: #08c;
border: 1px solid #08c;
color: #fff; }
/* Larger Screen Styling */
@media (min-width: 564px) {
.daterangepicker {
width: auto; }
.daterangepicker .ranges ul {
width: 160px; }
.daterangepicker.single .ranges ul {
width: 100%; }
.daterangepicker.single .calendar.left {
clear: none; }
.daterangepicker.single.ltr .ranges, .daterangepicker.single.ltr .calendar {
float: left; }
.daterangepicker.single.rtl .ranges, .daterangepicker.single.rtl .calendar {
float: right; }
.daterangepicker.ltr {
direction: ltr;
text-align: left; }
.daterangepicker.ltr .calendar.left {
clear: left;
margin-right: 0; }
.daterangepicker.ltr .calendar.left .calendar-table {
border-right: none;
border-top-right-radius: 0;
border-bottom-right-radius: 0; }
.daterangepicker.ltr .calendar.right {
margin-left: 0; }
.daterangepicker.ltr .calendar.right .calendar-table {
border-left: none;
border-top-left-radius: 0;
border-bottom-left-radius: 0; }
.daterangepicker.ltr .left .daterangepicker_input {
padding-right: 12px; }
.daterangepicker.ltr .calendar.left .calendar-table {
padding-right: 12px; }
.daterangepicker.ltr .ranges, .daterangepicker.ltr .calendar {
float: left; }
.daterangepicker.rtl {
direction: rtl;
text-align: right; }
.daterangepicker.rtl .calendar.left {
clear: right;
margin-left: 0; }
.daterangepicker.rtl .calendar.left .calendar-table {
border-left: none;
border-top-left-radius: 0;
border-bottom-left-radius: 0; }
.daterangepicker.rtl .calendar.right {
margin-right: 0; }
.daterangepicker.rtl .calendar.right .calendar-table {
border-right: none;
border-top-right-radius: 0;
border-bottom-right-radius: 0; }
.daterangepicker.rtl .left .daterangepicker_input {
padding-left: 12px; }
.daterangepicker.rtl .calendar.left .calendar-table {
padding-left: 12px; }
.daterangepicker.rtl .ranges, .daterangepicker.rtl .calendar {
text-align: right;
float: right; } }
@media (min-width: 730px) {
.daterangepicker .ranges {
width: auto; }
.daterangepicker.ltr .ranges {
float: left; }
.daterangepicker.rtl .ranges {
float: right; }
.daterangepicker .calendar.left {
clear: none !important; } }

1653
vendor/blobt/assets/bootstrap-daterangepicker/js/daterangepicker.js
File diff suppressed because it is too large
View File

203
vendor/blobt/grid/ActionColumn.php

@ -0,0 +1,203 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\grid;
use Yii;
use yii\helpers\Html;
use yii\helpers\Url;
use blobt\grid\Column;
class ActionColumn extends Column {
/**
* @var string 处理的控制器ID
*/
public $controller;
/**
* @var string 按钮模板
*/
public $template = '{view} {update} {delete}';
/**
* @var array 以按钮名为键,以匿名函数为值,通过匿名函数返回html,用来控制按钮的表现形式
* 匿名函数必须遵循以下申明方式:
*
* ```php
* function ($url, $model, $key) {
* // return the button HTML code
* }
* ```
*
* - `$url`: 按钮的跳转路径
* - `$model`: 每行的模型
* - `$key`: id值
*
* 使用案例:
* ```php
* [
* 'update' => function ($url, $model, $key) {
* return $model->status === 'editable' ? Html::a('Update', $url) : '';
* },
* ],
*
*/
public $buttons = [];
/** @var array 和上述$buttons功能类似,只是匿名函数返回布尔,只控制是否展示
* 匿名函数必须遵循以下申明方式:
*
* ```php
* function ($model, $key, $index) {
* return $model->status === 'editable';
* }
* ```
*
* 使用案例:
* ```php
* [
* 'update' => \Yii::$app->user->can('update'),
* ],
* ```
* @since 2.0.7
*/
public $visibleButtons = [];
/**
* @var callable 匿名函数,用作控制按钮Url
*
* 匿名函数必须遵循以下申明方式:
* ```php
* function (string $action, mixed $model, mixed $key, integer $index, ActionColumn $this) {
* //return string;
* }
* ```
*
* 如果没有设置,默认使用本类的[[createUrl()]].
*/
public $urlCreator;
/**
* @var array 按钮的html属性
*/
public $buttonOptions = [];
/**
* {@inheritdoc}
*/
public function init() {
parent::init();
$this->initDefaultButtons();
}
/**
* 初始化默认按钮
*/
protected function initDefaultButtons() {
$this->initDefaultButton('view', 'eye-open');
$this->initDefaultButton('update', 'pencil');
$this->initDefaultButton('delete', 'trash', [
'alertify-confirm' => Yii::t('yii', 'Are you sure you want to delete this item?')
]);
}
/**
* 初始化按钮
* @param string $name
* @param string $iconName
* @param array $additionalOptions 附加html属性
*/
protected function initDefaultButton($name, $iconName, $additionalOptions = []) {
if (!isset($this->buttons[$name]) && strpos($this->template, '{' . $name . '}') !== false) {
$this->buttons[$name] = function ($url, $model, $key) use ($name, $iconName, $additionalOptions) {
switch ($name) {
case 'view':
$title = Yii::t('yii', 'View');
break;
case 'update':
$title = Yii::t('yii', 'Update');
break;
case 'delete':
$title = Yii::t('yii', 'Delete');
break;
default:
$title = ucfirst($name);
}
$options = array_merge([
'title' => $title,
'aria-label' => $title,
'data-pjax' => '0',
], $additionalOptions, $this->buttonOptions);
$icon = Html::tag('span', '', ['class' => "glyphicon glyphicon-$iconName"]);
return Html::a($icon, $url, $options);
};
}
}
/**
* 通过给定的action和model创建一个URL.
*
* @param string $action 按钮名
* @param \yii\db\ActiveRecordInterface $model 数据模型
* @param mixed $key 模型的ID
* @param int $index 行号
* @return string the created URL
*/
public function createUrl($action, $model, $key, $index) {
if (is_callable($this->urlCreator)) {
return call_user_func($this->urlCreator, $action, $model, $key, $index, $this);
}
$params = is_array($key) ? $key : ['id' => (string) $key];
$params[0] = $this->controller ? $this->controller . '/' . $action : $action;
return Url::toRoute($params);
}
/**
* {@inheritdoc}
*/
protected function renderDataCellContent($model, $key, $index) {
return preg_replace_callback('/\\{([\w\-\/]+)\\}/', function ($matches) use ($model, $key, $index) {
$name = $matches[1];
if (isset($this->visibleButtons[$name])) {
$isVisible = $this->visibleButtons[$name] instanceof \Closure ? call_user_func($this->visibleButtons[$name], $model, $key, $index) : $this->visibleButtons[$name];
} else {
$isVisible = true;
}
if ($isVisible && isset($this->buttons[$name])) {
$url = $this->createUrl($name, $model, $key, $index);
return call_user_func($this->buttons[$name], $url, $model, $key);
}
return '';
}, $this->template);
}
}

162
vendor/blobt/grid/CheckboxColumn.php

@ -0,0 +1,162 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\grid;
use Closure;
use yii\base\InvalidConfigException;
use yii\helpers\Html;
use yii\helpers\Json;
use blobt\grid\DataColumn;
class CheckboxColumn extends Column {
/**
* @var string the name of the input checkbox input fields. This will be appended with `[]` to ensure it is an array.
*/
public $name = 'selection';
/**
* @var array|\Closure the HTML attributes for checkboxes. This can either be an array of
* attributes or an anonymous function ([[Closure]]) that returns such an array.
* The signature of the function should be the following: `function ($model, $key, $index, $column)`.
* Where `$model`, `$key`, and `$index` refer to the model, key and index of the row currently being rendered
* and `$column` is a reference to the [[CheckboxColumn]] object.
* A function may be used to assign different attributes to different rows based on the data in that row.
* Specifically if you want to set a different value for the checkbox
* you can use this option in the following way (in this example using the `name` attribute of the model):
*
* ```php
* 'checkboxOptions' => function ($model, $key, $index, $column) {
* return ['value' => $model->name];
* }
* ```
*
* @see \yii\helpers\Html::renderTagAttributes() for details on how attributes are being rendered.
*/
public $checkboxOptions = [];
/**
* @var bool whether it is possible to select multiple rows. Defaults to `true`.
*/
public $multiple = true;
/**
* @var string the css class that will be used to find the checkboxes.
* @since 2.0.9
*/
public $cssClass;
/**
* {@inheritdoc}
* @throws \yii\base\InvalidConfigException if [[name]] is not set.
*/
public function init() {
parent::init();
if (empty($this->name)) {
throw new InvalidConfigException('The "name" property must be set.');
}
if (substr_compare($this->name, '[]', -2, 2)) {
$this->name .= '[]';
}
$this->registerClientScript();
}
/**
* Renders the header cell content.
* The default implementation simply renders [[header]].
* This method may be overridden to customize the rendering of the header cell.
* @return string the rendering result
*/
protected function renderHeaderCellContent() {
if ($this->header !== null || !$this->multiple) {
return parent::renderHeaderCellContent();
}
return Html::checkbox($this->getHeaderCheckBoxName(), false, ['class' => 'select-on-check-all']);
}
/**
* {@inheritdoc}
*/
protected function renderDataCellContent($model, $key, $index) {
if ($this->content !== null) {
return parent::renderDataCellContent($model, $key, $index);
}
if ($this->checkboxOptions instanceof Closure) {
$options = call_user_func($this->checkboxOptions, $model, $key, $index, $this);
} else {
$options = $this->checkboxOptions;
}
if (!isset($options['value'])) {
$options['value'] = is_array($key) ? Json::encode($key) : $key;
}
if ($this->cssClass !== null) {
Html::addCssClass($options, $this->cssClass);
}
return Html::checkbox($this->name, !empty($options['checked']), $options);
}
/**
* Returns header checkbox name.
* @return string header checkbox name
* @since 2.0.8
*/
protected function getHeaderCheckBoxName() {
$name = $this->name;
if (substr_compare($name, '[]', -2, 2) === 0) {
$name = substr($name, 0, -2);
}
if (substr_compare($name, ']', -1, 1) === 0) {
$name = substr($name, 0, -1) . '_all]';
} else {
$name .= '_all';
}
return $name;
}
/**
* Registers the needed JavaScript.
* @since 2.0.8
*/
public function registerClientScript() {
$id = $this->grid->options['id'];
$options = Json::encode([
'name' => $this->name,
'class' => $this->cssClass,
'multiple' => $this->multiple,
'checkAll' => $this->grid->showHeader ? $this->getHeaderCheckBoxName() : null,
]);
$this->grid->getView()->registerJs("jQuery('#$id').yiiGridView('setSelectionColumn', $options);");
}
}

40
vendor/blobt/grid/Column.php

@ -0,0 +1,40 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\grid;
use Closure;
use yii\base\InvalidConfigException;
use yii\helpers\Html;
use yii\helpers\Json;
use yii\grid\Column as YiiColumn;
class Column extends YiiColumn {
public $width;
public $align;
}

71
vendor/blobt/grid/DataColumn.php

@ -0,0 +1,71 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\grid;
/**
*
*
* @author Blobt
* @email 380255922@qq.com
* @created Aug 13, 2019
*/
class DataColumn extends Column {
/**
* @var string 本列需要显示的模型属性值,
* 如果设置了value,则会显示value。
*/
public $attribute;
/**
* @var string 列首的label。如果不设置,则会显示attribute关联的label
*/
public $label;
/**
* @var bool 是否需要html转义
*/
public $encodeLabel = true;
/**
* @var string|array|Closure 每个数据模型的值应以哪种格式显示(例如“raw”`、“text”`、“html”`,`[date','php:y-m-d']`)。
* 默认格式为“文本”
*/
public $format = 'text';
/**
* @var bool 有时候我们记录数据时候,使用了整数值来代替字符,当此属性被设置成true时候,
* 会视图找到数值对应的字符,并显示出来
*/
public $showConstText = false;
/**
* @var bool 是否开始排序
*/
public $enableSorting = false;
}

641
vendor/blobt/grid/GridView.php

@ -0,0 +1,641 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\grid;
use Closure;
use Yii;
use yii\base\InvalidConfigException;
use yii\base\Model;
use yii\helpers\Html;
use yii\helpers\Json;
use yii\helpers\Url;
use yii\helpers\ArrayHelper;
use yii\i18n\Formatter;
use yii\widgets\BaseListView;
use blobt\web\GridViewAsset;
/**
* @author Blobt
* @email 380255922@qq.com
* @created Aug 13, 2019
*/
class GridView extends BaseListView {
/**
* @var string 渲染列数据的类,默认是'yii\grid\DataColumn'
*/
public $dataColumnClass;
/**
* @var array 表格说明的html属性
*/
public $captionOptions = [];
/**
* @var array 表格外层div的属性
*/
public $options = ['class' => 'box'];
/**
* @var array table的html属性
*/
public $tableOptions = ['class' => 'table table-bordered table-hover dataTable'];
/**
* @var array 表格头部html属性
*/
public $headerRowOptions = [];
/**
* @var array 表格脚部html属性
*/
public $footerRowOptions = [];
/**
* @var array|Cloure 表格每一行的html属性
* 这个参数除了可以是一个options数组外,还可以是一个匿名函数,该函数必须返回一个options数组,
* 渲染每一行都会调用该函数
* 该函数必须遵循以下声明规则
* ```php
* function ($model, $key, $index, $grid)
* ```
*
* - `$model`: 每行的模型
* - `$key`: id值
* - `$index`: [[dataProvider]]提供的索引号
* - `$grid`: GridView 对象
*/
public $rowOptions = [];
/**
* @var Closure an 一个匿名函数(结构和[[rowOptions]]一样),每行渲染前后都会被调用
*/
public $beforeRow;
public $afterRow;
/**
* @var bool 是否显示表格头
*/
public $showHeader = true;
/**
* @var bool 是否显示表格脚
*/
public $showFooter = false;
/**
* @var bool 没有数据情况下是否显示
*/
public $showOnEmpty = true;
/**
* @var array|Formatter 用来格式化输出属性值
*/
public $formatter;
/**
* @var string 摘要的显示样式
*
*
* - `{begin}`: 开始条数
* - `{end}`: 结束条数
* - `{count}`: 显示条数
* - `{totalCount}`: 总记录条数
* - `{page}`: 显示分页
* - `{pageCount}`: 总分页数
* - `{select}`: 显示页数
*/
public $summary = "{select} 显示{begin}~{end}条 共{totalCount}条";
/**
* @var array 摘要的html属性
*/
public $summaryOptions = ['class' => 'summary'];
/**
* @var array 列配置数组. 数组每一项代表一个列,列数组可以包括class、attribute、format、label等。
* 例子:
* ```php
* [
* ['class' => SerialColumn::className()],
* [
* 'class' => DataColumn::className(), //渲染用到的类,没一列都默认使用[[DataColumn]]渲染,所以这里可以忽略
* 'attribute' => 'name', //代表每一行的数据原
* 'format' => 'text', //输出的格式
* 'label' => 'Name', //label
* '' => ''
* ],
* ['class' => CheckboxColumn::className()],
* ]
* ```
*
* 当然,也支持简写成这样:[[DataColumn::attribute|attribute]], [[DataColumn::format|format]],
* [[DataColumn::label|label]] options: `"attribute:format:label"`.
* 所以上面例子的 "name" 列能简写成这样 : `"name:text:Name"`.
* 甚至"format""label"都是可以不制定的,因为它们都有默认值。
*
* 其实大多数情况下都可以使用简写:
*
* ```php
* [
* 'id',
* 'amount:currency:Total Amount',
* 'created_at:datetime',
* ]
* ```
*
* [[dataProvider]]提供active records, 且active record又和其它 active record建立了关联关系的,
* 例如 the `name` 属性是 `author` 关联,那么你可以这样制定数据:
*
* ```php
* // shortcut syntax
* 'author.name',
* // full syntax
* [
* 'attribute' => 'author.name',
* // ...
* ]
* ```
*/
public $columns = [];
/**
* @var string 当单元格数据为空时候显示的内容。
*/
public $emptyCell = '&nbsp;';
/**
* @var string TODO:这个目前用来做页数选择,具体原理没有研究清楚
*/
public $filterSelector = 'select[name="per-page"]';
/**
* @var type
*/
public $filter;
/**
* @var array 批量操作的选项
*/
public $batch;
/**
* @var string 表格的layout:
*
* - `{summary}`: 摘要.
* - `{items}`: 表格项.
* - `{pager}`: 分页.
* - `{batch}`: 批量处理
*/
public $layout = <<< HTML
<div class="box-body">
<div id="example2_wrapper" class="dataTables_wrapper form-inline dt-bootstrap">
<div class="row">
<div class="error-summary"><ul></ul></div>
</div>
<div class="row">
<div class="col-sm-3">
{batch}
<a href="create" class="btn btn-default"><i class="fa fa-plus"></i>添加</a>
<button type="button" class="btn btn-default"><i class="fa fa-file-excel-o"></i>导出</button>
</div>
<div class="col-sm-9">
{filter}
</div>
</div>
<div class="row">
<div class="col-sm-12">
{items}
</div>
</div>
<div class="row">
<div class="col-sm-5">
<div class="dataTables_info" id="example2_info" role="status" aria-live="polite">
{summary}
</div>
</div>
<div class="col-sm-7">
<div class="dataTables_paginate paging_simple_numbers">
{pager}
</div>
</div>
</div>
</div>
</div>
HTML;
public $batchTemplate = <<< HTML
<div class="btn-group">
<button type="button" class="btn btn-default btn checkbox-toggle"><i class="fa fa-square-o"></i></button>
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown" aria-expanded="false">批量操作</button>
<ul class="dropdown-menu" role="menu">
{items}
</ul>
</div>
HTML;
/**
* 初始化 grid view.
* 初始化必须的属性和每个列对象
* @return
*/
public function init() {
parent::init();
if ($this->formatter === null) {
$this->formatter = Yii::$app->getFormatter();
} elseif (is_array($this->formatter)) {
$this->formatter = Yii::createObject($this->formatter);
}
if (!$this->formatter instanceof Formatter) {
throw new InvalidConfigException('The "formatter" property must be either a Format object or a configuration array.');
}
$this->initColumns();
}
public function run() {
$view = $this->getView();
GridViewAsset::register($view);
$this->registerGridJs();
$this->registerIcheckJs();
$this->registerConfirmJs();
parent::run();
}
/**
* 注册GridView Js
*/
protected function registerGridJs() {
$options = Json::htmlEncode(['filterUrl' => Url::to(Yii::$app->request->url),
'filterSelector' => $this->filterSelector]);
$id = $this->options['id'];
$this->getView()->registerJs("jQuery('#$id').yiiGridView($options);");
}
/**
* 注册icheck Js
*/
protected function registerIcheckJs() {
$js = <<<SCRIPT
$('.dataTable input[type="checkbox"]').iCheck({
checkboxClass: 'icheckbox_flat-blue',
radioClass: 'iradio_flat-blue'
});
$(".checkbox-toggle").click(function () {
var clicks = $(this).data('clicks');
if (clicks) {
//Uncheck all checkboxes
$(".dataTable input[type='checkbox']").iCheck("uncheck");
$(".fa", this).removeClass("fa-check-square-o").addClass('fa-square-o');
} else {
//Check all checkboxes
$(".dataTable input[type='checkbox']").iCheck("check");
$(".fa", this).removeClass("fa-square-o").addClass('fa-check-square-o');
}
$(this).data("clicks", !clicks);
});
SCRIPT;
$this->getView()->registerJs($js);
}
/**
* 注册批量操作js
*/
protected function registerBatchJs() {
$js = <<<SCRIPT
$("a.batch_item").click(function(){
var url = $(this).data("url");
var act = $(this).text();
var selected = [];
$(".checked input").each(function(){
selected.push($(this).val());
});
if(selected.length > 0){
alertify.confirm('系统提示', "确定执行批量 '"+act+"' 操作?", function(){
$.ajax({
type: "POST",
url: url,
traditional:true,
data:{ 'ids[]':selected},
dataType: "json",
async:false
});
window.location.reload();
},function(){
});
}
return false;
})
SCRIPT;
$this->getView()->registerJs($js);
}
protected function registerConfirmJs() {
$js = <<<SCRIPT
$("a[alertify-confirm]").click(function(){
var message = $(this).attr('alertify-confirm');
var url = $(this).attr('href');
var id = $(this).data('id');
alertify.confirm('系统提示', message,function(){
$.ajax({
type: "POST",
url: url,
traditional:true,
data:{ id:id },
dataType: "json",
async:false
});
window.location.reload();
},function(){
});
return false;
});
SCRIPT;
$this->getView()->registerJs($js);
}
/**
* 渲染局部
* @return string|bool
*/
public function renderSection($name) {
switch ($name) {
case '{summary}':
return $this->renderSummary();
case '{items}':
return $this->renderItems();
case '{pager}':
return $this->renderPager();
case '{sorter}':
return $this->renderSorter();
case '{filter}':
return $this->renderFilter();
case '{batch}':
return $this->renderBatch();
default:
return false;
}
}
/**
* 渲染表格的html真实table
* @return string
*/
public function renderItems() {
$tableHeader = $this->showHeader ? $this->renderTableHeader() : false;
$tableBody = $this->renderTableBody();
$content = array_filter([
$tableHeader,
$tableBody
]);
return Html::tag('table', implode("\n", $content), $this->tableOptions);
}
/**
* 初始化每列
* @throws InvalidConfigException
*/
protected function initColumns() {
if (empty($this->columns)) {
throw new InvalidConfigException('The "columns" property must be set.');
}
foreach ($this->columns as $i => $column) {
if (is_string($column)) {
$column = $this->createDataColumn($column);
} else {
$column = Yii::createObject(array_merge([
'class' => $this->dataColumnClass ?: DataColumn::className(),
'grid' => $this,
], $column));
}
if (!$column->visible) {
unset($this->columns[$i]);
continue;
}
$this->columns[$i] = $column;
}
}
/**
* 渲染表头
* @return string
*/
public function renderTableHeader() {
$cells = [];
foreach ($this->columns as $column) {
/* @var $column Column */
$cells[] = $column->renderHeaderCell();
}
$content = Html::tag('tr', implode('', $cells), $this->headerRowOptions);
return "<thead>\n" . $content . "\n</thead>";
}
/**
* 渲染表格体
* @return string
*/
public function renderTableBody() {
$models = $this->dataProvider->getModels();
$keys = $this->dataProvider->getKeys();
$rows = [];
foreach ($models as $index => $model) {
$key = $keys[$index];
if ($this->beforeRow !== null) {
$row = call_user_func($this->beforeRow, $model, $key, $index, $this);
if (!empty($row)) {
$rows[] = $row;
}
}
$rows[] = $this->renderTableRow($model, $key, $index);
if ($this->afterRow !== null) {
$row = call_user_func($this->afterRow, $model, $key, $index, $this);
if (!empty($row)) {
$rows[] = $row;
}
}
}
if (empty($rows) && $this->emptyText !== false) {
$colspan = count($this->columns);
return "<tbody>\n<tr><td colspan=\"$colspan\">" . $this->renderEmpty() . "</td></tr>\n</tbody>";
}
return "<tbody>\n" . implode("\n", $rows) . "\n</tbody>";
}
/**
* 渲染表格的每行
* @param Objetc $model
* @param int $key
* @param int $index
* @return string
*/
public function renderTableRow($model, $key, $index) {
$cells = [];
foreach ($this->columns as $column) {
$cells[] = $column->renderDataCell($model, $key, $index);
}
if ($this->rowOptions instanceof Closure) {
$options = call_user_func($this->rowOptions, $model, $key, $index, $this);
} else {
$options = $this->rowOptions;
}
$options['data-key'] = is_array($key) ? json_encode($key) : (string) $key;
//TODO 各行变色放到这里不合理
if ($index % 2 == 0) {
$oddEven = 'odd';
} else {
$oddEven = 'even';
}
if (isset($options['class'])) {
$options['class'] += " " . $oddEven;
} else {
$options['class'] = $oddEven;
}
return Html::tag('tr', implode('', $cells), $options);
}
/**
* 渲染摘要显示
* @return string
*/
public function renderSummary() {
$count = $this->dataProvider->getCount();
if ($count <= 0) {
return '';
}
$summaryOptions = $this->summaryOptions;
$tag = ArrayHelper::remove($summaryOptions, 'tag', 'div');
if (($pagination = $this->dataProvider->getPagination()) !== false) {
$totalCount = $this->dataProvider->getTotalCount();
$begin = $pagination->getPage() * $pagination->pageSize + 1;
$end = $begin + $count - 1;
if ($begin > $end) {
$begin = $end;
}
$page = $pagination->getPage() + 1;
$pageCount = $pagination->pageCount;
}
return Yii::$app->getI18n()->format($this->summary, [
'begin' => $begin,
'end' => $end,
'count' => $count,
'totalCount' => $totalCount,
'page' => $page,
'pageCount' => $pageCount,
'select' => $this->renderCountSelect()
], Yii::$app->language);
}
/**
* 渲染批量操作
*/
public function renderBatch() {
if (empty($this->batch) && !is_array($this->batch)) {
return "";
}
$this->registerBatchJs();
$items = "";
foreach ($this->batch as $item) {
$items .= Html::tag('li', Html::a(Html::encode($item['label']), '#', ["data-url" => Html::encode($item['url']), "class" => "batch_item"]));
}
return strtr($this->batchTemplate, [
"{items}" => $items
]);
}
/**
* 渲染表格的页数select
* @return string
*/
protected function renderCountSelect() {
$items = [
"20" => 20,
"50" => 50,
"100" => 100
];
$per = "条/页";
$options = [];
foreach ($items as $key => $val) {
$options[$val] = "{$key}{$per}";
}
$perPage = !empty($_GET['per-page']) ? $_GET['per-page'] : 20;
return Html::dropDownList('per-page', $perPage, $options, ["class" => "form-control input-sm"]);
}
/**
* 渲染表格的筛选部分
* @return string
*/
protected function renderFilter() {
return $this->filter;
}
/**
* 根据给定格式,创建一个 [[DataColumn]] 对象
* @param string $text DataColumn 格式
* @return DataColumn 实例
* @throws InvalidConfigException
*/
protected function createDataColumn($text) {
if (!preg_match('/^([^:]+)(:(\w*))?(:(.*))?$/', $text, $matches)) {
throw new InvalidConfigException('The column must be specified in the format of "attribute", "attribute:format" or "attribute:format:label"');
}
return Yii::createObject([
'class' => $this->dataColumnClass ?: DataColumn::className(),
'grid' => $this,
'attribute' => $matches[1],
'format' => isset($matches[3]) ? $matches[3] : 'text',
'label' => isset($matches[5]) ? $matches[5] : null,
]);
}
}

0
vendor/blobt/web/AlertifyAsset.php

0
vendor/blobt/web/DatePickerAsset.php

0
vendor/blobt/web/DateRangePickerAsset.php

51
vendor/blobt/web/DaterangeBootstrapAsset.php

@ -0,0 +1,51 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\web;
use yii\web\AssetBundle;
/**
* Description of AdminlteAsset
*
* @author Blobt
* @email 380255922@qq.com
* @created Aug 27, 2019
*/
class DaterangeBootstrapAsset extends AssetBundle {
public $sourcePath = "@blobt/assets/bootstrap-daterangepicker";
public $css = [
'css/daterangepicker.css'
];
public $js = [
'js/daterangepicker.js'
];
public $depends = [
'yii\bootstrap\BootstrapAsset',
];
}

0
vendor/blobt/web/GridViewAsset.php

0
vendor/blobt/web/Select2Asset.php

163
vendor/blobt/widgets/DatePicker.php

@ -0,0 +1,163 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\widgets;
use yii\widgets\InputWidget;
use Yii;
use yii\base\InvalidConfigException;
use yii\helpers\ArrayHelper;
use yii\helpers\Html;
use yii\web\JsExpression;
use yii\helpers\Json;
use blobt\web\DatepickBootstrapAsset;
use blobt\helpers\DatetimeHelper;
/**
* 此DatePicker只适用于使用Unix时间戳保存时间的model
*
* @author Blobt
* @email 380255922@qq.com
* @created Aug 19, 2019
*/
class DatePicker extends InputWidget {
/**
* @var string 日期显示格式
*/
public $format = "Y-m-d";
/**
* @var string datepicker的日期显示input框的id,只用做显示
*/
public $pickerInputId;
/**
* @var boll 是否自动填充当天日期
*/
public $autoFill = false;
/**
* @inheritdoc
* @throws InvalidConfigException
* @throws \ReflectionException
*/
public function run() {
$this->initSetting();
$this->registerAsset();
echo $this->renderHiddenInput();
echo $this->renderDatapickerInput();
}
/**
* 初始化小物件的配置
*/
protected function initSetting() {
//初始化日期格式
if (empty($this->format)) {
$this->format = Yii::$app->formatter->dateFormat;
}
//关闭自动完成
$this->options["autocomplete"] = "off";
//生成一个picker input的 id
$this->pickerInputId = $this->options['id'] . "_" . Yii::$app->security->generateRandomKey(32);
}
/**
* 注册js和css
*/
protected function registerAsset() {
$view = $this->getView();
DatepickBootstrapAsset::register($view);
$options = [
"format" => $this->convertDateFormat($this->format),
"language" => "zh-CN"
];
$jsOptions = Json::encode($options);
$js = <<< SCRIPT
$('#{$this->pickerInputId}').datepicker({$jsOptions}).on('changeDate', function(e) {
$('#{$this->options['id']}').val(String(e.date.getTime()).substring(0,10));
});;
SCRIPT;
$view->registerJs($js);
}
/**
* 渲染一个用作保存Datepicker Unix时间错的hidden input
* @return string
*/
protected function renderHiddenInput() {
if ($this->hasModel()) {
return Html::activeInput('hidden', $this->model, $this->attribute, $this->options);
}
return Html::input('hidden', $this->name, $this->value, $this->options);
}
/**
* TODO:自动填充了今天为默认日期
* 渲染一个用作显示日期的字符格式 text input
* @return string
*/
protected function renderDatapickerInput() {
$value = '';
$options = $this->options;
$options['id'] = $this->pickerInputId;
if ($this->hasModel()) {
$timestamp = ArrayHelper::getValue($this->model, $this->attribute);
}
if (empty($timestamp) && $this->autoFill) {
$timestamp = time();
$value = date($this->format, $timestamp);
}
return Html::input('text', $this->name, $value, $options);
}
/**
* 转换php日期格式为bootstrap日期格式
*
* TODO:没有弄清所有格式的转换,后续添加
*
* @param string $format PHP日期格式字符串
* @return string
*/
protected static function convertDateFormat($format) {
$conversions = [
'd' => 'dd',
'm' => 'mm',
'Y' => 'yyyy',
];
return strtr($format, $conversions);
}
}

277
vendor/blobt/widgets/DateRangePicker.php

@ -0,0 +1,277 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\widgets;
use yii\widgets\InputWidget;
use Yii;
use yii\base\InvalidConfigException;
use yii\helpers\ArrayHelper;
use yii\helpers\Html;
use yii\web\JsExpression;
use blobt\helpers\DatetimeHelper;
use blobt\web\DaterangeBootstrapAsset;
use yii\helpers\Json;
/**
*
*
* @author Blobt
* @email 380255922@qq.com
* @created Aug 13, 2019
*/
class DateRangePicker extends InputWidget {
/**
* @var boolean 是否需要把值做转义
*/
public $encodeValue = true;
/**
* @var array input的html属性
*/
public $options = [];
/**
* @var string label
*/
public $label = "日期范围";
/**
* @var string 确定按钮显示内容
*/
public $applyLabel = "确定";
/**
* @var string 关闭按钮显示内容
*/
public $cancelLabel = "关闭";
/**
* @var string 自定义按钮显示内容
*/
public $customRangeLabel = "自定义";
/**
* @var array 星期一到星期日的显示
*/
public $daysOfWeek = ["", "", "", "", "", "", ""];
/**
* @var array 12个月份的显示
*/
public $monthNames = ["一月", "二月", "三月", "四月", "五月", "六月", "七月", "八月", "九月", "十月", "十一月", "十二月"];
/**
* @var array 选择器的基础配置参数
*/
protected $locale = [];
/**
* @var 快捷选择建
*/
public $ranges = [];
/**
* @var string 选择器默认选中的开始日期
*/
public $startDate;
/**
* @var string 选择器默认选中的结束日期
*/
public $endDate;
/**
* @var string 左侧显示的图标
*/
public $iconClass = "fa fa-calendar";
/**
* @var string 日期显示格式
*/
public $format = "Y-m-d";
/**
* @var string 选择框打开的位置
*/
public $opens = 'left';
/**
* @var bool 是否自动填入日期
*/
public $autoFill = false;
/**
* @inheritdoc
* @throws InvalidConfigException
* @throws \ReflectionException
*/
public function run() {
$this->initSetting();
$this->registerAsset();
echo $this->renderInputHtml('text');
}
/**
* @inheritdoc
*/
public function init() {
parent::init();
}
/**
* 初始化小物件的配置
*/
protected function initSetting() {
//初始化日期格式
if (empty($this->format)) {
$this->format = Yii::$app->formatter->dateFormat;
}
$this->format = $this->convertDateFormat($this->format);
//初始化基础配置
$this->locale = [
'cancelLabel' => $this->cancelLabel,
'applyLabel' => $this->applyLabel,
"customRangeLabel" => $this->customRangeLabel,
"daysOfWeek" => $this->daysOfWeek,
"monthNames" => $this->monthNames,
"format" => $this->format
];
//初始化快捷键
$this->initRange();
//关闭自动提示
$this->options = ArrayHelper::merge($this->options, [
"autocomplete" => "off",
"class" => "form-control",
"style" => "width:190px;"
]);
}
/**
* 注册js和css
*/
protected function registerAsset() {
$view = $this->getView();
DaterangeBootstrapAsset::register($view);
$options = [
"opens" => $this->opens,
"autoUpdateInput" => $this->autoFill,
"locale" => $this->locale,
"ranges" => $this->ranges
];
if (!empty($this->startDate)) {
$options["startDate"] = new JsExpression("moment('{$this->startDate}')");
}
if (!empty($this->endDate)) {
$options["endDate"] = new JsExpression("moment('{$this->endDate}')");
}
$jsOptions = Json::encode($options);
$js = <<< SCRIPT
$('#{$this->options['id']}').daterangepicker({$jsOptions});
$('#{$this->options['id']}').on('apply.daterangepicker', function(ev, picker) {
$(this).val(picker.startDate.format('{$this->format}') + ' ~ ' + picker.endDate.format('{$this->format}'));
});
$('#{$this->options['id']}').on('cancel.daterangepicker', function(ev, picker) {
$(this).val('');
});
SCRIPT;
$view->registerJs($js);
}
/**
* 初始化快捷按键数组
*/
protected function initRange() {
$this->ranges = [
'今天' => [new JsExpression("moment()"), new JsExpression("moment()")],
'昨天' => [new JsExpression("moment().subtract(1, 'days')"), new JsExpression("moment().subtract(1, 'days')")],
'最近7天' => [new JsExpression("moment().subtract(6, 'days')"), new JsExpression("moment()")],
'最近30天' => [new JsExpression("moment().subtract(29, 'days')"), new JsExpression("moment()")],
'本月' => [new JsExpression("moment().startOf('month')"), new JsExpression("moment().endOf('month')")],
'上月' => [new JsExpression("moment().subtract(1, 'month').startOf('month')"), new JsExpression("moment().subtract(1, 'month').endOf('month')")]
];
}
/**
* 转换php日期格式为Moment.js 日期格式
* @param string $format PHP日期格式字符串
* @return string
*/
protected static function convertDateFormat($format) {
$conversions = [
// second (带有前导零)
's' => 'ss',
// minute (带有前导零)
'i' => 'mm',
// hour in 12-hour format (没带前导零)
'g' => 'h',
// hour in 12-hour format (带有前导零)
'h' => 'hh',
// hour in 24-hour format (没带前导零)
'G' => 'H',
// hour in 24-hour format (带有前导零)
'H' => 'HH',
// day of the week locale
'w' => 'e',
// day of the week ISO
'W' => 'E',
// day of month (没带前导零)
'j' => 'D',
// day of month (带有前导零)
'd' => 'DD',
// day name short
'D' => 'DDD',
// day name long
'l' => 'DDDD',
// month of year (没带前导零)
'n' => 'M',
// month of year (带有前导零)
'm' => 'MM',
// month name short
'M' => 'MMM',
// month name long
'F' => 'MMMM',
// year (2位年)
'y' => 'YY',
// year (4位年)
'Y' => 'YYYY',
// unix timestamp
'U' => 'X',
];
return strtr($format, $conversions);
}
}

332
vendor/blobt/widgets/Menu.php

@ -0,0 +1,332 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\widgets;
use Yii;
use yii\base\Widget;
use yii\helpers\ArrayHelper;
use yii\helpers\Html;
use yii\helpers\Url;
/**
* 参照yii\widgets\Menu,根据AdminLTE样式从写的一个小物件
* @author Blobt
* @email 380255922@qq.com
* 使用例子
* <?php
* echo Menu::widget([
* 'items' => [
* ['label' => 'MAIN NAVIGATION', 'is_header' => true],
* ['label' => 'Documentation', 'url' => 'https:www.baidu.com', 'icon' => 'fa-book'],
* ['label' => 'Products', 'url' => ['product/index'], 'items' => [
* ['label' => 'New Arrivals', 'url' => ['product/index', 'tag' => 'new']],
* ['label' => 'Most Popular', 'url' => ['product/index', 'tag' => 'popular']],
* ]],
* ['label' => 'Login', 'url' => ['site/login'], 'visible' => Yii::$app->user->isGuest],
* ]
* ]);
* ?>
*
*
*/
class Menu extends Widget {
/**
* @var array 菜单的item数组。
* 菜单的item同时也是一个数组,结构如下所述:
* lable: string, optional,指定选项的label
* encode:boolean, optional,label是否需要转义
* url: string or array, optional, 生产菜单的路径
* 产生结果和yii的Url::to()方法一致,并且会套用[[linkTemplate]]模板
* visible: boolean, optional, 选项是否可见,默认是true(可见)
* active: boolean or Closure, optional, 是否被选中
* 如果为true,则会在css中添加[[activeCssClass]]
* 当使用Closure时候,匿名函数必须是`function ($item, $hasActiveChild, $isItemActive, $widget)`
* 匿名函数必须返回true或者false
* 如果不是使用匿名函数,就会使用[[isItemActive]]来判断item是否被选中
* items: array, optional, 指定子菜单选项,格式和父菜单是一样的
* template: string, optional,选项的渲染模板
* submenuTemplate: string, optional, 子菜单渲染模板
* options: array, optional, 指定html属性
*/
public $items = [];
/**
* @var array html属性,这些指定的属性会加到所有的item中
*/
public $itemOptions = [];
/**
* @var string 链接的渲染模板
*/
public $linkTemplateWithSub = "<a href=\"{url}\"><i class=\"fa {icon}\"></i><span>{label}</span><span class=\"pull-right-container\"><i class=\"fa fa-angle-left pull-right\"></i></span></a>";
public $linkTemplateNoSub = "<a href=\"{url}\"><i class=\"fa {icon}\"></i><span>{label}</span></a>";
/**
* @var string label的渲染模板
*/
public $labelTemplate = '{label}';
/**
* @var string 子菜单的渲染模板
*/
public $submenuTemplate = "\n<ul class=\"treeview-menu\">\n{items}\n</ul>\n";
/**
* @var boolean label是否要进行html转义
*/
public $encodeLabels = true;
/**
* @var string 被选中的菜单的CSS类
*/
public $activeCssClass = 'active';
/**
* @var string 控制二级菜单开合
*/
public $menuOpenClass = 'menu-open';
/**
* @var boolean 是否根据路由去判断菜单项是否被选中
*/
public $activateItems = true;
/**
* @var boolean 当某一个子菜单的选中时候是否也关联选中父菜单
*/
public $activateParents = true;
/**
* @var boolean 如果item的url没有设置时,是否不显示该item
*/
public $hideEmptyItems = true;
/**
* @var array 菜单容器标签的属性
*/
public $options = [
'class' => 'sidebar-menu',
'data-widget' => 'tree'
];
/**
* @var string 第一个菜单item的css类
*/
public $firstItemCssClass;
/**
* @var string 最后一个菜单item的css类
*/
public $lastItemCssClass;
/**
* @var string 路由 ,run的时候会自动获取当前路由
*/
public $route;
/**
* @var string $_GET参数
*/
public $params;
/**
* @var string 菜单项默认Icon
*/
public $defaultIcon = 'fa-circle-o';
/**
* 渲染菜单
*/
public function run() {
if ($this->route === null && Yii::$app->controller !== null) {
$this->route = Yii::$app->controller->getRoute();
}
if ($this->params === null) {
$this->params = Yii::$app->request->getQueryParams();
}
$items = $this->normalizeItems($this->items, $hasActiveChild);
if (!empty($items)) {
$options = $this->options;
$tag = ArrayHelper::remove($options, 'tag', 'ul');
return Html::tag($tag, $this->renderItems($items), $options);
}
}
/**
* 渲染菜单
* @param array $items
* @return string 渲染结果
*/
protected function renderItems($items) {
$lines = [];
foreach ($items as $i => $item) {
/* 获取菜单项的自定义属性 */
$options = array_merge($this->itemOptions, ArrayHelper::getValue($item, 'options', []));
$tag = ArrayHelper::remove($options, 'tag', 'li');
$class = [];
if ($item['active']) {
$class[] = $this->activeCssClass;
if (isset($item['items'])) {
$class[] = $this->menuOpenClass;
}
}
if ($i === 0 && $this->firstItemCssClass !== null) {
$class[] = $this->firstItemCssClass;
}
if ($i === $n - 1 && $this->lastItemCssClass !== null) {
$class[] = $this->lastItemCssClass;
}
if (isset($item['items'])) {
$class[] = 'treeview';
}
if (isset($item['is_header']) && $item['is_header']) {
$class[] = "header";
}
Html::addCssClass($options, $class);
$menu = $this->renderItem($item);
if (!empty($item['items'])) {
$submenuTemplate = ArrayHelper::getValue($item, 'submenuTemplate', $this->submenuTemplate);
$menu .= strtr($submenuTemplate, [
'{items}' => $this->renderItems($item['items']),
]);
}
$lines[] = Html::tag($tag, $menu, $options);
}
return implode("\n", $lines);
}
/**
* 渲染菜单项
* @param array $item
* @return string 渲染结果
*/
protected function renderItem($item) {
if (isset($item['url'])) {
if (isset($item['template'])) {
$template = $item['template'];
} else {
$template = isset($item['items']) ? $this->linkTemplateWithSub : $this->linkTemplateNoSub;
}
return strtr($template, [
'{url}' => Html::encode(Url::to($item['url'])),
'{label}' => Html::encode($item['label']),
'{icon}' => Html::encode($item['icon'])
]);
}
$template = ArrayHelper::getValue($item, 'template', $this->labelTemplate);
return strtr($template, [
'{label}' => $item['label'],
]);
}
/**
* 判断菜单项是否被选中
* @param $item array
* @return boolean $item
*/
protected function isItemActive($item) {
if (isset($item['url']) && is_array($item['url']) && isset($item['url'][0])) {
$route = Yii::getAlias($item['url'][0]);
if ($route[0] !== '/' && Yii::$app->controller) {
$route = Yii::$app->controller->module->getUniqueId() . '/' . $route;
}
if (ltrim($route, '/') !== $this->route) {
return false;
}
return true;
}
return false;
}
/**
* 格式化菜单item
* @param string $item
* @param bool $active
*/
protected function normalizeItems($items, &$active) {
foreach ($items as $i => $item) {
/* 去除visible 为 false的item */
if (isset($item['visible']) && !$item['visible']) {
unset($items[$i]);
continue;
}
/* 添加默认icon */
if (!isset($item['icon'])) {
if (!empty($this->defaultIcon)) {
$items[$i]['icon'] = $this->defaultIcon;
}
}
/* 添加label */
if (!isset($item['label'])) {
$item['label'] = '';
}
/* 转义HTML */
$encodeLabel = isset($item['encode']) ? $item['encode'] : $this->encodeLabels;
if ($encodeLabel) {
$items[$i]['label'] = Html::encode($item['label']);
}
/* 格式化子菜单 item */
$hasActiveChild = false;
if (isset($item['items'])) {
$items[$i]['items'] = $this->normalizeItems($item['items'], $hasActiveChild);
if (empty($items[$i]['items']) && $this->hideEmptyItems) {
unset($items[$i]['items']);
}
}
/* 处理菜单是否被选中 */
if (!isset($item['active'])) {
if ($this->activateParents && $hasActiveChild || $this->activateItems && $this->isItemActive($item)) {
$active = $items[$i]['active'] = true;
}
} elseif ($item['active'] instanceof Closure) {
$active = $items[$i]['active'] = call_user_func($item['active'], $item, $hasActiveChild, $this->isItemActive($item), $this);
} elseif ($item['active']) {
$active = true;
}
}
return array_values($items);
}
}

101
vendor/blobt/widgets/Select2.php

@ -0,0 +1,101 @@
<?php
/*
* The MIT License
*
* Copyright 2019 Blobt.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace blobt\widgets;
use yii\widgets\InputWidget;
use Yii;
use yii\base\InvalidConfigException;
use yii\helpers\ArrayHelper;
use yii\helpers\Html;
use blobt\web\Select2Asset;
/**
* Description of Select2
*
* @author Blobt
* @email 380255922@qq.com
* @created Aug 20, 2019
*/
class Select2 extends InputWidget {
/**
* @var array select的选项
*/
public $data = [];
/**
* @var array select 的html选择
*/
public $options;
/**
* @inheritdoc
* @throws \ReflectionException
* @throws \yii\base\InvalidConfigException
*/
public function run() {
d($this->id);
$this->registerAsset();
$this->registerSelect2Js();
return $this->renderSelect();
}
public function init() {
parent::init();
if ($this->hasModel() && !isset($options['name'])) {
$this->name = $this->options['name'] = Html::getInputName($this->model, $this->attribute);
}
}
/**
* 注册js和css
*/
protected function registerAsset() {
$view = $this->getView();
Select2Asset::register($view);
}
protected function registerSelect2Js() {
$js = <<<SCRIPT
$('#category-icon_type').select2();
SCRIPT;
$this->getView()->registerJs($js);
}
/**
* 渲染一个select
* @return string
*/
protected function renderSelect() {
$value = null;
if ($this->hasModel()) {
$value = ArrayHelper::getValue($this->model, $this->attribute);
}
return Html::dropDownList($this->name, $value, $this->data, $this->options);
}
}
Loading…
Cancel
Save