by Todd Geist


version 1.0.3  – 4/18/2013 – switched to using LayoutIDs instead of LayoutNumber. Handling nested NavBars better.

Honestly, there could be a lot more to this one. Its just a start. But it does work. 🙂  You can create navbars that are easy to style, and easy to use, and look great.


Bob Ellis

  • changed the setup to use LayoutIDs instead of LayoutNumbers. More robust
  • improved “navigate” script to better handle nested NavBars


  • Style-able using conditional formatting
    • use layout name for self aware high-lighting
  • Nav Bar Button labels are not based on layout naming
    • More flexible
  • Respects FileMaker layout security
    • Layouts that are hidden to the user do not appear in the nav bars
  • Multi-Level – you can create nested Nav Bars
  • Remembers the last selection of nested navbars
  • Includes pre and post hooks that fire on button selection

[ba-button link=”” color=”blue” target=”self”]Download Navigation[/ba-button]

46 responses to “Navigation”

  1. Bob Ellis says:

    Hello Todd, love what you are doing here! I have a question in regards to this module. The module is not saving the last visited sub page. Meaning if I navigate to Invoices: Passed Due -> Customers -> Invoices it defaults to the Invoices: Invoices layout. I ran the debugger and stepping through the code I came across some script steps in the Navigate script that are needing custom functions that are not present. The code in question is:

    Set Variable [$buttonNumber; Value:/*#Get ( $store ; $nameOfNavBar& "_LastChoice" )*/]
    Set Field[Navigation::variableStore; /*Let(
    varName = $nameOfNavBar & "_LastChoice"


    #Remove ( $store ; varName) &
    # ( varName ; $buttonNumber )


  2. Bob Ellis says:

    I look forward to it.

    I was able to get the module to work. I happened to have those custom functions in another file. Simply enabling those calcs after installing the cf’s was not the fix I had expected.

    After stepping through the scripts I noticed the #Remove($store ; varName) was actually removing everything in the variableStore field before adding the new parameters. Investigating further, I noticed the variableStore field was not a list, which I believe is what the #Remove() cf requires to work properly ( I could be using an outdated cf also, I haven’t looked that far), so I changed that set field step calc to:
    Let([ varName = $nameOfNavBar & "_LastChoice" ]; #Remove ( $store ; varName) & ¶ & # ( varName ; $buttonNumber ))

    That seemed to do the trick, (I haven’t tested it extensively to see if it will leave empty pr, or if that is an issue)

    Running it again, variableStore was holding a list, and those values were being swapped out as expected, however, when clicking on the Invoices button, it still refused to return to Passed Due. After further digging I looked into the $nextLevelNavbarFieldName being used to filter $fieldNamesOnLayout. The former was being set with a hard coded “Navigation::” to the field name where the latter had no table name, so they would never match. I removed the $table from the exit script step and now it works great!

    Love the module. It even returns to the last layout after closing the file and re-opening. I am hopefull this is something I can integrate into a “Sessions” table. Gears are turning….

    I almost pulled the trigger on purchasing a bolt on navigation system yesterday. Glad I didn’t. Your module does everything that one does but with far less overhead. Simply awesome!

    Thank you,

  3. Bruce Robertson says:

    “Passed Due” in invoice part of nav. Oops. Should be Past Due

  4. […]  or “mFM Modules” ( ModularFileMaker Modules ).  mFM Modules provide features like Navigation Bars, Transaction Frameworks, search utilities , SQL helpers, etc.  These are all below the level of […]

  5. Bob Ellis says:

    Little tip for those who may be using sub navbar on a single level layout, for example “Home”.

    When using the conditional formatting calculation below and your field is empty, it will evaluate to True and your empty field will not be hidden. Simply moving this condition above IsEmpty(Self) will hide your button.

    ln =Get (LayoutName) ;
    ln = Substitute( ln ; ":"; ¶ );

    n= GetValue(ln ; 2)


    Trim(n) = Self


  6. […]  or “mFM Modules” ( ModularFileMaker Modules ).  mFM Modules provide features like Navigation Bars, Transaction Frameworks, search utilities , SQL helpers, etc.  These are all below the level of […]

  7. NoHoWarlord says:

    Hello Todd,
    Were you at the March FMDiSC meeting when David Crossland did his presentation on passing parameters? He had a navigation engine in it that allowed him to create something similar.
    Thanks Todd!

    • Todd Geist says:

      Hey 🙂

      No I wasn’t there. I really didn’t want to do *this* Navigation engine, but I couldn’t find one. I hope other people post their own versions. We need more choices.


      • Michael Bateman says:

        Yes, what David was doing is perfect for here, but he may have other plans for it. But yeah, it would be great to have some choices on that front 🙂


  8. […] Bob Ellis came up with some nice additions to the Navigation Module. […]

  9. Simon Plint says:

    So to update to v1.0.3 do I only need to replace the contents of the Navigate script or is there more to it?

    Thanks so much for this site.


    • Bob Ellis says:

      Import/copy paste: Get Field Label, Get Layout Id, LayoutNameFromId, LayoutIdFromName

      Replace the Navigate Script
      Replace the Set Label For This Layout Script

  10. dvareika says:


    I was able to configure it all on a sample db.
    The only thing I do not know how to do is “My Dashboard” = Home to remain the button selected as with the other buttons.



    • dvareika says:

      Found it myself, the layout name has to be the same as the button name.
      Do not know why I could not at first place.

      Thanks a lot for everything, the Module is impressive!



      • Todd Geist says:

        Actually I think it is just the first word of the layout name. All that is done with conditional formatting on the repeating fields. so you can easily change the logic.

        Thanks 🙂

  11. Bruce Robertson says:

    I see that there is a small spelling error, a bit humorous:
    “Layouts that are hidden to the user do not appear in the nag bars”

    Probably that is supposed to be NAV bars but Nag bars could be an interesting new feature idea!

  12. Trevor Gildersleeve says:

    Great site, great module. Thanks for sharing. I’m just looking into the latest version (1.0.3 – 4/18/13) and just wanted to mention that the installation instructions in the README script needs a few updates. It mentions scripts that don’t exist, and the version # isn’t updated there either. Easy oversight, but also an easy fix that’ll instill confidence in the module if it’s documentation is current. Thanks again!

  13. Mikerrr says:

    +1 On the README being slightly out of date. Still easy enough to setup though.

    Are you able to have a navigation button call a script rather than go directly to a layout? If so, how?

    • Todd Geist says:

      You know, here is the really cool thing about this all being free and unlocked. You can download the file and fix something that you think needs fixing, then you can email the author or maintainer and share your fix with them. Then they can put it back into the main branch. That way the code keeps getting better and better.

      Remember most of this stuff is free. That means the people doing it can use all the help they can get.


    • Todd Geist says:

      As for running a script…. you could use an OnLayoutEnter script trigger to fire a script when the Navigation engine dropped the user on a layout.

      There are also hook scripts that run just before and just after the navigation occurs, you could intercept the script there.


  14. Ming Jiang says:

    Great idea, and useful module.

    It would be nice to have a demo video for each module.

  15. Matt Bowlby says:

    I am having trouble implementing this with more than two buttons in a nested nav bar. I had it working beautifully with a top nav bar and nested nav bars each with two buttons. But when I tried making three buttons on one of the navbars, it doesn’t seem to work. Any suggestions?

    • Matt Bowlby says:

      Nevermind. I have resolved it. I was not specifying the proper repetition for the third button.

  16. Simon Plint says:

    Todd, small bug in the script “Test for Field ( $fieldName ; $scriptName )”. Line 13, second “Show Custom Dialog” statement.

    Message code is “The script ” & Quote( Get (ScriptName) ) & ” & can’t find a field called ” & Quote( $field ) & “. Script execution will HALT”.

    $field should be $fieldName

    With this correction the script correctly notifies the user of the name of the field that is missing from the Navigation table.


  17. […]  or “mFM Modules” ( ModularFileMaker Modules ).  mFM Modules provide features like Navigation Bars, Transaction Frameworks, search utilities , SQL helpers, etc.  These are all below the level of […]

  18. Mike says:

    Hi Todd, this module is a lifesaver for a newbie like me. I’m following the data separation model with a solution I’m working on, with all permissions, etc. set in the data file. If the navigation module is set up on the interface file will it still prevent restricted layouts from showing up in a users navigation bar? Or is this best used in a single file solution?

  19. Charles South says:

    Oops … sorry … I posted a comment to the general Discussions topic when I should have posted it specifically to this discussion group having to do with the Navigation module. Sorry. Todd, maybe you can move my comment into this forum so it won’t interfere with your other more general forum.

    • Todd Geist says:

      Hi Charles,

      Unfortunately I can’t move your comment. But you are right on. The Layout ID calculation is flawed. I noticed this problem with the change that was made, but I didn’t have time to dig into it. Why don’t you download a copy of the file, and make the changes, and send it back to me. That would be great !



      • Charles South says:

        I don’t know how to send the file back to you (I don’t see your email address in the places I’ve looked in the mFM site). But the change is simple enough to describe, and I think there’s only one place it needs to be made — in the “Set Label For This Layout” script, in the bottom paragraph titled “Setting the layout ID instead of layout number”:

        Replace the two lines:
        Perform Script [“LayoutIdFromName ( layoutName )” Parameter: (Get(LayoutName)]
        Set Field By Name [$layoutNumberFieldName; Get ( ScriptResult )]

        Set Variable [$layoutID; Value: GetValue ( LayoutIDs(Get(FileName)) ; Get(LayoutNumber) )]
        Set Field By Name [$layoutNumberFieldName; $layoutID ]

        This works reliably because you are currently on the layout for which you wish the ID. If there were other places an ID needed to be determined then it would be worth creating a parallel script similar to the others in this module, titled “LayoutIdFromNumber (layoutNumber)” but as long as there is this one reference I consider it’s easier and clearer to do it directly as I did it above than to create the subscript.

  20. Matt Bowlby says:

    I have implemented the Navigation module along with the Multilingual Variable module. I would like the menu items in the navigation to be global variables (i.e. <>) defined using the Multilingual Variable module. Is it possible to do this? If I put the global variable in the script parameter of the Navigation module, it doesn’t show up correctly. I have tried entering “”<>”” and “$$Variable1”. Neither works.

    Any ideas? I want the names of the navigation items to change depending on the language that is selected.

    • Hey Matt;
      What you’re trying to accomplish is do-able, I think you might just need to leave out the quotation marks around the parameter you’re passing. Passing $$Variable1 instead of “$$Variable1” means that FileMaker Pro is going to evaluate that global variable instead of reading a string literal.

  21. JmcL07 says:

    Thanks for the module. The top menu works well but when I click on a sub-menu I get – Error “0” when running LayoutNameFromid (layout id) – Any ideas what could be causing this? Thanks,

  22. JmcL07 says:

    In the LayoutNameFromid (layoutid) the If [Isempty($layoutname)] triggers the custom dialog described above. Then in the Navigate script the If[ $error = 105] custom dialogue is triggered. Thanks

  23. John Colburn says:

    Sorry, I’m sure it’s just my ineptness, but I am unable to find a link on this page to download the Navigation module.


  24. Raving Coder says:

    Hi John,

    Did a little google search… This link still works…


  25. Evan Z says:

    I followed the steps in the READ ME file, though some of the steps are either mislabeled or the script does not exist:

    There is no “Setup Navigation” but I deciphered that that was the same as “Setup Navbars”, BUT, step 5, there is no “OnNavBarClicked” script so I’m not sure what to do next. I then copied an example Navbar from one of the layouts and nothing seems to happen. I’m sure it relates to step 5, but I do not see what the proper step is. Any help would be greatly appreciated!

Leave a Reply

Your email address will not be published. Required fields are marked *