多文件上传

说明

多文件上传功能是用js实现的flash效果,在我们的ecstore系统中,有两处用到了这种方法(1、商品图片上传;2、模板包上传),实现此功能的主要部分就是调用flash文件(uploader.swf)和 数据保存,接下来就是一起学习怎样去完成“多文件上传”的功能(此处主要是以b2c中多图片上传作为示例)。

调用flash

为了方便多次调用上传的功能,我们可以写一个包含了调用flash的文件(domfile.html),最后通过

<{include file="domfile.html"}>直接引用到你想要完成多文件上传的html页面中。(文件代码展示如下)

domfile.html

<div class="division" style="margin:0;position:relative">
	<!--flash按钮展示层-->
     <div class="clearfix">
         <span id="pic-uploader">
              <{button app="desktop" class="btn-upload" label=$___b2c="添加商品图片"|t:'b2c' icon="image_new.gif"}>
         </span>
     </div>
	<!--上传的图片展示层-->
     <div class="pic-area" id="pic-area">
         <input type="hidden" name="image_default" value="<{$goods.image_default_id}>" />
		 <div id='all-pics' style="width:100%">
		 <div class="gpic-box">
			<{include file="gimage.html" app='image'}>
		 </div>
	 </div>
</div>
<script>
//function setPos(){
 /*此处是加载文件上传表单<input type="file">
  *$$('.std-upload-txt')[0].setStyle('top',$('pic-uploader').getPosition().y+$('main').getScroll().y);
  */     
//}
//window.addEvent('domready',function(){
//  setPos.periodical(200);
//});
//var goodsEditor = null;

var goodsEditFrame = (function(){
//  setPos();
 /**
   *此处是删除调用的事件+路径
   *goodsEditor = new ShopExGoodsEditor('gEditor',{imgtype:'<{$uploader}>',url:'<{$url}>',goods_id:'<{$goods.id}>'}); 
   */ 

  Ex_Loader('uploader',function(){
  /**
    *此处是弹出的浮动窗口中整个页面的最外层“<div id='add' >”
    *var main =$('add').getParent('.dialog-content-body').setStyle('position','relative');
    *console.info($('add').getParent('.dialog-content-body'));
    */
        new Swiff.Uploader( {
            allowDuplicates: true,
            verbose: true,
	    //container:main,
	    //flash上传保存路径
            url:'index.php?app=image&ctl=admin_manage&act=gimage_swf_remote&sess_id='+sess_id,
	    //flash路径   
            path: '<{$file_dir}>/uploader.swf',   
	    //允许上传的图片(文件)类型(若果想修改为上传多文件的,在这里加载你要上传的文件的后缀)            
            typeFilter: {
                'Images (*.jpg, *.jpeg, *.gif, *.png)': '*.jpg; *.jpeg; *.gif; *.png'           
            },
	    //图片大小的限制
            fileSizeMax:<{$IMAGE_MAX_SIZE}>,                                                     
            target:'pic-uploader',
            onSelect:function(rs){
                if(rs)
                rs.each(function(v){
                    if(v.size>this.fileSizeMax){
                        alert(v.name+'<{t}>\n\n文件超出大小<{/t}>');
                    };
                },this);
            },
            onSelectFail:function(rs){
                rs.each(function(v){
                    if(v.validationError=='sizeLimitMax'){
                        alert(v.name+'<{t}>\n\n文件超出大小<{/t}>');
                    };
                });
            },
            onSelectSuccess:function(rs){
                var PID='up_';
                var _this=this;
                rs.each(function(v,i){
                     new Element('div',{'class':'gpic-box','id':PID+v.id}).inject($('all-pics'));
                });
                this.start();
            },
            onFileOpen:function(e){
                $('up_'+e.id).setHTML('<em style="font-size:13px;font-family:Georgia;">0%</em>');
            },
            onFileProgress:function(e){
                $('up_'+e.id).getElement('em').set('text',e.progress.percentLoaded+'%');
            },
            onFileComplete: function(res){
                if(res.response.error){
                    return  new MessageBox.error('<{t}>文件<{/t}>'+res.name+'<{t}>上传失败<{/t}>');
                }
                $('up_'+res.id).setHTML(res.response.text);
                if(!$E('#pic-area .current')&&$E('#pic-area .gpic')){
                  $E('#pic-area .gpic').onclick();
                }
            }
        });

    });


})();
</script>
接下来我们从控制器中来调用此文件。

index.php

<?php
class useremail_ctl_admin_file extends desktop_controller{
    function 
index(){
        
$this->finder('useremail_mdl_user',
            array(
                
'title'=>'会员详细信息录入',
                
'actions'=>array(
                    array(
                        
'label'=>app::get('useremail')->_('添加信息'),
                        
'icon' => 'add.gif',
                        
'href' => 'index.php?app=useremail&ctl=admin_file&act=add',
                        
/**
                         * 此处是弹出浮动小窗口
                         *'target'=>'dialog::{title:\''.app::get('useremail')->_('信息录入').'\',width:700,height:400}'
                         * /
                        /**此处是在新窗口打开(两种不同的窗口,会有不同的flash调用方法;这里用新窗口)*/
                        
'target'=>'_blank',
                    ),
                ),
            )
        );
    }

    function 
add(){
     
/**此处sess_id的使用场景是:在弹出子窗口中调用domfile.html文件时传给siss_id的参数*/
       //$this->pagedata['ssid'] = kernel::single('base_session')->sess_id();    //可有可无
         //此处必须有,他是flash的具体地址
        
$this->pagedata['file_dir'] = &app::get('image')->res_url;
        
//此处必须有,他是图片大小的限制
        
$this->pagedata['IMAGE_MAX_SIZE'] = 1024*1024*5;
        
$this->page('upfile.html');

    }
}

upfile.html
<!--  以下是引入flash页面-->
会员照片:<{include file="domfile.html"}>

根据以上的步骤,可以先测试一下效果,看看是不是想要的那种感觉。效果图如下:

在页面调用flash页面效果图:

在弹出子窗口调用flash页面效果

数据保存

ecstore系统上传图片的保存方法都很完善,我们只需要去看看他们的保存方法,不需要我们在重新去写方法。方法路径是:

“app=image&ctl=admin_manage&act=gimage_swf_remote”

以上的方法只是单独的保存图片相关的信息,返回了图片存储id,还没有与商品关联在一起,以下是保存商品时关联图片的方法。在商品保存方法中,对于图片关联表的保存处理方式如下(只是作为参考):

 $arr_remove_image = array();
  if( $_POST['goods']['images'] ){
     $oImage_attach = app::get('image')->model('image_attach');
      /*
       *根据相关商品id和goods类型查询当前商品已经关联的图片(此操作适合修改商品信息),删除原有的信息,从新做插入操作
       */
     $arr_image_attach = $oImage_attach->getList('*',array('target_id'=>$goods['goods_id'],'target_type'=>'goods'));
     foreach ((array)$arr_image_attach as $_arr_image_attach){
         if (!in_array($_arr_image_attach['image_id'],$_POST['goods']['images'])){
                 $arr_remove_image[] = $_arr_image_attach['image_id'];
             }
          }
    }

        if ( !$oGoods->save($goods) ){
            //保存商品数据
            $this->end(false,app::get('b2c')->_('您所填写的货号重复,请检查!'));
        }else{
	/*图片的处理*/
          if( $goods['images'] ){
                $oImage = &app::get('image')->model('image');
                if ($arr_remove_image){
                    foreach($arr_remove_image as $_arr_remove_image)
                        $test = $oImage->delete_image($_arr_remove_image,'goods');
                }
                //保存图片信息
                foreach($goods['images'] as $k=>$v){
                    $test = $oImage->rebuild($v['image_id'],array('S','M','L'),true);
                }
            }
          /**商品相关的其他内容处理及存储*/
        }
到这里,我们多图片上传处理完成,接下去的操作就是显示等其他的一些方式,就要靠自己去完成了。

多文件上传重点总结

多文件上传和多图片上传可以说是一样的原理,只需注意以下几个问题

  1. 调用flash时文件类型的罗列(把想要上传的文件类型用以下方式列出)
    typeFilter: {
                    'Images (*.jpg, *.psd,*.gif, *.png,*.bmp,*.zip,*.pdf,*.rar,*.xls,*.xlsx,*.doc,*.docx,*.ppt,*.pptx,*.csv,*.txt,)': '*.jpg; *.jpeg; *.gif; *.png; *.bmp; *.zip; *.pdf; *.rar; *.xls; *.xlsx; *.doc; *.docx; *.ppt; *.pptx; *.csv; *.txt; '           
                },
    
  2. 文件保存时需要扩展图片保存model中的store()方法(以下方法是多文件保存的一个示例,只能作为参考,具体的要以自己所需来处理)
    function store(){
            $file = $this->app->model('file');
            $file_name = $_FILES['Filedata']['name']; 
    		$hou=explode('.',$file_name);  //上传文件名
    		$hou='.'.end($hou);
    		$extname = array(
    				1 => '.txt',
    				2 => '.doc',
    				3 => '.zip',
    				4 => '.pdf',
    				5 => '.rar',
    				6 => '.xls',
    				7 => '.xlsx',
    				8 => '.docx',
    				9 => '.ppt',
    				10 => '.pptx',
    				11 => '.csv',
                    12=> '.gif',
                    13=> '.jpg',
                    14=> '.png',
                    15=> '.bmp',
    				16 => '.psd',
                );
    		
            if(!@is_dir(ROOT_DIR."/public/tmp/")){
    			@mkdir(ROOT_DIR."/public/tmp/",0777,true);
    		}
            $filepath = ROOT_DIR."/public/tmp/";     //存放的临时路径
            $upname =md5(time().'|'.$file_name);  //存放的文件名
    		$pathname=$filepath.$upname;        //  临时路径名
            $uppath=$_FILES['Filedata']['tmp_name'];
            if($_FILES['Filedata']['error'] == UPLOAD_ERR_NO_FILE) continue;
    		if(!is_uploaded_file($uppath)) return false;
            if(!move_uploaded_file($uppath,$pathname)){
    			return false;
    		}
    		$docname=time().'|'.$file_name;
    		if(in_array($hou,$extname)){
                   $upfile=array(
                        'file_id'=>md5(rand(0,9999).microtime()),
    					'file_name'=>$docname,
    					'path'=>$pathname,
    					'addtime'=>time(),
    				);
                    if(!$file->save($upfile)) return false;        
    			  $file_id = $upfile['file_id'];
    		}
            $this->pagedata['gimage']['file_id'] = $file_id;
    		$this->pagedata['gimage']['file_name'] = $file_name;
            $this->display('gimage.html');
            
            
        }
    

內容目录

上一个主题

多表连接

下一个主题

附录

快速搜索

输入相关的模块,术语,类或者函数名称进行搜索