向老式文件上传添加不显眼的进度条
你们都知道新一代花哨的,主要是基于 Flash 的文件上传器,例如 SWFUpload 可以在上传时显示进度条 - 一个很大的改进,特别是对于不稳定和低带宽的连接.
You all know the new generation of fancy, mostly Flash-based file uploaders like SWFUpload that can show a progress bar while uploading - a great improvement especially for shaky and low-bandwidth connections.
然而,这些上传者都自带了如何在客户端处理上传的逻辑.我正在寻找一种不显眼的方式来幻想"现有的经典文件上传,即在普通文件上传表单中引入进度条.
However, these uploaders all bring their own logic of how to handle uploads on the client side. I am looking for an unobtrusive way to "fancify" existing, classical file uploads, i.e. introducing a progress bar to normal file upload forms.
由于上传文件的架构,如果不在客户端进行一些调整,这很可能是不可能的.
Due to the architecture of uploading files, this is most likely not possible without some tweaking on the client side.
我正在寻找一种将调整保持在绝对最小值的解决方案,例如一个将自身添加到普通表单的 onsubmit 事件的组件,执行文件上传,显示一个漂亮的进度条,将生成的临时(服务器端)文件路径放入表单中,然后提交.在服务器端,我只需要修改我的脚本以使用flash上传器提供的文件路径,而不是$_FILES和consorts,并考虑一下安全性.
I am looking for a solution that keeps the tweaking to an absolute minimum, e.g. a component that adds itself to the onsubmit event of a normal form, performs the file upload, displays a nice progress bar, puts the resulting temporary (server side) file path into the form, and submits it. On the server side, I just have to modify my script to use the file path provided by the flash uploader, instead of $_FILES and consorts, and think about security for a moment.
这并不是所有基于 Flash 的上传者所做的:他们可以使用表单中的数据,但他们不提供按原样提交表单的可能性,我正在寻找什么.我正在寻找更进一步的(可能)基于 Flash 的上传功能.
推荐答案
我们通过安装 PECL 扩展pecl-uploadprogress
并在表单中添加了一个简单的 AJAX 回调来实现这一点:
We implemented this very simple by installing the PECL extension pecl-uploadprogress
and added a simple AJAX callback to the forms:
生成上传密钥:
$upload_id = genUploadKey();
function genUploadKey ($length = 11) {
$charset = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
for ($i=0; $i < $length; $i++)
$key .= $charset[(mt_rand(0,(strlen($charset)-1)))];
return $key;
}
创建一个 AJAX 回调处理程序(例如 uploadprogress.php):
Create an AJAX callback handler (eg. uploadprogress.php):
extract($_REQUEST);
// servlet that handles uploadprogress requests:
if ($upload_id) {
$data = uploadprogress_get_info($upload_id);
if (!$data)
$data['error'] = 'upload id not found';
else {
$avg_kb = $data['speed_average'] / 1024;
if ($avg_kb<100)
$avg_kb = round($avg_kb,1);
else if ($avg_kb<10)
$avg_kb = round($avg_kb,2);
else $avg_kb = round($avg_kb);
// two custom server calculations added to return data object:
$data['kb_average'] = $avg_kb;
$data['kb_uploaded'] = round($data['bytes_uploaded'] /1024);
}
echo json_encode($data);
exit;
}
// display on completion of upload:
if ($UPLOAD_IDENTIFIER) {
...
下载 jQuery 和 jQuery.uploadprogress 库(其中还包括上述代码段)并与您的表单集成:
Download jQuery and the jQuery.uploadprogress libraries (which also includes the above snippet) and integrate with your form:
<script type="text/javascript" src="jquery.min.js"></script>
<script type="text/javascript" src="jquery.uploadprogress.0.3.js"></script>
<script type="text/javascript">
jQuery(function () {
// apply uploadProgress plugin to form element
// with debug mode and array of data fields to publish to readout:
jQuery('#upload_form').uploadProgress({
progressURL:'uploadprogress.php',
displayFields : ['kb_uploaded','kb_average','est_sec'],
start: function() {
$('.upload-progress').show();
},
success: function() {
$('.upload-progress').hide();
jQuery(this).get(0).reset();
}
});
});
</script>
将此添加到您的上传表单:
Add this to your upload form:
<input name="UPLOAD_IDENTIFIER" type="hidden" value="$upload_id" />
这应该可以解决问题.这是从我们的代码库中提取的,可能无法开箱即用.但它应该告诉你这个想法.
That should do the trick. This is extracted from our code base and may not work out-of-the-box. But it should tell you the idea.
相关文章