731032406
Flash/Flex构架师 / 广东
积分 0

swfupload小经验


2010-07-05 点击:


swfupload DEMO
http://demo.swfupload.org/v220/index.htm

swfupload下载:http://code.google.com/p/swfupload/downloads/list

  SWFUpload是一个客户端文件上传工具,最初由Vinterwebb.se开发,它通过整合Flash与Javascript技术为 WEB开发者提供了一个具有丰富功能继而超越传统<input type="file" />标签的文件上传模式。

SWFUpload的主要特点
  * 可以同时上传多个文件;
  * 类似AJAX的无刷新上传;
  * 可以显示上传进度;
  * 良好的浏览器兼容性;
  * 兼容其他Javascript库 (例如:jQuery, Prototype等);
  * 支持Flash 8和Flash 9;

  SWFUpload不同于其他基于Flash构建的上传工具,它有着优雅的代码设计,开发者可以利用XHTML、CSS和 Javascript来随心所欲的定制它在浏览器下的外观;它还提供了一组简明的Javascript事件,借助它们开发者可以方便的在文件上传过程中更新页面内容来营造各种动态效果。

  在使用SWFUpload之前,请确认你具备一定的Javascript和DOM知识。在实际开发中,大部分的错误都是由于错误的设置和低劣的Event Handlers处理程序所造成的。

我第一次使用swfupload的时候,发现它和mootools的 1.10版本有冲突:当IE7刷新或者关闭的时候会导致swfupload组件脚本出错,换用最新的mootools之后正常。


另外一个问题就是session,很多时候接收文件上传数据的代码需要根据当前session来进行权限处理。在IE中没什么问题,在firefox中会无法获取session,原因应该是flash处理cookie的方式有所不同,导致在firefox中swfupload无法post当前用户的 cookie信息到服务端。解决方式也比较简单,就是自己获取cookie信息随着文件一并上传(flash9支持)即可。


asp.net中可以直接引用swfupload提供的global.asax来处理session信息,你只需要在创建swfupload对象的时候添加如下代码即可:
 

  1. 1        var swfu;  
  2. 2        function initswfu()  
  3. 3        {  
  4. 4            swfu = new SWFUpload({  
  5. 5     upload_url : "<%=Page.ResolveClientUrl("~/swfupload/upload.aspx")%>",  
  6. 6   flash_url : "<%=Page.ResolveClientUrl("~/swfupload/swfupload_f9.swf")%>",  
  7. 7   file_size_limit : "204800",  
  8. 8   file_types : "*.rar;*.zip",  
  9. 9   file_types_description : "打包文件",  
  10. 10       post_params : {  
  11. 11      "ASPSESSID" : "<%=Session.SessionID %>",  
  12. 12  "AUTHID" : "<%=Request.Cookies[FormsAuthentication.FormsCookieName].Value%>"  
  13. 13                    },  
  14. 14   
  15.  
  16.  
  17. 其中ASPSESSID是用户的sessionid,AUTHID是FormsAuthentication认证信息,
  18. 如果你不用 FormsAuthentication也可以去掉12行,当然如果你需要cookie中的其他自定义信息,
  19. 就在这里添加并需要修改 global.asax了。  

最近发现SWFUpload突然不能正常使用了。查看了官方文档http://www.swfupload.org/,发现原来是FLash 10的原因。Adobe在2008年的10月发布Flash 10,幸好SWFUpload在12月推出了SWFUpload v2,解决了这个问题。

SWFUpload是一个客户端文件上传工具,最初由Vinterwebb.se开发,它通过整合Flash与Javascript技术为WEB 开发者提供了一个具有丰富功能继而超越传统<input type="file" />标签的文件上传模式。
SWFUpload的主要特点
  * 可以同时上传多个文件;
  * 类似AJAX的无刷新上传;
  * 可以显示上传进度;
  * 良好的浏览器兼容性;
  * 兼容其他Javascript库 (例如:jQuery, Prototype等);
  * 对FLASH 9和FLASH 10播放器的支持(V2.2.0版本放弃了对Flash 8的支持)

而SWFUpload v2最主要的就是兼容了Flash Player 10的安全限制问题,但它也造成了和原来版本非常大的改动,注意哦,是非常大的,基本上,你就是要推翻原来的书写代码了,呵呵。

首先我们要下载新的SWFUpload
下载最新版本:http://swfupload.googlecode.com
我选择下载的是SWFUpload v2.2.0 Beta 4.1 Samples.zip,里面包含下面在线示范的例子的源代码,应该足够参考使用了,呵呵。

示范:
提供在线示范的例子: http://demo.swfupload.org/.

好,说重点的,怎么使用SWFUpload v2
在原来的SWFUpload版本中,我们会使用下列的句子来调用SWFUpload,主要是selectFiles();这个方法。
document.getElementById("BrowseButton").onclick = function () { swfu.selectFiles(); };
但在SWFUpload v2中,没有了这个方法,原因在下面会有详细解释,在这只说代替的代码。
在SWFUpload v2中,不能再使用html的button来触发SWFUpload,必须使用定制的Button,这其中比较要注意的是,button不能再用css控制,需要用图片来显示,共要做四张图,下面有详细说明。
用 <span id="spanButtonPlaceHolder"></span>来代替<input type="button" value="选择文件" onClick="swfu.selectFiles();"/>
然后在原来设定的地方加上button settings
// Button settings
button_image_url: "swfupload/BUTTON.gif", // Relative to the Flash file
button_width: "89",
button_height: "21",
button_placeholder_id: "spanButtonPlaceHolder",
button_text: '<span class="theFont">选择文件</span>',
button_text_style: ".theFont { font-size: 12; color: #FFFFFF;}",
button_text_left_padding: 12,
button_text_top_padding: 3,
大致大家能明白这事设置的意思,具体在下面有解释

完整的代码(功能是用来上传图片)
 
  1. var settings = {  
  2. flash_url : "swfupload/swfupload.swf",  
  3. upload_url: "Upload.php", // Relative to the SWF file  
  4. post_params: {"PHPSESSID" : "<?php echo session_id(); ?>"},  
  5. file_size_limit : "2MB",  
  6. file_types : "*.jpg;*.gif;*.png",  
  7. file_types_description : "",  
  8. file_upload_limit : 10,  
  9. file_queue_limit : 0,  
  10. custom_settings : {  
  11.   progressTarget : "fsUploadProgress",  
  12.   cancelButtonId : "btnCancel"  
  13. },  
  14. debug: false,  
  15. // Button settings  
  16. button_image_url: "swfupload/BUTTON.gif", // Relative to the Flash file  
  17. button_width: "89",  
  18. button_height: "21",  
  19. button_placeholder_id: "spanButtonPlaceHolder",  
  20. button_text: '<span class="theFont">选择文件</span>',  
  21. button_text_style: ".theFont { font-size: 12; color: #FFFFFF;}",  
  22. button_text_left_padding: 12,  
  23. button_text_top_padding: 3,   
  24.  
  25. // The event handler functions are defined in handlers.js  
  26. file_queued_handler : fileQueued,  
  27. file_queue_error_handler : fileQueueError,  
  28. file_dialog_complete_handler : fileDialogComplete,  
  29. upload_start_handler : uploadStart,  
  30. upload_progress_handler : uploadProgress,  
  31. upload_error_handler : uploadError,  
  32. upload_success_handler : uploadSuccess,  
  33. upload_complete_handler : uploadComplete, //如果使用swfu.startUpload();来控制几时上传照片的,这行就不要写。  
  34. queue_complete_handler : queueComplete // Queue plugin event   
  35.  
  36. };  
如果希望上传和选择文件的功能分开,可以再使用上传的功能,呵呵,upload_complete_handler : uploadComplete, 这行就不能写了,不然就是一键上传功能了。
<input type="button" value=" 上 传 " onClick="swfu.startUpload();"/>
还有停止和取消上传的,这个我就不一一写了,
好,大家应该基本上可以使用新的SWFUpload了。

SWFUpload V2的新增功能
Flash Player 10的安全机制更严格,类似打开文件上传的对话框的操作,一定需要用户交互才触发,如果用脚本触发,会报#2176的运行时错误。

void selectFile()
不赞成使用,不兼容Flash Player 10
弹出flash的文件选择对话框,只能选择单个文件。

void selectFiles()
不赞成使用,不兼容Flash Player 10
弹出flash的文件选择对话框,可一次性选择多个文件。

flash_width
固定值:1px
(v2.1.0已删除) 设置插入flash影片的HTML元素容器的宽度。如果此设置小于1像素,一些浏览器会出现功能异常。 因此该值在v2.1.0中删除了自定义设置,默认设置为1像素了。

flash_height
固定值:1px
(v2.1.0已删除) 设置插入flash影片的HTML元素容器的高度。如果此设置小于1像素,一些浏览器会出现功能异常。 因此该值在v2.1.0中删除了自定义设置,默认设置为1像素了。

flash_color
默认值:#FFFFFF
(v2.2.0已删除) 设置HTML页面中的flash背景色,默认为#FFFFFF

prevent_swf_caching
默认值:true
(v2.2.0新增)该布尔值设置是否在Flash URL后添加一个随机值,用来防止浏览器缓存了该SWF影片。这是为了解决一些基于IE-engine的浏览器上的出现一个BUG。

提醒:SWFUpload是直接在flash_url后添加了一个swfuploadrnd的随机参数。如果你给定的flash_url中已经存在了GET类型的参数,那么就会出现两个问号连接符导致错误。

button_placeholder_id
默认值:null
(v2.2.0新增) 该必要参数指定了swfupload.swf将要替换的页面内的DOM元素的ID值。当对应的DOM元素被替换为SWF元素时,SWF的容器会被添加一个名称为"swfupload"的样式选择器供CSS自定义使用。

button_image_url
默认值:空字符串
(v2.2.0新增) V2.2.0版最大的改变就是引入了一个按钮到SWF中,利用该参数可以设置一个相对于该swf文件或者是绝对地址的图片(或者是SWF),作为按钮的 UI展现。所有FLASH支持的图片类型都可以使用(gif,jpg,png,或者是一个SWF)。
该按钮图片需要经过一定规则(CSS Sprite)的处理。按钮图片中需要包括按钮的4个状态,从上到下依次是normal, hover, down/click, disabled.(可以参照官方demo中的图片)

button_width
默认值:1
(v2.2.0新增) 设置该SWF的宽度属性。

button_height
默认值:1
(v2.2.0新增)设置该SWF的高度属性(按钮图片高度的1/4)

button_text
默认值:空字符串
(v2.2.0新增) 该属性设置Flash Button中显示的文字,支持HTML。HTML文本的样式可以通过CSS选择器并配合button_text_style参数来设置。关于Flash 文本对HTML的支持详细可见 Adobe's Flash documentation。

button_text_style
默认值:"color: #000000; font-size: 16pt;"
(v2.2.0新增)此参数配合button_text参数,可以通过CSS样式来设置Flash Button中的文字样式。关于Flash文本对CSS的支持详细可见Adobe's Flash documentation

button_text_top_padding
默认值:0
(v2.2.0新增) 设置Flash Button上文字距离顶部的距离,可以使用负值。

button_text_left_padding
默认值:0
(v2.2.0新增) 设置Flash Button上文字距离左侧的距离,可以使用负值。

button_action
默认值:SWFUpload.BUTTON_ACTION.SELECT_FILES(多文件上传)
(v2.2.0新增) 设置Flash Button点击以后的动作。默认为SWFUpload.BUTTON_ACTION.SELECT_FILES,点击按钮将会打开多文件上传的对话框。如果设置为SWFUpload.BUTTON_ACTION.SELECT_FILE,则为单文件上传。如果设置为 SWFUpload.BUTTON_ACTION.START_UPLOAD,则启动文件上传。

button_disabled
默认值:false
(v2.2.0新增) 该布尔值设置Flash Button是否是禁用状态。当它处于禁用状态的时候,点击不会执行任何操作。

button_cursor
默认值:SWFUpload.CURSOR.ARROW(箭头光标)

(v2.2.0新增) 此参数可以设置鼠标划过Flash Button时的光标状态。默认为SWFUpload.CURSOR.ARROW,如果设置为SWFUpload.CURSOR.HAND,则为手形

button_window_mode
默认值:SWFUpload.WINDOW_MODE.WINDOW
(v2.2.0新增) 此参数可以设置浏览器具体以哪种模式显示该SWF影片。

最后,SWFUpload v2在the Mac Flash Player上不能正常功能。

小心swfupload 的cookie Bug


使用SWFUpload的时候一定要小心cookie bug:在非IE内核内核的浏览器下使用SWFUpload上传文件时,该请求会忽略自身浏览器中的所有cookie,只会将IE浏览器下的属于该域的持久cookie(persistent cookies)发送到服务端,非持久cookie( Session only)不会被发送。遗憾的是此Bug并非是SWFUpload内部实现的问题(所有的Flash上传都会存在此bug),而是FlashPlayer 的bug,所有使用FileReference类上传文件时会存在此问题。幸运的是我们有办法绕开此陷阱。

假设一种使用场景,用户登录系统以后,我们会在cookie中写入一个非持久的key值来判断用户身份。当用户使用SWFUpload上传文件的时候,服务端程序通过Requeset中的cookie来判断用户身份。在IE下我们的功能正常,但在FF下你会发现服务端脚本从Request中取到的 cookie是空的,这就是很多人遇到的cookie丢失。前面我也提到了非IE内核的浏览器忽略了自身的所有cookie。

假如用户同时在IE下登录了另外一个账号,并且选择了记住账号,那么我们的程序逻辑可能会写入一个持久的key值。然后用户在FF下上传照片,服务端是接受到cookie中的key值了,但遗憾的是此key是IE下登录账号的cookie,一不小心这就造成了用户身份判断错误的bug,A用户传了张照片居然是属于B用户的。

解决方法:

幸运的是AS3提供的URLRequest对象来包装客户端请求,我们可以上传文件的同时,给请求添加POST值对。因此当我们的上传程序需要依赖客户端cookie的时候,我们可以在上传开始前使用JS将我们需要的cookie读取出来,然后使用SWFUpload提供的 addPostParam方法添加到POST中去,服务端从POST中接受所需要的"cookie"值即可,不再依赖Request中的cookie机制。

 


    731032406  版权所有
    禁止任何用途(禁止转载、商用和个人使用)


所属分类:技术经验分享

本文标签:swfupload 经验

各位正在潜水的同学请注意,有0位无聊人士 在EBIBI附近出没!







    点击我更换图片 看不清
    评论内容 (*必填):

    (Ctrl + Enter 快速提交)