Revision history [back]

click to hide/show revision 1
initial version

answered 2014-11-27 15:42:23 +0800

cyiannoulis gravatar image cyiannoulis

Confirmed. The json geolocation object is null when it is passed from Firefox. In Chrome works fine. I am not sure if this is an issue related to ZK or to some sort of security/privacy settings.

The workaround i found is to re-package the location coordinates on client-side inside a new JSON object and then send this new object to the server. Here is a complete example demonstrating both chrome and firefox:

<?page title="Json Geo" contentType="text/html;charset=UTF-8"?>
<zk>
<window id="winMain" title="Json Geo" border="none" 
        xmlns:n="native" xmlns:w="client" 
        apply="snippets.json.GeolocationController">

    <vlayout>
        <hlayout valign="middle">
            Resolve Geolocation
            <button label="Chrome" w:onClick="sendGeolocationFromChrome();" />
            <button label="Firefox" w:onClick="sendGeolocationFromFirefox();" />
        </hlayout>
        <hlayout valign="middle">
            Your location: latitude<textbox id="txtLat" />, longitude<textbox id="txtLon" />  
        </hlayout>
    </vlayout>

</window>

<script type="text/javascript"><![CDATA[

    function sendGeolocationFromChrome() {
        navigator.geolocation.getCurrentPosition(function(position) {
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromChrome', position));
        });
    }

    function sendGeolocationFromFirefox() {
        navigator.geolocation.getCurrentPosition(function(position) {
            var lat = position.coords.latitude;
            var lon = position.coords.longitude;
            var jsonObject = {coords: {latitude: lat, longitude: lon}};
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromFirefox', jsonObject));
        });
    }

]]></script>

</zk>

And a simple controller with two event handlers, one for Chrome and one for Firefox:

import org.zkoss.json.JSONObject;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.event.Event;
import org.zkoss.zk.ui.select.SelectorComposer;
import org.zkoss.zk.ui.select.annotation.Listen;
import org.zkoss.zk.ui.select.annotation.Wire;
import org.zkoss.zul.Textbox;

public class GeolocationController extends SelectorComposer<Component> {

    private static final long serialVersionUID = 1L;

    @Wire private Textbox txtLat;
    @Wire private Textbox txtLon;

    @Listen("onSendLocationFromChrome = window")
    public void onSendLocationFromChrome(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }

    @Listen("onSendLocationFromFirefox = window")
    public void onSendLocationFromFirefox(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }
}

Tested with Chrome 39.0.2171.71 and Firefox 33.1.1. It doesn't work with IE 8.

Hope that helps

Costas

Confirmed. The json geolocation object is null when it is passed from Firefox. In Chrome works fine. I am not sure if this is an issue related to ZK or to some sort of security/privacy settings.

The workaround i found is to re-package the location coordinates on client-side inside a new JSON object and then send this new object to the server. Here is a complete example demonstrating both chrome and firefox:

<?page title="Json Geo" contentType="text/html;charset=UTF-8"?>
<zk>
<window id="winMain" title="Json Geo" border="none" 
        xmlns:n="native" xmlns:w="client" 
        apply="snippets.json.GeolocationController">

    <vlayout>
        <hlayout valign="middle">
            Resolve Geolocation
            <button label="Chrome" w:onClick="sendGeolocationFromChrome();" />
            <button label="Firefox" w:onClick="sendGeolocationFromFirefox();" />
        </hlayout>
        <hlayout valign="middle">
            Your location: latitude<textbox id="txtLat" />, longitude<textbox id="txtLon" />  
        </hlayout>
    </vlayout>

</window>

<script type="text/javascript"><![CDATA[

    function sendGeolocationFromChrome() {
        navigator.geolocation.getCurrentPosition(function(position) {
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromChrome', position));
        });
    }

    function sendGeolocationFromFirefox() {
        navigator.geolocation.getCurrentPosition(function(position) {
            var lat = position.coords.latitude;
            var lon = position.coords.longitude;
            var jsonObject = {coords: {latitude: lat, longitude: lon}};
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromFirefox', jsonObject));
        });
    }

]]></script>

</zk>

And a simple controller with two event handlers, one for Chrome and one for Firefox:

import org.zkoss.json.JSONObject;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.event.Event;
import org.zkoss.zk.ui.select.SelectorComposer;
import org.zkoss.zk.ui.select.annotation.Listen;
import org.zkoss.zk.ui.select.annotation.Wire;
import org.zkoss.zul.Textbox;

public class GeolocationController extends SelectorComposer<Component> {

    private static final long serialVersionUID = 1L;

    @Wire private Textbox txtLat;
    @Wire private Textbox txtLon;

    @Listen("onSendLocationFromChrome = window")
    public void onSendLocationFromChrome(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }

    @Listen("onSendLocationFromFirefox = window")
    public void onSendLocationFromFirefox(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }
}

Tested with Chrome 39.0.2171.71 and Firefox 33.1.1. It doesn't work with IE 8.8. I didn't test it with IE 9/10.

Hope that helps

Costas

Confirmed. The json geolocation object is null when it is passed from Firefox. In Chrome works fine. I am not sure if this is an issue related to ZK or to some sort of security/privacy settings.settings of the browser.

The workaround i found is to re-package the location coordinates on client-side inside a new JSON object and then send this new object to the server. Here is a complete example demonstrating both chrome and firefox:

<?page title="Json Geo" contentType="text/html;charset=UTF-8"?>
<zk>
<window id="winMain" title="Json Geo" border="none" 
        xmlns:n="native" xmlns:w="client" 
        apply="snippets.json.GeolocationController">

    <vlayout>
        <hlayout valign="middle">
            Resolve Geolocation
            <button label="Chrome" w:onClick="sendGeolocationFromChrome();" />
            <button label="Firefox" w:onClick="sendGeolocationFromFirefox();" />
        </hlayout>
        <hlayout valign="middle">
            Your location: latitude<textbox id="txtLat" />, longitude<textbox id="txtLon" />  
        </hlayout>
    </vlayout>

</window>

<script type="text/javascript"><![CDATA[

    function sendGeolocationFromChrome() {
        navigator.geolocation.getCurrentPosition(function(position) {
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromChrome', position));
        });
    }

    function sendGeolocationFromFirefox() {
        navigator.geolocation.getCurrentPosition(function(position) {
            var lat = position.coords.latitude;
            var lon = position.coords.longitude;
            var jsonObject = {coords: {latitude: lat, longitude: lon}};
            zAu.send(new zk.Event(zk.Widget.$('$winMain'), 'onSendLocationFromFirefox', jsonObject));
        });
    }

]]></script>

</zk>

And a simple controller with two event handlers, one for Chrome and one for Firefox:

import org.zkoss.json.JSONObject;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.event.Event;
import org.zkoss.zk.ui.select.SelectorComposer;
import org.zkoss.zk.ui.select.annotation.Listen;
import org.zkoss.zk.ui.select.annotation.Wire;
import org.zkoss.zul.Textbox;

public class GeolocationController extends SelectorComposer<Component> {

    private static final long serialVersionUID = 1L;

    @Wire private Textbox txtLat;
    @Wire private Textbox txtLon;

    @Listen("onSendLocationFromChrome = window")
    public void onSendLocationFromChrome(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }

    @Listen("onSendLocationFromFirefox = window")
    public void onSendLocationFromFirefox(Event e) {
        JSONObject geolocation = (JSONObject) e.getData();
        JSONObject coords = (JSONObject) geolocation.get("coords");
        Double lat = (Double)coords.get("latitude");
        Double lon = (Double)coords.get("longitude");
        txtLat.setValue(lat.toString());
        txtLon.setValue(lon.toString());
    }
}

Tested with Chrome 39.0.2171.71 and Firefox 33.1.1. It doesn't work with IE 8. I didn't test it with IE 9/10.

Hope that helps

Costas

Support Options
  • Email Support
  • Training
  • Consulting
  • Outsourcing
Learn More