~ubuntu-branches/ubuntu/trusty/blender/trusty

« back to all changes in this revision

Viewing changes to intern/cycles/render/image.cpp

  • Committer: Package Import Robot
  • Author(s): Jeremy Bicha
  • Date: 2013-03-06 12:08:47 UTC
  • mfrom: (1.5.1) (14.1.8 experimental)
  • Revision ID: package-import@ubuntu.com-20130306120847-frjfaryb2zrotwcg
Tags: 2.66a-1ubuntu1
* Resynchronize with Debian (LP: #1076930, #1089256, #1052743, #999024,
  #1122888, #1147084)
* debian/control:
  - Lower build-depends on libavcodec-dev since we're not
    doing the libav9 transition in Ubuntu yet

Show diffs side-by-side

added added

removed removed

Lines of Context:
34
34
ImageManager::ImageManager()
35
35
{
36
36
        need_update = true;
 
37
        pack_images = false;
37
38
        osl_texture_system = NULL;
 
39
        animation_frame = 0;
 
40
 
 
41
        tex_num_images = TEX_NUM_IMAGES;
 
42
        tex_num_float_images = TEX_NUM_FLOAT_IMAGES;
 
43
        tex_image_byte_start = TEX_IMAGE_BYTE_START;
38
44
}
39
45
 
40
46
ImageManager::~ImageManager()
45
51
                assert(!float_images[slot]);
46
52
}
47
53
 
 
54
void ImageManager::set_pack_images(bool pack_images_)
 
55
{
 
56
        pack_images = pack_images_;
 
57
}
 
58
 
48
59
void ImageManager::set_osl_texture_system(void *texture_system)
49
60
{
50
61
        osl_texture_system = texture_system;
51
62
}
52
63
 
53
 
static bool is_float_image(const string& filename)
54
 
{
 
64
void ImageManager::set_extended_image_limits(void)
 
65
{
 
66
        tex_num_images = TEX_EXTENDED_NUM_IMAGES;
 
67
        tex_num_float_images = TEX_EXTENDED_NUM_FLOAT_IMAGES;
 
68
        tex_image_byte_start = TEX_EXTENDED_IMAGE_BYTE_START;
 
69
}
 
70
 
 
71
bool ImageManager::set_animation_frame_update(int frame)
 
72
{
 
73
        if(frame != animation_frame) {
 
74
                animation_frame = frame;
 
75
 
 
76
                for(size_t slot = 0; slot < images.size(); slot++)
 
77
                        if(images[slot] && images[slot]->animated)
 
78
                                return true;
 
79
 
 
80
                for(size_t slot = 0; slot < float_images.size(); slot++)
 
81
                        if(float_images[slot] && float_images[slot]->animated)
 
82
                                return true;
 
83
        }
 
84
        
 
85
        return false;
 
86
}
 
87
 
 
88
bool ImageManager::is_float_image(const string& filename, void *builtin_data, bool& is_linear)
 
89
{
 
90
        bool is_float = false;
 
91
        is_linear = false;
 
92
 
 
93
        if(builtin_data) {
 
94
                if(builtin_image_info_cb) {
 
95
                        int width, height, channels;
 
96
                        builtin_image_info_cb(filename, builtin_data, is_float, width, height, channels);
 
97
                }
 
98
 
 
99
                if(is_float)
 
100
                        is_linear = true;
 
101
 
 
102
                return is_float;
 
103
        }
 
104
 
55
105
        ImageInput *in = ImageInput::create(filename);
56
 
        bool is_float = false;
57
106
 
58
107
        if(in) {
59
108
                ImageSpec spec;
60
109
 
61
110
                if(in->open(filename, spec)) {
62
111
                        /* check the main format, and channel formats;
63
 
                           if any are non-integer, we'll need a float texture slot */
64
 
                        if(spec.format == TypeDesc::HALF ||
65
 
                           spec.format == TypeDesc::FLOAT ||
66
 
                           spec.format == TypeDesc::DOUBLE) {
 
112
                         * if any take up more than one byte, we'll need a float texture slot */
 
113
                        if(spec.format.basesize() > 1) {
67
114
                                is_float = true;
 
115
                                is_linear = true;
68
116
                        }
69
117
 
70
118
                        for(size_t channel = 0; channel < spec.channelformats.size(); channel++) {
71
 
                                if(spec.channelformats[channel] == TypeDesc::HALF ||
72
 
                                   spec.channelformats[channel] == TypeDesc::FLOAT ||
73
 
                                   spec.channelformats[channel] == TypeDesc::DOUBLE) {
 
119
                                if(spec.channelformats[channel].basesize() > 1) {
74
120
                                        is_float = true;
 
121
                                        is_linear = true;
75
122
                                }
76
123
                        }
77
124
 
 
125
                        /* basic color space detection, not great but better than nothing
 
126
                         * before we do OpenColorIO integration */
 
127
                        if(is_float) {
 
128
                                string colorspace = spec.get_string_attribute("oiio:ColorSpace");
 
129
 
 
130
                                is_linear = !(colorspace == "sRGB" ||
 
131
                                              colorspace == "GammaCorrected" ||
 
132
                                                          strcmp(in->format_name(), "png") == 0);
 
133
                        }
 
134
                        else
 
135
                                is_linear = false;
 
136
 
78
137
                        in->close();
79
138
                }
80
139
 
84
143
        return is_float;
85
144
}
86
145
 
87
 
int ImageManager::add_image(const string& filename, bool& is_float)
 
146
int ImageManager::add_image(const string& filename, void *builtin_data, bool animated, bool& is_float, bool& is_linear)
88
147
{
89
148
        Image *img;
90
149
        size_t slot;
91
150
 
92
151
        /* load image info and find out if we need a float texture */
93
 
        is_float = is_float_image(filename);
 
152
        is_float = (pack_images)? false: is_float_image(filename, builtin_data, is_linear);
94
153
 
95
154
        if(is_float) {
96
155
                /* find existing image */
97
156
                for(slot = 0; slot < float_images.size(); slot++) {
98
157
                        if(float_images[slot] && float_images[slot]->filename == filename) {
99
158
                                float_images[slot]->users++;
100
 
                                return slot+TEX_IMAGE_FLOAT_START;
 
159
                                return slot;
101
160
                        }
102
161
                }
103
162
 
109
168
 
110
169
                if(slot == float_images.size()) {
111
170
                        /* max images limit reached */
112
 
                        if(float_images.size() == TEX_NUM_FLOAT_IMAGES)
 
171
                        if(float_images.size() == TEX_NUM_FLOAT_IMAGES) {
 
172
                                printf("ImageManager::add_image: float image limit reached %d, skipping '%s'\n",
 
173
                                       tex_num_float_images, filename.c_str());
113
174
                                return -1;
 
175
                        }
114
176
 
115
177
                        float_images.resize(float_images.size() + 1);
116
178
                }
118
180
                /* add new image */
119
181
                img = new Image();
120
182
                img->filename = filename;
 
183
                img->builtin_data = builtin_data;
121
184
                img->need_load = true;
 
185
                img->animated = animated;
122
186
                img->users = 1;
123
187
 
124
188
                float_images[slot] = img;
125
 
                /* report slot out of total set of textures */
126
 
                slot += TEX_IMAGE_FLOAT_START;
127
189
        }
128
190
        else {
129
191
                for(slot = 0; slot < images.size(); slot++) {
130
192
                        if(images[slot] && images[slot]->filename == filename) {
131
193
                                images[slot]->users++;
132
 
                                return slot;
 
194
                                return slot+tex_image_byte_start;
133
195
                        }
134
196
                }
135
197
 
141
203
 
142
204
                if(slot == images.size()) {
143
205
                        /* max images limit reached */
144
 
                        if(images.size() == TEX_NUM_IMAGES)
 
206
                        if(images.size() == tex_num_images) {
 
207
                                printf("ImageManager::add_image: byte image limit reached %d, skipping '%s'\n",
 
208
                                       tex_num_images, filename.c_str());
145
209
                                return -1;
 
210
                        }
146
211
 
147
212
                        images.resize(images.size() + 1);
148
213
                }
150
215
                /* add new image */
151
216
                img = new Image();
152
217
                img->filename = filename;
 
218
                img->builtin_data = builtin_data;
153
219
                img->need_load = true;
 
220
                img->animated = animated;
154
221
                img->users = 1;
155
222
 
156
223
                images[slot] = img;
 
224
 
 
225
                slot += tex_image_byte_start;
157
226
        }
158
227
        need_update = true;
159
228
 
160
229
        return slot;
161
230
}
162
231
 
163
 
void ImageManager::remove_image(const string& filename)
 
232
void ImageManager::remove_image(const string& filename, void *builtin_data)
164
233
{
165
234
        size_t slot;
166
235
 
167
236
        for(slot = 0; slot < images.size(); slot++) {
168
 
                if(images[slot] && images[slot]->filename == filename) {
 
237
                if(images[slot] && images[slot]->filename == filename && images[slot]->builtin_data == builtin_data) {
169
238
                        /* decrement user count */
170
239
                        images[slot]->users--;
171
240
                        assert(images[slot]->users >= 0);
172
241
 
173
242
                        /* don't remove immediately, rather do it all together later on. one of
174
 
                           the reasons for this is that on shader changes we add and remove nodes
175
 
                           that use them, but we do not want to reload the image all the time. */
 
243
                         * the reasons for this is that on shader changes we add and remove nodes
 
244
                         * that use them, but we do not want to reload the image all the time. */
176
245
                        if(images[slot]->users == 0)
177
246
                                need_update = true;
178
247
 
183
252
        if(slot == images.size()) {
184
253
                /* see if it's in a float texture slot */
185
254
                for(slot = 0; slot < float_images.size(); slot++) {
186
 
                        if(float_images[slot] && float_images[slot]->filename == filename) {
 
255
                        if(float_images[slot] && float_images[slot]->filename == filename && float_images[slot]->builtin_data == builtin_data) {
187
256
                                /* decrement user count */
188
257
                                float_images[slot]->users--;
189
258
                                assert(float_images[slot]->users >= 0);
190
259
 
191
260
                                /* don't remove immediately, rather do it all together later on. one of
192
 
                                   the reasons for this is that on shader changes we add and remove nodes
193
 
                                   that use them, but we do not want to reload the image all the time. */
 
261
                                 * the reasons for this is that on shader changes we add and remove nodes
 
262
                                 * that use them, but we do not want to reload the image all the time. */
194
263
                                if(float_images[slot]->users == 0)
195
264
                                        need_update = true;
196
265
 
205
274
        if(img->filename == "")
206
275
                return false;
207
276
 
208
 
        /* load image from file through OIIO */
209
 
        ImageInput *in = ImageInput::create(img->filename);
210
 
 
211
 
        if(!in)
212
 
                return false;
213
 
 
214
 
        ImageSpec spec;
215
 
 
216
 
        if(!in->open(img->filename, spec)) {
217
 
                delete in;
218
 
                return false;
 
277
        ImageInput *in = NULL;
 
278
        int width, height, components;
 
279
 
 
280
        if(!img->builtin_data) {
 
281
                /* load image from file through OIIO */
 
282
                in = ImageInput::create(img->filename);
 
283
 
 
284
                if(!in)
 
285
                        return false;
 
286
 
 
287
                ImageSpec spec;
 
288
 
 
289
                if(!in->open(img->filename, spec)) {
 
290
                        delete in;
 
291
                        return false;
 
292
                }
 
293
 
 
294
                width = spec.width;
 
295
                height = spec.height;
 
296
                components = spec.nchannels;
 
297
        }
 
298
        else {
 
299
                /* load image using builtin images callbacks */
 
300
                if(!builtin_image_info_cb || !builtin_image_pixels_cb)
 
301
                        return false;
 
302
 
 
303
                bool is_float;
 
304
                builtin_image_info_cb(img->filename, img->builtin_data, is_float, width, height, components);
219
305
        }
220
306
 
221
307
        /* we only handle certain number of components */
222
 
        int width = spec.width;
223
 
        int height = spec.height;
224
 
        int components = spec.nchannels;
225
 
 
226
308
        if(!(components == 1 || components == 3 || components == 4)) {
227
 
                in->close();
228
 
                delete in;
 
309
                if(in) {
 
310
                        in->close();
 
311
                        delete in;
 
312
                }
 
313
 
229
314
                return false;
230
315
        }
231
316
 
233
318
        uchar *pixels = (uchar*)tex_img.resize(width, height);
234
319
        int scanlinesize = width*components*sizeof(uchar);
235
320
 
236
 
        in->read_image(TypeDesc::UINT8,
237
 
                (uchar*)pixels + (height-1)*scanlinesize,
238
 
                AutoStride,
239
 
                -scanlinesize,
240
 
                AutoStride);
 
321
        if(in) {
 
322
                in->read_image(TypeDesc::UINT8,
 
323
                        (uchar*)pixels + (height-1)*scanlinesize,
 
324
                        AutoStride,
 
325
                        -scanlinesize,
 
326
                        AutoStride);
241
327
 
242
 
        in->close();
243
 
        delete in;
 
328
                in->close();
 
329
                delete in;
 
330
        }
 
331
        else {
 
332
                builtin_image_pixels_cb(img->filename, img->builtin_data, pixels);
 
333
        }
244
334
 
245
335
        if(components == 3) {
246
336
                for(int i = width*height-1; i >= 0; i--) {
267
357
        if(img->filename == "")
268
358
                return false;
269
359
 
270
 
        /* load image from file through OIIO */
271
 
        ImageInput *in = ImageInput::create(img->filename);
272
 
 
273
 
        if(!in)
274
 
                return false;
275
 
 
276
 
        ImageSpec spec;
277
 
 
278
 
        if(!in->open(img->filename, spec)) {
279
 
                delete in;
280
 
                return false;
281
 
        }
282
 
 
283
 
        /* we only handle certain number of components */
284
 
        int width = spec.width;
285
 
        int height = spec.height;
286
 
        int components = spec.nchannels;
 
360
        ImageInput *in = NULL;
 
361
        int width, height, components;
 
362
 
 
363
        if(!img->builtin_data) {
 
364
                /* load image from file through OIIO */
 
365
                in = ImageInput::create(img->filename);
 
366
 
 
367
                if(!in)
 
368
                        return false;
 
369
 
 
370
                ImageSpec spec;
 
371
 
 
372
                if(!in->open(img->filename, spec)) {
 
373
                        delete in;
 
374
                        return false;
 
375
                }
 
376
 
 
377
                /* we only handle certain number of components */
 
378
                width = spec.width;
 
379
                height = spec.height;
 
380
                components = spec.nchannels;
 
381
        }
 
382
        else {
 
383
                /* load image using builtin images callbacks */
 
384
                if(!builtin_image_info_cb || !builtin_image_float_pixels_cb)
 
385
                        return false;
 
386
 
 
387
                bool is_float;
 
388
                builtin_image_info_cb(img->filename, img->builtin_data, is_float, width, height, components);
 
389
        }
287
390
 
288
391
        if(!(components == 1 || components == 3 || components == 4)) {
289
 
                in->close();
290
 
                delete in;
 
392
                if(in) {
 
393
                        in->close();
 
394
                        delete in;
 
395
                }
291
396
                return false;
292
397
        }
293
398
 
295
400
        float *pixels = (float*)tex_img.resize(width, height);
296
401
        int scanlinesize = width*components*sizeof(float);
297
402
 
298
 
        in->read_image(TypeDesc::FLOAT,
299
 
                (uchar*)pixels + (height-1)*scanlinesize,
300
 
                AutoStride,
301
 
                -scanlinesize,
302
 
                AutoStride);
 
403
        if(in) {
 
404
                in->read_image(TypeDesc::FLOAT,
 
405
                        (uchar*)pixels + (height-1)*scanlinesize,
 
406
                        AutoStride,
 
407
                        -scanlinesize,
 
408
                        AutoStride);
303
409
 
304
 
        in->close();
305
 
        delete in;
 
410
                in->close();
 
411
                delete in;
 
412
        }
 
413
        else {
 
414
                builtin_image_float_pixels_cb(img->filename, img->builtin_data, pixels);
 
415
        }
306
416
 
307
417
        if(components == 3) {
308
418
                for(int i = width*height-1; i >= 0; i--) {
324
434
        return true;
325
435
}
326
436
 
327
 
void ImageManager::device_load_image(Device *device, DeviceScene *dscene, int slot)
 
437
void ImageManager::device_load_image(Device *device, DeviceScene *dscene, int slot, Progress *progress)
328
438
{
 
439
        if(progress->get_cancel())
 
440
                return;
329
441
        if(osl_texture_system)
330
442
                return;
331
443
 
332
444
        Image *img;
333
445
        bool is_float;
334
446
 
335
 
        if(slot < TEX_IMAGE_FLOAT_START) {
336
 
                img = images[slot];
 
447
        if(slot >= tex_image_byte_start) {
 
448
                img = images[slot - tex_image_byte_start];
337
449
                is_float = false;
338
450
        }
339
451
        else {
340
 
                img = float_images[slot - TEX_IMAGE_FLOAT_START];
 
452
                img = float_images[slot];
341
453
                is_float = true;
342
454
        }
343
455
 
344
456
        if(is_float) {
345
 
                device_vector<float4>& tex_img = dscene->tex_float_image[slot - TEX_IMAGE_FLOAT_START];
346
 
 
347
 
                if(tex_img.device_pointer)
 
457
                string filename = path_filename(float_images[slot]->filename);
 
458
                progress->set_status("Updating Images", "Loading " + filename);
 
459
 
 
460
                device_vector<float4>& tex_img = dscene->tex_float_image[slot];
 
461
 
 
462
                if(tex_img.device_pointer) {
 
463
                        thread_scoped_lock device_lock(device_mutex);
348
464
                        device->tex_free(tex_img);
 
465
                }
349
466
 
350
467
                if(!file_load_float_image(img, tex_img)) {
351
 
                        /* on failure to load, we set a 1x1 pixels black image */
 
468
                        /* on failure to load, we set a 1x1 pixels pink image */
352
469
                        float *pixels = (float*)tex_img.resize(1, 1);
353
470
 
354
 
                        pixels[0] = 0.0f;
355
 
                        pixels[1] = 0.0f;
356
 
                        pixels[2] = 0.0f;
357
 
                        pixels[3] = 0.0f;
 
471
                        pixels[0] = TEX_IMAGE_MISSING_R;
 
472
                        pixels[1] = TEX_IMAGE_MISSING_G;
 
473
                        pixels[2] = TEX_IMAGE_MISSING_B;
 
474
                        pixels[3] = TEX_IMAGE_MISSING_A;
358
475
                }
359
476
 
360
477
                string name;
362
479
                if(slot >= 10) name = string_printf("__tex_image_float_0%d", slot);
363
480
                else name = string_printf("__tex_image_float_00%d", slot);
364
481
 
365
 
                device->tex_alloc(name.c_str(), tex_img, true, true);
 
482
                if(!pack_images) {
 
483
                        thread_scoped_lock device_lock(device_mutex);
 
484
                        device->tex_alloc(name.c_str(), tex_img, true, true);
 
485
                }
366
486
        }
367
487
        else {
368
 
                device_vector<uchar4>& tex_img = dscene->tex_image[slot];
369
 
 
370
 
                if(tex_img.device_pointer)
 
488
                string filename = path_filename(images[slot - tex_image_byte_start]->filename);
 
489
                progress->set_status("Updating Images", "Loading " + filename);
 
490
 
 
491
                device_vector<uchar4>& tex_img = dscene->tex_image[slot - tex_image_byte_start];
 
492
 
 
493
                if(tex_img.device_pointer) {
 
494
                        thread_scoped_lock device_lock(device_mutex);
371
495
                        device->tex_free(tex_img);
 
496
                }
372
497
 
373
498
                if(!file_load_image(img, tex_img)) {
374
 
                        /* on failure to load, we set a 1x1 pixels black image */
 
499
                        /* on failure to load, we set a 1x1 pixels pink image */
375
500
                        uchar *pixels = (uchar*)tex_img.resize(1, 1);
376
501
 
377
 
                        pixels[0] = 0;
378
 
                        pixels[1] = 0;
379
 
                        pixels[2] = 0;
380
 
                        pixels[3] = 0;
 
502
                        pixels[0] = (TEX_IMAGE_MISSING_R * 255);
 
503
                        pixels[1] = (TEX_IMAGE_MISSING_G * 255);
 
504
                        pixels[2] = (TEX_IMAGE_MISSING_B * 255);
 
505
                        pixels[3] = (TEX_IMAGE_MISSING_A * 255);
381
506
                }
382
507
 
383
508
                string name;
385
510
                if(slot >= 10) name = string_printf("__tex_image_0%d", slot);
386
511
                else name = string_printf("__tex_image_00%d", slot);
387
512
 
388
 
                device->tex_alloc(name.c_str(), tex_img, true, true);
 
513
                if(!pack_images) {
 
514
                        thread_scoped_lock device_lock(device_mutex);
 
515
                        device->tex_alloc(name.c_str(), tex_img, true, true);
 
516
                }
389
517
        }
 
518
 
 
519
        img->need_load = false;
390
520
}
391
521
 
392
522
void ImageManager::device_free_image(Device *device, DeviceScene *dscene, int slot)
394
524
        Image *img;
395
525
        bool is_float;
396
526
 
397
 
        if(slot < TEX_IMAGE_FLOAT_START) {
398
 
                img = images[slot];
 
527
        if(slot >= tex_image_byte_start) {
 
528
                img = images[slot - tex_image_byte_start];
399
529
                is_float = false;
400
530
        }
401
531
        else {
402
 
                img = float_images[slot - TEX_IMAGE_FLOAT_START];
 
532
                img = float_images[slot];
403
533
                is_float = true;
404
534
        }
405
535
 
411
541
#endif
412
542
                }
413
543
                else if(is_float) {
414
 
                        device->tex_free(dscene->tex_float_image[slot - TEX_IMAGE_FLOAT_START]);
415
 
                        dscene->tex_float_image[slot - TEX_IMAGE_FLOAT_START].clear();
416
 
 
417
 
                        delete float_images[slot - TEX_IMAGE_FLOAT_START];
418
 
                        float_images[slot - TEX_IMAGE_FLOAT_START] = NULL;
 
544
                        device_vector<float4>& tex_img = dscene->tex_float_image[slot];
 
545
 
 
546
                        if(tex_img.device_pointer) {
 
547
                                thread_scoped_lock device_lock(device_mutex);
 
548
                                device->tex_free(tex_img);
 
549
                        }
 
550
 
 
551
                        tex_img.clear();
 
552
 
 
553
                        delete float_images[slot];
 
554
                        float_images[slot] = NULL;
419
555
                }
420
556
                else {
421
 
                        device->tex_free(dscene->tex_image[slot]);
422
 
                        dscene->tex_image[slot].clear();
423
 
 
424
 
                        delete images[slot];
425
 
                        images[slot] = NULL;
 
557
                        device_vector<uchar4>& tex_img = dscene->tex_image[slot - tex_image_byte_start];
 
558
 
 
559
                        if(tex_img.device_pointer) {
 
560
                                thread_scoped_lock device_lock(device_mutex);
 
561
                                device->tex_free(tex_img);
 
562
                        }
 
563
 
 
564
                        tex_img.clear();
 
565
 
 
566
                        delete images[slot - tex_image_byte_start];
 
567
                        images[slot - tex_image_byte_start] = NULL;
426
568
                }
427
569
        }
428
570
}
432
574
        if(!need_update)
433
575
                return;
434
576
 
 
577
        TaskPool pool;
 
578
 
435
579
        for(size_t slot = 0; slot < images.size(); slot++) {
436
 
                if(images[slot]) {
437
 
                        if(images[slot]->users == 0) {
438
 
                                device_free_image(device, dscene, slot);
439
 
                        }
440
 
                        else if(images[slot]->need_load) {
441
 
                                string name = path_filename(images[slot]->filename);
442
 
                                progress.set_status("Updating Images", "Loading " + name);
443
 
                                device_load_image(device, dscene, slot);
444
 
                                images[slot]->need_load = false;
445
 
                        }
 
580
                if(!images[slot])
 
581
                        continue;
446
582
 
447
 
                        if(progress.get_cancel()) return;
 
583
                if(images[slot]->users == 0) {
 
584
                        device_free_image(device, dscene, slot + tex_image_byte_start);
 
585
                }
 
586
                else if(images[slot]->need_load) {
 
587
                        if(!osl_texture_system) 
 
588
                                pool.push(function_bind(&ImageManager::device_load_image, this, device, dscene, slot + tex_image_byte_start, &progress));
448
589
                }
449
590
        }
450
591
 
451
592
        for(size_t slot = 0; slot < float_images.size(); slot++) {
452
 
                if(float_images[slot]) {
453
 
                        if(float_images[slot]->users == 0) {
454
 
                                device_free_image(device, dscene, slot + TEX_IMAGE_FLOAT_START);
455
 
                        }
456
 
                        else if(float_images[slot]->need_load) {
457
 
                                string name = path_filename(float_images[slot]->filename);
458
 
                                progress.set_status("Updating Images", "Loading " + name);
459
 
                                device_load_image(device, dscene, slot + TEX_IMAGE_FLOAT_START);
460
 
                                float_images[slot]->need_load = false;
461
 
                        }
 
593
                if(!float_images[slot])
 
594
                        continue;
462
595
 
463
 
                        if(progress.get_cancel()) return;
 
596
                if(float_images[slot]->users == 0) {
 
597
                        device_free_image(device, dscene, slot);
 
598
                }
 
599
                else if(float_images[slot]->need_load) {
 
600
                        if(!osl_texture_system) 
 
601
                                pool.push(function_bind(&ImageManager::device_load_image, this, device, dscene, slot, &progress));
464
602
                }
465
603
        }
466
604
 
 
605
        pool.wait_work();
 
606
 
 
607
        if(pack_images)
 
608
                device_pack_images(device, dscene, progress);
 
609
 
467
610
        need_update = false;
468
611
}
469
612
 
 
613
void ImageManager::device_pack_images(Device *device, DeviceScene *dscene, Progress& progess)
 
614
{
 
615
        /* for OpenCL, we pack all image textures inside a single big texture, and
 
616
         * will do our own interpolation in the kernel */
 
617
        size_t size = 0;
 
618
 
 
619
        for(size_t slot = 0; slot < images.size(); slot++) {
 
620
                if(!images[slot])
 
621
                        continue;
 
622
 
 
623
                device_vector<uchar4>& tex_img = dscene->tex_image[slot];
 
624
                size += tex_img.size();
 
625
        }
 
626
 
 
627
        uint4 *info = dscene->tex_image_packed_info.resize(images.size());
 
628
        uchar4 *pixels = dscene->tex_image_packed.resize(size);
 
629
 
 
630
        size_t offset = 0;
 
631
 
 
632
        for(size_t slot = 0; slot < images.size(); slot++) {
 
633
                if(!images[slot])
 
634
                        continue;
 
635
 
 
636
                device_vector<uchar4>& tex_img = dscene->tex_image[slot];
 
637
 
 
638
                info[slot] = make_uint4(tex_img.data_width, tex_img.data_height, offset, 1);
 
639
 
 
640
                memcpy(pixels+offset, (void*)tex_img.data_pointer, tex_img.memory_size());
 
641
                offset += tex_img.size();
 
642
        }
 
643
 
 
644
        if(dscene->tex_image_packed.size())
 
645
                device->tex_alloc("__tex_image_packed", dscene->tex_image_packed);
 
646
        if(dscene->tex_image_packed_info.size())
 
647
                device->tex_alloc("__tex_image_packed_info", dscene->tex_image_packed_info);
 
648
}
 
649
 
470
650
void ImageManager::device_free(Device *device, DeviceScene *dscene)
471
651
{
472
652
        for(size_t slot = 0; slot < images.size(); slot++)
 
653
                device_free_image(device, dscene, slot + tex_image_byte_start);
 
654
        for(size_t slot = 0; slot < float_images.size(); slot++)
473
655
                device_free_image(device, dscene, slot);
474
 
        for(size_t slot = 0; slot < float_images.size(); slot++)
475
 
                device_free_image(device, dscene, slot + TEX_IMAGE_FLOAT_START);
 
656
 
 
657
        device->tex_free(dscene->tex_image_packed);
 
658
        device->tex_free(dscene->tex_image_packed_info);
 
659
 
 
660
        dscene->tex_image_packed.clear();
 
661
        dscene->tex_image_packed_info.clear();
476
662
 
477
663
        images.clear();
478
664
        float_images.clear();