Custom UIShell: Close Tabs to the Right

Add a similar functionality to Firefox or other common browsers “Close Tabs to the Right” through right click in your uishell pattern or alternative uishell. I use this last

<af:commandMenuItem id="cm43" text="Close Tabs to the Right"
     actionListener="#{viewScope.dynTabManager.closeAllRight}">
  <af:setPropertyListener from="#{source.attributes.menuInvokedOnTab}"
       to="#{viewScope.dynTabManager.menuInvokedOnTab}"
       type="action"/>
</af:commandMenuItem>
    
public void closeAllRight(ActionEvent action) {
   List<String> tabsToRemove = new ArrayList();
   for(int poss=getActiveTabList().indexOf(getTab( getMenuInvokedOnTab()))+1 ; poss <getActiveTabList().size() ; poss++) {
      tabsToRemove.add(getActiveTabList().get(poss).getId());                                               
   }
   for (String t : tabsToRemove) {
      removeTab(t);
   }
}

FootNotes: This post is based on adf-11g-adding-close-this-close-others.html

Anuncios

Custom UIShell: making closeable the initial tabs.

With this pattern, among many other features, we have an option that allows us to open initial tabs. (when the application is started).–>closeable true in adfc-config

The problem is that if we make closeable this initial tab, when we close the initial tab and we try to open the initial tab again. We get a NullPointerException in addTab method of DynTabManager class

The problem is that the TaskflowId property in getInstance method  of  DynTab class is null.

I added these lines and now the initial Tab can be closeable.

public static DynTab getInstance(String tabName) {
 String beanName = tabName + "DynTab";
 String expr = "#{" + beanName + "}";
 DynTab tab = (DynTab)JsfUtils.getExpressionValue(expr);
 if (tab == null) {
  // try viewScope, must be used when tab is initially displayed
  expr = "#{viewScope." + beanName + "}";
  tab = (DynTab)JsfUtils.getExpressionValue(expr);
 }
 if (tab == null) {
  sLog.severe("Could not find DynTab bean " + beanName + "!");
 }
 tab.setName(tabName);

 //workaround to re-open the initial Tabs
 if ((tab.getTitle() == null) || (tab.getTitle().length() == 0)) {
  tab.setTitle(tabName);
 }
 tab.setTaskflowId(TaskFlowId.parse(tab.getTaskFlowIdString()));

 return tab;
}

and add a if in addTab method of DynTabManager class

public void addTab(DynTab tabToAdd) {
      if (tabTracker.getNumActive() >= tabTracker.getMaxNumberOfTabs()) {
            handleTooManyTabsOpen();
      } else {
          // The list of tabs doesn't get fragmented, so the first inactive tab always
          // shows as the right most tab.
          DynTab tab = getFirstInactiveTabOrThrow();
          tab.setTitle(tabToAdd.getTitle());
          tab.setActive(true);
          tab.setTaskflowId(tabToAdd.getTaskflowId());
          tab.setUniqueIdentifier(tabToAdd.getUniqueIdentifier());
          tab.setParameters(tabToAdd.getParameters());
          // add the DynTabManager instance as taskflow parameter so the
          // taskflow itself can open new tabs, and close tabs.
          if (tab.getParameters() != null) {
               tab.getParameters().put("dynTabManager", this);
               // add tab id so the taskflow iktself can change its label
               tab.getParameters().put("dynTabId", tab.getId());
           }
           tabTracker.setNumActive(tabTracker.getNumActive() + 1);
           setSelectedTabId(tab.getId());
        }
    }

Note:This post does not talk about Oracle UI Shell, we are talking about the UI Shell that can be downloaded from here.

Custom UIShell: getBinding returns null for any Tab running a taskflow

A few days ago, asked in forum that when we call a getActiveTabList for obtain a list of tabs opens at this moment, getBinding method always return null.

DynTabManager dynTabManager =(DynTabManager)JsfUtils.getManagedBeanValue("pageFlowScope.dynTabManager");
List listtabs =dynTabManager.getCurrentInstance().getActiveTabList();
for (DynTab t : listtabs) {
  System.out.println(t.getId());
  //return null
  t.getBinding()
}

It seems that the problem is that when we call t.getBinding(), the getCurrentBindingsEntry returns a bindingContainer for the current tab, instead of the BC of template

e.g: data.davelaar_demo_ui_view_UIShellPageDef.dynTabsTemplateBinding.r2.davelaar_demo_ui_view_pageDefs_
EditEmployeePageDef_WEB_INF_edit_employees_tf_xml_edit_employees

then when we do dynTabsBindings.get(getBindingKey()) in a getBinding method always return null

I added this lines in method getBingind of DynTab class

public DCTaskFlowBinding getBinding(){

 BindingContainer bc =BindingContext.getCurrent().getCurrentBindingsEntry();
 if (bc == null){
   return null;
 }
 BindingContainer dynTabsBindings =(BindingContainer) bc.get(PAGE_TEMPLATE_BINDING_KEY);
 if (dynTabsBindings == null){
   // use current bc directly
   dynTabsBindings = bc;
 }
 DCTaskFlowBinding binding = null;
 binding =(DCTaskFlowBinding) dynTabsBindings.get(getBindingKey()); // NOTRANS

 //new lines
 if (binding==null){
   BindingContext bindingCxt = BindingContext.getCurrent();
   // get uishell pagedef
   DCBindingContainer uishellBC=bindingCxt.findBindingContainer("davelaar_demo_ui_view_UIShellPageDef");
   //get template pagedef
   BindingContainer bc2= (BindingContainer)uishellBC.getExecutableBindings().get(0);
   return (DCTaskFlowBinding)bc2.get(getBindingKey());
 }
 return binding;
}

Note:This post does not talk about Oracle UI Shell, we are talking about the UI Shell that can be downloaded from here.