private void drawFooter() {
    // populate the extraWidgets toolstrip
    footerExtraWidgets.removeMembers(footerExtraWidgets.getMembers());
    if (!extraWidgetsAboveFooter.isEmpty()) {
      for (Canvas extraWidgetCanvas : extraWidgetsAboveFooter) {
        footerExtraWidgets.addMember(extraWidgetCanvas);
      }
      footerExtraWidgets.show();
    }

    footer.removeMembers(footer.getMembers());

    for (final CarouselActionInfo carouselAction : carouselActions) {

      if (null == carouselAction.getValueMap()) {
        // button action
        IButton button =
            new LocatableIButton(carouselAction.getLocatorId(), carouselAction.getTitle());
        button.setDisabled(true);
        button.setOverflow(Overflow.VISIBLE);
        button.addClickHandler(
            new ClickHandler() {
              public void onClick(ClickEvent clickEvent) {
                disableAllFooterControls();
                if (carouselAction.confirmMessage != null) {
                  String message = carouselAction.confirmMessage.replaceAll("\\#", "TODO:");

                  SC.ask(
                      message,
                      new BooleanCallback() {
                        public void execute(Boolean confirmed) {
                          if (confirmed) {
                            carouselAction.action.executeAction(null);
                          } else {
                            refreshCarouselInfo();
                          }
                        }
                      });
                } else {
                  carouselAction.action.executeAction(null);
                }
              }
            });

        carouselAction.actionCanvas = button;
        footer.addMember(button);

      } else {
        // menu action
        LocatableMenu menu = new LocatableMenu(carouselAction.getLocatorId() + "Menu");
        final Map<String, ? extends Object> menuEntries = carouselAction.getValueMap();
        for (final String key : menuEntries.keySet()) {
          MenuItem item = new MenuItem(key);
          item.addClickHandler(
              new com.smartgwt.client.widgets.menu.events.ClickHandler() {
                public void onClick(MenuItemClickEvent event) {
                  disableAllFooterControls();
                  carouselAction.getAction().executeAction(menuEntries.get(key));
                }
              });
          menu.addItem(item);
        }

        IMenuButton menuButton =
            new LocatableIMenuButton(carouselAction.getLocatorId(), carouselAction.getTitle());
        menuButton.setMenu(menu);
        menuButton.setDisabled(true);
        menuButton.setAutoFit(
            true); // this makes it pretty tight, but maybe better than the default, which is pretty
        // wide
        menuButton.setOverflow(Overflow.VISIBLE);
        menuButton.setShowMenuBelow(false);

        carouselAction.actionCanvas = menuButton;
        footer.addMember(menuButton);
      }
    }

    for (Canvas extraWidgetCanvas : extraWidgetsInMainFooter) {
      footer.addMember(extraWidgetCanvas);
    }

    footer.addMember(new LayoutSpacer());

    widthButton = new LocatableIButton(extendLocatorId("Width"), MSG.common_button_fixedWidth());
    widthButton.addClickHandler(
        new ClickHandler() {
          public void onClick(ClickEvent clickEvent) {
            carouselUsingFixedWidths = !carouselUsingFixedWidths;
            widthButton.setTitle(
                carouselUsingFixedWidths
                    ? MSG.common_button_scaleToFit()
                    : MSG.common_button_fixedWidth());
            buildCarousel(true);
          }
        });
    footer.addMember(widthButton);

    if (isShowFooterRefresh()) {
      this.refreshButton =
          new LocatableIButton(extendLocatorId("Refresh"), MSG.common_button_refresh());
      refreshButton.addClickHandler(
          new ClickHandler() {
            public void onClick(ClickEvent clickEvent) {
              disableAllFooterControls();
              refresh();
            }
          });
      footer.addMember(refreshButton);
    }

    previousButton =
        new LocatableIButton(extendLocatorId("Previous"), MSG.common_button_previous());
    previousButton.addClickHandler(
        new ClickHandler() {
          public void onClick(ClickEvent clickEvent) {
            disableAllFooterControls();
            previous();
          }
        });
    footer.addMember(previousButton);

    nextButton = new LocatableIButton(extendLocatorId("Next"), MSG.common_button_next());
    nextButton.addClickHandler(
        new ClickHandler() {
          public void onClick(ClickEvent clickEvent) {
            disableAllFooterControls();
            next();
          }
        });
    footer.addMember(nextButton);

    footer.addMember(carouselInfo);

    // Ensure buttons are initially set correctly.
    refreshCarouselInfo();
  }