summaryrefslogtreecommitdiff
path: root/framework/Web/UI/WebControls
diff options
context:
space:
mode:
authorxue <>2005-11-10 12:47:19 +0000
committerxue <>2005-11-10 12:47:19 +0000
commit55c4ac1bfe565f1ca7f537fdd8b7a201be28e581 (patch)
treea0599d5e36fdbb3f1e169ae56bab7d529597e3eb /framework/Web/UI/WebControls
Initial import of prado framework
Diffstat (limited to 'framework/Web/UI/WebControls')
-rw-r--r--framework/Web/UI/WebControls/TButton.php291
-rw-r--r--framework/Web/UI/WebControls/TCheckBox.php399
-rw-r--r--framework/Web/UI/WebControls/TContent.php47
-rw-r--r--framework/Web/UI/WebControls/TContentPlaceHolder.php47
-rw-r--r--framework/Web/UI/WebControls/TExpression.php61
-rw-r--r--framework/Web/UI/WebControls/TFont.php276
-rw-r--r--framework/Web/UI/WebControls/THiddenField.php123
-rw-r--r--framework/Web/UI/WebControls/THyperLink.php144
-rw-r--r--framework/Web/UI/WebControls/TImage.php122
-rw-r--r--framework/Web/UI/WebControls/TImageButton.php320
-rw-r--r--framework/Web/UI/WebControls/TLabel.php106
-rw-r--r--framework/Web/UI/WebControls/TLiteral.php79
-rw-r--r--framework/Web/UI/WebControls/TPanel.php162
-rw-r--r--framework/Web/UI/WebControls/TPlaceHolder.php25
-rw-r--r--framework/Web/UI/WebControls/TStatements.php61
-rw-r--r--framework/Web/UI/WebControls/TStyle.php334
-rw-r--r--framework/Web/UI/WebControls/TTextBox.php444
-rw-r--r--framework/Web/UI/WebControls/TWebControl.php368
18 files changed, 3409 insertions, 0 deletions
diff --git a/framework/Web/UI/WebControls/TButton.php b/framework/Web/UI/WebControls/TButton.php
new file mode 100644
index 00000000..f2ac6e21
--- /dev/null
+++ b/framework/Web/UI/WebControls/TButton.php
@@ -0,0 +1,291 @@
+<?php
+/**
+ * TButton class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TButton class
+ *
+ * TButton creates a click button on the page.
+ *
+ * You can create either a <b>submit</b> button or a <b>client</b> button by setting
+ * <b>UseSubmitBehavior</b> property. Set <b>Text</b> property to specify the button's caption.
+ * Upon clicking on the button, on the server side two events are raised by the button:
+ * <b>OnClick</b> and <b>OnCommand</b>. You can attach event handlers to these events
+ * to respond to the button click action. For <b>OnCommand</b> event, you can associate
+ * it with a command name and parameter by setting <b>CommandName</b> and <b>CommandParameter</b>
+ * properties, respectively. They are passed as the event parameter to the <b>OnCommand</b>
+ * event handler (see {@link TCommandEventParameter}).
+ *
+ * Clicking on button can trigger form validation, if <b>CausesValidation</b> is true.
+ * And the validation may be restricted within a certain group of validator controls by
+ * setting <b>ValidationGroup</b> property.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TButton extends TWebControl implements IPostBackEventHandler
+{
+ /**
+ * @return string tag name of the button
+ */
+ protected function getTagName()
+ {
+ return 'input';
+ }
+
+ /**
+ * Processes an object that is created during parsing template.
+ * This overrides the parent implementation by forbidding any body components.
+ * @param mixed the newly created object in template
+ * @throws TInvalidOperationException if a component is found within body
+ */
+ public function addParsedObject($object)
+ {
+ if(!is_string($object))
+ throw new TInvalidOperationException('body_contents_not_allowed',get_class($this).':'.$this->getUniqueID());
+ }
+
+ /**
+ * Adds attribute name-value pairs to renderer.
+ * This overrides the parent implementation with additional button specific attributes.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function addAttributesToRender($writer)
+ {
+ $page=$this->getPage();
+ $page->ensureRenderInForm($this);
+ if($this->getUseSubmitBehavior())
+ $writer->addAttribute('type','submit');
+ else
+ $writer->addAttribute('type','button');
+ if(($uniqueID=$this->getUniqueID())!=='')
+ $writer->addAttribute('name',$uniqueID);
+ $writer->addAttribute('value',$this->getText());
+
+ $onclick='';
+ if($this->getEnabled(true))
+ {
+ $onclick=$this->getOnClientClick();
+ if($onclick!=='')
+ $onclick=rtrim($onclick,';').';';
+ $onclick.=$page->getClientScript()->getPostBackEventReference($this->getPostBackOptions());
+ }
+ else if($this->getEnabled()) // in this case, parent will not render 'disabled'
+ $writer->addAttribute('disabled','disabled');
+ if($onclick!=='')
+ $writer->addAttribute('onclick','javascript:'.$onclick);
+ parent::addAttributesToRender($writer);
+ }
+
+ /**
+ * Renders the body content enclosed between the control tag.
+ * This overrides the parent implementation with nothing to be rendered.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function renderContents($writer)
+ {
+ }
+
+ /**
+ * OnClick event raiser.
+ * This method raises OnClick event.
+ * Be sure to invoke the parent implementation if this method is overriden.
+ * @param TEventParameter the event parameter
+ */
+ protected function onClick($param)
+ {
+ $this->raiseEvent('Click',$this,$param);
+ }
+
+ /**
+ * OnCommand event raiser.
+ * This method raises OnCommand event.
+ * Be sure to invoke the parent implementation if this method is overriden.
+ * @param TCommandEventParameter the event parameter
+ */
+ protected function onCommand($param)
+ {
+ $this->raiseEvent('Command',$this,$param);
+ $this->raiseBubbleEvent($this,$param);
+ }
+
+ /**
+ * Raises the postback event.
+ * This method is required by IPostBackEventHandler interface.
+ * If <b>CausesValidation</b> is true, it will invokes the page's {@validate}
+ * method first.
+ * It will raise <b>OnClick</b> and <b>OnCommand</b> events.
+ * This method is mainly used by framework and control developers.
+ * @param TEventParameter the event parameter
+ */
+ public function raisePostBackEvent($param)
+ {
+ if($this->getCausesValidation())
+ $this->getPage()->validate($this->getValidationGroup());
+ $this->onClick(new TEventParameter);
+ $this->onCommand(new TCommandEventParameter($this->getCommandName(),$this->getCommandParameter()));
+ }
+
+ /**
+ * Returns postback specifications for the button.
+ * This method is used by framework and control developers.
+ * @return TPostBackOptions parameters about how the button defines its postback behavior.
+ */
+ protected function getPostBackOptions()
+ {
+ $options=new TPostBackOptions($this);
+ $options->ClientSubmit=false;
+ $page=$this->getPage();
+ if($this->getCausesValidation() && $page->getValidators($this->getValidationGroup())->getCount()>0)
+ {
+ $options->PerformValidation=true;
+ $options->ValidationGroup=$this->getValidationGroup();
+ }
+ if($this->getPostBackUrl()!=='')
+ $options->ActionUrl=$this->getPostBackUrl();
+ $options->ClientSubmit=!$this->getUseSubmitBehavior();
+ return $options;
+ }
+
+ /**
+ * @return string caption of the button
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * @param string caption of the button
+ */
+ public function setText($value)
+ {
+ $this->setViewState('Text',$value,'');
+ }
+
+ /**
+ * @return boolean whether postback event trigger by this button will cause input validation, default is true
+ */
+ public function getCausesValidation()
+ {
+ return $this->getViewState('CausesValidation',true);
+ }
+
+ /**
+ * @param boolean whether postback event trigger by this button will cause input validation
+ */
+ public function setCausesValidation($value)
+ {
+ $this->setViewState('CausesValidation',TPropertyValue::ensureBoolean($value),true);
+ }
+
+ /**
+ * @return string the command name associated with the <b>OnCommand</b> event.
+ */
+ public function getCommandName()
+ {
+ return $this->getViewState('CommandName','');
+ }
+
+ /**
+ * Sets the command name associated with the <b>OnCommand</b> event.
+ * @param string the text caption to be set
+ */
+ public function setCommandName($value)
+ {
+ $this->setViewState('CommandName',$value,'');
+ }
+
+ /**
+ * @return string the parameter associated with the <b>OnCommand</b> event
+ */
+ public function getCommandParameter()
+ {
+ return $this->getViewState('CommandParameter','');
+ }
+
+ /**
+ * Sets the parameter associated with the <b>OnCommand</b> event.
+ * @param string the text caption to be set
+ */
+ public function setCommandParameter($value)
+ {
+ $this->setViewState('CommandParameter',$value,'');
+ }
+
+ /**
+ * @return boolean whether to use the button as a submit button, default is true.
+ */
+ public function getUseSubmitBehavior()
+ {
+ return $this->getViewState('UseSubmitBehavior',true);
+ }
+
+ /**
+ * @param boolean whether to use the button as a submit button
+ */
+ public function setUseSubmitBehavior($value)
+ {
+ $this->setViewState('UseSubmitBehavior',TPropertyValue::ensureBoolean($value),true);
+ }
+
+ /**
+ * @return string the group of validators which the button causes validation upon postback
+ */
+ public function getValidationGroup()
+ {
+ return $this->getViewState('ValidationGroup','');
+ }
+
+ /**
+ * @param string the group of validators which the button causes validation upon postback
+ */
+ public function setValidationGroup($value)
+ {
+ $this->setViewState('ValidationGroup',$value,'');
+ }
+
+ /**
+ * @return string the URL of the page to post to when the button is clicked, default is empty meaning post to the current page itself
+ */
+ public function getPostBackUrl()
+ {
+ return $this->getViewState('PostBackUrl','');
+ }
+
+ /**
+ * @param string the URL of the page to post to from the current page when the button is clicked, empty if post to the current page itself
+ */
+ public function setPostBackUrl($value)
+ {
+ $this->setViewState('PostBackUrl',$value,'');
+ }
+
+ /**
+ * @return string the javascript to be executed when the button is clicked
+ */
+ public function getOnClientClick()
+ {
+ return $this->getViewState('ClientClick','');
+ }
+
+ /**
+ * @param string the javascript to be executed when the button is clicked. Do not prefix it with "javascript:".
+ */
+ public function setOnClientClick($value)
+ {
+ $this->setViewState('OClientClick',$value,'');
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TCheckBox.php b/framework/Web/UI/WebControls/TCheckBox.php
new file mode 100644
index 00000000..02167544
--- /dev/null
+++ b/framework/Web/UI/WebControls/TCheckBox.php
@@ -0,0 +1,399 @@
+<?php
+/**
+ * TCheckBox class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TCheckBox class
+ *
+ * TCheckBox creates a check box on the page.
+ * You can specify the caption to display beside the check box by setting
+ * the <b>Text</b> property. The caption can appear either on the right
+ * or left of the check box, which is determined by the <b>TextAlign</b>
+ * property.
+ *
+ * To determine whether the TCheckBox component is checked,
+ * test the <b>Checked</b> property. The <b>OnCheckedChanged</b> event
+ * is raised when the <b>Checked</b> state of the TCheckBox component changes
+ * between posts to the server. You can provide an event handler for
+ * the <b>OnCheckedChanged</b> event to to programmatically
+ * control the actions performed when the state of the TCheckBox component changes
+ * between posts to the server.
+ *
+ * Note, <b>Text</b> will be HTML encoded before it is displayed in the TCheckBox component.
+ * If you don't want it to be so, set <b>EncodeText</b> to false.
+ *
+ * Namespace: System.Web.UI.WebControls
+ *
+ * Properties
+ * - <b>Text</b>, string, kept in viewstate
+ * <br>Gets or sets the text caption displayed in the TCheckBox component.
+ * - <b>EncodeText</b>, boolean, default=true, kept in viewstate
+ * <br>Gets or sets the value indicating whether Text should be HTML-encoded when rendering.
+ * - <b>TextAlign</b>, Left|Right, default=Right, kept in viewstate
+ * <br>Gets or sets the alignment of the text label associated with the TCheckBox component.
+ * - <b>Checked</b>, boolean, default=false, kept in viewstate
+ * <br>Gets or sets a value indicating whether the TCheckBox component is checked.
+ * - <b>AutoPostBack</b>, boolean, default=false, kept in viewstate
+ * <br>Gets or sets a value indicating whether the TCheckBox automatically posts back to the server when clicked.
+ *
+ * Events
+ * - <b>OnCheckedChanged</b> Occurs when the value of the <b>Checked</b> property changes between posts to the server.
+ *
+ * Examples
+ * - On a page template file, insert the following line to create a TCheckBox component,
+ * <code>
+ * <com:TCheckBox Text="Agree" OnCheckedChanged="checkAgree" />
+ * </code>
+ * The checkbox will show "Agree" text on its right side. If the user makes any change
+ * to the <b>Checked</b> state, the checkAgree() method of the page class will be invoked automatically.
+ *
+ * TFont encapsulates the CSS style fields related with font settings.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TCheckBox extends TWebControl implements IPostBackDataHandler, IValidatable
+{
+ public static $TEXT_ALIGN=array('Left','Right');
+
+ protected function getTagName()
+ {
+ return 'input';
+ }
+
+ protected function addAttributesToRender($writer)
+ {
+ }
+
+ /**
+ * Loads user input data.
+ * This method is primarly used by framework developers.
+ * @param string the key that can be used to retrieve data from the input data collection
+ * @param array the input data collection
+ * @return boolean whether the data of the control has been changed
+ */
+ public function loadPostData($key,$values)
+ {
+ $checked=$this->getChecked();
+ if(isset($values[$key])!=$checked)
+ {
+ $this->setChecked(!$checked);
+ return true;
+ }
+ else
+ return false;
+ }
+
+
+ /**
+ * Raises postdata changed event.
+ * This method calls {@link onCheckedChanged} method.
+ * This method is primarly used by framework developers.
+ */
+ public function raisePostDataChangedEvent()
+ {
+ $page=$this->getPage();
+ if($this->getAutoPostBack() && !$page->getIsPostBackEventControlRegistered())
+ {
+ $page->setAutoPostBackControl($this);
+ if($this->getCausesValidation())
+ $page->validate($this->getValidationGroup());
+ }
+ $this->onCheckedChanged(new TEventParameter);
+ }
+
+ /**
+ * This method is invoked when the value of the <b>Checked</b> property changes between posts to the server.
+ * The method raises 'CheckedChanged' event to fire up the event delegates.
+ * If you override this method, be sure to call the parent implementation
+ * so that the event delegates can be invoked.
+ * @param TEventParameter event parameter to be passed to the event handlers
+ */
+ protected function onCheckedChanged($param)
+ {
+ $this->raiseEvent('CheckedChanged',$this,$param);
+ }
+
+ /**
+ * Returns the value of the property that needs validation.
+ * @return mixed the property value to be validated
+ */
+ public function getValidationPropertyValue()
+ {
+ return $this->getChecked();
+ }
+
+ /**
+ * @return string the text caption of the checkbox
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * Sets the text caption of the checkbox.
+ * @param string the text caption to be set
+ */
+ public function setText($value)
+ {
+ $this->setViewState('Text',$value,'');
+ }
+
+ /**
+ * @return string the alignment of the text caption
+ */
+ public function getTextAlign()
+ {
+ return $this->getViewState('TextAlign','Right');
+ }
+
+ /**
+ * Sets the text alignment of the checkbox
+ * @param string either 'Left' or 'Right'
+ */
+ public function setTextAlign($value)
+ {
+ $this->setViewState('TextAlign',TPropertyValue::ensureEnum($value,self::$TEXT_ALIGN),'Right');
+ }
+
+ /**
+ * @return boolean whether the checkbox is checked
+ */
+ public function getChecked()
+ {
+ return $this->getViewState('Checked',false);
+ }
+
+ /**
+ * Sets a value indicating whether the checkbox is to be checked or not.
+ * @param boolean whether the checkbox is to be checked or not.
+ */
+ public function setChecked($value)
+ {
+ $this->setViewState('Checked',$value,false);
+ }
+
+ /**
+ * @return boolean whether clicking on the checkbox will post the page.
+ */
+ public function getAutoPostBack()
+ {
+ return $this->getViewState('AutoPostBack',false);
+ }
+
+ /**
+ * Sets a value indicating whether clicking on the checkbox will post the page.
+ * @param boolean whether clicking on the checkbox will post the page.
+ */
+ public function setAutoPostBack($value)
+ {
+ $this->setViewState('AutoPostBack',$value,false);
+ }
+
+ /**
+ * @return boolean whether postback event trigger by this checkbox will cause input validation, default is true.
+ */
+ public function getCausesValidation()
+ {
+ return $this->getViewState('CausesValidation',true);
+ }
+
+ /**
+ * Sets the value indicating whether postback event trigger by this checkbox will cause input validation.
+ * @param boolean whether postback event trigger by this checkbox will cause input validation.
+ */
+ public function setCausesValidation($value)
+ {
+ $this->setViewState('CausesValidation',TPropertyValue::ensureBoolean($value),true);
+ }
+
+ /**
+ * @return string the group of validators which the checkbox causes validation upon postback
+ */
+ public function getValidationGroup()
+ {
+ return $this->getViewState('ValidationGroup','');
+ }
+
+ /**
+ * @param string the group of validators which the checkbox causes validation upon postback
+ */
+ public function setValidationGroup($value)
+ {
+ $this->setViewState('ValidationGroup',$value,'');
+ }
+
+ /**
+ * Returns the attributes to be rendered.
+ * This method overrides the parent's implementation.
+ * @return ArrayObject attributes to be rendered
+ */
+ protected function getAttributesToRender()
+ {
+ $attributes=parent::getAttributesToRender();
+ if(isset($attributes['id'])) unset($attributes['id']);
+ if(isset($attributes['accesskey'])) unset($attributes['accesskey']);
+ if(isset($attributes['tabindex'])) unset($attributes['tabindex']);
+ return $attributes;
+ }
+
+ /**
+ * Renders the body content of the control.
+ * This method overrides the parent's implementation.
+ * @return string the rendering result.
+ */
+ protected function renderBody()
+ {
+ $name=$this->getUniqueID();
+ $disabled=!$this->isEnabled();
+ $id=$this->getClientID();
+
+ $input="<input id=\"$id\" type=\"checkbox\" name=\"$name\"";
+ if($this->isChecked())
+ $input.=" checked=\"checked\"";
+ if($disabled)
+ $input.=" disabled=\"disabled\"";
+ if($this->isAutoPostBack())
+ {
+ $page=$this->getPage();
+ $script=$page->getPostBackClientEvent($this,'');
+ $input.=" onclick=\"javascript:$script\"";
+ }
+ $accessKey=$this->getAccessKey();
+ if(strlen($accessKey))
+ $input.=" accesskey=\"$accessKey\"";
+ $tabIndex=$this->getTabIndex();
+ if(!empty($tabIndex))
+ $input.=" tabindex=\"$tabIndex\"";
+ $input.='/>';
+ $text=$this->isEncodeText()?pradoEncodeData($this->getText()):$this->getText();
+ if(strlen($text))
+ {
+ $label="<label for=\"$name\">$text</label>";
+ if($this->getTextAlign()=='Left')
+ $input="{$label}{$input}";
+ else
+ $input.=$label;
+ }
+ return $input;
+ }
+
+ protected function renderControl($writer)
+ {
+ $this->addAttributesToRender($writer);
+ $page=$this->getPage();
+ $page->ensureRenderInForm($this);
+ $needSpan=true;
+ if($this->getStyleCreated())
+ {
+ $this->getStyle()->addAttributesToRender($writer);
+ $needSpan=true;
+ }
+ if(!$this->getEnabled(true))
+ {
+ $writer->addAttribute('disabled','disabled');
+ $needSpan=true;
+ }
+ if(($tooltip=$this->getToolTip())!=='')
+ {
+ $writer->addAttribute('title',$tooltip);
+ $needSpan=true;
+ }
+ $onclick=null;
+ if($this->getHasAttributes())
+ {
+ $attributes=$this->getAttributes();
+ $value=$attributes->remove('value');
+ $onclick=$attributes->remove('onclick');
+ if($attributes->getCount())
+ {
+ foreach($attributes as $name=>$value)
+ $writer->addAttribute($name,$value);
+ }
+ $needSpan=true;
+ if($value!==null)
+ $attributes->add('value',$value);
+ }
+ if($needSpan)
+ $writer->renderBeginTag('span');
+ $clientID=$this->getClientID();
+ if(($text=$this->getText())!=='')
+ {
+ if($this->getTextAlign()==='Left')
+ {
+ $this->renderLabel($writer,$text,$clientID);
+ $this->renderInputTag($writer,$clientID,$onclick);
+ }
+ else
+ {
+ $this->renderInputTag($writer,$clientID,$onclick);
+ $this->renderLabel($writer,$text,$clientID);
+ }
+ }
+ else
+ $this->renderInputTag($writer,$clientID,$onclick);
+ if($needSpan)
+ $writer->renderEndTag();
+ }
+
+ private function renderLabel($writer,$text,$clientID)
+ {
+ $writer->addAttribute('for',$clientID);
+ // todo: custom label attributes rendering
+ $writer->renderBeginTag('label');
+ $writer->write($text);
+ $writer->renderEndTag();
+ }
+
+ protected function renderInputTag($writer,$clientID,$onclick)
+ {
+ if($clientID!=='')
+ $writer->addAttribute('id',$clientID);
+ $writer->addAttribute('type','checkbox');
+ if(($uniqueID=$this->getUniqueID())!=='')
+ $writer->addAttribute('name',$uniqueID);
+ //todo: render value attribute here
+ if($this->getChecked())
+ $writer->addAttribute('checked','checked');
+ if(!$this->getEnabled(true))
+ $writer->addAttribute('disabled','disabled');
+ $page=$this->getPage();
+ if($this->getAutoPostBack() && $page->getClientSupportsJavaScript())
+ {
+ $option=new TPostBackOptions($this);
+ if($this->getCausesValidation() && $page->getValidators($this->getValidationGroup())->getCount())
+ {
+ $option->PerformValidation=true;
+ $option->ValidationGroup=$this->getValidationGroup;
+ }
+ if($page->getForm())
+ $option->AutoPostBack=true;
+ if(!empty($onclick))
+ $onclick=rtrim($onclick,';').';';
+ $onclick.=$page->getClientScript()->getPostBackEventReference($option);
+ }
+ if(!empty($onclick))
+ $writer->addAttribute('onclick',$onclick);
+ if(($accesskey=$this->getAccessKey())!=='')
+ $writer->addAttribute('accesskey',$accesskey);
+ if(($tabindex=$this->getTabIndex())>0)
+ $writer->addAttribute('tabindex',$tabindex);
+ //todo: render input attributes
+ $writer->renderBeginTag('input');
+ $writer->renderEndTag();
+ }
+ // todo: onprerender???
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TContent.php b/framework/Web/UI/WebControls/TContent.php
new file mode 100644
index 00000000..61786c01
--- /dev/null
+++ b/framework/Web/UI/WebControls/TContent.php
@@ -0,0 +1,47 @@
+<?php
+/**
+ * TContent class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TContent class
+ *
+ * TContent specifies a block of content on a control's template
+ * that will be injected at somewhere of the master control's template.
+ * TContentPlaceHolder and {@link TContent} together implement a decoration
+ * pattern for prado templated controls. A template control
+ * (called content control) can specify a master control
+ * whose template contains some TContentPlaceHolder controls.
+ * {@link TContent} controls on the content control's template will replace the corresponding
+ * {@link TContentPlaceHolder} controls on the master control's template.
+ * This is called content injection. It is done by matching the IDs of
+ * {@link TContent} and {@link TContentPlaceHolder} controls.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TContent extends TControl implements INamingContainer
+{
+ /**
+ * This method is invoked after the control is instantiated on a template.
+ * This overrides the parent implementation by registering the content control
+ * to the template owner control.
+ * @param TControl potential parent of this control
+ */
+ public function createdOnTemplate($parent)
+ {
+ $this->getTemplateControl()->registerContent($this);
+ parent::createdOnTemplate($parent);
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TContentPlaceHolder.php b/framework/Web/UI/WebControls/TContentPlaceHolder.php
new file mode 100644
index 00000000..fc832fae
--- /dev/null
+++ b/framework/Web/UI/WebControls/TContentPlaceHolder.php
@@ -0,0 +1,47 @@
+<?php
+/**
+ * TContentPlaceHolder class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TContentPlaceHolder class
+ *
+ * TContentPlaceHolder reserves a place on a template where a {@link TContent}
+ * control can inject itself and its children in. TContentPlaceHolder and {@link TContent}
+ * together implement a decoration pattern for prado templated controls.
+ * A template control (called content control) can specify a master control
+ * whose template contains some TContentPlaceHolder controls.
+ * {@link TContent} controls on the content control's template will replace the corresponding
+ * {@link TContentPlaceHolder} controls on the master control's template.
+ * This is called content injection. It is done by matching the IDs of
+ * {@link TContent} and {@link TContentPlaceHolder} controls.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TContentPlaceHolder extends TControl
+{
+ /**
+ * This method is invoked after the control is instantiated on a template.
+ * This overrides the parent implementation by registering the content placeholder
+ * control to the template owner control. The placeholder control will NOT
+ * be added to the potential parent control!
+ * @param TControl potential parent of this control
+ */
+ public function createdOnTemplate($parent)
+ {
+ $loc=$parent->getHasControls()?$parent->getControls()->getCount():0;
+ $this->getTemplateControl()->registerContentPlaceHolder($this->getID(),$parent,$loc);
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TExpression.php b/framework/Web/UI/WebControls/TExpression.php
new file mode 100644
index 00000000..6cecf9c4
--- /dev/null
+++ b/framework/Web/UI/WebControls/TExpression.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * TExpression class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TExpression class
+ *
+ * TExpression evaluates a PHP expression and renders the result.
+ * The expression is evaluated during rendering stage. You can set
+ * it via the property <b>Expression</b>. You should also specify
+ * the context object by <b>Context</b> property which is used as
+ * the object in which the expression is evaluated. If the <b>Context</b>
+ * property is not set, the TExpression component itself will be
+ * assumed as the context.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TExpression extends TControl
+{
+ private $_e='';
+
+ /**
+ * @return string the expression to be evaluated
+ */
+ public function getExpression()
+ {
+ return $this->_e;
+ }
+
+ /**
+ * Sets the expression of the TExpression
+ * @param string the expression to be set
+ */
+ public function setExpression($value)
+ {
+ $this->_e=$value;
+ }
+
+ /**
+ * Renders the evaluation result of the expression.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function render($writer)
+ {
+ if($this->_e!=='')
+ $writer->write($this->evaluateExpression($this->_e));
+ }
+}
+
+?>
diff --git a/framework/Web/UI/WebControls/TFont.php b/framework/Web/UI/WebControls/TFont.php
new file mode 100644
index 00000000..468aa9f9
--- /dev/null
+++ b/framework/Web/UI/WebControls/TFont.php
@@ -0,0 +1,276 @@
+<?php
+/**
+ * TFont class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TFont class
+ *
+ * TFont encapsulates the CSS style fields related with font settings.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TFont extends TComponent
+{
+ /**
+ * Bits indicating the font states.
+ */
+ const IS_BOLD=0x01;
+ const IS_ITALIC=0x02;
+ const IS_OVERLINE=0x04;
+ const IS_STRIKEOUT=0x08;
+ const IS_UNDERLINE=0x10;
+
+ /**
+ * Bits indicating whether particular font states are changed.
+ */
+ const IS_SET_BOLD=0x01000;
+ const IS_SET_ITALIC=0x02000;
+ const IS_SET_OVERLINE=0x04000;
+ const IS_SET_STRIKEOUT=0x08000;
+ const IS_SET_UNDERLINE=0x10000;
+ const IS_SET_SIZE=0x20000;
+ const IS_SET_NAME=0x40000;
+
+ /**
+ * @var integer bits representing various states
+ */
+ private $_flags=0;
+ /**
+ * @var string font name
+ */
+ private $_name='';
+ /**
+ * @var string font size
+ */
+ private $_size='';
+
+ /**
+ * @return boolean whether the font is in bold face
+ */
+ public function getBold()
+ {
+ return ($this->_flags & self::IS_BOLD)!==0;
+ }
+
+ /**
+ * @param boolean whether the font is in bold face
+ */
+ public function setBold($value)
+ {
+ $this->_flags |= self::IS_SET_BOLD;
+ if($value)
+ $this->_flags |= self::IS_BOLD;
+ else
+ $this->_flags &= ~self::IS_BOLD;
+ }
+
+ /**
+ * @return boolean whether the font is in italic face
+ */
+ public function getItalic()
+ {
+ return ($this->_flags & self::IS_ITALIC)!==0;
+ }
+
+ /**
+ * @param boolean whether the font is italic
+ */
+ public function setItalic($value)
+ {
+ $this->_flags |= self::IS_SET_ITALIC;
+ if($value)
+ $this->_flags |= self::IS_ITALIC;
+ else
+ $this->_flags &= ~self::IS_ITALIC;
+ }
+
+ /**
+ * @return boolean whether the font is overlined
+ */
+ public function getOverline()
+ {
+ return ($this->_flags & self::IS_OVERLINE)!==0;
+ }
+
+ /**
+ * @param boolean whether the font is overlined
+ */
+ public function setOverline($value)
+ {
+ $this->_flags |= self::IS_SET_OVERLINE;
+ if($value)
+ $this->_flags |= self::IS_OVERLINE;
+ else
+ $this->_flags &= ~self::IS_OVERLINE;
+ }
+
+ /**
+ * @return string the font size
+ */
+ public function getSize()
+ {
+ return $this->_size;
+ }
+
+ /**
+ * @param string the font size
+ */
+ public function setSize($value)
+ {
+ $this->_flags |= self::IS_SET_SIZE;
+ $this->_size=$value;
+ }
+
+ /**
+ * @return boolean whether the font is strikeout
+ */
+ public function getStrikeout()
+ {
+ return ($this->_flags & self::IS_STRIKEOUT)!==0;
+ }
+
+ /**
+ * @param boolean whether the font is strikeout
+ */
+ public function setStrikeout($value)
+ {
+ $this->_flags |= self::IS_SET_STRIKEOUT;
+ if($value)
+ $this->_flags |= self::IS_STRIKEOUT;
+ else
+ $this->_flags &= ~self::IS_STRIKEOUT;
+ }
+
+ /**
+ * @return boolean whether the font is underlined
+ */
+ public function getUnderline()
+ {
+ return ($this->_flags & self::IS_UNDERLINE)!==0;
+ }
+
+ /**
+ * @param boolean whether the font is underlined
+ */
+ public function setUnderline($value)
+ {
+ $this->_flags |= self::IS_SET_UNDERLINE;
+ if($value)
+ $this->_flags |= self::IS_UNDERLINE;
+ else
+ $this->_flags &= ~self::IS_UNDERLINE;
+ }
+
+ /**
+ * @return string the font name (family)
+ */
+ public function getName()
+ {
+ return $this->_name;
+ }
+
+ /**
+ * @param string the font name (family)
+ */
+ public function setName($value)
+ {
+ $this->_flags |= self::IS_SET_NAME;
+ $this->_name=$value;
+ }
+
+ /**
+ * @return boolean whether the font is empty
+ */
+ public function getIsEmpty()
+ {
+ return !$this->_flags;
+ }
+
+ /**
+ * Clears up the font.
+ */
+ public function reset()
+ {
+ $this->_flags=0;
+ $this->_name='';
+ $this->_size='';
+ }
+
+ /**
+ * Merges the font with a new one.
+ * The fields in the new font will overwrite the current ones.
+ * @param TFont the new font
+ */
+ public function mergeWith($font)
+ {
+ if($font===null)
+ return;
+ if($font->_flags & self::IS_SET_BOLD)
+ $this->setBold($font->getBold());
+ if($font->_flags & self::IS_SET_ITALIC)
+ $this->setItalic($font->getItalic());
+ if($font->_flags & self::IS_SET_OVERLINE)
+ $this->setOverline($font->getOverline());
+ if($font->_flags & self::IS_SET_STRIKEOUT)
+ $this->setStrikeout($font->getStrikeout());
+ if($font->_flags & self::IS_SET_UNDERLINE)
+ $this->setUnderline($font->getUnderline());
+ if($font->_flags & self::IS_SET_SIZE)
+ $this->setSize($font->getSize());
+ if($font->_flags & self::IS_SET_NAMES)
+ $this->setName($font->getName());
+ }
+
+ /**
+ * Copies the font from a new one.
+ * The existing font will be cleared up first.
+ * @param TFont the new font.
+ */
+ public function copyFrom($font)
+ {
+ $this->reset();
+ $this->mergeWith($font);
+ }
+
+ /**
+ * @return string the font in a css style string representation.
+ */
+ public function toString()
+ {
+ if($this->getIsEmpty())
+ return '';
+ $str='';
+ if($this->_flags & self::IS_SET_BOLD)
+ $str.='font-weight:'.(($this->_flags & self::IS_BOLD)?'bold;':'normal;');
+ if($this->_flags & self::IS_SET_ITALIC)
+ $str.='font-style:'.(($this->_flags & self::IS_ITALIC)?'italic;':'normal;');
+ $textDec='';
+ if($this->_flags & self::IS_UNDERLINE)
+ $textDec.='underline';
+ if($this->_flags & self::IS_OVERLINE)
+ $textDec.=' overline';
+ if($this->_flags & self::IS_STRIKEOUT)
+ $textDec.=' line-through';
+ $textDec=ltrim($textDec);
+ if($textDec!=='')
+ $str.='text-decoration:'.$textDec.';';
+ if($this->_size!=='')
+ $str.='font-size:'.$this->_size.';';
+ if($this->_name!=='')
+ $str.='font-family:'.$this->_name.';';
+ return $str;
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/THiddenField.php b/framework/Web/UI/WebControls/THiddenField.php
new file mode 100644
index 00000000..c46f1cda
--- /dev/null
+++ b/framework/Web/UI/WebControls/THiddenField.php
@@ -0,0 +1,123 @@
+<?php
+/**
+ * THiddenField class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * THiddenField class
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class THiddenField extends TControl implements IPostBackDataHandler
+{
+ /**
+ * @return string tag name of the hyperlink
+ */
+ protected function getTagName()
+ {
+ return 'input';
+ }
+
+ public function focus()
+ {
+ throw new TInvalidOperationException('xxx');
+ }
+
+ protected function addAttributesToRender($writer)
+ {
+ $page=$this->getPage();
+ $page->ensureRenderInForm($this);
+ $writer->addAttribute('type','hidden');
+ if(($uid=$this->getUniqueID())!=='')
+ $writer->addAttribute('name',$uid);
+ if(($id=$this->getID())!=='')
+ $writer->addAttribute('id',$id);
+ if(($value=$this->getValue())!=='')
+ $writer->addAttribute('value',$value);
+ }
+
+ /**
+ * @return string the value of the THiddenField
+ */
+ public function getValue()
+ {
+ return $this->getViewState('Value','');
+ }
+
+ /**
+ * Sets the value of the THiddenField
+ * @param string the value to be set
+ */
+ public function setValue($value)
+ {
+ $this->setViewState('Value',$value,'');
+ }
+
+ public function getEnableTheming()
+ {
+ return false;
+ }
+
+ public function setEnableTheming($value)
+ {
+ throw new TInvalidOperationException('no_theming_support');
+ }
+
+ public function setSkinID($value)
+ {
+ throw new TInvalidOperationException('no_theming_support');
+ }
+
+ /**
+ * Loads hidden field data.
+ * This method is primarly used by framework developers.
+ * @param string the key that can be used to retrieve data from the input data collection
+ * @param array the input data collection
+ * @return boolean whether the data of the component has been changed
+ */
+ public function loadPostData($key,$values)
+ {
+ $value=$values[$key];
+ if($value===$this->getValue())
+ return false;
+ else
+ {
+ $this->setValue($value);
+ return true;
+ }
+ }
+
+ /**
+ * Raises postdata changed event.
+ * This method calls {@link onValueChanged} method.
+ * This method is primarly used by framework developers.
+ */
+ public function raisePostDataChangedEvent()
+ {
+ $this->onValueChanged(new TEventParameter);
+ }
+
+ /**
+ * This method is invoked when the value of the <b>Value</b> property changes between posts to the server.
+ * The method raises 'ValueChanged' event to fire up the event delegates.
+ * If you override this method, be sure to call the parent implementation
+ * so that the event delegates can be invoked.
+ * @param TEventParameter event parameter to be passed to the event handlers
+ */
+ public function onValueChanged($param)
+ {
+ $this->raiseEvent('ValueChanged',$this,$param);
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/THyperLink.php b/framework/Web/UI/WebControls/THyperLink.php
new file mode 100644
index 00000000..2b57e101
--- /dev/null
+++ b/framework/Web/UI/WebControls/THyperLink.php
@@ -0,0 +1,144 @@
+<?php
+/**
+ * THyperLink class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * THyperLink class
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class THyperLink extends TWebControl
+{
+ // todo: TControl::resolveClientUrl
+ /**
+ * @return string tag name of the hyperlink
+ */
+ protected function getTagName()
+ {
+ return 'a';
+ }
+
+ protected function addAttributesToRender($writer)
+ {
+ $isEnabled=$this->getEnabled(true);
+ if($this->getEnabled() && !$isEnabled)
+ $writer->addAttribute('disabled','disabled');
+ parent::addAttributesToRender($writer);
+ if(($url=$this->getNavigateUrl())!=='' && $isEnabled)
+ {
+ // todo
+ //$url=$this->resolveClientUrl($url);
+ $writer->addAttribute('href',$url);
+ }
+ if(($target=$this->getTarget())!=='')
+ $writer->addAttribute('target',$target);
+ }
+
+ /**
+ * Renders the body content of the hyperlink.
+ * @param THtmlTextWriter the writer for rendering
+ */
+ protected function renderContents($writer)
+ {
+ if(($imageUrl=$this->getImageUrl())==='')
+ {
+ if($this->getHasControls())
+ parent::renderContents($writer);
+ else
+ $writer->write($this->getText());
+ }
+ else
+ {
+ $image=new TImage;
+ $image->setImageUrl($this->resolveClientUrl($imageUrl));
+ if(($toolTip=$this->getToolTip())!=='')
+ $image->setToolTip($toolTip);
+ if(($text=$this->getText())!=='')
+ $image->setAlternateText($text);
+ $image->renderControl($writer);
+ }
+ }
+
+ /**
+ * @return string the text caption of the THyperLink
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * Sets the text caption of the THyperLink.
+ * @param string the text caption to be set
+ */
+ public function setText($value)
+ {
+ if($this->getHasControls())
+ $this->getControls()->clear();
+ $this->setViewState('Text',$value,'');
+ }
+
+ /**
+ * @return string the location of the image file for the THyperLink
+ */
+ public function getImageUrl()
+ {
+ return $this->getViewState('ImageUrl','');
+ }
+
+ /**
+ * Sets the location of image file of the THyperLink.
+ * @param string the image file location
+ */
+ public function setImageUrl($value)
+ {
+ $this->setViewState('ImageUrl',$value,'');
+ }
+
+ /**
+ * @return string the URL to link to when the THyperLink component is clicked.
+ */
+ public function getNavigateUrl()
+ {
+ return $this->getViewState('NavigateUrl','');
+ }
+
+ /**
+ * Sets the URL to link to when the THyperLink component is clicked.
+ * @param string the URL
+ */
+ public function setNavigateUrl($value)
+ {
+ $this->setViewState('NavigateUrl',$value,'');
+ }
+
+ /**
+ * @return string the target window or frame to display the Web page content linked to when the THyperLink component is clicked.
+ */
+ public function getTarget()
+ {
+ return $this->getViewState('Target','');
+ }
+
+ /**
+ * Sets the target window or frame to display the Web page content linked to when the THyperLink component is clicked.
+ * @param string the target window, valid values include '_blank', '_parent', '_self', '_top' and empty string.
+ */
+ public function setTarget($value)
+ {
+ $this->setViewState('Target',$value,'');
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TImage.php b/framework/Web/UI/WebControls/TImage.php
new file mode 100644
index 00000000..46e61083
--- /dev/null
+++ b/framework/Web/UI/WebControls/TImage.php
@@ -0,0 +1,122 @@
+<?php
+/**
+ * TImage class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TImage class
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TImage extends TWebControl
+{
+ public static $IMAGE_ALIGN=array('NotSet','AbsBottom','AbsMiddle','Baseline','Bottom','Left','Middle','Right','TextTop','Top');
+ // todo: TControl::resolveClientUrl()
+ /**
+ * @return string tag name of the image
+ */
+ protected function getTagName()
+ {
+ return 'img';
+ }
+
+ protected function addAttributesToRender($writer)
+ {
+ $writer->addAttribute('src',$this->getImageUrl());
+ $writer->addAttribute('alt',$this->getAlternateText());
+ if(($desc=$this->getDescriptionUrl())!=='')
+ $writer->addAttribute('longdesc',$this->resolveClientUrl($desc));
+ if(($align=$this->getImageAlign())!=='NotSet')
+ $writer->addAttribute('align',strtolower($align));
+ parent::addAttributesToRender($writer);
+ }
+
+ /**
+ * Renders the body content of the image.
+ * None will be rendered for an image.
+ * @param THtmlTextWriter the writer for rendering
+ */
+ protected function renderContents($writer)
+ {
+ }
+
+ /**
+ * @return string the alternative text displayed in the TImage component when the image is unavailable.
+ */
+ public function getAlternateText()
+ {
+ return $this->getViewState('AlternateText','');
+ }
+
+ /**
+ * Sets the alternative text to be displayed in the TImage when the image is unavailable.
+ * @param string the alternative text
+ */
+ public function setAlternateText($value)
+ {
+ $this->setViewState('AlternateText',$value,'');
+ }
+
+ /**
+ * @return string the alignment of the image with respective to other elements on the page.
+ */
+ public function getImageAlign()
+ {
+ return $this->getViewState('ImageAlign','');
+ }
+
+ /**
+ * Sets the alignment of the image with respective to other elements on the page.
+ * @param string the alignment of the image
+ */
+ public function setImageAlign($value)
+ {
+ $this->setViewState('ImageAlign',TPropertyValue::ensureEnum($value,self::$IMAGE_ALIGN),'NotSet');
+ }
+
+ /**
+ * @return string the location of the image file to be displayed
+ */
+ public function getImageUrl()
+ {
+ return $this->getViewState('ImageUrl','');
+ }
+
+ /**
+ * Sets the location of the image file to be displayed.
+ * @param string the location of the image file (file path or URL)
+ */
+ public function setImageUrl($value)
+ {
+ $this->setViewState('ImageUrl',$value,'');
+ }
+
+ /**
+ * @return string link to long description
+ */
+ public function getDescriptionUrl()
+ {
+ return $this->getViewState('DescriptionUrl','');
+ }
+
+ /**
+ * Sets the link to long description
+ * @param string the link to long description
+ */
+ public function setDescriptionUrl($value)
+ {
+ $this->setViewState('DescriptionUrl',$value,'');
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TImageButton.php b/framework/Web/UI/WebControls/TImageButton.php
new file mode 100644
index 00000000..6452c651
--- /dev/null
+++ b/framework/Web/UI/WebControls/TImageButton.php
@@ -0,0 +1,320 @@
+<?php
+/**
+ * TImageButton class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TImage class file
+ */
+require_once(dirname(__FILE__).'/TImage.php');
+
+/**
+ * TImageButton class
+ *
+ * TImageButton displays an image on the Web page and responds to mouse clicks on the image.
+ * It is similar to the TButton component except that the TImageButton also captures the
+ * coordinates where the image is clicked.
+ *
+ * Write a <b>OnClick</b> event handler to programmatically determine the coordinates
+ * where the image is clicked. The coordinates can be accessed through <b>x</b> and <b>y</b>
+ * properties of the event parameter which is of type <b>TImageClickEventParameter</b>.
+ * Note the origin (0, 0) is located at the upper left corner of the image.
+ *
+ * Write a <b>OnCommand</b> event handler to make the TImageButton component behave
+ * like a command button. A command name can be associated with the component by using
+ * the <b>CommandName</b> property. The <b>CommandParameter</b> property
+ * can also be used to pass additional information about the command,
+ * such as specifying ascending order. This allows multiple TImageButton components to be placed
+ * on the same Web page. In the event handler, you can also determine
+ * the <b>CommandName</b> property value and the <b>CommandParameter</b> property value
+ * through <b>name</b> and <b>parameter</b> of the event parameter which is of
+ * type <b>TCommandEventParameter</b>.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+
+class TImageButton extends TImage implements IPostBackDataHandler, IPostBackEventHandler
+{
+ private $_x=0;
+ private $_y=0;
+
+ /**
+ * @return string tag name of the button
+ */
+ protected function getTagName()
+ {
+ return 'input';
+ }
+
+ /**
+ * Adds attribute name-value pairs to renderer.
+ * This overrides the parent implementation with additional button specific attributes.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function addAttributesToRender($writer)
+ {
+ $page=$this->getPage();
+ $page->ensureRenderInForm($this);
+ $writer->addAttribute('type','image');
+ if(($uniqueID=$this->getUniqueID())!=='')
+ $writer->addAttribute('name',$uniqueID);
+
+ $onclick='';
+ if($this->getEnabled(true))
+ {
+ $onclick=$this->getOnClientClick();
+ if($onclick!=='')
+ $onclick=rtrim($onclick,';').';';
+ $onclick.=$page->getClientScript()->getPostBackEventReference($this->getPostBackOptions());
+ }
+ else if($this->getEnabled()) // in this case, parent will not render 'disabled'
+ $writer->addAttribute('disabled','disabled');
+ if($onclick!=='')
+ $writer->addAttribute('onclick','javascript:'.$onclick);
+ parent::addAttributesToRender($writer);
+ }
+
+ /**
+ * Returns postback specifications for the button.
+ * This method is used by framework and control developers.
+ * @return TPostBackOptions parameters about how the button defines its postback behavior.
+ */
+ protected function getPostBackOptions()
+ {
+ $options=new TPostBackOptions($this);
+ $options->ClientSubmit=false;
+ $page=$this->getPage();
+ if($this->getCausesValidation() && $page->getValidators($this->getValidationGroup())->getCount()>0)
+ {
+ $options->PerformValidation=true;
+ $options->ValidationGroup=$this->getValidationGroup();
+ }
+ if($this->getPostBackUrl()!=='')
+ $options->ActionUrl=$this->getPostBackUrl();
+ return $options;
+ }
+
+ /**
+ * This method checks if the TImageButton is clicked and loads the coordinates of the clicking position.
+ * This method is primarly used by framework developers.
+ * @param string the key that can be used to retrieve data from the input data collection
+ * @param array the input data collection
+ * @return boolean whether the data of the component has been changed
+ */
+ public function loadPostData($key,$values)
+ {
+ $uid=$this->getUniqueID();
+ if(isset($values["{$uid}_x"]) && isset($values["{$uid}_y"]))
+ {
+ $this->_x=intval($values["{$uid}_x"]);
+ $this->_y=intval($values["{$uid}_y"]);
+ $page=$this->getPage()->registerRequiresRaiseEvent($this);
+ }
+ return false;
+ }
+
+ /**
+ * Raises postback event.
+ * The implementation of this function should raise appropriate event(s) (e.g. OnClick, OnCommand)
+ * indicating the component is responsible for the postback event.
+ * This method is primarily used by framework developers.
+ * @param string the parameter associated with the postback event
+ */
+ public function raisePostBackEvent($param)
+ {
+ if($this->getCausesValidation())
+ $this->getPage()->validate($this->getValidationGroup());
+ $this->onClick(new TImageClickEventParameter($this->_x,$this->_y));
+ $this->onCommand(new TCommandEventParameter($this->getCommandName(),$this->getCommandParameter()));
+ }
+
+ /**
+ * A dummy implementation for the IPostBackDataHandler interface.
+ */
+ public function raisePostDataChangedEvent()
+ {
+ // no post data to handle
+ }
+
+ /**
+ * This method is invoked when the component is clicked.
+ * The method raises 'Click' event to fire up the event delegates.
+ * If you override this method, be sure to call the parent implementation
+ * so that the event delegates can be invoked.
+ * @param TEventParameter event parameter to be passed to the event handlers
+ */
+ public function onClick($param)
+ {
+ $this->raiseEvent('Click',$this,$param);
+ }
+
+ /**
+ * This method is invoked when the component is clicked.
+ * The method raises 'Command' event to fire up the event delegates.
+ * If you override this method, be sure to call the parent implementation
+ * so that the event delegates can be invoked.
+ * @param TCommandEventParameter event parameter to be passed to the event handlers
+ */
+ public function onCommand($param)
+ {
+ $this->raiseEvent('Command',$this,$param);
+ $this->raiseBubbleEvent($this,$param);
+ }
+
+ protected function onPreRender($param)
+ {
+ parent::onPreRender($param);
+ $this->getPage()->registerRequiresPostBack($this);
+ }
+
+ /**
+ * @return string the command name associated with the <b>OnCommand</b> event.
+ */
+ public function getCommandName()
+ {
+ return $this->getViewState('CommandName','');
+ }
+
+ /**
+ * Sets the command name associated with the <b>OnCommand</b> event.
+ * @param string the text caption to be set
+ */
+ public function setCommandName($value)
+ {
+ $this->setViewState('CommandName',$value,'');
+ }
+
+ /**
+ * @return string the parameter associated with the <b>OnCommand</b> event
+ */
+ public function getCommandParameter()
+ {
+ return $this->getViewState('CommandParameter','');
+ }
+
+ /**
+ * Sets the parameter associated with the <b>OnCommand</b> event.
+ * @param string the text caption to be set
+ */
+ public function setCommandParameter($value)
+ {
+ $this->setViewState('CommandParameter',$value,'');
+ }
+
+ /**
+ * @return boolean whether postback event trigger by this button will cause input validation
+ */
+ public function getCausesValidation()
+ {
+ return $this->getViewState('CausesValidation',true);
+ }
+
+ /**
+ * Sets the value indicating whether postback event trigger by this button will cause input validation.
+ * @param string the text caption to be set
+ */
+ public function setCausesValidation($value)
+ {
+ $this->setViewState('CausesValidation',$value,true);
+ }
+
+ /**
+ * @return string the group of validators which the button causes validation upon postback
+ */
+ public function getValidationGroup()
+ {
+ return $this->getViewState('ValidationGroup','');
+ }
+
+ /**
+ * @param string the group of validators which the button causes validation upon postback
+ */
+ public function setValidationGroup($value)
+ {
+ $this->setViewState('ValidationGroup',$value,'');
+ }
+
+ /**
+ * @return string the URL of the page to post to when the button is clicked, default is empty meaning post to the current page itself
+ */
+ public function getPostBackUrl()
+ {
+ return $this->getViewState('PostBackUrl','');
+ }
+
+ /**
+ * @param string the URL of the page to post to from the current page when the button is clicked, empty if post to the current page itself
+ */
+ public function setPostBackUrl($value)
+ {
+ $this->setViewState('PostBackUrl',$value,'');
+ }
+
+ /**
+ * @return string the javascript to be executed when the button is clicked
+ */
+ public function getOnClientClick()
+ {
+ return $this->getViewState('OnClientClick','');
+ }
+
+ /**
+ * @param string the javascript to be executed when the button is clicked. Do not prefix it with "javascript:".
+ */
+ public function setOnClientClick($value)
+ {
+ $this->setViewState('OnClientClick',$value,'');
+ }
+
+ /**
+ * @return string caption of the button
+ */
+ public function getText()
+ {
+ return $this->getAlternateText();
+ }
+
+ /**
+ * @param string caption of the button
+ */
+ public function setText($value)
+ {
+ $this->setAlternateText($value);
+ }
+}
+
+/**
+ * TImageClickEventParameter class
+ *
+ * TImageClickEventParameter encapsulates the parameter data for <b>OnClick</b>
+ * event of TImageButton components.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version v1.0, last update on 2004/08/13 21:44:52
+ * @package System.Web.UI.WebControls
+ */
+class TImageClickEventParameter extends TEventParameter
+{
+ /**
+ * the X coordinate of the clicking point
+ * @var integer
+ */
+ public $x=0;
+ /**
+ * the Y coordinate of the clicking point
+ * @var integer
+ */
+ public $y=0;
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TLabel.php b/framework/Web/UI/WebControls/TLabel.php
new file mode 100644
index 00000000..464a4cd7
--- /dev/null
+++ b/framework/Web/UI/WebControls/TLabel.php
@@ -0,0 +1,106 @@
+<?php
+/**
+ * TLabel class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TLabel class
+ *
+ * TLabel represents a label control that displays text on a Web pagge.
+ * Use <b>Text</b> property to set the text to be displayed.
+ * TLabel will render the contents enclosed within its component tag
+ * if <b>Text</b> is empty.
+ * To use TLabel as a form label, associate it with a control by setting the
+ * <b>AssociateControlID</b> property. The associated control must be locatable
+ * within the label's naming container.
+ *
+ * Note, <b>Text</b> will NOT be encoded for rendering.
+ * Make usre it does not contain dangerous characters that you want to avoid.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TLabel extends TWebControl
+{
+ /**
+ * @return string tag name of the label, returns 'label' if there is an associated control, 'span' otherwise.
+ */
+ protected function getTagName()
+ {
+ return ($this->getAssociatedControlID()==='')?'span':'label';
+ }
+
+ /**
+ * Adds attributes to renderer.
+ * @param THtmlTextWriter the renderer
+ * @throws TInvalidDataValueException if associated control cannot be found using the ID
+ */
+ protected function addAttributesToRender($writer)
+ {
+ if(($aid=$this->getAssociatedControlID())!=='')
+ {
+ if($control=$this->findControl($aid))
+ $writer->addAttribute('for',$control->getClientID());
+ else
+ throw new TInvalidDataValueException('control_not_found',$aid);
+ }
+ parent::addAttributesToRender($writer);
+ }
+
+ /**
+ * Renders the body content of the label.
+ * @param THtmlTextWriter the renderer
+ */
+ protected function renderContents($writer)
+ {
+ if(($text=$this->getText())==='')
+ parent::renderContents($writer);
+ else
+ $writer->write($text);
+ }
+
+ /**
+ * @return string the text value of the label
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * @param string the text value of the label
+ */
+ public function setText($value)
+ {
+ $this->setViewState('Text',$value,'');
+ }
+
+ /**
+ * @return string the associated control ID
+ */
+ public function getAssociatedControlID()
+ {
+ return $this->getViewState('AssociatedControlID','');
+ }
+
+ /**
+ * Sets the ID of the control that the label is associated with.
+ * The control must be locatable via {@link TControl::findControl} using the ID.
+ * @param string the associated control ID
+ */
+ public function setAssociatedControlID($value)
+ {
+ $this->setViewState('AssociatedControlID',$value,'');
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TLiteral.php b/framework/Web/UI/WebControls/TLiteral.php
new file mode 100644
index 00000000..0509724a
--- /dev/null
+++ b/framework/Web/UI/WebControls/TLiteral.php
@@ -0,0 +1,79 @@
+<?php
+/**
+ * TLiteral class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TLiteral class
+ *
+ * TLiteral reserves a location on the Web page to display static text or body content.
+ * The TLiteral control is similar to the TLabel control, except the TLiteral
+ * control does not allow you to apply a style to the displayed text.
+ * You can programmatically control the text displayed in the control by setting
+ * the <b>Text</b> property. If the <b>Text</b> property is empty, the content
+ * enclosed within the TLiteral control will be displayed. This is very useful
+ * for reserving a location on a page because you can add text and controls
+ * as children of TLiteral control and they will be rendered at the place.
+ *
+ * Note, <b>Text</b> is not HTML encoded before it is displayed in the TLiteral component.
+ * If the values for the component come from user input, be sure to validate the values
+ * to help prevent security vulnerabilities.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TLiteral extends TControl
+{
+ /**
+ * @return string the static text of the TLiteral
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * Sets the static text of the TLiteral
+ * @param string the text to be set
+ */
+ public function setText($value)
+ {
+ $this->setViewState('Text',$value,'');
+ }
+
+ public function getEncode()
+ {
+ return $this->getViewState('Encode',false);
+ }
+
+ public function setEncode($value)
+ {
+ $this->setViewState('Encode',$value,false);
+ }
+
+ /**
+ * Renders the evaluation result of the statements.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function render($writer)
+ {
+ if(($text=$this->getText())!=='')
+ {
+ if($this->getEncode())
+ $writer->write(THttpUtility::htmlEncode($text));
+ else
+ $writer->write($text);
+ }
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TPanel.php b/framework/Web/UI/WebControls/TPanel.php
new file mode 100644
index 00000000..36f70479
--- /dev/null
+++ b/framework/Web/UI/WebControls/TPanel.php
@@ -0,0 +1,162 @@
+<?php
+/**
+ * TPanel class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TPanel class
+ *
+ * TPanel represents a component that acts as a container for other component.
+ * It is especially useful when you want to generate components programmatically or hide/show a group of components.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TPanel extends TWebControl
+{
+ /**
+ * @return string tag name of the panel
+ */
+ protected function getTagName()
+ {
+ return 'div';
+ }
+
+ /**
+ * Adds attributes to renderer.
+ * @param THtmlTextWriter the renderer
+ */
+ protected function addAttributesToRender($writer)
+ {
+ $url=trim($this->getBackImageUrl());
+ if($url!=='')
+ $this->getStyle
+ base.AddAttributesToRender(writer);
+ string text1 = this.BackImageUrl;
+ if (text1.Trim().Length > 0)
+ {
+ writer.AddStyleAttribute(HtmlTextWriterStyle.BackgroundImage, "url(" + base.ResolveClientUrl(text1) + ")");
+ }
+ this.AddScrollingAttribute(this.ScrollBars, writer);
+ HorizontalAlign align1 = this.HorizontalAlign;
+ if (align1 != HorizontalAlign.NotSet)
+ {
+ TypeConverter converter1 = TypeDescriptor.GetConverter(typeof(HorizontalAlign));
+ writer.AddStyleAttribute(HtmlTextWriterStyle.TextAlign, converter1.ConvertToInvariantString(align1).ToLowerInvariant());
+ }
+ if (!this.Wrap)
+ {
+ if (base.EnableLegacyRendering)
+ {
+ writer.AddAttribute(HtmlTextWriterAttribute.Nowrap, "nowrap", false);
+ }
+ else
+ {
+ writer.AddStyleAttribute(HtmlTextWriterStyle.WhiteSpace, "nowrap");
+ }
+ }
+ if (this.Direction == ContentDirection.LeftToRight)
+ {
+ writer.AddAttribute(HtmlTextWriterAttribute.Dir, "ltr");
+ }
+ else if (this.Direction == ContentDirection.RightToLeft)
+ {
+ writer.AddAttribute(HtmlTextWriterAttribute.Dir, "rtl");
+ }
+ if (((!base.DesignMode && (this.Page != null)) && ((this.Page.Request != null) && (this.Page.Request.Browser.EcmaScriptVersion.Major > 0))) && ((this.Page.Request.Browser.W3CDomVersion.Major > 0) && (this.DefaultButton.Length > 0)))
+ {
+ Control control1 = this.FindControl(this.DefaultButton);
+ if (control1 is IButtonControl)
+ {
+ this.Page.ClientScript.RegisterDefaultButtonScript(control1, writer, true);
+ }
+ else
+ {
+ object[] objArray1 = new object[1] { this.ID } ;
+ throw new InvalidOperationException(SR.GetString("HtmlForm_OnlyIButtonControlCanBeDefaultButton", objArray1));
+ }
+ }
+
+ }
+
+ /**
+ * @return boolean whether the content wraps within the panel.
+ */
+ public function getWrap()
+ {
+ return $this->getViewState('Wrap',true);
+ }
+
+ /**
+ * Sets the value indicating whether the content wraps within the panel.
+ * @param boolean whether the content wraps within the panel.
+ */
+ public function setWrap($value)
+ {
+ $this->setViewState('Wrap',$value,true);
+ }
+
+ /**
+ * @return string the horizontal alignment of the contents within the panel.
+ */
+ public function getHorizontalAlign()
+ {
+ return $this->getViewState('HorizontalAlign','');
+ }
+
+ /**
+ * Sets the horizontal alignment of the contents within the panel.
+ * Valid values include 'justify', 'left', 'center', 'right' or empty string.
+ * @param string the horizontal alignment
+ */
+ public function setHorizontalAlign($value)
+ {
+ $this->setViewState('HorizontalAlign',$value,'');
+ }
+
+ /**
+ * @return string the URL of the background image for the panel component.
+ */
+ public function getBackImageUrl()
+ {
+ return $this->getViewState('BackImageUrl','');
+ }
+
+ /**
+ * Sets the URL of the background image for the panel component.
+ * @param string the URL
+ */
+ public function setBackImageUrl($value)
+ {
+ $this->setViewState('BackImageUrl',$value,'');
+ }
+
+ /**
+ * This overrides the parent implementation by rendering more TPanel-specific attributes.
+ * @return ArrayObject the attributes to be rendered
+ */
+ protected function getAttributesToRender()
+ {
+ $url=$this->getBackImageUrl();
+ if(strlen($url))
+ $this->setStyle(array('background-image'=>"url($url)"));
+ $attributes=parent::getAttributesToRender();
+ $align=$this->getHorizontalAlign();
+ if(strlen($align))
+ $attributes['align']=$align;
+ if(!$this->isWrap())
+ $attributes['nowrap']='nowrap';
+ return $attributes;
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TPlaceHolder.php b/framework/Web/UI/WebControls/TPlaceHolder.php
new file mode 100644
index 00000000..9149e180
--- /dev/null
+++ b/framework/Web/UI/WebControls/TPlaceHolder.php
@@ -0,0 +1,25 @@
+<?php
+/**
+ * TPlaceHolder class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TPlaceHolder class
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TPlaceHolder extends TControl
+{
+}
+
+?>
diff --git a/framework/Web/UI/WebControls/TStatements.php b/framework/Web/UI/WebControls/TStatements.php
new file mode 100644
index 00000000..e0892f2b
--- /dev/null
+++ b/framework/Web/UI/WebControls/TStatements.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * TStatements class file
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TStatements class
+ *
+ * TStatements executes a set of PHP statements and renders the display
+ * generated by the statements. The execution happens during rendering stage.
+ * You can set the statements via the property <b>Statements</b>.
+ * You should also specify the context object by <b>Context</b> property
+ * which is used as the object in which the statements is evaluated.
+ * If the <b>Context</b> property is not set, the TStatements component
+ * itself will be assumed as the context.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TStatements extends TControl
+{
+ private $_s='';
+
+ /**
+ * @return string the statements to be executed
+ */
+ public function getStatements()
+ {
+ return $this->_s;
+ }
+
+ /**
+ * Sets the statements of the TStatements
+ * @param string the statements to be set
+ */
+ public function setStatements($value)
+ {
+ $this->_s=$value;
+ }
+
+ /**
+ * Renders the evaluation result of the statements.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function render($writer)
+ {
+ if($this->_s!=='')
+ $writer->write($this->evaluateStatements($this->_s));
+ }
+}
+
+?>
diff --git a/framework/Web/UI/WebControls/TStyle.php b/framework/Web/UI/WebControls/TStyle.php
new file mode 100644
index 00000000..e1e92b1b
--- /dev/null
+++ b/framework/Web/UI/WebControls/TStyle.php
@@ -0,0 +1,334 @@
+<?php
+/**
+ * TStyle class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TStyle class
+ *
+ * TStyle encapsulates the CSS style applied to a control.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TStyle extends TComponent
+{
+ /**
+ * @var array The enumerable type for border styles
+ */
+ public static $ENUM_BORDER_STYLE=array('NotSet','None','Dashed','Dotted','Solid','Double','Groove','Ridge','Inset','Outset');
+
+ /**
+ * Various CSS fields
+ */
+ const FLD_BACKCOLOR=0;
+ const FLD_BORDERCOLOR=1;
+ const FLD_BORDERWIDTH=2;
+ const FLD_BORDERSTYLE=3;
+ const FLD_FONT=4;
+ const FLD_FORECOLOR=5;
+ const FLD_HEIGHT=6;
+ const FLD_WIDTH=7;
+ const FLD_CSSCLASS=8;
+ const FLD_STYLE=9;
+
+ /**
+ * @var array storage of CSS fields
+ */
+ private $_data=array();
+
+ /**
+ * @return string the background color of the control
+ */
+ public function getBackColor()
+ {
+ return isset($this->_data[self::FLD_BACKCOLOR])?$this->_data[self::FLD_BACKCOLOR]:'';
+ }
+
+ /**
+ * @param string the background color of the control
+ */
+ public function setBackColor($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_BACKCOLOR]);
+ else
+ $this->_data[self::FLD_BACKCOLOR]=$value;
+ }
+
+ /**
+ * @return string the border color of the control
+ */
+ public function getBorderColor()
+ {
+ return isset($this->_data[self::FLD_BORDERCOLOR])?$this->_data[self::FLD_BORDERCOLOR]:'';
+ }
+
+ /**
+ * @param string the border color of the control
+ */
+ public function setBorderColor($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_BORDERCOLOR]);
+ else
+ $this->_data[self::FLD_BORDERCOLOR]=$value;
+ }
+
+ /**
+ * @return string the border style of the control
+ */
+ public function getBorderStyle()
+ {
+ return isset($this->_data[self::FLD_BORDERSTYLE])?$this->_data[self::FLD_BORDERSTYLE]:'';
+ }
+
+ /**
+ * Sets the border style of the control.
+ * Valid values include:
+ * 'NotSet','None','Dashed','Dotted','Solid','Double','Groove','Ridge','Inset','Outset'
+ * @param string the border style of the control
+ */
+ public function setBorderStyle($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_BORDERSTYLE]);
+ else
+ $this->_data[self::FLD_BORDERSTYLE]=TPropertyValue::ensureEnum($value,self::$ENUM_BORDER_STYLE);
+ }
+
+ /**
+ * @return string the border width of the control
+ */
+ public function getBorderWidth()
+ {
+ return isset($this->_data[self::FLD_BORDERWIDTH])?$this->_data[self::FLD_BORDERWIDTH]:'';
+ }
+
+ /**
+ * @param string the border width of the control
+ */
+ public function setBorderWidth($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_BORDERWIDTH]);
+ else
+ $this->_data[self::FLD_BORDERWIDTH]=$value;
+ }
+
+ /**
+ * @return string the CSS class of the control
+ */
+ public function getCssClass()
+ {
+ return isset($this->_data[self::FLD_CSSCLASS])?$this->_data[self::FLD_CSSCLASS]:'';
+ }
+
+ /**
+ * @param string the name of the CSS class of the control
+ */
+ public function setCssClass($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_CSSCLASS]);
+ else
+ $this->_data[self::FLD_CSSCLASS]=$value;
+ }
+
+ /**
+ * @return TFont the font of the control
+ */
+ public function getFont()
+ {
+ if(!isset($this->_data[self::FLD_FONT]))
+ $this->_data[self::FLD_FONT]=new TFont;
+ return $this->_data[self::FLD_FONT];
+ }
+
+ /**
+ * @return string the foreground color of the control
+ */
+ public function getForeColor()
+ {
+ return isset($this->_data[self::FLD_FORECOLOR])?$this->_data[self::FLD_FORECOLOR]:'';
+ }
+
+ /**
+ * @param string the foreground color of the control
+ */
+ public function setForeColor($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_FORECOLOR]);
+ else
+ $this->_data[self::FLD_FORECOLOR]=$value;
+ }
+
+ /**
+ * @return string the height of the control
+ */
+ public function getHeight()
+ {
+ return isset($this->_data[self::FLD_HEIGHT])?$this->_data[self::FLD_HEIGHT]:'';
+ }
+
+ /**
+ * @param string the height of the control
+ */
+ public function setHeight($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_HEIGHT]);
+ else
+ $this->_data[self::FLD_HEIGHT]=$value;
+ }
+
+ /**
+ * @return string the custom style of the control
+ */
+ public function getStyle()
+ {
+ return isset($this->_data[self::FLD_STYLE])?$this->_data[self::FLD_STYLE]:'';
+ }
+
+ /**
+ * @param string the custom style of the control
+ */
+ public function setStyle($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_STYLE]);
+ else
+ $this->_data[self::FLD_STYLE]=$value;
+ }
+
+ /**
+ * @return string the width of the control
+ */
+ public function getWidth()
+ {
+ return isset($this->_data[self::FLD_WIDTH])?$this->_data[self::FLD_WIDTH]:'';
+ }
+
+ /**
+ * @param string the width of the control
+ */
+ public function setWidth($value)
+ {
+ if($value==='')
+ unset($this->_data[self::FLD_WIDTH]);
+ else
+ $this->_data[self::FLD_WIDTH]=$value;
+ }
+
+ /**
+ * @param boolean if the style contains nothing
+ */
+ public function getIsEmpty()
+ {
+ return empty($this->_data) || (isset($this->_data[self::FLD_FONT]) && $this->_data[self::FLD_FONT]->getIsEmpty());
+ }
+
+ /**
+ * Resets the style to the original empty state.
+ */
+ public function reset()
+ {
+ $this->_data=array();
+ $this->flags=0;
+ }
+
+ /**
+ * Merges the current style with another one.
+ * If the two styles have the same style field, the new one
+ * will overwrite the current one.
+ * @param TStyle the new style
+ */
+ public function mergeWith($style)
+ {
+ if($style===null)
+ return;
+ if(isset($style->_data[self::FLD_BACKCOLOR]))
+ $this->_data[self::FLD_BACKCOLOR]=$style->_data[self::FLD_BACKCOLOR];
+ if(isset($style->_data[self::FLD_BORDERCOLOR]))
+ $this->_data[self::FLD_BORDERCOLOR]=$style->_data[self::FLD_BORDERCOLOR];
+ if(isset($style->_data[self::FLD_BORDERWIDTH]))
+ $this->_data[self::FLD_BORDERWIDTH]=$style->_data[self::FLD_BORDERWIDTH];
+ if(isset($style->_data[self::FLD_BORDERSTYLE]))
+ $this->_data[self::FLD_BORDERSTYLE]=$style->_data[self::FLD_BORDERSTYLE];
+ if(isset($style->_data[self::FLD_FORECOLOR]))
+ $this->_data[self::FLD_FORECOLOR]=$style->_data[self::FLD_FORECOLOR];
+ if(isset($style->_data[self::FLD_HEIGHT]))
+ $this->_data[self::FLD_HEIGHT]=$style->_data[self::FLD_HEIGHT];
+ if(isset($style->_data[self::FLD_WIDTH]))
+ $this->_data[self::FLD_WIDTH]=$style->_data[self::FLD_WIDTH];
+ if(isset($style->_data[self::FLD_FONT]))
+ $this->getFont()->mergeWith($style->_data[self::FLD_FONT]);
+ if(isset($style->_data[self::FLD_CSSCLASS]))
+ $this->_data[self::FLD_CSSCLASS]=$style->_data[self::FLD_CSSCLASS];
+ }
+
+ /**
+ * Copies from a style.
+ * Existing style will be reset first.
+ * @param TStyle the new style
+ */
+ public function copyFrom($style)
+ {
+ $this->reset();
+ $this->mergeWith($style);
+ }
+
+ /**
+ * Converts the style into a string representation suitable for rendering.
+ * @return string the string representation of the style
+ */
+ public function toString()
+ {
+ if($this->getIsEmpty())
+ return '';
+ if(($str=$this->getStyle())!=='')
+ $str=rtrim($str).';';
+ if(isset($this->_data[self::FLD_BACKCOLOR]))
+ $str.='background-color:'.$this->_data[self::FLD_BACKCOLOR].';';
+ if(isset($this->_data[self::FLD_BORDERCOLOR]))
+ $str.='border-color:'.$this->_data[self::FLD_BORDERCOLOR].';';
+ if(isset($this->_data[self::FLD_BORDERWIDTH]))
+ $str.='border-width:'.$this->_data[self::FLD_BORDERWIDTH].';';
+ if(isset($this->_data[self::FLD_BORDERSTYLE]))
+ $str.='border-style:'.$this->_data[self::FLD_BORDERSTYLE].';';
+ if(isset($this->_data[self::FLD_FORECOLOR]))
+ $str.='color:'.$this->_data[self::FLD_FORECOLOR].';';
+ if(isset($this->_data[self::FLD_HEIGHT]))
+ $str.='height:'.$this->_data[self::FLD_HEIGHT].';';
+ if(isset($this->_data[self::FLD_WIDTH]))
+ $str.='width:'.$this->_data[self::FLD_WIDTH].';';
+ if(isset($this->_data[self::FLD_FONT]))
+ $str.=$this->_data[self::FLD_FONT]->toString();
+ return $str;
+ }
+
+ /**
+ * Adds attributes related to CSS styles to renderer.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ public function addAttributesToRender($writer)
+ {
+ $str=$this->toString();
+ if($str!=='')
+ $writer->addAttribute('style',$str);
+ if(isset($this->_data[self::FLD_CSSCLASS]))
+ $writer->addAttribute('class',$this->_data[self::FLD_CSSCLASS]);
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TTextBox.php b/framework/Web/UI/WebControls/TTextBox.php
new file mode 100644
index 00000000..700906e8
--- /dev/null
+++ b/framework/Web/UI/WebControls/TTextBox.php
@@ -0,0 +1,444 @@
+<?php
+/**
+ * TTextBox class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TTextBox class
+ *
+ * TTextBox displays a text box on the Web page for user input.
+ * The text displayed in the TTextBox control is determined by the <b>Text</b> property.
+ * You can create a <b>SingleLine</b>, a <b>MultiLine</b>, or a <b>Password</b> text box
+ * by setting the <b>TextMode</b> property.
+ * If the TTextBox control is a multiline text box, the number of rows
+ * it displays is determined by the <b>Rows</b> property, and the <b>Wrap</b> property
+ * can be used to determine whether to wrap the text in the component.
+ *
+ * To specify the display width of the text box, in characters, set the <b>Columns</b> property.
+ * To prevent the text displayed in the component from being modified,
+ * set the <b>ReadOnly</b> property to true. If you want to limit the user input
+ * to a specified number of characters, set the <b>MaxLength</b> property. To use AutoComplete
+ * feature, set the <b>AutoCompleteType</b> property.
+ *
+ * If <b>AutoPostBack</b> is set true, updating the text box and then changing the focus out of it
+ * will cause postback action. And if <b>CausesValidation</b> is true, validation will also
+ * be processed, which can be further restricted within a <b>ValidationGroup</b>.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TTextBox extends TWebControl implements IPostBackDataHandler, IValidatable
+{
+ /**
+ * @var array enumeration of the valid AutoCompleteType values.
+ */
+ public static $AUTO_COMPLETE_TYPE=array('BusinessCity','BusinessCountryRegion','BusinessFax','BusinessPhone','BusinessState','BusinessStreetAddress','BusinessUrl','BusinessZipCode','Cellular','Company','Department','Disabled','DisplayName','Email','FirstName','Gender','HomeCity','HomeCountryRegion','HomeFax','Homepage','HomePhone','HomeState','HomeStreetAddress','HomeZipCode','JobTitle','LastName','MiddleName','None','Notes','Office','Pager','Search');
+ /**
+ * @var array enumeration of the valid TextMode values.
+ */
+ public static $TEXT_MODE=array('SingleLine','MultiLine','Password');
+
+ /**
+ * @return string tag name of the textbox
+ */
+ protected function getTagName()
+ {
+ return ($this->getTextMode()==='MultiLine')?'textarea':'input';
+ }
+
+ /**
+ * Processes an object that is created during parsing template.
+ * This overrides the parent implementation by forbidding any body components.
+ * @param mixed the newly created object in template
+ * @throws TInvalidOperationException if a component is found within body
+ */
+ public function addParsedObject($object)
+ {
+ if(!is_string($object))
+ throw new TInvalidOperationException('body_contents_not_allowed',get_class($this).':'.$this->getUniqueID());
+ }
+
+ /**
+ * Adds attribute name-value pairs to renderer.
+ * This overrides the parent implementation with additional textbox specific attributes.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function addAttributesToRender($writer)
+ {
+ $page=$this->getPage();
+ $page->ensureRenderInForm($this);
+ if(($uid=$this->getUniqueID())!=='')
+ $writer->addAttribute('name',$uid);
+ if(($textMode=$this->getTextMode())==='MultiLine')
+ {
+ if(($rows=$this->getRows())>0)
+ $writer->addAttribute('rows',$rows);
+ if(($cols=$this->getColumns())>0)
+ $writer->addAttribute('cols',$cols);
+ if(!$this->getWrap())
+ $writer->addAttribute('wrap','off');
+ }
+ else
+ {
+ if($textMode==='SingleLine')
+ {
+ $writer->addAttribute('type','text');
+ if(($text=$this->getText())!=='')
+ $writer->addAttribute('value',$text);
+ if(($act=$this->getAutoCompleteType())!=='None')
+ {
+ if($act==='Disabled')
+ $writer->addAttribute('autocomplete','off');
+ else if($act==='Search')
+ $writer->addAttribute('vcard_name','search');
+ else if($act==='HomeCountryRegion')
+ $writer->addAttribute('vcard_name','HomeCountry');
+ else if($act==='BusinessCountryRegion')
+ $writer->addAttribute('vcard_name','BusinessCountry');
+ else
+ {
+ if(($pos=strpos($act,'Business'))===0)
+ $act='Business'.'.'.substr($act,8);
+ else if(($pos=strpos($act,'Home'))===0)
+ $act='Home'.'.'.substr($act,4);
+ $writer->addAttribute('vcard_name','vCard.'.$act);
+ }
+ }
+ }
+ else
+ {
+ $writer->addAttribute('type','password');
+ }
+ if(($cols=$this->getColumns())>0)
+ $writer->addAttribute('size',$cols);
+ if(($maxLength=$this->getMaxLength())>0)
+ $writer->addAttribute('maxlength',$maxLength);
+ }
+ if($this->getReadOnly())
+ $writer->addAttribute('readonly','readonly');
+ if(!$this->getEnabled(true) && $this->getEnabled()) // in this case parent will not render 'disabled'
+ $writer->addAttribute('disabled','disabled');
+ if($this->getAutoPostBack() && $page->getClientSupportsJavaScript())
+ {
+ $onchange='';
+ $onkeypress='if (WebForm_TextBoxKeyHandler() == false) return false;';
+ if($this->getHasAttributes())
+ {
+ $attributes=$this->getAttributes();
+ $onchange=$attributes->itemAt('onchange');
+ if($onchange!=='')
+ $onchange=rtrim($onchange,';').';';
+ $attributes->remove('onchange');
+ $onkeypress.=$attributes->itemAt('onkeypress');
+ $attributes->remove('onkeypress');
+ }
+
+ $option=new TPostBackOptions($this);
+ if($this->getCausesValidation())
+ {
+ $option->PerformValidation=true;
+ $option->ValidationGroup=$this->getValidationGroup();
+ }
+ if($page->getForm())
+ $option->AutoPostBack=true;
+ $onchange.=$page->getClientScript()->getPostBackEventReference($option);
+ $writer->addAttribute('onchange',$onchange);
+ $writer->addAttribute('onkeypress',$onkeypress);
+ }
+ parent::addAttributesToRender($writer);
+ }
+
+ /**
+ * Loads user input data.
+ * This method is primarly used by framework developers.
+ * @param string the key that can be used to retrieve data from the input data collection
+ * @param array the input data collection
+ * @return boolean whether the data of the component has been changed
+ */
+ public function loadPostData($key,$values)
+ {
+ $value=$values[$key];
+ if(!$this->getReadOnly() && $this->getText()!==$value)
+ {
+ $this->setText($value);
+ return true;
+ }
+ else
+ return false;
+ }
+
+ protected function onPreRender($param)
+ {
+ parent::onPreRender($param);
+ if(($page=$this->getPage()) && $this->getEnabled(true))
+ {
+ // TODO
+ //if($this->getTextMode()==='Password' || ($this->hasEventHandler('TextChanged') && $this->getVisible()))
+ // $page->registerEnabledControl($this);
+ if($this->getAutoPostBack())
+ {
+ $page->registerWebFormsScript();
+ $page->registerPostBackScript();
+ $page->registerFocusScript();
+ }
+ }
+ }
+
+ /**
+ * Returns the value to be validated.
+ * This methid is required by IValidatable interface.
+ * @return mixed the value of the property to be validated.
+ */
+ public function getValidationPropertyValue()
+ {
+ return $this->getText();
+ }
+
+ /**
+ * This method is invoked when the value of the <b>Text</b> property changes on postback.
+ * The method raises 'TextChanged' event.
+ * If you override this method, be sure to call the parent implementation to ensure
+ * the invocation of the attached event handlers.
+ * @param TEventParameter event parameter to be passed to the event handlers
+ */
+ protected function onTextChanged($param)
+ {
+ $this->raiseEvent('TextChanged',$this,$param);
+ }
+
+ /**
+ * Raises postdata changed event.
+ * This method is required by IPostBackDataHandler interface.
+ * It is invoked by the framework when <b>Text</b> property is changed on postback.
+ * This method is primarly used by framework developers.
+ */
+ public function raisePostDataChangedEvent()
+ {
+ $page=$this->getPage();
+ if($this->getAutoPostBack() && !$page->getIsPostBackEventControlRegistered())
+ {
+ $page->setAutoPostBackControl($this);
+ if($this->getCausesValidation())
+ $page->validate($this->getValidationGroup());
+ }
+ $this->onTextChanged(new TEventParameter);
+ }
+
+ /**
+ * Renders the body content of the textbox when it is in MultiLine text mode.
+ * @param THtmlTextWriter the writer for rendering
+ */
+ protected function renderContents($writer)
+ {
+ if($this->getTextMode()==='MultiLine')
+ $writer->write(THttpUtility::htmlEncode($this->getText()));
+ }
+
+ /**
+ * @return string the AutoComplete type of the textbox
+ */
+ public function getAutoCompleteType()
+ {
+ return $this->getViewState('AutoCompleteType','None');
+ }
+
+ /**
+ * @param string the AutoComplete type of the textbox, default value is 'None'.
+ * Valid values include:
+ * 'BusinessCity','BusinessCountryRegion','BusinessFax','BusinessPhone',
+ * 'BusinessState','BusinessStreetAddress','BusinessUrl','BusinessZipCode',
+ * 'Cellular','Company','Department','Disabled','DisplayName','Email',
+ * 'FirstName','Gender','HomeCity','HomeCountryRegion','HomeFax','Homepage',
+ * 'HomePhone','HomeState','HomeStreetAddress','HomeZipCode','JobTitle',
+ * 'LastName','MiddleName','None','Notes','Office','Pager','Search'
+ * @throws TInvalidDataValueException if the input parameter is not a valid AutoComplete type
+ */
+ public function setAutoCompleteType($value)
+ {
+ $this->setViewState('AutoCompleteType',TPropertyValue::ensureEnum($value,self::$AUTO_COMPLETE_TYPE),'None');
+ }
+
+ /**
+ * @return boolean a value indicating whether an automatic postback to the server
+ * will occur whenever the user modifies the text in the TTextBox control and
+ * then tabs out of the component.
+ */
+ public function getAutoPostBack()
+ {
+ return $this->getViewState('AutoPostBack',false);
+ }
+
+ /**
+ * Sets the value indicating if postback automatically.
+ * An automatic postback to the server will occur whenever the user
+ * modifies the text in the TTextBox control and then tabs out of the component.
+ * @param boolean the value indicating if postback automatically
+ */
+ public function setAutoPostBack($value)
+ {
+ $this->setViewState('AutoPostBack',TPropertyValue::ensureBoolean($value),false);
+ }
+
+ /**
+ * @return boolean whether postback event trigger by this text box will cause input validation, default is true.
+ */
+ public function getCausesValidation()
+ {
+ return $this->getViewState('CausesValidation',true);
+ }
+
+ /**
+ * Sets the value indicating whether postback event trigger by this text box will cause input validation.
+ * @param boolean whether postback event trigger by this button will cause input validation.
+ */
+ public function setCausesValidation($value)
+ {
+ $this->setViewState('CausesValidation',TPropertyValue::ensureBoolean($value),true);
+ }
+
+ /**
+ * @return integer the display width of the text box in characters, default is 0 meaning not set.
+ */
+ public function getColumns()
+ {
+ return $this->getViewState('Columns',0);
+ }
+
+ /**
+ * Sets the display width of the text box in characters.
+ * @param integer the display width, set it 0 to clear the setting
+ */
+ public function setColumns($value)
+ {
+ $this->setViewState('Columns',TPropertyValue::ensureInteger($value),0);
+ }
+
+ /**
+ * @return integer the maximum number of characters allowed in the text box, default is 0 meaning not set.
+ */
+ public function getMaxLength()
+ {
+ return $this->getViewState('MaxLength',0);
+ }
+
+ /**
+ * Sets the maximum number of characters allowed in the text box.
+ * @param integer the maximum length, set it 0 to clear the setting
+ */
+ public function setMaxLength($value)
+ {
+ $this->setViewState('MaxLength',TPropertyValue::ensureInteger($value),0);
+ }
+
+ /**
+ * @return boolean whether the textbox is read only, default is false
+ */
+ public function getReadOnly()
+ {
+ return $this->getViewState('ReadOnly',false);
+ }
+
+ /**
+ * @param boolean whether the textbox is read only
+ */
+ public function setReadOnly($value)
+ {
+ $this->setViewState('ReadOnly',TPropertyValue::ensureBoolean($value),false);
+ }
+
+ /**
+ * @return integer the number of rows displayed in a multiline text box, default is 4
+ */
+ public function getRows()
+ {
+ return $this->getViewState('Rows',4);
+ }
+
+ /**
+ * Sets the number of rows displayed in a multiline text box.
+ * @param integer the number of rows, set it 0 to clear the setting
+ */
+ public function setRows($value)
+ {
+ $this->setViewState('Rows',TPropertyValue::ensureInteger($value),4);
+ }
+
+ /**
+ * @return string the text content of the TTextBox control.
+ */
+ public function getText()
+ {
+ return $this->getViewState('Text','');
+ }
+
+ /**
+ * Sets the text content of the TTextBox control.
+ * @param string the text content
+ */
+ public function setText($value)
+ {
+ $this->setViewState('Text',$value,'');
+ }
+
+ /**
+ * @return string the behavior mode (SingleLine, MultiLine, or Password) of the TTextBox component.
+ */
+ public function getTextMode()
+ {
+ return $this->getViewState('TextMode','SingleLine');
+ }
+
+ /**
+ * Sets the behavior mode (SingleLine, MultiLine, or Password) of the TTextBox component.
+ * @param string the text mode
+ * @throws TInvalidDataValueException if the input value is not a valid text mode.
+ */
+ public function setTextMode($value)
+ {
+ $this->setViewState('TextMode',TPropertyValue::ensureEnum($value,self::$TEXT_MODE),'SingleLine');
+ }
+
+ /**
+ * @return string the group of validators which the text box causes validation upon postback
+ */
+ public function getValidationGroup()
+ {
+ return $this->getViewState('ValidationGroup','');
+ }
+
+ /**
+ * @param string the group of validators which the text box causes validation upon postback
+ */
+ public function setValidationGroup($value)
+ {
+ $this->setViewState('ValidationGroup',$value,'');
+ }
+
+ /**
+ * @return boolean whether the text content wraps within a multiline text box.
+ */
+ public function getWrap()
+ {
+ return $this->getViewState('Wrap',true);
+ }
+
+ /**
+ * Sets the value indicating whether the text content wraps within a multiline text box.
+ * @param boolean whether the text content wraps within a multiline text box.
+ */
+ public function setWrap($value)
+ {
+ $this->setViewState('Wrap',TPropertyValue::ensureBoolean($value),true);
+ }
+}
+
+?> \ No newline at end of file
diff --git a/framework/Web/UI/WebControls/TWebControl.php b/framework/Web/UI/WebControls/TWebControl.php
new file mode 100644
index 00000000..8a9765f7
--- /dev/null
+++ b/framework/Web/UI/WebControls/TWebControl.php
@@ -0,0 +1,368 @@
+<?php
+/**
+ * TWebControl class file.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.xisc.com/
+ * @copyright Copyright &copy; 2004-2005, Qiang Xue
+ * @license http://www.opensource.org/licenses/bsd-license.php BSD License
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ */
+
+/**
+ * TWebControl class
+ *
+ * TWebControl is the base class for controls that share a common set
+ * of UI-related properties and methods. TWebControl derived controls
+ * are usually corresponding to HTML tags. They thus have tag name, attributes
+ * and body contents. You can override {@link getTagName} to specify the tag name,
+ * {@link addAttributesToRender} to specify the attributes to be rendered,
+ * and {@link renderContents} to customize the body content rendering.
+ * TWebControl encapsulates a set of properties related with CSS style fields,
+ * such as <b>BackColor</b>, <b>BorderWidth</b>, etc.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @version $Revision: $ $Date: $
+ * @package System.Web.UI.WebControls
+ * @since 3.0
+ */
+class TWebControl extends TControl
+{
+ /**
+ * @return string the access key of the control
+ */
+ public function getAccessKey()
+ {
+ return $this->getViewState('AccessKey','');
+ }
+
+ /**
+ * Sets the access key of the control.
+ * Only one-character string can be set, or an exception will be raised.
+ * Pass empty string if you want to disable access key.
+ * @param string the access key to be set
+ * @throws TInvalidDataValueException if the access key is specified with more than one character
+ */
+ public function setAccessKey($value)
+ {
+ if(strlen($value)>1)
+ throw new TInvalidDataValueException('invalid_accesskey',get_class($this));
+ $this->setViewState('AccessKey',$value,'');
+ }
+
+ /**
+ * @return string the background color of the control
+ */
+ public function getBackColor()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getBackColor();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the background color of the control
+ */
+ public function setBackColor($value)
+ {
+ $this->getStyle()->setBackColor($value);
+ }
+
+ /**
+ * @return string the border color of the control
+ */
+ public function getBorderColor()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getBorderColor();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the border color of the control
+ */
+ public function setBorderColor($value)
+ {
+ $this->getStyle()->setBorderColor($value);
+ }
+
+ /**
+ * @return string the border style of the control
+ */
+ public function getBorderStyle()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getBorderStyle();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the border style of the control
+ */
+ public function setBorderStyle($value)
+ {
+ $this->getStyle()->setBorderStyle($value);
+ }
+
+ /**
+ * @return string the border width of the control
+ */
+ public function getBorderWidth()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getBorderWidth();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the border width of the control
+ */
+ public function setBorderWidth($value)
+ {
+ $this->getStyle()->setBorderWidth($value);
+ }
+
+ /**
+ * @return TFont the font of the control
+ */
+ public function getFont()
+ {
+ return $this->getStyle()->getFont();
+ }
+
+ /**
+ * @return string the foreground color of the control
+ */
+ public function getForeColor()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getForeColor();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the foreground color of the control
+ */
+ public function setForeColor($value)
+ {
+ $this->getStyle()->setForeColor($value);
+ }
+
+ /**
+ * @return string the height of the control
+ */
+ public function getHeight()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getHeight();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the css class of the control
+ */
+ public function setCssClass($value)
+ {
+ $this->getStyle()->setCssClass($value);
+ }
+
+ /**
+ * @return string the css class of the control
+ */
+ public function getCssClass()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getCssClass();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the height of the control
+ */
+ public function setHeight($value)
+ {
+ $this->getStyle()->setHeight($value);
+ }
+
+ public function getStyleCreated()
+ {
+ return $this->getViewState('Style',null)!==null;
+ }
+
+ /**
+ * @return TStyle the object representing the css style of the control
+ */
+ public function getStyle()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style;
+ else
+ {
+ $style=new TStyle;
+ $this->setViewState('Style',$style,null);
+ return $style;
+ }
+ }
+
+ /**
+ * Sets the css style string of the control.
+ * The style string will be prefixed to the styles set via other control properties (e.g. Height, Width).
+ * @param string the css style string
+ * @throws TInvalidDataValueException if the parameter is not a string
+ */
+ public function setStyle($value)
+ {
+ if(is_string($value))
+ $this->getStyle()->setStyle($value);
+ else
+ throw new TInvalidDataValueException('invalid_style_value',get_class($this));
+ }
+
+ /**
+ * @return integer the tab index of the control
+ */
+ public function getTabIndex()
+ {
+ return $this->getViewState('TabIndex',0);
+ }
+
+ /**
+ * Sets the tab index of the control.
+ * Pass 0 if you want to disable tab index.
+ * @param integer the tab index to be set
+ */
+ public function setTabIndex($value)
+ {
+ $this->setViewState('TabIndex',TPropertyValue::ensureInteger($value),0);
+ }
+
+ /**
+ * Returns the tag name used for this control.
+ * By default, the tag name is 'span'.
+ * You can override this method to provide customized tag names.
+ * @return string tag name of the control to be rendered
+ */
+ protected function getTagName()
+ {
+ return 'span';
+ }
+
+ /**
+ * @return string the tooltip of the control
+ */
+ public function getToolTip()
+ {
+ return $this->getViewState('ToolTip','');
+ }
+
+ /**
+ * Sets the tooltip of the control.
+ * Pass empty string if you want to disable tooltip.
+ * @param string the tooltip to be set
+ */
+ public function setToolTip($value)
+ {
+ $this->setViewState('ToolTip',$value,'');
+ }
+
+ /**
+ * @return string the width of the control
+ */
+ public function getWidth()
+ {
+ if($style=$this->getViewState('Style',null))
+ return $style->getWidth();
+ else
+ return '';
+ }
+
+ /**
+ * @param string the width of the control
+ */
+ public function setWidth($value)
+ {
+ $this->getStyle()->setWidth($value);
+ }
+
+ /**
+ * Adds attribute name-value pairs to renderer.
+ * This method can be overriden to provide customized attributes to be rendered.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function addAttributesToRender($writer)
+ {
+ if($this->getID()!=='')
+ $writer->addAttribute('id',$this->getClientID());
+ if(($accessKey=$this->getAccessKey())!=='')
+ $writer->addAttribute('accesskey',$accessKey);
+ if(!$this->getEnabled())
+ $writer->addAttribute('disabled','disabled');
+ if(($tabIndex=$this->getTabIndex())>0)
+ $writer->addAttribute('tabindex',$tabIndex);
+ if(($toolTip=$this->getToolTip())!=='')
+ $writer->addAttribute('title',$toolTip);
+ if($style=$this->getViewState('Style',null))
+ $style->addAttributesToRender($writer);
+ if($attributes=$this->getViewState('Attributes',null))
+ {
+ foreach($attributes as $name=>$value)
+ $writer->addAttribute($name,$value);
+ }
+ }
+
+ /**
+ * Renders the control.
+ * This method overrides the parent implementation by replacing it with
+ * the following sequence:
+ * - {@link renderBeginTag}
+ * - {@link renderContents}
+ * - {@link renderEndTag}
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function render($writer)
+ {
+ $this->renderBeginTag($writer);
+ $this->renderContents($writer);
+ $this->renderEndTag($writer);
+ }
+
+ /**
+ * Renders the openning tag for the control (including attributes)
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function renderBeginTag($writer)
+ {
+ $this->addAttributesToRender($writer);
+ $writer->renderBeginTag($this->getTagName());
+ }
+
+ /**
+ * Renders the body content enclosed between the control tag.
+ * By default, child controls and text strings will be rendered.
+ * You can override this method to provide customized content rendering.
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function renderContents($writer)
+ {
+ parent::renderChildren($writer);
+ }
+
+ /**
+ * Renders the closing tag for the control
+ * @param THtmlTextWriter the writer used for the rendering purpose
+ */
+ protected function renderEndTag($writer)
+ {
+ $writer->renderEndTag();
+ }
+}
+
+?> \ No newline at end of file