Skip to content

Commit 8ea4b0b

Browse files
committed
Add objc_ptr.hpp
1 parent c423b95 commit 8ea4b0b

File tree

1 file changed

+115
-0
lines changed

1 file changed

+115
-0
lines changed
Lines changed: 115 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,115 @@
1+
//
2+
// objc_ptr.hpp
3+
// OpenGraphCxx
4+
//
5+
// Status: Complete
6+
// Modified based Compute code
7+
8+
#ifndef OPENGRAPH_CXX_UTIL_OBJC_PTR_HPP
9+
#define OPENGRAPH_CXX_UTIL_OBJC_PTR_HPP
10+
11+
#include <OpenGraph/OGBase.h>
12+
13+
#if OG_TARGET_OS_DARWIN
14+
#include <objc/objc.h>
15+
#include <objc/runtime.h>
16+
17+
OG_ASSUME_NONNULL_BEGIN
18+
19+
// Redeclare APIs from the Objective-C runtime.
20+
// These functions are not available through public headers, but are guaranteed
21+
// to exist on OS X >= 10.9 and iOS >= 7.0.
22+
OBJC_EXPORT id objc_retain(id obj);
23+
OBJC_EXPORT void objc_release(id obj);
24+
25+
namespace util {
26+
27+
template <typename T> class objc_ptr {
28+
private:
29+
id _storage;
30+
31+
static OG_INLINE id to_storage(T obj) { return (id)obj; }
32+
static OG_INLINE T from_storage(id storage) { return (T)storage; }
33+
34+
public:
35+
OG_CONSTEXPR objc_ptr() OG_NOEXCEPT : _storage(nil) {}
36+
OG_CONSTEXPR objc_ptr(std::nullptr_t) OG_NOEXCEPT : _storage(nil) {}
37+
38+
explicit objc_ptr(T obj) : _storage(to_storage(obj)) {
39+
if (_storage) {
40+
objc_retain(_storage);
41+
}
42+
}
43+
44+
~objc_ptr() {
45+
if (_storage) {
46+
objc_release(_storage);
47+
}
48+
}
49+
50+
// MARK: - Copy and move constructors
51+
52+
objc_ptr(const objc_ptr &other) OG_NOEXCEPT : _storage(other._storage) {
53+
if (_storage) {
54+
objc_retain(_storage);
55+
}
56+
}
57+
58+
objc_ptr(objc_ptr &&other) OG_NOEXCEPT : _storage(other._storage) {
59+
other._storage = nil;
60+
}
61+
62+
// MARK: - Copy and move assignment operators
63+
64+
objc_ptr &operator=(const objc_ptr &other) OG_NOEXCEPT {
65+
if (this != &other) {
66+
if (_storage) {
67+
objc_release(_storage);
68+
}
69+
_storage = other._storage;
70+
if (_storage) {
71+
objc_retain(_storage);
72+
}
73+
}
74+
return *this;
75+
}
76+
77+
objc_ptr &operator=(objc_ptr &&other) OG_NOEXCEPT {
78+
if (this != &other) {
79+
if (_storage) {
80+
objc_release(_storage);
81+
}
82+
_storage = other._storage;
83+
other._storage = nil;
84+
}
85+
return *this;
86+
}
87+
88+
// MARK: - Modifiers
89+
90+
void reset() OG_NOEXCEPT { reset(nil); }
91+
92+
void reset(T obj = nil) OG_NOEXCEPT {
93+
if (_storage != obj) {
94+
if (_storage) {
95+
objc_release(_storage);
96+
}
97+
_storage = to_storage(obj);
98+
if (_storage) {
99+
objc_retain(_storage);
100+
}
101+
}
102+
}
103+
104+
T get() const OG_NOEXCEPT { return from_storage(_storage); }
105+
106+
explicit operator bool() const OG_NOEXCEPT { return _storage != nil; }
107+
}; /* class objc_ptr */
108+
109+
} /* namespace util */
110+
111+
OG_ASSUME_NONNULL_END
112+
113+
#endif
114+
115+
#endif /* OPENGRAPH_CXX_UTIL_OBJC_PTR_HPP */

0 commit comments

Comments
 (0)