diff --git a/src/gr/spinellis/umlgraph/doclet/ContextMatcher.java b/src/gr/spinellis/umlgraph/doclet/ContextMatcher.java
index d6b014e..81f9360 100644
--- a/src/gr/spinellis/umlgraph/doclet/ContextMatcher.java
+++ b/src/gr/spinellis/umlgraph/doclet/ContextMatcher.java
@@ -22,6 +22,9 @@ import java.io.IOException;
import java.io.PrintWriter;
import java.io.Writer;
import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
import java.util.regex.Pattern;
import com.sun.javadoc.ClassDoc;
@@ -32,13 +35,20 @@ import com.sun.javadoc.RootDoc;
* the regual expression specified. The context center is computed by regex lookup.
* Depending on the specified Options, inferred relations and dependencies will
* be used as well.
+ *
+ * This class needs to perform quite a bit of computations in order to gather
+ * the network of class releationships, so you are allowed to reuse it should
+ * you
* @author wolf
*/
public class ContextMatcher implements ClassMatcher {
ClassGraphHack cg;
Pattern pattern;
- ArrayList matched;
+ List matched;
+ Set visited = new HashSet();
Options opt;
+ RootDoc root;
+ boolean keepParentHide;
/**
* Builds the context matcher
@@ -46,18 +56,35 @@ public class ContextMatcher implements ClassMatcher {
* @param pattern The pattern that will match the "center" of this
* context
* @param opt The options will be used to decide on inference
+ * @param keepParentHide If true, parent option hide patterns will be
+ * preserved, so that classes hidden by the options won't
+ * be shown in the context
* @throws IOException
*/
- public ContextMatcher(RootDoc root, Pattern pattern, Options options) throws IOException {
+ public ContextMatcher(RootDoc root, Pattern pattern, Options options, boolean keepParentHide) throws IOException {
this.pattern = pattern;
+ this.root = root;
+ this.keepParentHide = keepParentHide;
opt = (Options) options.clone();
opt.setOption(new String[] {"-!hide"});
opt.setOption(new String[] {"-!attributes"});
opt.setOption(new String[] {"-!operations"});
this.cg = new ClassGraphHack(root, opt);
+ setContextCenter(pattern);
+ }
+
+ /**
+ * Can be used to setup a different pattern for this context matcher.
+ *
+ * This can be used to speed up subsequent matching with the same global
+ * options, since the class network informations will be reused.
+ * @param pattern
+ */
+ public void setContextCenter(Pattern pattern) {
// build up the classgraph printing the relations for all of the
// classes that make up the "center" of this context
+ this.pattern = pattern;
matched = new ArrayList();
for (ClassDoc cd : root.classes()) {
if (pattern.matcher(cd.toString()).matches()) {
@@ -74,7 +101,13 @@ public class ContextMatcher implements ClassMatcher {
* @param cd
*/
private void addToGraph(ClassDoc cd) {
- cg.printClass(cd);
+ // avoid adding twice the same class, but don't rely on cg.getClassInfo since there
+ // are other ways to add a classInfor than printing the class
+ if(visited.contains(cd.toString()))
+ return;
+
+ visited.add(cd.toString());
+ cg.printClass(cd, false);
cg.printRelations(cd);
if (opt.inferRelationships) {
cg.printInferredRelations(cd);
@@ -88,6 +121,9 @@ public class ContextMatcher implements ClassMatcher {
* @see gr.spinellis.umlgraph.doclet.ClassMatcher#matches(com.sun.javadoc.ClassDoc)
*/
public boolean matches(ClassDoc cd) {
+ if (keepParentHide && opt.matchesHideExpression(cd.toString()))
+ return false;
+
// if the class is matched, it's in by default.
if (matched.contains(cd))
return true;
diff --git a/src/org/umlgraph/doclet/ContextMatcher.java b/src/org/umlgraph/doclet/ContextMatcher.java
index d6b014e..81f9360 100644
--- a/src/org/umlgraph/doclet/ContextMatcher.java
+++ b/src/org/umlgraph/doclet/ContextMatcher.java
@@ -22,6 +22,9 @@ import java.io.IOException;
import java.io.PrintWriter;
import java.io.Writer;
import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
import java.util.regex.Pattern;
import com.sun.javadoc.ClassDoc;
@@ -32,13 +35,20 @@ import com.sun.javadoc.RootDoc;
* the regual expression specified. The context center is computed by regex lookup.
* Depending on the specified Options, inferred relations and dependencies will
* be used as well.
+ *
+ * This class needs to perform quite a bit of computations in order to gather
+ * the network of class releationships, so you are allowed to reuse it should
+ * you
* @author wolf
*/
public class ContextMatcher implements ClassMatcher {
ClassGraphHack cg;
Pattern pattern;
- ArrayList matched;
+ List matched;
+ Set visited = new HashSet();
Options opt;
+ RootDoc root;
+ boolean keepParentHide;
/**
* Builds the context matcher
@@ -46,18 +56,35 @@ public class ContextMatcher implements ClassMatcher {
* @param pattern The pattern that will match the "center" of this
* context
* @param opt The options will be used to decide on inference
+ * @param keepParentHide If true, parent option hide patterns will be
+ * preserved, so that classes hidden by the options won't
+ * be shown in the context
* @throws IOException
*/
- public ContextMatcher(RootDoc root, Pattern pattern, Options options) throws IOException {
+ public ContextMatcher(RootDoc root, Pattern pattern, Options options, boolean keepParentHide) throws IOException {
this.pattern = pattern;
+ this.root = root;
+ this.keepParentHide = keepParentHide;
opt = (Options) options.clone();
opt.setOption(new String[] {"-!hide"});
opt.setOption(new String[] {"-!attributes"});
opt.setOption(new String[] {"-!operations"});
this.cg = new ClassGraphHack(root, opt);
+ setContextCenter(pattern);
+ }
+
+ /**
+ * Can be used to setup a different pattern for this context matcher.
+ *
+ * This can be used to speed up subsequent matching with the same global
+ * options, since the class network informations will be reused.
+ * @param pattern
+ */
+ public void setContextCenter(Pattern pattern) {
// build up the classgraph printing the relations for all of the
// classes that make up the "center" of this context
+ this.pattern = pattern;
matched = new ArrayList();
for (ClassDoc cd : root.classes()) {
if (pattern.matcher(cd.toString()).matches()) {
@@ -74,7 +101,13 @@ public class ContextMatcher implements ClassMatcher {
* @param cd
*/
private void addToGraph(ClassDoc cd) {
- cg.printClass(cd);
+ // avoid adding twice the same class, but don't rely on cg.getClassInfo since there
+ // are other ways to add a classInfor than printing the class
+ if(visited.contains(cd.toString()))
+ return;
+
+ visited.add(cd.toString());
+ cg.printClass(cd, false);
cg.printRelations(cd);
if (opt.inferRelationships) {
cg.printInferredRelations(cd);
@@ -88,6 +121,9 @@ public class ContextMatcher implements ClassMatcher {
* @see gr.spinellis.umlgraph.doclet.ClassMatcher#matches(com.sun.javadoc.ClassDoc)
*/
public boolean matches(ClassDoc cd) {
+ if (keepParentHide && opt.matchesHideExpression(cd.toString()))
+ return false;
+
// if the class is matched, it's in by default.
if (matched.contains(cd))
return true;