Java 设置添加ckeditor图片上传功能
第一步:
1.ckeditor中配置文件 config。js/*** @license Copyright (c) 2003-2013, CKSource - Frederico Knabben. All rights reserved.* For licensing, see LICENSE.html or http://ckeditor.com/license*/CKEDITOR.editorConfig = function( config ) {config.toolbar = 'Full'; config.toolbar_Full = [ { name: 'mode' },{ name: 'document', items : ['Source','-','Save','NewPage','DocProps','Preview','Print','-','Templates' ] },{ name: 'clipboard', items : [ 'Cut','Copy','Paste','PasteText','PasteFromWord','-','Undo','Redo' ] }, { name: 'editing', items : [ 'Find','Replace','-','SelectAll','-','SpellChecker', 'Scayt' ] }, { name: 'forms', items : [ 'Form', 'Checkbox', 'Radio','TextField', 'Textarea', 'Select', 'Button', 'ImageButton', 'HiddenField' ] },'/', { name: 'basicstyles', items : ['Bold','Italic','Underline','Strike','Subscript','Superscript','-','RemoveFormat' ] },{ name: 'paragraph', items : ['JustifyLeft', 'JustifyCenter', 'JustifyRight','JustifyBlock' , 'NumberedList','BulletedList','-','Outdent','Indent','-','Blockquote','CreateDiv', '-','JustifyLeft','JustifyCenter','JustifyRight','JustifyBlock','-','BidiLtr','BidiRtl'] }, { name: 'links', items : [ 'Link','Unlink','Anchor' ] }, { name: 'insert', items: ['Image','Flash','Table','HorizontalRule','Smiley','SpecialChar','PageBreak','Iframe' ]},'/', { name: 'styles', items : [ 'Styles','Format','Font','FontSize' ] }, { name:'colors', items : [ 'TextColor','BGColor' ] }, { name: 'tools', items : [ 'Maximize','ShowBlocks','-','About' ] } ]; config.toolbar = 'MyToolbar';//其中'-'表示工具之间分隔的竖线,'/'表示换行 ,其中下面的代码分别代表什么可以去网上查,这里不加以赘述。config.toolbar_MyToolbar =[{ name: 'document', items : [ 'Preview','-','Templates'] },{ name: 'clipboard', items : [ 'Cut','Copy','Paste','PasteText','PasteFromWord','-','Undo','Redo' ] },{ name: 'insert', items : [ 'Image','Table','HorizontalRule','Smiley','SpecialChar' ] },{ name: 'links', items : [ 'Link','Unlink','Anchor' ] },{ name: 'tools', items : [ 'Maximize' ] },'/',{ name: 'styles', items : [ 'Styles','Format' ] },{ name: 'basicstyles', items : [ 'Bold','Italic','Underline' ] },{ name: 'paragraph', items : [ 'JustifyLeft', 'JustifyCenter', 'JustifyRight','JustifyBlock' ,'NumberedList','BulletedList','-','Outdent','Indent','-','Blockquote' ] }];config.removeDialogTabs = 'image:advanced;link:advanced';config.pasteFromWordRemoveStyles = true;config.image_previewText=' '; //预览区域显示内容(预览区域在开始的时候会有一大串英文,在此将这些英文去除)//获得action的相对路径var pathName = window.document.location.pathname;//获取带"/"的项目名var projectName = pathName.substring(0, pathName.substr(1).indexOf('/') + 1);//加上改行代码后就会显示上传功能,但是“上传到服务器”按钮不能正常使用,这里配置的action就是处理图片上传的后台逻辑config.filebrowserUploadUrl=projectName+'/jxhd/uploadImAction.do?'; //固定路径};
============================================================================================================================================
第二步:
2.设置jsp页面,引用ckeditor
//引入ckeditor的js文件,src中为ckeditor.js的路径
<script type="text/javascript" src='<%=host%>/thirdparty/ckeditor/ckeditor.js'></script>//使用ckeditor的代码部分
·····
<td><common:textarea name="xxlbActionForm"property="content" validator="text(0,3000)"empty="true" styleId="contentid" cols="1" rows="8" label="内容" /><script type="text/javascript">//使用ckeditor,这里可以设置ckeditor的一些属性,比如高度和宽度,工具栏等等CKEDITOR.replace("contentid",{toolbar : 'MyToolbar',width:600,height:200});</script>
</td>
·····//js获得ckeditor框中内容,
<script type="text/javascript">function fun_save(){//获取当前页面部分内容var ckEditor = CKEDITOR.instances.contentid; //其中contentval是以html的格式var contentval = ckEditor.getData();····}
</script>
============================================================================================================================================
第三步:
2。Struts1中后台处理图片上传的action代码/*** uploadImAction.java* @date 2015年3月6日* @author xiaomage*/import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Iterator;
import java.util.List;import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileItemFactory;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.time.DateUtils;
import org.apache.log4j.Logger;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;import sun.misc.BASE64Encoder;import com.cvicse.exception.DataAccessException;
import com.cvicse.infra.base.BaseAction;/*** @author ma_hju**/
public class UploadImAction extends BaseAction {/*** * @param mapping* ActionMapping 映射对象* @param form* ActionForm 表单对象* @param request* HttpServletRequest 请求* @param response* HttpServletResponse 响应* @throws DataAccessException * @throws ObjectNotExistException*//*** <p>功能描述:[字段功能描述]</p>*/private static final long serialVersionUID = 1L;protected final Logger logger = Logger.getLogger(UploadImAction.class);/** ~~~ 上传文件的保存路径 */private static final String FILE_UPLOAD_DIR = "/upload";/** ~~~ 上传文件的保存的下一级路径,标示存储类型 */private static final String FILE_UPLOAD_SUB_IMG_DIR = "/img";/** ~~~ 为了能让CKEDITOR加载到上传的图片,此处将位置限制在了/file/jxhdxxlb下,这个文件夹可以自定义*/private static final String FOR_FREEMARKER_LOAD_DIR = "/file/jxhdxxlb";/** ~~~ 每个上传子目录保存的文件的最大数目 */private static final int MAX_NUM_PER_UPLOAD_SUB_DIR = 500;/** ~~~ 上传文件的最大文件大小 */private static final long MAX_FILE_SIZE = 1024 * 1024 * 2;/** ~~~ 系统默认建立和使用的以时间字符串作为文件名称的时间格式*/private static final String DEFAULT_SUB_FOLDER_FORMAT_AUTO = "yyyyMMdd";/** ~~~ 这里扩充一下格式,防止手动建立的不统一*/private static final String DEFAULT_SUB_FOLDER_FORMAT_NO_AUTO = "yyyy-MM-dd";public ActionForward execute(ActionMapping mapping, ActionForm form,HttpServletRequest request, HttpServletResponse response) throws DataAccessException {response.setCharacterEncoding("UTF-8");PrintWriter out=null;// 判断提交的请求是否包含文件boolean isMultipart = ServletFileUpload.isMultipartContent(request);if (!isMultipart) {//return;}// 获取目录File floder = buildFolder(request);if (null == floder) {//return;}//获得ckeditor的一个重要参数String callback =request.getParameter("CKEditorFuncNum");//获得项目名String xmName = request.getContextPath();//String path = request.getSession().getServletContext().getRealPath("/");//StringBuffer URL = request.getRequestURL();try{response.setContentType("text/html; charset=UTF-8");response.setHeader("Cache-Control", "no-cache");out = response.getWriter();// 上传文件的返回地址String fileUrl = "";//----start----从request中获得上传文件的方法,此为核心代码FileItemFactory factory = new DiskFileItemFactory(); ServletFileUpload servletFileUpload = new ServletFileUpload(factory); //中文路径、上传图片名中文乱码问题解决代码servletFileUpload.setHeaderEncoding("UTF-8");servletFileUpload.setFileSizeMax(MAX_FILE_SIZE); @SuppressWarnings("unchecked") List<FileItem> fileitem = servletFileUpload.parseRequest(request); if (null == fileitem || 0 == fileitem.size()) {//return;}Iterator<FileItem> fileitemIndex = fileitem.iterator();if (fileitemIndex.hasNext()) {FileItem file = fileitemIndex.next();if (file.isFormField()) {logger.error("上传文件非法!isFormField=true");}//----end----从request中获得上传文件的方法,此为核心代码,file中就是上传的文件信息//file.getName()获得文件在本地的地址,getFileName()方法获得文件名String fileClientName = getFileName(file.getName());//fileFix为该文件的格式String fileFix = StringUtils.substring(fileClientName,fileClientName.lastIndexOf(".") + 1);//判断图片的格式if (!StringUtils.equalsIgnoreCase(fileFix, "jpg")&& !StringUtils.equalsIgnoreCase(fileFix, "jpeg")&& !StringUtils.equalsIgnoreCase(fileFix, "bmp")&& !StringUtils.equalsIgnoreCase(fileFix, "gif")&& !StringUtils.equalsIgnoreCase(fileFix, "png")) {logger.error("上传文件的格式错误=" + fileFix);//return;}if (logger.isInfoEnabled()) {logger.info("开始上传文件:" + file.getName());}// 为了客户端已经设置好了图片名称在服务器继续能够明确识别,这里不改名称File newfile = new File(floder, fileClientName);//开始上传文件file.write(newfile);if (logger.isInfoEnabled()) {logger.info("上传文件结束,新名称:" + fileClientName + ".floder:"+ newfile.getPath());}// 组装返回url,以便于ckeditor定位图片fileUrl = FOR_FREEMARKER_LOAD_DIR + FILE_UPLOAD_DIR + FILE_UPLOAD_SUB_IMG_DIR + File.separator+floder.getName()+ File.separator + newfile.getName();fileUrl = fileUrl.substring(1);// 去掉/jxhdxxlb的第一个/,否则ckeditor不识别fileUrl = StringUtils.replace(fileUrl, "\\", "/");// 返回“图像”选项卡并显示图片,这里是ckeditor返回图像并显示的代码 out.println("<script type=\"text/javascript\">"); out.println("window.parent.CKEDITOR.tools.callFunction(" + callback+ ",'" + xmName+"/"+fileUrl+ "','')"); // 相对路径用于显示图片 out.println("</script>");}out.flush();out.close();}catch(Exception e){response.setContentType("text/html;charset=UTF-8");out.println("<script type=\"text/javascript\">");out.println("window.parent.CKEDITOR.tools.callFunction("+ callback + ",'','图片上传失败,请重新上传!','')");out.println("</script>");}return null ; }/*** 获取文件名称* @param str* @return*/public String getFileName(String str){int index = str.lastIndexOf("\\");if(-1 != index){return str.substring(index+1);} else {return str;}}/*** 创建目录* * @return*/public File buildFolder(HttpServletRequest request) {// 这里照顾一下CKEDITOR,由于ftl放置位置的原因,这里必须要在freemarker目录下才能被加载到图片,否则虽然可以正常上传和使用,但是// 在控件中无法正常操作String realPath = request.getSession().getServletContext().getRealPath(FOR_FREEMARKER_LOAD_DIR);logger.error(realPath);// 一级目录,如果不存在,创建File firstFolder = new File(realPath + FILE_UPLOAD_DIR);if (!firstFolder.exists()) {if (!firstFolder.mkdir()) {//return null;}}// 二级目录,如果不存在,创建String folderdir = realPath + FILE_UPLOAD_DIR + FILE_UPLOAD_SUB_IMG_DIR;if (logger.isDebugEnabled()) {logger.debug("folderdir" + folderdir);}if (StringUtils.isBlank(folderdir)) {logger.error("路径错误:" + folderdir);//return null;}File floder = new File(folderdir);if (!floder.exists()) {if (!floder.mkdir()) {logger.error("创建文件夹出错!path=" + folderdir);//return null;}}// 再往下的文件夹都是以时间字符串来命名的,所以获取最新时间的文件夹即可String[] files = floder.list();if (null != files && 0 < files.length) {// 含有子文件夹,则获取最新的一个Date oldDate = null;int index = -1;for (int i = 0; i < files.length; i++) {String fileName = files[i];try {Date thisDate = DateUtils.parseDate(fileName, new String[] {DEFAULT_SUB_FOLDER_FORMAT_AUTO, DEFAULT_SUB_FOLDER_FORMAT_NO_AUTO });if (oldDate == null) {oldDate = thisDate;index = i;} else {if (thisDate.after(oldDate)) {// 保存最新的时间和数组中的下标oldDate = thisDate;index = i;}}} catch (ParseException e) {// 这里异常吃掉,不用做什么,如果解析失败,会建立新的文件夹,防止人为的建立文件夹导致的异常。}}// for// 判断当前最新的文件夹下是否已经存在了最大数目的图片if (null != oldDate && -1 != index) {File pointfloder = new File(folderdir + File.separator+ files[index]);if (!pointfloder.exists()) {if (!pointfloder.mkdir()) {logger.error("创建文件夹出错!path=" + folderdir);//return null;}}// 如果文件夹下的文件超过了最大值,那么也需要新建一个文件夹String[] pointfloderFiles = pointfloder.list();if (null != pointfloderFiles&& MAX_NUM_PER_UPLOAD_SUB_DIR < pointfloderFiles.length) {return buildNewFile(folderdir);}return pointfloder;}// 查找当前子文件夹失败,新建一个return buildNewFile(folderdir);} else {// 不含有子文件夹,新建一个,通常系统首次上传会有这个情况return buildNewFile(folderdir);}}/*** 创建一个新文件* @param path* @return*/public File buildNewFile(String path){// 不含有子文件夹,新建一个,通常系统首次上传会有这个情况File newFile = buildFileBySysTime(path);if (null == newFile) {logger.error("创建文件夹失败!newFile=" + newFile);}return newFile;}/*** 根据当前的时间建立文件夹,时间格式yyyyMMdd* * @param path* @return*/public File buildFileBySysTime(String path) {DateFormat df = new SimpleDateFormat(DEFAULT_SUB_FOLDER_FORMAT_AUTO);String fileName = df.format(new Date());File file = new File(path + File.separator + fileName);if (!file.mkdir()) {return null;}return file;}}================================================================================================================================第四步:
Struts文件中要配置action的跳转<!-- 图片上传 start--><action path="/uploadImAction" scope="request"type="com.cvicse.szxy.jxhd.xxlb.action.UploadImAction" ></action>注意:这里配置时不要配置form,原因是struts1.2中ActionForm和ServletFileUpload.parseRequest(request)不能同时使用。网上匿名高人是这么解释的:解释struts用ActionForm的方式处理上传附件的一些问题,struts接收到enctype="multipart/form-data"的post请求后,会看那
个对应的action有没有配置actionform,如果配置了,就会作一些处理,所以你在action里得到的request已经不是一个普通的request
了,而是一个被封装过的request。如果想得到原始的request,就不要struts-config.xml里给action类配置actionform。
ServletFileUpload.parseRequest(request)中的request用的是普通的request,而使用actionForm时request被封装,从而
导致ServletFileUpload.parseRequest(request)取不到值,为空。目前来说,无法解决ActionForm和ServletFileUpload.parseRequest(request)
共存问题,那只能换别的上传方式了!详情可参考:http://blog.sina.com.cn/s/blog_4873f8e00100qxnn.html
==============================================================================================================================================================至此ckeditor功能基本上是配置完成了。下面说一下在配置过程中可能遇到的一些问题和解决方法:1.上传图片时路径或图片名含中文有乱码问题。解决方法:添加一下代码//中文路径、上传图片名中文乱码问题解决代码servletFileUpload.setHeaderEncoding("UTF-8");2。图片能上传到服务器但是预览时不能查看图片。主要原因是:返回图像地址时路径不正确// 返回“图像”选项卡并显示图片,这里是ckeditor返回图像并显示的代码 out.println("<script type=\"text/javascript\">"); out.println("window.parent.CKEDITOR.tools.callFunction(" + callback+ ",'" + xmName+"/"+fileUrl+ "','')"); // 相对路径用于显示图片 out.println("</script>");解决方法:根据自己的实际情况修改返回的图片路径。3.点击“上传到服务器”按钮,显示找不到网页错误,即跳转不到action可能原因:查看Struts中的action跳转的配置,看是否配置了actionform,struts1.2中ActionForm和ServletFileUpload.parseRequest(request)不能同时使用。4.该action中保存图片用的是三级目录,我也是引用网上大神的代码,对此大神是这样说的:“写代码前,看看我们的现状吧,我们可能会让这个图片上传到图片服务器去,但是呢,兜里尚未有足够的银子,而且这个图片暂时量不大,所以现阶段还是保存在应用的特定位置中,够无奈的吧,没办法,谁让咱么有特定的图片服务器呢,那么就下办法在本应用下作文章吧。我们采用一个upload/img的目录,来保存图片文件,以后要迁移到图片服务器也方便些。但是问题来了,所有的图片都放到这个文件夹下,岂不是很庞大,而且一旦超过1000张,文件搜索速度是有点折磨的,那就咱想想办法吧,那就再建立一级目录,每一级下面最多放500张,如果当前文件夹下超过了500张,就重新建立一个文件夹,放入其中。这样目录就变成了三级的 upload/img/20100824 我们采用时间字符串来命名。”5.这个action方法也是我参考网上大神的代码,根据自己项目的需求加以修改。我项目使用的是Struts1。详情可参考:http://blog.csdn.net/quzishen/article/details/58342076.ckeditor工具缓存比较严重,开发的时候修改他的js文件后每次都需要清浏览器缓存才能起作用。
Java 设置添加ckeditor图片上传功能相关推荐
- ckeditor java 上传_java使用CKEditor实现图片上传功能
java如何使用ckeditor实现图片上传功能,具体内容如下 1.根据实际需要下载指定的ckeditor 2.删除文件ckeditor/plugins/image/dialogs/image.js预 ...
- Java图片上传功能
文章目录 实现步骤 核心API 详情代码 在使用图片上传功能时,本文章采用表单提交的方法来上传,所以在表单当中需要加上参数enctype="multipart/form-data" ...
- ckfinder php 配置,PHP中Ckeditor+Ckfinder配置图片上传功能_PHP教程
从标题来看我们知道Ckeditor不支持图片上传功能,它是需要一个组件Ckfinder才可以支持上传图片, 本文章就来详细的介绍了如何配置Ckeditor+Ckfinder实现图片上传的功能. 第一: ...
- Smiditor实现图片上传功能
Simditor 是 Tower 开源的一个基于浏览器所见即所得的文本编辑器. 相比传统的编辑器它的特点是: 功能精简,加载快速 输出格式化的标准 HTML 每一个功能都有非常优秀的使用体验 兼容的主 ...
- php ckeditor 上传图片,CKEditor图片上传的PHP实现
编辑文章是网站后台的常用功能,CKEditor是目前流行的富文本编辑器,它使用方便但要做一些配置才能实现上传本地图片到服务器的功能.在参考了一篇java下CKEditor图片上传的博文后,我用PHP实 ...
- 用jsp实现简单的图片上传功能
用jsp实现简单的图片上传功能 1 先做一个页面,选择上传的图片 <body><form action="uploadServlet" enctype=" ...
- 关于微信内置浏览器,打开图片上传功能,调用的问题
关于微信内置浏览器,打开图片上传功能,调用的问题 前段时间,项目完结测试的时候,同事打开魅族手机测试,无意中发现一个奇葩的问题! 描述: 显示的是文件系统,列表式的,没有调用相机的功能图标,为什么呢? ...
- (转)淘淘商城系列——实现图片上传功能
http://blog.csdn.net/yerenyuan_pku/article/details/72808000 上文我们使用FastDFS-Client进行了简单的文件上传操作测试,淘淘商城项 ...
- 纯前端实现图片上传功能
纯前端实现图片上传功能,告别后端formData上传 使用ElementUI中的upload组件+腾讯云实现简单的图片上传功能 了解了upload的基本属性之后我们要开始上硬菜了 使用ElementU ...
- PHP实现图片上传功能
PHP实现图片上传功能: 第一个页: picupload.php 代码如下: <form action="picop.php" method="post" ...
最新文章
- Laravel框架学习 -- php artisan down/up
- 进阶学习(1) Gradle 项目管理工具的使用
- 深度学习将会变革NLP中的中文分词——TODO 待好好细看
- 自学python该买几本书-自学Python一年,看了几十本书,我发现了这些捷径!
- Ubuntu上安装TensorFlow(python2.7版)
- POJ 2152 Fire(树形DP)
- 蓝牙L2CAP剖析(一)
- linux kill命令详解
- (五)ElasticSearch 6.1.1数据类型
- [HDOJ1897]继续畅通工程
- arcgis的numpy模块_数据分析之numpy模块
- 一种语音控制PPT翻页系统的制作方法
- 一款非常牛逼的 Java 爬虫框架!(请低调使用)
- 当浏览器是ie11以前版本的,跳转到ie升级页
- html双人可悔棋五子棋源码,MATLAB实现五子棋游戏(双人对战、可悔棋).pdf
- 服务器上怎么强制删除文件夹,Windows10系统强制删除文件的方法
- 毕业设计——基于STM32的家庭健康监测系统
- 关闭微信内置浏览器页面
- 不会吧,不会吧,全网最细汉诺塔讲解,不会有人不知道吧。面试官直呼内行,看完只想默默找水喝(C语言)
- 《天使与魔鬼》读后感