PluginProbe
Contact Forms by Cimatti / 1.3
Contact Forms by Cimatti v1.3
2.3.6 2.3.5 2.3.0 2.2.32 2.2.4 2.2.0 2.1.2 2.1.1 trunk 1.0 1.1 1.2 1.2.1 1.3 1.3.1 1.3.2 1.3.3 1.3.4 1.3.5 1.3.6 1.3.7 1.3.8 1.3.9 1.4.0 1.4.1 All 62 releases
contact-forms / AccuaForm.php

AccuaForm.php in Contact Forms by Cimatti 1.3, at AccuaForm.php

1,016 lines 32.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 class AccuaForm extends Form {
3 protected static $submitted = null;
4 protected static $valid = null;
5 protected static $submittedID = null;
6 protected static $submittedBuildID = null;
7 protected static $submittedForm = null;
8 protected static $submittedFormUsed = false;
9 protected static $submittedData = null;
10 protected static $rawData = null;
11 protected static $submittedMessages = '';
12
13 protected $formID = null;
14 protected $buildID = null;
15 protected $validate_functions = array();
16 protected $submit_functions = array();
17 protected $elements_sleep;
18 public $stats = array();
19 protected $accua_ajax;
20 protected $locale = null;
21 protected $language = null;
22 protected $files = array();
23
24 protected $original_locale = null;
25 protected $original_language = null;
26 protected $original_l10n = null;
27 protected $forced_language = false;
28 protected $elementsByName = array();
29
30 public function force_language() {
31 if ((!$this->forced_language) && $this->language && function_exists('qtrans_getLanguage')) {
32 global $q_config;
33 $this->original_language = $q_config['language'];
34
35 if ($this->language != $this->original_language) {
36 $this->original_locale =& $GLOBALS['wp_locale'];
37 $this->original_l10n =& $GLOBALS['l10n'];
38
39 unset($GLOBALS['wp_locale']);
40 unset($GLOBALS['l10n']);
41 $GLOBALS['l10n'] = array();
42
43 $GLOBALS['q_config']['language'] = $this->language;
44 load_default_textdomain();
45 load_plugin_textdomain( 'accua-form-api', false, ACCUA_FORM_API_PLUGIN_TEXTDOMAIN_PATH);
46 require_once( ABSPATH . WPINC . '/locale.php' );
47 $GLOBALS['wp_locale'] =& new WP_Locale();
48 $GLOBALS['wp_locale']->register_globals();
49
50 $this->forced_language = true;
51 }
52 }
53 }
54
55 public function restore_language() {
56 if ($this->forced_language) {
57 unset($GLOBALS['wp_locale']);
58 unset($GLOBALS['l10n']);
59
60 $GLOBALS['q_config']['language'] = $this->original_language;
61 $GLOBALS['l10n'] =& $this->original_l10n;
62 $GLOBALS['wp_locale'] =& $this->original_locale;
63 if ($GLOBALS['wp_locale']) {
64 $GLOBALS['wp_locale']->register_globals();
65 }
66
67 $this->forced_language = false;
68 }
69 }
70
71 public function __sleep() {
72 $this->elements_sleep = $this->getElements();
73 return array('attributes', 'elements_sleep', 'error', 'view', 'prefix', 'widthSuffix', 'ajax', 'ajaxCallback', 'attributes', 'jQueryUITheme', 'resourcesPath', 'prevent', 'width', 'formID', 'buildID', 'validate_functions', 'submit_functions', 'stats', 'accua_ajax', 'locale', 'language', 'files');
74 }
75
76 public function __wakeup() {
77 foreach ($this->elements_sleep as $element) {
78 $this->addElement($element);
79 }
80 unset($this->elements_sleep);
81 if ($this->view) {
82 $this->view->setForm($this);
83 }
84 if ($this->error) {
85 $this->error->setForm($this);
86 }
87 }
88
89 public function addElement($element) {
90 $name = $element->getName();
91 if ($name) {
92 $this->elementsByName[$name] = $element;
93 }
94 return parent::addElement($element);
95 }
96
97 public function getElementByName($name) {
98 if (isset($this->elementsByName[$name])) {
99 return $this->elementsByName[$name];
100 } else {
101 return null;
102 }
103 }
104
105 public static function sessionID() {
106 $sessionid = session_id();
107 if ($sessionid === '') {
108 session_start();
109 $sessionid = session_id();
110 }
111 return $sessionid;
112 }
113
114 public static function getBaseURL() {
115 static $ret = null;
116 if ($ret === null) {
117 $s = empty($_SERVER["HTTPS"]) ? '' : ($_SERVER["HTTPS"] == "on") ? "s" : "";
118 $sp = strtolower($_SERVER["SERVER_PROTOCOL"]);
119 $protocol = substr($sp, 0, strpos($sp, "/")) . $s;
120 $port = ($_SERVER["SERVER_PORT"] == "80") ? "" : (":".$_SERVER["SERVER_PORT"]);
121 $ret = $protocol . "://" . $_SERVER['SERVER_NAME'] . $port;
122 }
123 return $ret;
124 }
125
126 public static function create($baseid = 'pfbc', $params = array()) {
127 if (self::isSubmit() && (!self::isValid()) && ($baseid === self::$submittedID) && (!self::$submittedFormUsed)) {
128 self::$submittedFormUsed = true;
129 if (!(self::isValid() || empty(self::$submittedForm))) {
130 $form = self::$submittedForm;
131 $form->setValues(self::$submittedData);
132 return $form;
133 }
134 $form = new AccuaForm ($baseid, $params, self::$submittedBuildID);
135 $form->setValues(self::$submittedData);
136 } else {
137 $form = new AccuaForm($baseid, $params);
138 }
139 if (function_exists($baseid)) {
140 call_user_func($baseid, $form);
141 }
142 do_action('accua_form_alter', $baseid, $form);
143 return $form;
144 }
145
146 function __construct($id = 'pfbc', $params = array(), $buildid = '') {
147 if ($buildid === '') {
148 $buildid = 'accua-form_' . $id . '_' . uniqid();
149 }
150
151 if (is_array($params)) {
152 $params += array(
153 'width' => '',
154 'layout' => 'sidebyside',
155 );
156 //$width = $params['width'];
157 } else {
158 //$width = $params;
159 $params = array(
160 //'width' => $width,
161 'layout' => 'sidebyside',
162 );
163 }
164 $class = 'accua-form ' . $id;
165 switch ($params['layout']) {
166 case 'toplabel':
167 $this->view = new AccuaForm_View_Standard();
168 $class .= ' accua-form-view-standard';
169 break;
170 case 'sidebyside':
171 default:
172 $this->view = new AccuaForm_View_SideBySide(
173 '19',
174 array('labelPaddingRight' => '1')
175 );
176 $class .= ' accua-form-view-sidebyside';
177 }
178 $this->error = new AccuaForm_Error_Standard(array(
179 'errorfound' => '',
180 'errorsfound' => '',
181 ));
182 if ($width === ""){
183 $width = "100%";
184 }
185 $this->attributes = array(
186 'class' => $class,
187 'novalidate' => 'novalidate',
188 );
189
190 parent::__construct($buildid, $width);
191
192
193 $this->formID = $id;
194 $this->buildID = $buildid;
195 $this->addElement(new Element_Hidden('_AccuaForm_ID', $id));
196 $this->addElement(new Element_Hidden('_AccuaForm_buildID', $buildid));
197 $this->addElement(new Element_Hidden('_AccuaForm_wpnonce', wp_create_nonce( $buildid )));
198 $this->addElement(new Element_Hidden('_AccuaForm_jsuuid', ''));
199 $this->addElement(new Element_Hidden('_AccuaForm_referrer', ''));
200 $this->addElement(new Element_Hidden('_AccuaForm_user_agent', ''));
201 $this->addElement(new Element_Hidden('_AccuaForm_platform', ''));
202 $this->addElement(new Element_Hidden('_AccuaForm_tentatives', '0'));
203 $this->addElement(new Element_Hidden('_AccuaForm_submit_method', 'normal'));
204 $this->addElement(new Element_Hidden('_AccuaForm_hash', ''));
205 $this->addElement(new Element_Hidden('_AccuaForm_iv', ''));
206 $this->addElement(new Element_Hidden('_AccuaForm_data', ''));
207 /*
208 * - Prima di generare l'html del form, salva una copia serializzata compreso di codice SHA2, criptato, in _AccuaForm_serialized
209 * - Quando ricevi il form, decripta _AccuaForm_serialized e controlla che sia valido
210 *
211 * */
212
213 //$this->addElement(new Element_Hidden('PHPSESSID', self::sessionID()));
214 $this->prevent = array('jQuery', 'jQueryUI', 'jQueryUIButtons', 'focus', 'style');
215 $this->configure(array('action' => ''));
216
217 if (function_exists('qtrans_getLanguage')) {
218 $this->language = qtrans_getLanguage();
219 $this->locale = $GLOBALS['q_config']['locale'][$this->language];
220 } else {
221 $this->locale = get_locale();
222 $this->language = explode('_', $this->locale);
223 $this->language = $this->language[0];
224 }
225
226 global $post;
227 $pid = empty($post->ID) ? 0 : $post->ID;
228
229 $uri = isset($GLOBALS['q_config']['url_info']['original_url']) ? $GLOBALS['q_config']['url_info']['original_url'] : $_SERVER['REQUEST_URI'];
230
231 $url = self::getBaseURL() . $uri ;
232
233 $this->stats = array(
234 'pid' => $pid,
235 'ip' => $_SERVER['REMOTE_ADDR'], //updated after submit
236 'original_ip' => $_SERVER['REMOTE_ADDR'], //unreliable if using a static page caching system
237 'uri' => $uri,
238 'url' => $url,
239 'referrer' => $_SERVER['HTTP_REFERER'], //updated after submit using javascript
240 'original_referrer' => $_SERVER['HTTP_REFERER'], //unreliable if using a static page caching system
241 'lang' => $this->language,
242 'locale' => $this->locale,
243 'created' => time(),
244 'submitted' => null,
245 'user_agent' => '',
246 'platform' => '',
247 'tentatives' => '',
248 'submit_method' => '',
249 );
250
251 $this->view->setForm($this);
252 $this->error->setForm($this);
253 }
254
255 public static function isSubmit() {
256 if (self::$submitted !== null) {
257 return self::$submitted;
258 }
259 self::$submitted = false;
260 $sessid = self::sessionID();
261
262 if($_SERVER['REQUEST_METHOD'] == 'POST') {
263 self::$rawData = stripslashes_deep($_POST);
264 } else {
265 self::$rawData = stripslashes_deep($_GET);
266 }
267
268 if (empty(self::$rawData['_AccuaForm_ID']) || empty(self::$rawData['_AccuaForm_buildID']) || empty(self::$rawData['_AccuaForm_wpnonce']) /* || empty(self::$rawData['PHPSESSID']) */
269 || empty(self::$rawData['_AccuaForm_hash']) || empty(self::$rawData['_AccuaForm_iv']) || empty(self::$rawData['_AccuaForm_data'])) {
270 return false;
271 }
272
273 /*
274 if (self::$rawData['PHPSESSID'] !== $sessid) {
275 return false;
276 }
277 */
278
279 $id = self::$rawData['_AccuaForm_buildID'];
280 $form = self::wp_recover(self::$rawData['_AccuaForm_hash'], self::$rawData['_AccuaForm_iv'], self::$rawData['_AccuaForm_data']);
281
282 if (empty($form)) {
283 return false;
284 }
285
286 if ($form->formID !== self::$rawData['_AccuaForm_ID'] || $form->buildID !== $id ) {
287 return false;
288 }
289
290 /*
291 if (!wp_verify_nonce(self::$rawData['_AccuaForm_wpnonce'], $id)) {
292 return false;
293 }
294 */
295
296 /* check if already submitted from uuid and other parameters */
297 $already_submitted = false;
298 if (!empty(self::$rawData['_AccuaForm_jsuuid'])) {
299 if (preg_match("/^[a-z0-9]{25}$/", self::$rawData['_AccuaForm_jsuuid'])) {
300 $already_submitted_data = get_transient('accuaformsub_'.self::$rawData['_AccuaForm_jsuuid']);
301 if ($already_submitted_data && $already_submitted_data['buildID'] == $form->buildID) {
302 $form = $already_submitted_data['form'];
303 self::$submittedMessages = $already_submitted_data['submittedMessages'];
304 self::$valid = true;
305 $already_submitted = true;
306 }
307 } else {
308 return false;
309 }
310 }
311
312 if (!$already_submitted) {
313 $form->stats['submitted'] = time();
314 $form->stats['ip'] = $_SERVER['REMOTE_ADDR'];
315 $form->stats['referrer'] = self::$rawData['_AccuaForm_referrer'];
316 $form->stats['jsuuid'] = self::$rawData['_AccuaForm_jsuuid'];
317 $form->stats['user_agent'] = self::$rawData['_AccuaForm_user_agent'];
318 $form->stats['platform'] = self::$rawData['_AccuaForm_platform'];
319 $form->stats['tentatives'] = self::$rawData['_AccuaForm_tentatives'];
320 $form->stats['submit_method'] = self::$rawData['_AccuaForm_submit_method'];
321 }
322 self::$submitted = true;
323 self::$submittedID = $form->formID;
324 self::$submittedBuildID = $form->buildID;
325 self::$submittedForm = $form;
326 return true;
327 }
328
329 public static function isValid() {
330 if (!self::isSubmit()){
331 return null;
332 }
333 if (self::$valid !== null) {
334 return self::$valid;
335 }
336
337 //$subdata = array();
338 $id = self::$submittedBuildID;
339 //$form = self::wp_recover($id);
340 $form = self::$submittedForm;
341 $valid = true;
342
343 $form->force_language();
344
345 /*Any values/errors stored in the session for this form are cleared.*/
346 self::clearValues($id);
347 self::clearErrors($id);
348
349 self::$submittedData = array();
350 /*Each element's value is saved in the session and checked against any validation rules applied
351 to the element.*/
352 $elements = $form->getElements();
353 if(!empty($elements)) {
354 foreach($elements as $element) {
355 $invalidFile = false;
356 $name = $element->getName();
357 if(substr($name, -2) == "[]") {
358 $name = substr($name, 0, -2);
359 }
360
361 /*The File element must be handled differently b/c it uses the $_FILES superglobal and
362 not $_GET or $_POST.*/
363 if($element instanceof AccuaForm_Element_File) {
364 if (!empty($form->files[$name]['name'])) {
365 $value = $form->files[$name]['name'];
366 } else if ((!empty($_FILES[$name])) && ($_FILES[$name]['error'] != UPLOAD_ERR_NO_FILE)) {
367 //$file = $_FILES[$name];
368 //include_once( ABSPATH . '/wp-admin/includes/file.php' );
369 //$overrides = array( 'test_form' => false );
370 //$file = wp_handle_upload( $file, $overrides );
371
372 $file = $element->handle_upload($_FILES[$name]);
373 $value = $file['name'];
374
375 if (empty($file['errors'])) {
376 $form->files[$name] = $file;
377 } else {
378 self::setError($id, $file['errors'] , $name);
379 $valid = false;
380 $invalidFile = true;
381 }
382 } else {
383 $value = null;
384 }
385 } else if ($element instanceof Element_File){
386 $value = $_FILES[$name]["name"];
387 } else if (isset(self::$rawData[$name])) {
388 $value = self::$rawData[$name];
389 if(is_array($value)) {
390 foreach($value as $key => $value_i) {
391 $value[$key] = (string) $value_i;
392 }
393 } else {
394 $value = (string) $value;
395 }
396 } else {
397 $value = null;
398 }
399
400 //self::setSessionValue($id, $name, $value);
401
402 /*If a validation error is found, the error message is saved in the session along with
403 the element's name.*/
404 if(!$element->isValid($value)) {
405 self::setError($id, $element->getErrors(), $name);
406 $valid = false;
407 if ($element instanceof AccuaForm_Element_File) {
408 $invalidFile = true;
409 }
410 }
411
412 if($invalidFile) {
413 if (isset($file['tmp_name'])) {
414 unlink($element->getDestPath . $file['tmp_name']);
415 unset($form->files[$name]);
416 }
417 } else if($name !== '') {
418 self::$submittedData[$name] = $value;
419 }
420 }
421 }
422 $_SESSION["pfbc"][$id]["values"] = self::$submittedData;
423
424
425 if (function_exists(self::$submittedID.'_validate')) {
426 $valid = call_user_func(self::$submittedID.'_validate', $valid, self::$submittedID, self::$submittedData, $form);
427 }
428 $valid = apply_filters('accua_form_validate', $valid, self::$submittedID, self::$submittedData, $form);
429
430 asort($form->validate_functions);
431 foreach($form->validate_functions as $func => $priority){
432 if (function_exists($func)) {
433 $valid = call_user_func($func, $valid, self::$submittedID, self::$submittedData, $form);
434 }
435 }
436
437 if ($valid) {
438 if (function_exists(self::$submittedID.'_submit')) {
439 call_user_func(self::$submittedID.'_submit', self::$submittedID, self::$submittedData, $form);
440 }
441 do_action('accua_form_submit', self::$submittedID, self::$submittedData, $form);
442 asort($form->submit_functions);
443 foreach($form->submit_functions as $func => $priority){
444 if (function_exists($func)) {
445 call_user_func($func, self::$submittedID, self::$submittedData, $form);
446 }
447 }
448 }
449
450 /*If no validation errors were found, the form's session values are cleared.*/
451 /*
452 if($valid) {
453 if($clearValues)
454 self::clearValues($id);
455 self::clearErrors($id);
456 }
457 */
458
459 //TODO: Should i save here?
460 //$form->save();
461 //$_SESSION["pfbc"][$id]["form"] = serialize($form);
462
463 $form->restore_language();
464
465 if ($valid && self::$rawData['_AccuaForm_jsuuid'] ) {
466 set_transient('accuaformsub_'.self::$rawData['_AccuaForm_jsuuid'], array(
467 'buildID' => self::$submittedBuildID,
468 'form' => self::$submittedForm,
469 'submittedMessages' => self::$submittedMessages,
470 ), 86400);
471 }
472
473 return self::$valid = (bool)$valid;
474 }
475
476 public static function getSubmittedData() {
477 self::isValid();
478 return self::$submittedData;
479 }
480
481 public static function getSumbittedID() {
482 trigger_error('Use getSubmittedID() instead', (defined('E_USER_DEPRECATED')?E_USER_DEPRECATED:E_USER_NOTICE));
483 return self::getSubmittedID();
484 }
485
486 public static function getSubmittedID() {
487 if (self::isSubmit()) {
488 return self::$submittedID;
489 } else {
490 return null;
491 }
492 }
493
494 public static function getSubmittedForm() {
495 if (self::isSubmit()) {
496 return self::$submittedForm;
497 } else {
498 return null;
499 }
500 }
501
502 /*This method restores the serialized form instance.*/
503 protected static function wp_recover($hash,$iv,$data) {
504 /*
505 if(!empty($_SESSION["pfbc"][$id]["form"]))
506 return unserialize($_SESSION["pfbc"][$id]["form"]);
507 */
508 /*
509 $storename = 'accua_form_' . md5($id);
510 if ($stored = get_transient($storename)) {
511 return unserialize($stored);
512 }
513 */
514
515 $keys = get_option('accua_form_api_keys', array());
516 @ $hash = base64_decode($hash);
517 @ $iv = base64_decode($iv);
518 @ $data = base64_decode($data);
519
520 if (!($hash && $iv && $data)) {
521 return;
522 }
523
524 if (!class_exists('Crypt_Hash')) {
525 require_once('phpseclib-crypt/Hash.php');
526 }
527 $hasher = new Crypt_Hash('sha1');
528 $hasher->setKey($keys['hash']);
529 @ $hash2 = $hasher->hash($iv.$data);
530
531 if ($hash !== $hash2) {
532 return;
533 }
534
535 if (!class_exists('Crypt_AES')) {
536 require_once('phpseclib-crypt/AES.php');
537 }
538
539 $cipher = new Crypt_AES();
540 $cipher->setPassword($keys['aes']);
541 @ $cipher->setIV($iv);
542 @ $data = $cipher->decrypt($data);
543
544 if ($data) {
545 @ $form = unserialize($data);
546 if ($form) {
547 return $form;
548 }
549 }
550 }
551
552 protected function wp_save() {
553 /*
554 $storename = 'accua_form_' . md5($this->buildID);
555 //$serialized = isset($_SESSION["pfbc"][$this->buildID]["form"]) ? $_SESSION["pfbc"][$this->buildID]["form"] : serialize($this);
556 $serialized = serialize($this);
557 set_transient($storename, $serialized, 2764800); // 32 days
558 */
559
560 if (!class_exists('Crypt_Hash')) {
561 require_once('phpseclib-crypt/Hash.php');
562 }
563 if (!class_exists('Crypt_AES')) {
564 require_once('phpseclib-crypt/AES.php');
565 }
566
567 $keys = get_option('accua_form_api_keys', array());
568 if (!(isset($keys['aes']) && isset($keys['hash']))) {
569 accua_form_api_install();
570 $keys = get_option('accua_form_api_keys', array());
571 }
572
573 $data = serialize($this);
574 $iv = wp_generate_password(64,true,true);
575
576 $cipher = new Crypt_AES();
577 $cipher->setPassword($keys['aes']);
578 $cipher->setIV($iv);
579 $data = $cipher->encrypt($data);
580
581 $hasher = new Crypt_Hash('sha1');
582 $hasher->setKey($keys['hash']);
583 $hash = $hasher->hash($iv.$data);
584
585 $ret = array(
586 '_AccuaForm_hash' => base64_encode($hash),
587 '_AccuaForm_iv' => base64_encode($iv),
588 '_AccuaForm_data' => base64_encode($data),
589 );
590 if (isset($_SESSION["pfbc"][$this->buildID]["values"])) {
591 $_SESSION["pfbc"][$this->buildID]["values"] = $ret + $_SESSION["pfbc"][$this->buildID]["values"];
592 }
593 $this->setValues($ret);
594 return $ret;
595 }
596
597 public function getLocale() {
598 return $this->locale;
599 }
600
601 public function getLanguage() {
602 return $this->language;
603 }
604
605 public function addValidateFunction($function_name, $priority = 0) {
606 $this->validate_functions[$function_name] = $priority;
607 }
608
609 public function addSubmitFunction($function_name, $priority = 0) {
610 $this->submit_functions[$function_name] = $priority;
611 }
612
613 public function getSubmittedMessages(){
614 return self::$submittedMessages;
615 }
616
617 public function setSubmittedMessages($msg){
618 return self::$submittedMessages = $msg;
619 }
620
621 public function appendSubmittedmessages($msg){
622 return self::$submittedMessages .= $msg;
623 }
624
625 public function render($returnHTML = false) {
626 $this->wp_save();
627 if($returnHTML) {
628 ob_start();
629 }
630 parent::render(false);
631 if (!empty($this->accua_ajax)) {
632 $ajax_url = json_encode(admin_url('admin-ajax.php?action=accua_form_submit'));
633 $submit_fail_message = json_encode(__('Unable to submit the form, please retry', 'accua-form-api'));
634 $required_message = json_encode(__('Please fill in all required fields', 'accua-form-api'));
635 $valid_mail_message = json_encode(__('You have to enter a valid email address where required', 'accua-form-api'));
636 $js_buildid = preg_replace('/[^a-zA-Z0-9_]/m','_',$this->buildID);
637 $formid = $this->getId();
638 $hostname = json_encode($_SERVER['SERVER_NAME']);
639
640 $post_url = json_encode($this->stats['url']);
641
642
643 echo <<<JS
644 <script type="text/javascript">
645 //<![CDATA[
646 var _handle_ajax_submit_{$js_buildid} = function() {return true;}
647 var _handle_ajax_submit_complete_{$js_buildid} = function() {return false;}
648 var _handle_ajax_submit_timeout_{$js_buildid} = function() {return false;}
649 var _handle_ajax_submit_message_{$js_buildid} = function() {}
650 var _handle_ajax_submit_response_{$js_buildid} = function() {}
651
652 jQuery(function($) {
653 var thisform = $("#{$this->buildID}");
654 var ajax_enabled = {$hostname} == location.hostname ;
655
656 var response_messages = $("#_response_messages_{$this->buildID}");
657 if (! response_messages.length) {
658 response_messages = $("<div id='_response_messages_{$this->buildID}' class='accua-form-messages'></div>");
659 $("#{$this->buildID}").before(response_messages);
660 }
661 var throbbler = $("<span class='accua_form_api_throbbler'></span>");
662
663 var _ajax_submitting_{$js_buildid} = false;
664 var timeout_handler = false;
665 var timeout_count = 0;
666 var fail_count = 0;
667 var disabled_fields = false;
668
669 var jsuuid_field = $('input[name="_AccuaForm_jsuuid"]', thisform);
670 var jsuuid = jsuuid_field.val();
671 if (jsuuid == '') {
672 var chars = '0123456789abcdefghijklmnopqrstuvwxyz'.split('');
673 var radix = chars.length
674 for (i = 0; i < 25; i++) {
675 jsuuid += chars[0 | Math.random()*radix];
676 }
677 jsuuid_field.val(jsuuid);
678 }
679
680 _handle_ajax_submit_{$js_buildid} = function() {
681 if (_ajax_submitting_{$js_buildid}) {
682 return false;
683 }
684
685 JS;
686 $this->error->clear();
687 echo <<<JS
688
689 var valid_empty = true;
690 var valid_mail = true;
691
692 $("#{$this->buildID} .pfbc-element").removeClass('pfbc-invalid');
693
694 $('.accuaforms-field-required', thisform).each(function(){
695 var field = $(this);
696
697 if (field.attr('type') === 'checkbox') {
698 if (field.is(':checked')) {
699 return true;
700 }
701 } else {
702 if (! field.val().match(/^\s*$/)) {
703 return true;
704 }
705 }
706
707 valid_empty = false;
708 field.parents("#{$this->buildID} .pfbc-element").addClass('pfbc-invalid');
709 });
710
711 $('.pfbc-textbox[type="email"]', thisform).each(function(){
712 var field = $(this);
713
714 if (field.val().match(/^\s*$/)) {
715 return true;
716 }
717
718 if (field.val().match( /^([a-zA-Z0-9_.+%-])+@(([a-zA-Z0-9-])+\.)+([a-zA-Z0-9])+$/ )) {
719 return true;
720 }
721
722 valid_mail = false;
723 field.parents("#{$this->buildID} .pfbc-element").addClass('pfbc-invalid');
724
725 });
726
727 if (valid_empty && valid_mail) {
728 thisform.append(throbbler);
729 _ajax_submitting_{$js_buildid} = true;
730 $('input[name="_AccuaForm_tentatives"]', thisform).val(fail_count);
731 disabled_fields = $("input, textarea, button, select").not('[type="submit"]').not(':disabled');
732 disabled_fields.attr('readonly','readonly');
733 timeout_count = 0;
734 if (ajax_enabled) {
735 $("#submit_target_{$js_buildid}").attr('src','').removeAttr('src');
736 timeout_handler = setTimeout(_handle_ajax_submit_timeout_{$js_buildid}, 5000);
737 }
738 return true;
739 } else {
740 var message = '';
741 if (!valid_empty) {
742 message += $required_message + '<br />';
743 }
744 if (!valid_mail) {
745 message += $valid_mail_message + '<br />';
746 }
747 thisform.append('<div class="pfbc-error ui-state-error ui-corner-all">' + message + '</div>');
748 return false;
749 }
750 }
751
752
753 _handle_ajax_submit_timeout_{$js_buildid} = function() {
754 if (_ajax_submitting_{$js_buildid}) {
755 if (timeout_count < 60) {
756 timeout_count++;
757 timeout_handler = setTimeout(_handle_ajax_submit_timeout_{$js_buildid}, 500);
758 _handle_ajax_submit_complete_{$js_buildid}();
759 } else {
760 timeout_handler = false;
761 _handle_ajax_submit_complete_{$js_buildid}();
762 if (_ajax_submitting_{$js_buildid}) {
763 _handle_ajax_submit_response_{$js_buildid}(false);
764 }
765 }
766 }
767 }
768
769 _handle_ajax_submit_complete_{$js_buildid} = function() {
770 if (_ajax_submitting_{$js_buildid}) {
771 var response = false;
772 try {
773 var responsedoc = frames['submit_target_{$js_buildid}'].document;
774 if (responsedoc.getElementById("accua-form-ajax-response-loaded")) {
775 response = $.parseJSON(responsedoc.getElementById("accua-form-ajax-response").innerHTML);
776 }
777 } catch (err) {
778 response = false;
779 }
780 if (response) {
781 return _handle_ajax_submit_response_{$js_buildid} (response);
782 }
783 }
784 }
785
786 _handle_ajax_submit_message_{$js_buildid} = function(message) {
787 if (_ajax_submitting_{$js_buildid}) {
788 var response = false;
789 try {
790 response = $.parseJSON(message.data);
791 if (response.jsuuid != jsuuid || response.buildID != "{$this->buildID}") {
792 response = false;
793 }
794 } catch (err) {
795 response = false;
796 }
797 if (response) {
798 return _handle_ajax_submit_response_{$js_buildid} (response);
799 }
800 }
801 }
802
803 _handle_ajax_submit_response_{$js_buildid} = function(response) {
804 if (_ajax_submitting_{$js_buildid}) {
805 if(response && typeof(response) == "object" && typeof(response.submitted) == "boolean") {
806 response_messages.html(response.messages);
807 if (response.submitted) {
808 if (response.valid) {
809 JS;
810 /*A callback function can be specified to handle any post submission events.*/
811 if(!empty($this->ajaxCallback)) {
812 echo $this->ajaxCallback, "(response);";
813 } else {
814 echo "$('#{$this->buildID}').hide();";
815 }
816 echo <<<JS
817 } else {
818 JS;
819 $this->error->applyAjaxErrorResponse();
820 echo <<<JS
821
822 for (var name in response.files) {
823 $(".pfbc-fieldwrap:has(input[type='file'][name='"+name+"'])", thisform).html(response.files[name]);
824 }
825
826 $("input[name='_AccuaForm_hash']",thisform).val(response._AccuaForm_hash);
827 $("input[name='_AccuaForm_iv']", thisform).val(response._AccuaForm_iv);
828 $("input[name='_AccuaForm_data']",thisform).val(response._AccuaForm_data);
829
830 disabled_fields.removeAttr('readonly');
831 }
832 }
833 } else {
834 fail_count++;
835 if (fail_count > 2) {
836 ajax_enabled = false;
837 thisform.attr("action", {$post_url} );
838 thisform.removeAttr("target");
839 $('input[name="_AccuaForm_submit_method"]', thisform).val('fallback');
840 }
841 thisform.append('<div class="pfbc-error ui-state-error ui-corner-all">' + $submit_fail_message + '</div>');
842 }
843 throbbler.remove();
844 _ajax_submitting_{$js_buildid} = false;
845 if (timeout_handler) {
846 clearTimeout(timeout_handler);
847 timeout_handler = false;
848 }
849 }
850 }
851
852 if (ajax_enabled) {
853 thisform.attr("action", {$ajax_url} );
854 thisform.attr("target","submit_target_{$js_buildid}");
855 try {
856 window.addEventListener('message', _handle_ajax_submit_message_{$js_buildid}, false);
857 } catch (e) { }
858 $('input[name="_AccuaForm_submit_method"]', thisform).val('iframe');
859 } else {
860 thisform.attr("action", {$post_url} );
861 }
862 thisform.attr("onsubmit","return _handle_ajax_submit_{$js_buildid}()");
863 });
864 //]]>
865 </script>
866 <iframe id="submit_target_{$js_buildid}" name="submit_target_{$js_buildid}" onload="_handle_ajax_submit_complete_{$js_buildid}()" onerror="_handle_ajax_submit_complete_{$js_buildid}()" style="width:0;height:0;border:0px solid #fff"></iframe>
867 JS;
868 }
869
870 echo <<<JSREFERRER
871 <script type="text/javascript">
872 jQuery(function($){
873 var referrerfield = $("#{$this->buildID} input[name='_AccuaForm_referrer']");
874 if (referrerfield.val() == '') {
875 referrerfield.val(document.referrer);
876 }
877 $("#{$this->buildID} input[name='_AccuaForm_user_agent']").val(navigator.userAgent);
878 $("#{$this->buildID} input[name='_AccuaForm_platform']").val(navigator.platform);
879 });
880 </script>
881 JSREFERRER;
882
883 if($returnHTML) {
884 $html = ob_get_contents();
885 ob_end_clean();
886 return $html;
887 }
888 }
889
890 protected function renderJS() {
891 $this->renderJSFiles();
892
893 echo '<script type="text/javascript">';
894 $this->view->renderJS();
895 foreach($this->elements as $element)
896 $element->renderJS();
897
898 $id = $this->attributes["id"];
899
900 echo 'jQuery(document).ready(function() {';
901 /*jQuery is used to set the focus of the form's initial element.*/
902 if(!in_array("focus", $this->prevent))
903 echo 'jQuery("#', $id, ' :input:visible:enabled:first").focus();';
904
905 $this->view->jQueryDocumentReady();
906 foreach($this->elements as $element)
907 $element->jQueryDocumentReady();
908
909 /*For ajax, an anonymous onsubmit javascript function is bound to the form using jQuery. jQuery's
910 serialize function is used to grab each element's name/value pair.* /
911 if(!empty($this->ajax)) {
912 echo 'jQuery("#', $id, '").bind("submit", function() {';
913 $this->error->clear();
914 echo <<<JS
915 jQuery.ajax({
916 url: "{$this->attributes["action"]}",
917 type: "{$this->attributes["method"]}",
918 data: jQuery("#$id").serialize(),
919 success: function(response) {
920 if(response != undefined && typeof response == "object" && response.errors) {
921 JS;
922 $this->error->applyAjaxErrorResponse();
923 echo <<<JS
924 jQuery("html, body").animate({ scrollTop: jQuery("#$id").offset().top }, 500 );
925 }
926 else {
927 JS;
928 /*A callback function can be specified to handle any post submission events.* /
929 if(!empty($this->ajaxCallback))
930 echo $this->ajaxCallback, "(response);";
931 echo <<<JS
932 }
933 }
934 });
935 return false;
936 });
937
938 JS;
939 }
940 */
941 echo <<<JS
942 });
943 </script>
944 JS;
945 }
946
947 protected function renderCSS() {
948
949 }
950
951 public function getAjax() {
952 return $this->accua_ajax;
953 }
954
955 public function getFile($fieldname) {
956 if (isset($this->files[$fieldname])) {
957 return $this->files[$fieldname];
958 }
959 }
960
961 public function renameFile($fieldname, $newname) {
962 if (isset($this->files[$fieldname])) {
963 $file = $this->files[$fieldname];
964 @ $renamed = rename($file['dest_path'].$file['tmp_name'], $file['dest_path'].$newname);
965 if ($renamed) {
966 $this->files[$fieldname]['new_name'] = $newname;
967 return true;
968 }
969 }
970 return false;
971 }
972
973 public static function renderAjaxErrorResponse($return = false) {
974 if ($form = self::$submittedForm) {
975 $form->error->setForm($form);
976 return $form->error->renderAjaxErrorResponse($return);
977 }
978 }
979
980 public function setFormError($errors, $element = '') {
981 return self::setError($this->buildID, $errors, $element);
982 }
983
984 public function setClass($class) {
985 if(!empty($this->attributes["class"]))
986 $this->attributes["class"] .= " " . $class;
987 else
988 $this->attributes["class"] = $class;
989 }
990
991 public static function ajaxSubmit() {
992 $ret = array(
993 'valid' => false,
994 'messages' => self::getSubmittedMessages(),
995 'jsuuid' => self::$rawData['_AccuaForm_jsuuid'],
996 'buildID' => self::$submittedBuildID,
997 'files' => array(),
998 );
999 if ($ret['submitted'] = self::isSubmit()){
1000 if ($ret['valid'] = self::isValid()) {
1001
1002 } else {
1003 $ret['errors'] = self::renderAjaxErrorResponse(true);
1004 }
1005 $form = self::$submittedForm;
1006 foreach ($form->files as $fieldname => $file) {
1007 if (!empty($file['name'])) {
1008 $ret['files'][$fieldname] = $form->getElementByName($fieldname)->getAlreadySubmittedText();
1009 }
1010 }
1011 $ret += $form->wp_save();
1012 }
1013 return $ret;
1014 }
1015 }
1016