修改Fckeditor图片上传功能(java版)



                 Fckeditor默认是带图片上传的功能 但是这不能满足我们的要求 比如说有的版本的Fckeditor有中文乱码的问题,我用的这个Fckediotr上传图片还有Bug,另外也没办法给图片加水印,传上去的图片还是放在工程下的将来会导致图片越来越庞大,怎么办呢? 我们自己动手丰衣足食,把fckeditor改造成我们需要的.

 

               我用的Fckeditor的jar包是2.5版本的 这个版本图片没有中文乱码 另外如果有中文乱码的问题我建议也不要把图片名称改为UUID名称,因为当用户把自己的图片传上去的时候 想点浏览在去找这张图片的时候 他发现上面的那么多的名字根本分不清哪个是他这次传上来的.有人会问那图片名字重复了怎么办呢?Fckeditor已经考虑到这个问题了 他检测到服务器上有这个名字的图片他会自动重命名.废话不多说了我们来看我是怎么干的.

 

             我们要解决的几个问题

             1.上传图片放到服务器的一个物理位置而不是工程下.

             2.解决Fckeditor2.5版本中图片上传 没有flush的问题

             3.增加水印功能.

          

               Fckeditor低版本的时候我们需要重写一个Servlet 但是我发现这个版本图片上传功能是放在一个类下的而不是

旧版本中的ConnectorServlet.那既然需要重写一个类 而这个类呢有是ConnectorServlet中调用的那我们是不是得先重写ConnectorServlet 然后在重写这个类,然后再把自己写的ConnectorServlet配置到web.xml中呢?不用那么麻烦我不是那样做的 看下图我是怎么做的 ,并请大家自己思考为什么可以这么做.

 

             

 

                           我在工程下建了和fckeditor相同的包结构然后把我需要重写的类从Fckeditor源代码中拷了过来

 好了 我们开始修改吧

 

                 Dispatcher.java中doPost方法

  

            

	UploadResponse doPost(final HttpServletRequest request) {
		logger.debug("Entering Dispatcher#doPost");
		//String type = null;
		Context context = ThreadLocalData.getContext();
		context.logBaseParameters();
		
		UploadResponse uploadResponse = null;
		// check permissions for user actions
		if (!RequestCycleHandler.isEnabledForFileUpload(request))
			uploadResponse = UploadResponse.getFileUploadDisabledError();
		// check parameters  
		else if (!Command.isValidForPost(context.getCommandStr()))
			uploadResponse = UploadResponse.getInvalidCommandError();
		else if (!ResourceType.isValidType(context.getTypeStr()))
			uploadResponse = UploadResponse.getInvalidResourceTypeError();
		else if (!UtilsFile.isValidPath(context.getCurrentFolderStr()))
			uploadResponse = UploadResponse.getInvalidCurrentFolderError();
		else {

			// call the Connector#fileUpload
			ResourceType type = context.getDefaultResourceType();
			FileItemFactory factory = new DiskFileItemFactory();
			ServletFileUpload upload = new ServletFileUpload(factory);
			try {
				List<FileItem> items = upload.parseRequest(request);
				// We upload just one file at the same time
				FileItem uplFile = items.get(0);
				// Some browsers transfer the entire source path not just the
				// filename
				String fileName = FilenameUtils.getName(uplFile.getName());
				logger.debug("Parameter NewFile: {}", fileName);
				// check the extension
				if (type.isNotAllowedExtension(FilenameUtils
						.getExtension(fileName)))
					uploadResponse = UploadResponse.getInvalidFileTypeError();
				// Secure image check (can't be done if QuickUpload)
				else if (type.equals(ResourceType.IMAGE)
						&& PropertiesLoader.isSecureImageUploads()
						&& !UtilsFile.isImage(uplFile.getInputStream())) {
					uploadResponse = UploadResponse.getInvalidFileTypeError();
				} else {
					String sanitizedFileName = UtilsFile
							.sanitizeFileName(fileName);
					//修改为UUID文件名称  我这里注释掉了 如下代码可以把上传的图片名称改为UUID
					//sanitizedFileName = UUID.randomUUID().toString()+sanitizedFileName.substring(sanitizedFileName.lastIndexOf("."), sanitizedFileName.length());
					logger.debug("Parameter NewFile (sanitized): {}",
							sanitizedFileName);
					String newFileName = connector.fileUpload(type, context
							.getCurrentFolderStr(), sanitizedFileName, uplFile
							.getInputStream());
					
					
					
					String fileUrl = UtilsResponse.fileUrl(RequestCycleHandler
							.getUserFilesPath(request), type, context
							.getCurrentFolderStr(), newFileName);
					//Fckeditor上传有两种 一种是上传图片 一种是上传附件
					//如果是图片的话 我用这个action来预览图片
					if(type.equals(ResourceType.IMAGE))
					{
						fileUrl = "tumbnail.action?fileName="+sanitizedFileName;
					}
					//如果是上传附件的话 用如下的action来下载附件
					else if(type.equals(ResourceType.FILE)){
					    sanitizedFileName = URLEncoder.encode(sanitizedFileName, "utf-8");
						fileUrl = request.getContextPath()+"/attachmentDownload.action?fileName="+sanitizedFileName;
					}
					
					if (sanitizedFileName.equals(newFileName))
						uploadResponse = UploadResponse.getOK(fileUrl);
					else {
						uploadResponse = UploadResponse.getFileRenamedWarning(fileUrl, newFileName);
						logger.debug("Parameter NewFile (renamed): {}",
								newFileName);
					}
				}
				uplFile.delete();
			} catch (InvalidCurrentFolderException e) {
				uploadResponse = UploadResponse.getInvalidCurrentFolderError();
			} catch (WriteException e) {
				uploadResponse = UploadResponse.getFileUploadWriteError();
			} catch (IOException e) {
				uploadResponse = UploadResponse.getFileUploadWriteError();
			} catch (FileUploadException e) {
				uploadResponse = UploadResponse.getFileUploadWriteError();
			}
		}
		
		logger.debug("Exiting Dispatcher#doPost");
		return uploadResponse;
	}

 

   

   AbstractLocalFileSystemConnector.java 中 fileUpload方法

 

 

	public String fileUpload(final ResourceType type, final String currentFolder, final String fileName, final InputStream inputStream) throws InvalidCurrentFolderException, WriteException {
		String absolutePath = getRealUserFilesAbsolutePath(RequestCycleHandler.getUserFilesAbsolutePath(ThreadLocalData.getRequest()));
        File typeDir = getOrCreateResourceTypeDir(absolutePath, type);
		File currentDir = new File(typeDir, currentFolder);
		if (!currentDir.exists() || !currentDir.isDirectory())
			throw new InvalidCurrentFolderException();

		File newFile = new File(currentDir, fileName);
		File fileToSave = UtilsFile.getUniqueFile(newFile.getAbsoluteFile());

		OutputStream outputStream = null;
		try {
			outputStream = new FileOutputStream(fileToSave);
			IOUtils.copyLarge(inputStream, outputStream);

		} catch (IOException e) {
			throw new WriteException();
		} finally {
			try {
			    
				if (outputStream != null) {
				    //这里解决这个版本中图片上传没有flush的bug
					outputStream.flush();
					IOUtils.closeQuietly(outputStream);
				}
				    IOUtils.closeQuietly(inputStream);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}

		String format = fileToSave.getName().substring(fileToSave.getName().lastIndexOf(".") + 1, fileToSave.getName().length());
		
		//下面给图片加水印
		//如果是图片的话 加水印
		if (ImageUtils.isPicture(format)) {
			ImageUtils.pressImage(servletContext.getRealPath("themes/cms/image/") +"\\"+ "sxgajj.png", newFile.getAbsoluteFile().getAbsolutePath());
		}

		return fileToSave.getName();
	}

 

   另外还有图片预览的action 和 加水印的代码

 

   图片预览的action代码

 

  

public class FckImgPreviewAction {
	private String fileName;
	
	public String execute() {

		if (fileName != null) {
		    //图片在服务器上的物理存放路径
			String path = ResourceBundle.getBundle("sysConfig").getString("userFilePath.image");

			File file = new File("/" + path + fileName);
			HttpServletResponse resp = ServletActionContext.getResponse();
			OutputStream os = null;
			InputStream is = null;
			if (file.exists()) {
				try {
					is = new FileInputStream(file);
					os = resp.getOutputStream();
					IOUtils.copyLarge(is, os);
				} catch (IOException e) {
					e.printStackTrace();
				}finally{
					try {
						IOUtils.closeQuietly(is);
						if(os != null)
						{
							os.flush();
							IOUtils.closeQuietly(os);
						}
					} catch (IOException e) {
						e.printStackTrace();
					}
					
				}
			}
		}
		return null;

	}

	public String getFileName() {
		return fileName;
	}

	public void setFileName(String fileName) {
		this.fileName = fileName;
	}
	
}

 

 

  

	/**
	 * @param pressImg 水印文件路径
	 * @param targetImg 目标文件路径
	 */
	public final static void pressImage(String pressImg, String targetImg) {
		FileOutputStream out = null;
		try {
			File _file = new File(targetImg);
			Image src = ImageIO.read(_file);
			int wideth = src.getWidth(null);
			int height = src.getHeight(null);
			BufferedImage image = new BufferedImage(wideth, height, BufferedImage.TYPE_INT_RGB);
			Graphics g = image.createGraphics();
			g.drawImage(src, 0, 0, wideth, height, null);
			// 水印文件
			File _filebiao = new File(pressImg);
			Image src_biao = ImageIO.read(_filebiao);
			int wideth_biao = src_biao.getWidth(null);
			int height_biao = src_biao.getHeight(null);
			g.drawImage(src_biao, wideth - wideth_biao, height - height_biao, wideth_biao, height_biao, null);
			// /
			g.dispose();
			out = new FileOutputStream(targetImg);
			JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
			encoder.encode(image);
			
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			if(out!=null)
			{
				try {
					out.flush();
					out.close();
				} catch (IOException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
			
		}
	}

 

   还有个重要的类差点忘了  GetResponse.java  GetResponse方法 

 

   让fck在上传完图片后 fck图片预览图片url正确的显示

  

	public GetResponse(Command command, ResourceType type,
			String currentFolder, String constructedUrl) {

		try {
			DocumentBuilderFactory factory = DocumentBuilderFactory
					.newInstance();
			DocumentBuilder builder = factory.newDocumentBuilder();
			document = builder.newDocument();
		} catch (ParserConfigurationException e) {
			throw new RuntimeException(e);
		}

		Element root = document.createElement("Connector");
		document.appendChild(root);
		root.setAttribute("command", command.getName());
		root.setAttribute("resourceType", type.getName());

		Element currentFolderElement = document.createElement("CurrentFolder");
		currentFolderElement.setAttribute("path", currentFolder);
		
		if(type.equals(ResourceType.IMAGE))
		{
			constructedUrl = "tumbnail.action?fileName=";
		}
		else if(type.equals(ResourceType.FILE)){
			
			constructedUrl = "attachmentDownload.action?fileName=";
		}
		
		currentFolderElement.setAttribute("url", constructedUrl);
		
		
		//System.out.println(constructedUrl);
		root.appendChild(currentFolderElement);

	}

 

 

    ok了 看下效果

 

 

 

 

 



 

 

            

  

          

 

 

 

 

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值