The router isn't available in enteringInteractive

Fuse 0.30

It appears that you can’t navigate when returning to the application in order to reset the view state.

// This works when responding to a click event
exports.goStart = function() {
    router.goto("start", {})
}

// But you can't call router from a lifecycle event
Lifecycle.on("enteringInteractive", function() {
    router.goto("start", {})
})

Fuse.Scripting.ScriptException: 
Name: ReferenceError

Error message: Can't find variable: router

File name: MainView.js

Line number: 71

JS stack trace: MainView.js:71:15

(lldb) 

libc++abi.dylib: terminating with uncaught exception of type uThrowable: Uno.Exception
(lldb) Process 497 stopped
* thread #1: tid = 0xe00f, 0x0000000191e4e014 libsystem_kernel.dylib`__pthread_kill + 8, queue = 'com.apple.main-thread', stop reason = signal SIGABRT
    frame #0: 0x0000000191e4e014 libsystem_kernel.dylib`__pthread_kill + 8
libsystem_kernel.dylib`__pthread_kill:
->  0x191e4e014 <+8>:  b.lo   0x191e4e02c               ; <+32>
    0x191e4e018 <+12>: stp    x29, x30, [sp, #-16]!
    0x191e4e01c <+16>: mov    x29, sp
    0x191e4e020 <+20>: bl     0x191e317b4               ; cerror_nocancel
(lldb) * thread #1: tid = 0xe00f, 0x0000000191e4e014 libsystem_kernel.dylib`__pthread_kill + 8, queue = 'com.apple.main-thread', stop reason = signal SIGABRT
  * frame #0: 0x0000000191e4e014 libsystem_kernel.dylib`__pthread_kill + 8
    frame #1: 0x0000000191dc23f4 libsystem_c.dylib`abort + 140
    frame #2: 0x000000019188d2d4 libc++abi.dylib`<redacted> + 132
    frame #3: 0x00000001918aaca8 libc++abi.dylib`<redacted> + 280
    frame #4: 0x00000001918b8860 libobjc.A.dylib`<redacted> + 152
    frame #5: 0x00000001918a766c libc++abi.dylib`<redacted> + 16
    frame #6: 0x00000001918a6f84 libc++abi.dylib`__cxa_throw + 136
    frame #7: 0x0000000100172c40 Veckoappen`g::Fuse::AppBase::OnUnhandledException(this=0x0000000174464c80, e=0x0000000170463140, propagate=false) + 336 at Fuse.g.cpp:539 [opt]
    frame #8: 0x00000001001063d0 Veckoappen`g::Fuse::App::OnTick(this=0x000000013df39e20, sender=<unavailable>, args=<unavailable>) + 124 at Fuse.App.mm:211 [opt]
    frame #9: 0x0000000100275a3c Veckoappen`uDelegate::Invoke(this=0x00000001700999b0, retval=<unavailable>, args=0x000000016fd3d9e0, count=2) + 220 at ObjectModel.cpp:1440 [opt]
    frame #10: 0x0000000100275d48 Veckoappen`uDelegate::Invoke(this=<unavailable>, count=<unavailable>) + 180 at ObjectModel.cpp:1531 [opt]
    frame #11: 0x00000001002520a8 Veckoappen`g::Uno::Platform2::Display::OnTick(this=0x00000001702a37e0, args=0x0000000170465040) + 68 at Uno.Platform2.g.cpp:1292 [opt]
    frame #12: 0x0000000100278a0c Veckoappen`::-[uDisplayTickNotifier uOnDisplayTick:](self=0x00000001702041a0, _cmd=<unavailable>, sender=0x000000017001dab0) + 132 at Uno.Platform2.Display.mm:42 [opt]
    frame #13: 0x0000000196083640 QuartzCore`<redacted> + 44
    frame #14: 0x00000001960834ec QuartzCore`<redacted> + 444
    frame #15: 0x00000001930ec570 IOKit`IODispatchCalloutFromCFMessage + 372
    frame #16: 0x0000000192e1656c CoreFoundation`<redacted> + 180
    frame #17: 0x0000000192e2e934 CoreFoundation`<redacted> + 56
    frame #18: 0x0000000192e2e0e8 CoreFoundation`<redacted> + 436
    frame #19: 0x0000000192e2bbcc CoreFoundation`<redacted> + 1840
    frame #20: 0x0000000192d5a048 CoreFoundation`CFRunLoopRunSpecific + 444
    frame #21: 0x00000001947dd198 GraphicsServices`GSEventRunModal + 180
    frame #22: 0x0000000198d34628 UIKit`<redacted> + 684
    frame #23: 0x0000000198d2f360 UIKit`UIApplicationMain + 208
    frame #24: 0x000000010027880c Veckoappen`main(argc=1, argv=0x000000016fd3fbe8) + 116 at Main.mm:17 [opt]
    frame #25: 0x0000000191d3c5b8 libdyld.dylib`<redacted> + 4

ERROR: iOS run failed.

Could you include some more of your code so that we can see more of how its structured?

Its hard to tell if these two functions are in the same file or not for example, and also how they relate to the UX :slight_smile:

Apologies for not creating a proper test case. The structure of the files looks like this:

MainView.ux

<App>
    <JavaScript File="MainView.js" />

    <Router ux:Name="router" />

    <ClientPanel>
        <ux:Include File="MainNavigator.ux"/>
    </ClientPanel>

</App>

MainView.js

var Lifecycle = require('FuseJS/Lifecycle')

// This works when responding to a click event
exports.goStart = function() {
    router.goto("start", {})
}

// But you can't call router from a lifecycle event
Lifecycle.on("enteringInteractive", function() {
    router.goto("start", {})
})

MainNavigator.ux

<DockPanel>

    <PageControl>
        <ux:Include File="Pages/Start.ux" />

        <Navigator ux:Name="other">

            <Page ux:Template="blank" Color="#fff" Transition="None" />

            <Panel ux:Template="events" Transition="None">
                <PageControl>
                    <ux:Include File="Pages/Events.ux" />
                </PageControl>
            </Panel>
            
            <ux:Include File="Pages/Settings.ux" />
            
        </Navigator>

    </PageControl>

    <Grid Dock="Bottom" Color="#444" RowCount="1" ColumnCount="3" Padding="4">
        <NavIcon Title="Overview" File="Assets/icons/start.png" Clicked="{goStart}" />
        <NavIcon Title="Events" File="Assets/icons/organizations.png" Clicked="{goEvents}" />
        <NavIcon Title="Settings" File="Assets/icons/settings.png" Clicked="{goSettings}" />
    </Grid>

</DockPanel>

Hi!

I just made a test case, and it works fine for me. Here is the code i used:

MainView.ux

<App>
	<Panel>
		<JavaScript File="MainView.js" />

		<Router ux:Name="router" />

		<DockPanel>
			<Grid ColumnCount="3" RowCount="1" Height="100" Dock="Top">
				<Button Text="P1" Clicked="{goto1}"/>
				<Button Text="P2" Clicked="{goto2}"/>
				<Button Text="P3" Clicked="{goto3}"/>
			</Grid>

			<Navigator DefaultPath="page1">
				<Page ux:Template="page1" Color="Red" />
				<Page ux:Template="page2" Color="Green" />
				<Page ux:Template="page3" Color="Blue" />
				<Page ux:Template="page4" Color="Black" />
			</Navigator>
		</DockPanel>
	</Panel>
</App>

MainView.js

var Observable = require("FuseJS/Observable");
var Lifecycle = require("FuseJS/Lifecycle");

function goto1() { router.goto("page1"); }
function goto2() { router.goto("page2"); }
function goto3() { router.goto("page3"); }


Lifecycle.on("enteringInteractive", function(){
	router.goto("page4");
});

module.exports = {
	goto1, goto2, goto3
};

There might be some other reason why you’re getting that error, but i think there is some more code that i’m not seeing.

Another thing you should be aware of is that using <ux:Include as a primary way of splittin up code into files is considered bad practice. You should instead try to componentize using ux:Class. You can read about that in this article: https://www.fusetools.com/docs/basics/creating-components

<ux:Include covers some edge cases, but can make your code more difficult to reason about.

Please see if you’re able to pinpoint the error using my code example as a reference and let me know how it goes :slight_smile:

Awesome! I’ll try to create a test case to force the bug.

Thanks for the tip on components, I’ll revisit that document.

Just for the record, I had by mistake required my js-file from itself (don’t ask…). Now that I fixed this it is all working as expected. I am guessing that the second instance wasn’t bound properly to the router which caused the bug in the event listener of that instance. I believe you can close this issue.

great!

Glad we got it sorted :slight_smile: