Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
CocoaUtils.h
Go to the documentation of this file.
1// @(#)root/graf2d:$Id$
2// Author: Timur Pocheptsov 6/12/2011
3
4/*************************************************************************
5 * Copyright (C) 1995-2012, Rene Brun and Fons Rademakers. *
6 * All rights reserved. *
7 * *
8 * For the licensing terms see $ROOTSYS/LICENSE. *
9 * For the list of contributors see $ROOTSYS/README/CREDITS. *
10 *************************************************************************/
11
12#ifndef ROOT_CocoaUtils
13#define ROOT_CocoaUtils
14
15#include <cstddef>
16#include <cassert>
17
18#include <Foundation/Foundation.h>
19
20namespace ROOT {
21namespace MacOSX {
22namespace Util {
23
24/////////////////////////////////////////////////////////////////////
25// //
26// NSStrongReference. Class to keep strong reference to NSObject. //
27// //
28/////////////////////////////////////////////////////////////////////
29
30template<class DerivedType>
32public:
34 : fNSObject(nil)
35 {
36 }
37
38 explicit NSStrongReference(NSObject *nsObject)
39 : fNSObject([nsObject retain])
40 {
41 }
42
44 : fNSObject([rhs.fNSObject retain])
45 {
46 }
47
48
50 {
51 [fNSObject release];
52 }
53
55 {
56 if (&rhs != this) {
57 //Even if both reference the same NSObject, it's ok to do release.
58 [fNSObject release];
59 fNSObject = [rhs.fNSObject retain];
60 }
61
62 return *this;
63 }
64
66 {
67 fNSObject = rhs.fNSObject;
68 rhs.fNSObject = nil;
69 }
70
72 {
73 //In case you're smart enough to self assign
74 //(using std::move, for example):
75 assert(this != &rhs);
76
77 fNSObject = rhs.fNSObject;
78 rhs.fNSObject = nil;
79
80 return *this;
81 }
82
84 {
85 if (nsObject != fNSObject) {
86 [fNSObject release];
87 fNSObject = [nsObject retain];
88 }
89
90 return *this;
91 }
92
93 DerivedType *Get()const
94 {
95 return (DerivedType *)fNSObject;
96 }
97
98 void Reset(NSObject *object)
99 {
100 if (fNSObject != object) {
101 NSObject *obj = [object retain];
102 [fNSObject release];
103 fNSObject = obj;
104 }
105 }
106
107private:
109};
110
111///////////////////////////////////////////////////////////////////
112// //
113// NSScopeGuard. //
114// //
115///////////////////////////////////////////////////////////////////
116
117template<class DerivedType>
119public:
121 : fNSObject(nil)
122 {
123 }
124
125 explicit NSScopeGuard(NSObject *nsObject)
126 : fNSObject(nsObject)
127 {
128 }
130 {
131 [fNSObject release];//nothing for nil.
132 }
133
134public:
135
136 DerivedType *Get()const
137 {
138 return (DerivedType *)fNSObject;
139 }
140
141 void Reset(NSObject *object)
142 {
143 if (object != fNSObject) {
144 [fNSObject release];
146 }
147 }
148
150 {
151 NSObject *ret = fNSObject;
152 fNSObject = nil;
153 return ret;
154 }
155private:
157
160};
161
162//////////////////////////////////////
163// //
164// RAII class for autorelease pool. //
165// //
166//////////////////////////////////////
167
169public:
170 explicit AutoreleasePool(bool delayCreation = false);
172
173 //Drains the previous pool (if any)
174 //and activates a new one.
175 void Reset();
176
177private:
178 NSAutoreleasePool *fPool;
179
182};
183
184///////////////////////////////////////////////////////////
185// //
186// Strong reference for a Core Foundation object. //
187// This class can have specializations for CF object //
188// with it's own version of retain or release. //
189// //
190///////////////////////////////////////////////////////////
191
192template<class RefType>
194public:
196 : fRef(0)
197 {
198 }
199
200 CFStrongReference(RefType ref, bool initRetain)
201 : fRef(ref)
202 {
203 if (initRetain && ref)
204 CFRetain(ref);
205 }
206
208 {
209 fRef = rhs.fRef;
210 if (fRef)
211 CFRetain(fRef);
212 }
213
215 {
216 if (this != &rhs) {
217 if (fRef)
218 CFRelease(fRef);//Ok even if rhs references the same.
219 fRef = rhs.fRef;
220 if (fRef)
221 CFRetain(fRef);
222 }
223
224 return *this;
225 }
226
228 {
229 fRef = rhs.fRef;
230 rhs.fRef = 0;
231 }
232
234 {
235 // Do not: a = std::move(a) :)
236 assert(this != &rhs);
237
238 fRef = rhs.fRef;
239 rhs.fRef = 0;
240
241 return *this;
242 }
243
245 {
246 if (fRef)
247 CFRelease(fRef);
248 }
249
250 RefType Get()const
251 {
252 return fRef;
253 }
254
255private:
256 RefType fRef;
257};
258
259///////////////////////////////////////////////////
260// //
261// Scope guard for Core Foundations objects. //
262// Specializations can be defined to call //
263// something different from CFRetain/CFRelease. //
264// //
265///////////////////////////////////////////////////
266
267template<class RefType>
269public:
271 : fRef(0)
272 {
273 }
274
275 explicit CFScopeGuard(RefType ref)
276 : fRef(ref)
277 {
278 }
279
281 {
282 if (fRef)
283 CFRelease(fRef);
284 }
285
286 RefType Get()const
287 {
288 return fRef;
289 }
290
291 void Reset(RefType ref)
292 {
293 if (ref != fRef) {
294 if (fRef)
295 CFRelease(fRef);
296 fRef = ref;
297 }
298 }
299
300 RefType Release()
301 {
302 RefType ret = fRef;
303 fRef = 0;
304 return ret;
305 }
306
307private:
308 RefType fRef;
309
312};
313
314///////////////////////////////////////////////////
315// //
316// Scoped array - scope guard for an array. //
317// Sometimes, I can not use std::vector, //
318// for example, data is allocated in TGCocoa //
319// and must be later freed in Objective-C code. //
320// To make the code exception-safe, I still //
321// have to care about memory, which is already //
322// allocated. //
323// //
324///////////////////////////////////////////////////
325
326template<class T>
328public:
329 explicit ScopedArray(T * p = 0)
330 : fData(p)
331 {
332 }
333
335 {
336 delete [] fData;
337 }
338
339 void Reset(T * p)
340 {
341 if (p != fData)
342 delete [] fData;
343 fData = p;
344 }
345
347 {
348 T *ret = fData;
349 fData = 0;
350 return ret;
351 }
352
353 T &operator [] (std::ptrdiff_t index)const
354 {
355 return fData[index];
356 }
357
358 T *Get()const
359 {
360 return fData;
361 }
362
363private:
365
368};
369
370}//Util
371}//MacOSX
372}//ROOT
373
374#endif
AutoreleasePool(const AutoreleasePool &rhs)
AutoreleasePool(bool delayCreation=false)
AutoreleasePool & operator=(const AutoreleasePool &rhs)
CFScopeGuard(const CFScopeGuard &rhs)
CFScopeGuard & operator=(const CFScopeGuard &rhs)
CFStrongReference(RefType ref, bool initRetain)
Definition CocoaUtils.h:200
CFStrongReference(const CFStrongReference &rhs)
Definition CocoaUtils.h:207
CFStrongReference(CFStrongReference &&rhs)
Definition CocoaUtils.h:227
CFStrongReference & operator=(const CFStrongReference &rhs)
Definition CocoaUtils.h:214
DerivedType * Get() const
Definition CocoaUtils.h:136
NSScopeGuard & operator=(const NSScopeGuard &rhs)
NSScopeGuard(const NSScopeGuard &rhs)
NSScopeGuard(NSObject *nsObject)
Definition CocoaUtils.h:125
void Reset(NSObject *object)
Definition CocoaUtils.h:141
NSStrongReference(NSObject *nsObject)
Definition CocoaUtils.h:38
NSStrongReference(const NSStrongReference &rhs)
Definition CocoaUtils.h:43
NSStrongReference & operator=(const NSStrongReference &rhs)
Definition CocoaUtils.h:54
NSStrongReference(NSStrongReference &&rhs)
Definition CocoaUtils.h:65
T & operator[](std::ptrdiff_t index) const
Definition CocoaUtils.h:353
ScopedArray(const ScopedArray &rhs)
ScopedArray & operator=(const ScopedArray &rhs)
tbb::task_arena is an alias of tbb::interface7::task_arena, which doesn't allow to forward declare tb...