>> Why would you need to do getValues more than once?
>
> Sorry, that's not what I meant. Let me put it this way...
>
> When you request the value of something, if that's your only intent,
> shouldn't the value of the source remain unchanged in the process?
> For example, $object->getName() should just return the Name and not
> change the value of Name in the process. Or, in this case, if you
> request values for the elements of a form, would you expect to change
> the values of those elements in the process?
>
> It seems like the change in value, the tmp files being removed, is
> unexpected when I'm calling $form->getValues. What do you think?
>
> Also, if you're working with form file elements, don't you have to
> make sure that you process the uploaded files before calling something
> like $object->saveEntry($form->getValues())? (or you have to use
> $form->getValue('property') )
>
> -Ed
>
Hi, I'm a newbie of ZF so I' don't know if what I did it's OK or not
this case; anyway,
that's how I did to avoid this problem:
1) create an extension of Zend_Form_Element_File overloading the
getValue() method and removing from it only this code:
if (!$this->receive()) {
return null;
}
as follow
class Planet_Form_Element_File extends Zend_Form_Element_File
{
public function init()
{
$t = Zend_Registry::getInstance()->translate;
$label = (null !== $t) ? $t->_($this->getName()) :
ucfirst(str_replace("_", " ", $this->getName()));
$this->setLabel($label);
}
public function loadDefaultDecorators()
{
$this->setDecorators(array(
'ViewHelper',
'Errors',
array('decorator' => array('td' => 'HtmlTag'), 'options' =>
array('tag' => 'td')),
array('Label', array('tag' => 'td')),
array('decorator' => array('tr' => 'HtmlTag'), 'options' =>
array('tag' => 'tr'))
));
}
/**
* Processes the file, returns null or the filename only
* For the complete path, use getFileName
*
* @return null|string
*/
public function getValue()
{
if (!is_null($this->_value)) {
return $this->_value;
}
$content =
$this->getTransferAdapter()->getFileName($this->getName());
if (empty($content)) {
return null;
}
if (!$this->isValid(null)) {
return null;
}
$filenames = $this->getFileName();
if (count($filenames) == 1) {
$this->_value = basename($filenames);
return $this->_value;
}
$this->_value = array();
foreach($filenames as $filename) {
$this->_value[] = basename($filename);
}
return $this->_value;
}
}
Then to handle the files use (forward methods to) an adapter (forced to
Zend_File_Transfer_Adapter_Http 'cause there's no other :p) like this
/** Planet_Exception */
require_once 'Planet/Exception.php';
class Planet_File_Transfer extends Zend_File_Transfer
{
/**
* Transfer Adapter
*
* @var Zend_File_Transfer_Adapter_Http
*/
protected $_adapter;
/**
* Creates a file processing handler
*
* @param string $protocol Protocol to use
*/
public function __construct($protocol = null)
{
switch (strtoupper($protocol)) {
default:
$adapter = 'Zend_File_Transfer_Adapter_Http';
break;
}
Zend_Loader::loadClass($adapter);
$this->_adapter = new $adapter();
if (!$this->_adapter instanceof
Zend_File_Transfer_Adapter_Abstract) {
require_once 'Zend/File/Transfer/Exception.php';
throw new Zend_File_Transfer_Exception("Adapter " . $adapter
. " does not extend Zend_File_Transfer_Adapter'");
}
return $this->_adapter;
}
/**
* Wraps the methods of the adapter object
*
* @param string $method
* @param array $params
* @return mixed
*/
public function __call($method, $params)
{
if(!$this->_adapter instanceof
Zend_File_Transfer_Adapter_Abstract ||
!method_exists($this->_adapter,$method)){
throw new Planet_Exception('Adapter has not a method ' .
$method);
return false;
}
return call_user_func_array(array($this->_adapter, $method),
$params);
}
/**
* Get a property of the adapter object
*
* @param string $property
* @return mixed
*/
public function __get($property)
{
if(!property_exists(get_class($this->_adapter), $property)){
throw new Planet_Exception('Adapter has not a property ' .
$property);
return false;
}
return $this->_adapter->$property;
}
/**
* Set a property of the adapter object
*
* @param string $property
* @param mixed $value
* @return Zend_File_Transfer_Adapter_Abstract
*/
public function __set($property, $value) {
if(!property_exists(get_class($this->_adapter), $property)){
throw new Planet_Exception('Adapter has not a property ' .
$property);
return false;
}
$this->_adapter->$property = $value;
return $this->_adapter;
}
}
And use it :
in form script)
$attached_file = new Planet_Form_Element_File('attached_file');
$this->addElement($attached_file);
in server receiver script)
$upload = new Planet_File_Transfer();
$files = $upload->getFileInfo();
so the file is still in your tmp dir and have to be manually
moved as usual
I did also a Planet_Image_Handler that uses an adapter:
1) Planet_Image_Magick (or)
2) Planet_Image_Gd
for the image handling (resizing) under a common interface
Planet_Image_Adapter_Interface
this is to create 3 images from 1 ... renaming them into
123_0.jpg (big)
123_1.jpg (med)
123_2.jpg (small)
foreach ($files as $file => $info)
{
$resizeMap = array(1,2,3);
if(file_exists($info['tmp_name']))
{
$size = getimagesize($info['tmp_name']);
$class =
Zend_Registry::getInstance()->configuration->image->adapter->class;
$image_handler = new Planet_Image_Handler( new
$class($info) );
$image_handler->getAdapter()->setTargetDir(APPLICATION_PATH .
'/usr/admin/html/files/');
$image_handler->init();
/** debug */
// $image_handler->getAdapter()->setVerbose(true);
foreach($resizeMap as $k => $q)
{
$imageName = $id . '_' . ($k) . '.jpg';
$new_w = intval($size[0]/$q);
$new_h = intval($size[1]/$q);
$image_handler->setTarget(APPLICATION_PATH .
'/usr/admin/html/files/' . $imageName);
$image_handler->resize($new_w, $new_h);
$image_handler->save();
}
$image_handler->getAdapter()->cleanup();
}
}
}
Hope this help
Bye
Simone
--
________________________________________________________________________________
Simone Cosci - Planet S.r.l. Sistemi informatici
Via Giorgio Ambrosoli, 39 - 50018, Scandicci, Firenze, Italy
WEB: http://www.planetweb.it - http://www.ticka.it
E-Mail s.cosci@nextidea.it
Tel. +39 055 7350271 - Fax. +39 055 7351109 - Cell. 347 4237084
________________________________________________________________________________
没有评论:
发表评论