Skip to content

Commit

Permalink
[Jobs] Adds dynamic price display to multiposting form (both summary …
Browse files Browse the repository at this point in the history
…and form display mode)
  • Loading branch information
TiSiE committed May 27, 2015
1 parent 48531c9 commit 60714bb
Show file tree
Hide file tree
Showing 9 changed files with 232 additions and 162 deletions.
101 changes: 81 additions & 20 deletions module/Jobs/public/js/form.multiposting-select.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,57 +13,118 @@
;
(function ($) {

var resultTmpl = null;
var selectTmpl = null;
var numberFormat = {
'delimiter': ',',
'decimal': '.'
};


function displayResult(item)
{
if (item.children) {
return item.text;
}

console.debug(item);
var data = parseTextToJson(item.text);
console.debug(data);
var data = $.fn.multipostingSelect.getOptionData(item.text);

var link = '<a href="' + data.link + '">' + data.linkText + '</a>';
var desc = data.desc.replace(/%s/, link);
data.desc = data.desc.replace(/%s/, link);

return $('<strong>' + data.name + ' - ' + data.headline + '</strong><br><small>' + desc + '</small>');
return tmpl(resultTmpl, data);
}

function displaySelection(item)
{
var data = parseTextToJson(item.text);
var data = $.fn.multipostingSelect.getOptionData(item.text);

return data.name + ' ( ' + data.duration + ' )';
return tmpl(selectTmpl, data);
}

function parseTextToJson(text)
function updatePrice(e)
{
var textArr = text.split('|');
var $select = $(e.target);
var selected = $select.find('option:selected');
var sum = $.fn.multipostingSelect.calculatePrice(selected);
var price = $.fn.multipostingSelect.formatPrice(sum, numberFormat);

$('#' + $select.attr('id') + '-total span').text(price);

return {
name: textArr[0],
headline: textArr[1],
desc: textArr[2],
linkText: textArr[3],
link: textArr[4],
duration: textArr[5]
};
}

function tmpl(template, vars)
{
for (var key in vars) {
var search = new RegExp('%' + key, 'gi');
template = template.replace(search, vars[key]);
}

return template;
}

$(function() {
var $select = $('#jobPortals-channel');
var $select = $('#jobPortals-portals');
var data = $select.data();
//var $eventSelect = $(".js-example-events");

// get templates
var id = $select.attr('id');
resultTmpl = $('span#' + id + '-result-tmpl').data('template');
selectTmpl = $('span#' + id + '-select-tmpl').data('template');
numberTmpl = $('span#' + id + '-currency-tmpl').data('template');
numberFormat.delimiter = numberTmpl.substr(1,1);
numberFormat.decimal = numberTmpl.substr(5,1);

$select.select2({
//allowClear: true,
placeholder: data.placeholder,
formatResult: displayResult,
formatSelection: displaySelection
});
console.debug($select);

$select.on("change", updatePrice);
$select.trigger('change');
});

$.fn.multipostingSelect = {};
$.fn.multipostingSelect.formatPrice = function(price, numberFormat)
{
price = price.toFixed(2)
.replace(".", numberFormat.decimal)
.replace(/(\d)(?=(\d{3})+(?!\d))/g, "$1" + numberFormat.delimiter);

return price;

};

$.fn.multipostingSelect.calculatePrice = function(selectedOptions)
{
var sum = 0;

for (var i= 0, c=selectedOptions.length; i<c; i+=1) {
var data = $.fn.multipostingSelect.getOptionData($(selectedOptions[i]).text());
sum += data.price;
}

return sum;
};

$.fn.multipostingSelect.getOptionData = function(text)
{
var textArr = text.split('|');

return {
name: textArr[0],
headline: textArr[1],
desc: textArr[2],
linkText: textArr[3],
link: textArr[4],
duration: textArr[5],
nicePrice: textArr[6],
price: parseFloat(textArr[7])

};
};

})(jQuery);

2 changes: 1 addition & 1 deletion module/Jobs/src/Jobs/Entity/Job.php
Original file line number Diff line number Diff line change
Expand Up @@ -261,7 +261,7 @@ class Job extends BaseEntity implements JobInterface, DraftableEntityInterface {
* Can contain various Portals
*
* @var array
* @ODM\Hash*/
* @ODM\Collection*/
protected $portals = array();

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,9 @@ public function createService(ServiceLocatorInterface $serviceLocator)
. $channel->getHeadLine() . '|'
. $channel->getDescription() . '|'
. $channel->getLinkText() . '|'
. $link . '|' . $channel->getPublishDuration();
. $link . '|' . $channel->getPublishDuration() . '|'
. $channel->getFormattedPrice() . '|'
. $channel->getPrice();
}


Expand Down
126 changes: 24 additions & 102 deletions module/Jobs/src/Jobs/Form/MultipostFieldset.php
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,17 @@

namespace Jobs\Form;

use Core\Entity\DraftableEntityInterface;
use Zend\Form\Fieldset;
use Core\Entity\Hydrator\EntityHydrator;
use Zend\Stdlib\ArrayUtils;
use Core\Form\ViewPartialProviderInterface;
use Core\Form\propagateAttributeInterface;

class MultipostFieldset extends Fieldset implements propagateAttributeInterface
/**
*
* @author Mathias Weitz <weitz@cross-solution.de>
* @author Mathias Gelhausen <gelhausen@cross-solution.de>
* @todo write test
*/
class MultipostFieldset extends Fieldset
{

public function getHydrator()
Expand All @@ -33,110 +37,28 @@ public function getHydrator()
*/
public function init()
{
$portals = $this->getFormFactory()->getFormElementManager()->getServiceLocator()->get('Jobs/Options/Provider');

$this->setAttribute('id', 'jobportals-fieldset');
$this->setName('jobPortals');


foreach ($portals as $key=>$portal) {
if (empty($portal->label)) {
throw new \RuntimeException('missing label');
}

$options=array(
'long_label' => $portal->description,
'headline' => $portal->headLine,
'linktext' => $portal->linkText,
'route' => $portal->route,
'params' => $portal->params,
'label' => $portal->label,
);

$this->add(
array(
// at some point we need an own Element for additional specific information like duration or premiums
// InfoCheckbox is just a surrogate
//'type' => 'Jobs/portalsElement',
'label' => $portal->label,
'type' => 'InfoCheckbox',
'property' => true,
'name' => $key,
'options' => $options,
'attributes' => array(
'data-trigger' => 'submit',
),
)
);
}
}

public function enableAll($enable = true)
{
foreach ($this as $forms) {
$forms->setAttribute('disabled', 'disabled');
}
return $this;
}

/**
* @return array
*/
protected function extract()
{
$object = $this->getObject();
$values = $object->getPortals();
$formValues = array();
foreach ($values as $key => $value) {
$formValues[$key] = $value['active'];
}
return $formValues;
}

public function bindValues(array $values = array())
{
$aggregateValues = $this->makeAggregateValues($values);
$object = $this->getObject();
$object->setPortals($aggregateValues);
return $this->object;
$this->add(
array(
'type' => 'Jobs\MultipostingSelect',
'property' => true,
'name' => 'portals',
'options' => array(
'label' => /*@translate*/ 'Portals',
),
)
);
}

/**
* usual this function should write all values into the
* @param array|\Traversable $data
* @throws \InvalidArgumentException
* @return void
*/
public function populateValues($data)
public function setObject($object)
{
if (!is_array($data) && !$data instanceof \Traversable) {
throw new \InvalidArgumentException(sprintf(
'%s expects an array or Traversable set of data; received "%s"',
__METHOD__,
(is_object($data) ? get_class($data) : gettype($data))
));
}

$aggregateValues = $this->makeAggregateValues($data);
}

public function makeAggregateValues($data)
{
$aggregateValues = array();
foreach ($data as $portalName => $portalValue) {
$valueExists = array_key_exists($portalName, $this->byName);
if (!$valueExists) {
# throw new Exception\InvalidArgumentException('value does not exist');
continue;
if ($object instanceOf DraftableEntityInterface && !$object->isDraft())
foreach ($this as $element) {
$element->setAttribute('disabled', 'disabled');
}

// set the element Values
// @TODO set the element values in populateValues (that means untwisting them there)
$element = $this->byName[$portalName];
$element->setValue($data[$portalName]);
$aggregateValues[$portalName] = array('active' => $portalValue, 'name' => $portalName);
}
return $aggregateValues;
return parent::setObject($object);
}

}
}
13 changes: 7 additions & 6 deletions module/Jobs/src/Jobs/Form/PreviewFieldset.php
Original file line number Diff line number Diff line change
Expand Up @@ -10,16 +10,16 @@

namespace Jobs\Form;

use Core\Entity\DraftableEntityInterface;
use Zend\Form\Fieldset;
use Core\Entity\Hydrator\EntityHydrator;
use Core\Form\propagateAttributeInterface;

/**
* Defines the formular files of the 3rd formular for entering a job opening
*
* @package Jobs\Form
*/
class PreviewFieldset extends Fieldset implements propagateAttributeInterface
class PreviewFieldset extends Fieldset
{
public function getHydrator()
{
Expand Down Expand Up @@ -54,11 +54,12 @@ public function init()

}

public function enableAll($enable = true)
public function setObject($object)
{
foreach ($this as $forms) {
$forms->setAttribute('disabled', 'disabled');
if ($object instanceOf DraftableEntityInterface && !$object->isDraft())
foreach ($this as $element) {
$element->setAttribute('disabled', 'disabled');
}
return $this;
return parent::setObject($object);
}
}
18 changes: 18 additions & 0 deletions module/Jobs/src/Jobs/Options/ChannelOptions.php
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,24 @@ public function getKey()
return $this->key;
}

public function getFormattedPrice($currencyPosition = 'right')
{

$price = sprintf('%01.2f', $this->getPrice());

if ('none' === $currencyPosition) {
return $price;
}

$currency = $this->getCurrency();

if ('left' == $currencyPosition) {
return $currency . ' ' . $price;
}

return $price . ' ' . $currency;
}

/**
* Gets the price of a channel
*
Expand Down
Loading

0 comments on commit 60714bb

Please sign in to comment.