GOOGLE Maps in einem Sharepoint 2013 Listview darstellen

Heute öffnet mal unsere Entwicklungsabteilung eine Truhe in der Sharepoint-Schatzkammer.

Jeder der schon einmal eine Website mit Microsoft Sharepoint erstellt hat, kennt wahrscheinlich das Problem, dass man gerne auf der Kontaktseite eine Karte einblenden möchte, die den Standort der Firma oder Filiale anzeigt und das am Besten mit einer Google Map. Dafür gibt es zwar eine ganze Menge fertiger Webparts und Scripte, aber die meisten funktionieren nicht mehr in Sharepoint 2013 oder sie sind für den gebotenen Funktionsumfang viel zu teuer.
Dieser Artikel beschreibt, wie man in Sharepoint 2013 mit Hilfe der jQuery Erweiterung zGoogleMap (von zazar) eine „Google Maps“-Karte anzeigen lassen kann. Die Orte, die angezeigt werden sollen, kommen dabei aus einer herkömmlichen Sharepoint Liste und die Erweiterung wird in einen XSLT View eingebunden.

Zuerst legen wir in unserer XSL Datei ein neues Template an, das die Daten aus unserer Liste verarbeiten kann.

<xsl:template name="RenderViewWithMap">
<xsl:variable name="Rows" select="/dsQueryResponse/Rows/Row" />
<xsl:choose>
<xsl:when test="count($Rows) = 0">
<xsl:call-template name="RenderViewEmpty" />
</xsl:when>
<xsl:otherwise>
<script src="https://maps.google.com/maps/api/js?sensor=false&amp;region=DE" type="text/javascript"></script>
<script src="/_catalogs/masterpage/js/jquery.zgooglemap.min.js" type="text/javascript"></script>
<div class="ViewWithMapContainer">
<xsl:attribute name="View">
<xsl:value-of select="$View" />
</xsl:attribute>
<xsl:attribute name="ListTitle">
<xsl:value-of select="$ListTitle" />
</xsl:attribute>
<xsl:apply-templates />
<xsl:for-each select="$Rows">
<xsl:call-template name="RenderViewWithMapRow" />
</xsl:for-each>

</div>
</xsl:otherwise>

</xsl:choose>

</xsl:template>

Die Daten aus dem Query in der aspx Datei werden hier der Variablen „Rows“ zugwiesen. Danach wird getestet, ob die Query überhaupt Ergebniszeilen zurückgegeben hat und je nachdem wird das Template „RenderViewEmpty“ bzw. für jede Zeile das Template „RenderViewWithMapRow“ aufgerufen. Bevor das Template zum Rendern der Zeilen aufgerufen wird, werden noch die benötigten Javascripte für die Google Map API und zGoogleMap eingebunden. (jQuery sollte natürlich auch noch eingebunden werden, falls das noch nicht im Mastertemplate geschehen ist.)

Als nächstes definieren wir das Template für die leere Liste.

<xsl:template name="RenderViewEmpty">
<!-- Insert code for view without a result. -->
</xsl:template>

Dann kommt der interessanteste Teil, nämlich die Darstellung der Karte für die Ergebniszeilen.


<xsl:template name="RenderViewWithMapRow">
<div>
<div id="googlemap" style="width: 600px; height: 600px;"></div>
<div id="details" style="display: table; padding-left: 10px;">
<p>
<b>Büro <xsl:value-of select="@Title" /></b>
</p>
<xsl:call-template name="RenderViewColumn">
<xsl:with-param name="Value" select="@WorkAddress" />
</xsl:call-template>
<xsl:value-of select="@WorkZip"/>, <xsl:value-of select="@WorkCity"/>
<br />
T <xsl:value-of select="@WorkPhone"/> <br></br>
F <xsl:value-of select="@WorkFax"/> <br></br>
<xsl:call-template name="ViewAsEMail">
<xsl:with-param name="EMail" select="@EMail" />
</xsl:call-template>

</div>
</div>
<script type="text/javascript">
var myWorkAddress = '<xsl:value-of select="normalize-space(@WorkAddress)"/>';
var myWorkCity = '<xsl:value-of select="normalize-space(@WorkCity)"/>';
var myWorkPhone = '<xsl:value-of select="normalize-space(@WorkPhone)"/>';
var myWorkFax = '<xsl:value-of select="normalize-space(@WorkFax)"/>';
var myEMail = '<xsl:value-of select="normalize-space(@EMail)"/>';
var myWorkZip  = '<xsl:value-of select="normalize-space(@WorkZip)"/>';
var aLocations = new Array( myWorkAddress + ',' + myWorkCity + ',de');
var aTitles = new Array('Location '+ myWorkCity );
var aSummary = new Array('<h3>Location in '+ myWorkCity + '</h3><p>' + myWorkAddress + '<br />' + myWorkZip + ' ' + myWorkCity + '<br />T '+ myWorkPhone + '<br />F ' + myWorkFax + '<br /><a href="mailto:' + myEMail + '">' + myEMail + '</a></p>');
jQuery(document).ready(function() {
jQuery('#googlemap').GoogleMap(aLocations, aTitles, aSummary, { type: 3, width: '600px', height: '600px', zoom: 12});
});

</script>

</xsl:template>

Zuerst wird ein HTML Template definiert, das die Daten aus den Ergebniszeilen darstellt. Darin findet man auch das DIV-Element „googlemap“, das die Karte später aufnehmen wird.
Weil zGoogleMaps über Javascript gesteuert wird, müssen wir zunächst die Sharepoint-Variablen in JavaScript-Variablen schreiben. Das geschieht mit dem Befehl


var myVariable = '';

Hier ist wichtig, dass mit der Funktion „normalize-space“ alle Whitespaces wie Zeilenumbrüche und Tabulatoren aus der Variablen entfernt werden, da sonst JavaScript einen Fehler wegen nicht abgeschlossenen String-Literalen melden würde.

Danach werden die Arrays aLocations, aTitles und aSummary für den Aufruf von zGoogleMap zusammengebaut.
Schließlich wird in der ready-Funktion, also wenn das Dokument vollständig geladen wurde, das DIV-Element „googlemap“ durch die Karte ersetzt. Das sollte es gewesen sein.

Wenn wir nun in der aspx Datei, die unser XSLT View benutzt, sicherstellen, dass der Webpart, der unser Template „RenderViewWithMap“ aufruft genau ein Element zurückliefert, wird eine GoogleMap mit den Daten aus der Liste dargestellt.

Natürlich gibt es auch andere – vielleicht auch bessere – Wege eine Google Map in einem Sharepoint View darzustellen, aber die vorgestellte Methode funktioniert problemlos, lässt sich leicht einbauen und mit einfachen Mitteln an eigene Bedürfnisse anpassen.