/classes/jigoshop_tax.class.php

https://github.com/steveclarkcouk/jigoshop · PHP · 265 lines · 120 code · 58 blank · 87 comment · 40 complexity · 0987627e6a3e08c8fb7c0169132176b8 MD5 · raw file

  1. <?php
  2. /**
  3. * Tax Class
  4. *
  5. * Calculates tax added value from a total
  6. *
  7. * DISCLAIMER
  8. *
  9. * Do not edit or add directly to this file if you wish to upgrade Jigoshop to newer
  10. * versions in the future. If you wish to customise Jigoshop core for your needs,
  11. * please use our GitHub repository to publish essential changes for consideration.
  12. *
  13. * @package Jigoshop
  14. * @category Checkout
  15. * @author Jigowatt
  16. * @copyright Copyright (c) 2011 Jigowatt Ltd.
  17. * @license http://jigoshop.com/license/commercial-edition
  18. */
  19. class jigoshop_tax {
  20. public $rates;
  21. /**
  22. * Get the current tax class
  23. *
  24. * @return array
  25. */
  26. function jigoshop_tax() {
  27. $this->rates = $this->get_tax_rates();
  28. }
  29. /**
  30. * Get an array of tax classes
  31. *
  32. * @return array
  33. */
  34. function get_tax_classes() {
  35. $classes = get_option('jigoshop_tax_classes');
  36. $classes = explode("\n", $classes);
  37. $classes = array_map('trim', $classes);
  38. $classes_array = array();
  39. if (sizeof($classes)>0) foreach ($classes as $class) :
  40. if ($class) $classes_array[] = $class;
  41. endforeach;
  42. return $classes_array;
  43. }
  44. /**
  45. * Get the tax rates as an array
  46. *
  47. * @return array
  48. */
  49. function get_tax_rates() {
  50. $tax_rates = get_option('jigoshop_tax_rates');
  51. $tax_rates_array = array();
  52. if ($tax_rates && is_array($tax_rates) && sizeof($tax_rates)>0) foreach( $tax_rates as $rate ) :
  53. if ($rate['class']) :
  54. $tax_rates_array[$rate['country']][$rate['state']][$rate['class']] = array( 'rate' => $rate['rate'], 'shipping' => $rate['shipping'] );
  55. else :
  56. // Standard Rate
  57. $tax_rates_array[$rate['country']][$rate['state']]['*'] = $rate['rate'] = array( 'rate' => $rate['rate'], 'shipping' => $rate['shipping'] );
  58. endif;
  59. endforeach;
  60. return $tax_rates_array;
  61. }
  62. /**
  63. * Searches for a country / state tax rate
  64. *
  65. * @param string country
  66. * @param string state
  67. * @param object Tax Class
  68. * @return int
  69. */
  70. function find_rate( $country, $state = '*', $tax_class = '' ) {
  71. $rate['rate'] = 0;
  72. if (isset($this->rates[ $country ][ $state ])) :
  73. if ($tax_class) :
  74. if (isset($this->rates[ $country ][ $state ][$tax_class])) :
  75. $rate = $this->rates[ $country ][ $state ][$tax_class];
  76. endif;
  77. else :
  78. $rate = $this->rates[ $country ][ $state ][ '*' ];
  79. endif;
  80. elseif (isset($this->rates[ $country ][ '*' ])) :
  81. if ($tax_class) :
  82. if (isset($this->rates[ $country ][ '*' ][$tax_class])) :
  83. $rate = $this->rates[ $country ][ '*' ][$tax_class];
  84. endif;
  85. else :
  86. $rate = $this->rates[ $country ][ '*' ][ '*' ];
  87. endif;
  88. endif;
  89. return $rate;
  90. }
  91. /**
  92. * Get the current taxation rate using find_rate()
  93. *
  94. * @param object Tax Class
  95. * @return int
  96. */
  97. function get_rate( $tax_class = '' ) {
  98. /* Checkout uses customer location, otherwise use store base rate */
  99. // if ( defined('JIGOSHOP_CHECKOUT') && JIGOSHOP_CHECKOUT ) :
  100. $country = jigoshop_customer::get_shipping_country();
  101. $state = jigoshop_customer::get_shipping_state();
  102. $rate = $this->find_rate( $country, $state, $tax_class );
  103. return $rate['rate'];
  104. // else :
  105. // return $this->get_shop_base_rate( $tax_class );
  106. // endif;
  107. }
  108. /**
  109. * Get the shop's taxation rate using find_rate()
  110. *
  111. * @param object Tax Class
  112. * @return int
  113. */
  114. function get_shop_base_rate( $tax_class = '' ) {
  115. $country = jigoshop_countries::get_base_country();
  116. $state = jigoshop_countries::get_base_state();
  117. $rate = $this->find_rate( $country, $state, $tax_class );
  118. return $rate['rate'];
  119. }
  120. /**
  121. * Get the tax rate based on the country and state
  122. *
  123. * @param object Tax Class
  124. * @return mixed
  125. */
  126. function get_shipping_tax_rate( $tax_class = '' ) {
  127. if (defined('JIGOSHOP_CHECKOUT') && JIGOSHOP_CHECKOUT) :
  128. $country = jigoshop_customer::get_country();
  129. $state = jigoshop_customer::get_state();
  130. else :
  131. $country = jigoshop_countries::get_base_country();
  132. $state = jigoshop_countries::get_base_state();
  133. endif;
  134. // If we are here then shipping is taxable - work it out
  135. if ($tax_class) :
  136. // This will be per item shipping
  137. $rate = $this->find_rate( $country, $state, $tax_class );
  138. if (isset($rate['shipping']) && $rate['shipping']=='yes') :
  139. return $rate['rate'];
  140. else :
  141. // Get standard rate
  142. $rate = $this->find_rate( $country, $state );
  143. if (isset($rate['shipping']) && $rate['shipping']=='yes') return $rate['rate'];
  144. endif;
  145. else :
  146. // This will be per order shipping - loop through the order and find the highest tax class rate
  147. $found_rates = array();
  148. $found_shipping_rates = array();
  149. // Loop cart and find the highest tax band
  150. if (sizeof(jigoshop_cart::$cart_contents)>0) : foreach (jigoshop_cart::$cart_contents as $item) :
  151. if ($item['data']->data['tax_class']) :
  152. $found_rate = $this->find_rate( $country, $state, $item['data']->data['tax_class'] );
  153. $found_rates[] = $found_rate['rate'];
  154. if (isset($found_rate['shipping']) && $found_rate['shipping']=='yes') $found_shipping_rates[] = $found_rate['rate'];
  155. endif;
  156. endforeach; endif;
  157. if (sizeof($found_rates) > 0 && sizeof($found_shipping_rates) > 0) :
  158. rsort($found_rates);
  159. rsort($found_shipping_rates);
  160. if ($found_rates[0] == $found_shipping_rates[0]) :
  161. return $found_shipping_rates[0];
  162. else :
  163. // Use standard rate
  164. $rate = $this->find_rate( $country, $state );
  165. if (isset($rate['shipping']) && $rate['shipping']=='yes') return $rate['rate'];
  166. endif;
  167. else :
  168. // Use standard rate
  169. $rate = $this->find_rate( $country, $state );
  170. if (isset($rate['shipping']) && $rate['shipping']=='yes') return $rate['rate'];
  171. endif;
  172. endif;
  173. return 0; // return false
  174. }
  175. /**
  176. * Calculate the tax using the final value
  177. *
  178. * @param int Price
  179. * @param int Taxation Rate
  180. * @return int
  181. */
  182. function calc_tax( $price, $rate, $price_includes_tax = true ) {
  183. // To avoid float rounding errors, work with integers (pence)
  184. $price = round($price * 100, 0);
  185. if ($price_includes_tax) :
  186. $price_excluding_tax = ($price / ( 1 + ($rate / 100)));
  187. $tax_amount = ($price - $price_excluding_tax);
  188. else :
  189. $tax_amount = $price * ($rate/100);
  190. endif;
  191. $tax_amount = $tax_amount / 100; // Back to pounds
  192. // use 4 decimal precision to avoid rounding errors:
  193. return number_format($tax_amount, 4, '.', '');
  194. }
  195. /**
  196. * Calculate the shipping tax using the final value
  197. *
  198. * @param int Price
  199. * @param int Taxation Rate
  200. * @return int
  201. */
  202. function calc_shipping_tax( $price, $rate ) {
  203. $rate = round($rate, 4);
  204. $tax_amount = $price * ($rate/100);
  205. return round($tax_amount, 2);
  206. }
  207. }