@@ -6,11 +6,16 @@ use graphene_core::raster_types::CPU;
6
6
use graphene_core:: raster_types:: Raster ;
7
7
use std:: collections:: HashMap ;
8
8
use std:: hash:: Hash ;
9
- use std:: sync:: Arc ;
10
- use std:: sync:: Mutex ;
9
+ use std:: hash:: Hasher ;
10
+ use std:: sync:: atomic:: { AtomicU64 , Ordering } ;
11
+ use std:: sync:: { Arc , Mutex } ;
11
12
12
- #[ derive( Clone , Debug , PartialEq , DynAny , Default , serde:: Serialize , serde:: Deserialize ) ]
13
+ // TODO: This is a temporary hack, be sure to not reuse this when the brush is being rewritten.
14
+ static NEXT_BRUSH_CACHE_IMPL_ID : AtomicU64 = AtomicU64 :: new ( 0 ) ;
15
+
16
+ #[ derive( Clone , Debug , DynAny , serde:: Serialize , serde:: Deserialize ) ]
13
17
struct BrushCacheImpl {
18
+ unique_id : u64 ,
14
19
// The full previous input that was cached.
15
20
prev_input : Vec < BrushStroke > ,
16
21
@@ -90,9 +95,29 @@ impl BrushCacheImpl {
90
95
}
91
96
}
92
97
98
+ impl Default for BrushCacheImpl {
99
+ fn default ( ) -> Self {
100
+ Self {
101
+ unique_id : NEXT_BRUSH_CACHE_IMPL_ID . fetch_add ( 1 , Ordering :: SeqCst ) ,
102
+ prev_input : Vec :: new ( ) ,
103
+ background : Default :: default ( ) ,
104
+ blended_image : Default :: default ( ) ,
105
+ last_stroke_texture : Default :: default ( ) ,
106
+ brush_texture_cache : HashMap :: new ( ) ,
107
+ }
108
+ }
109
+ }
110
+
111
+ impl PartialEq for BrushCacheImpl {
112
+ fn eq ( & self , other : & Self ) -> bool {
113
+ self . unique_id == other. unique_id
114
+ }
115
+ }
116
+
93
117
impl Hash for BrushCacheImpl {
94
- // Zero hash.
95
- fn hash < H : std:: hash:: Hasher > ( & self , _state : & mut H ) { }
118
+ fn hash < H : Hasher > ( & self , state : & mut H ) {
119
+ self . unique_id . hash ( state) ;
120
+ }
96
121
}
97
122
98
123
#[ derive( Clone , Debug , Default ) ]
@@ -103,82 +128,55 @@ pub struct BrushPlan {
103
128
pub first_stroke_point_skip : usize ,
104
129
}
105
130
106
- #[ derive( Debug , DynAny , serde:: Serialize , serde:: Deserialize ) ]
107
- pub struct BrushCache {
108
- inner : Arc < Mutex < BrushCacheImpl > > ,
109
- proto : bool ,
110
- }
111
-
112
- impl Default for BrushCache {
113
- fn default ( ) -> Self {
114
- Self :: new_proto ( )
115
- }
116
- }
131
+ #[ derive( Debug , Default , DynAny , serde:: Serialize , serde:: Deserialize ) ]
132
+ pub struct BrushCache ( Arc < Mutex < BrushCacheImpl > > ) ;
117
133
118
134
// A bit of a cursed implementation to work around the current node system.
119
135
// The original object is a 'prototype' that when cloned gives you a independent
120
136
// new object. Any further clones however are all the same underlying cache object.
121
137
impl Clone for BrushCache {
122
138
fn clone ( & self ) -> Self {
123
- if self . proto {
124
- let inner_val = self . inner . lock ( ) . unwrap ( ) ;
125
- Self {
126
- inner : Arc :: new ( Mutex :: new ( inner_val. clone ( ) ) ) ,
127
- proto : false ,
128
- }
129
- } else {
130
- Self {
131
- inner : Arc :: clone ( & self . inner ) ,
132
- proto : false ,
133
- }
134
- }
139
+ Self ( Arc :: new ( Mutex :: new ( self . 0 . lock ( ) . unwrap ( ) . clone ( ) ) ) )
135
140
}
136
141
}
137
142
138
143
impl PartialEq for BrushCache {
139
144
fn eq ( & self , other : & Self ) -> bool {
140
- if Arc :: ptr_eq ( & self . inner , & other. inner ) {
145
+ if Arc :: ptr_eq ( & self . 0 , & other. 0 ) {
141
146
return true ;
142
147
}
143
148
144
- let s = self . inner . lock ( ) . unwrap ( ) ;
145
- let o = other. inner . lock ( ) . unwrap ( ) ;
149
+ let s = self . 0 . lock ( ) . unwrap ( ) ;
150
+ let o = other. 0 . lock ( ) . unwrap ( ) ;
146
151
147
152
* s == * o
148
153
}
149
154
}
150
155
151
156
impl Hash for BrushCache {
152
157
fn hash < H : std:: hash:: Hasher > ( & self , state : & mut H ) {
153
- self . inner . lock ( ) . unwrap ( ) . hash ( state) ;
158
+ self . 0 . lock ( ) . unwrap ( ) . hash ( state) ;
154
159
}
155
160
}
156
161
157
162
impl BrushCache {
158
- pub fn new_proto ( ) -> Self {
159
- Self {
160
- inner : Default :: default ( ) ,
161
- proto : true ,
162
- }
163
- }
164
-
165
163
pub fn compute_brush_plan ( & self , background : Instance < Raster < CPU > > , input : & [ BrushStroke ] ) -> BrushPlan {
166
- let mut inner = self . inner . lock ( ) . unwrap ( ) ;
164
+ let mut inner = self . 0 . lock ( ) . unwrap ( ) ;
167
165
inner. compute_brush_plan ( background, input)
168
166
}
169
167
170
168
pub fn cache_results ( & self , input : Vec < BrushStroke > , blended_image : Instance < Raster < CPU > > , last_stroke_texture : Instance < Raster < CPU > > ) {
171
- let mut inner = self . inner . lock ( ) . unwrap ( ) ;
169
+ let mut inner = self . 0 . lock ( ) . unwrap ( ) ;
172
170
inner. cache_results ( input, blended_image, last_stroke_texture)
173
171
}
174
172
175
173
pub fn get_cached_brush ( & self , style : & BrushStyle ) -> Option < Raster < CPU > > {
176
- let inner = self . inner . lock ( ) . unwrap ( ) ;
174
+ let inner = self . 0 . lock ( ) . unwrap ( ) ;
177
175
inner. brush_texture_cache . get ( style) . cloned ( )
178
176
}
179
177
180
178
pub fn store_brush ( & self , style : BrushStyle , brush : Raster < CPU > ) {
181
- let mut inner = self . inner . lock ( ) . unwrap ( ) ;
179
+ let mut inner = self . 0 . lock ( ) . unwrap ( ) ;
182
180
inner. brush_texture_cache . insert ( style, brush) ;
183
181
}
184
182
}
0 commit comments