File indexing completed on 2024-12-22 05:36:51

0001 <?php
0002 /**
0003  * Zend Framework
0004  *
0005  * LICENSE
0006  *
0007  * This source file is subject to the new BSD license that is bundled
0008  * with this package in the file LICENSE.txt.
0009  * It is also available through the world-wide-web at this URL:
0010  * http://framework.zend.com/license/new-bsd
0011  * If you did not receive a copy of the license and are unable to
0012  * obtain it through the world-wide-web, please send an email
0013  * to license@zend.com so we can send you a copy immediately.
0014  *
0015  * @category  Zend
0016  * @package   Zend_Measure
0017  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0018  * @license   http://framework.zend.com/license/new-bsd     New BSD License
0019  * @version   $Id$
0020  */
0021 
0022 /**
0023  * @see Zend_Locale
0024  */
0025 // require_once 'Zend/Locale.php';
0026 
0027 /**
0028  * @see Zend_Locale_Math
0029  */
0030 // require_once 'Zend/Locale/Math.php';
0031 
0032 /**
0033  * @see Zend_Locale_Format
0034  */
0035 // require_once 'Zend/Locale/Format.php';
0036 
0037 /**
0038  * Abstract class for all measurements
0039  *
0040  * @category   Zend
0041  * @package    Zend_Measure
0042  * @subpackage Zend_Measure_Abstract
0043  * @copyright  Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com)
0044  * @license    http://framework.zend.com/license/new-bsd     New BSD License
0045  */
0046 abstract class Zend_Measure_Abstract
0047 {
0048     /**
0049      * Plain value in standard unit
0050      *
0051      * @var string $_value
0052      */
0053     protected $_value;
0054 
0055     /**
0056      * Original type for this unit
0057      *
0058      * @var string $_type
0059      */
0060     protected $_type;
0061 
0062     /**
0063      * Locale identifier
0064      *
0065      * @var string $_locale
0066      */
0067     protected $_locale = null;
0068 
0069     /**
0070      * Unit types for this measurement
0071      */
0072     protected $_units = array();
0073 
0074     /**
0075      * Zend_Measure_Abstract is an abstract class for the different measurement types
0076      *
0077      * @param  mixed       $value  Value as string, integer, real or float
0078      * @param  int         $type   OPTIONAL a measure type f.e. Zend_Measure_Length::METER
0079      * @param  Zend_Locale $locale OPTIONAL a Zend_Locale Type
0080      * @throws Zend_Measure_Exception
0081      */
0082     public function __construct($value, $type = null, $locale = null)
0083     {
0084         if (($type !== null) and (Zend_Locale::isLocale($type, null, false))) {
0085             $locale = $type;
0086             $type = null;
0087         }
0088 
0089         $this->setLocale($locale);
0090         if ($type === null) {
0091             $type = $this->_units['STANDARD'];
0092         }
0093 
0094         if (isset($this->_units[$type]) === false) {
0095             // require_once 'Zend/Measure/Exception.php';
0096             throw new Zend_Measure_Exception("Type ($type) is unknown");
0097         }
0098 
0099         $this->setValue($value, $type, $this->_locale);
0100     }
0101 
0102     /**
0103      * Returns the actual set locale
0104      *
0105      * @return string
0106      */
0107     public function getLocale()
0108     {
0109         return $this->_locale;
0110     }
0111 
0112     /**
0113      * Sets a new locale for the value representation
0114      *
0115      * @param string|Zend_Locale $locale (Optional) New locale to set
0116      * @param boolean            $check  False, check but don't set; True, set the new locale
0117      * @return Zend_Measure_Abstract
0118      */
0119     public function setLocale($locale = null, $check = false)
0120     {
0121         if (empty($locale)) {
0122             // require_once 'Zend/Registry.php';
0123             if (Zend_Registry::isRegistered('Zend_Locale') === true) {
0124                 $locale = Zend_Registry::get('Zend_Locale');
0125             }
0126         }
0127 
0128         if ($locale === null) {
0129             $locale = new Zend_Locale();
0130         }
0131 
0132         if (!Zend_Locale::isLocale($locale, true, false)) {
0133             if (!Zend_Locale::isLocale($locale, false, false)) {
0134                 // require_once 'Zend/Measure/Exception.php';
0135                 throw new Zend_Measure_Exception("Language (" . (string) $locale . ") is unknown");
0136             }
0137 
0138             $locale = new Zend_Locale($locale);
0139         }
0140 
0141         if (!$check) {
0142             $this->_locale = (string) $locale;
0143         }
0144         return $this;
0145     }
0146 
0147     /**
0148      * Returns the internal value
0149      *
0150      * @param integer            $round  (Optional) Rounds the value to an given precision,
0151      *                                              Default is -1 which returns without rounding
0152      * @param string|Zend_Locale $locale (Optional) Locale for number representation
0153      * @return integer|string
0154      */
0155     public function getValue($round = -1, $locale = null)
0156     {
0157         if ($round < 0) {
0158             $return = $this->_value;
0159         } else {
0160             $return = Zend_Locale_Math::round($this->_value, $round);
0161         }
0162 
0163         if ($locale !== null) {
0164             $this->setLocale($locale, true);
0165             return Zend_Locale_Format::toNumber($return, array('locale' => $locale));
0166         }
0167 
0168         return $return;
0169     }
0170 
0171     /**
0172      * Set a new value
0173      *
0174      * @param  integer|string      $value   Value as string, integer, real or float
0175      * @param  string              $type    OPTIONAL A measure type f.e. Zend_Measure_Length::METER
0176      * @param  string|Zend_Locale  $locale  OPTIONAL Locale for parsing numbers
0177      * @throws Zend_Measure_Exception
0178      * @return Zend_Measure_Abstract
0179      */
0180     public function setValue($value, $type = null, $locale = null)
0181     {
0182         if (($type !== null) and (Zend_Locale::isLocale($type, null, false))) {
0183             $locale = $type;
0184             $type = null;
0185         }
0186 
0187         if ($locale === null) {
0188             $locale = $this->_locale;
0189         }
0190 
0191         $this->setLocale($locale, true);
0192         if ($type === null) {
0193             $type = $this->_units['STANDARD'];
0194         }
0195 
0196         if (empty($this->_units[$type])) {
0197             // require_once 'Zend/Measure/Exception.php';
0198             throw new Zend_Measure_Exception("Type ($type) is unknown");
0199         }
0200 
0201         try {
0202             $value = Zend_Locale_Format::getNumber($value, array('locale' => $locale));
0203         } catch(Exception $e) {
0204             // require_once 'Zend/Measure/Exception.php';
0205             throw new Zend_Measure_Exception($e->getMessage(), $e->getCode(), $e);
0206         }
0207 
0208         $this->_value = $value;
0209         $this->setType($type);
0210         return $this;
0211     }
0212 
0213     /**
0214      * Returns the original type
0215      *
0216      * @return type
0217      */
0218     public function getType()
0219     {
0220         return $this->_type;
0221     }
0222 
0223     /**
0224      * Set a new type, and convert the value
0225      *
0226      * @param  string $type New type to set
0227      * @throws Zend_Measure_Exception
0228      * @return Zend_Measure_Abstract
0229      */
0230     public function setType($type)
0231     {
0232         if (empty($this->_units[$type])) {
0233             // require_once 'Zend/Measure/Exception.php';
0234             throw new Zend_Measure_Exception("Type ($type) is unknown");
0235         }
0236 
0237         if (empty($this->_type)) {
0238             $this->_type = $type;
0239         } else {
0240             // Convert to standard value
0241             $value = $this->_value;
0242             if (is_array($this->_units[$this->getType()][0])) {
0243                 foreach ($this->_units[$this->getType()][0] as $key => $found) {
0244                     switch ($key) {
0245                         case "/":
0246                             if ($found != 0) {
0247                                 $value = call_user_func(Zend_Locale_Math::$div, $value, $found, 25);
0248                             }
0249                             break;
0250                         case "+":
0251                             $value = call_user_func(Zend_Locale_Math::$add, $value, $found, 25);
0252                             break;
0253                         case "-":
0254                             $value = call_user_func(Zend_Locale_Math::$sub, $value, $found, 25);
0255                             break;
0256                         default:
0257                             $value = call_user_func(Zend_Locale_Math::$mul, $value, $found, 25);
0258                             break;
0259                     }
0260                 }
0261             } else {
0262                 $value = call_user_func(Zend_Locale_Math::$mul, $value, $this->_units[$this->getType()][0], 25);
0263             }
0264 
0265             // Convert to expected value
0266             if (is_array($this->_units[$type][0])) {
0267                 foreach (array_reverse($this->_units[$type][0]) as $key => $found) {
0268                     switch ($key) {
0269                         case "/":
0270                             $value = call_user_func(Zend_Locale_Math::$mul, $value, $found, 25);
0271                             break;
0272                         case "+":
0273                             $value = call_user_func(Zend_Locale_Math::$sub, $value, $found, 25);
0274                             break;
0275                         case "-":
0276                             $value = call_user_func(Zend_Locale_Math::$add, $value, $found, 25);
0277                             break;
0278                         default:
0279                             if ($found != 0) {
0280                                 $value = call_user_func(Zend_Locale_Math::$div, $value, $found, 25);
0281                             }
0282                             break;
0283                     }
0284                 }
0285             } else {
0286                 $value = call_user_func(Zend_Locale_Math::$div, $value, $this->_units[$type][0], 25);
0287             }
0288 
0289             $slength = strlen($value);
0290             $length  = 0;
0291             for($i = 1; $i <= $slength; ++$i) {
0292                 if ($value[$slength - $i] != '0') {
0293                     $length = 26 - $i;
0294                     break;
0295                 }
0296             }
0297 
0298             $this->_value = Zend_Locale_Math::round($value, $length);
0299             $this->_type  = $type;
0300         }
0301         return $this;
0302     }
0303 
0304     /**
0305      * Compare if the value and type is equal
0306      *
0307      * @param  Zend_Measure_Abstract $object object to compare
0308      * @return boolean
0309      */
0310     public function equals($object)
0311     {
0312         if ((string) $object == $this->toString()) {
0313             return true;
0314         }
0315 
0316         return false;
0317     }
0318 
0319     /**
0320      * Returns a string representation
0321      *
0322      * @param  integer            $round  (Optional) Runds the value to an given exception
0323      * @param  string|Zend_Locale $locale (Optional) Locale to set for the number
0324      * @return string
0325      */
0326     public function toString($round = -1, $locale = null)
0327     {
0328         if ($locale === null) {
0329             $locale = $this->_locale;
0330         }
0331 
0332         return $this->getValue($round, $locale) . ' ' . $this->_units[$this->getType()][1];
0333     }
0334 
0335     /**
0336      * Returns a string representation
0337      *
0338      * @return string
0339      */
0340     public function __toString()
0341     {
0342         return $this->toString();
0343     }
0344 
0345     /**
0346      * Returns the conversion list
0347      *
0348      * @return array
0349      */
0350     public function getConversionList()
0351     {
0352         return $this->_units;
0353     }
0354 
0355     /**
0356      * Alias function for setType returning the converted unit
0357      *
0358      * @param  string             $type   Constant Type
0359      * @param  integer            $round  (Optional) Rounds the value to a given precision
0360      * @param  string|Zend_Locale $locale (Optional) Locale to set for the number
0361      * @return string
0362      */
0363     public function convertTo($type, $round = 2, $locale = null)
0364     {
0365         $this->setType($type);
0366         return $this->toString($round, $locale);
0367     }
0368 
0369     /**
0370      * Adds an unit to another one
0371      *
0372      * @param  Zend_Measure_Abstract $object object of same unit type
0373      * @return Zend_Measure_Abstract
0374      */
0375     public function add($object)
0376     {
0377         $object->setType($this->getType());
0378         $value  = $this->getValue(-1) + $object->getValue(-1);
0379 
0380         $this->setValue($value, $this->getType(), $this->_locale);
0381         return $this;
0382     }
0383 
0384     /**
0385      * Substracts an unit from another one
0386      *
0387      * @param  Zend_Measure_Abstract $object object of same unit type
0388      * @return Zend_Measure_Abstract
0389      */
0390     public function sub($object)
0391     {
0392         $object->setType($this->getType());
0393         $value  = $this->getValue(-1) - $object->getValue(-1);
0394 
0395         $this->setValue($value, $this->getType(), $this->_locale);
0396         return $this;
0397     }
0398 
0399     /**
0400      * Compares two units
0401      *
0402      * @param  Zend_Measure_Abstract $object object of same unit type
0403      * @return boolean
0404      */
0405     public function compare($object)
0406     {
0407         $object->setType($this->getType());
0408         $value  = $this->getValue(-1) - $object->getValue(-1);
0409 
0410         if ($value < 0) {
0411             return -1;
0412         } else if ($value > 0) {
0413             return 1;
0414         }
0415 
0416         return 0;
0417     }
0418 }