Current Path : /var/www/html/clients/rebirth.e-nk.ru/ips_kernel/ |
Current File : /var/www/html/clients/rebirth.e-nk.ru/ips_kernel/class_xml.php |
<?php /* +-------------------------------------------------------------------------- | Invision Power Board | ============================================= | by Matthew Mecham | (c) 2001 - 2006 Invision Power Services, Inc. | Nullified by Terabyte | ============================================= | | +--------------------------------------------------------------------------- | > $Date: 2005-10-10 14:03:20 +0100 (Mon, 10 Oct 2005) $ | > $Revision: 22 $ | > $Author: matt $ +--------------------------------------------------------------------------- | | > XML handling methods (KERNEL) | > Module written by Matt Mecham | > Date started: 25th February | | > Module Version Number: 1.0.0 +-------------------------------------------------------------------------- */ /** * IPS Kernel Pages: XML Creation and Extraction Functions * * This class contains all generic functions to handle * the creation of XML documents and the parsing of XML documents * * Example Usage: * <code> * <productlist name="myname" version="1.0"> * <productgroup name="thisgroup"> * <product id="1.0"> * <description>This is a descrption</description> * <title>Baked Beans</title> * <room store="1">103</room> * </product> * </productgroup> * </productlist> * * // Set the root tag * $xml->xml_set_root( 'productlist', array( 'name' => 'myname', 'version' => '1.0' ) ); * * // Add a group * $xml->xml_add_group( 'productgroup', array( 'name' => 'thisgroup' ) ); * * // Build entry content * $content[] = $xml->xml_build_simple_tag( 'description', "This is a descrption" ); * $content[] = $xml->xml_build_simple_tag( 'title' , "Baked Beans" ); * $content[] = $xml->xml_build_simple_tag( 'room' , '103' , array( 'store' => 1 ) ); * * // Build entry * $entry[] = $xml->xml_build_entry( 'product', $content, array( 'id' => '1.0' ) ); * * // Add to group 'productlist' * $xml->xml_add_entry_to_group( 'productgroup', $entry ); * * // Format.. * $xml->xml_format_document(); * * // Get XML document * $filecontents = $xml->xml_document; * * // Parse XML document * $xml->xml_parse_document( $filecontents ); * * // Show XML array * print_r( $xml->xml_array ); * * // print "Baked Beans"; * print $xml->xml_array['productlist']['productgroup']['product'][0]['title']['VALUE']; * * // print "1"; * print $xml->xml_array['productlist']['productgroup']['product'][0]['room']['ATTRIBUTES']['store']; * </code> * * @package IPS_KERNEL * @subpackage XMLHandling * @author Matt Mecham * @copyright Invision Power Services, Inc. * @version 2.1 */ /** * */ /** * XML Creation and Extraction Functions * * Methods and functions for handling XML documents * * @package IPS_KERNEL * @subpackage XMLHandling * @author Matt Mecham * @version 2.1 */ class class_xml { /** * XML header * * @var string */ var $header = ""; /** * Root tag name * * @var string */ var $root_tag = ''; /** * Root attributes * * @var string */ var $root_attributes = ""; /** * Array of entries * * @var array */ var $entries = array(); /** * String of compiled XML document * * @var string */ var $xml_document = ""; /** * Work variable * * @var integer */ var $depth = 0; /** * Tmp doc, used during creation * * @var string */ var $tmp_doc = ""; /** * Tag groups * * @var string */ var $groups = ""; /** * Index numerically flag * * @var integer */ var $index_numeric = 0; /** * Collapse duplicate tags flag * * @var integer */ var $collapse_dups = 1; /** * Main XML array of parsed components * * @var array */ var $xml_array = array(); /** * Collapse newlines in CDATA tags * * @var integer */ var $collapse_newlines = 1; /** * Use lite parser flag * * @var integer */ var $lite_parser = 0; /** * DOC type * * @ var string */ var $doc_type = 'ISO-8859-1'; /*-------------------------------------------------------------------------*/ // CONSTRUCTOR /*-------------------------------------------------------------------------*/ function class_xml() { @ini_set("memory_limit", "128M"); //$this->header = '<?xml version="1.0" encoding="'.$this->doc_type.'"?'.'>'; } /*-------------------------------------------------------------------------*/ // Parse an XML document into arrays /*-------------------------------------------------------------------------*/ /** * Parse an XML document into an array of field and values * * @param string Raw XML Data * @return void */ function xml_parse_document( $xml ) { $i = -1; //----------------------------------------- // Use "lite" parser //----------------------------------------- if ( $this->lite_parser ) { $lite = new xml_lite_parse(); $lite->xml_parse_it( $xml ); $this->xml_array = $this->_xml_get_children( $lite->stack, $i ); //----------------------------------------- // Free willy..er..memory //----------------------------------------- $lite->garbage_collect(); } //----------------------------------------- // Use PHP EXPAT Parser? //----------------------------------------- else { if ( $this->use_doctype && in_array( strtolower($this->doc_type), array( 'us-ascii', 'utf-8', 'iso-8859-1' ) ) ) { $parser = xml_parser_create( $this->doc_type ); } else { $parser = xml_parser_create(); } xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, 0); xml_parser_set_option($parser, XML_OPTION_SKIP_WHITE , 0); xml_parse_into_struct($parser, $xml, $vals); xml_parser_free($parser); $this->xml_array = $this->_xml_get_children($vals, $i); } //----------------------------------------- // Garbage collect //----------------------------------------- unset( $vals ); unset( $xml ); } /*-------------------------------------------------------------------------*/ // Format the XML document /*-------------------------------------------------------------------------*/ /** * Parse an array into an XML document * * @param array Entry array * @return void */ function xml_format_document( $entry=array() ) { $this->header = '<?xml version="1.0" encoding="'.$this->doc_type.'"?'.'>'; $this->xml_document = $this->header ? $this->header."\n" : ''; $this->xml_document .= "<".$this->root_tag.$this->root_attributes.">\n"; $this->xml_document .= $this->tmp_doc; $this->xml_document .= "\n</".$this->root_tag.">"; $this->tmp_doc = ""; } /*-------------------------------------------------------------------------*/ // Set the root tags /*-------------------------------------------------------------------------*/ /** * Set the root tag * * @param string Root tag name * @param array Root tag attributes * @return void */ function xml_set_root($tag, $attributes=array() ) { $this->root_tag = $tag; $this->root_attributes = $this->_xml_build_attribute_string( $attributes ); } /*-------------------------------------------------------------------------*/ // Add entries to the group /*-------------------------------------------------------------------------*/ /** * Add entry to XML group * * @param string Tag name * @param array Entry values * @return void */ function xml_add_entry_to_group($tag, $entry=array() ) { $this->tmp_doc .= "\t".$this->groups[ $tag ]; if ( is_array( $entry ) and count( $entry ) ) { foreach( $entry as $e ) { $this->tmp_doc .= "\n\t\t".$e."\n"; } } $this->tmp_doc .= "\t</".$tag.">\n"; } /*-------------------------------------------------------------------------*/ // Builds an entry /*-------------------------------------------------------------------------*/ /** * Build an XML entry * * @param string Tag name * @param array Content array * @param array Attributes * @return string */ function xml_build_entry( $tag, $content=array(), $attributes=array() ) { $entry = "<" . $tag . $this->_xml_build_attribute_string($attributes) . ">\n"; if ( is_array( $content ) and count( $content ) ) { foreach( $content as $c ) { $entry .= "\t\t\t".$c."\n"; } } $entry .= "\t\t</" . $tag . ">"; return $entry; } /*-------------------------------------------------------------------------*/ // Add a group /*-------------------------------------------------------------------------*/ /** * Add a group to an XML document * * @param string Tag name * @param array Attributes * @return string */ function xml_add_group( $tag, $attributes=array() ) { $this->groups[ $tag ] = "<" . $tag . $this->_xml_build_attribute_string($attributes) . ">"; } /*-------------------------------------------------------------------------*/ // Builds a simple <tag [key="value"]>content</tag> structure /*-------------------------------------------------------------------------*/ /** * Build and XML simple tag * * @param string Tag name * @param string Tag value * @param array Attributes * @return string */ function xml_build_simple_tag( $tag, $description="", $attributes=array() ) { return "<" . $tag . $this->_xml_build_attribute_string($attributes) . ">" . $this->_xml_encode_string($description) . "</" . $tag . ">"; } /*-------------------------------------------------------------------------*/ // INTERNAL: Build tree node // Adapted from http://eric.pollmann.net/work/public_domain/ /*-------------------------------------------------------------------------*/ /** * Build tree node * * @param array Values * @param array Values * @param string Counter * @param string Tag type * @return array */ function _xml_build_tag( $thisvals, $vals, &$i, $type ) { $tag = array(); if ( isset($thisvals['attributes']) ) { $tag['ATTRIBUTES'] = $this->_xml_decode_attribute($thisvals['attributes']); } if ( $type === 'complete' ) { $tag['VALUE'] = $this->_xml_unconvert_safecdata($thisvals['value']); } else { $tag = array_merge( $tag, $this->_xml_get_children($vals, $i) ); } return $tag; } /*-------------------------------------------------------------------------*/ // INTERNAL: Build a nested array of children // Adapted from http://eric.pollmann.net/work/public_domain/ /*-------------------------------------------------------------------------*/ /** * Build a nested array of children * * @param array Values * @param string Counter * @return array */ function _xml_get_children($vals, &$i) { $children = array(); //----------------------------------- // CDATA before children //----------------------------------- if ( $i > -1 && isset( $vals[$i]['value'] ) ) { $children['VALUE'] = $this->_xml_unconvert_safecdata( $vals[$i]['value'] ); } //----------------------------------- // Loopy loo //----------------------------------- while( ++$i < count( $vals ) ) { $type = $vals[$i]['type']; //----------------------------------- // CDATA after children //----------------------------------- if ($type === 'cdata') { $children['VALUE'] .= $this->_xml_unconvert_safecdata( $vals[$i]['value'] ); } //----------------------------------- // COMPLETE: At end of current branch // OPEN: Node has children, recurse //----------------------------------- else if ( $type === 'complete' OR $type === 'open' ) { $tag = $this->_xml_build_tag( $vals[$i], $vals, $i, $type ); if ( $this->index_numeric ) { $tag['TAG'] = $vals[$i]['tag']; $children[] = $tag; } else { $children[$vals[$i]['tag']][] = $tag; } } //----------------------------------- // End of node? //----------------------------------- else if ($type === 'close') { break; } } if ( $this->collapse_dups ) { foreach( $children as $key => $value ) { if ( is_array($value) && (count($value) == 1) ) { $children[$key] = $value[0]; } } } return $children; } /*-------------------------------------------------------------------------*/ // INTERNAL: Builds attribute string /*-------------------------------------------------------------------------*/ /** * Builds attribute string * * @param array Values * @return string */ function _xml_build_attribute_string( $array = array() ) { if ( is_array( $array ) and count( $array ) ) { $string = array(); foreach( $array as $k => $v ) { $v = trim( $this->_xml_encode_attribute($v) ); $string[] = $k.'="'.$v.'"'; } return ' ' . implode( " ", $string ); } } /*-------------------------------------------------------------------------*/ // INTERNAL: Encodes an attribute string /*-------------------------------------------------------------------------*/ /** * Encode XML attribute (Make safe for transport) * * @param string Raw data * @return string Converted Data */ function _xml_encode_attribute( $t ) { $t = preg_replace("/&(?!#[0-9]+;)/s", '&', $t ); $t = str_replace( "<", "<" , $t ); $t = str_replace( ">", ">" , $t ); $t = str_replace( '"', """, $t ); $t = str_replace( "'", ''', $t ); return $t; } /*-------------------------------------------------------------------------*/ // INTERNAL: Encodes an attribute string /*-------------------------------------------------------------------------*/ /** * Decode XML attribute (Make safe for transport) * * @param string Raw data * @return string Converted Data */ function _xml_decode_attribute( $t ) { $t = str_replace( "&" , "&", $t ); $t = str_replace( "<" , "<", $t ); $t = str_replace( ">" , ">", $t ); $t = str_replace( """, '"', $t ); $t = str_replace( "'", "'", $t ); return $t; } /*-------------------------------------------------------------------------*/ // INTERNAL: Encodes a string to make it safe (uses cdata) /*-------------------------------------------------------------------------*/ /** * Encode XML attribute (Make safe for transport) * * @param string Raw data * @return string Converted Data */ function _xml_encode_string( $v ) { if ( preg_match( "/['\"\[\]<>&]/", $v ) ) { $v = "<![CDATA[" . $this->_xml_convert_safecdata($v) . "]]>"; } if ( $this->collapse_newlines ) { $v = str_replace( "\r\n", "\n", $v ); } return $v; } /*-------------------------------------------------------------------------*/ // INTERNAL: Ensures no embedding of cdata /*-------------------------------------------------------------------------*/ /** * Encode CDATA XML attribute (Make safe for transport) * * @param string Raw data * @return string Converted Data */ function _xml_convert_safecdata( $v ) { # Legacy //$v = str_replace( "<![CDATA[", "<!¢|CDATA|", $v ); //$v = str_replace( "]]>" , "|¢]>" , $v ); # New $v = str_replace( "<![CDATA[", "<!#^#|CDATA|", $v ); $v = str_replace( "]]>" , "|#^#]>" , $v ); return $v; } /*-------------------------------------------------------------------------*/ // INTERNAL: Uncoverts safe embedding /*-------------------------------------------------------------------------*/ /** * Decode CDATA XML attribute (Make safe for transport) * * @param string Raw data * @return string Converted Data */ function _xml_unconvert_safecdata( $v ) { # Legacy $v = str_replace( "<!¢|CDATA|", "<![CDATA[", $v ); $v = str_replace( "|¢]>" , "]]>" , $v ); # New $v = str_replace( "<!#^#|CDATA|", "<![CDATA[", $v ); $v = str_replace( "|#^#]>" , "]]>" , $v ); return $v; } } //====================================================================================== // CLASS: XML_LITE_PARSE (Takes parsed XML and puts into EXPAT compatible array //====================================================================================== /** * XML-LITE Extraction * * Methods and functions for handling XML documents * * @package IPS_KERNEL * @subpackage XMLHandling * @author Matt Mecham * @version 2.1 */ class xml_lite_parse { var $xml_class; var $parser; var $preserve_cdata = 1; var $stack = array(); var $level = 1; var $tagname = ""; var $array_id = 0; var $last_id = 0; var $tagopen = array(); var $xmldoc = ""; /*-------------------------------------------------------------------------*/ // CONSTRUCTOR /*-------------------------------------------------------------------------*/ function xml_lite_parse() { } /*-------------------------------------------------------------------------*/ // Main parser /*-------------------------------------------------------------------------*/ function xml_parse_it( $xmldoc ) { $parser = new xml_extract(); $this->xmldoc = $xmldoc; unset( $xmldoc ); //----------------------------------------- // Set up element handlers //----------------------------------------- $parser->my_xml_set_element_handler( array(&$this, 'my_start_element'), array(&$this, 'my_end_element') ); $parser->my_xml_set_character_data_handler(array(&$this, 'my_data_element')); if ( $this->preserve_cdata ) { $parser->my_xml_set_cdata_section_handler( array(&$this, 'my_cdata_element') ); } $parser->xml_parse_document( $this->xmldoc ); } /*-------------------------------------------------------------------------*/ // Start element /*-------------------------------------------------------------------------*/ function my_start_element( &$parser_obj, $name, $attr ) { //------------------------------- // Add to stack //------------------------------- $this->stack[ $this->array_id ] = array( 'tag' => $name, 'type' => 'open', 'level' => $this->level, 'value' => '', ); //------------------------------- // Attributes? //------------------------------- if ( is_array( $attr ) and count( $attr ) ) { $this->stack[ $this->array_id ]['attributes'] = $attr; } //------------------------------- // Flying higher than an eagle? //------------------------------- if ( $this->tagname != $name ) { if ( $this->tagopen[ $name ] ) { $this->level = $this->tagopen[ $name ]; } else { $this->level++; } } //------------------------------- // Set current tag name //------------------------------- $this->tagname = $name; //------------------------------- // Inc. array ID //------------------------------- $this->array_id++; //------------------------------- // Set tag == depth //------------------------------- $this->tagopen[ $name ] = $this->level; } /*-------------------------------------------------------------------------*/ // Start element /*-------------------------------------------------------------------------*/ function my_end_element( &$parser_obj, $name ) { $this->stack[ $this->array_id ] = array( 'tag' => $name, 'type' => 'close', 'level' => $this->tagopen[ $name ] - 1, ); //------------------------------- // Update already done data? //------------------------------- if ( ( $this->stack[ $this->array_id - 2 ]['tag'] == $this->tagname ) AND ( $this->stack[ $this->array_id - 1 ]['_data'] == 1 ) ) { //------------------------------- // Update previous tag //------------------------------- $this->stack[ $this->array_id - 2 ]['value'] = class_xml::_xml_unconvert_safecdata( $this->stack[ $this->array_id - 1 ]['value'] ); $this->stack[ $this->array_id - 2 ]['type'] = 'complete'; unset( $this->stack[ $this->array_id - 1 ] ); unset( $this->stack[ $this->array_id ] ); $this->array_id -= 2; $this->last_id = $this->array_id - 1; } $this->tagname = ""; $this->array_id++; $this->level--; } /*-------------------------------------------------------------------------*/ // DATA element /*-------------------------------------------------------------------------*/ function my_data_element( &$parser_obj, $data ) { if ( $this->tagname ) { $this->stack[ $this->array_id ] = array( 'tag' => $this->tagname, 'type' => 'open', 'level' => $this->level, 'value' => class_xml::_xml_unconvert_safecdata($data), '_data' => 1 ); } //------------------------------- // Inc. array ID //------------------------------- $this->array_id++; } /*-------------------------------------------------------------------------*/ // CDATA element /*-------------------------------------------------------------------------*/ function my_cdata_element( &$parser_obj, $data ) { $this->my_data_element( $parser_obj, $data ); } /*-------------------------------------------------------------------------*/ // Free memory /*-------------------------------------------------------------------------*/ function garbage_collect() { $this->stack = array(); $this->tagname = array(); $this->array_id = 0; $this->level = 0; $this->xmldoc = ""; } } //====================================================================================== // CLASS: XML_EXTRACT (Parses XML file) //====================================================================================== /** * XML-LITE Extraction Sub class * * Methods and functions for handling XML documents * * @package IPS_KERNEL * @subpackage XMLHandling * @author Matt Mecham * @version 2.1 */ class xml_extract { var $xml_array = array(); var $chr_sofar = ""; var $handler_cdata_handler; var $handler_character_data; var $handler_end_element; var $handler_start_element; //----------------------------------------- // Definitions //----------------------------------------- var $xml_constants = array( 'CDATA_TAG' => '![CDATA[', 'CDATA_LEN' => 8, 'NOTATION' => '!NOTATION', 'DOCTYPE' => '!DOCTYPE' ); /*-------------------------------------------------------------------------*/ // CONSTRUCTOR /*-------------------------------------------------------------------------*/ function xml_extract() { } /*-------------------------------------------------------------------------*/ // MAIN "PARSE" ROUTINE (Roughly mime EXPAT in PHP) /*-------------------------------------------------------------------------*/ function xml_parse_document( $xml ) { //----------------------------------------- // Grab all relevant XML data // Strip off header, DOC TYPE, etc //----------------------------------------- $xml = preg_replace( "#^(?:.*?)?(<.*>)(?:.*?)?$#s", "\\1", $xml ); $xml_strlen = strlen( $xml ); //----------------------------------------- // Pick through, char by char //----------------------------------------- for( $i = 0 ; $i < $xml_strlen; $i++ ) { $chr = $xml{$i}; switch( $chr ) { case '<': if ( substr( $this->chr_sofar, 0, $this->xml_constants['CDATA_LEN'] ) == $this->xml_constants['CDATA_TAG'] ) { //----------------------------------------- // Processing CDATA //----------------------------------------- $this->chr_sofar .= $chr; } else { $this->parse_between_tags( $this->chr_sofar ); $this->chr_sofar = ''; } break; case '>': if ( ( substr( $this->chr_sofar, 0, $this->xml_constants['CDATA_LEN'] ) == $this->xml_constants['CDATA_TAG'] ) AND ! ( ( $this->_get_nth_char_from_end( $this->chr_sofar, 0 ) == ']' ) AND ( $this->_get_nth_char_from_end( $this->chr_sofar, 1 ) == ']' ) ) ) { $this->chr_sofar .= $chr; } else { if( $xml{ strlen($this->chr_sofar +1) } == ']' ) { $this->chr_sofar .= $chr; } else { $this->parse_tag( $this->chr_sofar ); $this->chr_sofar = ''; } } break; default: $this->chr_sofar .= $chr; } } unset($xml); } /*-------------------------------------------------------------------------*/ // Parse tag /*-------------------------------------------------------------------------*/ function parse_tag( $text ) { $attr = array(); $text = trim($text); $fchr = $text{0}; switch ($fchr) { //----------------------------------------- // First char is closing tag? //----------------------------------------- case '/': $tag_name = substr($text, 1); $this->exec_end_element($tag_name); break; //----------------------------------------- // First char is instruction/doctype? //----------------------------------------- case '!': $uc_tag_text = strtoupper($text); if ( strpos($uc_tag_text, $this->xml_constants['CDATA_TAG']) !== false ) { //----------------------------------------- // CDATA text //----------------------------------------- $total = strlen($text); $openbrace_cnt = 0; $tn_text = ''; for ( $i = 0; $i < $total; $i++ ) { $cc = $text{$i}; //----------------------------------------- // End of CDATA? //----------------------------------------- if ( ($cc == ']') && ( $text{($i + 1)} == ']' ) ) { if( ! $text{($i + 2)} == ']' ) { break; } else { $tn_text .= $cc; } } else if ($openbrace_cnt > 1) { $tn_text .= $cc; } else if ($cc == '[') { //----------------------------------------- // Won't get here until first OB reached //----------------------------------------- $openbrace_cnt ++; } } if ( $this->handler_cdata_handler == null ) { $this->exec_character_data($tn_text); } else { $this->exec_cdata_element($tn_text); } } else if ( strpos( $uc_tag_text, $this->xml_constants['NOTATION'] ) !== false ) { //----------------------------------------- // !NOTATION? Ignore! //----------------------------------------- return; } else if ( substr($text, 0, 2) == '!-' ) { //----------------------------------------- // !Comment? Ignore! //----------------------------------------- return; } break; //----------------------------------------- // Case is ?INSTRUCTION? //----------------------------------------- case '?': //----------------------------------------- // Instruction? Ignore! //----------------------------------------- return; //----------------------------------------- // Normal tag - woohoo! //----------------------------------------- default: if ( (strpos($text, '"') !== false) || (strpos($text, "'") !== false) ) { $total = strlen($text); $tag_name = ''; for ($i = 0; $i < $total; $i++) { $cc = $text{$i}; if ($cc == ' ') { $attr = $this->parse_attr(substr($text, $i)); break; } else { $tag_name.= $cc; } } if ( strrpos($text, '/') == ( strlen($text) - 1 ) ) { $this->exec_start_element($tag_name, $attr); $this->exec_end_element($tag_name); } else { $this->exec_start_element($tag_name, $attr); } } else { if ( strpos($text, '/') !== false ) { $text = trim( substr( $text, 0, ( strrchr($text, '/' ) - 1 ) ) ); $this->exec_start_element($text, $attr); $this->exec_end_element($text); } else { $this->exec_start_element($text, $attr); } } } } /*-------------------------------------------------------------------------*/ // Parse Attributes /*-------------------------------------------------------------------------*/ function parse_attr( $text ) { $text = trim($text); $attr_array = array(); $query_entity = false; $total = strlen($text); $dump_key = ''; $dump_value = ''; $cur_state = 0; // 0 = none, 1 = key, 2 = value $quote_type = ''; for ($i = 0; $i < $total; $i++) { $cc = $text{$i}; if ( $cur_state == 0 ) { if ( trim($cc != '') ) { $cur_state = 1; } } switch ($cc) { //----------------------------------------- // Tab and we're in a value? //----------------------------------------- case "\t": if ( $cur_state == 2 ) { $dump_value .= $cc; } else { $cc = ''; } break; //----------------------------------------- // Newlines.. //----------------------------------------- case "\n": case "\r": $cc = ''; break; //----------------------------------------- // Param value //----------------------------------------- case '=': if ( $cur_state == 2 ) { $dump_value .= $cc; } else { $cur_state = 2; $quote_type = ''; $query_entity = false; } break; //----------------------------------------- // Quoted //----------------------------------------- case '"': if ($cur_state == 2) { if ($quote_type == '') { $quote_type = '"'; } else { if ($quote_type == $cc) { $attr_array[ trim($dump_key) ] = trim($dump_value); $dump_key = $dump_value = $quote_type = ''; $cur_state = 0; } else { $dump_value .= $cc; } } } break; //----------------------------------------- // Quoted //----------------------------------------- case "'": if ($cur_state == 2) { if ($quote_type == '') { $quote_type = "'"; } else { if ($quote_type == $cc) { $attr_array[ trim($dump_key) ] = trim($dump_value); $dump_key = $dump_value = $quote_type = ''; $cur_state = 0; } else { $dump_value .= $cc; } } } break; //----------------------------------------- // Entity? //----------------------------------------- case '&': $query_entity = true; $dump_value .= $cc; break; default: if ($cur_state == 1) { $dump_key .= $cc; } else { $dump_value .= $cc; } } } return $attr_array; } /*-------------------------------------------------------------------------*/ // Parse between the element tags /*-------------------------------------------------------------------------*/ function parse_between_tags( $t ) { if ( trim($t ) != '') { $this->exec_character_data($t); } } /*-------------------------------------------------------------------------*/ // Exec_events /*-------------------------------------------------------------------------*/ function exec_character_data( $data ) { call_user_func( $this->handler_character_data, $this, $data ); } function exec_start_element( $tagname, $attr ) { call_user_func( $this->handler_start_element, $this, $tagname, $attr ); } function exec_end_element( $tagname ) { call_user_func( $this->handler_end_element, $this, $tagname ); } function exec_cdata_element( $data ) { call_user_func( $this->handler_cdata_handler, $this, $data ); } /*-------------------------------------------------------------------------*/ // Set xml element handlers /*-------------------------------------------------------------------------*/ function my_xml_set_element_handler($startHandler, $endHandler) { $this->handler_start_element = $startHandler; $this->handler_end_element = $endHandler; } function my_xml_set_character_data_handler($handler) { $this->handler_character_data = &$handler; } function my_xml_set_cdata_section_handler($handler) { $this->handler_cdata_handler = &$handler; } /*-------------------------------------------------------------------------*/ // Internal: Get nth character of $text /*-------------------------------------------------------------------------*/ function _get_nth_char_from_end( $t, $i ) { return $t{ ( strlen( $t ) - 1 - $i ) }; } } ?>