annotate dstep/objc/bridge/Capsule.d @ 1:033d260cfc9b

First upload of the bridge
author Jacob Carlborg <doob@me.com>
date Thu, 18 Jun 2009 22:00:13 +0200
parents
children 9fd439a28ce3
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
1 /**
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
2 * Copyright: Copyright (c) 2009 Jacob Carlborg.
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
3 * Authors: Jacob Carlborg
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
4 * Version: Initial created: Feb 3, 2009
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
5 * License: $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost Software License 1.0)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
6 */
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
7 module dstep.objc.bridge.Capsule;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
8
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
9 version (Tango)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
10 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
11 import tango.core.Memory;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
12 import tango.math.Math : log2;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
13
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
14 alias GC.addRoot addRoot;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
15
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
16 import tango.core.Traits;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
17 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
18
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
19 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
20 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
21 import std.gc : addRoot;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
22 import std.math : log2;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
23 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
24
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
25 import dstep.internal.String;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
26 import dstep.objc.bridge.Bridge;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
27 import dstep.objc.bridge.TypeEncoding;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
28 import dstep.objc.bridge.Wrapper;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
29 import dstep.objc.message;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
30 import dstep.objc.objc;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
31 import dstep.objc.runtime;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
32 import bindings = dstep.objc.bindings;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
33
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
34 import mambo.io;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
35
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
36 template ObjcType (T)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
37 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
38 static if (needsEncapsulation!(T))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
39 alias id ObjcType;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
40
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
41 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
42 alias T ObjcType;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
43 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
44
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
45 Class capsuleClass ()
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
46 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
47 if (!Capsule.capsuleClass)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
48 initCapsuleClass;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
49
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
50 return Capsule.capsuleClass;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
51 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
52
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
53 private struct Capsule
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
54 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
55 static Class capsuleClass;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
56
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
57 static id create (Object object, Class capsuleClass)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
58 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
59 id capsule = objc.createInstance(capsuleClass, 0);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
60
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
61 Bridge.setDObject(object, capsule);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
62
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
63 return capsule;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
64 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
65
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
66 static id description (id self, SEL op)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
67 in
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
68 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
69 assert(isCapsule(self));
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
70 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
71 body
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
72 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
73 return encapsuleString(decapsule!(Object)(self).toString);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
74 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
75
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
76 static hash_t hash (id self, SEL op)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
77 in
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
78 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
79 assert(isCapsule(self));
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
80 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
81 body
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
82 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
83 return decapsule!(Object)(self).toHash;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
84 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
85
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
86 static byte isEqual (id self, SEL op, Object object)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
87 in
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
88 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
89 assert(isCapsule(self));
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
90 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
91 body
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
92 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
93 return decapsule!(Object)(self) == object;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
94 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
95 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
96
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
97 private void initCapsuleClass ()
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
98 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
99 Class superClass = cast(Class) objc.getClass!("NSObject");
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
100 Capsule.capsuleClass = objc.allocateClassPair!("D_Object")(superClass, 0);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
101
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
102 ubyte alignment = cast(ubyte) log2(Bridge.DObjectType.sizeof);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
103
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
104 Capsule.capsuleClass.addIvar!(Bridge.dObjectVar, encode!(Bridge.DObjectType))(Bridge.DObjectType.sizeof, alignment);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
105
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
106 Capsule.capsuleClass.addMethod!(encodeCallable!(Capsule.description))(sel.registerName!("description"), cast(IMP) &Capsule.description);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
107 Capsule.capsuleClass.addMethod!(encodeCallable!(Capsule.hash))(sel.registerName!("hash"), cast(IMP) &Capsule.hash);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
108 Capsule.capsuleClass.addMethod!(encodeCallable!(Capsule.isEqual))(sel.registerName!("isEqual"), cast (IMP) &Capsule.isEqual);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
109
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
110 objc.registerClassPair(capsuleClass);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
111 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
112
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
113 bool isCapsule (id capsule)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
114 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
115 if (!capsule)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
116 return false;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
117
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
118 Class cls = capsule.isa;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
119 return cls.getInstanceVariable!(Bridge.dObjectVar) !is null;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
120 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
121
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
122 template needsEncapsulation (T)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
123 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
124 static if (is(T == class))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
125 const needsEncapsulation = true;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
126
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
127 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
128 const needsEncapsulation = false;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
129 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
130
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
131 ObjcType!(T) encapsule (T) (T value)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
132 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
133 static if (needsEncapsulation!(T))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
134 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
135 if (!value)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
136 return null;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
137
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
138 if (auto wrapper = cast(ObjcWrapper) value)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
139 return wrapper.objcObject;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
140
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
141 return Capsule.create(value, capsuleClass);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
142 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
143
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
144 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
145 return value;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
146 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
147
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
148 template decapsule (T)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
149 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
150 T decapsule (ObjcType!(T) value)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
151 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
152 static if (needsEncapsulation!(T))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
153 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
154 if (isCapsule(value))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
155 return cast(T) Bridge.getDObject(value);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
156
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
157 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
158 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
159 static if (is(T : ObjcWrapper))
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
160 new T(value);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
161
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
162 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
163 return null;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
164 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
165 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
166
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
167 else
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
168 return value;
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
169 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
170 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
171
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
172 private id encapsuleString (string str)
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
173 {
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
174 enum { NSUTF8StringEncoding = 4 }
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
175
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
176 return objc.getClass!("NSString").msgSend(sel.registerName!("alloc")).msgSend(sel.registerName!("initWithBytes:length:encoding:"), str.ptr, str.length, NSUTF8StringEncoding);
033d260cfc9b First upload of the bridge
Jacob Carlborg <doob@me.com>
parents:
diff changeset
177 }