1765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye/*******************************************************************************
2765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * Copyright (c) 2011 Google, Inc.
3765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * All rights reserved. This program and the accompanying materials
4765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * are made available under the terms of the Eclipse Public License v1.0
5765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * which accompanies this distribution, and is available at
6765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * http://www.eclipse.org/legal/epl-v10.html
7765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye *
8765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * Contributors:
9765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye *    Google, Inc. - initial API and implementation
10765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye *******************************************************************************/
11765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyepackage org.eclipse.wb.internal.core.editor.structure.property;
12765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
13765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyeimport com.google.common.collect.Lists;
14765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
15765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyeimport org.eclipse.wb.internal.core.model.property.Property;
16765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyeimport org.eclipse.wb.internal.core.model.property.PropertyManager;
17765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
18765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyeimport java.util.Iterator;
19765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyeimport java.util.List;
20765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
21765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye/**
22765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * Helper for computing intersection of {@link Property} arrays.
23765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye *
24765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * @author scheglov_ke
25765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye * @coverage core.editor.structure
26765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye */
27765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbyepublic final class PropertyListIntersector {
28765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  private List<PropertyGroup> m_intersection;
29765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
30765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  ////////////////////////////////////////////////////////////////////////////
31765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  //
32765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  // Access
33765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  //
34765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  ////////////////////////////////////////////////////////////////////////////
35765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  /**
36765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   * Updates intersection by intersecting with new given array.
37765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   */
38765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  public void intersect(Property[] properties) {
39765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    if (m_intersection == null) {
40765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      m_intersection = Lists.newArrayList();
41765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      for (int i = 0; i < properties.length; i++) {
42765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        Property property = properties[i];
43765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        m_intersection.add(new PropertyGroup(property));
44765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      }
45765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    } else {
46765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      for (Iterator<PropertyGroup> I = m_intersection.iterator(); I.hasNext();) {
47765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        PropertyGroup propertyGroup = I.next();
48765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        if (!propertyGroup.add(properties)) {
49765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye          I.remove();
50765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        }
51765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      }
52765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
53765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  }
54765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
55765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  /**
56765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   * @return the array of matched composite {@link Property}'s.
57765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   */
58765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  public Property[] getProperties() {
59765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    List<Property> properties = Lists.newArrayList();
60765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    for (PropertyGroup propertyGroup : m_intersection) {
61765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      Property compositeProperty = propertyGroup.getCompositeProperty();
62765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      if (compositeProperty != null) {
63765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        properties.add(compositeProperty);
64765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      }
65765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
66765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
67765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    return properties.toArray(new Property[properties.size()]);
68765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  }
69765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
70765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  ////////////////////////////////////////////////////////////////////////////
71765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  //
72765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  // PropertyGroup
73765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  //
74765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  ////////////////////////////////////////////////////////////////////////////
75765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  /**
76765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   * The group of {@link Property}'s that match.
77765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye   */
78765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  private static final class PropertyGroup {
79765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    private final List<Property> m_properties = Lists.newArrayList();
80765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
81765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
82765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
83765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    // Constructor
84765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
85765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
86765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    public PropertyGroup(Property property) {
87765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      m_properties.add(property);
88765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
89765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
90765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
91765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
92765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    // Access
93765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
94765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
95765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    /**
96765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     * @return <code>true</code> if new matched {@link Property} from given array was added.
97765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     */
98765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    public boolean add(Property[] properties) {
99765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      for (Property property : properties) {
100765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        if (add(property)) {
101765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye          return true;
102765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        }
103765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      }
104765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      // no match
105765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      return false;
106765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
107765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
108765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    /**
109765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     * @return the composite {@link Property} for this group.
110765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     */
111765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    public Property getCompositeProperty() {
112765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      Property properties[] = m_properties.toArray(new Property[m_properties.size()]);
113765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      return properties[0].getComposite(properties);
114765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
115765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye
116765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
117765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
118765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    // Internal
119765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    //
120765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    ////////////////////////////////////////////////////////////////////////////
121765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    /**
122765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     * @return <code>true</code> if given {@link Property} matches and was added.
123765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye     */
124765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    private boolean add(Property property) {
125765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      Property example = m_properties.get(0);
126765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      if (example.getClass() == property.getClass()
127765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye          && example.getTitle().equals(property.getTitle())
128765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye          && PropertyManager.getCategory(example) == PropertyManager.getCategory(property)) {
129765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        m_properties.add(property);
130765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye        return true;
131765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      }
132765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      // no match
133765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye      return false;
134765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye    }
135765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye  }
136765e52e2d30d0754625b8c7af6c36e93612f15beTor Norbye}
137