GetExceptionMessage() . "\n";
$msg .= $e->GetDetails() . "\n";
$msg .= $e->GetStackTrace() . "\n";
RenderTextToImage($msg);
}
catch (Exception $ex) {
$msg = $ex->GetMessage();
RenderTextToImage($msg);
}
imagedestroy($groupIcon);
imagedestroy($dwfIcon);
imagedestroy($rasterIcon);
imagedestroy($themeIcon);
?>
getElementsByTagName("CompositeTypeStyle");
if ($styleNodes->length > 0) {
for ($i = 0; $i < $styleNodes->length; $i++) {
$showInLegend = $styleNodes->item($i)->getElementsByTagName("ShowInLegend");
if($showInLegend->length > 0) {
if($showInLegend->item(0)->nodeValue == "false") {
continue; // This typestyle does not need to be shown in the legend
}
}
$ruleNodes = $styleNodes->item($i)->getElementsByTagName("CompositeRule");
$totalRules += $ruleNodes->length;
if ($ruleNodes->length > 0)
$gt = ($i + 1);
}
return $totalRules > 1;
} else {
for ($i = 0; $i < count($typeStyles); $i++) {
$styleNodes = $scaleRange->getElementsByTagName($typeStyles[$i]);
for ($j = 0; $j < $styleNodes->length; $j++) {
$showInLegend = $styleNodes->item($j)->getElementsByTagName("ShowInLegend");
if($showInLegend->length > 0) {
if($showInLegend->item(0)->nodeValue == "false") {
continue; // This typestyle does not need to be shown in the legend
}
}
$ruleNodes = $styleNodes->item($j)->getElementsByTagName($ruleNames[$i]);
$totalRules += $ruleNodes->length;
if ($ruleNodes->length > 0)
array_push($geomTypes, ($i + 1));
}
}
//A themed layer has # rules > # style types, implying at least one or more style types
//has > 1 rule attached
if (count($geomTypes) == 1) { //Single type, need to set the geom type
$gt = $geomTypes[0];
}
return $totalRules > 1;
}
}
// HasVisibleLayers
//
// Returns true if the group has one or more visible or the group has no visible layers but one or more
// of its child groups has one or more visible layers.
function HasVisibleLayers($groupName)
{
global $groupVisibleLayerCount, $groupChildren;
$total = 0;
if (array_key_exists($groupName, $groupVisibleLayerCount)) {
if ($groupVisibleLayerCount[$groupName] > 0) {
return true;
}
}
if (array_key_exists($groupName, $groupChildren)) {
foreach ($groupChildren[$groupName] as $childGroupName) {
if (HasVisibleLayers($childGroupName)) {
return true;
}
}
}
return false;
}
// CompileVisibleLayerCount
//
// Sets up the various temporary data structures for establishing visible layer count and group relationships
function CompileVisibleLayerCount($map)
{
global $groupVisibleLayerCount, $groupParents, $groupChildren;
$layers = $map->GetLayers();
$groups = $map->GetLayerGroups();
for ($i = 0; $i < $layers->GetCount(); $i++) {
$layer = $layers->GetItem($i);
if (!$layer->IsVisible()) //Not visible
continue;
$parentGroup = $layer->GetGroup();
if ($parentGroup == NULL) //No parent
continue;
$groupName = $parentGroup->GetName();
if (!array_key_exists($groupName, $groupVisibleLayerCount)) {
$groupVisibleLayerCount[$groupName] = 0;
}
$groupVisibleLayerCount[$groupName]++;
}
for ($i = 0; $i < $groups->GetCount(); $i++) {
$group = $groups->GetItem($i);
$parentGroup = $group->GetGroup();
if ($parentGroup != NULL) {
$groupName = $group->GetName();
$parentGroupName = $parentGroup->GetName();
$groupParents[$groupName] = $parentGroupName;
if (!array_key_exists($parentGroupName, $groupChildren)) {
$groupChildren[$parentGroupName] = array();
}
array_push($groupChildren, $groupName);
}
}
}
function GenerateLegend()
{
global $sessionID, $mapName, $width, $height, $offsetX, $offsetY, $xPad, $yPad, $iconWidth, $iconHeight, $xIndent, $groupIcon, $fontIndex, $textColor;
$userInfo = new MgUserInformation($sessionID);
$siteConnection = new MgSiteConnection();
$siteConnection->Open($userInfo);
$resourceService = $siteConnection->CreateService(MgServiceType::ResourceService);
$mappingService = $siteConnection->CreateService(MgServiceType::MappingService);
$map = new MgMap($siteConnection);
$map->Open($mapName);
$scale = $map->GetViewScale();
CompileVisibleLayerCount($map);
$image = imagecreatetruecolor($width, $height);
$white = imagecolorallocate($image, 255, 255, 255);
$textColor = imagecolorallocate($image, 0, 0, 0);
imagefilledrectangle($image, 0, 0, $width, $height, $white);
//Uncomment regions marked with BEGIN DEBUG / END DEBUG and comment out regions marked with
//BEGIN COMMENT OUT IF DEBUGGING / END COMMENT OUT IF DEBUGGING to see what PHP-isms get spewed out
//that may be tripping up rendering
//
//Also replace instances of "////print_r" with "//print_r" to insta-uncomment all debugging calls
//==BEGIN DEBUG==
//header("Content-type: text/html", true);
//==END DEBUG==
ProcessGroupsForLegend($mappingService, $resourceService, $map, $scale, NULL, $image);
//==BEGIN COMMENT OUT IF DEBUGGING==
header("Content-type: image/png");
imagepng($image);
//==END COMMENT OUT IF DEBUGGING==
//==BEGIN DEBUG==
/*
ob_start();
imagepng($image);
$im = base64_encode(ob_get_contents());
ob_end_clean();
echo "";
*/
//==END DEBUG==
imagecolordeallocate($image, $white);
imagecolordeallocate($image, $textColor);
imagedestroy($image);
}
function ProcessGroupsForLegend($mappingService, $resourceService, $map, $scale, $parentGroup, $image) {
global $iconWidth, $iconHeight, $height, $fontIndex, $iconFormat, $offsetX, $offsetY, $font, $fontSizePt, $xPad, $yPad, $xIndent, $themeIcon, $groupIcon, $dwfIcon, $rasterIcon, $textColor;
$groups = $map->GetLayerGroups();
ProcessLayersForLegend($mappingService, $resourceService, $map, $scale, $parentGroup, $image);
for ($i = 0; $i < $groups->GetCount(); $i++) {
$group = $groups->GetItem($i);
$parentGroupOfGroup = $group->GetGroup();
//One has a parent and the other one doesn't
if (($parentGroupOfGroup != NULL && $parentGroup == NULL) ||
($parentGroupOfGroup == NULL && $parentGroup != NULL)) {
continue;
}
//Parents aren't same
if (($parentGroupOfGroup != NULL && $parentGroup != NULL) &&
($parentGroupOfGroup->GetObjectId() != $parentGroup->GetObjectId())) {
continue;
}
if (!$group->GetDisplayInLegend())
continue;
//There are no actual visible layers to render icons for.
if (!HasVisibleLayers($group->GetName()))
continue;
//print_r("GROUP: ".$group->GetLegendLabel()." (".$group->GetName().") - ".$group->GetObjectId()."
");
//Draw the image
imagecopy($image, $groupIcon, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
imagestring($image, $fontIndex, ($offsetX + $xPad + 16), $offsetY, $group->GetLegendLabel(), $textColor);
$offsetX += $xIndent;
$offsetY += $iconHeight;
$offsetY += $yPad;
if ($offsetY > $height)
break;
ProcessGroupsForLegend($mappingService, $resourceService, $map, $scale, $group, $image);
$offsetX -= $xIndent;
}
}
function ProcessLayersForLegend($mappingService, $resourceService, $map, $scale, $group, $image) {
global $iconWidth, $iconHeight, $height, $fontIndex, $iconFormat, $offsetX, $offsetY, $font, $fontSizePt, $xPad, $yPad, $xIndent, $themeIcon, $groupIcon, $dwfIcon, $rasterIcon, $textColor;
$layers = $map->GetLayers();
for ($i = 0; $i < $layers->GetCount(); $i++) {
$layer = $layers->GetItem($i);
if (!$layer->IsVisible() || !$layer->GetDisplayInLegend()) {
//print_r("[SKIP]: Skipping layer (".$layer->GetLegendLabel().") - not visible or not set to display in legend
");
continue;
}
if ($offsetY > $height) {
//print_r("********** STOP! Past image bounds ****************
");
break;
}
$parentGroup = $layer->GetGroup();
$bRequiredInLegend = false;
$grpId = "";
$parentId = "";
if ($group != NULL)
$grpId = $group->GetObjectId();
if ($parentGroup != NULL)
$parentId = $parentGroup->GetObjectId();
if ($group == NULL && $parentGroup == NULL)
$bRequiredInLegend = true;
else if ($parentGroup != NULL && $group != NULL && $group->GetObjectId() == $parentGroup->GetObjectId())
$bRequiredInLegend = true;
if (!$bRequiredInLegend) {
//print_r("[SKIP]: Skipping layer (".$layer->GetLegendLabel().", group: $grpId, layer's parent: $parentId) - not required in legend
");
continue;
}
$ldfId = $layer->GetLayerDefinition();
$layerContent = $resourceService->GetResourceContent($ldfId);
$xmldoc = new DOMDocument();
$xmldoc->loadXML(ByteReaderToString($layerContent));
$scaleRanges = $xmldoc->getElementsByTagName('VectorScaleRange');
if ($scaleRanges->length == 0) {
$scaleRanges = $xmldoc->getElementsByTagName('GridScaleRange');
if ($scaleRanges->length > 0) {
//Draw the image
imagecopy($image, $rasterIcon, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
//Draw the label
//imagettftext($image, $fontSizePt, 0, ($offsetX + $xPad + $iconWidth), $offsetY, $textColor, $font, $layer->GetLegendLabel());
imagestring($image, $fontIndex, ($offsetX + $xPad + $iconWidth), $offsetY, $layer->GetLegendLabel(), $textColor);
$offsetY += $yPad;
$offsetY += $iconHeight;
return;
} else {
$scaleRanges = $xmldoc->getElementsByTagName('DrawingLayerDefinition');
if ($scaleRanges->length > 0) {
//Draw the image
imagecopy($image, $dwfIcon, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
//Draw the label
//imagettftext($image, $fontSizePt, 0, ($offsetX + $xPad + $iconWidth), $offsetY, $textColor, $font, $layer->GetLegendLabel());
imagestring($image, $fontIndex, ($offsetX + $xPad + $iconWidth), $offsetY, $layer->GetLegendLabel(), $textColor);
$offsetY += $yPad;
$offsetY += $iconHeight;
return;
}
}
}
//print_r("Processing layer (".$layer->GetLegendLabel()."). Scale range count: ".$scaleRanges->length."
");
for ($sc = 0; $sc < $scaleRanges->length; $sc++)
{
$scaleRangeObj = NULL;
$scaleRangeObj->styles = array();
$scaleRange = $scaleRanges->item($sc);
$minElt = $scaleRange->getElementsByTagName('MinScale');
$maxElt = $scaleRange->getElementsByTagName('MaxScale');
$minScale = "0";
$maxScale = 'infinity'; // as MDF's VectorScaleRange::MAX_MAP_SCALE
if ($minElt->length > 0)
$minScale = $minElt->item(0)->nodeValue;
if ($maxElt->length > 0)
$maxScale = $maxElt->item(0)->nodeValue;
//Style is within our scale
if (($minScale == "0" && $maxScale == "infinity") ||
($scale >= floatval($minScale) && $scale <= floatval($maxScale)) ||
($maxScale == "infinity" && $scale >= floatval($minScale))) {
$styleIndex = 0;
if (!IsThemed($scaleRange, $gt)) {
//print_r($layer->GetLegendLabel()." - ".$ldfId->ToString()." - Un-themed layer (geomType: $gt)
");
$icon = $mappingService->GenerateLegendImage($ldfId, $scale, $iconWidth, $iconHeight, $iconFormat, $gt, 0);
$sink = new MgByteSink($icon);
$tempImage = sys_get_temp_dir() . DIRECTORY_SEPARATOR . "mgo_icon" . uniqid();
$sink->ToFile($tempImage);
$iconImg = imagecreatefrompng($tempImage);
//Draw the image
imagecopy($image, $iconImg, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
imagedestroy($iconImg);
unlink($tempImage);
//Draw the label
//imagettftext($image, $fontSizePt, 0, ($offsetX + $xPad + $iconWidth), $offsetY, $textColor, $font, $layer->GetLegendLabel());
imagestring($image, $fontIndex, ($offsetX + $xPad + $iconWidth), $offsetY, $layer->GetLegendLabel(), $textColor);
$offsetY += $yPad;
$offsetY += $iconHeight;
} else {
if ($scaleRange->getElementsByTagName("CompositeTypeStyle")->length > 0) {
$typeStyles = array(4 => "CompositeTypeStyle");
$ruleNames = array(4 => "CompositeRule");
} else {
$typeStyles = array(1 => "PointTypeStyle", 2 => "LineTypeStyle", 3 => "AreaTypeStyle");
$ruleNames = array(1 => "PointRule", 2 => "LineRule", 3 => "AreaRule");
}
//print_r($layer->GetLegendLabel()." - ".$ldfId->ToString()." - Themed layer ()
");
//Draw the theme icon
imagecopy($image, $themeIcon, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
//Draw the themed layer label
//imagettftext($image, $fontSizePt, 0, ($offsetX + $xPad + $iconWidth), $offsetY, $textColor, $font, $layer->GetLegendLabel());
imagestring($image, $fontIndex, ($offsetX + $xPad + $iconWidth), $offsetY, $layer->GetLegendLabel(), $textColor);
$offsetX += $xIndent;
$offsetY += $yPad;
$offsetY += $iconHeight;
//for($ts=0, $count = count($typeStyles); $ts < $count; $ts++)
foreach ($typeStyles as $ts => $styleName)
{
//print_r(" - Checking $styleName ($ts)
");
$typeStyle = $scaleRange->getElementsByTagName($styleName);
$catIndex = 0;
//print_r(" -- Found ".$typeStyle->length." elements
");
for($st = 0; $st < $typeStyle->length; $st++) {
$styleObj = NULL;
// We will check if this typestyle is going to be shown in the legend
$showInLegend = $typeStyle->item($st)->getElementsByTagName("ShowInLegend");
if($showInLegend->length > 0) {
if($showInLegend->item(0)->nodeValue == "false") {
//print_r("Skipping $styleName in (".$layer->GetLegendLabel().") because ShowInLegend is: ".$showInLegend->item(0)->nodeValue."
");
continue; // This typestyle does not need to be shown in the legend
}
}
$rules = $typeStyle->item($st)->getElementsByTagName($ruleNames[$ts]);
for($r = 0; $r < $rules->length; $r++) {
$rule = $rules->item($r);
$label = $rule->getElementsByTagName("LegendLabel");
$labelText = $label->length==1? $label->item(0)->nodeValue: "";
$icon = $mappingService->GenerateLegendImage($ldfId, $scale, $iconWidth, $iconHeight, $iconFormat, $ts, $catIndex++);
$sink = new MgByteSink($icon);
$tempImage = sys_get_temp_dir() . DIRECTORY_SEPARATOR . "mgo_icon" . uniqid();
$sink->ToFile($tempImage);
$iconImg = imagecreatefrompng($tempImage);
//Draw the image
imagecopy($image, $iconImg, $offsetX, $offsetY, 0, 0, $iconWidth, $iconHeight);
imagedestroy($iconImg);
unlink($tempImage);
//Draw the label
//imagettftext($image, $fontSizePt, 0, ($offsetX + $xPad + $iconWidth), $offsetY, $textColor, $font, $layer->GetLegendLabel());
imagestring($image, $fontIndex, ($offsetX + $xPad + $iconWidth), $offsetY, $labelText, $textColor);
$offsetY += $yPad;
$offsetY += $iconHeight;
if ($offsetY > $height)
break;
}
}
}
$offsetX -= $xIndent;
}
} else {
//print_r("[SKIP]: Layer (".$layer->GetLegendLabel()."). Current scale ($scale) does not fit scale range [$minScale to $maxScale]
");
}
}
}
}
function GetParameters()
{
global $sessionID, $mapName, $width, $height;
$args = $_GET;
if ($_SERVER["REQUEST_METHOD"] == "POST")
{
$args = $_POST;
}
// Not necessary to validate the parameters
$sessionID = $args["session_id"];
$mapName = $args["map_name"];
$width = $args["width"];
$height = $args["height"];
}
?>