Accordion Navigation in FMP16

Document created by DanielShanahan on Nov 2, 2017
Version 1Show Document
  • View in full screen mode

Intro

Accordion navigation is a common design pattern in both web and desktop applications.  A quick look at admin templates shows the predominance of this method of navigation.

 

Web_Admin_Accordion_Nav.png

 

A search for admin templates shows how common vertical, accordion navigation is in data driven web design.

 

This design pattern has been a bit tricky in FileMaker Pro.  Portals have been successfully used in the past, as I’ve described in this thread.  One of the issues with using a portal for accordion navigation is that a relationship must be created between the navigation table and every table occurrence where you want the accordion navigation to appear.

 

Another method is now available, thanks to the new Card window in FileMaker 16.   With Card windows no relationships are required, which greatly simplifies the relationship graph.  In this document I’ll walk through one method for creating vertical, accordion navigation.  I’ll use the Inventory starter solution that comes with FileMaker Pro 16.  The end result will have three stages:

  1. Hidden
  2. Level 1 Displayed
  3. Level 2 Displayed

 

Those states look like this:

Accordion_Nav_Three_Stages.png

From left to right, the three stages of accordion menus in FileMaker Pro using a Card window: Hidden, Level 1 Displayed, Level 2 Displayed

 

Step 1: Define Navigation List

The first thing we need to do is determine what will be in our navigation.  This can be done inside FileMaker Pro, but I prefer to use a text editor for simplicity.  That way, I can create and manipulate the list before I’m ready to create data records.  It’s ok if we don’t think of everything at the beginning.  And, in fact, I’ve purposely left one out.  As we’ll see later, adding additional items to the list is fairly simple.  Here’s the first run at a list:

 

Company

Item

Purchasing

Receiving

Put-away

Sales

Shipping

Admin

 

That’s the level one list.  Each of those will have a sub-menu, which I’ll call Level 2.  So the expanded list looks like this:

 

Company

  Last Record(s)

  Find Company

  New Company

  Show All Companies

  Show All Customers

  Show All Vendors

  Customers Dashboard

  Vendors Dashboard

Item

  Last Record(s)

  Find Item

  New Item

  Show All Items

  Item Dashboard

Purchasing

  Last Record(s)

  Find PO

  New PO

  Show All POs

  Show Pending POs

  Show Closed POs

  Purchasing Dashboard

Receiving

  Last Record(s)

  Find Receipt

  New Receipt

  Show All Receipts

  Show PO Receipts

  Show Return Receipts

  Show Transfer Receipts

  Receiving Dashboard

Put-away

  Last Record(s)

  Find Put-away

  New Put-away

  Show All Put-away

  Show Pending Put-away

  Show In Progress Put-away

  Put-away Dashboard

Sales

  Last Record(s)

  Find Sales Order

  New Sales Order

  Show All Sales Orders

  Show Pending Sales Orders

  Show Closed Sales Orders

  Sales Dashboard

Picking

  Last Record(s)

  Find Pick

  Show All Picks

  Show Pending Picks

  Show In Progress Picks

  Show Completed Picks

  Picking Dashboard

Shipping

  Last Record(s)

  Find Shipping

  Show All Shipping

  Show Pending Shipping

  Show In Progress Shipping

  Show Closed Shipping

  Shipping Dashboard

Admin

  Settings

  Warehouses

  Locations

  Unit of Measure

  Unit of Measure Conversion

  Integrations

 

Step 2: Select the File

Now that we have out list we can go into FileMaker Pro and start to build the navigation.  To download the Inventory starter solution from FileMaker Pro, go to the application’s horizontal menu, File/Get Started…

 

FMP_Getting_Started.png

Accessing the starter solutions from FileMaker Pro 16.

 

Once inside the Get Started window, scroll down to the Inventory starter solution and click the “Create from This Starter Solution” template.

 

Step 3: Menu table and fields

Card windows enable developers to display data from a different context without leaving the original context.   In other words, we are able to see data in a different table.  So the first thing we need to do is create that table.  Open Manage Database (File/Manage/Database…), click the Tables tab and add a new table.  I’ve named the table “Menu”.  Double click the newly created table to navigate to the Fields tab for Menu.  We’ll need four fields:

 

  1. labelName  - Text
  2. level - Number
  3. sortOrder - Number
  4. sortOrderList - Summary = List of sortOrder

 

Step 4: Layouts

When we created the new table, a new layout should have automatically been created.  Go to the Manage Layouts window (File/Manage/Layouts…).  If “Menu” is not at the bottom of the list, then go to the bottom of the Manage Layouts window and click “New”.

 

I use two layouts for this technique.  One is a user interface layout - in other words, the navigation menu itself - and the other is a set up layout.  So let’s change the name of the first Menu layout from “Menu” to “Menu User Interface”.  Duplicate that layout and change the name to “Menu Setup”.  Unmark both of them so that they do no appear in the Layout drop down list.

 

Accordion_Nav_Layout_Setup.png

Two new Menu layouts in the Manage Layouts window.  Note that both are unchecked so as to not appear in the Layout drop down.

 

Step 5: Importing the Data

Go to the Menu Setup layout.  We’ll need to get the list data into this table (unless you typed the list directly into FileMaker Pro).  If you used a text editor you can import that into FileMaker Pro.  However, if you used tabs, as I did above, then FileMaker may not place the data in the correct field.  There are a number of ways to prevent this and a few more to correct it.  Its a bit of a rabbit hole to go down all the possibilities, so I’ll describe one corrective method.

 

Here is what the Menu Setup layout looks like in Table View after I imported the text file:

 

 

Accordion_Nav_List_Import.png

The tab in front of the level 2 text string imported into the level field.

 

The first thing I want to do is set the correct data for the level 1 labels.  It will be easy to find.  I’ll search for all the records where the level field is empty:

 

Accordion_Nav_Data_Cleanup_1.png

Now, that I have all the level one fields selected, I can easily set the level field of one of the records to 1 and Replace Field Contents (Records/Replace Field Contents…).  Make sure that you only have the found set you want to change.  There is no undo for Replace Field Contents.

 

Accordion_Nav_Data_Cleanup_2.png

 

Now I can go into labelName and find all the records where that field is empty:

 

Accordion_Nav_Data_Cleanup_3.png

Again, making sure that you have the correct found count (because Replace Field Contents cannot be undone), set labelName field to be the same as the level field.  To do this, go to Replace Field Contents (Records/Replace Field Contents…), select the radio button “Replace with calculated results: Specify…”:

 

Accordion_Nav_Data_Cleanup_4.png

While we’re in this found set, we can also change the level field to 2.  Change the level field of one of the records (it doesn’t matter which one, as long as we’re still in the correct found set) and change it to 2.  While still in that field, select Replace Field Contents (Records/Replace Field Contents…):

 

Accordion_Nav_Data_Cleanup_5.png

The Menu data should now be correct:

 

Accordion_Nav_Data_Cleanup_6.png

 

Step 6: Set the sortOrder

Now that the data is in the proper fields, we need to set the sort order.  This will determine how the records in the Card table will display on our menu.  You could create a script to loop through the list and set the sort order or you can set the field manually.  I did the latter.  In our example, that means modifying 71 records.

 

The convention for the sort order is such that level one records are whole numbers, starting at 1 and incrementing by 1, so

 

Company 1

Item 2

Purchasing 3

and so on.

 

The child records have their parent number followed by a decimal and then another number, starting at 1 and incrementing by 1.  The exception to this is that the last level 2 record in each list ends in .99.  This is for a UI (user interface) trick that I’ll explain later.  So now we have the data all set:

 

Accordion_Nav_Sort_Order.png

 

But what happens if we want to add or change the list?  For example, when I created my original list above, I didn’t add Transfers.  I’d like to add that to my Inventory navigation and I’d like it to go above Admin.  That means that the Transfer records for level 1 and level 2 will have a sort order of 9 and all the Admin records will need to get bumped up to level 10.  To do that, I’ll find all the Admin records by searching for 9*.  Once I have that found set, I can use Replace Field Contents (Records/Replace Field Contents…) and replace with a calculation.

 

Accordion_Nav_Bumping_Order.png

 

There are a number of ways to do this.  I used the Substitute () function.  It doesn’t change the level 1 field, but it gets all the level 2 fields.  I can then manually change the level 1 field from 9 to 10.

 

Once I’ve done that, I can add the Transfer records, setting the level and sortOrder fields manually:

 

Accordion_Nav_Adding_Order.png

 

Step 7: Layout Design

Once the data is set, we can turn our attention to the layout design for the accordion navigation.  Go to the Menu User Interface layout that we created in Step 4 above.  Set this layout to be a list view.  We’ll need a header.  A footer is optional; I’ve kept the footer.

 

At the bare minimum, we only need 3 objects, all of them single button button bars.

 

The first button we need is a way to close the Card window.  That will go in the header.  For this icon I wanted a hamburger menu (3 stacked, horizontal lines) with an arrow.  FileMaker doesn’t offer this in their suite of icons, so I used Icon Manager V16 by inDats.  This is a fantastic tool, in my opinion and its my first “go-to” source when looking for icons to supplement FileMaker’s native icon library.

 

The button to close the window is a simple single step button that closes the current window.  If you need additional activities to happen upon closing the navigation window, then you’ll want to run that from a script instead of a single step.

 

Technically, this first button can be a button object instead of a button bar, but for simplicity’s sake, I made them all the same object type, namely single button button bars.

 

The next two button bars are also single buttons.  They are text only at this point.  We’ll add icons further below.  But you don’t have to add the icons.  If text alone works for your solution, then it simplifies the process.  Text for both of the buttons comes from the label name.  Double clicking the button bar brings up the button bar set up dialog where you can select the field:

 

Accordion_Nav_Label.png

We need two things to differentiate these two button bars:

  1. Color
  2. Hide criteria

 

The first, color, adds visual appeal as we open and close the accordion.  It will indicate that added options are now available to the user.  When you use color to differentiate level 2 from level 1, make sure you know your users.  According to the website www.colorblindawareness.org, approximately 1 in 12 men and 1 in 200 women are affected.  Check with your users before selecting colors for differentiation.

 

For the purposes of this demo, the level 1 button is the Default style and the level 2 button is the Body Button Bar.

 

The next thing we need to do is make sure the correct button is showing.  Remember, when we display the Card window for our accordion navigation, we’ll be showing a list view with two buttons in the body.  But we only want to see one of those buttons per record.  To do this, select the level 1 button bar (the one with the Default style) and in the inspector set this object to hide under this condition:

Menu::level <> 1

 

For the level 2 button bar (the one with the Body Button Bar style), set the condition to this:

Menu::level <> 2

 

The last thing to do is to stack the buttons.  Stacking objects used to be a pain in FileMaker Pro.  But in FMP 16 we now have the Layout Object Window, so making modifications is relatively easy.  Here is the layout, with the stacked button bars (level 1 button bar is underneath level 2 and not visible):

 

Accordion_Nav_Stacked_ButtonBars.png

 

Step 8: Displaying the Accordion Navigation

Now we need to display our accordion navigation button on the different layouts.  I’ll be using the Products Details layout for this demo.  I want the accordion menu on the left hand side, so I need to put a button in the upper left corner.  There is already a button there (< Inventory List), so I’ll delete that object and change to a new, single button button bar.  Again, I wanted a hamburger icon with an arrow, so I’m using an icon from the InDats Icon Library:

 

Accordion_Nav_Calling_ButtonBar.png

And here is the script for the new button:

New Window [ Style: Card ; Name: “Menu” ; Using layout: “Menu User Interface” (Menu) ; Height: 725 ; Width: 250 ; Top: 0 ; Left: 0]

Enter Find Mode [ Pause Off ]

Set Field [ Menu: :level ; 1 ]

Perform Find [ ]

Sort Records [ Restore ; With dialog: Off ]

 

Exit Script [ Text Result: ]

 

This script opens the Accordion Navigation menu in a closed state.  That is, it only shows level 1 records.

 

Here’s the New Window Dialog window:

Accordion_Nav_Script_Vertical_Menu.png

Positioning the window at 0, 0 puts the new window in the upper left corner.  You may need to play around with the Height and Width of the card window to get the right size.

 

The Sort Records at the end of the script sorts by the field Menu::sortOrder which we set when initializing the data in the Menu table.  Once the Accordion Menu is open, the hamburger icon at the top simply closes the current window, as previously mentioned.  That creates the toggle effect of the hamburger menu opening and closing the accordion.

 

Accordion_Nav_Show_Closed_Nav.png

 

Step 9: Toggle Level 2

Now that the main menu is visible, we want to select one of the options in order to expand the menu.  A script performs the toggle:

 

Set Variable [ $sortOrderBase; Value:Menu::sortOrder ]

 

#only expand for first level

If [ Menu::level <> 1 ]

  Exit Script [ ]

End If

 

#menu is either closed, opened with the current selection, or open with a different selection

 

If [ PatternCount ( Menu::sortOrderList ; "." ) = 0 ]

  #menu is collapsed; open user selected sub menu

  Perform Script [ “expand menu”; Parameter: $sortOrderBase ]

 

Else If [ PatternCount ( Menu::sortOrderList ; $sortOrderBase & "." ) > 1 ]

  #this menu item is already expanded; toggle it to close

  Perform Script [ “vertical menu” ]

 

Else

  Perform Script [ "vertical menu" ]

  Perform Script [ “expand menu”; Parameter: $sortOrderBase ] End If

 

Exit Script [ ]

 

There are only three possibilities for the menu:

  1. It is closed and therefore needs to be opened.
  2. It is opened and therefore needs to be closed.
  3. It is opened but on a different selection.  Therefore, close that selection first before opening the new one.

 

To expand the level 2 menu, we call the “expand menu” subscript:

Set Variable [ $sortOrderBase ; Value : Get ( ScriptParameter ) ]

 

Enter Find Mode [ Pause: Off ]

Set Field [ Menu::sortOrder ; $sortOrderBase & “*” ]

Extend Found Set []

Sort Records [ Restore ; With dialog Off ]

 

Exit Script [ Text Results: ]

 

Again, the Sort Records step sorts on the field Menu::sortOrder.

 

Once the level 2 options are available, users would be able to click those buttons to perform the desired event.  (In this demo, I simply have the script open a custom dialog).

 

That’s the basics of the Accordion Navigation Menu.  However, we can do a couple more things to increase its visual appeal.

 

Step 10: Give It Depth

As it is, the navigation menu is flat.  Adding depth to the level 2 menu provides the user with a visual cue that she is within a section.

 

Accordion_Nav_Level_2_Flat.png

To add depth, we’ll return to the Menu User Interface layout and add two more objects.  The objects are both shape objects, in the form of a rectangle.  The two objects are identical in height and width.  They differ slightly in color.  In fact, they are both gradients.  The only difference is that direction of the gradient.

 

Accordion_Nav_Gradients.png

The lines I’m using are 6 pts. tall.  You may want to play with the height to see how the gradients appear on your screens.

 

I’ll place the gradient rectangles at the top and bottom of the Body part.  However, I don’t want them to show for all records.  They should never appear on a level 1 menu record.  For level 2, they should only appear before the first and after the last record.  Before the first is easy since we know the first level 2 record has a sort value of n.1 (1.1, 2.1, 3.1, etc.).  However, the quantity of level 2 sub menus varies.  For example, Company has 8 sub menu records (i.e. level 2 records) whereas Item only has 5.  So how do we find the last sub menu record when there is variation?

 

You may recall in our numbering system we ended each group with n.99 (1.99, 2.99, 3.99, etc.).  We’ll never have 99 sub menus (at least, we SHOULD never have 99 sub menus!).  And it will also sort to the bottom of the sub menu list.  Using that static number for the last record in each set allows us to know where the bottom is.  Now that we know the top and bottom we can hide the gradients accordingly.

 

The top gradient is hidden when:

PatternCount ( Menu::sortOrder ; ".1" ) = 0

 

And the bottom gradient is hidden when:

PatternCount ( Menu::sortOrder ; ".99" ) = 0

 

Accordion_Nav_Gratients_2.png

Two gradient rectangle objects, one at the top of the Body part and the other at the bottom.  Extended beyond the Body part to help demonstration their location.

 

Now, with the gradients, in place, the Accordion Navigation Menu has a bit of depth when level 2 is visible.  Take a look at these side-by-side comparisons, one with depth and the other flat:

 

Accordion_Nav_Depth_Comparison.png

 

Step 11: Adding Icons

Lastly, we can spice up the menu by making it a bit more visually appealing.  To do that, we’ll add icons.  Icons present a bit of a problem, however.  Unlike the button label, which can vary based on a calculation, the button icon is static for a particular button.  There is no way to say:

 

If [ Menu::labelName = “Company” ]

  Company icon

Else If [ Menu::labelName = “Item” ]

  Item icon

etc.

 

In order to show the icons, we’ll need to change our two button bars from single button button bars to multiple button button bars.  If we go back over to the Menu Set layout, we can perform a search for level 1 records and we’ll see that there are 10 records.  Level 2 records has 68 records in that found set.  However, that doesn’t mean that we need 68 buttons in the level 2 button bar because many of the level 2 records will have the same icon.  For example, there are 9 level 2 records with “Find” in the labelName (Find Company, Find Item, Find Pick, etc.).  These will all have the same icon.  Likewise for “New”, “Last”, and “Show”.  What we end up with is a button bar with 11 different icons for level 2 (Last, Find, New, Show, Dashboard, Settings, Warehouses, Locations, Integrations, Unit of Measure, and Unit of Measure Conversion).

 

Adding the additional buttons to the button bar will not expand the width of the button bar.  That’s good because we need to to remain the same width as the single button button bar.  That makes for a bit of a tight design area, but not awful.

 

Once we have our buttons we can add the icons.  Each button receives its own, unique icon.  Then we’ll need to hide the button accordingly.  For level 1, it is pretty straight forward.  We hide the button when the labelName does not equal a certain label.  For example, the Company icon will not show when

 

Menu::labelName <> “Company

 

Level 2 buttons are slightly different since one icon will be used for several records.  The hide calculation for level 2 is

 

PatternCount ( Menu::labelName ; "Last" ) = 0

 

In other words, when “Last” IS in the labelName field, then show the icon.  And remember, the actual button label is a calculation based on the labelName field, so the text is dynamic.

 

Here’s what the new button bars look like in Layout Mode:

 

Accordion_Nav_Multiple_Button_Button_Bars.png

Notice that the level 2 icons are not showing.  In order to create a visual of a tree structure, I set the level 2 buttons with a higher padding than the level 1.

 

Accordion_Nav_Padding.png

 

And that’s one way to create an Accordion Navigation Menu with icons:

 

Accordion_Nav_With_Icons.png

 

The demo file is available at FileMaker Inventory Resources.

11 people found this helpful

Attachments

    Outcomes