web/lib/Zend/Measure/Abstract.php
changeset 64 162c1de6545a
parent 19 1c2f13fd785c
child 68 ecaf28ffe26e
equal deleted inserted replaced
63:5b37998e522e 64:162c1de6545a
       
     1 <?php
       
     2 /**
       
     3  * Zend Framework
       
     4  *
       
     5  * LICENSE
       
     6  *
       
     7  * This source file is subject to the new BSD license that is bundled
       
     8  * with this package in the file LICENSE.txt.
       
     9  * It is also available through the world-wide-web at this URL:
       
    10  * http://framework.zend.com/license/new-bsd
       
    11  * If you did not receive a copy of the license and are unable to
       
    12  * obtain it through the world-wide-web, please send an email
       
    13  * to license@zend.com so we can send you a copy immediately.
       
    14  *
       
    15  * @category  Zend
       
    16  * @package   Zend_Measure
       
    17  * @copyright  Copyright (c) 2005-2010 Zend Technologies USA Inc. (http://www.zend.com)
       
    18  * @license   http://framework.zend.com/license/new-bsd     New BSD License
       
    19  * @version   $Id: Abstract.php 21329 2010-03-04 22:06:08Z thomas $
       
    20  */
       
    21 
       
    22 /**
       
    23  * @see Zend_Locale
       
    24  */
       
    25 require_once 'Zend/Locale.php';
       
    26 
       
    27 /**
       
    28  * @see Zend_Locale_Math
       
    29  */
       
    30 require_once 'Zend/Locale/Math.php';
       
    31 
       
    32 /**
       
    33  * @see Zend_Locale_Format
       
    34  */
       
    35 require_once 'Zend/Locale/Format.php';
       
    36 
       
    37 /**
       
    38  * Abstract class for all measurements
       
    39  *
       
    40  * @category   Zend
       
    41  * @package    Zend_Measure
       
    42  * @subpackage Zend_Measure_Abstract
       
    43  * @copyright  Copyright (c) 2005-2010 Zend Technologies USA Inc. (http://www.zend.com)
       
    44  * @license    http://framework.zend.com/license/new-bsd     New BSD License
       
    45  */
       
    46 abstract class Zend_Measure_Abstract
       
    47 {
       
    48     /**
       
    49      * Plain value in standard unit
       
    50      *
       
    51      * @var string $_value
       
    52      */
       
    53     protected $_value;
       
    54 
       
    55     /**
       
    56      * Original type for this unit
       
    57      *
       
    58      * @var string $_type
       
    59      */
       
    60     protected $_type;
       
    61 
       
    62     /**
       
    63      * Locale identifier
       
    64      *
       
    65      * @var string $_locale
       
    66      */
       
    67     protected $_locale = null;
       
    68 
       
    69     /**
       
    70      * Unit types for this measurement
       
    71      */
       
    72     protected $_units = array();
       
    73 
       
    74     /**
       
    75      * Zend_Measure_Abstract is an abstract class for the different measurement types
       
    76      *
       
    77      * @param  $value  mixed  - Value as string, integer, real or float
       
    78      * @param  $type   type   - OPTIONAL a measure type f.e. Zend_Measure_Length::METER
       
    79      * @param  $locale locale - OPTIONAL a Zend_Locale Type
       
    80      * @throws Zend_Measure_Exception
       
    81      */
       
    82     public function __construct($value, $type = null, $locale = null)
       
    83     {
       
    84         if (($type !== null) and (Zend_Locale::isLocale($type, null, false))) {
       
    85             $locale = $type;
       
    86             $type = null;
       
    87         }
       
    88 
       
    89         $this->setLocale($locale);
       
    90         if ($type === null) {
       
    91             $type = $this->_units['STANDARD'];
       
    92         }
       
    93 
       
    94         if (isset($this->_units[$type]) === false) {
       
    95             require_once 'Zend/Measure/Exception.php';
       
    96             throw new Zend_Measure_Exception("Type ($type) is unknown");
       
    97         }
       
    98 
       
    99         $this->setValue($value, $type, $this->_locale);
       
   100     }
       
   101 
       
   102     /**
       
   103      * Returns the actual set locale
       
   104      *
       
   105      * @return string
       
   106      */
       
   107     public function getLocale()
       
   108     {
       
   109         return $this->_locale;
       
   110     }
       
   111 
       
   112     /**
       
   113      * Sets a new locale for the value representation
       
   114      *
       
   115      * @param string|Zend_Locale $locale (Optional) New locale to set
       
   116      * @param boolean            $check  False, check but don't set; True, set the new locale
       
   117      * @return Zend_Measure_Abstract
       
   118      */
       
   119     public function setLocale($locale = null, $check = false)
       
   120     {
       
   121         if (empty($locale)) {
       
   122             require_once 'Zend/Registry.php';
       
   123             if (Zend_Registry::isRegistered('Zend_Locale') === true) {
       
   124                 $locale = Zend_Registry::get('Zend_Locale');
       
   125             }
       
   126         }
       
   127 
       
   128         if ($locale === null) {
       
   129             $locale = new Zend_Locale();
       
   130         }
       
   131 
       
   132         if (!Zend_Locale::isLocale($locale, true, false)) {
       
   133             if (!Zend_Locale::isLocale($locale, false, false)) {
       
   134                 require_once 'Zend/Measure/Exception.php';
       
   135                 throw new Zend_Measure_Exception("Language (" . (string) $locale . ") is unknown");
       
   136             }
       
   137 
       
   138             $locale = new Zend_Locale($locale);
       
   139         }
       
   140 
       
   141         if (!$check) {
       
   142             $this->_locale = (string) $locale;
       
   143         }
       
   144         return $this;
       
   145     }
       
   146 
       
   147     /**
       
   148      * Returns the internal value
       
   149      *
       
   150      * @param integer            $round  (Optional) Rounds the value to an given precision,
       
   151      *                                              Default is -1 which returns without rounding
       
   152      * @param string|Zend_Locale $locale (Optional) Locale for number representation
       
   153      * @return integer|string
       
   154      */
       
   155     public function getValue($round = -1, $locale = null)
       
   156     {
       
   157         if ($round < 0) {
       
   158             $return = $this->_value;
       
   159         } else {
       
   160             $return = Zend_Locale_Math::round($this->_value, $round);
       
   161         }
       
   162 
       
   163         if ($locale !== null) {
       
   164             $this->setLocale($locale, true);
       
   165             return Zend_Locale_Format::toNumber($return, array('locale' => $locale));
       
   166         }
       
   167 
       
   168         return $return;
       
   169     }
       
   170 
       
   171     /**
       
   172      * Set a new value
       
   173      *
       
   174      * @param  integer|string      $value   Value as string, integer, real or float
       
   175      * @param  string              $type    OPTIONAL A measure type f.e. Zend_Measure_Length::METER
       
   176      * @param  string|Zend_Locale  $locale  OPTIONAL Locale for parsing numbers
       
   177      * @throws Zend_Measure_Exception
       
   178      * @return Zend_Measure_Abstract
       
   179      */
       
   180     public function setValue($value, $type = null, $locale = null)
       
   181     {
       
   182         if (($type !== null) and (Zend_Locale::isLocale($type, null, false))) {
       
   183             $locale = $type;
       
   184             $type = null;
       
   185         }
       
   186 
       
   187         if ($locale === null) {
       
   188             $locale = $this->_locale;
       
   189         }
       
   190 
       
   191         $this->setLocale($locale, true);
       
   192         if ($type === null) {
       
   193             $type = $this->_units['STANDARD'];
       
   194         }
       
   195 
       
   196         if (empty($this->_units[$type])) {
       
   197             require_once 'Zend/Measure/Exception.php';
       
   198             throw new Zend_Measure_Exception("Type ($type) is unknown");
       
   199         }
       
   200 
       
   201         try {
       
   202             $value = Zend_Locale_Format::getNumber($value, array('locale' => $locale));
       
   203         } catch(Exception $e) {
       
   204             require_once 'Zend/Measure/Exception.php';
       
   205             throw new Zend_Measure_Exception($e->getMessage(), $e->getCode(), $e);
       
   206         }
       
   207 
       
   208         $this->_value = $value;
       
   209         $this->setType($type);
       
   210         return $this;
       
   211     }
       
   212 
       
   213     /**
       
   214      * Returns the original type
       
   215      *
       
   216      * @return type
       
   217      */
       
   218     public function getType()
       
   219     {
       
   220         return $this->_type;
       
   221     }
       
   222 
       
   223     /**
       
   224      * Set a new type, and convert the value
       
   225      *
       
   226      * @param  string $type New type to set
       
   227      * @throws Zend_Measure_Exception
       
   228      * @return Zend_Measure_Abstract
       
   229      */
       
   230     public function setType($type)
       
   231     {
       
   232         if (empty($this->_units[$type])) {
       
   233             require_once 'Zend/Measure/Exception.php';
       
   234             throw new Zend_Measure_Exception("Type ($type) is unknown");
       
   235         }
       
   236 
       
   237         if (empty($this->_type)) {
       
   238             $this->_type = $type;
       
   239         } else {
       
   240             // Convert to standard value
       
   241             $value = $this->_value;
       
   242             if (is_array($this->_units[$this->getType()][0])) {
       
   243                 foreach ($this->_units[$this->getType()][0] as $key => $found) {
       
   244                     switch ($key) {
       
   245                         case "/":
       
   246                             if ($found != 0) {
       
   247                                 $value = call_user_func(Zend_Locale_Math::$div, $value, $found, 25);
       
   248                             }
       
   249                             break;
       
   250                         case "+":
       
   251                             $value = call_user_func(Zend_Locale_Math::$add, $value, $found, 25);
       
   252                             break;
       
   253                         case "-":
       
   254                             $value = call_user_func(Zend_Locale_Math::$sub, $value, $found, 25);
       
   255                             break;
       
   256                         default:
       
   257                             $value = call_user_func(Zend_Locale_Math::$mul, $value, $found, 25);
       
   258                             break;
       
   259                     }
       
   260                 }
       
   261             } else {
       
   262                 $value = call_user_func(Zend_Locale_Math::$mul, $value, $this->_units[$this->getType()][0], 25);
       
   263             }
       
   264 
       
   265             // Convert to expected value
       
   266             if (is_array($this->_units[$type][0])) {
       
   267                 foreach (array_reverse($this->_units[$type][0]) as $key => $found) {
       
   268                     switch ($key) {
       
   269                         case "/":
       
   270                             $value = call_user_func(Zend_Locale_Math::$mul, $value, $found, 25);
       
   271                             break;
       
   272                         case "+":
       
   273                             $value = call_user_func(Zend_Locale_Math::$sub, $value, $found, 25);
       
   274                             break;
       
   275                         case "-":
       
   276                             $value = call_user_func(Zend_Locale_Math::$add, $value, $found, 25);
       
   277                             break;
       
   278                         default:
       
   279                             if ($found != 0) {
       
   280                                 $value = call_user_func(Zend_Locale_Math::$div, $value, $found, 25);
       
   281                             }
       
   282                             break;
       
   283                     }
       
   284                 }
       
   285             } else {
       
   286                 $value = call_user_func(Zend_Locale_Math::$div, $value, $this->_units[$type][0], 25);
       
   287             }
       
   288 
       
   289             $slength = strlen($value);
       
   290             $length  = 0;
       
   291             for($i = 1; $i <= $slength; ++$i) {
       
   292                 if ($value[$slength - $i] != '0') {
       
   293                     $length = 26 - $i;
       
   294                     break;
       
   295                 }
       
   296             }
       
   297 
       
   298             $this->_value = Zend_Locale_Math::round($value, $length);
       
   299             $this->_type  = $type;
       
   300         }
       
   301         return $this;
       
   302     }
       
   303 
       
   304     /**
       
   305      * Compare if the value and type is equal
       
   306      *
       
   307      * @param  Zend_Measure_Abstract $object object to compare
       
   308      * @return boolean
       
   309      */
       
   310     public function equals($object)
       
   311     {
       
   312         if ((string) $object == $this->toString()) {
       
   313             return true;
       
   314         }
       
   315 
       
   316         return false;
       
   317     }
       
   318 
       
   319     /**
       
   320      * Returns a string representation
       
   321      *
       
   322      * @param  integer            $round  (Optional) Runds the value to an given exception
       
   323      * @param  string|Zend_Locale $locale (Optional) Locale to set for the number
       
   324      * @return string
       
   325      */
       
   326     public function toString($round = -1, $locale = null)
       
   327     {
       
   328         if ($locale === null) {
       
   329             $locale = $this->_locale;
       
   330         }
       
   331 
       
   332         return $this->getValue($round, $locale) . ' ' . $this->_units[$this->getType()][1];
       
   333     }
       
   334 
       
   335     /**
       
   336      * Returns a string representation
       
   337      *
       
   338      * @return string
       
   339      */
       
   340     public function __toString()
       
   341     {
       
   342         return $this->toString();
       
   343     }
       
   344 
       
   345     /**
       
   346      * Returns the conversion list
       
   347      *
       
   348      * @return array
       
   349      */
       
   350     public function getConversionList()
       
   351     {
       
   352         return $this->_units;
       
   353     }
       
   354 
       
   355     /**
       
   356      * Alias function for setType returning the converted unit
       
   357      *
       
   358      * @param  string             $type   Constant Type
       
   359      * @param  integer            $round  (Optional) Rounds the value to a given precision
       
   360      * @param  string|Zend_Locale $locale (Optional) Locale to set for the number
       
   361      * @return string
       
   362      */
       
   363     public function convertTo($type, $round = 2, $locale = null)
       
   364     {
       
   365         $this->setType($type);
       
   366         return $this->toString($round, $locale);
       
   367     }
       
   368 
       
   369     /**
       
   370      * Adds an unit to another one
       
   371      *
       
   372      * @param  Zend_Measure_Abstract $object object of same unit type
       
   373      * @return Zend_Measure_Abstract
       
   374      */
       
   375     public function add($object)
       
   376     {
       
   377         $object->setType($this->getType());
       
   378         $value  = $this->getValue(-1) + $object->getValue(-1);
       
   379 
       
   380         $this->setValue($value, $this->getType(), $this->_locale);
       
   381         return $this;
       
   382     }
       
   383 
       
   384     /**
       
   385      * Substracts an unit from another one
       
   386      *
       
   387      * @param  Zend_Measure_Abstract $object object of same unit type
       
   388      * @return Zend_Measure_Abstract
       
   389      */
       
   390     public function sub($object)
       
   391     {
       
   392         $object->setType($this->getType());
       
   393         $value  = $this->getValue(-1) - $object->getValue(-1);
       
   394 
       
   395         $this->setValue($value, $this->getType(), $this->_locale);
       
   396         return $this;
       
   397     }
       
   398 
       
   399     /**
       
   400      * Compares two units
       
   401      *
       
   402      * @param  Zend_Measure_Abstract $object object of same unit type
       
   403      * @return boolean
       
   404      */
       
   405     public function compare($object)
       
   406     {
       
   407         $object->setType($this->getType());
       
   408         $value  = $this->getValue(-1) - $object->getValue(-1);
       
   409 
       
   410         if ($value < 0) {
       
   411             return -1;
       
   412         } else if ($value > 0) {
       
   413             return 1;
       
   414         }
       
   415 
       
   416         return 0;
       
   417     }
       
   418 }