Jump to content

[SOLVED] Help with OOP and callback functions using xml_parse()


Recommended Posts

Hello, I just joined because I am stuck.  I have been programming in procedural php for several years and am attempting to learn oop.  I have successfully converted several pieces of code to classes, but am really stuck on this one.

 

I keep getting this error:

xml_parse(): Unable to call handler startElement()

 

First I will post the working procedural code followed by the problematic class.  The methods within the class that the problem occurs are: readXML, startElement, endElement, and characterData.

 

There could be other things wrong with how I am coding this and I appreciate any criticism as I want/need to learn this, but the main goal is to get the problematic methods working.

 

Thanks in advance,

-CroNiX

 

working procedural code:

<?php
$x = parseme("test.xml");
function parseme($filename){
$xml_parser = xml_parser_create(); 
xml_set_element_handler($xml_parser, "startElement", "endElement");
xml_set_character_data_handler($xml_parser, "characterData");
$fp = fopen($filename,"r")
	or die("Error reading RSS data.");

while ($data = fread($fp, 4096))
	xml_parse($xml_parser, $data, feof($fp))
		or die(sprintf("XML error: %s at line %d",  
           xml_error_string(xml_get_error_code($xml_parser)),  
           xml_get_current_line_number($xml_parser)));

fclose($fp);
xml_parser_free($xml_parser);
}

function startElement($parser, $tagName, $attrs) {
global $insideitem, $tag;
if ($insideitem) {
	$tag = $tagName;
} elseif ($tagName == "ITEM") {
	$insideitem = true;
}
}

function characterData($parser, $data) {
global $insideitem, $tag, $title, $description, $link;
if ($insideitem) {
    switch ($tag) {
		case "TITLE":
			$title .= $data;
			break;
		case "DESCRIPTION":
			$description .= $data;
			break;
		case "LINK":
			$link .= $data;
			break;
	}
}
}

function endElement($parser, $tagName) {
global $insideitem, $tag, $title, $description, $link;
if ($tagName == "ITEM") {

	htmlspecialchars(printf("<p>%s</p>",trim($description)),ENT_COMPAT);
	$title = "";
	$description = "";
	$link = "";
	$insideitem = false;
}
}
?>

 

Problematic Class code:

<?php
class GalleryXML {
public $xml_file = "gallery.xml";  	//xml file name
public $image_folder = ".";			//image folder
public $th_prefix = "th_";			//thumbnail prefix (to avoid trying to get exif from them)

public $insideitem;
public $tag;
public $title;
public $description;
public $link;
public $xml_parser;

function __construct() {
	if(!function_exists('exif_read_data')) die('PHP is missing the EXIF extension.');
}

function generateXML(){

	if(file_exists($this->xml_file)) unlink($this->xml_file);
	$f = fopen($this->xml_file, "a");
	if($f){
		fputs($f,"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n\n<rss version=\"2.0\">");
		fputs($f,"<gallerydata>");
		$handle = opendir($this->image_folder);
		while (($file = readdir($handle)) !== false) {
			//filter out thumbnails and everything but jpegs
			if((preg_match("/jpg|jpeg/i", $file)) && (!preg_match("/^" . $this->th_prefix . "/i", $file))){	
				$exif_array =  @exif_read_data($file);
				$title = isset($exif_array['Title']) ? $exif_array['Title'] : "" ;
				$im_dir = $this->image_folder == "." ? "" : $this->image_folder . "/";
				fputs($f,"<ITEM><DESCRIPTION>");
				fputs($f,htmlentities("<a href=\"" . $im_dir . $file . "\" rel=\"lightbox\" title=\"$title\"><div class=\"horizontal\"><img src=\"" . $im_dir . $this->th_prefix . "$file\" alt=\"$title\"  border=\"0\" /></div></a><div class=\"lightboxDesc\">$title</div>",ENT_COMPAT));
				fputs($f,"</DESCRIPTION></ITEM>");
			}
		}			
	}
	fputs($f,"</gallerydata></rss>");
	closedir($handle);
	fclose($f);
}

function readXML(){
	$this->xml_parser = xml_parser_create(); 
	xml_set_object($this->xml_parser, $this);
	xml_set_element_handler($this->xml_parser, "startElemnet", "endElement");
	xml_set_character_data_handler($this->xml_parser, "characterData");

	$fp = fopen($this->xml_file,"r") or die("Error reading RSS data.");

	while ($data = fread($fp, 4096))
	   xml_parse($this->xml_parser, $data, feof($fp))
	       // Handle errors in parsing
	       or die(sprintf("XML error: %s at line %d",  
	           xml_error_string(xml_get_error_code($this->xml_parser)),  
	           xml_get_current_line_number($this->xml_parser)));

	fclose($fp);
	xml_parser_free($this->xml_parser);
}
function startElement($parser, $tagName, $attrs) {
   	if ($this->insideitem) {
		$this->tag = $tagName;
   	} elseif ($tagName == "ITEM") {
       	$this->insideitem = true;
   	}
}
function endElement($parser, $tagName) {
   if ($tagName == "ITEM") {

     htmlspecialchars(printf("<p>%s</p>",trim($this->description)),ENT_COMPAT);
	   $this->title = "";
       $this->description = "";
       $this->link = "";
	   $this->insideitem = false;
   }
}
function characterData($parser, $data) {
   if ($this->insideitem) {
    switch ($this->tag) {
       case "TITLE":
           $this->title .= $data;
           break;
       case "DESCRIPTION":
           $this->description .= $data;
           break;
       case "LINK":
           $this->link .= $data;
           break;
       }
   }
}
/**
 * @return string
 */
public function getImage_folder() {
	return $this->image_folder;
}

/**
 * @return string
 */
public function getTh_prefix() {
	return $this->th_prefix;
}

/**
 * @return string
 */
public function getXml_file() {
	return $this->xml_file;
}

/**
 * @param string $image_folder
 */
public function setImage_folder($image_folder) {
	$this->image_folder = $image_folder;
}

/**
 * @param string $th_prefix
 */
public function setTh_prefix($th_prefix) {
	$this->th_prefix = $th_prefix;
}

/**
 * @param string $xml_file
 */
public function setXml_file($xml_file) {
	$this->xml_file = $xml_file;
}
}
$im= new GalleryXML();

$im->setXml_file("test.xml");
//$im->generateXML();
$im->readXML();
?>

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.