{"id":19990285,"url":"https://github.com/wangerzi/layui-authtree","last_synced_at":"2025-05-04T09:34:59.897Z","repository":{"id":118161098,"uuid":"127369385","full_name":"wangerzi/layui-authtree","owner":"wangerzi","description":"扩展 layui 的权限树 authtree","archived":false,"fork":false,"pushed_at":"2020-06-22T10:08:35.000Z","size":2661,"stargazers_count":269,"open_issues_count":9,"forks_count":82,"subscribers_count":21,"default_branch":"master","last_synced_at":"2024-11-13T04:52:19.347Z","etag":null,"topics":["authorization","layui","layui-authtree","layui-form"],"latest_commit_sha":null,"homepage":"","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/wangerzi.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2018-03-30T02:10:16.000Z","updated_at":"2024-10-24T06:36:54.000Z","dependencies_parsed_at":null,"dependency_job_id":"0b0d0d2c-0096-4fd0-a0c1-52044ce719f9","html_url":"https://github.com/wangerzi/layui-authtree","commit_stats":null,"previous_names":[],"tags_count":8,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wangerzi%2Flayui-authtree","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wangerzi%2Flayui-authtree/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wangerzi%2Flayui-authtree/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wangerzi%2Flayui-authtree/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/wangerzi","download_url":"https://codeload.github.com/wangerzi/layui-authtree/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":252316861,"owners_count":21728521,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["authorization","layui","layui-authtree","layui-form"],"created_at":"2024-11-13T04:51:07.234Z","updated_at":"2025-05-04T09:34:59.880Z","avatar_url":"https://github.com/wangerzi.png","language":"JavaScript","funding_links":[],"categories":["JavaScript"],"sub_categories":[],"readme":"# 扩展 layui 的权限树 authtree\n\nlayui自身提供一个tree树形菜单，但是并不适用于权限控制中，比如：选择用户组的权限（树形结构），需要使用form表单提交用户所选权限数据。\n\n项目中遇到了此类需求，所以特意封装了一个扩展用于渲染此类操作。\n\n\u003e  特别注意：由于此模块基于 layui.form，所以权限树的渲染目标需要在 .layui-form .layui-item下，否则将无法渲染出样式。\n\n\u003e 环境提示：预览环境需要部署在服务器下，不然无法异步获取权限树的数据\n\n## 功能演示：\n\n##### 在线演示：\n\n[http://authtree.wj2015.com/](http://authtree.wj2015.com/)\n\n![功能演示](https://raw.githubusercontent.com/wangerzi/layui-authtree/master/screenGIF.gif)\n\n\n##### 沟通交流群：\n\n**QQ群号：** 789188686\n\n![QQ交流群](https://raw.githubusercontent.com/wangerzi/layui-authtree/master/qq_group_qrcode.png)\n\n## 更新预告：\n\nv2.0 新增半选中状态、选中/半选中/未选中图标配置、重绘节点、附带额外信息、额外操作区等功能。\n\n\u003e 由于项目初期采用 layui.form 后导致很多自带样式不可控，以及 layui 版本变化带来的样式调整问题，目前已经卡住无法改动了，打算通过重构的形式让本项目恢复迭代，重构的2.0版本会保留核心的主题功能、一些好用的配置项，以及新增一些反馈频繁的半选、重绘节点、附带额外信息等功能。\n\u003e 具体重构由于个人工作原因和前端技能还不够了然于胸等缘故，开发时间会有点长，目前还停留在规划阶段。\n\n## 更新记录：\n2020-06-18 v1.3 支持节点不可选择、主题配置、隐藏左单选/多选框、树转列表树支持配置 value/checked/disabled的键名、叶子节点横排、末级节点横排\n\n2018-11-19 v1.2 支持单选树、下拉树、展开/收起图标配置\n\n2018-09-23 v1.1 新增自动展开所有选中节点,列表转树,支持双击展开子节点等方法,消除BUG\n\n2018-09-23 v1.0 正式版，方法效率优化以及新增监听事件，消除各种BUG\n\n2018-09-19 v1.0 预览版，完善权限树的方法，新增方法请见函数列表和演示样例\n\n2018-09-06 v0.5 新增authwidth参数用于适应节点名称宽度，默认true\n\n2018-05-03 v0.4 新增获取全部数据、全部已选数据、全部未选数据方法，修复编码问题。\n\n2018-05-03 v.03 新增默认展开全部的配置项(openall)，并将部分配置项作为可选参数通过对象传递。\n\n2018-03-30 v0.2 修复一级菜单没有子菜单时，显示错位的问题，支持获取叶子结点数据，支持自定义lay-filter\n\n2018-03-24 v0.1 最初版本\n\n## 期望收集\n\n- [x] 全选-全不选功能\n- [x] 显示到某层的功能（展开全部/收起全部）\n- [x] 最新添加/最新取消节点\n- [ ] 样例添加搜索功能\n- [x] 普通列表转权限树功能\n- [x] 权限树以适合单选框的形式转义\n- [x] 配置新增“取消级联选中”功能\n- [x] 树节点双击打开/关闭\n- [x] 支持对勾选的进行展开，而不是整个树\n- [ ] 新增toolbar，用于扩展权限控制的操作\n- [ ] 部分选择权限的时候，他的父级前面不打对号，换个其他符号\n- [x] 可以配置单选/多选，并可选 lay-skin 属性\n- [x] 新增事件 dbclick 用于监听双击\n- [x] 监听事件，新增 opt 参数，用于回调时便利的获取渲染参数，新增 tree 参数，用于把渲染数据传递过去\n- [x] 左侧单选/多选可以被隐藏\n- [x] 渲染/转换列表的时候可以禁止被选中\n- [ ] 可以支持 `reload` 方法用于重新渲染\n- [ ] 支持 `data` 参数用于节点的扩展属性\n- [x] 树转下拉树支持自定义初始递归id\n- [x] render() 函数支持自定义子节点列表字段\n- [ ] layer 中的 authtree 渲染说明(特别说明 iframe 中的渲染问题和修改BUG后浏览器缓存问题)\n- [x] render() 函数支持 checkedId 功能\n- [x] render() 函数调用/点击时自动给所有已渲染的树 autoWidth()\n- [x] 主题配置及相关说明\n- [x] 叶子节点横排\n- [x] 末级节点横排\n\n## BUG收集\n- [x] 插件BUG - 数据量达到150+会比较卡\n- [x] 插件BUG - 没有选中父节点时不能取消全选\n- [x] 样例BUG - 异步获取数据失败时权限树渲染为空，并且没有友好的提示用户\n- [x] 单选权限树-监听事件失效\n- [x] 如果子节点列表为 [] 或者 {} 会渲染下拉三角的问题\n\n## 快速上手\n\n\u003e 由于插件规模扩大和功能的增加，导致插件上手难度有一定的增加。但如果只使用核心功能，其实没有必要去研究插件的所有方法，故在此把此插件解决核心需求的方法展示出来。\n\n#### 第一步：为权限树提供容器\n\n\u003e 注意：`id=\"LAY-auth-tree-index\"` 是整颗树的容器，需要包含在 `form.layui-form \u003e div.layui-form-item \u003e div.layui-input-block` 中，否则依照 layui 的规则无法渲染多选框\n\n```html\n\u003cform class=\"layui-form\"\u003e\n    \u003cdiv class=\"layui-form-item\"\u003e\n        \u003clabel class=\"layui-form-label\"\u003e角色名称\u003c/label\u003e\n        \u003cdiv class=\"layui-input-block\"\u003e\n            \u003cinput class=\"layui-input\" type=\"text\" name=\"name\" placeholder=\"请输入角色名称\" /\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"layui-form-item\"\u003e\n        \u003clabel class=\"layui-form-label\"\u003e选择权限\u003c/label\u003e\n        \u003cdiv class=\"layui-input-block\"\u003e\n            \u003cdiv id=\"LAY-auth-tree-index\"\u003e\u003c/div\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n    \u003cdiv class=\"layui-form-item\"\u003e\n        \u003cdiv class=\"layui-input-block\"\u003e\n            \u003cbutton class=\"layui-btn\" type=\"submit\" lay-submit lay-filter=\"LAY-auth-tree-submit\"\u003e提交\u003c/button\u003e\n            \u003cbutton class=\"layui-btn layui-btn-primary\" type=\"reset\"\u003e重置\u003c/button\u003e\n        \u003c/div\u003e\n    \u003c/div\u003e\n\u003c/form\u003e\n```\n\n#### 第二步：下载源码并引入插件\n\n如果使用 `layuiadmin`,则只需要将插件(`extends/authtree.js`)放到 `controller/`下,然后 `layui.use` 即可,或者可以放在 `lib/extend` 中,只不过需要改 `config.js`\n\n非 `layuiadmin` 初始化如下：\n\n```javascript\nlayui.config({\n\tbase: 'extends/',\n}).extend({\n\tauthtree: 'authtree',\n});\n```\n\n如果需要使用主题，建议将 `themes/` 复制到可以被浏览器访问到的地方，然后参考 [主题使用方式](https://github.com/wangerzi/layui-authtree#%E4%B8%BB%E9%A2%98%E4%BD%BF%E7%94%A8%E6%96%B9%E5%BC%8F) 进行配置。\n\n#### 第三步：异步获取权限数据并渲染\n\n`render` 传递的第一个参数，即为树的目标容器，这也是以后操作这颗树的重要标志\n\n`listConvert` 是 `authtree` 提供的内置函数，可以将普通的列表数据转换为 权限树需要的数据结构，如有此需求请查看该函数对应文档\n\n```javascript\nlayui.use(['jquery', 'authtree', 'form', 'layer'], function(){\n\tvar $ = layui.jquery;\n\tvar authtree = layui.authtree;\n\tvar form = layui.form;\n\tvar layer = layui.layer;\n\t// 一般来说，权限数据是异步传递过来的\n\t$.ajax({\n\t\turl: 'tree.json',\n\t\tdataType: 'json',\n\t\tsuccess: function(data){\n            var trees = data.data.trees;\n            // 如果后台返回的不是树结构，请使用 authtree.listConvert 转换\n            authtree.render('#LAY-auth-tree-index', trees, {\n\t\t\t\tinputname: 'authids[]', \n\t\t\t\tlayfilter: 'lay-check-auth', \n\t\t\t\tautowidth: true,\n\t\t\t});\n        }\n    });\n});\n```\n\n至此，一个最基础的权限树就已经完成了，如果想实现演示GIF内的各种扩展功能，请继续往下看，并参考源码。\n\n## 主题定制\n\n### 参与主题定制\n\n完善中...\n\n### 已上线主题列表\n\n| 主题名称            | 版本   | 作者                              | 备注                                            | 上传时间   |\n| ------------------- | ------ | --------------------------------- | ----------------------------------------------- | ---------- |\n| auth-skin-default   | v1.0.0 | Jeffrey Wang(admin@wj2015.com)    | 默认主题，感谢lipengfei886@qq.com提供的基础样式 | 2019-05-07 |\n| auth-skin-universal | v1.0.0 | lipengfei886(lipengfei886@qq.com) | lipengfei886@qq.com提供的绿色背景样式           | 2019-05-09 |\n\n### 主题使用方式\n\n调用主题在调用 [**render(dst, trees, opt)**](https://github.com/wangerzi/layui-authtree#render-%E5%8F%82%E6%95%B0%E9%85%8D%E7%BD%AE) 渲染树的时候配置 `theme` 和 `themePath` 参数，分别代表 主题名称、主题文件路径，主题文件路径必须是浏览器可以访问到的绝对或相对路径。\n\n假设我们需要使用 `auth-skin-default` ，主题文件夹放到了 `/layui_exts/authtree/themes` 中，我们在渲染的时候就可以编写如下代码。\n\n```javascript\nauthtree.render('#LAY-auth-tree-hide-choose-dom', trees, {\n    layfilter: 'LAY-auth-tree-hide-choose-input',\n    theme: 'auth-skin-default',\n    themePath: '/layui_exts/authtree/themes/' // 主题路径，默认 layui_exts/tree_themes/\n});\n```\n\n## 数据库设计和后台程序参考\n\n正在完善中....\n\n## 函数列表\n\n| 函数名                                                       | 描述                                                         | 备注            |\n| ------------------------------------------------------------ | ------------------------------------------------------------ | --------------- |\n| [**render(dst, trees, opt)**](https://github.com/wangerzi/layui-authtree#render-%E5%8F%82%E6%95%B0%E9%85%8D%E7%BD%AE) | 初始化一棵权限树                                             | opt参数详见文档 |\n| [**listConvert(list, opt)**](https://github.com/wangerzi/layui-authtree#listconvert-%E5%8F%82%E6%95%B0%E9%85%8D%E7%BD%AE) | 将普通列表无限递归转换为树（opt参数可配置项，请参考下方参数配置） | opt参数详见文档 |\n| [treeConvertSelect(tree, opt)](https://github.com/wangerzi/layui-authtree#treeconvertselect%E5%8F%82%E6%95%B0%E9%85%8D%E7%BD%AE) | 将树转为单选树，如果后台返回列表数据，可以先 listConvert() 转换为树 | opt参数详见文档 |\n| getMaxDept(dst)                                              | 获取树的最大深度                                             |                 |\n| **checkAll(dst)**                                            | 全选所有节点                                                 |                 |\n| **uncheckAll(dst)**                                          | 取消选中所有节点                                             |                 |\n| showChecked(dst)                                             | 显示所有选中节点对应层级（无论父级节点是否选中，均会级联显示） |                 |\n| showAll(dst)                                                 | 显示整颗树                                                   |                 |\n| closeAll(dst)                                                | 关闭整颗树                                                   |                 |\n| toggleAll(dst)                                               | 树的显示/关闭切换                                            |                 |\n| showDept(dst, dept)                                          | 显示此树到第 dept 层                                         |                 |\n| closeDept(dst, dept)                                         | 第 dept 层之后全部关闭                                       |                 |\n| getLeaf(dst)                                                 | 获取叶子节点（form.on()需延迟获取）                          |                 |\n| getAll(dst)                                                  | 获取所有节点数据（form.on()需延迟获取）                      |                 |\n| getLastChecked(dst)                                          | 最新选中节点数据（之前未选-现在选中）（form.on()需延迟获取） |                 |\n| getChecked(dst)                                              | 获取所有选中节点的数据（form.on()需延迟获取）                |                 |\n| getLastNotChecked(dst)                                       | 最新取消（之前选中-现在未选）（form.on()需延迟获取）         |                 |\n| getNotChecked(dst)                                           | 获取未选中数据（form.on()需延迟获取）                        |                 |\n\n## 重要函数参数配置\n\n#### render 参数配置\n\n`render()` 函数是本插件的核心方法，调用 `render(dst, trees, opt)` 函数时\n\ntrees 对象中基础属性含义如下：\n\n| 参数名   | 描述                                    | 默认  |\n| -------- | --------------------------------------- | ----- |\n| name     | 显示在外的名称(可通过 nameKey改变)      |       |\n| value    | 单选/多选表单的值(可通过 valueKey 改变) |       |\n| checked  | 是否选中(可通过 checkedKey改变)         | false |\n| disabled | 是否不可选择(可通过 disabledKey改变)    | false |\n| type | 是否在一行上显示(可通过 authType 改变)    | false |\n\nopt 参数如下：\n\n| 参数名               | 描述                                                         | 默认                    |\n| -------------------- | ------------------------------------------------------------ | ----------------------- |\n| **inputname**        | 上传上去的 input 表单的name                                  | menuids[]               |\n| layfilter            | input 元素的 layfilter，可通过 authtree.on('change(layfilter)') 监听 | checkauth               |\n| openall              | 是否初始化显示全部                                           | false                   |\n| **dblshow**          | 双击展开节点                                                 | false                   |\n| hidechoose           | 隐藏左侧 单选/多选框 - 特殊需求使用，建议checkType=radio     | false                   |\n| dbltimeout           | 双击展开节点延迟(最好不要超过300，不然单击延迟会比较高)      | 180                     |\n| openchecked          | 默认展开有选中数据的层                                       | true                    |\n| **autochecked**      | 选中节点后,是否自动选中直属父级并且选中所有子节点            | true                    |\n| **autoclose**        | 取消节点选中后,是否自动取消父级选中(当兄弟节点均为未选中时)  | true                    |\n| **collapseLeafNode** | 叶子节点横排开关（仅使用主题有效）                           | false                    |\n| **collapseLastDepthNode** | 末级节点横排开关（仅使用主题有效）                           | false                    |\n| checkType            | 选择表单类型，checkbox: 多选，radio: 单选                    | checkbox                |\n| checkSkin            | 表单渲染的 lay-skin 参数，详见官方文档                       | primary                 |\n| openIconContent      | 展开的前显字符配置（默认是方向向下的三角形，就像这样▼）      | ▼                       |\n| closeIconContent     | 折叠的前显字符配置（默认是方向向右的三角形，就像这样▶）      | ▶                       |\n| prefixChildStr       | 有子节点的前显字符配置                                       | ├─                      |\n| checkedKey           | 渲染 checked(选中状态)的属性名称，支持数组                   | checked                 |\n| childKey             | 渲染 子节点的属性名称                                        | list                    |\n| disabledKey          | 渲染 disabled(禁止选中状态)的属性名称，支持数组              | disabled                |\n| nameKey              | 渲染 title(多选框的外显名称)的属性名称                       | name                    |\n| valueKey             | 渲染 value(上传d值)的属性名称                                | value                   |\n| theme                | 主题名称（取自 [已上线主题列表](https://github.com/wangerzi/layui-authtree#%E5%B7%B2%E4%B8%8A%E7%BA%BF%E4%B8%BB%E9%A2%98%E5%88%97%E8%A1%A8)） |                         |\n| themePath            | 主题路径（配置时记得最后的反斜杠）                           | layui_exts/tree_themes/ |\n| formFilter           | layui的form表单lay-filter避免与其他form冲突                  | t1                      |\n\n##### 自动选中 用法描述：\n\n\u003e 自动选中父级节点：开启后，选中某节点，会将其上层所有未选中父节点设为选中，并且将其下层所有节点设为选中；取消选中某节点，其所有子节点均取消。\n\u003e\n\u003e 自动取消父级节点：开启后，取消选中某一子节点，当其兄弟节点均处于未选中状态，自动取消父级节点\n\u003e\n\u003e\n\u003e\n\u003e 两种状态一般同时开启，或者同时关闭，不然可能体验有点奇怪\n\n##### checkType = radio 的特殊说明：\n\n\u003e 如果 checkType = radio，表示需要使用单选树，那么此时传入的 inputname 就不能是类似「\"ids[]\"」这种带中括号的形式，而应该是「\"id\"」，不然由于 layui 表单的特殊提交逻辑，会将 ids[] 换成 ids[1] ids[2]，导致单选节点的 name 不重复，变成可以多选的单选。\n\n#### treeConvertSelect参数配置\n\n`treeConverSelect` 是用于树转换为『单选树』的方法，其中 opt 参数如下\n\n| 参数名           | 描述                                                         | 默认值   |\n| ---------------- | ------------------------------------------------------------ | -------- |\n| childKey         | 子节点列表的Key                                              | list     |\n| valueKey         | 值的key                                                      | value    |\n| checkedKey       | 选中的key - 支持数组                                         | checked  |\n| disabledKey      | 禁用的key - 支持数组                                         | disabled |\n| prefixChildStr   | 有子节点的名称显示前缀                                       | ├─       |\n| prefixNoChildStr | 没有子节点的名称显示前缀                                     | ●        |\n| prefixDeptStr    | 树的深度影响的子节点显示前缀                                 |          |\n| prefixFirstEmpty | 如果第一列就存在没有子节点的情况，加的特殊前缀(占位用，正常使用不需要修改) |          |\n\n**调用样例**\n\n```html\n\u003cscript type=\"text/javascript\"\u003e\n$.ajax({\n    url: 'tree.json',\n    dataType: 'json',\n    success: function(res){\n        // 更多传入参数及其具体意义请查看文档\n        var selectList = authtree.treeConvertSelect(res.data.trees, {\n            childKey: 'list',\n        });\n        console.log(selectList);\n        // 渲染单选框\n        var string =  laytpl($('#LAY-auth-tree-convert-select').html()).render({\n            // 为了 layFilter 的唯一性，使用模板渲染的方式传递\n            layFilter: 'LAY-auth-tree-convert-select-input',\n            list: selectList,\n            code: JSON.stringify(res, null, 2),\n        });\n        $('#LAY-auth-tree-convert-select-dom').html(string);\n        layui.code({\n            title: '返回的树状数据'\n        });\n        form.render('select');\n        // 使用form.on('select(LAY-FILTER)')监听选中\n        form.on('select(LAY-auth-tree-convert-select-input)', function(data){\n            console.log('选中信息', data);\n        });\n    },\n    error: function(xml, errstr, err) {\n        layer.alert(errstr+'，获取样例数据失败，请检查是否部署在本地服务器中！');\n    }\n});\n\u003c/script\u003e\n\u003c!- 单选树的模板-\u003e\n\u003cscript type=\"text/html\" id=\"LAY-auth-tree-convert-select\"\u003e\n\u003cfieldset class=\"layui-elem-field layui-field-title\"\u003e\n\t\u003clegend\u003e树转下拉树\u003c/legend\u003e\n\u003c/fieldset\u003e\n\u003cform class=\"layui-form\"\u003e\n\t\u003cdiv class=\"layui-form-item\"\u003e\n\t\t\u003clabel class=\"layui-form-label\"\u003e转换结果\u003c/label\u003e\n\t\t\u003cdiv class=\"layui-input-block\"\u003e\n\t\t\t\u003cselect name=\"authid\" class=\"layui-input\" lay-filter=\"{{d.layFilter}}\"\u003e\n\t\t\t\t{{# layui.each(d.list, function(index, item) { }}\n\t\t\t\t\u003coption value=\"{{item.value}}\" {{item.checked?'selected':''}} {{item.disabled?'disabled':''}}\u003e{{item.name}}\u003c/option\u003e\n\t\t\t\t{{# });}}\n\t\t\t\u003c/select\u003e\n\t\t\u003c/div\u003e\n\t\u003c/div\u003e\n\t\u003cblockquote class=\"layui-elem-quote\"\u003e注：如果返回的是列表数据而非树状数据，可以先进行『列表转树』操作。\u003cbr\u003e往后如果对这方面的效率有需求，请联系我添加一个 『列表转下拉树』的功能！\u003c/blockquote\u003e\n\t\u003cpre class=\"layui-code\"\u003e{{d.code}}\u003c/pre\u003e\n\u003c/form\u003e\n\u003c/script\u003e\n```\n\n#### listConvert 参数配置\n\n`listConvert` 是用于转换列表和树结构的方法，参数比较灵活，调用 `listConvert(list, opt)` 时，opt可传入参数如下\n\n| 参数名         | 描述                                               | 默认值   |\n| -------------- | -------------------------------------------------- | -------- |\n| **primaryKey** | 主键                                               | id       |\n| **parentKey**  | 父级id对应键                                       | pid      |\n| startPid       | 作为父节点的pid，会先查找此pid对应的节点作为父节点 | 0        |\n| nameKey        | 节点标题对应的key                                  | name     |\n| valueKey       | 节点值对应的key                                    | id       |\n| **checkedKey** | 节点是否选中的字段（支持 String 和 Array）         | checked  |\n| disabledKey    | 节点是否不可选的字段（支持String和Array）          | disabled |\n\n\u003e **关于 checkedKey 参数的设计：**\n\u003e\n\u003e 权限树的初始化选中是为 “编辑权限” 这个场景开发的，编辑权限的时候，从 **『角色-权限表』** 读取某个角色对应的权限信息，所以读取出来的结果是 **『某个角色的权限id列表』** 。\n\u003e\n\u003e 判断节点是否应该处于选中状态，就是判断这个 **『节点的id』** 是否在 **『查找出来的权限id列表』** 中，基于这个想法，我把 checkedKey 设计为可传入 字符/数组，用以简化后台数据处理流程。\n\u003e\n\u003e 如果 checkedKey 为字符串，则直接将 list 中对应**checkedKey**对应字段隐射到 节点的 checked 字段中去；如果为数组，则会判断**valueKey**对应字段是否在 **checkedKey** 数组里边。\n\n##### 后台编辑权限API代码示例（PHP）\n\n```php\n\u003c?php\n$role_id = $_GET['role_id'];\n$auth_list = []; // 获取数据库中 权限表数据\n$role_auth_list = []; // 获取数据库中某个角色的 角色-权限表数据\n\n$data = [\n    'code' =\u003e 0,\n    'msg'  =\u003e '获取成功',\n    'data' =\u003e [\n        'list' =\u003e $auth_list,\n        'checkedId' =\u003e array_column($role_auth_list, 'authid'),\n    ],\n];\necho json_encode($data);\n```\n\n##### API返回数据示例\n\n```json\n{\n  \"code\": 0,\n  \"msg\": \"获取成功\",\n  \"data\": {\n    \"list\": [\n      { \"id\": 1, \"name\": \"用户管理\", \"pid\": 0 },\n      { \"id\": 2, \"name\": \"用户组管理\", \"pid\": 0 },\n      { \"id\": 3, \"name\": \"角色管理\", \"pid\": 2 },\n      { \"id\": 4, \"name\": \"添加角色\", \"pid\":  3},\n      { \"id\": 5, \"name\": \"角色列表\", \"pid\": 3 },\n      { \"id\": 6, \"name\": \"管理员管理\", \"pid\": 0 },\n      { \"id\": 7, \"name\": \"添加管理员\", \"pid\": 6 },\n      { \"id\": 8, \"name\": \"管理员列表\", \"pid\": 6 }\n    ],\n    \"checkedId\": [ 1,  2, 3, 4 ]\n  }\n}\n```\n\n##### 前端使用样例\n\n这里注意 `startPid` 参数的数据类型需要和列表返回的一致，`id` 和 `pid` 的数据类型需一致，如果列表返回的id数据均为字符串，则 startPid 应该为 `'0'`\n\n```javascript\nvar trees = authtree.listConvert(res.data.list, {\n    primaryKey: 'id'\n    ,startPid: 0\n    ,parentKey: 'pid'\n    ,nameKey: 'name'\n    ,valueKey: 'id'\n    ,checkedKey: res.data.checkedId\n});\n```\n\n## 监听事件\n\n| 事件名称   | 描述                                               | 样例                                 |\n| ---------- | -------------------------------------------------- | ------------------------------------ |\n| change     | 监听节点树节点选中状态改变(包括全选等)             | authtree.on('change(layfilter)')     |\n| checkAll   | 监听全选(目前仅限手动操作的全选)                   | authtree.on('checkAll(layfilter)')   |\n| uncheckAll | 监听全不选(目前仅限手动操作的全不选)               | authtree.on('uncheckAll(layfilter)') |\n| deptChange | 监听层数改变（包括点击、展开、关闭、全部展开关闭） | authtree.on('deptChange(layfilter)') |\n| dblclick   | 监听双击事件                                       | authtree.on('dblclick(layfilter)')   |\n\n### change事件返回参数一览\n\n| 参数名称 | 描述                       |\n| -------- | -------------------------- |\n| dst      | 目标id                     |\n| oinput   | input的jQuery对象          |\n| opt      | 渲染本树的参数             |\n| othis    | 美化后的jQuery对象         |\n| tree     | 此树的树状数据             |\n| value    | 这个单选/多选的value属性值 |\n\n\n\n## 功能概览：\n\n1. 支持无限级渲染结构树\n2. 点击深层次节点，父级节点中没有被选中的节点会被自动选中\n3. 单独点击父节点，子节点会全部 选中/去选中\n4. 支持默认选中（适用于编辑权限）\n5. 支持自定义表单名称（上传数据的name）\n6. 支持自定义lay-filter用于监听权限树选中(v0.2新增)\n7. 支持获取选中叶子结点信息(v0.2新增)\n8. 自适应标签名字长度配置(v0.5新增)\n9. 支持各种方式花样获取数据（v1.0 新增，具体参考函数表）\n10. 支持普通列表转树(v1.1 支持)\n11. 支持自动展开所有选中节点(v1.1 支持)\n12. 支持列表转树(v1.1 支持)\n13. 支持双击展开子节点(v1.1 支持)\n14. 支持配置渲染参数、单选树、下拉树(v1.2 支持)\n\n## 使用方法：\n\n\u003e 注意：此扩展需先引入layui.js方可正常使用。demo详见index.html\n\n##### js使用样例：\n\n```javascript\n// 注：extends/为authtree.js的存放路径\nlayui.config({\n\tbase: 'extends/',\n}).extend({\n\tauthtree: 'authtree',\n});\nlayui.use(['jquery', 'authtree', 'form', 'layer'], function(){\n\tvar $ = layui.jquery;\n\tvar authtree = layui.authtree;\n\tvar form = layui.form;\n\tvar layer = layui.layer;\n\t// 初始化\n\t$.ajax({\n\t\turl: 'tree.json',\n\t\tdataType: 'json',\n\t\tsuccess: function(data){\n\t\t\t// 渲染时传入渲染目标ID，树形结构数据（具体结构看样例，checked表示默认选中），以及input表单的名字\n\t\t\tauthtree.render('#LAY-auth-tree-index', data.data.trees, {\n\t\t\t\tinputname: 'authids[]', \n\t\t\t\tlayfilter: 'lay-check-auth', \n\t\t\t\t// openall: true,\n\t\t\t\tautowidth: true,\n\t\t\t});\n\n\t\t\t// PS:使用 form.on() 会引起了事件冒泡延迟的BUG，需要 setTimeout()，并且无法监听全选/全不选\n\t\t\tform.on('checkbox(lay-check-auth)', function(data){\n\t\t\t\t// 注意这里：需要等待事件冒泡完成，不然获取叶子节点不准确。\n\t\t\t\tsetTimeout(function(){\n\t\t\t\t\tconsole.log('监听 form 触发事件数据', data);\n\t\t\t\t\t// 获取选中的叶子节点\n\t\t\t\t\tvar leaf = authtree.getLeaf('#LAY-auth-tree-index');\n\t\t\t\t\tconsole.log('leaf', leaf);\n\t\t\t\t\t// 获取最新选中\n\t\t\t\t\tvar lastChecked = authtree.getLastChecked('#LAY-auth-tree-index');\n\t\t\t\t\tconsole.log('lastChecked', lastChecked);\n\t\t\t\t\t// 获取最新取消\n\t\t\t\t\tvar lastNotChecked = authtree.getLastNotChecked('#LAY-auth-tree-index');\n\t\t\t\t\tconsole.log('lastNotChecked', lastNotChecked);\n\t\t\t\t}, 100);\n\t\t\t});\n\t\t\t// 使用 authtree.on() 不会有冒泡延迟\n\t\t\tauthtree.on('change(lay-check-auth)', function(data) {\n\t\t\t\tconsole.log('监听 authtree 触发事件数据', data);\n\t\t\t\t// 获取所有节点\n\t\t\t\tvar all = authtree.getAll('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('all', all);\n\t\t\t\t// 获取所有已选中节点\n\t\t\t\tvar checked = authtree.getChecked('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('checked', checked);\n\t\t\t\t// 获取所有未选中节点\n\t\t\t\tvar notchecked = authtree.getNotChecked('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('notchecked', notchecked);\n\t\t\t\t// 获取选中的叶子节点\n\t\t\t\tvar leaf = authtree.getLeaf('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('leaf', leaf);\n\t\t\t\t// 获取最新选中\n\t\t\t\tvar lastChecked = authtree.getLastChecked('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('lastChecked', lastChecked);\n\t\t\t\t// 获取最新取消\n\t\t\t\tvar lastNotChecked = authtree.getLastNotChecked('#LAY-auth-tree-index');\n\t\t\t\tconsole.log('lastNotChecked', lastNotChecked);\n\t\t\t});\n\t\t\tauthtree.on('deptChange(lay-check-auth)', function(data) {\n\t\t\t\tconsole.log('监听到显示层数改变',data);\n\t\t\t});\n\t\t}\n\t});\n\tform.on('submit(LAY-auth-tree-submit)', function(obj){\n\t\tvar authids = authtree.getAll('#LAY-auth-tree-index');\n\t\tconsole.log('Choosed authids is', authids);\n\t\tobj.field.authids = authids;\n\t\t$.ajax({\n\t\t\turl: 'tree.json',\n\t\t\tdataType: 'json',\n\t\t\tdata: obj.field,\n\t\t\tsuccess: function(res){\n\t\t\t\tlayer.alert('提交成功！');\n\t\t\t}\n\t\t});\n\t\treturn false;\n\t});\n});\n```\n\n##### 权限树返回样例：\n\n\u003e name是节点名称，value是需要上传的值（如：菜单id），checked控制是否默认选中，list内部是子节点。\n\n```json\n{\n  \"code\": 0,\n  \"msg\": \"获取成功\",\n  \"data\": {\n    \"trees\":[\n    \t{\"name\": \"用户管理\", \"value\": \"xsgl\", \"checked\": true, \"list\": [\n    \t\t{\"name\": \"用户组\", \"value\": \"xsgl-basic\", \"checked\": true, \"list\": [\n    \t\t\t{\"name\": \"本站用户\", \"value\": \"xsgl-basic-xsxm\", \"checked\": true, \"list\": [\n    \t\t\t\t{\"name\": \"用户列表\", \"value\": \"xsgl-basic-xsxm-readonly\", \"checked\": true},\n    \t\t\t\t{\"name\": \"新增用户\", \"value\": \"xsgl-basic-xsxm-editable\", \"checked\": false}\n    \t\t\t]},\n                {\"name\": \"第三方用户\", \"value\": \"xsgl-basic-xsxm\", \"checked\": true, \"list\": [\n                    {\"name\": \"用户列表\", \"value\": \"xsgl-basic-xsxm-readonly\", \"checked\": true}\n                ]}\n    \t\t]}\n    \t]},\n    \t{\"name\": \"用户组管理\", \"value\": \"sbgl\", \"checked\": true, \"list\": [\n    \t\t{\"name\": \"角色管理\", \"value\": \"sbgl-sbsjlb\", \"checked\": true, \"list\":[\n    \t\t\t{\"name\": \"添加角色\", \"value\": \"sbgl-sbsjlb-dj\", \"checked\": true},\n    \t\t\t{\"name\": \"角色列表\", \"value\": \"sbgl-sbsjlb-yl\", \"checked\": false}\n    \t\t]},\n            {\"name\": \"管理员管理\", \"value\": \"sbgl-sbsjlb\", \"checked\": true, \"list\":[\n                {\"name\": \"添加管理员\", \"value\": \"sbgl-sbsjlb-dj\", \"checked\": true},\n                {\"name\": \"管理员列表\", \"value\": \"sbgl-sbsjlb-yl\", \"checked\": false}\n            ]}\n    \t]}\n    ]\n  }\n}\n```\n\n##### Demo说明：\n\nindex.html\t\t\t页面文件+JS处理文件\n\ntree.json\t\t\t模拟权限树数据\n\nextends/authtree.js\t权限树扩展\n\nlayui/\t\t\t\t官网下载的layui\n\n## 特别感谢\n\n##### layui社区:\n\n感谢 [Xiao情子](https://fly.layui.com/u/13405224/)、[挽手说梦话](https://fly.layui.com/u/15279936/)、[呆呆17](https://fly.layui.com/u/21441168/)、[空痕影](https://fly.layui.com/u/24549336/)、[mmmmargin](https://fly.layui.com/u/16231488/)、[Son](https://fly.layui.com/u/10266648/)、[夏诺](https://fly.layui.com/u/7003752/)、[尧仙子](https://fly.layui.com/u/7185864/)、[徐俊](https://fly.layui.com/u/6566280/)、[IBean](https://fly.layui.com/u/4473336/) 等童鞋提供的建议\n\n##### github:\n\n感谢 [adminpass](https://github.com/adminpass) 、[MrZhouL](https://github.com/MrZhouL)、[lzjlxebr](https://github.com/lzjlxebr)、[lintiansheng](https://github.com/lintiansheng) 、[5ini99](https://github.com/5ini99)等人提供的反馈和建议","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fwangerzi%2Flayui-authtree","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fwangerzi%2Flayui-authtree","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fwangerzi%2Flayui-authtree/lists"}