Overview

Namespaces

  • MvcCore
    • Ext
      • Auth
        • Virtual
      • Debug
        • Tracy
      • Form
        • Core
        • Validators
      • Request
      • Router
        • Lang
      • View
        • Helpers
  • None

Classes

  • MvcCore
  • MvcCore\Config
  • MvcCore\Controller
  • MvcCore\Debug
  • MvcCore\Ext\Auth
  • MvcCore\Ext\Auth\Controller
  • MvcCore\Ext\Auth\SignInForm
  • MvcCore\Ext\Auth\SignOutForm
  • MvcCore\Ext\Auth\User
  • MvcCore\Ext\Auth\Virtual\Controller
  • MvcCore\Ext\Auth\Virtual\Form
  • MvcCore\Ext\Auth\Virtual\User
  • MvcCore\Ext\Debug\Tracy
  • MvcCore\Ext\Debug\Tracy\AuthPanel
  • MvcCore\Ext\Debug\Tracy\IncludePanel
  • MvcCore\Ext\Debug\Tracy\MvcCorePanel
  • MvcCore\Ext\Debug\Tracy\RoutingPanel
  • MvcCore\Ext\Debug\Tracy\SessionPanel
  • MvcCore\Ext\Form
  • MvcCore\Ext\Form\Button
  • MvcCore\Ext\Form\Checkbox
  • MvcCore\Ext\Form\CheckboxGroup
  • MvcCore\Ext\Form\Core\Base
  • MvcCore\Ext\Form\Core\Configuration
  • MvcCore\Ext\Form\Core\Field
  • MvcCore\Ext\Form\Core\FieldGroup
  • MvcCore\Ext\Form\Core\Helpers
  • MvcCore\Ext\Form\Core\Validator
  • MvcCore\Ext\Form\Core\View
  • MvcCore\Ext\Form\CountrySelect
  • MvcCore\Ext\Form\Date
  • MvcCore\Ext\Form\DateTime
  • MvcCore\Ext\Form\Email
  • MvcCore\Ext\Form\Hidden
  • MvcCore\Ext\Form\NoType
  • MvcCore\Ext\Form\Number
  • MvcCore\Ext\Form\Password
  • MvcCore\Ext\Form\RadioGroup
  • MvcCore\Ext\Form\Range
  • MvcCore\Ext\Form\ResetButton
  • MvcCore\Ext\Form\ResetInput
  • MvcCore\Ext\Form\Select
  • MvcCore\Ext\Form\SubmitButton
  • MvcCore\Ext\Form\SubmitInput
  • MvcCore\Ext\Form\Text
  • MvcCore\Ext\Form\Textarea
  • MvcCore\Ext\Form\Time
  • MvcCore\Ext\Form\Validators\CompanyId
  • MvcCore\Ext\Form\Validators\CompanyVatId
  • MvcCore\Ext\Form\Validators\Date
  • MvcCore\Ext\Form\Validators\Email
  • MvcCore\Ext\Form\Validators\FloatVal
  • MvcCore\Ext\Form\Validators\Integer
  • MvcCore\Ext\Form\Validators\Maxlength
  • MvcCore\Ext\Form\Validators\MaxSelectedOptions
  • MvcCore\Ext\Form\Validators\MinSelectedOptions
  • MvcCore\Ext\Form\Validators\NumberField
  • MvcCore\Ext\Form\Validators\Pattern
  • MvcCore\Ext\Form\Validators\Phone
  • MvcCore\Ext\Form\Validators\RangeField
  • MvcCore\Ext\Form\Validators\SafeString
  • MvcCore\Ext\Form\Validators\Time
  • MvcCore\Ext\Form\Validators\Url
  • MvcCore\Ext\Form\Validators\ValueInOptions
  • MvcCore\Ext\Form\Validators\ZipCode
  • MvcCore\Ext\Request\ApacheDpi
  • MvcCore\Ext\Request\Cli
  • MvcCore\Ext\Router\Lang
  • MvcCore\Ext\Router\Lang\Route
  • MvcCore\Ext\Router\Media
  • MvcCore\Ext\Router\MediaSiteKey
  • MvcCore\Ext\View\Helpers\Assets
  • MvcCore\Ext\View\Helpers\Css
  • MvcCore\Ext\View\Helpers\Js
  • MvcCore\Ext\View\Helpers\LineBreaks
  • MvcCore\Model
  • MvcCore\Request
  • MvcCore\Response
  • MvcCore\Route
  • MvcCore\Router
  • MvcCore\Session
  • MvcCore\Tool
  • MvcCore\View

Exceptions

  • MvcCore\Ext\Form\Core\Exception
  • Overview
  • Namespace
  • Class
  • Tree
  1:   2:   3:   4:   5:   6:   7:   8:   9:  10:  11:  12:  13:  14:  15:  16:  17:  18:  19:  20:  21:  22:  23:  24:  25:  26:  27:  28:  29:  30:  31:  32:  33:  34:  35:  36:  37:  38:  39:  40:  41:  42:  43:  44:  45:  46:  47:  48:  49:  50:  51:  52:  53:  54:  55:  56:  57:  58:  59:  60:  61:  62:  63:  64:  65:  66:  67:  68:  69:  70:  71:  72:  73:  74:  75:  76:  77:  78:  79:  80:  81:  82:  83:  84:  85:  86:  87:  88:  89:  90:  91:  92:  93:  94:  95:  96:  97:  98:  99: 100: 101: 102: 103: 104: 105: 106: 107: 108: 109: 110: 111: 112: 113: 114: 115: 116: 117: 118: 119: 120: 121: 122: 123: 124: 125: 126: 127: 128: 129: 130: 131: 132: 133: 134: 135: 136: 137: 138: 139: 140: 141: 142: 143: 144: 145: 146: 147: 148: 149: 150: 151: 152: 153: 154: 155: 156: 157: 158: 159: 160: 161: 162: 163: 164: 165: 166: 167: 168: 169: 170: 171: 172: 173: 174: 175: 176: 177: 178: 179: 180: 181: 182: 183: 184: 185: 186: 187: 188: 189: 190: 191: 192: 193: 194: 195: 196: 197: 198: 199: 200: 201: 202: 203: 204: 205: 206: 207: 208: 209: 210: 211: 212: 213: 214: 215: 216: 217: 218: 219: 220: 221: 222: 223: 224: 225: 226: 227: 228: 229: 230: 231: 232: 233: 234: 235: 236: 237: 238: 239: 240: 241: 242: 243: 244: 245: 246: 247: 248: 249: 250: 251: 252: 253: 254: 255: 256: 257: 258: 259: 260: 261: 262: 263: 264: 265: 266: 267: 268: 269: 270: 271: 272: 273: 274: 275: 276: 277: 278: 279: 280: 281: 282: 283: 284: 285: 286: 287: 288: 289: 290: 291: 292: 293: 294: 295: 296: 297: 298: 299: 300: 301: 302: 303: 304: 305: 306: 307: 308: 309: 310: 311: 312: 313: 314: 315: 316: 317: 318: 319: 320: 321: 322: 323: 324: 325: 326: 327: 328: 329: 330: 331: 332: 333: 334: 335: 336: 337: 338: 339: 340: 341: 342: 343: 344: 345: 346: 347: 348: 349: 350: 351: 352: 353: 354: 355: 356: 357: 358: 359: 360: 361: 362: 363: 364: 365: 366: 367: 368: 369: 370: 371: 372: 373: 374: 375: 376: 377: 378: 379: 380: 381: 382: 383: 384: 385: 386: 387: 388: 389: 390: 391: 392: 393: 394: 395: 396: 397: 398: 399: 400: 401: 402: 403: 404: 405: 406: 407: 408: 409: 410: 411: 412: 413: 414: 415: 416: 417: 418: 419: 420: 421: 422: 423: 424: 425: 426: 427: 428: 429: 430: 431: 432: 433: 434: 435: 436: 437: 438: 439: 440: 441: 442: 443: 444: 445: 446: 447: 448: 449: 450: 451: 452: 453: 454: 455: 456: 457: 458: 459: 460: 461: 462: 463: 464: 465: 466: 467: 468: 469: 470: 471: 472: 473: 474: 475: 476: 477: 478: 479: 480: 481: 482: 483: 484: 485: 486: 487: 488: 489: 490: 491: 492: 493: 494: 495: 496: 497: 498: 499: 500: 501: 502: 503: 504: 505: 506: 507: 508: 509: 510: 511: 512: 513: 514: 515: 516: 517: 518: 519: 520: 521: 522: 523: 524: 525: 526: 527: 528: 529: 530: 531: 532: 533: 534: 535: 536: 537: 538: 539: 540: 541: 542: 543: 544: 545: 546: 547: 548: 549: 550: 551: 552: 553: 554: 555: 556: 557: 558: 559: 560: 561: 562: 563: 564: 565: 566: 567: 568: 569: 570: 571: 572: 573: 574: 575: 576: 577: 578: 579: 580: 581: 582: 583: 584: 585: 586: 587: 588: 589: 590: 591: 592: 593: 594: 595: 596: 597: 598: 599: 600: 601: 602: 603: 604: 605: 606: 607: 608: 609: 610: 611: 612: 613: 614: 615: 616: 617: 618: 619: 620: 621: 622: 623: 624: 625: 626: 627: 628: 629: 630: 631: 632: 633: 634: 635: 636: 637: 638: 639: 640: 641: 642: 643: 644: 645: 646: 647: 648: 649: 650: 651: 652: 653: 654: 655: 656: 657: 658: 659: 660: 661: 662: 663: 664: 665: 666: 667: 668: 669: 670: 671: 672: 673: 674: 675: 676: 677: 678: 679: 680: 681: 682: 683: 684: 685: 686: 687: 688: 689: 690: 691: 692: 693: 694: 695: 696: 697: 698: 699: 700: 701: 702: 703: 704: 705: 706: 707: 708: 709: 710: 711: 712: 713: 714: 715: 716: 717: 718: 719: 720: 721: 722: 723: 724: 725: 726: 727: 728: 729: 730: 731: 732: 733: 734: 735: 736: 737: 738: 739: 740: 741: 742: 743: 744: 745: 746: 747: 748: 749: 750: 751: 752: 753: 754: 755: 756: 757: 758: 759: 760: 761: 762: 763: 764: 765: 766: 767: 768: 769: 
<?php

/**
 * MvcCore
 *
 * This source file is subject to the BSD 3 License
 * For the full copyright and license information, please view 
 * the LICENSE.md file that are distributed with this source code.
 *
 * @copyright   Copyright (c) 2016 Tom FlĂ­dr (https://github.com/mvccore/mvccore)
 * @license     https://mvccore.github.io/docs/mvccore/4.0.0/LICENCE.md
 */

namespace MvcCore\Ext\Form\Core;

require_once('Configuration.php');
//require_once('Exception.php');
//require_once('View.php');

abstract class Field
{
    /**
     * Form control html id
     * @var string
     */
    public $Id = '';
    /**
     * Form control type, usually used in <input type=""> 
     * attr value, but unique type accross all form field types.
     * @var string
     */
    public $Type = '';
    /**
     * Form control specific name, server as key in submitting process
     * where is sended it's used completed value.
     * @requires
     * @var string
     */
    public $Name = '';
    /**
     * Form control value.
     * @var string
     */
    public $Value = '';
    /**
     * Form control label visible text, text only.
     * @var string
     */
    public $Label = '';
    /**
     * Location where to render <label> element.
     * 'left' by default.
     * @var string
     */
    public $LabelSide = 'left'; // right | left
    /**
     * Form control attribute required, determinating 
     * if controll will be required to complete by user.
     * @var bool
     */
    public $Required = null;
    /**
     * Form control attribute readonly, determinating
     * if controll will be readonly to not completed by user,
     * and readonly by submitting process - so only session value will be used.
     * @var bool
     */
    public $Readonly = FALSE;
    /**
     * Form control attribute disabled, determinating
     * if controll will be disabled to not completed by user,
     * and disabled by submitting process - so only session value will be used.
     * @var bool
     */
    public $Disabled = FALSE;
    /**
     * Boolean telling if field will be translated or not.
     * If nothing is configured as boolean, $field->Form->Translate values is used.
     * If $field->Translate is TRUE, translated are placeholders, label texts and error messages.
     * @var bool
     */
    public $Translate = NULL;
    /**
     * Control/label rendering mode, defined in form by defaut as: 'normal'.
     * Normal means label will be rendered before control, only for checkbox 
     * and radio buttons labels will be rendered after controls.
     * Another possible values are 'no-label' and 'label-around'.
     * Use \MvcCore\Ext\Form::FIELD_RENDER_MODE_NORMAL, \MvcCore\Ext\Form::FIELD_RENDER_MODE_NO_LABEL and
     * \MvcCore\Ext\Form::FIELD_RENDER_MODE_LABEL_AROUND.
     * @var string
     */
    public $RenderMode = NULL;
    /**
     * Html element css class string value, more classes separated by space.
     * @var array
     */
    public $CssClasses = array();
    /**
     * Collection with html <input> element additional attributes by array keys/values.
     * @var array
     */
    public $ControlAttrs = array();
    /**
     * Collection with html <label> element additional attributes by array keys/values.
     * @var array
     */
    public $LabelAttrs = array();
    /**
     * List of validator classes end-names or list of closure functions
     * accepting arguments: $submitValue, $fieldName, \MvcCore\Ext\Form\Core\Field & $field
     * and returning safe value as result. Closure function should call 
     * $field->Form->AddError() internaly if necessary and submitted value is not correct.
     * All validator classes are located in directory: /Form/Validators/...
     * For validator class \MvcCore\Ext\Form\Validators\Numeric is necessary only tu set 'Numeric'.
     * @var string[]|\Closure[]
     */
    public $Validators = array();
    /**
     * Field instance errors for rendering process.
     * @var string[]
     */
    public $Errors = array();
    /**
     * Field relative template path without .phtml extension, 
     * empty string by default to render field naturaly.
     * If there is configured any path, relative from directory /App/Views/Scripts,
     * field is rendered by custom template.
     * @var string
     */
    public $TemplatePath = '';
    /**
     * Form field view, object container with variables from local context to render in template.
     * Created automaticly inside \MvcCore\Ext\Form\Core\Field before field rendering process.
     * @var \MvcCore\Ext\Form\Core\View
     */
    public $View = NULL;
    /**
     * Supporting javascript full class name.
     * @var string
     */
    public $JsClass = '';
    /**
     * Supporting javascript file relative path.
     * Replacement '__MVCCORE_FORM_DIR__' is in rendering process 
     * replaced by \MvcCore\Ext\Form library root dir or by any other
     * reconfigured value from $this->Form->jsAssetsRootDir;
     * @var string
     */
    public $Js = '';
    /**
     * Supporting css file relative path.
     * Replacement '__MVCCORE_FORM_DIR__' is in rendering process
     * replaced by \MvcCore\Ext\Form library root dir or by any other
     * reconfigured value from $this->Form->cssAssetsRootDir;
     * @var string
     */
    public $Css = '';
    /**
     * Form instance where current fields is placed.
     * @var \MvcCore\Ext\Form
     */
    public $Form = NULL;
    /**
     * Core rendering templates storrage.
     * Those templates are used in form natural rendering process, form custom
     * template rendering process, natural field rendering process but not
     * by custom field rendering process.
     * @var array
     */
    public static $Templates = array(
        'label'             => '<label for="{id}"{attrs}>{label}</label>',
        'control'           => '<input id="{id}" name="{name}" type="{type}" value="{value}"{attrs} />',
        'togetherLabelLeft' => '<label for="{id}"{attrs}><span>{label}</span>{control}</label>',
        'togetherLabelRight'=> '<label for="{id}"{attrs}>{control}<span>{label}</span></label>',
    );
    /**
     * Local $this context properties which is not possible 
     * to configure throught constructor config array.
     * @var string[]
     */
    protected static $declaredProtectedProperties = array(
        'Id', 'View', 'Form', 'Field',
    );


    /* setters and getters ********************************************************************/

    /**
     * Set field name, used to identify submitting value.
     * @requires
     * @param string $name 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetName ($name) {
        $this->Name = $name;
        return $this;
    }
    /**
     * Set input type like: 'text', 'number', 'range'...
     * @param string $type
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetType ($type) {
        $this->Type = $type;
        return $this;
    }
    /**
     * Set control label visible text.
     * Translation will be processed internaly inside 
     * Simpleform before rendering process by $this->Form->Translator();
     * @param string $label
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetLabel ($label) {
        $this->Label = $label;
        return $this;
    }
    /**
     * Set label side - location where label will be rendered.
     * By default $this->LabelSide is configured to 'left'.
     * If you want to reconfigure it to different side, 
     * next possible value is 'right'.
     * @param string $labelSide
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetLabelSide ($labelSide = 'right') {
        $this->LabelSide = $labelSide;
        return $this;
    }
    /**
     * Set required boolean if field will be 
     * required to complete by user for submit.
     * @param bool $required 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetRequired ($required = TRUE) {
        $this->Required = $required;
        return $this;
    }
    /**
     * Set read only boolean if field will be
     * read only, not possible to complete by user for submit,
     * result value will be used from session.
     * @param bool $readonly 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetReadonly ($readonly = TRUE) {
        $this->Readonly = $readonly;
        return $this;
    }
    /**
     * Set field render mode to render label normaly before control
     * by value 'normal', which controls have mostly configured by default 
     * or to render label around the control by value 'label-around' or
     * to not render any label by value 'no-label'.
     * Use \MvcCore\Ext\Form class constants:
     * - \MvcCore\Ext\Form::FIELD_RENDER_MODE_NORMAL
     * - \MvcCore\Ext\Form::FIELD_RENDER_MODE_LABEL_AROUND
     * - \MvcCore\Ext\Form::FIELD_RENDER_MODE_NO_LABEL
     * @param string $renderMode 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetRenderMode ($renderMode = \MvcCore\Ext\Form\Core\Configuration::FIELD_RENDER_MODE_LABEL_AROUND) {
        $this->RenderMode = $renderMode;
        return $this;
    }
    /**
     * Set control value, should be string or array, by field type implementation.
     * @param string|array|mixed $value 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetValue ($value) {
        $this->Value = $value;
        return $this;
    }
    /**
     * Get control value, should be string or array, by field type implementation.
     * @return string|array
     */
    public function GetValue () {
        return $this->Value;
    }
    /**
     * Set translate to TRUE if you want to translate this field.
     * It is necessary to set up any $form->Translator callable to
     * translate cotnrol placeholder, label and error messages.
     * @param bool $translate 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetTranslate ($translate = TRUE) {
        $this->Translate = $translate;
        return $this;
    }
    /**
     * Set disabled boolean if field will be
     * disabled for user, not possible to complete 
     * by user for submit and disabled in submitting process,
     * result value will be used from session.
     * @param bool $readonly
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetDisabled ($disabled) {
        $this->Disabled = $disabled;
        return $this;
    }
    /**
     * Set value to control html class attribute.
     * More classes is necessary to set as strings separated by spaces.
     * @param string $cssClasses 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetCssClasses ($cssClasses) {
        if (gettype($cssClasses) == 'array') {
            $this->CssClasses = $cssClasses;
        } else {
            $this->CssClasses = explode(' ', (string)$cssClasses);
        }
        return $this;
    }
    /**
     * Add value to html class attribute.
     * More classes is necessary to add as strings separated by spaces.
     * @param string $cssClasses
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function AddCssClass ($cssClass) {
        $this->CssClasses[] = $cssClass;
        return $this;
    }
    /**
     * Set any additional control html attributes by key/value array.
     * Do not use system attributes as id, name, value, readonly, disabled, class...
     * @param array $attrs 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetControlAttrs ($attrs = array()) {
        $this->ControlAttrs = $attrs;
        return $this;
    }
    /**
     * Add any additional control html attributes by key/value array.
     * Do not use system attributes as id, name, value, readonly, disabled, class...
     * Use specific setter for them.
     * @param array $attrs
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function AddControlAttr ($attr = array()) {
        $this->ControlAttrs[] = $attr;
        return $this;
    }
    /**
     * Set any additional control html attributes by key/value array.
     * @param array $attrs
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetLabelAttrs ($attrs = array()) {
        $this->LabelAttrs = $attrs;
        return $this;
    }
    /**
     * Add any additional control html attributes by key/value array.
     * @param array $attrs
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function AddLabelAttr ($attr = array()) {
        $this->LabelAttrs[] = $attr;
        return $this;
    }
    /**
     * Set field validators collection, it shoud be validator class end-name in pascal
     * case or closure function. All validators are located in /Form/Validators/... 
     * dir. So for validator class \MvcCore\Ext\Form\Validators\Numeric is necessary only to set
     * array('Numeric'). Or any validator shoud be defined as simple closure function
     * accepting arguments: $submitValue, $fieldName, \MvcCore\Ext\Form\Core\Field & $field
     * and returnning safe value as result. This closure function shoud call 
     * $field->Form->AddError(); whenever is necessary and values is not correct.
     * @param string[]|\Closure[] $validators 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetValidators ($validators = array()) {
        $this->Validators = $validators;
        return $this;
    }
    /**
     * Add field validators, it shoud be validator class end-name in pascal
     * case or closure function. All validators are located in /Form/Validators/... 
     * dir. So for validator class \MvcCore\Ext\Form\Validators\Numeric is necessary only to set
     * array('Numeric'). Or any validator shoud be defined as simple closure function
     * accepting arguments: $submitValue, $fieldName, \MvcCore\Ext\Form\Core\Field & $field
     * and returnning safe value as result. This closure function shoud call
     * $field->Form->AddError(); whenever is necessary and values is not correct.
     * @param string|Closure,... $validators
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function AddValidators () {
        $args = func_get_args();
        foreach ($args as $arg) $this->Validators[] = $arg;
        return $this;
    }
    /**
     * Set template relative path without .phtml extension,
     * if you want to render field by custom template.
     * Empty string by default to render field naturaly.
     * If there is configured any path, relative from directory /App/Views/Scripts,
     * field is rendered by custom template.
     * @param string $templatePath 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetTemplatePath ($templatePath = '') {
        $this->TemplatePath = $templatePath;
        return $this;
    }
    /**
     * Set supporting javascript full class name.
     * @param string $jsClass 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetJsClass ($jsClass) {
        $this->JsClass = $jsClass;
        return $this;
    }
    /**
     * Set supporting javascript file relative path.
     * Replacement '__MVCCORE_FORM_DIR__' is in rendering process
     * replaced by \MvcCore\Ext\Form library root dir or by any other
     * reconfigured value from $this->Form->jsAssetsRootDir;
     * @param string $jsFullFile
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetJs ($jsFullFile) {
        $this->Js = $jsFullFile;
        return $this;
    }
    /**
     * Set supporting css file relative path.
     * Replacement '__MVCCORE_FORM_DIR__' is in rendering process
     * replaced by \MvcCore\Ext\Form library root dir or by any other
     * reconfigured value from $this->Form->cssAssetsRootDir;
     * @param string $cssFullFile
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function SetCss ($cssFullFile) {
        $this->Css = $cssFullFile;
        return $this;
    }
    /**
     * Add field error message.
     * This method is always called internaly from \MvcCore\Ext\Form
     * in render preparing process. Do not use it. 
     * To add form error properly, use $field->Form->AddError(); 
     * method isntead.
     * @param string $errorText 
     * @return \MvcCore\Ext\Form\Core\Field
     */
    public function AddError ($errorText) {
        $this->Errors[] = $errorText;
        return $this;
    }


    /* core methods **************************************************************************/

    /**
     * Create new form control instance.
     * @param array $cfg config array with camel case 
     *                   public properties and its values which you want to configure.
     * @throws \MvcCore\Ext\Form\Core\Exception
     */
    public function __construct ($cfg = array()) {
        static::$Templates = (object) static::$Templates;
        foreach ($cfg as $key => $value) {
            $propertyName = ucfirst($key);
            if (in_array($propertyName, static::$declaredProtectedProperties)) {
                $clsName = get_class($this);
                include_once('Exception.php');
                throw new \MvcCore\Ext\Form\Core\Exception(
                    "Property: '$propertyName' is protected, class: '$clsName'."
                );
            } else {
                $this->$propertyName = $value;
            }
        }
    }
    /**
     * Set any nondeclared property dynamicly 
     * to get it in view by rendering process.
     * @param string $name 
     * @param mixed $value 
     */
    public function __set ($name, $value) {
        $this->$name = $value;
    }
    /**
     * This method  is called internaly from \MvcCore\Ext\Form after field
     * is added into form by $form->AddField(); method. Do not use it 
     * if you are only user of this library.
     * - check if field has any name, which is required
     * - set up form and field id attribute by form id and field name
     * - set up required
     * @param \MvcCore\Ext\Form $form 
     * @throws \MvcCore\Ext\Form\Core\Exception 
     * @return void
     */
    public function OnAdded (\MvcCore\Ext\Form & $form) {
        if (!$this->Name) {
            $clsName = get_class($this);
            include_once('Exception.php');
            throw new \MvcCore\Ext\Form\Core\Exception("No 'Name' defined for form field: '$clsName'.");
        }
        $this->Form = $form;
        $this->Id = implode(Configuration::HTML_IDS_DELIMITER, array(
            $form->Id,
            $this->Name
        ));
        // if there is no specific required boolean - set required boolean by form
        $this->Required = is_null($this->Required) ? $form->Required : $this->Required ;
    }
    /**
     * Set up field properties before rendering process.
     * - set up field render mode
     * - set up translation boolean
     * - translate label if any
     * @return void
     */
    public function SetUp () {
        $form = $this->Form;
        $translator = $form->Translator;
        // if there is no specific render mode - set render mode by form
        if (is_null($this->RenderMode)) {
            $this->RenderMode = $form->FieldsDefaultRenderMode;
        }
        // translate only if Translate options is null or true and translator handler is defined
        if (
            (is_null($this->Translate) || $this->Translate === TRUE || $form->Translate) && 
            !is_null($translator)
        ) {
            $this->Translate = TRUE;
        } else {
            $this->Translate = FALSE;
        }
        if ($this->Translate && $this->Label) {
            $this->Label = call_user_func($translator, $this->Label, $form->Lang);
        }
    }


    /* rendering ******************************************************************************/

    /**
     * Render field in full mode, naturaly or by custom template.
     * @return string
     */
    public function Render () {
        if ($this->TemplatePath) {
            return $this->RenderTemplate();
        } else {
            return $this->RenderNaturally();
        }
    }
    /**
     * Render field by configured template.
     * This method creates $view = new \MvcCore\Ext\Form\Core\View
     * sets all local context variables into it and renders it into string.
     * @return string
     */
    public function RenderTemplate () {
        include_once('View.php');
        $view = new View($this->Form);
        $this->Field = $this;
        $view->SetUp($this);
        return $view->Render($this->Form->TemplateTypePath, $this->TemplatePath);
    }
    /**
     * Render field naturaly by render mode.
     * Field shoud be rendered with label beside, label around 
     * or without label by local field configuration. Also there 
     * could be rendered specific field errors before or after field
     * if field form is configured in that way.
     * @return string
     */
    public function RenderNaturally () {
        $result = '';
        if ($this->RenderMode == Configuration::FIELD_RENDER_MODE_NORMAL && $this->Label) {
            $result = $this->RenderLabelAndControl();
        } else if ($this->RenderMode == Configuration::FIELD_RENDER_MODE_LABEL_AROUND && $this->Label) {
            $result = $this->RenderControlInsideLabel();
        } else if ($this->RenderMode == Configuration::FIELD_RENDER_MODE_NO_LABEL || !$this->Label) {
            $result = $this->RenderControl();
            $errors = $this->RenderErrors();
            if ($this->Form->ErrorsRenderMode !== Configuration::ERROR_RENDER_MODE_BEFORE_EACH_CONTROL) {
                $result = $errors . $result;
            } else if ($this->Form->ErrorsRenderMode !== Configuration::ERROR_RENDER_MODE_AFTER_EACH_CONTROL) {
                $result .= $errors;
            }
        }
        return $result;
    }
    /**
     * Render field control and label by local configuration in left or in right side,
     * errors beside if form is configured to render specific errors beside controls.
     * @return string
     */
    public function RenderLabelAndControl () {
        $result = "";
        if ($this->LabelSide == 'left') {
            $result = $this->RenderLabel() . $this->RenderControl();
        } else {
            $result = $this->RenderControl() . $this->RenderLabel();
        }
        $errors = $this->RenderErrors();
        if ($this->Form->ErrorsRenderMode == Configuration::ERROR_RENDER_MODE_BEFORE_EACH_CONTROL) {
            $result = $errors . $result;
        } else if ($this->Form->ErrorsRenderMode == Configuration::ERROR_RENDER_MODE_AFTER_EACH_CONTROL) {
            $result .= $errors;
        }
        return $result;
    }
    /**
     * Render field control inside label by local configuration, render field
     * errors beside if form is configured to render specific errors beside controls.
     * @return string
     */
    public function RenderControlInsideLabel () {
        if ($this->RenderMode == Configuration::FIELD_RENDER_MODE_NO_LABEL) return $this->RenderControl();
        $attrsStr = $this->renderLabelAttrsWithFieldVars();
        $template = $this->LabelSide == 'left' ? static::$Templates->togetherLabelLeft : static::$Templates->togetherLabelRight;
        $result = $this->Form->View->Format($template, array(
            'id'        => $this->Id, 
            'label'     => $this->Label,
            'control'   => $this->RenderControl(),
            'attrs'     => $attrsStr ? " $attrsStr" : '', 
        ));
        $errors = $this->RenderErrors();
        if ($this->Form->ErrorsRenderMode == Configuration::ERROR_RENDER_MODE_BEFORE_EACH_CONTROL) {
            $result = $errors . $result;
        } else if ($this->Form->ErrorsRenderMode == Configuration::ERROR_RENDER_MODE_AFTER_EACH_CONTROL) {
            $result .= $errors;
        }
        return $result;
    }
    /**
     * Render control tag only without label or specific errors.
     * @return string
     */
    public function RenderControl () {
        $attrsStr = $this->renderControlAttrsWithFieldVars();
        return $this->Form->View->Format(static::$Templates->control, array(
            'id'        => $this->Id, 
            'name'      => $this->Name, 
            'type'      => $this->Type,
            'value'     => $this->Value,
            'attrs'     => $attrsStr ? " $attrsStr" : '', 
        ));
    }
    /**
     * Render label tag only without control or specific errors.
     * @return string
     */
    public function RenderLabel () {
        if ($this->RenderMode == Configuration::FIELD_RENDER_MODE_NO_LABEL) return '';
        $attrsStr = $this->renderLabelAttrsWithFieldVars();
        return $this->Form->View->Format(static::$Templates->label, array(
            'id'        => $this->Id, 
            'label'     => $this->Label,
            'attrs'     => $attrsStr ? " $attrsStr" : '', 
        ));
    }
    /**
     * Render field specific errors only without control or label.
     * @return string
     */
    public function RenderErrors () {
        $result = "";
        if ($this->Errors && $this->Form->ErrorsRenderMode !== Configuration::ERROR_RENDER_MODE_ALL_TOGETHER) {
            $result .= '<span class="errors">';
            foreach ($this->Errors as $key => $errorMessage) {
                $errorCssClass = 'error';
                if (isset($this->Fields[$key])) $errorCssClass .= " $key";
                $result .= "<span class=\"$errorCssClass\">$errorMessage</span>";
            }
            $result .= '</span>';
        }
        return $result;
    }


    /* protected renderers *******************************************************************/

    /**
     * Complete HTML attributes and css classes strings for label element
     * by selected field variables from $this field context
     * only if called $fieldVars item in $this field context is 
     * something different then NULL value.
     * Automaticly render into attributes and css classes also 
     * system field properties: 'Disabled', 'Readonly' and 'Required'
     * in boolean mode. All named field context properties translate
     * into attributes names and css classes strings from PascalCase into
     * dashed-case.
     * @param string[] $fieldVars 
     * @return string
     */
    protected function renderLabelAttrsWithFieldVars ($fieldVars = array()) {
        return $this->renderAttrsWithFieldVars(
            $fieldVars, $this->LabelAttrs, $this->CssClasses
        );
    }
    /**
     * Complete HTML attributes and css classes strings for control element
     * by selected field variables from $this field context
     * only if called $fieldVars item in $this field context is
     * something different then NULL value.
     * Automaticly render into attributes and css classes also
     * system field properties: 'Disabled', 'Readonly' and 'Required'
     * in boolean mode. All named field context properties translate
     * into attributes names and css classes strings from PascalCase into
     * dashed-case.
     * @param string[] $fieldVars
     * @return string
     */
    protected function renderControlAttrsWithFieldVars ($fieldVars = array()) {
        return $this->renderAttrsWithFieldVars(
            $fieldVars, $this->ControlAttrs, $this->CssClasses, TRUE
        );
    }
    /**
     * Complete HTML attributes and css classes strings for label/control element
     * by selected field variables from $this field context
     * only if called $fieldVars item in $this field context is
     * something different then NULL value.
     * Automaticly render into attributes and css classes also
     * system field properties: 'Disabled', 'Readonly' and 'Required'
     * in boolean mode. All named field context properties translate
     * into attributes names and css classes strings from PascalCase into
     * dashed-case.
     * Only if fourth param is false, do not add system attributes in boolean 
     * mode into attributes, only into css class.
     * @param string[] $fieldVars 
     * @param array $fieldAttrs 
     * @param array $cssClasses 
     * @param bool $controlRendering 
     * @return string
     */
    protected function renderAttrsWithFieldVars (
        $fieldVars = array(), $fieldAttrs = array(), $cssClasses = array(), $controlRendering = FALSE
    ) {
        $attrs = array();
        foreach ($fieldVars as $fieldVar) {
            if (!is_null($this->$fieldVar)) {
                $attrName = \MvcCore\Tool::GetDashedFromPascalCase($fieldVar);
                $attrs[$attrName] = $this->$fieldVar;
            }
        }
        $boolFieldVars = array('Disabled', 'Readonly', 'Required');
        foreach ($boolFieldVars as $fieldVar) {
            if ($this->$fieldVar) {
                $attrName = lcfirst($fieldVar);
                if ($controlRendering) $attrs[$attrName] = $attrName;
                $cssClasses[] = $attrName;
            }
        }
        $cssClasses[] = \MvcCore\Tool::GetDashedFromPascalCase($this->Name);
        $attrs['class'] = implode(' ', $cssClasses);
        include_once('View.php');
        return View::RenderAttrs(
            array_merge($fieldAttrs, $attrs)
        );
    }
}
MvcCore API documentation generated by ApiGen