前言
这里只是自己的一个想法。此想法只完成了里面的一部分。记于此,希望有同样需求的同学们共同讨论和学习。
我也是刚学习使用这个框架。在学习使用的过程中有这样的一个需求。我的某一个文章分类下面的文章需要添加两个字段(原价、现价),我想很多同学都有这样的需求吧。要是能向onethink那样为模型添加字段就好了。那就自己来实现吧。想一想实现步骤。
1、在分类里添加此分类下的文章需要自定义的字段;
2、在添加文章选择分类的时候查看此分类下是否有自定义的字段,有就展示出来。
我去,这么简单!!!
1 设计
还记得我们在使用thinkcmf的是候的模板设计功能么(有点启发了)。模版里的json文件就是用来控制模版的设计的。那么我们也用一个数组或对象(我们暂时把它命名为selfFields)来定义我们自定义的文章分类字段,在添加文章的时候,当我们选择了文章分类后,就通过这个分类对应的这个selfFields来生成自定义字段的html,然后再把html插入到分类的后面。好像很完美呀!
2 实现
2.1 selfFields的添加和存储
首先selfFields肯定是要在添加分分类的时候生成的。那我们就来看看分类表的结构把。
{
"thumbnail":"portal\/20171102\/6676d62fca5e4080d338b044c30aca45.jpg",
"self_field":{ //此分类下的文章自定义字段
"old_price":{
"title":"原价",
"value":"",
"type":"text",
"tip":"",
"rule":{
"require":true
}
},
"now_price":{
"title":"现价",
"value":"",
"type":"text",
"tip":"",
"rule":{
"require":true
}
}
}
}
好吧,虽然有点扯。先就这样吧。
文件\thinkcmf\public\themes\admin_simpleboot3\portal\admin_category\add.html修改两处
文件\thinkcmf\app\portal\controller\AdminCategoryController.php
public function addPost()
{
$portalCategoryModel = new PortalCategoryModel();
$data = $this->request->param();
//--start--添加代码---
$self_field=json_decode(htmlspecialchars_decode($data['more']['self_field']),true);
if ($self_field){
$data['more']['self_field']=$self_field;
}else{
unset( $data['more']['self_field']);
}
//----end----添加代码---
$result = $this->validate($data, 'PortalCategory');
if ($result !== true) {
$this->error($result);
}
$result = $portalCategoryModel->addCategory($data);
if ($result === false) {
$this->error('添加失败!');
}
$this->success('添加成功!', url('AdminCategory/index'));
}
到此分类这面的工作好像就完了,当然分类修改就不多说了。
2.2 在添加文章的时候插入自定义的分类字段
我们在添加文章的时候,当选完分类的时候,通过Ajax从后端获取到生好的html字符串,然后插入到分类字段的后面。
2.2.1 前端
文件\thinkcmf\public\themes\admin_simpleboot3\portal\admin_article\add.html
function doSelectCategory() {
var selectedCategoriesId = $('#js-categories-id-input').val();
openIframeLayer("{:url('AdminCategory/select')}?ids=" + selectedCategoriesId, '请选择分类', {
area: ['700px', '400px'],
btn: ['确定', '取消'],
yes: function (index, layero) {
//do something
var iframeWin = window[layero.find('iframe')[0]['name']];
var selectedCategories = iframeWin.confirm();
if (selectedCategories.selectedCategoriesId.length == 0) {
layer.msg('请选择分类');
return;
}
$('#js-categories-id-input').val(selectedCategories.selectedCategoriesId.join(','));
$('#js-categories-name-input').val(selectedCategories.selectedCategoriesName.join(' '));
//console.log(layer.getFrameIndex(index));
//只需要添加下面这一段 只需要添加下面这一段 只需要添加下面这一段
//选择分类后 就需要动态获取 需要加载的此分类的自定义的文章字段
$.post('{:url("AdminCategory/getCategorySelfFieldHtml")}',
{id:selectedCategories.selectedCategoriesId.join(',')},
function (data) {
$('.self-field').remove();
$('#js-categories-name-input').parent().parent().after(data);
}
);
//只需要添加上面这一段 只需要添加上面这一段 只需要添加上面这一段
layer.close(index); //如果设定了yes回调,需进行手工关闭
}
});
}
2.2.2 后端生成html
在上面我们是在AdminCategory/getCategorySelfFieldHtml中获取的html。
$.post('{:url("AdminCategory/getCategorySelfFieldHtml")}'
那我们就去后端实现它吧!!
文件\thinkcmf\app\portal\controller\AdminCategoryController.php添加方法
public function getCategorySelfFieldHtml()
{
$ids = $this->request->param('id');
$ids=explode(',',$ids);
$portalCategoryModel = new PortalCategoryModel();
$categoryData=$portalCategoryModel->field('id,more')->find($ids[0])->toArray();
if (!empty($categoryData['more']['self_field'])){
//下面有一个类 我要去实现它
$categoryHtmleService= new \app\portal\service\CategoryHtmleService();
$categoryHtml=$categoryHtmleService->getCategorySelfFieldHtml($categoryData['more']['self_field']);
return $categoryHtml;
}
}
添加\thinkcmf\app\portal\service\CategoryHtmleService.php
// +----------------------------------------------------------------------
// | jaydon
// +----------------------------------------------------------------------
// | Copyright
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: Jaydon
// +----------------------------------------------------------------------
namespace app\portal\service;
class CategoryHtmleService
{
public function getCategorySelfFieldHtml($self_fields){
$htmlString='';
foreach ($self_fields as $key=>$self_field){
switch ($self_field['type']){
case "text":
$htmlString.=$this->parseText($self_field,$key); //这次就实现这个方法吧 下面的慢慢去实现吧
break;
case "textarea":
$htmlString.=$this->parseTextarea($self_field,$key);
break;
case "date":
$htmlString.=$this->parseDate($self_field,$key);
break;
case "datetime":
$htmlString.=$this->parseDatetime($self_field,$key);
break;
case "image":
$htmlString.=$this->parseImage($self_field,$key);
break;
case "photos":
$htmlString.=$this->parsePhotos($self_field,$key);
break;
case "number":
$htmlString.=$this->parseNumber($self_field,$key);
break;
case "location":
$htmlString.=$this->parseLocation($self_field,$key);
break;
case "file":
$htmlString.=$this->parseFilet($self_field,$key);
break;
case "color":
$htmlString.=$this->parseColor($self_field,$key);
break;
case "array":
$htmlString.=$this->parseArray($self_field,$key);
break;
case "select":
$htmlString.=$this->parseSelect($self_field,$key);
break;
case "slide":
$htmlString.=$this->parseSlide($self_field,$key);
break;
}
}
return $htmlString;
}
/**
* 拼接textl类型的html 注意name的拼接 name="post[more][self_fields][$key]
* @param $self_field
* @param $key
* @return string
*/
public function parseText($self_field,$key){
true === $self_field['rule']['require'] ? $required='required' : $required='';
$htmlString="
".$self_field['title']."*
";
return $htmlString;
}
}
到此好像就完成了。
test
提交的数据
存入了数据库
至于文章编辑的时候,就是先把自定义的html生成,而且把value也生成在里面即可。
以上就是我的一些想法,写得不好 ,还望各位大神指点。