Fixed bug #11621: XSS vulnerabilities in workspace module
[Packages/TYPO3.CMS.git] / typo3 / wizard_table.php
old mode 100755 (executable)
new mode 100644 (file)
index 6bb61e2..3331109
@@ -1,22 +1,22 @@
 <?php
 /***************************************************************
 *  Copyright notice
-*  
-*  (c) 1999-2004 Kasper Skaarhoj (kasper@typo3.com)
+*
+*  (c) 1999-2009 Kasper Skaarhoj (kasperYYYY@typo3.com)
 *  All rights reserved
 *
-*  This script is part of the TYPO3 project. The TYPO3 project is 
+*  This script is part of the TYPO3 project. The TYPO3 project is
 *  free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
-* 
+*
 *  The GNU General Public License can be found at
 *  http://www.gnu.org/copyleft/gpl.html.
-*  A copy is found in the textfile GPL.txt and important notices to the license 
+*  A copy is found in the textfile GPL.txt and important notices to the license
 *  from the author is found in LICENSE.txt distributed with these scripts.
 *
-* 
+*
 *  This script is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *
 *  This copyright notice MUST APPEAR in all copies of the script!
 ***************************************************************/
-/** 
- * Wizard to help make tables (eg. for tt_content elements) of type "table". 
+/**
+ * Wizard to help make tables (eg. for tt_content elements) of type "table".
  * Each line is a table row, each cell divided by a |
  *
  * $Id$
  * Revised for TYPO3 3.6 November/2003 by Kasper Skaarhoj
  * XHTML compliant
- * 
- * @author     Kasper Skaarhoj <kasper@typo3.com>
+ *
+ * @author     Kasper Skaarhoj <kasperYYYY@typo3.com>
  */
 /**
  * [CLASS/FUNCTION INDEX of SCRIPT]
  *
  *
  *
- *   84: class SC_wizard_table 
- *  112:     function init()   
- *  150:     function main()   
- *  166:     function printContent()   
- *  175:     function tableWizard()    
+ *   84: class SC_wizard_table
+ *  116:     function init()
+ *  158:     function main()
+ *  173:     function printContent()
+ *  184:     function tableWizard()
  *
  *              SECTION: Helper functions
- *  214:     function getConfigCode($row)      
- *  280:     function getTableHTML($cfgArr,$row)       
- *  429:     function changeFunc()     
- *  545:     function cfgArray2CfgString($cfgArr)      
- *  576:     function cfgString2CfgArray($cfgStr,$cols)        
+ *  223:     function getConfigCode($row)
+ *  293:     function getTableHTML($cfgArr,$row)
+ *  450:     function changeFunc()
+ *  572:     function cfgArray2CfgString($cfgArr)
+ *  603:     function cfgString2CfgArray($cfgStr,$cols)
  *
  * TOTAL FUNCTIONS: 9
  * (This index is automatically created/updated by the extension "extdeveval")
  *
  */
 
+
 
 $BACK_PATH='';
 require ('init.php');
 require ('template.php');
-include ('sysext/lang/locallang_wizards.php');
+$LANG->includeLLFile('EXT:lang/locallang_wizards.xml');
 
 
 
@@ -76,15 +76,20 @@ include ('sysext/lang/locallang_wizards.php');
 
 /**
  * Script Class for rendering the Table Wizard
- * 
- * @author     Kasper Skaarhoj <kasper@typo3.com>
+ *
+ * @author     Kasper Skaarhoj <kasperYYYY@typo3.com>
  * @package TYPO3
  * @subpackage core
  */
 class SC_wizard_table {
 
                        // Internal, dynamic:
-       var $doc;                                       // Document template object
+       /**
+        * document template object
+        *
+        * @var mediumDoc
+        */
+       var $doc;
        var $content;                           // Content accumulation for the module.
        var $include_once=array();      // List of files to include.
        var $inputStyle=0;                      // True, then <input> fields are shown, not textareas.
@@ -92,6 +97,7 @@ class SC_wizard_table {
 
                // Internal, static:
        var $xmlStorage=0;                      // If set, the string version of the content is interpreted/written as XML instead of the original linebased kind. This variable still needs binding to the wizard parameters - but support is ready!
+       var $numNewRows=1;                      // Number of new rows to add in bottom of wizard
        var $colsFieldName='cols';      // Name of field in parent record which MAY contain the number of columns for the table - here hardcoded to the value of tt_content. Should be set by TCEform parameters (from P)
 
 
@@ -99,6 +105,9 @@ class SC_wizard_table {
        var $P;                                         // Wizard parameters, coming from TCEforms linking to the wizard.
        var $TABLECFG;                          // The array which is constantly submitted by the multidimensional form of this wizard.
 
+               // table parsing
+       var $tableParsing_quote;                        // quoting of table cells
+       var $tableParsing_delimiter;            // delimiter between table cells
 
 
 
@@ -106,76 +115,126 @@ class SC_wizard_table {
 
        /**
         * Initialization of the class
-        * 
-        * @return      void            
+        *
+        * @return      void
         */
        function init() {
-               global $BACK_PATH,$HTTP_POST_VARS;
-
                        // GPvars:
                $this->P = t3lib_div::_GP('P');
                $this->TABLECFG = t3lib_div::_GP('TABLE');
 
+                       // Setting options:
+               $this->xmlStorage = $this->P['params']['xmlOutput'];
+               $this->numNewRows = t3lib_div::intInRange($this->P['params']['numNewRows'],1,50,5);
+
                        // Textareas or input fields:
                $this->inputStyle=isset($this->TABLECFG['textFields']) ? $this->TABLECFG['textFields'] : 1;
 
                        // Document template object:
-               $this->doc = t3lib_div::makeInstance('mediumDoc');
-               $this->doc->docType = 'xhtml_trans';
-               $this->doc->backPath = $BACK_PATH;
+               $this->doc = t3lib_div::makeInstance('template');
+               $this->doc->backPath = $GLOBALS['BACK_PATH'];
+               $this->doc->setModuleTemplate('templates/wizard_table.html');
                $this->doc->JScode=$this->doc->wrapScriptTags('
                        function jumpToUrl(URL,formEl)  {       //
-                               document.location = URL;
+                               window.location.href = URL;
                        }
                ');
-                               
+
                        // Setting form tag:
                list($rUri) = explode('#',t3lib_div::getIndpEnv('REQUEST_URI'));
                $this->doc->form ='<form action="'.htmlspecialchars($rUri).'" method="post" name="wizardForm">';
-               
-                       // Start page:
-               $this->content.=$this->doc->startPage('Table');
 
                        // If save command found, include tcemain:
-               if ($HTTP_POST_VARS['savedok_x'] || $HTTP_POST_VARS['saveandclosedok_x'])       {
+               if ($_POST['savedok_x'] || $_POST['saveandclosedok_x']) {
                        $this->include_once[]=PATH_t3lib.'class.t3lib_tcemain.php';
                }
+
+               $this->tableParsing_delimiter = '|';
+               $this->tableParsing_quote = '';
        }
 
        /**
         * Main function, rendering the table wizard
-        * 
-        * @return      void            
+        *
+        * @return      void
         */
        function main() {
-               global $LANG;
-
-               if ($this->P['table'] && $this->P['field'] && $this->P['uid'])  {
-                       $this->content.=$this->doc->section($LANG->getLL('table_title'),$this->tableWizard(),0,1);
+               if ($this->P['table'] && $this->P['field'] && $this->P['uid']) {
+                       $this->content.= $this->doc->section($GLOBALS['LANG']->getLL('table_title'), $this->tableWizard(), 0, 1);
                } else {
-                       $this->content.=$this->doc->section($LANG->getLL('table_title'),'<span class="typo3-red">'.$LANG->getLL('table_noData',1).'</span>',0,1);
+                       $this->content.= $this->doc->section($GLOBALS['LANG']->getLL('table_title'), '<span class="typo3-red">' . $GLOBALS['LANG']->getLL('table_noData',1) . '</span>', 0, 1);
                }
-               $this->content.=$this->doc->endPage();
+
+               // Setting up the buttons and markers for docheader
+               $docHeaderButtons = $this->getButtons();
+               $markers['CSH'] = $docHeaderButtons['csh'];
+               $markers['CONTENT'] = $this->content;
+
+               // Build the <body> for the module
+               $this->content = $this->doc->startPage('Table');
+               $this->content.= $this->doc->moduleBody($this->pageinfo, $docHeaderButtons, $markers);
+               $this->content.= $this->doc->endPage();
+               $this->content = $this->doc->insertStylesAndJS($this->content);
        }
 
        /**
         * Outputting the accumulated content to screen
-        * 
-        * @return      void            
+        *
+        * @return      void
         */
        function printContent() {
                echo $this->content;
        }
-       
+
+       /**
+        * Create the panel of buttons for submitting the form or otherwise perform operations.
+        *
+        * @return array all available buttons as an assoc. array
+        */
+       protected function getButtons() {
+               $buttons = array(
+                       'csh' => '',
+                       'csh_buttons' => '',
+                       'close' => '',
+                       'save' => '',
+                       'save_close' => '',
+                       'reload' => '',
+               );
+
+               if ($this->P['table'] && $this->P['field'] && $this->P['uid']) {
+                       // CSH
+                       $buttons['csh'] = t3lib_BEfunc::cshItem('xMOD_csh_corebe', 'wizard_table_wiz', $GLOBALS['BACK_PATH'], '');
+
+                       // CSH Buttons
+                       $buttons['csh_buttons'] = t3lib_BEfunc::cshItem('xMOD_csh_corebe', 'wizard_table_wiz_buttons', $GLOBALS['BACK_PATH'], '');
+
+                       // Close
+                       $buttons['close'] = '<a href="#" onclick="' . htmlspecialchars('jumpToUrl(unescape(\'' . rawurlencode($this->P['returnUrl']) . '\')); return false;') . '">' .
+                               '<img' . t3lib_iconWorks::skinImg($this->doc->backPath, 'gfx/closedok.gif') . ' class="c-inputButton" title="' . $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.php:rm.closeDoc', 1) . '" alt="" />' .
+                               '</a>';
+
+                       // Save
+                       $buttons['save'] = '<input type="image" class="c-inputButton" name="savedok"' . t3lib_iconWorks::skinImg($this->doc->backPath, 'gfx/savedok.gif') . ' title="' . $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.php:rm.saveDoc', 1) . '" />';
+
+                       // Save & Close
+                       $buttons['save_close'] = '<input type="image" class="c-inputButton" name="saveandclosedok"' . t3lib_iconWorks::skinImg($this->doc->backPath, 'gfx/saveandclosedok.gif') . ' title="' . $GLOBALS['LANG']->sL('LLL:EXT:lang/locallang_core.php:rm.saveCloseDoc', 1) . '" />';
+
+                       // Reload
+                       $buttons['reload'] = '<input type="image" class="c-inputButton" name="_refresh"' . t3lib_iconWorks::skinImg($this->doc->backPath, 'gfx/refresh_n.gif') . ' title="' . $GLOBALS['LANG']->getLL('forms_refresh', 1) . '" />';
+               }
+
+               return $buttons;
+       }
+
        /**
         * Draws the table wizard content
-        * 
+        *
         * @return      string          HTML content for the form.
         */
        function tableWizard()  {
-               
+
                        // First, check the references by selecting the record:
-               $row=t3lib_BEfunc::getRecord($this->P['table'],$this->P['uid']);
+               $row = t3lib_BEfunc::getRecord($this->P['table'],$this->P['uid']);
                if (!is_array($row))    {
                        t3lib_BEfunc::typo3PrintError ('Wizard Error','No reference to record',0);
                        exit;
@@ -184,9 +243,9 @@ class SC_wizard_table {
                        // This will get the content of the form configuration code field to us - possibly cleaned up, saved to database etc. if the form has been submitted in the meantime.
                $tableCfgArray = $this->getConfigCode($row);
 
-                       // Generation of the Table Wizards HTML code:           
+                       // Generation of the Table Wizards HTML code:
                $content = $this->getTableHTML($tableCfgArray,$row);
-               
+
                        // Return content:
                return $content;
        }
@@ -206,25 +265,32 @@ class SC_wizard_table {
        /**
         * Will get and return the configuration code string
         * Will also save (and possibly redirect/exit) the content if a save button has been pressed
-        * 
+        *
         * @param       array           Current parent record row
         * @return      array           Table config code in an array
         * @access private
         */
        function getConfigCode($row)    {
-               global $HTTP_POST_VARS;
 
-                       // If some data has been submitted, then construct 
+                       // get delimiter settings
+               $flexForm = t3lib_div::xml2array($row['pi_flexform']);
+
+               if (is_array($flexForm)) {
+                       $this->tableParsing_quote = $flexForm['data']['s_parsing']['lDEF']['tableparsing_quote']['vDEF']?chr(intval($flexForm['data']['s_parsing']['lDEF']['tableparsing_quote']['vDEF'])):'';
+                       $this->tableParsing_delimiter = $flexForm['data']['s_parsing']['lDEF']['tableparsing_delimiter']['vDEF']?chr(intval($flexForm['data']['s_parsing']['lDEF']['tableparsing_delimiter']['vDEF'])):'|';
+               }
+
+                       // If some data has been submitted, then construct
                if (isset($this->TABLECFG['c']))        {
-                       
+
                                // Process incoming:
                        $this->changeFunc();
-                       
-                       
+
+
                                // Convert to string (either line based or XML):
                        if ($this->xmlStorage)  {
                                        // Convert the input array to XML:
-                               $bodyText = t3lib_div::array2xml($this->TABLECFG['c'],'',0,'T3TableWizard');
+                               $bodyText = t3lib_div::array2xml_cs($this->TABLECFG['c'],'T3TableWizard');
 
                                        // Setting cfgArr directly from the input:
                                $cfgArr = $this->TABLECFG['c'];
@@ -235,26 +301,25 @@ class SC_wizard_table {
                                        // Create cfgArr from the string based configuration - that way it is cleaned up and any incompatibilities will be removed!
                                $cfgArr = $this->cfgString2CfgArray($bodyText,$row[$this->colsFieldName]);
                        }
-                                               
+
                                // If a save button has been pressed, then save the new field content:
-                       if ($HTTP_POST_VARS['savedok_x'] || $HTTP_POST_VARS['saveandclosedok_x'])       {
-                       
+                       if ($_POST['savedok_x'] || $_POST['saveandclosedok_x']) {
+
                                        // Make TCEmain object:
                                $tce = t3lib_div::makeInstance('t3lib_TCEmain');
                                $tce->stripslashes_values=0;
-                               
+
                                        // Put content into the data array:
                                $data=array();
                                $data[$this->P['table']][$this->P['uid']][$this->P['field']]=$bodyText;
-       
+
                                        // Perform the update:
                                $tce->start($data,array());
                                $tce->process_datamap();
-                               
+
                                        // If the save/close button was pressed, then redirect the screen:
-                               if ($HTTP_POST_VARS['saveandclosedok_x'])       {
-                                       header('Location: '.t3lib_div::locationHeaderUrl($this->P['returnUrl']));
-                                       exit;
+                               if ($_POST['saveandclosedok_x']) {
+                                       t3lib_utility_Http::redirect($this->P['returnUrl']);
                                }
                        }
                } else {        // If nothing has been submitted, load the $bodyText variable from the selected database row:
@@ -265,13 +330,13 @@ class SC_wizard_table {
                        }
                        $cfgArr = is_array($cfgArr) ? $cfgArr : array();
                }
-               
+
                return $cfgArr;
        }
 
        /**
         * Creates the HTML for the Table Wizard:
-        * 
+        *
         * @param       array           Table config array
         * @param       array           Current parent record array
         * @return      string          HTML for the table wizard
@@ -288,25 +353,25 @@ class SC_wizard_table {
                                        // Initialize:
                                $cells=array();
                                $a=0;
-       
+
                                        // Traverse the columns:
                                foreach($cellArr as $cellContent)       {
                                        if ($this->inputStyle)  {
                                                $cells[]='<input type="text"'.$this->doc->formWidth(20).' name="TABLE[c]['.(($k+1)*2).']['.(($a+1)*2).']" value="'.htmlspecialchars($cellContent).'" />';
                                        } else {
-                                               $cellContent=eregi_replace('<br[ ]?[\/]?>',chr(10),$cellContent);
+                                               $cellContent=preg_replace('/<br[ ]?[\/]?>/i',chr(10),$cellContent);
                                                $cells[]='<textarea '.$this->doc->formWidth(20).' rows="5" name="TABLE[c]['.(($k+1)*2).']['.(($a+1)*2).']">'.t3lib_div::formatForTextarea($cellContent).'</textarea>';
                                        }
-                                       
+
                                                // Increment counter:
                                        $a++;
                                }
-               
+
                                        // CTRL panel for a table row (move up/down/around):
                                $onClick="document.wizardForm.action+='#ANC_".(($k+1)*2-2)."';";
                                $onClick=' onclick="'.htmlspecialchars($onClick).'"';
                                $ctrl='';
-                               
+
                                $brTag=$this->inputStyle?'':'<br />';
                                if ($k!=0)      {
                                        $ctrl.='<input type="image" name="TABLE[row_up]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/pil2up.gif','').$onClick.' title="'.$LANG->getLL('table_up',1).'" />'.$brTag;
@@ -314,26 +379,27 @@ class SC_wizard_table {
                                        $ctrl.='<input type="image" name="TABLE[row_bottom]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/turn_up.gif','').$onClick.' title="'.$LANG->getLL('table_bottom',1).'" />'.$brTag;
                                }
                                $ctrl.='<input type="image" name="TABLE[row_remove]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/garbage.gif','').$onClick.' title="'.$LANG->getLL('table_removeRow',1).'" />'.$brTag;
-               
+
+// FIXME what is $tLines? See wizard_forms.php for the same.
                                if (($k+1)!=count($tLines))     {
                                        $ctrl.='<input type="image" name="TABLE[row_down]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/pil2down.gif','').$onClick.' title="'.$LANG->getLL('table_down',1).'" />'.$brTag;
                                } else {
                                        $ctrl.='<input type="image" name="TABLE[row_top]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/turn_down.gif','').$onClick.' title="'.$LANG->getLL('table_top',1).'" />'.$brTag;
                                }
                                $ctrl.='<input type="image" name="TABLE[row_add]['.(($k+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/add.gif','').$onClick.' title="'.$LANG->getLL('table_addRow',1).'" />'.$brTag;
-               
+
                                $tRows[]='
                                        <tr class="bgColor4">
                                                <td class="bgColor5"><a name="ANC_'.(($k+1)*2).'"></a><span class="c-wizButtonsV">'.$ctrl.'</span></td>
                                                <td>'.implode('</td>
                                                <td>',$cells).'</td>
                                        </tr>';
-                                       
+
                                        // Increment counter:
                                $k++;
                        }
                }
-       
+
                        // CTRL panel for a table column (move left/right/around/delete)
                $cells=array();
                $cells[]='';
@@ -341,16 +407,16 @@ class SC_wizard_table {
                reset($cfgArr);
                $firstRow=current($cfgArr);
                if (is_array($firstRow))        {
-                               
+
                                // Init:
                        $a=0;
                        $cols=count($firstRow);
-                               
+
                                // Traverse first row:
                        foreach($firstRow as $temp)     {
                                $ctrl='';
                                if ($a!=0)      {
-                                       $ctrl.='<input type="image" name="TABLE[col_left]['.(($a+1)*2).']"'.t3lib_iconWorks::skinImg('','gfx/pil2left.gif','').' title="'.$LANG->getLL('table_left',1).'" />';
+                                       $ctrl.='<input type="image" name="TABLE[col_left]['.(($a+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/pil2left.gif','').' title="'.$LANG->getLL('table_left',1).'" />';
                                } else {
                                        $ctrl.='<input type="image" name="TABLE[col_end]['.(($a+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/turn_left.gif','').' title="'.$LANG->getLL('table_end',1).'" />';
                                }
@@ -362,7 +428,7 @@ class SC_wizard_table {
                                }
                                $ctrl.='<input type="image" name="TABLE[col_add]['.(($a+1)*2).']"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/add.gif','').' title="'.$LANG->getLL('table_addColumn',1).'" />';
                                $cells[]='<span class="c-wizButtonsH">'.$ctrl.'</span>';
-                               
+
                                        // Incr. counter:
                                $a++;
                        }
@@ -372,34 +438,20 @@ class SC_wizard_table {
                                        <td align="center">',$cells).'</td>
                                </tr>';
                }
-       
+
+               $content = '';
+
                        // Implode all table rows into a string, wrapped in table tags.
-               $content = '
+               $content.= '
+
 
-               
                        <!--
                                Table wizard
                        -->
                        <table border="0" cellpadding="0" cellspacing="1" id="typo3-tablewizard">
                                '.implode('',$tRows).'
                        </table>';
-               
-                       // Add saving buttons in the bottom:
-               $content.= '
-               
-                       <!--
-                               Save buttons:
-                       -->
-                       <div id="c-saveButtonPanel">';
-               $content.= '<input type="image" class="c-inputButton" name="savedok"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/savedok.gif','').' title="'.$LANG->sL('LLL:EXT:lang/locallang_core.php:rm.saveDoc',1).'" />';
-               $content.= '<input type="image" class="c-inputButton" name="saveandclosedok"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/saveandclosedok.gif','').' title="'.$LANG->sL('LLL:EXT:lang/locallang_core.php:rm.saveCloseDoc',1).'" />';
-               $content.= '<a href="#" onclick="'.htmlspecialchars('jumpToUrl(unescape(\''.rawurlencode($this->P['returnUrl']).'\')); return false;').'">'.
-                                       '<img'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/closedok.gif','width="21" height="16"').' class="c-inputButton" title="'.$LANG->sL('LLL:EXT:lang/locallang_core.php:rm.closeDoc',1).'" alt="" />'.
-                                       '</a>';
-               $content.= '<input type="image" class="c-inputButton" name="_refresh"'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/refresh_n.gif','').' title="'.$LANG->getLL('forms_refresh',1).'" />
-                       </div>
-                       ';
-       
+
                        // Input type checkbox:
                $content.= '
 
@@ -409,62 +461,62 @@ class SC_wizard_table {
                        <div id="c-inputMode">
                                '.
                                '<input type="hidden" name="TABLE[textFields]" value="0" />'.
-                               '<input type="checkbox" name="TABLE[textFields]" value="1"'.($this->inputStyle?' checked="checked"':'').' /> '.
-                               $LANG->getLL('table_smallFields').'
+                               '<input type="checkbox" name="TABLE[textFields]" id="textFields" value="1"'.($this->inputStyle?' checked="checked"':'').' /> <label for="textFields">'.
+                               $LANG->getLL('table_smallFields').'</label>
                        </div>
-                       
+
                        <br /><br />
                        ';
-               
+
                        // Return content:
                return $content;
        }
 
        /**
         * Detects if a control button (up/down/around/delete) has been pressed for an item and accordingly it will manipulate the internal TABLECFG array
-        * 
-        * @return      void            
+        *
+        * @return      void
         * @access private
         */
        function changeFunc()   {
-               if ($this->TABLECFG['col_remove'])      {       
+               if ($this->TABLECFG['col_remove'])      {
                        $kk = key($this->TABLECFG['col_remove']);
                        $cmd='col_remove';
-               } elseif ($this->TABLECFG['col_add'])   {       
+               } elseif ($this->TABLECFG['col_add'])   {
                        $kk = key($this->TABLECFG['col_add']);
                        $cmd='col_add';
-               } elseif ($this->TABLECFG['col_start']) {       
+               } elseif ($this->TABLECFG['col_start']) {
                        $kk = key($this->TABLECFG['col_start']);
                        $cmd='col_start';
-               } elseif ($this->TABLECFG['col_end'])   {       
+               } elseif ($this->TABLECFG['col_end'])   {
                        $kk = key($this->TABLECFG['col_end']);
                        $cmd='col_end';
-               } elseif ($this->TABLECFG['col_left'])  {       
+               } elseif ($this->TABLECFG['col_left'])  {
                        $kk = key($this->TABLECFG['col_left']);
                        $cmd='col_left';
-               } elseif ($this->TABLECFG['col_right']) {       
+               } elseif ($this->TABLECFG['col_right']) {
                        $kk = key($this->TABLECFG['col_right']);
                        $cmd='col_right';
-               } elseif ($this->TABLECFG['row_remove'])        {       
+               } elseif ($this->TABLECFG['row_remove'])        {
                        $kk = key($this->TABLECFG['row_remove']);
                        $cmd='row_remove';
-               } elseif ($this->TABLECFG['row_add'])   {       
+               } elseif ($this->TABLECFG['row_add'])   {
                        $kk = key($this->TABLECFG['row_add']);
                        $cmd='row_add';
-               } elseif ($this->TABLECFG['row_top'])   {       
+               } elseif ($this->TABLECFG['row_top'])   {
                        $kk = key($this->TABLECFG['row_top']);
                        $cmd='row_top';
                } elseif ($this->TABLECFG['row_bottom'])        {
                        $kk = key($this->TABLECFG['row_bottom']);
                        $cmd='row_bottom';
-               } elseif ($this->TABLECFG['row_up'])    {       
+               } elseif ($this->TABLECFG['row_up'])    {
                        $kk = key($this->TABLECFG['row_up']);
                        $cmd='row_up';
-               } elseif ($this->TABLECFG['row_down'])  {       
+               } elseif ($this->TABLECFG['row_down'])  {
                        $kk = key($this->TABLECFG['row_down']);
                        $cmd='row_down';
                }
-       
+
                if ($cmd && t3lib_div::testInt($kk)) {
                        if (substr($cmd,0,4)=='row_')   {
                                switch($cmd)    {
@@ -472,7 +524,13 @@ class SC_wizard_table {
                                                unset($this->TABLECFG['c'][$kk]);
                                        break;
                                        case 'row_add':
-                                               $this->TABLECFG['c'][$kk+1]=array();
+                                               for($a=1;$a<=$this->numNewRows;$a++)    {
+                                                       if (!isset($this->TABLECFG['c'][$kk+$a]))       {       // Checking if set: The point is that any new row inbetween existing rows will be true after one row is added while if rows are added in the bottom of the table there will be no existing rows to stop the addition of new rows which means it will add up to $this->numNewRows rows then.
+                                                               $this->TABLECFG['c'][$kk+$a] = array();
+                                                       } else {
+                                                               break;
+                                                       }
+                                               }
                                        break;
                                        case 'row_top':
                                                $this->TABLECFG['c'][1]=$this->TABLECFG['c'][$kk];
@@ -537,13 +595,13 @@ class SC_wizard_table {
 
        /**
         * Converts the input array to a configuration code string
-        * 
+        *
         * @param       array           Array of table configuration (follows the input structure from the table wizard POST form)
         * @return      string          The array converted into a string with line-based configuration.
         * @see cfgString2CfgArray()
         */
        function cfgArray2CfgString($cfgArr)    {
-       
+
                        // Initialize:
                $inLines=array();
 
@@ -553,21 +611,21 @@ class SC_wizard_table {
                        $thisLine=array();
                        reset($this->TABLECFG['c'][$a]);
                        while(list($b)=each($this->TABLECFG['c'][$a]))  {
-                               $thisLine[]=str_replace('|','',$this->TABLECFG['c'][$a][$b]);
+                               $thisLine[]=$this->tableParsing_quote.str_replace($this->tableParsing_delimiter,'',$this->TABLECFG['c'][$a][$b]).$this->tableParsing_quote;
                        }
-                       $inLines[]=implode('|',$thisLine);
+                       $inLines[]=implode($this->tableParsing_delimiter,$thisLine);
                }
-               
+
                        // Finally, implode the lines into a string:
                $bodyText = implode(chr(10),$inLines);
-               
+
                        // Return the configuration code:
                return $bodyText;
        }
-       
+
        /**
         * Converts the input configuration code string into an array
-        * 
+        *
         * @param       string          Configuration code
         * @param       integer         Default number of columns
         * @return      array           Configuration array
@@ -577,47 +635,41 @@ class SC_wizard_table {
 
                        // Explode lines in the configuration code - each line is a table row.
                $tLines=explode(chr(10),$cfgStr);
-       
+
                        // Setting number of columns
                if (!$cols && trim($tLines[0])) {       // auto...
-                       $cols = count(explode('|',$tLines[0]));
+                       $cols = count(explode($this->tableParsing_delimiter,$tLines[0]));
                }
                $cols=$cols?$cols:4;
-       
+
                        // Traverse the number of table elements:
                $cfgArr=array();
                foreach($tLines as $k => $v)    {
-               
+
                                // Initialize:
-                       $vParts = explode('|',$v);
+                       $vParts = explode($this->tableParsing_delimiter,$v);
 
-                               // Traverse columns:                    
+                               // Traverse columns:
                        for ($a=0;$a<$cols;$a++)        {
+                               if ($this->tableParsing_quote && substr($vParts[$a],0,1) == $this->tableParsing_quote && substr($vParts[$a],-1,1) == $this->tableParsing_quote) {
+                                       $vParts[$a] = substr(trim($vParts[$a]),1,-1);
+                               }
                                $cfgArr[$k][$a]=$vParts[$a];
                        }
                }
-               
+
                        // Return configuration array:
                return $cfgArr;
        }
 }
 
-// Include extension?
+
 if (defined('TYPO3_MODE') && $TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['typo3/wizard_table.php']) {
        include_once($TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['typo3/wizard_table.php']);
 }
 
 
 
-
-
-
-
-
-
-
-
-
 // Make instance:
 $SOBE = t3lib_div::makeInstance('SC_wizard_table');
 $SOBE->init();
@@ -627,4 +679,5 @@ foreach($SOBE->include_once as $INC_FILE)   include_once($INC_FILE);
 
 $SOBE->main();
 $SOBE->printContent();
+
 ?>
\ No newline at end of file