Coverage Report - org.apache.tapestry.pageload.EventConnectionVisitor
 
Classes in this File Line Coverage Branch Coverage Complexity
EventConnectionVisitor
0%
0/122
0%
0/82
5.273
 
 1  
 package org.apache.tapestry.pageload;
 2  
 
 3  
 import org.apache.hivemind.ApplicationRuntimeException;
 4  
 import org.apache.hivemind.PoolManageable;
 5  
 import org.apache.tapestry.IComponent;
 6  
 import org.apache.tapestry.IForm;
 7  
 import org.apache.tapestry.IPage;
 8  
 import org.apache.tapestry.IRender;
 9  
 import org.apache.tapestry.form.IFormComponent;
 10  
 import org.apache.tapestry.internal.Component;
 11  
 import org.apache.tapestry.internal.event.ComponentEventProperty;
 12  
 import org.apache.tapestry.internal.event.EventBoundListener;
 13  
 import org.apache.tapestry.internal.event.IComponentEventInvoker;
 14  
 import org.apache.tapestry.spec.IComponentSpecification;
 15  
 
 16  
 import java.util.*;
 17  
 
 18  
 /**
 19  
  * Handles connecting up components and forms targeted with the EventListener annotation.
 20  
  */
 21  0
 public class EventConnectionVisitor implements IComponentVisitor, PoolManageable {
 22  
 
 23  
     IComponentEventInvoker _invoker;
 24  
 
 25  0
     IPage _currentPage = null;
 26  0
     List _forms = new ArrayList();
 27  
 
 28  
     public void visitComponent(IComponent component)
 29  
     {
 30  0
         checkComponentPage(component);
 31  
 
 32  0
         Map events = component.getSpecification().getComponentEvents();
 33  0
         Set keySet = events.keySet();
 34  0
         String[] compIds = (String[]) keySet.toArray(new String[keySet.size()]);
 35  
 
 36  0
         for (int i=0; i < compIds.length; i++)
 37  
         {
 38  0
             String compId = compIds[i];
 39  
 
 40  
             // find the targeted component, first search component children
 41  
             // and then page children if not contained by component
 42  
 
 43  0
             IComponent comp = findComponent(compId, component);
 44  
 
 45  0
             if (comp == null && !IPage.class.isInstance(component))
 46  
             {
 47  0
                 comp = findComponent(compId, component.getPage());
 48  
             }
 49  
 
 50  0
             if (comp == null)
 51  0
                 continue;
 52  
 
 53  0
             if (Component.class.isInstance(comp))
 54  0
                 ((Component)comp).setHasEvents(true);
 55  
 
 56  
             // wire up with idPath
 57  
 
 58  0
             String idPath = comp.getExtendedId();
 59  
 
 60  0
             component.getSpecification().rewireComponentId(compId, idPath, component.getIdPath());
 61  
 
 62  0
             _invoker.addEventListener(idPath, component.getSpecification());
 63  0
             wireFormEvents(comp, component.getSpecification());
 64  
         }
 65  
 
 66  
         // find form element targets for re-mapping with proper idpath && IEventInvoker connection
 67  
 
 68  0
         events = component.getSpecification().getElementEvents();
 69  0
         Iterator it = events.keySet().iterator();
 70  
 
 71  
         // for efficiency later in ComponentEventConnectionWorker
 72  
 
 73  0
         if (events.size() > 0 && Component.class.isInstance(component))
 74  
         {
 75  0
             ((Component)component).setHasEvents(true);
 76  
         }
 77  
 
 78  0
         while (it.hasNext())
 79  
         {
 80  0
             String elementId = (String) it.next();
 81  0
             ComponentEventProperty property = (ComponentEventProperty) events.get(elementId);
 82  
 
 83  0
             Iterator bindingIt  = property.getFormEvents().iterator();
 84  0
             while (bindingIt.hasNext())
 85  
             {
 86  0
                 String key = (String) bindingIt.next();
 87  0
                 List listeners = property.getFormEventListeners(key);
 88  
 
 89  0
                 for (int i=0; i < listeners.size(); i++)
 90  
                 {
 91  0
                     EventBoundListener listener = (EventBoundListener) listeners.get(i);
 92  0
                     wireElementFormEvents(listener, component, component.getSpecification());
 93  
                 }
 94  0
             }
 95  0
         }
 96  0
     }
 97  
 
 98  
     void wireElementFormEvents(EventBoundListener listener, IComponent component, IComponentSpecification spec)
 99  
     {
 100  0
         if (listener.getFormId() == null)
 101  0
             return;
 102  
 
 103  0
         if (_forms.size() < 1)
 104  0
             discoverPageForms(component.getPage());
 105  
 
 106  0
         IForm form = null;
 107  0
         for (int i=0; i < _forms.size(); i++)
 108  
         {
 109  0
             IForm f = (IForm) _forms.get(i);
 110  0
             if (listener.getFormId().equals(f.getExtendedId()) || listener.getFormId().equals(f.getId()))
 111  
             {
 112  0
                 form = f;
 113  0
                 break;
 114  
             }
 115  
         }
 116  
 
 117  
         // couldn't find the form they specified
 118  
 
 119  0
         if (form == null)
 120  0
             throw new ApplicationRuntimeException(PageloadMessages.componentNotFound(listener.getFormId()),
 121  
                                                   component, component.getLocation(), null);
 122  
 
 123  0
         String idPath = form.getExtendedId();
 124  
 
 125  0
         listener.setFormId(idPath);
 126  0
         _invoker.addFormEventListener(idPath, spec);
 127  0
     }
 128  
 
 129  
     void wireFormEvents(IComponent component, IComponentSpecification listener)
 130  
     {
 131  0
         if (!IFormComponent.class.isInstance(component))
 132  0
             return;
 133  
 
 134  0
         IFormComponent fcomp = (IFormComponent) component;
 135  
 
 136  0
         if (_forms.size() < 1)
 137  0
             discoverPageForms(fcomp.getPage());
 138  
 
 139  0
         IForm form = findComponentForm(fcomp);
 140  0
         if (form == null)
 141  0
             return;
 142  
 
 143  0
         listener.connectAutoSubmitEvents(component, form);
 144  0
         _invoker.addFormEventListener(form.getExtendedId(), listener);
 145  0
     }
 146  
 
 147  
     IComponent findComponent(String id, IComponent target)
 148  
     {
 149  0
         Map components = target.getComponents();
 150  0
         if (components == null)
 151  0
             return null;
 152  
 
 153  0
         IComponent comp = (IComponent) components.get(id);
 154  0
         if (comp != null)
 155  0
             return comp;
 156  
 
 157  0
         Iterator children = components.values().iterator();
 158  
 
 159  0
         while (children.hasNext())
 160  
         {
 161  0
             IComponent child = (IComponent) children.next();
 162  
 
 163  0
             comp = findComponent(id, child);
 164  0
             if (comp != null)
 165  0
                 return comp;
 166  0
         }
 167  
 
 168  0
         return null;
 169  
     }
 170  
 
 171  
     void discoverPageForms(IComponent parent)
 172  
     {
 173  0
         if (IForm.class.isInstance(parent))
 174  0
             _forms.add(parent);
 175  
 
 176  0
         Iterator it = parent.getComponents().values().iterator();
 177  0
         while (it.hasNext())
 178  
         {
 179  0
             IComponent comp = (IComponent)it.next();
 180  
 
 181  0
             discoverPageForms(comp);
 182  0
         }
 183  0
     }
 184  
 
 185  
     IForm findComponentForm(IFormComponent child)
 186  
     {
 187  0
         for (int i = 0; i < _forms.size(); i++)
 188  
         {
 189  0
             IForm form = (IForm) _forms.get(i);
 190  
 
 191  0
             IComponent match = findContainedComponent(child.getExtendedId(), (Component)form);
 192  0
             if (match != null)
 193  0
                 return form;
 194  
         }
 195  
 
 196  0
         return null;
 197  
     }
 198  
 
 199  
     IComponent findContainedComponent(String idPath, Component container)
 200  
     {
 201  0
         IComponent comp = (IComponent) container;
 202  
 
 203  0
         if (idPath.equals(comp.getExtendedId()))
 204  0
             return comp;
 205  
 
 206  0
         IRender[] children = container.getContainedRenderers();
 207  0
         if (children == null)
 208  0
             return null;
 209  
 
 210  0
         for (int i=0; i < children.length; i++)
 211  
         {
 212  0
             if (children[i] == null)
 213  0
                 return null;
 214  
 
 215  0
             if (!Component.class.isInstance(children[i]))
 216  0
                 continue;
 217  
 
 218  0
             IComponent found = findContainedComponent(idPath, (Component)children[i]);
 219  0
             if (found != null)
 220  0
                 return found;
 221  
         }
 222  
 
 223  0
         return null;
 224  
     }
 225  
 
 226  
     void checkComponentPage(IComponent component)
 227  
     {
 228  0
         if (_currentPage == null)
 229  
         {
 230  0
             _currentPage = component.getPage();
 231  0
             _forms.clear();
 232  0
         } else if (component.getPage() != _currentPage)
 233  
         {
 234  0
             _currentPage = component.getPage();
 235  0
             _forms.clear();
 236  
         }
 237  0
     }
 238  
 
 239  
     public void activateService()
 240  
     {
 241  0
         _currentPage = null;
 242  0
         _forms.clear();
 243  0
     }
 244  
 
 245  
     public void passivateService()
 246  
     {
 247  0
         _currentPage = null;
 248  0
         _forms.clear();
 249  0
     }
 250  
 
 251  
     // injected
 252  
     public void setEventInvoker(IComponentEventInvoker invoker)
 253  
     {
 254  0
         _invoker = invoker;
 255  0
     }
 256  
 }