D2Admin 1.7

Former-commit-id: 3010ce31114fdc121006451c72f9e18306239fd2
This commit is contained in:
liyang
2019-05-07 09:26:18 +08:00
parent 46bc6ca451
commit d07d15ed8c
952 changed files with 171232 additions and 0 deletions
+3
View File
@@ -0,0 +1,3 @@
> 1%
last 2 versions
not ie <= 8
+10
View File
@@ -0,0 +1,10 @@
# 所有环境默认
# 页面 title 前缀
VUE_APP_TITLE=D2Admin
# 网络请求公用地址
VUE_APP_API=/api/
# 仓库地址
VUE_APP_REPO=https://github.com/d2-projects/d2-admin
+4
View File
@@ -0,0 +1,4 @@
# 开发环境
# 页面 title 前缀
VUE_APP_TITLE=D2Admin Dev
+7
View File
@@ -0,0 +1,7 @@
# No Mock 构建
# 指定构建模式
NODE_ENV=production
# 标记当前是 No Mock 构建
VUE_APP_BUILD_MODE=nomock
+7
View File
@@ -0,0 +1,7 @@
# travis
# 指定构建模式
NODE_ENV=production
# 标记当前是 CI 自动构建
VUE_APP_BUILD_MODE=TRAVIS
+11
View File
@@ -0,0 +1,11 @@
# 忽略目录
build/
tests/
node_modules/
# node 覆盖率文件
coverage/
# 忽略文件
**/*-min.js
**/*.min.js
+17
View File
@@ -0,0 +1,17 @@
module.exports = {
root: true,
env: {
node: true
},
'extends': [
'plugin:vue/essential',
'@vue/standard'
],
rules: {
'no-console': process.env.NODE_ENV === 'production' ? 'error' : 'off',
'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off'
},
parserOptions: {
parser: 'babel-eslint'
}
}
+11
View File
@@ -0,0 +1,11 @@
---
name: "👾 BUG"
about: 代码错误
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
👾 BUG | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "🎮 示例相关"
about: 增加或者完善示例
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
🎮 示例相关 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "🌈 显示优化"
about: 显示方面调整
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
🌈 显示优化 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "📔 文档相关"
about: 更新或者新增文档内容
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
📔 文档相关 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "🔩 功能开发"
about: 开发新的功能
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
🔩 功能开发 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "🖐 其它问题"
about: 其它类型的 issue 请使用该模板
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
🖐 其它问题 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "🤔 提问"
about: 提出使用方面的问题
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
🤔 提问 | 你的标题
```
如果需要,在这里描述具体内容
+11
View File
@@ -0,0 +1,11 @@
---
name: "⚙ 功能升级"
about: 升级某个功能
---
```
为了统一格式,请将下面一行复制到 `Title` 栏,然后删除这部分
⚙ 功能升级 | 你的标题
```
如果需要,在这里描述具体内容
+17
View File
@@ -0,0 +1,17 @@
.DS_Store
node_modules
/dist
# Log files
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# Editor directories and files
.idea
.vscode
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw*
+5
View File
@@ -0,0 +1,5 @@
module.exports = {
plugins: {
autoprefixer: {}
}
}
+21
View File
@@ -0,0 +1,21 @@
MIT License
Copyright (c) 2018 李杨
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.
+153
View File
@@ -0,0 +1,153 @@
![banner](https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/banner.png)
<p align="center">
<a><img src="https://img.shields.io/github/release/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/npm/v/@d2-admin/ice-scaffold.svg"/></a>
<a href="https://www.travis-ci.org/d2-projects/d2-admin"><img src="https://www.travis-ci.org/d2-projects/d2-admin.svg?branch=master"/></a>
<a><img src="https://img.shields.io/github/last-commit/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/badge/code_style-standard-brightgreen.svg"/></a>
</p>
<p align="center">
<a><img src="https://img.shields.io/github/issues/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-closed/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-pr/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-pr-closed/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/forks/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/stars/d2-projects/d2-admin.svg"/></a>
</p>
D2Admin is a fully open source and free enterprise back-end product front-end integration solution, using the latest front-end technology stack, has prepared most of the project preparations, and with a lot of sample code to help the management system agile development.
[中文介绍](https://github.com/d2-projects/d2-admin/blob/master/README.zh.md) | **English**
## Document
[document](https://doc.d2admin.fairyever.com)
## Preview
[preview](https://d2admin.fairyever.com)
## Features
* Build with vue-cli3
* First screen loading waiting animation
* Five themes
* Built-in UEditor rich text editor
* Detailed documentation
* Login and logout
* Separate routing and menu settings
* Foldable sidebar
* Multi-national language
* Rich text editor
* Markdown editor
* full screen
* Fontawesome icon library
* Icon selector
* Automatically register SVG icon
* Simulation data
* Clipboard package
* Chart library
* Time and date calculation tool
* Import Excel ( xlsx + csv )
* Data export Excel ( xlsx + csv )
* Data export text
* Digital animation
* Drag and drop the size of the block layout
* Grid layout for drag and resize and position
* Out-of-the-box page layout components
* Load and parse markdown files
* GitHub style markdown display component
* markdown internal code highlighting
* Expanded Baidu cloud link resolution and optimized display for markdown
* Right click menu component
* Custom scrollbars and scrolling controls
* Common style extraction, convenient theme customization
* Support temporary menu configuration
* System function display module `1.1.4 +`
* Multi-tab mode `1.1.4 +`
* Beautify the scroll bar `1.1.4 +`
* json view `1.1.4 +`
* cookie wrapper `1.1.5 +`
* Multi-tab global control API `1.1.5 +`
* Menu Global Control API `1.1.5 +`
* Multi-tab page close control support right-click menu `1.1.10 +`
* Modular global state management `1.2.0 +`
* Multiple data persistence methods: distinguish users, distinguish routes, page data snapshot function `1.2.0 +`
* Support for menu system that jumps out of external links `1.2.0 +`
* Support menu svg icon `1.3.0 +`
* Logging and error catching `1.3.0 +`
* Global menu search `1.3.0 +`
* Custom login redirect `1.3.0 +`
* Switch global base component size `1.4.0 +`
* Page loading progress bar `1.4.1 +`
* Adaptive top menu bar `1.4.7 +`
* Support for merging cells when exporting xslx `1.5.4 +`
## Other version
| Name | HomePage | Preview | Introduction |
| --- | --- | --- | --- |
| Starter template | [Github](https://github.com/d2-projects/d2-admin-start-kit) | [Preview](https://start-kit.d2admin.fairyever.com) | |
| D2 Admin Renren | [Github](https://github.com/d2-projects/d2-admin-renren-security-enterprise) | [Preview](https://renren.d2admin.fairyever.com) | [renren](https://www.renren.io) |
| Alibaba Ice scaffold | [Ice](https://alibaba.github.io/ice/scaffold?type=vue) | [Preview](https://ice.d2admin.fairyever.com) | [Introduction](https://juejin.im/post/5b6349716fb9a04f834669d6) |
## Ecology
| Name | HomePage | Preview | Introduction |
| --- | --- | --- | --- |
| D2 Daily | [Github](https://github.com/d2-projects/d2-awesome) | [Site](https://awesome.fairyever.com/daily/) | Update news and resources in the design and technology circles every day |
| D2 CRUD | [Github](https://github.com/d2-projects/d2-crud) | [Preview](https://d2admin.fairyever.com/#/demo/d2-crud/index) | Table common operation package |
| D2 Ribbons | [Github](https://github.com/d2-projects/d2-ribbons) | [Preview](https://github.com/d2-projects/d2-ribbons) | Open source project logo library |
## Derived open source projects
> These projects are contributed by the open source community and are not guaranteed to use the latest version of D2Admin. Please contact their open source authors for related usage questions.
| Name | Github / HomePage | Preview | Introduction |
| --- | --- | --- | --- |
| d2-admin-pm | [Github](https://github.com/wjkang/d2-admin-pm) | [Preview](http://jaycewu.coding.me/d2-admin-pm) | RBAC privilege management solution based on d2-admin |
| LanBlog | [Github](https://github.com/sinksmell/LanBlog) | [Preview](http://47.101.222.133/) | Vue + Beego restful api personal blog system |
## Open source backend implementation
> The backend is contributed by the open source community. The latest version of D2Admin is not guaranteed. Please contact its open source author for related usage issues.
| Name | technology | HomePage | Preview | Introduction |
| --- | --- | --- | --- | --- |
| **jiiiiiin-security** | Spring Boot + Spring Security | [Github](https://github.com/Jiiiiiin/jiiiiiin-security) | [Preview](https://github.com/Jiiiiiin/jiiiiiin-security) | Separate front-end and back-end content management infrastructure projects, focusing on user rights management functions |
| **Taroco** | Spring Cloud | [Github](https://github.com/liuht777/Taroco) | [Preview](http://111.231.192.110/) | Complete microservice enterprise solution |
| **Aooms** | Spring Cloud | [Gitee](https://gitee.com/cyb-javaer/Aooms) | [Preview](https://www.yuboon.com/Aooms) | Extremely fast microservice development, not just as simple as JFinal |
| **GOA** | Beego | [Github](https://github.com/Qsnh/goa) | [Preview](http://goaio.vip/) | Online question answering system based on Beego + Vue |
## Badge
If your open source project is based on D2Admin development, please add the following badge to your README:
<a href="https://github.com/d2-projects/d2-admin" target="_blank">
<img src="https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/d2-admin@2x.png" width="200">
</a>
Copy the following code into the README to:
``` html
<a href="https://github.com/d2-projects/d2-admin" target="_blank"><img src="https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/d2-admin@2x.png" width="200"></a>
```
At the same time, you can report your project to us. We will place the excellent project in D2Admin and help you publicize it.
## Important Contributor
* [@FairyEver](https://github.com/FairyEver)
* [@sunhaoxiang](https://github.com/sunhaoxiang)
* [@Aysnine](https://github.com/Aysnine)
* [@han-feng](https://github.com/han-feng)
* [@rongxingsun](https://github.com/rongxingsun)
* [@dnyz520](https://github.com/dnyz520)
## License
[MIT](https://github.com/d2-projects/d2-admin/blob/master/LICENSE)
Copyright (c) 2018-present FairyEver
+167
View File
@@ -0,0 +1,167 @@
![banner](https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/banner.png)
<p align="center">
<a><img src="https://img.shields.io/github/release/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/npm/v/@d2-admin/ice-scaffold.svg"/></a>
<a href="https://www.travis-ci.org/d2-projects/d2-admin"><img src="https://www.travis-ci.org/d2-projects/d2-admin.svg?branch=master"/></a>
<a><img src="https://img.shields.io/github/last-commit/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/badge/code_style-standard-brightgreen.svg"/></a>
</p>
<p align="center">
<a><img src="https://img.shields.io/github/issues/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-closed/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-pr/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/issues-pr-closed/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/forks/d2-projects/d2-admin.svg"/></a>
<a><img src="https://img.shields.io/github/stars/d2-projects/d2-admin.svg"/></a>
</p>
[D2Admin](https://github.com/d2-projects/d2-admin) 是一个完全 **开源免费** 的企业中后台产品前端集成方案,使用最新的前端技术栈,已经做好大部分项目前期准备工作,并且带有大量示例代码,助力管理系统敏捷开发。
**中文介绍** | [English](https://github.com/d2-projects/d2-admin)
## 文档
[文档](https://doc.d2admin.fairyever.com)
## 预览
[预览地址](https://d2admin.fairyever.com)
## 码云仓库
[码云](https://gitee.com/fairyever/d2-admin)
> 如果您在 github 仓库下载很慢,可以尝试使用我们的码云仓库克隆代码
## 功能
* 使用 vue-cli3 构建
* 首屏加载等待动画
* 五款主题
* 内置 UEditor 富文本编辑器
* 详细的文档
* 登录和注销
* 分离的路由和菜单设置
* 可折叠侧边栏
* 多国语
* 富文本编辑器
* Markdown 编辑器
* 全屏
* Fontawesome 图标库
* 图标选择器
* 自动注册 SVG 图标
* 模拟数据
* 剪贴板封装
* 图表库
* 时间日期计算工具
* 导入 Excel ( xlsx + csv )
* 数据导出 Excel ( xlsx + csv )
* 数据导出文本
* 数字动画
* 可拖拽调整大小的区块布局
* 可拖拽调整大小和位置的网格布局
* 开箱即用的页面布局组件
* 加载并解析 markdown 文件
* GitHub 样式的 markdown 显示组件
* markdown 内代码高亮
* 为 markdown 扩展了百度云链接解析和优化显示
* 右键菜单组件
* 自定义滚动条和滚动控制
* 公用样式抽离,方便的主题定制
* 支持临时菜单配置
* 系统功能展示模块 `1.1.4 +`
* 多标签页模式 `1.1.4 +`
* 美化滚动条 `1.1.4 +`
* json view `1.1.4 +`
* cookie 封装 `1.1.5 +`
* 多标签页全局控制 API `1.1.5 +`
* 菜单全局控制 API `1.1.5 +`
* 多标签页关闭控制支持右键菜单 `1.1.10 +`
* 模块化全局状态管理 `1.2.0 +`
* 多种数据持久化方式:区分用户,区分路由,页面数据快照功能 `1.2.0 +`
* 支持跳出外部链接的菜单系统 `1.2.0 +`
* 支持菜单 svg 图标 `1.3.0 +`
* 日志记录和错误捕捉 `1.3.0 +`
* 全局菜单搜索 `1.3.0 +`
* 自定义登录重定向 `1.3.0 +`
* 切换全局基础组件尺寸 `1.4.0 +`
* 页面载入进度条 `1.4.1 +`
* 自适应的顶部菜单栏 `1.4.7 +`
* 数据导出 xslx 时支持合并单元格 `1.5.4 +`
## 其它版本
| 名称 | Github / 主页 | 预览 | 介绍 |
| --- | --- | --- | --- |
| 简化版模板 | [Github](https://github.com/d2-projects/d2-admin-start-kit) | [预览](https://start-kit.d2admin.fairyever.com) | 无 |
| 人人开源适配 | [Github](https://github.com/d2-projects/d2-admin-renren-security-enterprise) | [预览](https://renren.d2admin.fairyever.com) | [人人开源](https://www.renren.io) |
| 飞冰脚手架 | [飞冰](https://alibaba.github.io/ice/scaffold?type=vue) | [预览](https://ice.d2admin.fairyever.com) | [介绍](https://juejin.im/post/5b6349716fb9a04f834669d6) |
## 生态
| 名称 | Github / 主页 | 预览 | 介绍 |
| --- | --- | --- | --- |
| D2 日报 | [Github](https://github.com/d2-projects/d2-awesome) | [网站](https://awesome.fairyever.com/daily/) | 每天更新设计与技术圈的新闻和资源 |
| D2 CRUD | [Github](https://github.com/d2-projects/d2-crud) | [预览](https://d2admin.fairyever.com/#/demo/d2-crud/index) | 表格常用操作封装 |
| D2 Ribbons | [Github](https://github.com/d2-projects/d2-ribbons) | [预览](https://github.com/d2-projects/d2-ribbons) | 开源项目徽标库 |
## 衍生开源项目
> 这些项目由开源社区贡献,不保证使用 D2Admin 最新版本,相关使用问题请联系其开源作者。
| 名称 | Github / 主页 | 预览 | 介绍 |
| --- | --- | --- | --- |
| d2-admin-pm | [Github](https://github.com/wjkang/d2-admin-pm) | [预览](http://jaycewu.coding.me/d2-admin-pm) | 基于 d2-admin 的 RBAC 权限管理解决方案 |
| LanBlog | [Github](https://github.com/sinksmell/LanBlog) | [预览](http://47.101.222.133/) | Vue + Beego restful api 开发的懒人博客 |
## 开源后端实现
> 后端由开源社区贡献,不保证使用 D2Admin 最新版本,相关使用问题请联系其开源作者。
| 名称 | 技术 | Github / 主页 | 预览 | 介绍 |
| --- | --- | --- | --- | --- |
| jiiiiiin-security | Spring Boot + Spring Security | [Github](https://github.com/Jiiiiiin/jiiiiiin-security) | [预览](https://github.com/Jiiiiiin/jiiiiiin-security) | 前后端分离的内容管理基础项目,注重用户权限管理功能 |
| Taroco | Spring Cloud | [Github](https://github.com/liuht777/Taroco) | [预览](http://111.231.192.110/) | 整套微服务企业级解决方案 |
| Aooms | Spring Cloud | [码云](https://gitee.com/cyb-javaer/Aooms) | [预览](https://www.yuboon.com/Aooms) | 极速微服务开发,不止像JFinal一样简单 |
| GOA | Beego | [Github](https://github.com/Qsnh/goa) | [预览](http://goaio.vip/) | 基于 Beego + Vue 开发的在线问答系统 |
## 徽章
如果您的开源项目基于 D2Admin 开发,请在您的 README 添加下面的徽章:
<a href="https://github.com/d2-projects/d2-admin" target="_blank">
<img src="https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/d2-admin@2x.png" width="200">
</a>
复制下面代码加入到 README 中即可:
``` html
<a href="https://github.com/d2-projects/d2-admin" target="_blank"><img src="https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/d2-admin@2x.png" width="200"></a>
```
同时您可以将您的项目汇报给我们,优秀项目我们会放置在 D2Admin 相关位置并帮助您宣传。
## 加入我们
D2Admin 是完全开源免费的项目,旨在帮助开发者更方便地进行管理系统开发,同时也提供 2000 人的 QQ 交流群和微信群,前后端的朋友可以相互答疑,项目组成员全部在内,所有 D2 相关项目使用问题欢迎在群内提问。
![join](https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/join@2x.png)
## 重要贡献者
* [@FairyEver](https://github.com/FairyEver)
* [@sunhaoxiang](https://github.com/sunhaoxiang)
* [@Aysnine](https://github.com/Aysnine)
* [@han-feng](https://github.com/han-feng)
* [@rongxingsun](https://github.com/rongxingsun)
* [@dnyz520](https://github.com/dnyz520)
## License
[MIT](https://github.com/d2-projects/d2-admin/blob/master/LICENSE)
Copyright (c) 2018-present FairyEver
![](https://raw.githubusercontent.com/FairyEver/d2-admin/master/doc/image/give-a-star@2x.png)
+5
View File
@@ -0,0 +1,5 @@
module.exports = {
presets: [
'@vue/app'
]
}
Binary file not shown.

After

Width:  |  Height:  |  Size: 748 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 23 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 258 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 470 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 271 KiB

+23
View File
@@ -0,0 +1,23 @@
module.exports = {
moduleFileExtensions: [
'js',
'jsx',
'json',
'vue'
],
transform: {
'^.+\\.vue$': 'vue-jest',
'.+\\.(css|styl|less|sass|scss|png|jpg|ttf|woff|woff2)$': 'jest-transform-stub',
'^.+\\.jsx?$': 'babel-jest'
},
moduleNameMapper: {
'^@/(.*)$': '<rootDir>/src/$1'
},
snapshotSerializers: [
'jest-serializer-vue'
],
testMatch: [
'**/tests/unit/**/*.spec.(js|jsx|ts|tsx)|**/__tests__/*.(js|jsx|ts|tsx)'
],
testURL: 'http://localhost/'
}
+15974
View File
File diff suppressed because it is too large Load Diff
+74
View File
@@ -0,0 +1,74 @@
{
"name": "d2-admin",
"version": "1.7.0",
"scripts": {
"serve": "vue-cli-service serve --open",
"start": "npm run serve",
"dev": "npm run serve",
"build": "vue-cli-service build",
"build:nomock": "vue-cli-service build --mode nomock",
"build:travis": "vue-cli-service build --mode travis",
"lint": "vue-cli-service lint --fix",
"test:unit": "vue-cli-service test:unit"
},
"dependencies": {
"@d2-admin/filters-dayjs": "^1.0.3",
"@d2-projects/d2-crud": "^2.0.5",
"@d2-projects/vue-table-export": "^1.0.1",
"@d2-projects/vue-table-import": "^1.0.0",
"axios": "^0.18.0",
"better-scroll": "^1.15.2",
"clipboard-polyfill": "^2.8.0",
"core-js": "^2.6.5",
"countup.js": "^2.0.4",
"dayjs": "^1.8.12",
"echarts": "^4.2.1",
"element-ui": "^2.7.2",
"flex.css": "^1.1.7",
"fuse.js": "^3.4.4",
"github-markdown-css": "^3.0.1",
"highlight.js": "^9.15.6",
"hotkeys-js": "^3.6.2",
"js-cookie": "^2.2.0",
"lodash": "^4.17.11",
"lowdb": "^1.0.0",
"marked": "^0.6.2",
"mockjs": "^1.0.1-beta3",
"nprogress": "^0.2.0",
"qs": "^6.7.0",
"quill": "^1.3.6",
"screenfull": "^4.2.0",
"simplemde": "^1.11.2",
"ua-parser-js": "^0.7.19",
"v-charts": "^1.19.0",
"v-contextmenu": "^2.8.0",
"vue": "^2.6.10",
"vue-grid-layout": "^2.3.4",
"vue-i18n": "^8.10.0",
"vue-json-tree-view": "^2.1.4",
"vue-router": "^3.0.3",
"vue-splitpane": "^1.0.4",
"vue-ueditor-wrap": "^2.4.1",
"vuex": "^3.0.1"
},
"devDependencies": {
"@kazupon/vue-i18n-loader": "^0.3.0",
"@vue/cli-plugin-babel": "^3.6.0",
"@vue/cli-plugin-eslint": "^3.6.0",
"@vue/cli-plugin-unit-jest": "^3.6.0",
"@vue/cli-service": "^3.6.0",
"@vue/eslint-config-standard": "^4.0.0",
"@vue/test-utils": "1.0.0-beta.29",
"babel-core": "7.0.0-bridge.0",
"babel-eslint": "^10.0.1",
"babel-jest": "^23.6.0",
"eslint": "^5.16.0",
"eslint-plugin-vue": "^5.0.0",
"sass": "^1.18.0",
"sass-loader": "^7.1.0",
"svg-sprite-loader": "^4.1.3",
"text-loader": "0.0.1",
"uglifyjs-webpack-plugin": "^2.1.2",
"vue-template-compiler": "^2.5.21"
}
}
+3
View File
@@ -0,0 +1,3 @@
> 1%
last 2 versions
not ie <= 8
+21
View File
@@ -0,0 +1,21 @@
.DS_Store
node_modules
/dist
# local env files
.env.local
.env.*.local
# Log files
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# Editor directories and files
.idea
.vscode
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw*
+5
View File
@@ -0,0 +1,5 @@
module.exports = {
plugins: {
autoprefixer: {}
}
}
+1
View File
@@ -0,0 +1 @@
# filters-dayjs
+5
View File
@@ -0,0 +1,5 @@
module.exports = {
presets: [
'@vue/app'
]
}
File diff suppressed because it is too large Load Diff
+18
View File
@@ -0,0 +1,18 @@
{
"name": "@d2-admin/filters-dayjs",
"version": "1.0.3",
"main": "dist/@d2-admin/filters-dayjs.common.js",
"scripts": {
"build": "vue-cli-service build --target lib --name @d2-admin/filters-dayjs --entry src/main.js"
},
"dependencies": {
"core-js": "^2.6.5",
"dayjs": "^1.8.12",
"vue": "^2.6.6"
},
"devDependencies": {
"@vue/cli-plugin-babel": "^3.0.0",
"@vue/cli-service": "^3.0.0",
"vue-template-compiler": "^2.5.21"
}
}
+86
View File
@@ -0,0 +1,86 @@
// 日期时间相关 filter
// https://github.com/iamkun/dayjs/blob/master/docs/zh-cn/API-reference.md
import dayjs from 'dayjs'
// 对象代理
const P = Day => {
return new Proxy(Day, {
get (target, key) {
if (dayjs.isDayjs(target)) {
// 是 Dayjs 对象,正常返回
return target[key]
} else {
// 不是 Dayjs 对象
if (dayjs(target).isValid()) {
// 尝试帮用户解析成 Dayjs 对象
return dayjs(target)[key]
} else {
// 无法解析
return function () {
return '无效日期'
}
}
}
},
set (target, key, value) {
target[key] = value
}
})
}
export default {
// ---------- [ dayjs 解析 ] ----------
// 时间字符串 | Date 对象 | Unix 时间戳 (毫秒)
day: value => dayjs(value),
// Unix 时间戳 (秒)
date_unix: value => dayjs.unix(value),
// ---------- [ 获取 ] ----------
date_year: Day => P(Day).year(),
date_month: Day => P(Day).month(),
date_date: Day => P(Day).date(),
date_day: Day => P(Day).day(),
date_hour: Day => P(Day).hour(),
date_minute: Day => P(Day).minute(),
date_second: Day => P(Day).second(),
date_millisecond: Day => P(Day).millisecond(),
// ---------- [ 设置 ] ----------
// date | day | month | year | hour | minute | second | millisecond
// 对大小写不敏感
date_set: (Day, unit, value) => P(Day).set(unit, value),
// ---------- [ 操作 ] ----------
// 增加
date_add: (Day, value, unit) => P(Day).add(value, unit),
// 减少
date_subtract: (Day, value, unit) => P(Day).subtract(value, unit),
// 开头时间
date_startof: (Day, unit) => P(Day).startOf(unit),
// 末尾时间
date_endof: (Day, unit) => P(Day).endOf(unit),
// ---------- [ 显示 ] ----------
// 格式化
date_format: (Day, setting = 'YYYY-MM-DD HH:mm:ss') => P(Day).format(setting),
// 时间差
date_diff: (Day, Day2 = '', unit = 'millisecond', accurate = false) => P(Day).diff(dayjs(Day2), unit, accurate),
// Unix 时间戳 (毫秒)
date_value_millisecond: Day => P(Day).valueOf(),
// Unix 时间戳 (秒)
date_value_second: Day => P(Day).unix(),
// 月份的天数
date_days_in_month: Day => P(Day).daysInMonth(),
// Date 对象
date_to_date: Day => P(Day).toDate(),
// JSON
date_to_json: Day => P(Day).toJSON(),
// ISO8601 格式
date_to_iso: Day => P(Day).toISOString(),
// 字符
date_to_string: Day => P(Day).toString(),
// ---------- [ 查询 ] ----------
// 是否之前
date_is_before: (Day, Day2, unit = 'millisecond') => P(Day).isBefore(dayjs(Day2), unit),
// 是否之后
date_is_after: (Day, Day2, unit = 'millisecond') => P(Day).isAfter(dayjs(Day2), unit),
// 是否相同
date_is_same: (Day, Day2, unit = 'millisecond') => P(Day).isSame(dayjs(Day2), unit)
}
+15
View File
@@ -0,0 +1,15 @@
import filters from './filters'
const vueFiltersDate = {
install: function (Vue, options) {
Object.keys(filters).forEach(name => {
Vue.filter(name, filters[name])
})
}
}
if (typeof window !== 'undefined' && window.Vue) {
window.Vue.use(vueFiltersDate)
}
export default vueFiltersDate
File diff suppressed because it is too large Load Diff
+100
View File
@@ -0,0 +1,100 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<style>
body, html {
width: 100%;
height: 100%;
margin: 0px;
}
body {
display: flex;
align-items: center;
justify-content: center;
perspective: 900px;
background-color: #FFF;
}
.cube {
width: 100px;
height: 100px;
position: relative;
transform-style: preserve-3d;
animation: rotate 10s linear infinite;
}
.cube:after {
content: '';
width: 100%;
height: 100%;
box-shadow: 0 0 50px rgba(0, 0, 0, 0.2);
position: absolute;
transform-origin: bottom;
transform-style: preserve-3d;
transform: rotateX(90deg) translateY(50px) translateZ(-50px);
background-color: rgba(0, 0, 0, 0.1);
}
.cube div {
background-color: rgba(64, 158, 255, 0.7);
position: absolute;
width: 100%;
height: 100%;
border: 1px solid rgb(27, 99, 170);
box-shadow: 0 0 60px rgba(64, 158, 255, 0.7);
}
.cube div:nth-child(1) {
transform: translateZ(-50px);
animation: shade 10s -5s linear infinite;
}
.cube div:nth-child(2) {
transform: translateZ(50px) rotateY(180deg);
animation: shade 10s linear infinite;
}
.cube div:nth-child(3) {
transform-origin: right;
transform: translateZ(50px) rotateY(270deg);
animation: shade 10s -2.5s linear infinite;
}
.cube div:nth-child(4) {
transform-origin: left;
transform: translateZ(50px) rotateY(90deg);
animation: shade 10s -7.5s linear infinite;
}
.cube div:nth-child(5) {
transform-origin: bottom;
transform: translateZ(50px) rotateX(90deg);
background-color: rgba(0, 0, 0, 0.7);
}
.cube div:nth-child(6) {
transform-origin: top;
transform: translateZ(50px) rotateX(270deg);
}
@keyframes rotate {
0% {
transform: rotateX(-15deg) rotateY(0deg);
}
100% {
transform: rotateX(-15deg) rotateY(360deg);
}
}
@keyframes shade {
50% {
background-color: rgba(0, 0, 0, 0.7);
}
}
</style>
<title>demo</title>
</head>
<body>
<div class="cube">
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
<div></div>
</div>
</body>
</html>
BIN
View File
Binary file not shown.

After

Width:  |  Height:  |  Size: 66 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

+6
View File
@@ -0,0 +1,6 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32" width="32" height="32" fill="white">
<path opacity=".25" d="M16 0 A16 16 0 0 0 16 32 A16 16 0 0 0 16 0 M16 4 A12 12 0 0 1 16 28 A12 12 0 0 1 16 4"/>
<path d="M16 0 A16 16 0 0 1 32 16 L28 16 A12 12 0 0 0 16 4z">
<animateTransform attributeName="transform" type="rotate" from="0 16 16" to="360 16 16" dur="0.8s" repeatCount="indefinite" />
</path>
</svg>

After

Width:  |  Height:  |  Size: 422 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 86 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 359 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 20 KiB

+55
View File
@@ -0,0 +1,55 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width,initial-scale=1.0">
<link rel="icon" href="<%= BASE_URL %>icon.ico">
<title><%= VUE_APP_TITLE %></title>
<style>
html, body, #app { height: 100%; margin: 0px; padding: 0px; }
.d2-home { background-color: #303133; height: 100%; display: flex; flex-direction: column; }
.d2-home__main { user-select: none; width: 100%; flex-grow: 1; display: flex; justify-content: center; align-items: center; flex-direction: column; }
.d2-home__footer { width: 100%; flex-grow: 0; text-align: center; padding: 1em 0; }
.d2-home__footer > a { font-size: 12px; color: #ABABAB; text-decoration: none; }
.d2-home__loading { height: 32px; width: 32px; margin-bottom: 20px; }
.d2-home__title { color: #FFF; font-size: 14px; margin-bottom: 10px; }
.d2-home__sub-title { color: #ABABAB; font-size: 12px; }
</style>
<script>
var _hmt = _hmt || [];
var hmid = "bc38887aa5588add05a38704342ad7e8";
(function() { var hm = document.createElement("script"); hm.src = "https://hm.baidu.com/hm.js?" + hmid; var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(hm, s);})();
</script>
</head>
<body>
<noscript>
<strong>
很抱歉,如果没有 JavaScript 支持,D2Admin 将不能正常工作。请启用浏览器的 JavaScript 然后继续。
</strong>
</noscript>
<div id="app">
<div class="d2-home">
<div class="d2-home__main">
<img
class="d2-home__loading"
src="./image/loading/loading-spin.svg"
alt="loading">
<div class="d2-home__title">
正在加载资源
</div>
<div class="d2-home__sub-title">
初次加载资源可能需要较多时间 请耐心等待
</div>
</div>
<div class="d2-home__footer">
<a
href="https://github.com/d2-projects/d2-admin"
target="_blank">
https://github.com/d2-projects/d2-admin
</a>
</div>
</div>
</div>
</body>
</html>
Binary file not shown.

After

Width:  |  Height:  |  Size: 5.2 KiB

@@ -0,0 +1,40 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title></title>
<style type="text/css">
*{color: #838383;margin: 0;padding: 0}
html,body {font-size: 12px;overflow: hidden; }
.content{padding:5px 0 0 15px;}
input{width:210px;height:21px;line-height:21px;margin-left: 4px;}
</style>
</head>
<body>
<div class="content">
<span><var id="lang_input_anchorName"></var></span><input id="anchorName" value="" />
</div>
<script type="text/javascript" src="../internal.js"></script>
<script type="text/javascript">
var anchorInput = $G('anchorName'),
node = editor.selection.getRange().getClosedNode();
if(node && node.tagName == 'IMG' && (node = node.getAttribute('anchorname'))){
anchorInput.value = node;
}
anchorInput.onkeydown = function(evt){
evt = evt || window.event;
if(evt.keyCode == 13){
editor.execCommand('anchor', anchorInput.value);
dialog.close();
domUtils.preventDefault(evt)
}
};
dialog.onok = function (){
editor.execCommand('anchor', anchorInput.value);
dialog.close();
};
$focus(anchorInput);
</script>
</body>
</html>
@@ -0,0 +1,681 @@
@charset "utf-8";
/* dialog样式 */
.wrapper {
zoom: 1;
width: 630px;
*width: 626px;
height: 380px;
margin: 0 auto;
padding: 10px;
position: relative;
font-family: sans-serif;
}
/*tab样式框大小*/
.tabhead {
float:left;
}
.tabbody {
width: 100%;
height: 346px;
position: relative;
clear: both;
}
.tabbody .panel {
position: absolute;
width: 0;
height: 0;
background: #fff;
overflow: hidden;
display: none;
}
.tabbody .panel.focus {
width: 100%;
height: 346px;
display: block;
}
/* 上传附件 */
.tabbody #upload.panel {
width: 0;
height: 0;
overflow: hidden;
position: absolute !important;
clip: rect(1px, 1px, 1px, 1px);
background: #fff;
display: block;
}
.tabbody #upload.panel.focus {
width: 100%;
height: 346px;
display: block;
clip: auto;
}
#upload .queueList {
margin: 0;
width: 100%;
height: 100%;
position: absolute;
overflow: hidden;
}
#upload p {
margin: 0;
}
.element-invisible {
width: 0 !important;
height: 0 !important;
border: 0;
padding: 0;
margin: 0;
overflow: hidden;
position: absolute !important;
clip: rect(1px, 1px, 1px, 1px);
}
#upload .placeholder {
margin: 10px;
border: 2px dashed #e6e6e6;
*border: 0px dashed #e6e6e6;
height: 172px;
padding-top: 150px;
text-align: center;
background: url(./images/image.png) center 70px no-repeat;
color: #cccccc;
font-size: 18px;
position: relative;
top:0;
*top: 10px;
}
#upload .placeholder .webuploader-pick {
font-size: 18px;
background: #00b7ee;
border-radius: 3px;
line-height: 44px;
padding: 0 30px;
*width: 120px;
color: #fff;
display: inline-block;
margin: 0 auto 20px auto;
cursor: pointer;
box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1);
}
#upload .placeholder .webuploader-pick-hover {
background: #00a2d4;
}
#filePickerContainer {
text-align: center;
}
#upload .placeholder .flashTip {
color: #666666;
font-size: 12px;
position: absolute;
width: 100%;
text-align: center;
bottom: 20px;
}
#upload .placeholder .flashTip a {
color: #0785d1;
text-decoration: none;
}
#upload .placeholder .flashTip a:hover {
text-decoration: underline;
}
#upload .placeholder.webuploader-dnd-over {
border-color: #999999;
}
#upload .filelist {
list-style: none;
margin: 0;
padding: 0;
overflow-x: hidden;
overflow-y: auto;
position: relative;
height: 300px;
}
#upload .filelist:after {
content: '';
display: block;
width: 0;
height: 0;
overflow: hidden;
clear: both;
}
#upload .filelist li {
width: 113px;
height: 113px;
background: url(./images/bg.png);
text-align: center;
margin: 9px 0 0 9px;
*margin: 6px 0 0 6px;
position: relative;
display: block;
float: left;
overflow: hidden;
font-size: 12px;
}
#upload .filelist li p.log {
position: relative;
top: -45px;
}
#upload .filelist li p.title {
position: absolute;
top: 0;
left: 0;
width: 100%;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
top: 5px;
text-indent: 5px;
text-align: left;
}
#upload .filelist li p.progress {
position: absolute;
width: 100%;
bottom: 0;
left: 0;
height: 8px;
overflow: hidden;
z-index: 50;
margin: 0;
border-radius: 0;
background: none;
-webkit-box-shadow: 0 0 0;
}
#upload .filelist li p.progress span {
display: none;
overflow: hidden;
width: 0;
height: 100%;
background: #1483d8 url(./images/progress.png) repeat-x;
-webit-transition: width 200ms linear;
-moz-transition: width 200ms linear;
-o-transition: width 200ms linear;
-ms-transition: width 200ms linear;
transition: width 200ms linear;
-webkit-animation: progressmove 2s linear infinite;
-moz-animation: progressmove 2s linear infinite;
-o-animation: progressmove 2s linear infinite;
-ms-animation: progressmove 2s linear infinite;
animation: progressmove 2s linear infinite;
-webkit-transform: translateZ(0);
}
@-webkit-keyframes progressmove {
0% {
background-position: 0 0;
}
100% {
background-position: 17px 0;
}
}
@-moz-keyframes progressmove {
0% {
background-position: 0 0;
}
100% {
background-position: 17px 0;
}
}
@keyframes progressmove {
0% {
background-position: 0 0;
}
100% {
background-position: 17px 0;
}
}
#upload .filelist li p.imgWrap {
position: relative;
z-index: 2;
line-height: 113px;
vertical-align: middle;
overflow: hidden;
width: 113px;
height: 113px;
-webkit-transform-origin: 50% 50%;
-moz-transform-origin: 50% 50%;
-o-transform-origin: 50% 50%;
-ms-transform-origin: 50% 50%;
transform-origin: 50% 50%;
-webit-transition: 200ms ease-out;
-moz-transition: 200ms ease-out;
-o-transition: 200ms ease-out;
-ms-transition: 200ms ease-out;
transition: 200ms ease-out;
}
#upload .filelist li p.imgWrap.notimage {
margin-top: 0;
width: 111px;
height: 111px;
border: 1px #eeeeee solid;
}
#upload .filelist li p.imgWrap.notimage i.file-preview {
margin-top: 15px;
}
#upload .filelist li img {
width: 100%;
}
#upload .filelist li p.error {
background: #f43838;
color: #fff;
position: absolute;
bottom: 0;
left: 0;
height: 28px;
line-height: 28px;
width: 100%;
z-index: 100;
display:none;
}
#upload .filelist li .success {
display: block;
position: absolute;
left: 0;
bottom: 0;
height: 40px;
width: 100%;
z-index: 200;
background: url(./images/success.png) no-repeat right bottom;
background-image: url(./images/success.gif) \9;
}
#upload .filelist li.filePickerBlock {
width: 113px;
height: 113px;
background: url(./images/image.png) no-repeat center 12px;
border: 1px solid #eeeeee;
border-radius: 0;
}
#upload .filelist li.filePickerBlock div.webuploader-pick {
width: 100%;
height: 100%;
margin: 0;
padding: 0;
opacity: 0;
background: none;
font-size: 0;
}
#upload .filelist div.file-panel {
position: absolute;
height: 0;
filter: progid:DXImageTransform.Microsoft.gradient(GradientType=0, startColorstr='#80000000', endColorstr='#80000000') \0;
background: rgba(0, 0, 0, 0.5);
width: 100%;
top: 0;
left: 0;
overflow: hidden;
z-index: 300;
}
#upload .filelist div.file-panel span {
width: 24px;
height: 24px;
display: inline;
float: right;
text-indent: -9999px;
overflow: hidden;
background: url(./images/icons.png) no-repeat;
background: url(./images/icons.gif) no-repeat \9;
margin: 5px 1px 1px;
cursor: pointer;
-webkit-tap-highlight-color: rgba(0,0,0,0);
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}
#upload .filelist div.file-panel span.rotateLeft {
display:none;
background-position: 0 -24px;
}
#upload .filelist div.file-panel span.rotateLeft:hover {
background-position: 0 0;
}
#upload .filelist div.file-panel span.rotateRight {
display:none;
background-position: -24px -24px;
}
#upload .filelist div.file-panel span.rotateRight:hover {
background-position: -24px 0;
}
#upload .filelist div.file-panel span.cancel {
background-position: -48px -24px;
}
#upload .filelist div.file-panel span.cancel:hover {
background-position: -48px 0;
}
#upload .statusBar {
height: 45px;
border-bottom: 1px solid #dadada;
margin: 0 10px;
padding: 0;
line-height: 45px;
vertical-align: middle;
position: relative;
}
#upload .statusBar .progress {
border: 1px solid #1483d8;
width: 198px;
background: #fff;
height: 18px;
position: absolute;
top: 12px;
display: none;
text-align: center;
line-height: 18px;
color: #6dbfff;
margin: 0 10px 0 0;
}
#upload .statusBar .progress span.percentage {
width: 0;
height: 100%;
left: 0;
top: 0;
background: #1483d8;
position: absolute;
}
#upload .statusBar .progress span.text {
position: relative;
z-index: 10;
}
#upload .statusBar .info {
display: inline-block;
font-size: 14px;
color: #666666;
}
#upload .statusBar .btns {
position: absolute;
top: 7px;
right: 0;
line-height: 30px;
}
#filePickerBtn {
display: inline-block;
float: left;
}
#upload .statusBar .btns .webuploader-pick,
#upload .statusBar .btns .uploadBtn,
#upload .statusBar .btns .uploadBtn.state-uploading,
#upload .statusBar .btns .uploadBtn.state-paused {
background: #ffffff;
border: 1px solid #cfcfcf;
color: #565656;
padding: 0 18px;
display: inline-block;
border-radius: 3px;
margin-left: 10px;
cursor: pointer;
font-size: 14px;
float: left;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}
#upload .statusBar .btns .webuploader-pick-hover,
#upload .statusBar .btns .uploadBtn:hover,
#upload .statusBar .btns .uploadBtn.state-uploading:hover,
#upload .statusBar .btns .uploadBtn.state-paused:hover {
background: #f0f0f0;
}
#upload .statusBar .btns .uploadBtn,
#upload .statusBar .btns .uploadBtn.state-paused{
background: #00b7ee;
color: #fff;
border-color: transparent;
}
#upload .statusBar .btns .uploadBtn:hover,
#upload .statusBar .btns .uploadBtn.state-paused:hover{
background: #00a2d4;
}
#upload .statusBar .btns .uploadBtn.disabled {
pointer-events: none;
filter:alpha(opacity=60);
-moz-opacity:0.6;
-khtml-opacity: 0.6;
opacity: 0.6;
}
/* 图片管理样式 */
#online {
width: 100%;
height: 336px;
padding: 10px 0 0 0;
}
#online #fileList{
width: 100%;
height: 100%;
overflow-x: hidden;
overflow-y: auto;
position: relative;
}
#online ul {
display: block;
list-style: none;
margin: 0;
padding: 0;
}
#online li {
float: left;
display: block;
list-style: none;
padding: 0;
width: 113px;
height: 113px;
margin: 0 0 9px 9px;
*margin: 0 0 6px 6px;
background-color: #eee;
overflow: hidden;
cursor: pointer;
position: relative;
}
#online li.clearFloat {
float: none;
clear: both;
display: block;
width:0;
height:0;
margin: 0;
padding: 0;
}
#online li img {
cursor: pointer;
}
#online li div.file-wrapper {
cursor: pointer;
position: absolute;
display: block;
width: 111px;
height: 111px;
border: 1px solid #eee;
background: url("./images/bg.png") repeat;
}
#online li div span.file-title{
display: block;
padding: 0 3px;
margin: 3px 0 0 0;
font-size: 12px;
height: 13px;
color: #555555;
text-align: center;
width: 107px;
white-space: nowrap;
word-break: break-all;
overflow: hidden;
text-overflow: ellipsis;
}
#online li .icon {
cursor: pointer;
width: 113px;
height: 113px;
position: absolute;
top: 0;
left: 0;
z-index: 2;
border: 0;
background-repeat: no-repeat;
}
#online li .icon:hover {
width: 107px;
height: 107px;
border: 3px solid #1094fa;
}
#online li.selected .icon {
background-image: url(images/success.png);
background-image: url(images/success.gif) \9;
background-position: 75px 75px;
}
#online li.selected .icon:hover {
width: 107px;
height: 107px;
border: 3px solid #1094fa;
background-position: 72px 72px;
}
/* 在线文件的文件预览图标 */
i.file-preview {
display: block;
margin: 10px auto;
width: 70px;
height: 70px;
background-image: url("./images/file-icons.png");
background-image: url("./images/file-icons.gif") \9;
background-position: -140px center;
background-repeat: no-repeat;
}
i.file-preview.file-type-dir{
background-position: 0 center;
}
i.file-preview.file-type-file{
background-position: -140px center;
}
i.file-preview.file-type-filelist{
background-position: -210px center;
}
i.file-preview.file-type-zip,
i.file-preview.file-type-rar,
i.file-preview.file-type-7z,
i.file-preview.file-type-tar,
i.file-preview.file-type-gz,
i.file-preview.file-type-bz2{
background-position: -280px center;
}
i.file-preview.file-type-xls,
i.file-preview.file-type-xlsx{
background-position: -350px center;
}
i.file-preview.file-type-doc,
i.file-preview.file-type-docx{
background-position: -420px center;
}
i.file-preview.file-type-ppt,
i.file-preview.file-type-pptx{
background-position: -490px center;
}
i.file-preview.file-type-vsd{
background-position: -560px center;
}
i.file-preview.file-type-pdf{
background-position: -630px center;
}
i.file-preview.file-type-txt,
i.file-preview.file-type-md,
i.file-preview.file-type-json,
i.file-preview.file-type-htm,
i.file-preview.file-type-xml,
i.file-preview.file-type-html,
i.file-preview.file-type-js,
i.file-preview.file-type-css,
i.file-preview.file-type-php,
i.file-preview.file-type-jsp,
i.file-preview.file-type-asp{
background-position: -700px center;
}
i.file-preview.file-type-apk{
background-position: -770px center;
}
i.file-preview.file-type-exe{
background-position: -840px center;
}
i.file-preview.file-type-ipa{
background-position: -910px center;
}
i.file-preview.file-type-mp4,
i.file-preview.file-type-swf,
i.file-preview.file-type-mkv,
i.file-preview.file-type-avi,
i.file-preview.file-type-flv,
i.file-preview.file-type-mov,
i.file-preview.file-type-mpg,
i.file-preview.file-type-mpeg,
i.file-preview.file-type-ogv,
i.file-preview.file-type-webm,
i.file-preview.file-type-rm,
i.file-preview.file-type-rmvb{
background-position: -980px center;
}
i.file-preview.file-type-ogg,
i.file-preview.file-type-wav,
i.file-preview.file-type-wmv,
i.file-preview.file-type-mid,
i.file-preview.file-type-mp3{
background-position: -1050px center;
}
i.file-preview.file-type-jpg,
i.file-preview.file-type-jpeg,
i.file-preview.file-type-gif,
i.file-preview.file-type-bmp,
i.file-preview.file-type-png,
i.file-preview.file-type-psd{
background-position: -140px center;
}
@@ -0,0 +1,60 @@
<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>ueditor图片对话框</title>
<script type="text/javascript" src="../internal.js"></script>
<!-- jquery -->
<script type="text/javascript" src="../../third-party/jquery-1.10.2.min.js"></script>
<!-- webuploader -->
<script src="../../third-party/webuploader/webuploader.min.js"></script>
<link rel="stylesheet" type="text/css" href="../../third-party/webuploader/webuploader.css">
<!-- attachment dialog -->
<link rel="stylesheet" href="attachment.css" type="text/css" />
</head>
<body>
<div class="wrapper">
<div id="tabhead" class="tabhead">
<span class="tab focus" data-content-id="upload"><var id="lang_tab_upload"></var></span>
<span class="tab" data-content-id="online"><var id="lang_tab_online"></var></span>
</div>
<div id="tabbody" class="tabbody">
<!-- 上传图片 -->
<div id="upload" class="panel focus">
<div id="queueList" class="queueList">
<div class="statusBar element-invisible">
<div class="progress">
<span class="text">0%</span>
<span class="percentage"></span>
</div><div class="info"></div>
<div class="btns">
<div id="filePickerBtn"></div>
<div class="uploadBtn"><var id="lang_start_upload"></var></div>
</div>
</div>
<div id="dndArea" class="placeholder">
<div class="filePickerContainer">
<div id="filePickerReady"></div>
</div>
</div>
<ul class="filelist element-invisible">
<li id="filePickerBlock" class="filePickerBlock"></li>
</ul>
</div>
</div>
<!-- 在线图片 -->
<div id="online" class="panel">
<div id="fileList"><var id="lang_imgLoading"></var></div>
</div>
</div>
</div>
<script type="text/javascript" src="attachment.js"></script>
</body>
</html>
@@ -0,0 +1,760 @@
/**
* User: Jinqn
* Date: 14-04-08
* Time: 下午16:34
* 上传图片对话框逻辑代码,包括tab: 远程图片/上传图片/在线图片/搜索图片
*/
(function () {
var uploadFile,
onlineFile;
window.onload = function () {
initTabs();
initButtons();
};
/* 初始化tab标签 */
function initTabs() {
var tabs = $G('tabhead').children;
for (var i = 0; i < tabs.length; i++) {
domUtils.on(tabs[i], "click", function (e) {
var target = e.target || e.srcElement;
setTabFocus(target.getAttribute('data-content-id'));
});
}
setTabFocus('upload');
}
/* 初始化tabbody */
function setTabFocus(id) {
if(!id) return;
var i, bodyId, tabs = $G('tabhead').children;
for (i = 0; i < tabs.length; i++) {
bodyId = tabs[i].getAttribute('data-content-id')
if (bodyId == id) {
domUtils.addClass(tabs[i], 'focus');
domUtils.addClass($G(bodyId), 'focus');
} else {
domUtils.removeClasses(tabs[i], 'focus');
domUtils.removeClasses($G(bodyId), 'focus');
}
}
switch (id) {
case 'upload':
uploadFile = uploadFile || new UploadFile('queueList');
break;
case 'online':
onlineFile = onlineFile || new OnlineFile('fileList');
break;
}
}
/* 初始化onok事件 */
function initButtons() {
dialog.onok = function () {
var list = [], id, tabs = $G('tabhead').children;
for (var i = 0; i < tabs.length; i++) {
if (domUtils.hasClass(tabs[i], 'focus')) {
id = tabs[i].getAttribute('data-content-id');
break;
}
}
switch (id) {
case 'upload':
list = uploadFile.getInsertList();
var count = uploadFile.getQueueCount();
if (count) {
$('.info', '#queueList').html('<span style="color:red;">' + '还有2个未上传文件'.replace(/[\d]/, count) + '</span>');
return false;
}
break;
case 'online':
list = onlineFile.getInsertList();
break;
}
editor.execCommand('insertfile', list);
};
}
/* 上传附件 */
function UploadFile(target) {
this.$wrap = target.constructor == String ? $('#' + target) : $(target);
this.init();
}
UploadFile.prototype = {
init: function () {
this.fileList = [];
this.initContainer();
this.initUploader();
},
initContainer: function () {
this.$queue = this.$wrap.find('.filelist');
},
/* 初始化容器 */
initUploader: function () {
var _this = this,
$ = jQuery, // just in case. Make sure it's not an other libaray.
$wrap = _this.$wrap,
// 图片容器
$queue = $wrap.find('.filelist'),
// 状态栏,包括进度和控制按钮
$statusBar = $wrap.find('.statusBar'),
// 文件总体选择信息。
$info = $statusBar.find('.info'),
// 上传按钮
$upload = $wrap.find('.uploadBtn'),
// 上传按钮
$filePickerBtn = $wrap.find('.filePickerBtn'),
// 上传按钮
$filePickerBlock = $wrap.find('.filePickerBlock'),
// 没选择文件之前的内容。
$placeHolder = $wrap.find('.placeholder'),
// 总体进度条
$progress = $statusBar.find('.progress').hide(),
// 添加的文件数量
fileCount = 0,
// 添加的文件总大小
fileSize = 0,
// 优化retina, 在retina下这个值是2
ratio = window.devicePixelRatio || 1,
// 缩略图大小
thumbnailWidth = 113 * ratio,
thumbnailHeight = 113 * ratio,
// 可能有pedding, ready, uploading, confirm, done.
state = '',
// 所有文件的进度信息,key为file id
percentages = {},
supportTransition = (function () {
var s = document.createElement('p').style,
r = 'transition' in s ||
'WebkitTransition' in s ||
'MozTransition' in s ||
'msTransition' in s ||
'OTransition' in s;
s = null;
return r;
})(),
// WebUploader实例
uploader,
actionUrl = editor.getActionUrl(editor.getOpt('fileActionName')),
fileMaxSize = editor.getOpt('fileMaxSize'),
acceptExtensions = (editor.getOpt('fileAllowFiles') || []).join('').replace(/\./g, ',').replace(/^[,]/, '');;
if (!WebUploader.Uploader.support()) {
$('#filePickerReady').after($('<div>').html(lang.errorNotSupport)).hide();
return;
} else if (!editor.getOpt('fileActionName')) {
$('#filePickerReady').after($('<div>').html(lang.errorLoadConfig)).hide();
return;
}
uploader = _this.uploader = WebUploader.create({
pick: {
id: '#filePickerReady',
label: lang.uploadSelectFile
},
swf: '../../third-party/webuploader/Uploader.swf',
server: actionUrl,
fileVal: editor.getOpt('fileFieldName'),
duplicate: true,
fileSingleSizeLimit: fileMaxSize,
compress: false
});
uploader.addButton({
id: '#filePickerBlock'
});
uploader.addButton({
id: '#filePickerBtn',
label: lang.uploadAddFile
});
setState('pedding');
// 当有文件添加进来时执行,负责view的创建
function addFile(file) {
var $li = $('<li id="' + file.id + '">' +
'<p class="title">' + file.name + '</p>' +
'<p class="imgWrap"></p>' +
'<p class="progress"><span></span></p>' +
'</li>'),
$btns = $('<div class="file-panel">' +
'<span class="cancel">' + lang.uploadDelete + '</span>' +
'<span class="rotateRight">' + lang.uploadTurnRight + '</span>' +
'<span class="rotateLeft">' + lang.uploadTurnLeft + '</span></div>').appendTo($li),
$prgress = $li.find('p.progress span'),
$wrap = $li.find('p.imgWrap'),
$info = $('<p class="error"></p>').hide().appendTo($li),
showError = function (code) {
switch (code) {
case 'exceed_size':
text = lang.errorExceedSize;
break;
case 'interrupt':
text = lang.errorInterrupt;
break;
case 'http':
text = lang.errorHttp;
break;
case 'not_allow_type':
text = lang.errorFileType;
break;
default:
text = lang.errorUploadRetry;
break;
}
$info.text(text).show();
};
if (file.getStatus() === 'invalid') {
showError(file.statusText);
} else {
$wrap.text(lang.uploadPreview);
if ('|png|jpg|jpeg|bmp|gif|'.indexOf('|'+file.ext.toLowerCase()+'|') == -1) {
$wrap.empty().addClass('notimage').append('<i class="file-preview file-type-' + file.ext.toLowerCase() + '"></i>' +
'<span class="file-title" title="' + file.name + '">' + file.name + '</span>');
} else {
if (browser.ie && browser.version <= 7) {
$wrap.text(lang.uploadNoPreview);
} else {
uploader.makeThumb(file, function (error, src) {
if (error || !src) {
$wrap.text(lang.uploadNoPreview);
} else {
var $img = $('<img src="' + src + '">');
$wrap.empty().append($img);
$img.on('error', function () {
$wrap.text(lang.uploadNoPreview);
});
}
}, thumbnailWidth, thumbnailHeight);
}
}
percentages[ file.id ] = [ file.size, 0 ];
file.rotation = 0;
/* 检查文件格式 */
if (!file.ext || acceptExtensions.indexOf(file.ext.toLowerCase()) == -1) {
showError('not_allow_type');
uploader.removeFile(file);
}
}
file.on('statuschange', function (cur, prev) {
if (prev === 'progress') {
$prgress.hide().width(0);
} else if (prev === 'queued') {
$li.off('mouseenter mouseleave');
$btns.remove();
}
// 成功
if (cur === 'error' || cur === 'invalid') {
showError(file.statusText);
percentages[ file.id ][ 1 ] = 1;
} else if (cur === 'interrupt') {
showError('interrupt');
} else if (cur === 'queued') {
percentages[ file.id ][ 1 ] = 0;
} else if (cur === 'progress') {
$info.hide();
$prgress.css('display', 'block');
} else if (cur === 'complete') {
}
$li.removeClass('state-' + prev).addClass('state-' + cur);
});
$li.on('mouseenter', function () {
$btns.stop().animate({height: 30});
});
$li.on('mouseleave', function () {
$btns.stop().animate({height: 0});
});
$btns.on('click', 'span', function () {
var index = $(this).index(),
deg;
switch (index) {
case 0:
uploader.removeFile(file);
return;
case 1:
file.rotation += 90;
break;
case 2:
file.rotation -= 90;
break;
}
if (supportTransition) {
deg = 'rotate(' + file.rotation + 'deg)';
$wrap.css({
'-webkit-transform': deg,
'-mos-transform': deg,
'-o-transform': deg,
'transform': deg
});
} else {
$wrap.css('filter', 'progid:DXImageTransform.Microsoft.BasicImage(rotation=' + (~~((file.rotation / 90) % 4 + 4) % 4) + ')');
}
});
$li.insertBefore($filePickerBlock);
}
// 负责view的销毁
function removeFile(file) {
var $li = $('#' + file.id);
delete percentages[ file.id ];
updateTotalProgress();
$li.off().find('.file-panel').off().end().remove();
}
function updateTotalProgress() {
var loaded = 0,
total = 0,
spans = $progress.children(),
percent;
$.each(percentages, function (k, v) {
total += v[ 0 ];
loaded += v[ 0 ] * v[ 1 ];
});
percent = total ? loaded / total : 0;
spans.eq(0).text(Math.round(percent * 100) + '%');
spans.eq(1).css('width', Math.round(percent * 100) + '%');
updateStatus();
}
function setState(val, files) {
if (val != state) {
var stats = uploader.getStats();
$upload.removeClass('state-' + state);
$upload.addClass('state-' + val);
switch (val) {
/* 未选择文件 */
case 'pedding':
$queue.addClass('element-invisible');
$statusBar.addClass('element-invisible');
$placeHolder.removeClass('element-invisible');
$progress.hide(); $info.hide();
uploader.refresh();
break;
/* 可以开始上传 */
case 'ready':
$placeHolder.addClass('element-invisible');
$queue.removeClass('element-invisible');
$statusBar.removeClass('element-invisible');
$progress.hide(); $info.show();
$upload.text(lang.uploadStart);
uploader.refresh();
break;
/* 上传中 */
case 'uploading':
$progress.show(); $info.hide();
$upload.text(lang.uploadPause);
break;
/* 暂停上传 */
case 'paused':
$progress.show(); $info.hide();
$upload.text(lang.uploadContinue);
break;
case 'confirm':
$progress.show(); $info.hide();
$upload.text(lang.uploadStart);
stats = uploader.getStats();
if (stats.successNum && !stats.uploadFailNum) {
setState('finish');
return;
}
break;
case 'finish':
$progress.hide(); $info.show();
if (stats.uploadFailNum) {
$upload.text(lang.uploadRetry);
} else {
$upload.text(lang.uploadStart);
}
break;
}
state = val;
updateStatus();
}
if (!_this.getQueueCount()) {
$upload.addClass('disabled')
} else {
$upload.removeClass('disabled')
}
}
function updateStatus() {
var text = '', stats;
if (state === 'ready') {
text = lang.updateStatusReady.replace('_', fileCount).replace('_KB', WebUploader.formatSize(fileSize));
} else if (state === 'confirm') {
stats = uploader.getStats();
if (stats.uploadFailNum) {
text = lang.updateStatusConfirm.replace('_', stats.successNum).replace('_', stats.successNum);
}
} else {
stats = uploader.getStats();
text = lang.updateStatusFinish.replace('_', fileCount).
replace('_KB', WebUploader.formatSize(fileSize)).
replace('_', stats.successNum);
if (stats.uploadFailNum) {
text += lang.updateStatusError.replace('_', stats.uploadFailNum);
}
}
$info.html(text);
}
uploader.on('fileQueued', function (file) {
fileCount++;
fileSize += file.size;
if (fileCount === 1) {
$placeHolder.addClass('element-invisible');
$statusBar.show();
}
addFile(file);
});
uploader.on('fileDequeued', function (file) {
fileCount--;
fileSize -= file.size;
removeFile(file);
updateTotalProgress();
});
uploader.on('filesQueued', function (file) {
if (!uploader.isInProgress() && (state == 'pedding' || state == 'finish' || state == 'confirm' || state == 'ready')) {
setState('ready');
}
updateTotalProgress();
});
uploader.on('all', function (type, files) {
switch (type) {
case 'uploadFinished':
setState('confirm', files);
break;
case 'startUpload':
/* 添加额外的GET参数 */
var params = utils.serializeParam(editor.queryCommandValue('serverparam')) || '',
url = utils.formatUrl(actionUrl + (actionUrl.indexOf('?') == -1 ? '?':'&') + 'encode=utf-8&' + params);
uploader.option('server', url);
setState('uploading', files);
break;
case 'stopUpload':
setState('paused', files);
break;
}
});
uploader.on('uploadBeforeSend', function (file, data, header) {
//这里可以通过data对象添加POST参数
header['X_Requested_With'] = 'XMLHttpRequest';
// HaoChuan9421
if(editor.options.headers && Object.prototype.toString.apply(editor.options.headers) === "[object Object]"){
for(var key in editor.options.headers){
header[key] = editor.options.headers[key]
}
}
});
uploader.on('uploadProgress', function (file, percentage) {
var $li = $('#' + file.id),
$percent = $li.find('.progress span');
$percent.css('width', percentage * 100 + '%');
percentages[ file.id ][ 1 ] = percentage;
updateTotalProgress();
});
uploader.on('uploadSuccess', function (file, ret) {
var $file = $('#' + file.id);
try {
var responseText = (ret._raw || ret),
json = utils.str2json(responseText);
if (json.state == 'SUCCESS') {
_this.fileList.push(json);
$file.append('<span class="success"></span>');
} else {
$file.find('.error').text(json.state).show();
}
} catch (e) {
$file.find('.error').text(lang.errorServerUpload).show();
}
});
uploader.on('uploadError', function (file, code) {
});
uploader.on('error', function (code, file) {
if (code == 'Q_TYPE_DENIED' || code == 'F_EXCEED_SIZE') {
addFile(file);
}
});
uploader.on('uploadComplete', function (file, ret) {
});
$upload.on('click', function () {
if ($(this).hasClass('disabled')) {
return false;
}
if (state === 'ready') {
uploader.upload();
} else if (state === 'paused') {
uploader.upload();
} else if (state === 'uploading') {
uploader.stop();
}
});
$upload.addClass('state-' + state);
updateTotalProgress();
},
getQueueCount: function () {
var file, i, status, readyFile = 0, files = this.uploader.getFiles();
for (i = 0; file = files[i++]; ) {
status = file.getStatus();
if (status == 'queued' || status == 'uploading' || status == 'progress') readyFile++;
}
return readyFile;
},
getInsertList: function () {
var i, link, data, list = [],
prefix = editor.getOpt('fileUrlPrefix');
for (i = 0; i < this.fileList.length; i++) {
data = this.fileList[i];
link = data.url;
list.push({
title: data.original || link.substr(link.lastIndexOf('/') + 1),
url: prefix + link
});
}
return list;
}
};
/* 在线附件 */
function OnlineFile(target) {
this.container = utils.isString(target) ? document.getElementById(target) : target;
this.init();
}
OnlineFile.prototype = {
init: function () {
this.initContainer();
this.initEvents();
this.initData();
},
/* 初始化容器 */
initContainer: function () {
this.container.innerHTML = '';
this.list = document.createElement('ul');
this.clearFloat = document.createElement('li');
domUtils.addClass(this.list, 'list');
domUtils.addClass(this.clearFloat, 'clearFloat');
this.list.appendChild(this.clearFloat);
this.container.appendChild(this.list);
},
/* 初始化滚动事件,滚动到地步自动拉取数据 */
initEvents: function () {
var _this = this;
/* 滚动拉取图片 */
domUtils.on($G('fileList'), 'scroll', function(e){
var panel = this;
if (panel.scrollHeight - (panel.offsetHeight + panel.scrollTop) < 10) {
_this.getFileData();
}
});
/* 选中图片 */
domUtils.on(this.list, 'click', function (e) {
var target = e.target || e.srcElement,
li = target.parentNode;
if (li.tagName.toLowerCase() == 'li') {
if (domUtils.hasClass(li, 'selected')) {
domUtils.removeClasses(li, 'selected');
} else {
domUtils.addClass(li, 'selected');
}
}
});
},
/* 初始化第一次的数据 */
initData: function () {
/* 拉取数据需要使用的值 */
this.state = 0;
this.listSize = editor.getOpt('fileManagerListSize');
this.listIndex = 0;
this.listEnd = false;
/* 第一次拉取数据 */
this.getFileData();
},
/* 向后台拉取图片列表数据 */
getFileData: function () {
var _this = this;
if(!_this.listEnd && !this.isLoadingData) {
this.isLoadingData = true;
ajax.request(editor.getActionUrl(editor.getOpt('fileManagerActionName')), {
timeout: 100000,
data: utils.extend({
start: this.listIndex,
size: this.listSize
}, editor.queryCommandValue('serverparam')),
method: 'get',
onsuccess: function (r) {
try {
var json = eval('(' + r.responseText + ')');
if (json.state == 'SUCCESS') {
_this.pushData(json.list);
_this.listIndex = parseInt(json.start) + parseInt(json.list.length);
if(_this.listIndex >= json.total) {
_this.listEnd = true;
}
_this.isLoadingData = false;
}
} catch (e) {
if(r.responseText.indexOf('ue_separate_ue') != -1) {
var list = r.responseText.split(r.responseText);
_this.pushData(list);
_this.listIndex = parseInt(list.length);
_this.listEnd = true;
_this.isLoadingData = false;
}
}
},
onerror: function () {
_this.isLoadingData = false;
}
});
}
},
/* 添加图片到列表界面上 */
pushData: function (list) {
var i, item, img, filetype, preview, icon, _this = this,
urlPrefix = editor.getOpt('fileManagerUrlPrefix');
for (i = 0; i < list.length; i++) {
if(list[i] && list[i].url) {
item = document.createElement('li');
icon = document.createElement('span');
filetype = list[i].url.substr(list[i].url.lastIndexOf('.') + 1);
if ( "png|jpg|jpeg|gif|bmp".indexOf(filetype) != -1 ) {
preview = document.createElement('img');
domUtils.on(preview, 'load', (function(image){
return function(){
_this.scale(image, image.parentNode.offsetWidth, image.parentNode.offsetHeight);
};
})(preview));
preview.width = 113;
preview.setAttribute('src', urlPrefix + list[i].url + (list[i].url.indexOf('?') == -1 ? '?noCache=':'&noCache=') + (+new Date()).toString(36) );
} else {
var ic = document.createElement('i'),
textSpan = document.createElement('span');
textSpan.innerHTML = list[i].url.substr(list[i].url.lastIndexOf('/') + 1);
preview = document.createElement('div');
preview.appendChild(ic);
preview.appendChild(textSpan);
domUtils.addClass(preview, 'file-wrapper');
domUtils.addClass(textSpan, 'file-title');
domUtils.addClass(ic, 'file-type-' + filetype);
domUtils.addClass(ic, 'file-preview');
}
domUtils.addClass(icon, 'icon');
item.setAttribute('data-url', urlPrefix + list[i].url);
if (list[i].original) {
item.setAttribute('data-title', list[i].original);
}
item.appendChild(preview);
item.appendChild(icon);
this.list.insertBefore(item, this.clearFloat);
}
}
},
/* 改变图片大小 */
scale: function (img, w, h, type) {
var ow = img.width,
oh = img.height;
if (type == 'justify') {
if (ow >= oh) {
img.width = w;
img.height = h * oh / ow;
img.style.marginLeft = '-' + parseInt((img.width - w) / 2) + 'px';
} else {
img.width = w * ow / oh;
img.height = h;
img.style.marginTop = '-' + parseInt((img.height - h) / 2) + 'px';
}
} else {
if (ow >= oh) {
img.width = w * ow / oh;
img.height = h;
img.style.marginLeft = '-' + parseInt((img.width - w) / 2) + 'px';
} else {
img.width = w;
img.height = h * oh / ow;
img.style.marginTop = '-' + parseInt((img.height - h) / 2) + 'px';
}
}
},
getInsertList: function () {
var i, lis = this.list.children, list = [];
for (i = 0; i < lis.length; i++) {
if (domUtils.hasClass(lis[i], 'selected')) {
var url = lis[i].getAttribute('data-url');
var title = lis[i].getAttribute('data-title') || url.substr(url.lastIndexOf('/') + 1);
list.push({
title: title,
url: url
});
}
}
return list;
}
};
})();
Binary file not shown.

After

Width:  |  Height:  |  Size: 923 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 841 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1012 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 949 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 950 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 986 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1001 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 996 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1001 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1009 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1007 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 970 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1005 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 20 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 43 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 453 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 445 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

@@ -0,0 +1,94 @@
.wrapper{ width: 424px;margin: 10px auto; zoom:1;position: relative}
.tabbody{height:225px;}
.tabbody .panel { position: absolute;width:100%; height:100%;background: #fff; display: none;}
.tabbody .focus { display: block;}
body{font-size: 12px;color: #888;overflow: hidden;}
input,label{vertical-align:middle}
.clear{clear: both;}
.pl{padding-left: 18px;padding-left: 23px\9;}
#imageList {width: 420px;height: 215px;margin-top: 10px;overflow: hidden;overflow-y: auto;}
#imageList div {float: left;width: 100px;height: 95px;margin: 5px 10px;}
#imageList img {cursor: pointer;border: 2px solid white;}
.bgarea{margin: 10px;padding: 5px;height: 84%;border: 1px solid #A8A297;}
.content div{margin: 10px 0 10px 5px;}
.content .iptradio{margin: 0px 5px 5px 0px;}
.txt{width:280px;}
.wrapcolor{height: 19px;}
div.color{float: left;margin: 0;}
#colorPicker{width: 17px;height: 17px;border: 1px solid #CCC;display: inline-block;border-radius: 3px;box-shadow: 2px 2px 5px #D3D6DA;margin: 0;float: left;}
div.alignment,#custom{margin-left: 23px;margin-left: 28px\9;}
#custom input{height: 15px;min-height: 15px;width:20px;}
#repeatType{width:100px;}
/* 图片管理样式 */
#imgManager {
width: 100%;
height: 225px;
}
#imgManager #imageList{
width: 100%;
overflow-x: hidden;
overflow-y: auto;
}
#imgManager ul {
display: block;
list-style: none;
margin: 0;
padding: 0;
}
#imgManager li {
float: left;
display: block;
list-style: none;
padding: 0;
width: 113px;
height: 113px;
margin: 9px 0 0 19px;
background-color: #eee;
overflow: hidden;
cursor: pointer;
position: relative;
}
#imgManager li.clearFloat {
float: none;
clear: both;
display: block;
width:0;
height:0;
margin: 0;
padding: 0;
}
#imgManager li img {
cursor: pointer;
}
#imgManager li .icon {
cursor: pointer;
width: 113px;
height: 113px;
position: absolute;
top: 0;
left: 0;
z-index: 2;
border: 0;
background-repeat: no-repeat;
}
#imgManager li .icon:hover {
width: 107px;
height: 107px;
border: 3px solid #1094fa;
}
#imgManager li.selected .icon {
background-image: url(images/success.png);
background-position: 75px 75px;
}
#imgManager li.selected .icon:hover {
width: 107px;
height: 107px;
border: 3px solid #1094fa;
background-position: 72px 72px;
}
@@ -0,0 +1,56 @@
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=utf-8"/>
<script type="text/javascript" src="../internal.js"></script>
<link rel="stylesheet" type="text/css" href="background.css">
</head>
<body>
<div id="bg_container" class="wrapper">
<div id="tabHeads" class="tabhead">
<span class="focus" data-content-id="normal"><var id="lang_background_normal"></var></span>
<span class="" data-content-id="imgManager"><var id="lang_background_local"></var></span>
</div>
<div id="tabBodys" class="tabbody">
<div id="normal" class="panel focus">
<fieldset class="bgarea">
<legend><var id="lang_background_set"></var></legend>
<div class="content">
<div>
<label><input id="nocolorRadio" class="iptradio" type="radio" name="t" value="none" checked="checked"><var id="lang_background_none"></var></label>
<label><input id="coloredRadio" class="iptradio" type="radio" name="t" value="color"><var id="lang_background_colored"></var></label>
</div>
<div class="wrapcolor pl">
<div class="color">
<var id="lang_background_color"></var>:
</div>
<div id="colorPicker"></div>
<div class="clear"></div>
</div>
<div class="wrapcolor pl">
<label><var id="lang_background_netimg"></var>:</label><input class="txt" type="text" id="url">
</div>
<div id="alignment" class="alignment">
<var id="lang_background_align"></var>:<select id="repeatType">
<option value="center"></option>
<option value="repeat-x"></option>
<option value="repeat-y"></option>
<option value="repeat"></option>
<option value="self"></option>
</select>
</div>
<div id="custom" >
<var id="lang_background_position"></var>:x:<input type="text" size="1" id="x" maxlength="4" value="0">px&nbsp;&nbsp;y:<input type="text" size="1" id="y" maxlength="4" value="0">px
</div>
</div>
</fieldset>
</div>
<div id="imgManager" class="panel">
<div id="imageList" style=""></div>
</div>
</div>
</div>
<script type="text/javascript" src="background.js"></script>
</body>
</html>
@@ -0,0 +1,376 @@
(function () {
var onlineImage,
backupStyle = editor.queryCommandValue('background');
window.onload = function () {
initTabs();
initColorSelector();
};
/* 初始化tab标签 */
function initTabs(){
var tabs = $G('tabHeads').children;
for (var i = 0; i < tabs.length; i++) {
domUtils.on(tabs[i], "click", function (e) {
var target = e.target || e.srcElement;
for (var j = 0; j < tabs.length; j++) {
if(tabs[j] == target){
tabs[j].className = "focus";
var contentId = tabs[j].getAttribute('data-content-id');
$G(contentId).style.display = "block";
if(contentId == 'imgManager') {
initImagePanel();
}
}else {
tabs[j].className = "";
$G(tabs[j].getAttribute('data-content-id')).style.display = "none";
}
}
});
}
}
/* 初始化颜色设置 */
function initColorSelector () {
var obj = editor.queryCommandValue('background');
if (obj) {
var color = obj['background-color'],
repeat = obj['background-repeat'] || 'repeat',
image = obj['background-image'] || '',
position = obj['background-position'] || 'center center',
pos = position.split(' '),
x = parseInt(pos[0]) || 0,
y = parseInt(pos[1]) || 0;
if(repeat == 'no-repeat' && (x || y)) repeat = 'self';
image = image.match(/url[\s]*\(([^\)]*)\)/);
image = image ? image[1]:'';
updateFormState('colored', color, image, repeat, x, y);
} else {
updateFormState();
}
var updateHandler = function () {
updateFormState();
updateBackground();
}
domUtils.on($G('nocolorRadio'), 'click', updateBackground);
domUtils.on($G('coloredRadio'), 'click', updateHandler);
domUtils.on($G('url'), 'keyup', function(){
if($G('url').value && $G('alignment').style.display == "none") {
utils.each($G('repeatType').children, function(item){
item.selected = ('repeat' == item.getAttribute('value') ? 'selected':false);
});
}
updateHandler();
});
domUtils.on($G('repeatType'), 'change', updateHandler);
domUtils.on($G('x'), 'keyup', updateBackground);
domUtils.on($G('y'), 'keyup', updateBackground);
initColorPicker();
}
/* 初始化颜色选择器 */
function initColorPicker() {
var me = editor,
cp = $G("colorPicker");
/* 生成颜色选择器ui对象 */
var popup = new UE.ui.Popup({
content: new UE.ui.ColorPicker({
noColorText: me.getLang("clearColor"),
editor: me,
onpickcolor: function (t, color) {
updateFormState('colored', color);
updateBackground();
UE.ui.Popup.postHide();
},
onpicknocolor: function (t, color) {
updateFormState('colored', 'transparent');
updateBackground();
UE.ui.Popup.postHide();
}
}),
editor: me,
onhide: function () {
}
});
/* 设置颜色选择器 */
domUtils.on(cp, "click", function () {
popup.showAnchor(this);
});
domUtils.on(document, 'mousedown', function (evt) {
var el = evt.target || evt.srcElement;
UE.ui.Popup.postHide(el);
});
domUtils.on(window, 'scroll', function () {
UE.ui.Popup.postHide();
});
}
/* 初始化在线图片列表 */
function initImagePanel() {
onlineImage = onlineImage || new OnlineImage('imageList');
}
/* 更新背景色设置面板 */
function updateFormState (radio, color, url, align, x, y) {
var nocolorRadio = $G('nocolorRadio'),
coloredRadio = $G('coloredRadio');
if(radio) {
nocolorRadio.checked = (radio == 'colored' ? false:'checked');
coloredRadio.checked = (radio == 'colored' ? 'checked':false);
}
if(color) {
domUtils.setStyle($G("colorPicker"), "background-color", color);
}
if(url && /^\//.test(url)) {
var a = document.createElement('a');
a.href = url;
browser.ie && (a.href = a.href);
url = browser.ie ? a.href:(a.protocol + '//' + a.host + a.pathname + a.search + a.hash);
}
if(url || url === '') {
$G('url').value = url;
}
if(align) {
utils.each($G('repeatType').children, function(item){
item.selected = (align == item.getAttribute('value') ? 'selected':false);
});
}
if(x || y) {
$G('x').value = parseInt(x) || 0;
$G('y').value = parseInt(y) || 0;
}
$G('alignment').style.display = coloredRadio.checked && $G('url').value ? '':'none';
$G('custom').style.display = coloredRadio.checked && $G('url').value && $G('repeatType').value == 'self' ? '':'none';
}
/* 更新背景颜色 */
function updateBackground () {
if ($G('coloredRadio').checked) {
var color = domUtils.getStyle($G("colorPicker"), "background-color"),
bgimg = $G("url").value,
align = $G("repeatType").value,
backgroundObj = {
"background-repeat": "no-repeat",
"background-position": "center center"
};
if (color) backgroundObj["background-color"] = color;
if (bgimg) backgroundObj["background-image"] = 'url(' + bgimg + ')';
if (align == 'self') {
backgroundObj["background-position"] = $G("x").value + "px " + $G("y").value + "px";
} else if (align == 'repeat-x' || align == 'repeat-y' || align == 'repeat') {
backgroundObj["background-repeat"] = align;
}
editor.execCommand('background', backgroundObj);
} else {
editor.execCommand('background', null);
}
}
/* 在线图片 */
function OnlineImage(target) {
this.container = utils.isString(target) ? document.getElementById(target) : target;
this.init();
}
OnlineImage.prototype = {
init: function () {
this.reset();
this.initEvents();
},
/* 初始化容器 */
initContainer: function () {
this.container.innerHTML = '';
this.list = document.createElement('ul');
this.clearFloat = document.createElement('li');
domUtils.addClass(this.list, 'list');
domUtils.addClass(this.clearFloat, 'clearFloat');
this.list.id = 'imageListUl';
this.list.appendChild(this.clearFloat);
this.container.appendChild(this.list);
},
/* 初始化滚动事件,滚动到地步自动拉取数据 */
initEvents: function () {
var _this = this;
/* 滚动拉取图片 */
domUtils.on($G('imageList'), 'scroll', function(e){
var panel = this;
if (panel.scrollHeight - (panel.offsetHeight + panel.scrollTop) < 10) {
_this.getImageData();
}
});
/* 选中图片 */
domUtils.on(this.container, 'click', function (e) {
var target = e.target || e.srcElement,
li = target.parentNode,
nodes = $G('imageListUl').childNodes;
if (li.tagName.toLowerCase() == 'li') {
updateFormState('nocolor', null, '');
for (var i = 0, node; node = nodes[i++];) {
if (node == li && !domUtils.hasClass(node, 'selected')) {
domUtils.addClass(node, 'selected');
updateFormState('colored', null, li.firstChild.getAttribute("_src"), 'repeat');
} else {
domUtils.removeClasses(node, 'selected');
}
}
updateBackground();
}
});
},
/* 初始化第一次的数据 */
initData: function () {
/* 拉取数据需要使用的值 */
this.state = 0;
this.listSize = editor.getOpt('imageManagerListSize');
this.listIndex = 0;
this.listEnd = false;
/* 第一次拉取数据 */
this.getImageData();
},
/* 重置界面 */
reset: function() {
this.initContainer();
this.initData();
},
/* 向后台拉取图片列表数据 */
getImageData: function () {
var _this = this;
if(!_this.listEnd && !this.isLoadingData) {
this.isLoadingData = true;
var url = editor.getActionUrl(editor.getOpt('imageManagerActionName')),
isJsonp = utils.isCrossDomainUrl(url);
ajax.request(url, {
'timeout': 100000,
'dataType': isJsonp ? 'jsonp':'',
'data': utils.extend({
start: this.listIndex,
size: this.listSize
}, editor.queryCommandValue('serverparam')),
'method': 'get',
'onsuccess': function (r) {
try {
var json = isJsonp ? r:eval('(' + r.responseText + ')');
if (json.state == 'SUCCESS') {
_this.pushData(json.list);
_this.listIndex = parseInt(json.start) + parseInt(json.list.length);
if(_this.listIndex >= json.total) {
_this.listEnd = true;
}
_this.isLoadingData = false;
}
} catch (e) {
if(r.responseText.indexOf('ue_separate_ue') != -1) {
var list = r.responseText.split(r.responseText);
_this.pushData(list);
_this.listIndex = parseInt(list.length);
_this.listEnd = true;
_this.isLoadingData = false;
}
}
},
'onerror': function () {
_this.isLoadingData = false;
}
});
}
},
/* 添加图片到列表界面上 */
pushData: function (list) {
var i, item, img, icon, _this = this,
urlPrefix = editor.getOpt('imageManagerUrlPrefix');
for (i = 0; i < list.length; i++) {
if(list[i] && list[i].url) {
item = document.createElement('li');
img = document.createElement('img');
icon = document.createElement('span');
domUtils.on(img, 'load', (function(image){
return function(){
_this.scale(image, image.parentNode.offsetWidth, image.parentNode.offsetHeight);
}
})(img));
img.width = 113;
img.setAttribute('src', urlPrefix + list[i].url + (list[i].url.indexOf('?') == -1 ? '?noCache=':'&noCache=') + (+new Date()).toString(36) );
img.setAttribute('_src', urlPrefix + list[i].url);
domUtils.addClass(icon, 'icon');
item.appendChild(img);
item.appendChild(icon);
this.list.insertBefore(item, this.clearFloat);
}
}
},
/* 改变图片大小 */
scale: function (img, w, h, type) {
var ow = img.width,
oh = img.height;
if (type == 'justify') {
if (ow >= oh) {
img.width = w;
img.height = h * oh / ow;
img.style.marginLeft = '-' + parseInt((img.width - w) / 2) + 'px';
} else {
img.width = w * ow / oh;
img.height = h;
img.style.marginTop = '-' + parseInt((img.height - h) / 2) + 'px';
}
} else {
if (ow >= oh) {
img.width = w * ow / oh;
img.height = h;
img.style.marginLeft = '-' + parseInt((img.width - w) / 2) + 'px';
} else {
img.width = w;
img.height = h * oh / ow;
img.style.marginTop = '-' + parseInt((img.height - h) / 2) + 'px';
}
}
},
getInsertList: function () {
var i, lis = this.list.children, list = [], align = getAlign();
for (i = 0; i < lis.length; i++) {
if (domUtils.hasClass(lis[i], 'selected')) {
var img = lis[i].firstChild,
src = img.getAttribute('_src');
list.push({
src: src,
_src: src,
floatStyle: align
});
}
}
return list;
}
};
dialog.onok = function () {
updateBackground();
editor.fireEvent('saveScene');
};
dialog.oncancel = function () {
editor.execCommand('background', backupStyle);
};
})();
Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

@@ -0,0 +1,65 @@
/*
* 图表配置文件
* */
//不同类型的配置
var typeConfig = [
{
chart: {
type: 'line'
},
plotOptions: {
line: {
dataLabels: {
enabled: false
},
enableMouseTracking: true
}
}
}, {
chart: {
type: 'line'
},
plotOptions: {
line: {
dataLabels: {
enabled: true
},
enableMouseTracking: false
}
}
}, {
chart: {
type: 'area'
}
}, {
chart: {
type: 'bar'
}
}, {
chart: {
type: 'column'
}
}, {
chart: {
plotBackgroundColor: null,
plotBorderWidth: null,
plotShadow: false
},
plotOptions: {
pie: {
allowPointSelect: true,
cursor: 'pointer',
dataLabels: {
enabled: true,
color: '#000000',
connectorColor: '#000000',
formatter: function() {
return '<b>'+ this.point.name +'</b>: '+ ( Math.round( this.point.percentage*100 ) / 100 ) +' %';
}
}
}
}
}
];
@@ -0,0 +1,165 @@
html, body {
width: 100%;
height: 100%;
margin: 0;
padding: 0;
overflow-x: hidden;
}
.main {
width: 100%;
overflow: hidden;
}
.table-view {
height: 100%;
float: left;
margin: 20px;
width: 40%;
}
.table-view .table-container {
width: 100%;
margin-bottom: 50px;
overflow: scroll;
}
.table-view th {
padding: 5px 10px;
background-color: #F7F7F7;
}
.table-view td {
width: 50px;
text-align: center;
padding:0;
}
.table-container input {
width: 40px;
padding: 5px;
border: none;
outline: none;
}
.table-view caption {
font-size: 18px;
text-align: left;
}
.charts-view {
/*margin-left: 49%!important;*/
width: 50%;
margin-left: 49%;
height: 400px;
}
.charts-container {
border-left: 1px solid #c3c3c3;
}
.charts-format fieldset {
padding-left: 20px;
margin-bottom: 50px;
}
.charts-format legend {
padding-left: 10px;
padding-right: 10px;
}
.format-item-container {
padding: 20px;
}
.format-item-container label {
display: block;
margin: 10px 0;
}
.charts-format .data-item {
border: 1px solid black;
outline: none;
padding: 2px 3px;
}
/* 图表类型 */
.charts-type {
margin-top: 50px;
height: 300px;
}
.scroll-view {
border: 1px solid #c3c3c3;
border-left: none;
border-right: none;
overflow: hidden;
}
.scroll-container {
margin: 20px;
width: 100%;
overflow: hidden;
}
.scroll-bed {
width: 10000px;
_margin-top: 20px;
-webkit-transition: margin-left .5s ease;
-moz-transition: margin-left .5s ease;
transition: margin-left .5s ease;
}
.view-box {
display: inline-block;
*display: inline;
*zoom: 1;
margin-right: 20px;
border: 2px solid white;
line-height: 0;
overflow: hidden;
cursor: pointer;
}
.view-box img {
border: 1px solid #cecece;
}
.view-box.selected {
border-color: #7274A7;
}
.button-container {
margin-bottom: 20px;
text-align: center;
}
.button-container a {
display: inline-block;
width: 100px;
height: 25px;
line-height: 25px;
border: 1px solid #c2ccd1;
margin-right: 30px;
text-decoration: none;
color: black;
-webkit-border-radius: 2px;
-moz-border-radius: 2px;
border-radius: 2px;
}
.button-container a:HOVER {
background: #fcfcfc;
}
.button-container a:ACTIVE {
border-top-color: #c2ccd1;
box-shadow:inset 0 5px 4px -4px rgba(49, 49, 64, 0.1);
}
.edui-charts-not-data {
height: 100px;
line-height: 100px;
text-align: center;
}
@@ -0,0 +1,89 @@
<!DOCTYPE html>
<html>
<head>
<title>chart</title>
<meta chartset="utf-8">
<link rel="stylesheet" type="text/css" href="charts.css">
<script type="text/javascript" src="../internal.js"></script>
</head>
<body>
<div class="main">
<div class="table-view">
<h3><var id="lang_data_source"></var></h3>
<div id="tableContainer" class="table-container"></div>
<h3><var id="lang_chart_format"></var></h3>
<form name="data-form">
<div class="charts-format">
<fieldset>
<legend><var id="lang_data_align"></var></legend>
<div class="format-item-container">
<label>
<input type="radio" class="format-ctrl not-pie-item" name="charts-format" value="1" checked="checked">
<var id="lang_chart_align_same"></var>
</label>
<label>
<input type="radio" class="format-ctrl not-pie-item" name="charts-format" value="-1">
<var id="lang_chart_align_reverse"></var>
</label>
<br>
</div>
</fieldset>
<fieldset>
<legend><var id="lang_chart_title"></var></legend>
<div class="format-item-container">
<label>
<var id="lang_chart_main_title"></var><input type="text" name="title" class="data-item">
</label>
<label>
<var id="lang_chart_sub_title"></var><input type="text" name="sub-title" class="data-item not-pie-item">
</label>
<label>
<var id="lang_chart_x_title"></var><input type="text" name="x-title" class="data-item not-pie-item">
</label>
<label>
<var id="lang_chart_y_title"></var><input type="text" name="y-title" class="data-item not-pie-item">
</label>
</div>
</fieldset>
<fieldset>
<legend><var id="lang_chart_tip"></var></legend>
<div class="format-item-container">
<label>
<var id="lang_cahrt_tip_prefix"></var>
<input type="text" id="tipInput" name="tip" class="data-item" disabled="disabled">
</label>
<p><var id="lang_cahrt_tip_description"></var></p>
</div>
</fieldset>
<fieldset>
<legend><var id="lang_chart_data_unit"></var></legend>
<div class="format-item-container">
<label><var id="lang_chart_data_unit_title"></var><input type="text" name="unit" class="data-item"></label>
<p><var id="lang_chart_data_unit_description"></var></p>
</div>
</fieldset>
</div>
</form>
</div>
<div class="charts-view">
<div id="chartsContainer" class="charts-container"></div>
<div id="chartsType" class="charts-type">
<h3><var id="lang_chart_type"></var></h3>
<div class="scroll-view">
<div class="scroll-container">
<div id="scrollBed" class="scroll-bed"></div>
</div>
<div id="buttonContainer" class="button-container">
<a href="#" data-title="prev"><var id="lang_prev_btn"></var></a>
<a href="#" data-title="next"><var id="lang_next_btn"></var></a>
</div>
</div>
</div>
</div>
</div>
<script src="../../third-party/jquery-1.10.2.min.js"></script>
<script src="../../third-party/highcharts/highcharts.js"></script>
<script src="chart.config.js"></script>
<script src="charts.js"></script>
</body>
</html>
+519
View File
@@ -0,0 +1,519 @@
/*
* 图片转换对话框脚本
**/
var tableData = [],
//编辑器页面table
editorTable = null,
chartsConfig = window.typeConfig,
resizeTimer = null,
//初始默认图表类型
currentChartType = 0;
window.onload = function () {
editorTable = domUtils.findParentByTagName( editor.selection.getRange().startContainer, 'table', true);
//未找到表格, 显示错误页面
if ( !editorTable ) {
document.body.innerHTML = "<div class='edui-charts-not-data'>未找到数据</div>";
return;
}
//初始化图表类型选择
initChartsTypeView();
renderTable( editorTable );
initEvent();
initUserConfig( editorTable.getAttribute( "data-chart" ) );
$( "#scrollBed .view-box:eq("+ currentChartType +")" ).trigger( "click" );
updateViewType( currentChartType );
dialog.addListener( "resize", function () {
if ( resizeTimer != null ) {
window.clearTimeout( resizeTimer );
}
resizeTimer = window.setTimeout( function () {
resizeTimer = null;
renderCharts();
}, 500 );
} );
};
function initChartsTypeView () {
var contents = [];
for ( var i = 0, len = chartsConfig.length; i<len; i++ ) {
contents.push( '<div class="view-box" data-chart-type="'+ i +'"><img width="300" src="images/charts'+ i +'.png"></div>' );
}
$( "#scrollBed" ).html( contents.join( "" ) );
}
//渲染table, 以便用户修改数据
function renderTable ( table ) {
var tableHtml = [];
//构造数据
for ( var i = 0, row; row = table.rows[ i ]; i++ ) {
tableData[ i ] = [];
tableHtml[ i ] = [];
for ( var j = 0, cell; cell = row.cells[ j ]; j++ ) {
var value = getCellValue( cell );
if ( i > 0 && j > 0 ) {
value = +value;
}
if ( i === 0 || j === 0 ) {
tableHtml[ i ].push( '<th>'+ value +'</th>' );
} else {
tableHtml[ i ].push( '<td><input type="text" class="data-item" value="'+ value +'"></td>' );
}
tableData[ i ][ j ] = value;
}
tableHtml[ i ] = tableHtml[ i ].join( "" );
}
//draw 表格
$( "#tableContainer" ).html( '<table id="showTable" border="1"><tbody><tr>'+ tableHtml.join( "</tr><tr>" ) +'</tr></tbody></table>' );
}
/*
* 根据表格已有的图表属性初始化当前图表属性
*/
function initUserConfig ( config ) {
var parsedConfig = {};
if ( !config ) {
return;
}
config = config.split( ";" );
$.each( config, function ( index, item ) {
item = item.split( ":" );
parsedConfig[ item[ 0 ] ] = item[ 1 ];
} );
setUserConfig( parsedConfig );
}
function initEvent () {
var cacheValue = null,
//图表类型数
typeViewCount = chartsConfig.length- 1,
$chartsTypeViewBox = $( '#scrollBed .view-box' );
$( ".charts-format" ).delegate( ".format-ctrl", "change", function () {
renderCharts();
} )
$( ".table-view" ).delegate( ".data-item", "focus", function () {
cacheValue = this.value;
} ).delegate( ".data-item", "blur", function () {
if ( this.value !== cacheValue ) {
renderCharts();
}
cacheValue = null;
} );
$( "#buttonContainer" ).delegate( "a", "click", function (e) {
e.preventDefault();
if ( this.getAttribute( "data-title" ) === 'prev' ) {
if ( currentChartType > 0 ) {
currentChartType--;
updateViewType( currentChartType );
}
} else {
if ( currentChartType < typeViewCount ) {
currentChartType++;
updateViewType( currentChartType );
}
}
} );
//图表类型变化
$( '#scrollBed' ).delegate( ".view-box", "click", function (e) {
var index = $( this ).attr( "data-chart-type" );
$chartsTypeViewBox.removeClass( "selected" );
$( $chartsTypeViewBox[ index ] ).addClass( "selected" );
currentChartType = index | 0;
//饼图, 禁用部分配置
if ( currentChartType === chartsConfig.length - 1 ) {
disableNotPieConfig();
//启用完整配置
} else {
enableNotPieConfig();
}
renderCharts();
} );
}
function renderCharts () {
var data = collectData();
$('#chartsContainer').highcharts( $.extend( {}, chartsConfig[ currentChartType ], {
credits: {
enabled: false
},
exporting: {
enabled: false
},
title: {
text: data.title,
x: -20 //center
},
subtitle: {
text: data.subTitle,
x: -20
},
xAxis: {
title: {
text: data.xTitle
},
categories: data.categories
},
yAxis: {
title: {
text: data.yTitle
},
plotLines: [{
value: 0,
width: 1,
color: '#808080'
}]
},
tooltip: {
enabled: true,
valueSuffix: data.suffix
},
legend: {
layout: 'vertical',
align: 'right',
verticalAlign: 'middle',
borderWidth: 1
},
series: data.series
} ));
}
function updateViewType ( index ) {
$( "#scrollBed" ).css( 'marginLeft', -index*324+'px' );
}
function collectData () {
var form = document.forms[ 'data-form' ],
data = null;
if ( currentChartType !== chartsConfig.length - 1 ) {
data = getSeriesAndCategories();
$.extend( data, getUserConfig() );
//饼图数据格式
} else {
data = getSeriesForPieChart();
data.title = form[ 'title' ].value;
data.suffix = form[ 'unit' ].value;
}
return data;
}
/**
* 获取用户配置信息
*/
function getUserConfig () {
var form = document.forms[ 'data-form' ],
info = {
title: form[ 'title' ].value,
subTitle: form[ 'sub-title' ].value,
xTitle: form[ 'x-title' ].value,
yTitle: form[ 'y-title' ].value,
suffix: form[ 'unit' ].value,
//数据对齐方式
tableDataFormat: getTableDataFormat (),
//饼图提示文字
tip: $( "#tipInput" ).val()
};
return info;
}
function setUserConfig ( config ) {
var form = document.forms[ 'data-form' ];
config.title && ( form[ 'title' ].value = config.title );
config.subTitle && ( form[ 'sub-title' ].value = config.subTitle );
config.xTitle && ( form[ 'x-title' ].value = config.xTitle );
config.yTitle && ( form[ 'y-title' ].value = config.yTitle );
config.suffix && ( form[ 'unit' ].value = config.suffix );
config.dataFormat == "-1" && ( form[ 'charts-format' ][ 1 ].checked = true );
config.tip && ( form[ 'tip' ].value = config.tip );
currentChartType = config.chartType || 0;
}
function getSeriesAndCategories () {
var form = document.forms[ 'data-form' ],
series = [],
categories = [],
tmp = [],
tableData = getTableData();
//反转数据
if ( getTableDataFormat() === "-1" ) {
for ( var i = 0, len = tableData.length; i < len; i++ ) {
for ( var j = 0, jlen = tableData[ i ].length; j < jlen; j++ ) {
if ( !tmp[ j ] ) {
tmp[ j ] = [];
}
tmp[ j ][ i ] = tableData[ i ][ j ];
}
}
tableData = tmp;
}
categories = tableData[0].slice( 1 );
for ( var i = 1, data; data = tableData[ i ]; i++ ) {
series.push( {
name: data[ 0 ],
data: data.slice( 1 )
} );
}
return {
series: series,
categories: categories
};
}
/*
* 获取数据源数据对齐方式
*/
function getTableDataFormat () {
var form = document.forms[ 'data-form' ],
items = form['charts-format'];
return items[ 0 ].checked ? items[ 0 ].value : items[ 1 ].value;
}
/*
* 禁用非饼图类型的配置项
*/
function disableNotPieConfig() {
updateConfigItem( 'disable' );
}
/*
* 启用非饼图类型的配置项
*/
function enableNotPieConfig() {
updateConfigItem( 'enable' );
}
function updateConfigItem ( value ) {
var table = $( "#showTable" )[ 0 ],
isDisable = value === 'disable' ? true : false;
//table中的input处理
for ( var i = 2 , row; row = table.rows[ i ]; i++ ) {
for ( var j = 1, cell; cell = row.cells[ j ]; j++ ) {
$( "input", cell ).attr( "disabled", isDisable );
}
}
//其他项处理
$( "input.not-pie-item" ).attr( "disabled", isDisable );
$( "#tipInput" ).attr( "disabled", !isDisable )
}
/*
* 获取饼图数据
* 饼图的数据只取第一行的
**/
function getSeriesForPieChart () {
var series = {
type: 'pie',
name: $("#tipInput").val(),
data: []
},
tableData = getTableData();
for ( var j = 1, jlen = tableData[ 0 ].length; j < jlen; j++ ) {
var title = tableData[ 0 ][ j ],
val = tableData[ 1 ][ j ];
series.data.push( [ title, val ] );
}
return {
series: [ series ]
};
}
function getTableData () {
var table = document.getElementById( "showTable" ),
xCount = table.rows[0].cells.length - 1,
values = getTableInputValue();
for ( var i = 0, value; value = values[ i ]; i++ ) {
tableData[ Math.floor( i / xCount ) + 1 ][ i % xCount + 1 ] = values[ i ];
}
return tableData;
}
function getTableInputValue () {
var table = document.getElementById( "showTable" ),
inputs = table.getElementsByTagName( "input" ),
values = [];
for ( var i = 0, input; input = inputs[ i ]; i++ ) {
values.push( input.value | 0 );
}
return values;
}
function getCellValue ( cell ) {
var value = utils.trim( ( cell.innerText || cell.textContent || '' ) );
return value.replace( new RegExp( UE.dom.domUtils.fillChar, 'g' ), '' ).replace( /^\s+|\s+$/g, '' );
}
//dialog确认事件
dialog.onok = function () {
//收集信息
var form = document.forms[ 'data-form' ],
info = getUserConfig();
//添加图表类型
info.chartType = currentChartType;
//同步表格数据到编辑器
syncTableData();
//执行图表命令
editor.execCommand( 'charts', info );
};
/*
* 同步图表编辑视图的表格数据到编辑器里的原始表格
*/
function syncTableData () {
var tableData = getTableData();
for ( var i = 1, row; row = editorTable.rows[ i ]; i++ ) {
for ( var j = 1, cell; cell = row.cells[ j ]; j++ ) {
cell.innerHTML = tableData[ i ] [ j ];
}
}
}

Some files were not shown because too many files have changed in this diff Show More