Ticket Created
over 3 years ago

WERETECH-12628

LocalMoment is wrong

The documentation fails to provide an initializing Constructor and the example is wrong.

a) It requires (where, when) not (when, where).

b) it doesn't take a Gregorian.moment as the when argument.

This, from the documentation fails:

if (Gregorian has :localMoment){
		var options = {
			:year   => 2018,
			:month  => 2,
			:day    => 24,
			:hour   => 0,
			:min    => 12 
		};
		var when = Gregorian.moment(options);
		
		var where = new Position.Location({
			:latitude  =>  38.85391,
			:longitude => -94.79630,
			:format    => :degrees,
		});

		var local = Gregorian.localMoment(when, where);
		var info = Gregorian.info(local, Time.FORMAT_SHORT);
	}

This works

if (Gregorian has :localMoment){
		var options = {
			:year   => 2018,
			:month  => 2,
			:day    => 24,
			:hour   => 0,
			:min    => 12 
		};
		var when = Gregorian.moment(options);
		
		var where = new Position.Location({
			:latitude  =>  38.85391,
			:longitude => -94.79630,
			:format    => :degrees,
		});

		var local = Gregorian.localMoment(where, when.value());
		var info = Gregorian.info(local, Time.FORMAT_SHORT);
	}

- note (where, when), not (when, where) , and a number not a moment.

  • I just hit this bug for anyone wondering. Calling the API as per the docs crashes on device "unhandled exception". However calling value() as described above works fine. However, you have to do a disgusting trick like this to make the type checker happy:

    var z = m1.value() as Lang.Number or Time.Moment;
    var t1 = Time.Gregorian.localMoment(l1, z);

  • More than a year passed by and no reply.
    I'm trying to use `Gregorian.localMoment` with the SDK 6.4.2 and the simulator.
    When using

    Gregorian.localMoment(where, when.value());

    I get:

    Invalid '$.Toybox.Lang.Number' passed as parameter 2 of type '$.Toybox.Time.Moment'.

    But if I use

    Gregorian.localMoment(where, when);

    The app crashes with

    Exception: UnexpectedTypeException: Expected an object of type Time.Moment

  • So, as far as I see, when I build the project with SDK >= 4.1.6, localMoment requires a Time.Gregorian.moment as a second argument.

    However, given the exception mentioned above, when the app is running on the watch, localMoment requires a Number (when.value()).

    I suspect, either I am configuring something wrong, or the most recent SDK doesn't accurately simulate the watch firmware (at least for my fenix-6).

    Only workaround I found so far is to build the project with SDK 4.1.5, where localMoment still requires a Number as a second argument.

    This way both the simulator and the watch are happy using a Number and I can build the project successfully.

  • Hi, is there any recent update on this one? I am currently having the same problem.

    Trying to create a a localMoment as per documentation:

    import Toybox.Position;
    import Toybox.Time;
    
    function getLocalMoment() {
        var day = Time.Gregorian.info(Time.now(), Time.FORMAT_MEDIUM);
    
        var options = {
            :year   => day.year,
            :month  => day.month,
            :day    => day.day,
            :hour   => 0,
            :min    => 0
        };
    
        var when = Time.Gregorian.moment(options);
    
        var where = new Position.Location({
            :latitude  => 38.85391,
            :longitude => -94.79630,
            :format    => :degrees,
        });
    
        try {
            var local = Time.Gregorian.localMoment(where, when);
        } catch( ex ) {
            ex.printStackTrace();
        }
    
        return local;
    }
    "where" is a Position.Location and "when" is a Time.Gregorian.moment.

    This works perfectly fine in the simulator, but when it's side loaded to the watch (fenix6) it crashes with the following exception:
    Exception: UnexpectedTypeException: Expected Number, given Object
    Stack: 
      - pc: 0x100004bc
      - pc: 0x1000013e
      - pc: 0x1000083f


    Apparently, 
    Time.Gregorian.localMoment requires a Time.Gregorian.moment to initialise within the simulator, while a Number to initialise within the watch.

    It looks as if the simulator is running a different API version than the watch? Or is it some configuration mistake on my side?

    My manifext.xml has 
    version="3" and minApiLevel="3.2.0", which I believe should be fine, given that localMoment is supported since 3.3.0.
  • Thanks for the insights Alan.raceQs

    I have now tested my data field using the Gregorian.localMoment(where, when.value()) function call. It's called three times every second in my App. After some time of running, I think 5-10 min, it crashed in the very line with a call to this function! And, it crashed with 

         Error: Out Of Memory Error
         Details: 'Failed invoking <symbol>'    

    So, something in this function implementation on my Epix2 seem to leak memory or whatever. Clearly this function cannot be trusted in practice!!!!