How to make a validation and a calculation on CCK multiple field
This is how you can add validation and a calculation on a CCK field programmatically. i have a CCK field (integer) with unlimited number of items allowed. User can add the time in different formats and I have a restriction on min 15 minutes. The allowed format is:
[numeric]h[numeric]m like 3h15m
[numeric]h like 2h
[numeric]m like 45m
[numeric] like 60
The value is converted to a numeric value representing minutes.
<?php
/**
* form alter hook
**/
function my_module_form_alter(&$form, &$form_state, $form_id) {
if (isset($form['body_field']['body']['#rows'])) {
$form['body_field']['body']['#rows'] = 5;
}
if ($form_id == "log_node_form") {
$form['#after_build'] = array('my_module_after_build');
}
}
/**
* after build function
**/
function my_module_after_build($form_element, &$form_state) {
//Remove pre set validation functions and set custom
foreach ($form_element['field_l_time'] as $key => $value) {
if (is_numeric($key)) {
unset($form_element['field_l_time'][$key]['#element_validate']);
$form_element['field_l_time'][$key]['#element_validate'][0] = 'my_module_validate_time';
}
}
return $form_element;
}
function my_module_validate_time($element, &$form_state) {
$field_name = $element['#field_name']; //field_l_time
$type_name = $element['#type_name']; //log
$field = content_fields($field_name, $type_name);
$field_key = $element['#columns'][0]; //value
$value = $element['#value'][$field_key]; //4h30m
$title = $field['widget']['label'];
if (!empty($value)) {
if (is_numeric($value)) {
if ($value < 15) {
$error_field = implode('][', $element['#parents']) .']['. $field_key;
form_set_error($error_field, t('%element must be more than 15 min. (1)', array('%element' => $title)));
}else{
form_set_value($element[$field_key], $value, $form_state);
}
}elseif (preg_match('/(^[0-9]{1,}h[0-9]{1,}m$)|(^[0-9]{1,}h$)|(^[0-9]{1,}m$)/i', $value)) {
$value = _calc_time_spent($value);
if ($value < 15) {
$error_field = implode('][', $element['#parents']) .']['. $field_key;
form_set_error($error_field, t('%element must be more than 15 min. (1)', array('%element' => $title)));
}else{
form_set_value($element[$field_key], $value, $form_state);
}
}else{
$error_field = implode('][', $element['#parents']) .']['. $field_key;
form_set_error($error_field, t('%element must be numeric or specified time format', array('%element' => $title)));
//form_error($element, t('%element must be numeric or specified time format', array('%element' => $title)));
//form_set_value($element, 0, $form_state);
$time_instructions = '<b>This is how you can specify time:</b>
<br>Numeric value: <i>15</i> for 15 minutes
<br>Formatted value: <i>15m</i> for 15 minutes
<br>Formatted value: <i>2h</i> for 2 hours
<br>Formatted value: <i>5h45m</i> for 5 hours and 45 minutes';
drupal_set_message(t($time_instructions));
}
}
return $element;
}
/**
* Converts formatted time to minutes
*
* @param unknown_type $timespent
* @return unknown
*/
function _calc_time_spent($timespent) {
$timespent = mb_strtolower($timespent);
if (stripos($timespent, "h") !== FALSE) {
$unit["h"] = "h";
}
if (stripos($timespent, "m") !== FALSE) {
$unit["m"] = "m";
}
$timespent = str_replace($unit, ":", $timespent);
$timespent = explode(":", $timespent);
if (is_numeric($timespent[0])) {
if (isset($unit["h"])) {
$minutes = $timespent[0]*60; //Hours
}else{
$minutes = $timespent[0]; //Minutes
}
}
if (is_numeric($timespent[1])) {
$minutes += $timespent[1]; //Minutes
}
return $minutes;
}
?>
Knowledge keywords: