forked from kohsuke/com4j
-
Notifications
You must be signed in to change notification settings - Fork 2
Expand file tree
/
Copy pathComCollection.java
More file actions
86 lines (73 loc) · 2.23 KB
/
Copy pathComCollection.java
File metadata and controls
86 lines (73 loc) · 2.23 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
package com4j;
import com4j.stdole.IEnumVARIANT;
import java.util.Iterator;
import java.util.NoSuchElementException;
/**
* Wraps IEnumVARIANT and implements {@link Iterator}.
*
* @author Kohsuke Kawaguchi
* @author Michael Schnell (ScM, (C) 2008, 2009, Michael-Schnell@gmx.de)
*/
final class ComCollection<T> implements Iterator<T> {
/**
* The wrapped IEnumVARIANT
*/
private final IEnumVARIANT e;
/**
* The prefetched next VARIANT element
*/
private Variant next;
/**
* The expected item type.
*/
private final Class<T> type;
/**
* Constructs a new ComCollection
* @param type The class object of the type
* @param e The newly wrapped IEnumVARIANT
*/
ComCollection(Class<T> type, IEnumVARIANT e) {
this.e = e;
this.type = type;
this.next = new Variant();
fetch();
}
public boolean hasNext() {
return next!=null;
}
@SuppressWarnings("unchecked")
public T next() {
if(next==null)
throw new NoSuchElementException();
try {
// ideally we'd like to use ChangeVariantType to do the conversion
// but for now let's just support interface types
if(Com4jObject.class.isAssignableFrom(type)) {
return (T)next.object((Class<? extends Com4jObject>)type);
} else
throw new UnsupportedOperationException("I don't know how to handle "+type);
} finally {
fetch();
}
}
/**
* Removing an element from the iterator is not supported
*/
public void remove() throws UnsupportedOperationException {
throw new UnsupportedOperationException("Removing an element from a ComCollection iterator is not supported.");
}
/**
* Fetches the next element.
*/
private void fetch() {
next.clear();
// We need to remember for what thread the IEnumVARIANT was marshaled. Because if we want to interpret this
// VARIANT as an interface pointer later on, we need to do this in the same thread!
next.thread = e.getComThread();
int r = e.next(1,next);
if(r==0) {
next = null;
e.dispose();
}
}
}