Cycles: Code cleanup, spaces around keywords
[blender-staging.git] / intern / cycles / app / cycles_xml.cpp
1 /*
2  * Copyright 2011-2013 Blender Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include <stdio.h>
18
19 #include <sstream>
20 #include <algorithm>
21 #include <iterator>
22
23 #include "camera.h"
24 #include "film.h"
25 #include "graph.h"
26 #include "integrator.h"
27 #include "light.h"
28 #include "mesh.h"
29 #include "nodes.h"
30 #include "object.h"
31 #include "shader.h"
32 #include "scene.h"
33
34 #include "subd_mesh.h"
35 #include "subd_patch.h"
36 #include "subd_split.h"
37
38 #include "util_debug.h"
39 #include "util_foreach.h"
40 #include "util_path.h"
41 #include "util_transform.h"
42 #include "util_xml.h"
43
44 #include "cycles_xml.h"
45
46 CCL_NAMESPACE_BEGIN
47
48 /* XML reading state */
49
50 struct XMLReadState {
51         Scene *scene;           /* scene pointer */
52         Transform tfm;          /* current transform state */
53         bool smooth;            /* smooth normal state */
54         int shader;                     /* current shader */
55         string base;            /* base path to current file*/
56         float dicing_rate;      /* current dicing rate */
57         Mesh::DisplacementMethod displacement_method;
58 };
59
60 /* Attribute Reading */
61
62 static bool xml_read_bool(bool *value, pugi::xml_node node, const char *name)
63 {
64         pugi::xml_attribute attr = node.attribute(name);
65
66         if(attr) {
67                 *value = (string_iequals(attr.value(), "true")) || (atoi(attr.value()) != 0);
68                 return true;
69         }
70
71         return false;
72 }
73
74 static bool xml_read_int(int *value, pugi::xml_node node, const char *name)
75 {
76         pugi::xml_attribute attr = node.attribute(name);
77
78         if(attr) {
79                 *value = atoi(attr.value());
80                 return true;
81         }
82
83         return false;
84 }
85
86 static bool xml_read_int_array(vector<int>& value, pugi::xml_node node, const char *name)
87 {
88         pugi::xml_attribute attr = node.attribute(name);
89
90         if(attr) {
91                 vector<string> tokens;
92                 string_split(tokens, attr.value());
93
94                 foreach(const string& token, tokens)
95                         value.push_back(atoi(token.c_str()));
96
97                 return true;
98         }
99
100         return false;
101 }
102
103 static bool xml_read_float(float *value, pugi::xml_node node, const char *name)
104 {
105         pugi::xml_attribute attr = node.attribute(name);
106
107         if(attr) {
108                 *value = (float)atof(attr.value());
109                 return true;
110         }
111
112         return false;
113 }
114
115 static bool xml_read_float_array(vector<float>& value, pugi::xml_node node, const char *name)
116 {
117         pugi::xml_attribute attr = node.attribute(name);
118
119         if(attr) {
120                 vector<string> tokens;
121                 string_split(tokens, attr.value());
122
123                 foreach(const string& token, tokens)
124                         value.push_back((float)atof(token.c_str()));
125
126                 return true;
127         }
128
129         return false;
130 }
131
132 static bool xml_read_float3(float3 *value, pugi::xml_node node, const char *name)
133 {
134         vector<float> array;
135
136         if(xml_read_float_array(array, node, name) && array.size() == 3) {
137                 *value = make_float3(array[0], array[1], array[2]);
138                 return true;
139         }
140
141         return false;
142 }
143
144 static bool xml_read_float3_array(vector<float3>& value, pugi::xml_node node, const char *name)
145 {
146         vector<float> array;
147
148         if(xml_read_float_array(array, node, name)) {
149                 for(size_t i = 0; i < array.size(); i += 3)
150                         value.push_back(make_float3(array[i+0], array[i+1], array[i+2]));
151
152                 return true;
153         }
154
155         return false;
156 }
157
158 static bool xml_read_float4(float4 *value, pugi::xml_node node, const char *name)
159 {
160         vector<float> array;
161
162         if(xml_read_float_array(array, node, name) && array.size() == 4) {
163                 *value = make_float4(array[0], array[1], array[2], array[3]);
164                 return true;
165         }
166
167         return false;
168 }
169
170 static bool xml_read_string(string *str, pugi::xml_node node, const char *name)
171 {
172         pugi::xml_attribute attr = node.attribute(name);
173
174         if(attr) {
175                 *str = attr.value();
176                 return true;
177         }
178
179         return false;
180 }
181
182 static bool xml_read_ustring(ustring *str, pugi::xml_node node, const char *name)
183 {
184         pugi::xml_attribute attr = node.attribute(name);
185
186         if(attr) {
187                 *str = ustring(attr.value());
188                 return true;
189         }
190
191         return false;
192 }
193
194 static bool xml_equal_string(pugi::xml_node node, const char *name, const char *value)
195 {
196         pugi::xml_attribute attr = node.attribute(name);
197
198         if(attr)
199                 return string_iequals(attr.value(), value);
200         
201         return false;
202 }
203
204 static bool xml_read_enum(ustring *str, ShaderEnum& enm, pugi::xml_node node, const char *name)
205 {
206         pugi::xml_attribute attr = node.attribute(name);
207
208         if(attr) {
209                 ustring ustr(attr.value());
210
211                 if(enm.exists(ustr)) {
212                         *str = ustr;
213                         return true;
214                 }
215                 else
216                         fprintf(stderr, "Unknown value \"%s\" for attribute \"%s\".\n", ustr.c_str(), name);
217         }
218
219         return false;
220 }
221
222 static ShaderSocketType xml_read_socket_type(pugi::xml_node node, const char *name)
223 {
224         pugi::xml_attribute attr = node.attribute(name);
225
226         if(attr) {
227                 string value = attr.value();
228                 if(string_iequals(value, "float"))
229                         return SHADER_SOCKET_FLOAT;
230                 else if(string_iequals(value, "int"))
231                         return SHADER_SOCKET_INT;
232                 else if(string_iequals(value, "color"))
233                         return SHADER_SOCKET_COLOR;
234                 else if(string_iequals(value, "vector"))
235                         return SHADER_SOCKET_VECTOR;
236                 else if(string_iequals(value, "point"))
237                         return SHADER_SOCKET_POINT;
238                 else if(string_iequals(value, "normal"))
239                         return SHADER_SOCKET_NORMAL;
240                 else if(string_iequals(value, "closure color"))
241                         return SHADER_SOCKET_CLOSURE;
242                 else if(string_iequals(value, "string"))
243                         return SHADER_SOCKET_STRING;
244                 else
245                         fprintf(stderr, "Unknown shader socket type \"%s\" for attribute \"%s\".\n", value.c_str(), name);
246         }
247         
248         return SHADER_SOCKET_UNDEFINED;
249 }
250
251 /* Film */
252
253 static void xml_read_film(const XMLReadState& state, pugi::xml_node node)
254 {
255         Film *film = state.scene->film;
256         
257         xml_read_float(&film->exposure, node, "exposure");
258
259         /* ToDo: Filter Type */
260         xml_read_float(&film->filter_width, node, "filter_width");
261 }
262
263 /* Integrator */
264
265 static void xml_read_integrator(const XMLReadState& state, pugi::xml_node node)
266 {
267         Integrator *integrator = state.scene->integrator;
268         
269         /* Branched Path */
270         bool branched = false;
271         xml_read_bool(&branched, node, "branched");
272
273         if(branched) {
274                 integrator->method = Integrator::BRANCHED_PATH;
275
276                 xml_read_int(&integrator->diffuse_samples, node, "diffuse_samples");
277                 xml_read_int(&integrator->glossy_samples, node, "glossy_samples");
278                 xml_read_int(&integrator->transmission_samples, node, "transmission_samples");
279                 xml_read_int(&integrator->ao_samples, node, "ao_samples");
280                 xml_read_int(&integrator->mesh_light_samples, node, "mesh_light_samples");
281                 xml_read_int(&integrator->subsurface_samples, node, "subsurface_samples");
282                 xml_read_int(&integrator->volume_samples, node, "volume_samples");
283                 xml_read_bool(&integrator->sample_all_lights_direct, node, "sample_all_lights_direct");
284                 xml_read_bool(&integrator->sample_all_lights_indirect, node, "sample_all_lights_indirect");
285         }
286         
287         /* Bounces */
288         xml_read_int(&integrator->min_bounce, node, "min_bounce");
289         xml_read_int(&integrator->max_bounce, node, "max_bounce");
290         
291         xml_read_int(&integrator->max_diffuse_bounce, node, "max_diffuse_bounce");
292         xml_read_int(&integrator->max_glossy_bounce, node, "max_glossy_bounce");
293         xml_read_int(&integrator->max_transmission_bounce, node, "max_transmission_bounce");
294         xml_read_int(&integrator->max_volume_bounce, node, "max_volume_bounce");
295         
296         /* Transparency */
297         xml_read_int(&integrator->transparent_min_bounce, node, "transparent_min_bounce");
298         xml_read_int(&integrator->transparent_max_bounce, node, "transparent_max_bounce");
299         xml_read_bool(&integrator->transparent_shadows, node, "transparent_shadows");
300         
301         /* Volume */
302         xml_read_float(&integrator->volume_step_size, node, "volume_step_size");
303         xml_read_int(&integrator->volume_max_steps, node, "volume_max_steps");
304         
305         /* Various Settings */
306         xml_read_bool(&integrator->caustics_reflective, node, "caustics_reflective");
307         xml_read_bool(&integrator->caustics_refractive, node, "caustics_refractive");
308         xml_read_float(&integrator->filter_glossy, node, "filter_glossy");
309         
310         xml_read_int(&integrator->seed, node, "seed");
311         xml_read_float(&integrator->sample_clamp_direct, node, "sample_clamp_direct");
312         xml_read_float(&integrator->sample_clamp_indirect, node, "sample_clamp_indirect");
313 }
314
315 /* Camera */
316
317 static void xml_read_camera(const XMLReadState& state, pugi::xml_node node)
318 {
319         Camera *cam = state.scene->camera;
320
321         xml_read_int(&cam->width, node, "width");
322         xml_read_int(&cam->height, node, "height");
323
324         if(xml_read_float(&cam->fov, node, "fov"))
325                 cam->fov = DEG2RADF(cam->fov);
326
327         xml_read_float(&cam->nearclip, node, "nearclip");
328         xml_read_float(&cam->farclip, node, "farclip");
329         xml_read_float(&cam->aperturesize, node, "aperturesize"); // 0.5*focallength/fstop
330         xml_read_float(&cam->focaldistance, node, "focaldistance");
331         xml_read_float(&cam->shuttertime, node, "shuttertime");
332         xml_read_float(&cam->aperture_ratio, node, "aperture_ratio");
333
334         if(xml_equal_string(node, "type", "orthographic"))
335                 cam->type = CAMERA_ORTHOGRAPHIC;
336         else if(xml_equal_string(node, "type", "perspective"))
337                 cam->type = CAMERA_PERSPECTIVE;
338         else if(xml_equal_string(node, "type", "panorama"))
339                 cam->type = CAMERA_PANORAMA;
340
341         if(xml_equal_string(node, "panorama_type", "equirectangular"))
342                 cam->panorama_type = PANORAMA_EQUIRECTANGULAR;
343         else if(xml_equal_string(node, "panorama_type", "fisheye_equidistant"))
344                 cam->panorama_type = PANORAMA_FISHEYE_EQUIDISTANT;
345         else if(xml_equal_string(node, "panorama_type", "fisheye_equisolid"))
346                 cam->panorama_type = PANORAMA_FISHEYE_EQUISOLID;
347
348         xml_read_float(&cam->fisheye_fov, node, "fisheye_fov");
349         xml_read_float(&cam->fisheye_lens, node, "fisheye_lens");
350
351         xml_read_float(&cam->sensorwidth, node, "sensorwidth");
352         xml_read_float(&cam->sensorheight, node, "sensorheight");
353
354         cam->matrix = state.tfm;
355
356         cam->need_update = true;
357         cam->update();
358 }
359
360 /* Shader */
361
362 static string xml_socket_name(const char *name)
363 {
364         string sname = name;
365         size_t i;
366
367         while((i = sname.find(" ")) != string::npos)
368                 sname.replace(i, 1, "");
369         
370         return sname;
371 }
372
373 static void xml_read_shader_graph(const XMLReadState& state, Shader *shader, pugi::xml_node graph_node)
374 {
375         ShaderGraph *graph = new ShaderGraph();
376
377         map<string, ShaderNode*> nodemap;
378
379         nodemap["output"] = graph->output();
380
381         for(pugi::xml_node node = graph_node.first_child(); node; node = node.next_sibling()) {
382                 ShaderNode *snode = NULL;
383
384                 if(string_iequals(node.name(), "image_texture")) {
385                         ImageTextureNode *img = new ImageTextureNode();
386
387                         xml_read_string(&img->filename, node, "src");
388                         img->filename = path_join(state.base, img->filename);
389                         
390                         xml_read_enum(&img->color_space, ImageTextureNode::color_space_enum, node, "color_space");
391                         xml_read_enum(&img->projection, ImageTextureNode::projection_enum, node, "projection");
392                         xml_read_float(&img->projection_blend, node, "projection_blend");
393
394                         snode = img;
395                 }
396                 else if(string_iequals(node.name(), "environment_texture")) {
397                         EnvironmentTextureNode *env = new EnvironmentTextureNode();
398
399                         xml_read_string(&env->filename, node, "src");
400                         env->filename = path_join(state.base, env->filename);
401                         
402                         xml_read_enum(&env->color_space, EnvironmentTextureNode::color_space_enum, node, "color_space");
403                         xml_read_enum(&env->projection, EnvironmentTextureNode::projection_enum, node, "projection");
404
405                         snode = env;
406                 }
407                 else if(string_iequals(node.name(), "osl_shader")) {
408                         OSLScriptNode *osl = new OSLScriptNode();
409
410                         /* Source */
411                         xml_read_string(&osl->filepath, node, "src");
412                         if(path_is_relative(osl->filepath)) {
413                                 osl->filepath = path_join(state.base, osl->filepath);
414                         }
415
416                         /* Generate inputs/outputs from node sockets
417                          *
418                          * Note: ShaderInput/ShaderOutput store shallow string copies only!
419                          * Socket names must be stored in the extra lists instead. */
420                         /* read input values */
421                         for(pugi::xml_node param = node.first_child(); param; param = param.next_sibling()) {
422                                 if(string_iequals(param.name(), "input")) {
423                                         string name;
424                                         if(!xml_read_string(&name, param, "name"))
425                                                 continue;
426                                         
427                                         ShaderSocketType type = xml_read_socket_type(param, "type");
428                                         if(type == SHADER_SOCKET_UNDEFINED)
429                                                 continue;
430                                         
431                                         osl->input_names.push_back(ustring(name));
432                                         osl->add_input(osl->input_names.back().c_str(), type);
433                                 }
434                                 else if(string_iequals(param.name(), "output")) {
435                                         string name;
436                                         if(!xml_read_string(&name, param, "name"))
437                                                 continue;
438                                         
439                                         ShaderSocketType type = xml_read_socket_type(param, "type");
440                                         if(type == SHADER_SOCKET_UNDEFINED)
441                                                 continue;
442                                         
443                                         osl->output_names.push_back(ustring(name));
444                                         osl->add_output(osl->output_names.back().c_str(), type);
445                                 }
446                         }
447                         
448                         snode = osl;
449                 }
450                 else if(string_iequals(node.name(), "sky_texture")) {
451                         SkyTextureNode *sky = new SkyTextureNode();
452                         
453                         xml_read_enum(&sky->type, SkyTextureNode::type_enum, node, "type");
454                         xml_read_float3(&sky->sun_direction, node, "sun_direction");
455                         xml_read_float(&sky->turbidity, node, "turbidity");
456                         xml_read_float(&sky->ground_albedo, node, "ground_albedo");
457                         
458                         snode = sky;
459                 }
460                 else if(string_iequals(node.name(), "noise_texture")) {
461                         snode = new NoiseTextureNode();
462                 }
463                 else if(string_iequals(node.name(), "checker_texture")) {
464                         snode = new CheckerTextureNode();
465                 }
466                 else if(string_iequals(node.name(), "brick_texture")) {
467                         BrickTextureNode *brick = new BrickTextureNode();
468
469                         xml_read_float(&brick->offset, node, "offset");
470                         xml_read_int(&brick->offset_frequency, node, "offset_frequency");
471                         xml_read_float(&brick->squash, node, "squash");
472                         xml_read_int(&brick->squash_frequency, node, "squash_frequency");
473
474                         snode = brick;
475                 }
476                 else if(string_iequals(node.name(), "gradient_texture")) {
477                         GradientTextureNode *blend = new GradientTextureNode();
478                         xml_read_enum(&blend->type, GradientTextureNode::type_enum, node, "type");
479                         snode = blend;
480                 }
481                 else if(string_iequals(node.name(), "voronoi_texture")) {
482                         VoronoiTextureNode *voronoi = new VoronoiTextureNode();
483                         xml_read_enum(&voronoi->coloring, VoronoiTextureNode::coloring_enum, node, "coloring");
484                         snode = voronoi;
485                 }
486                 else if(string_iequals(node.name(), "musgrave_texture")) {
487                         MusgraveTextureNode *musgrave = new MusgraveTextureNode();
488                         xml_read_enum(&musgrave->type, MusgraveTextureNode::type_enum, node, "type");
489                         snode = musgrave;
490                 }
491                 else if(string_iequals(node.name(), "magic_texture")) {
492                         MagicTextureNode *magic = new MagicTextureNode();
493                         xml_read_int(&magic->depth, node, "depth");
494                         snode = magic;
495                 }
496                 else if(string_iequals(node.name(), "noise_texture")) {
497                         NoiseTextureNode *dist = new NoiseTextureNode();
498                         snode = dist;
499                 }
500                 else if(string_iequals(node.name(), "wave_texture")) {
501                         WaveTextureNode *wave = new WaveTextureNode();
502                         xml_read_enum(&wave->type, WaveTextureNode::type_enum, node, "type");
503                         snode = wave;
504                 }
505                 else if(string_iequals(node.name(), "normal")) {
506                         NormalNode *normal = new NormalNode();
507                         xml_read_float3(&normal->direction, node, "direction");
508                         snode = normal;
509                 }
510                 else if(string_iequals(node.name(), "mapping")) {
511                         snode = new MappingNode();
512                 }
513                 else if(string_iequals(node.name(), "anisotropic_bsdf")) {
514                         AnisotropicBsdfNode *aniso = new AnisotropicBsdfNode();
515                         xml_read_enum(&aniso->distribution, AnisotropicBsdfNode::distribution_enum, node, "distribution");
516                         snode = aniso;
517                 }
518                 else if(string_iequals(node.name(), "diffuse_bsdf")) {
519                         snode = new DiffuseBsdfNode();
520                 }
521                 else if(string_iequals(node.name(), "translucent_bsdf")) {
522                         snode = new TranslucentBsdfNode();
523                 }
524                 else if(string_iequals(node.name(), "transparent_bsdf")) {
525                         snode = new TransparentBsdfNode();
526                 }
527                 else if(string_iequals(node.name(), "velvet_bsdf")) {
528                         snode = new VelvetBsdfNode();
529                 }
530                 else if(string_iequals(node.name(), "toon_bsdf")) {
531                         ToonBsdfNode *toon = new ToonBsdfNode();
532                         xml_read_enum(&toon->component, ToonBsdfNode::component_enum, node, "component");
533                         snode = toon;
534                 }
535                 else if(string_iequals(node.name(), "glossy_bsdf")) {
536                         GlossyBsdfNode *glossy = new GlossyBsdfNode();
537                         xml_read_enum(&glossy->distribution, GlossyBsdfNode::distribution_enum, node, "distribution");
538                         snode = glossy;
539                 }
540                 else if(string_iequals(node.name(), "glass_bsdf")) {
541                         GlassBsdfNode *diel = new GlassBsdfNode();
542                         xml_read_enum(&diel->distribution, GlassBsdfNode::distribution_enum, node, "distribution");
543                         snode = diel;
544                 }
545                 else if(string_iequals(node.name(), "refraction_bsdf")) {
546                         RefractionBsdfNode *diel = new RefractionBsdfNode();
547                         xml_read_enum(&diel->distribution, RefractionBsdfNode::distribution_enum, node, "distribution");
548                         snode = diel;
549                 }
550                 else if(string_iequals(node.name(), "hair_bsdf")) {
551                         HairBsdfNode *hair = new HairBsdfNode();
552                         xml_read_enum(&hair->component, HairBsdfNode::component_enum, node, "component");
553                         snode = hair;
554                 }
555                 else if(string_iequals(node.name(), "emission")) {
556                         snode = new EmissionNode();
557                 }
558                 else if(string_iequals(node.name(), "ambient_occlusion")) {
559                         snode = new AmbientOcclusionNode();
560                 }
561                 else if(string_iequals(node.name(), "background")) {
562                         snode = new BackgroundNode();
563                 }
564                 else if(string_iequals(node.name(), "absorption_volume")) {
565                         snode = new AbsorptionVolumeNode();
566                 }
567                 else if(string_iequals(node.name(), "scatter_volume")) {
568                         snode = new ScatterVolumeNode();
569                 }
570                 else if(string_iequals(node.name(), "subsurface_scattering")) {
571                         SubsurfaceScatteringNode *sss = new SubsurfaceScatteringNode();
572                         //xml_read_enum(&sss->falloff, SubsurfaceScatteringNode::falloff_enum, node, "falloff");
573                         snode = sss;
574                 }
575                 else if(string_iequals(node.name(), "geometry")) {
576                         snode = new GeometryNode();
577                 }
578                 else if(string_iequals(node.name(), "texture_coordinate")) {
579                         snode = new TextureCoordinateNode();
580                 }
581                 else if(string_iequals(node.name(), "light_path")) {
582                         snode = new LightPathNode();
583                 }
584                 else if(string_iequals(node.name(), "light_falloff")) {
585                         snode = new LightFalloffNode();
586                 }
587                 else if(string_iequals(node.name(), "object_info")) {
588                         snode = new ObjectInfoNode();
589                 }
590                 else if(string_iequals(node.name(), "particle_info")) {
591                         snode = new ParticleInfoNode();
592                 }
593                 else if(string_iequals(node.name(), "hair_info")) {
594                         snode = new HairInfoNode();
595                 }
596                 else if(string_iequals(node.name(), "value")) {
597                         ValueNode *value = new ValueNode();
598                         xml_read_float(&value->value, node, "value");
599                         snode = value;
600                 }
601                 else if(string_iequals(node.name(), "color")) {
602                         ColorNode *color = new ColorNode();
603                         xml_read_float3(&color->value, node, "value");
604                         snode = color;
605                 }
606                 else if(string_iequals(node.name(), "mix_closure")) {
607                         snode = new MixClosureNode();
608                 }
609                 else if(string_iequals(node.name(), "add_closure")) {
610                         snode = new AddClosureNode();
611                 }
612                 else if(string_iequals(node.name(), "invert")) {
613                         snode = new InvertNode();
614                 }
615                 else if(string_iequals(node.name(), "mix")) {
616                         MixNode *mix = new MixNode();
617                         xml_read_enum(&mix->type, MixNode::type_enum, node, "type");
618                         xml_read_bool(&mix->use_clamp, node, "use_clamp");
619                         snode = mix;
620                 }
621                 else if(string_iequals(node.name(), "gamma")) {
622                         snode = new GammaNode();
623                 }
624                 else if(string_iequals(node.name(), "brightness")) {
625                         snode = new BrightContrastNode();
626                 }
627                 else if(string_iequals(node.name(), "combine_rgb")) {
628                         snode = new CombineRGBNode();
629                 }
630                 else if(string_iequals(node.name(), "separate_rgb")) {
631                         snode = new SeparateRGBNode();
632                 }
633                 else if(string_iequals(node.name(), "combine_hsv")) {
634                         snode = new CombineHSVNode();
635                 }
636                 else if(string_iequals(node.name(), "separate_hsv")) {
637                         snode = new SeparateHSVNode();
638                 }
639                 else if(string_iequals(node.name(), "combine_xyz")) {
640                         snode = new CombineHSVNode();
641                 }
642                 else if(string_iequals(node.name(), "separate_xyz")) {
643                         snode = new SeparateHSVNode();
644                 }
645                 else if(string_iequals(node.name(), "hsv")) {
646                         snode = new HSVNode();
647                 }
648                 else if(string_iequals(node.name(), "wavelength")) {
649                         snode = new WavelengthNode();
650                 }
651                 else if(string_iequals(node.name(), "blackbody")) {
652                         snode = new BlackbodyNode();
653                 }
654                 else if(string_iequals(node.name(), "attribute")) {
655                         AttributeNode *attr = new AttributeNode();
656                         xml_read_ustring(&attr->attribute, node, "attribute");
657                         snode = attr;
658                 }
659                 else if(string_iequals(node.name(), "uv_map")) {
660                         UVMapNode *uvm = new UVMapNode();
661                         xml_read_ustring(&uvm->attribute, node, "uv_map");
662                         snode = uvm;
663                 }
664                 else if(string_iequals(node.name(), "camera")) {
665                         snode = new CameraNode();
666                 }
667                 else if(string_iequals(node.name(), "fresnel")) {
668                         snode = new FresnelNode();
669                 }
670                 else if(string_iequals(node.name(), "layer_weight")) {
671                         snode = new LayerWeightNode();
672                 }
673                 else if(string_iequals(node.name(), "wireframe")) {
674                         WireframeNode *wire = new WireframeNode;
675                         xml_read_bool(&wire->use_pixel_size, node, "use_pixel_size");
676                         snode = wire;
677                 }
678                 else if(string_iequals(node.name(), "normal_map")) {
679                         NormalMapNode *nmap = new NormalMapNode;
680                         xml_read_ustring(&nmap->attribute, node, "attribute");
681                         xml_read_enum(&nmap->space, NormalMapNode::space_enum, node, "space");
682                         snode = nmap;
683                 }
684                 else if(string_iequals(node.name(), "tangent")) {
685                         TangentNode *tangent = new TangentNode;
686                         xml_read_ustring(&tangent->attribute, node, "attribute");
687                         xml_read_enum(&tangent->direction_type, TangentNode::direction_type_enum, node, "direction_type");
688                         xml_read_enum(&tangent->axis, TangentNode::axis_enum, node, "axis");
689                         snode = tangent;
690                 }
691                 else if(string_iequals(node.name(), "math")) {
692                         MathNode *math = new MathNode();
693                         xml_read_enum(&math->type, MathNode::type_enum, node, "type");
694                         xml_read_bool(&math->use_clamp, node, "use_clamp");
695                         snode = math;
696                 }
697                 else if(string_iequals(node.name(), "vector_math")) {
698                         VectorMathNode *vmath = new VectorMathNode();
699                         xml_read_enum(&vmath->type, VectorMathNode::type_enum, node, "type");
700                         snode = vmath;
701                 }
702                 else if(string_iequals(node.name(), "vector_transform")) {
703                         VectorTransformNode *vtransform = new VectorTransformNode();
704                         xml_read_enum(&vtransform->type, VectorTransformNode::type_enum, node, "type");
705                         xml_read_enum(&vtransform->convert_from, VectorTransformNode::convert_space_enum, node, "convert_from");
706                         xml_read_enum(&vtransform->convert_to, VectorTransformNode::convert_space_enum, node, "convert_to");
707                         snode = vtransform;
708                 }
709                 else if(string_iequals(node.name(), "connect")) {
710                         /* connect nodes */
711                         vector<string> from_tokens, to_tokens;
712
713                         string_split(from_tokens, node.attribute("from").value());
714                         string_split(to_tokens, node.attribute("to").value());
715
716                         if(from_tokens.size() == 2 && to_tokens.size() == 2) {
717                                 /* find nodes and sockets */
718                                 ShaderOutput *output = NULL;
719                                 ShaderInput *input = NULL;
720
721                                 if(nodemap.find(from_tokens[0]) != nodemap.end()) {
722                                         ShaderNode *fromnode = nodemap[from_tokens[0]];
723
724                                         foreach(ShaderOutput *out, fromnode->outputs)
725                                                 if(string_iequals(xml_socket_name(out->name), from_tokens[1]))
726                                                         output = out;
727
728                                         if(!output)
729                                                 fprintf(stderr, "Unknown output socket name \"%s\" on \"%s\".\n", from_tokens[1].c_str(), from_tokens[0].c_str());
730                                 }
731                                 else
732                                         fprintf(stderr, "Unknown shader node name \"%s\".\n", from_tokens[0].c_str());
733
734                                 if(nodemap.find(to_tokens[0]) != nodemap.end()) {
735                                         ShaderNode *tonode = nodemap[to_tokens[0]];
736
737                                         foreach(ShaderInput *in, tonode->inputs)
738                                                 if(string_iequals(xml_socket_name(in->name), to_tokens[1]))
739                                                         input = in;
740
741                                         if(!input)
742                                                 fprintf(stderr, "Unknown input socket name \"%s\" on \"%s\".\n", to_tokens[1].c_str(), to_tokens[0].c_str());
743                                 }
744                                 else
745                                         fprintf(stderr, "Unknown shader node name \"%s\".\n", to_tokens[0].c_str());
746
747                                 /* connect */
748                                 if(output && input)
749                                         graph->connect(output, input);
750                         }
751                         else
752                                 fprintf(stderr, "Invalid from or to value for connect node.\n");
753                 }
754                 else
755                         fprintf(stderr, "Unknown shader node \"%s\".\n", node.name());
756
757                 if(snode) {
758                         /* add to graph */
759                         graph->add(snode);
760
761                         /* add to map for name lookups */
762                         string name = "";
763                         xml_read_string(&name, node, "name");
764
765                         nodemap[name] = snode;
766
767                         /* read input values */
768                         for(pugi::xml_attribute attr = node.first_attribute(); attr; attr = attr.next_attribute()) {
769                                 foreach(ShaderInput *in, snode->inputs) {
770                                         if(string_iequals(in->name, attr.name())) {
771                                                 switch(in->type) {
772                                                         case SHADER_SOCKET_FLOAT:
773                                                         case SHADER_SOCKET_INT:
774                                                                 xml_read_float(&in->value.x, node, attr.name());
775                                                                 break;
776                                                         case SHADER_SOCKET_COLOR:
777                                                         case SHADER_SOCKET_VECTOR:
778                                                         case SHADER_SOCKET_POINT:
779                                                         case SHADER_SOCKET_NORMAL:
780                                                                 xml_read_float3(&in->value, node, attr.name());
781                                                                 break;
782                                                         case SHADER_SOCKET_STRING:
783                                                                 xml_read_ustring( &in->value_string, node, attr.name() );
784                                                                 break;
785                                                         default:
786                                                                 break;
787                                                 }
788                                         }
789                                 }
790                         }
791                 }
792         }
793
794         shader->set_graph(graph);
795         shader->tag_update(state.scene);
796 }
797
798 static void xml_read_shader(const XMLReadState& state, pugi::xml_node node)
799 {
800         Shader *shader = new Shader();
801
802         xml_read_string(&shader->name, node, "name");
803         xml_read_bool(&shader->use_mis, node, "use_mis");
804         xml_read_bool(&shader->use_transparent_shadow, node, "use_transparent_shadow");
805
806         /* Volume */
807         xml_read_bool(&shader->heterogeneous_volume, node, "heterogeneous_volume");
808         xml_read_int(&shader->volume_interpolation_method, node, "volume_interpolation_method");
809
810         if(xml_equal_string(node, "volume_sampling_method", "distance"))
811                 shader->volume_sampling_method = VOLUME_SAMPLING_DISTANCE;
812         else if(xml_equal_string(node, "volume_sampling_method", "equiangular"))
813                 shader->volume_sampling_method = VOLUME_SAMPLING_EQUIANGULAR;
814         else if(xml_equal_string(node, "volume_sampling_method", "multiple_importance"))
815                 shader->volume_sampling_method = VOLUME_SAMPLING_MULTIPLE_IMPORTANCE;
816
817         xml_read_shader_graph(state, shader, node);
818         state.scene->shaders.push_back(shader);
819 }
820
821 /* Background */
822
823 static void xml_read_background(const XMLReadState& state, pugi::xml_node node)
824 {
825         Shader *shader = state.scene->shaders[state.scene->default_background];
826         
827         xml_read_bool(&shader->heterogeneous_volume, node, "heterogeneous_volume");
828         xml_read_int(&shader->volume_interpolation_method, node, "volume_interpolation_method");
829
830         if(xml_equal_string(node, "volume_sampling_method", "distance"))
831                 shader->volume_sampling_method = VOLUME_SAMPLING_DISTANCE;
832         else if(xml_equal_string(node, "volume_sampling_method", "equiangular"))
833                 shader->volume_sampling_method = VOLUME_SAMPLING_EQUIANGULAR;
834         else if(xml_equal_string(node, "volume_sampling_method", "multiple_importance"))
835                 shader->volume_sampling_method = VOLUME_SAMPLING_MULTIPLE_IMPORTANCE;
836
837         xml_read_shader_graph(state, shader, node);
838 }
839
840 /* Mesh */
841
842 static Mesh *xml_add_mesh(Scene *scene, const Transform& tfm)
843 {
844         /* create mesh */
845         Mesh *mesh = new Mesh();
846         scene->meshes.push_back(mesh);
847
848         /* create object*/
849         Object *object = new Object();
850         object->mesh = mesh;
851         object->tfm = tfm;
852         scene->objects.push_back(object);
853
854         return mesh;
855 }
856
857 static void xml_read_mesh(const XMLReadState& state, pugi::xml_node node)
858 {
859         /* add mesh */
860         Mesh *mesh = xml_add_mesh(state.scene, state.tfm);
861         mesh->used_shaders.push_back(state.shader);
862
863         /* read state */
864         int shader = state.shader;
865         bool smooth = state.smooth;
866
867         mesh->displacement_method = state.displacement_method;
868
869         /* read vertices and polygons, RIB style */
870         vector<float3> P;
871         vector<int> verts, nverts;
872
873         xml_read_float3_array(P, node, "P");
874         xml_read_int_array(verts, node, "verts");
875         xml_read_int_array(nverts, node, "nverts");
876
877         if(xml_equal_string(node, "subdivision", "catmull-clark")) {
878                 /* create subd mesh */
879                 SubdMesh sdmesh;
880
881                 /* create subd vertices */
882                 for(size_t i = 0; i < P.size(); i++)
883                         sdmesh.add_vert(P[i]);
884
885                 /* create subd faces */
886                 int index_offset = 0;
887
888                 for(size_t i = 0; i < nverts.size(); i++) {
889                         if(nverts[i] == 4) {
890                                 int v0 = verts[index_offset + 0];
891                                 int v1 = verts[index_offset + 1];
892                                 int v2 = verts[index_offset + 2];
893                                 int v3 = verts[index_offset + 3];
894
895                                 sdmesh.add_face(v0, v1, v2, v3);
896                         }
897                         else {
898                                 for(int j = 0; j < nverts[i]-2; j++) {
899                                         int v0 = verts[index_offset];
900                                         int v1 = verts[index_offset + j + 1];
901                                         int v2 = verts[index_offset + j + 2];
902
903                                         sdmesh.add_face(v0, v1, v2);
904                                 }
905                         }
906
907                         index_offset += nverts[i];
908                 }
909
910                 /* finalize subd mesh */
911                 sdmesh.finish();
912
913                 /* parameters */
914                 SubdParams sdparams(mesh, shader, smooth);
915                 xml_read_float(&sdparams.dicing_rate, node, "dicing_rate");
916
917                 DiagSplit dsplit(sdparams);
918                 sdmesh.tessellate(&dsplit);
919         }
920         else {
921                 /* create vertices */
922                 mesh->verts = P;
923
924                 /* create triangles */
925                 int index_offset = 0;
926
927                 for(size_t i = 0; i < nverts.size(); i++) {
928                         for(int j = 0; j < nverts[i]-2; j++) {
929                                 int v0 = verts[index_offset];
930                                 int v1 = verts[index_offset + j + 1];
931                                 int v2 = verts[index_offset + j + 2];
932
933                                 assert(v0 < (int)P.size());
934                                 assert(v1 < (int)P.size());
935                                 assert(v2 < (int)P.size());
936
937                                 mesh->add_triangle(v0, v1, v2, shader, smooth);
938                         }
939
940                         index_offset += nverts[i];
941                 }
942         }
943
944         /* temporary for test compatibility */
945         mesh->attributes.remove(ATTR_STD_VERTEX_NORMAL);
946 }
947
948 /* Patch */
949
950 static void xml_read_patch(const XMLReadState& state, pugi::xml_node node)
951 {
952         /* read patch */
953         Patch *patch = NULL;
954
955         vector<float3> P;
956         xml_read_float3_array(P, node, "P");
957
958         if(xml_equal_string(node, "type", "bilinear")) {
959                 /* bilinear patch */
960                 if(P.size() == 4) {
961                         LinearQuadPatch *bpatch = new LinearQuadPatch();
962
963                         for(int i = 0; i < 4; i++)
964                                 P[i] = transform_point(&state.tfm, P[i]);
965                         memcpy(bpatch->hull, &P[0], sizeof(bpatch->hull));
966
967                         patch = bpatch;
968                 }
969                 else
970                         fprintf(stderr, "Invalid number of control points for bilinear patch.\n");
971         }
972         else if(xml_equal_string(node, "type", "bicubic")) {
973                 /* bicubic patch */
974                 if(P.size() == 16) {
975                         BicubicPatch *bpatch = new BicubicPatch();
976
977                         for(int i = 0; i < 16; i++)
978                                 P[i] = transform_point(&state.tfm, P[i]);
979                         memcpy(bpatch->hull, &P[0], sizeof(bpatch->hull));
980
981                         patch = bpatch;
982                 }
983                 else
984                         fprintf(stderr, "Invalid number of control points for bicubic patch.\n");
985         }
986         else
987                 fprintf(stderr, "Unknown patch type.\n");
988
989         if(patch) {
990                 /* add mesh */
991                 Mesh *mesh = xml_add_mesh(state.scene, transform_identity());
992
993                 mesh->used_shaders.push_back(state.shader);
994
995                 /* split */
996                 SubdParams sdparams(mesh, state.shader, state.smooth);
997                 xml_read_float(&sdparams.dicing_rate, node, "dicing_rate");
998
999                 DiagSplit dsplit(sdparams);
1000                 dsplit.split_quad(patch);
1001
1002                 delete patch;
1003
1004                 /* temporary for test compatibility */
1005                 mesh->attributes.remove(ATTR_STD_VERTEX_NORMAL);
1006         }
1007 }
1008
1009 /* Light */
1010
1011 static void xml_read_light(const XMLReadState& state, pugi::xml_node node)
1012 {
1013         Light *light = new Light();
1014         light->shader = state.shader;
1015
1016         /* Light Type
1017          * 0: Point, 1: Sun, 3: Area, 5: Spot */
1018         int type = 0;
1019         xml_read_int(&type, node, "type");
1020         light->type = (LightType)type;
1021
1022         /* Spot Light */
1023         xml_read_float(&light->spot_angle, node, "spot_angle");
1024         xml_read_float(&light->spot_smooth, node, "spot_smooth");
1025
1026         /* Area Light */
1027         xml_read_float(&light->sizeu, node, "sizeu");
1028         xml_read_float(&light->sizev, node, "sizev");
1029         xml_read_float3(&light->axisu, node, "axisu");
1030         xml_read_float3(&light->axisv, node, "axisv");
1031         
1032         /* Generic */
1033         xml_read_float(&light->size, node, "size");
1034         xml_read_float3(&light->dir, node, "dir");
1035         xml_read_float3(&light->co, node, "P");
1036         light->co = transform_point(&state.tfm, light->co);
1037
1038         state.scene->lights.push_back(light);
1039 }
1040
1041 /* Transform */
1042
1043 static void xml_read_transform(pugi::xml_node node, Transform& tfm)
1044 {
1045         if(node.attribute("matrix")) {
1046                 vector<float> matrix;
1047                 if(xml_read_float_array(matrix, node, "matrix") && matrix.size() == 16)
1048                         tfm = tfm * transform_transpose((*(Transform*)&matrix[0]));
1049         }
1050
1051         if(node.attribute("translate")) {
1052                 float3 translate = make_float3(0.0f, 0.0f, 0.0f);
1053                 xml_read_float3(&translate, node, "translate");
1054                 tfm = tfm * transform_translate(translate);
1055         }
1056
1057         if(node.attribute("rotate")) {
1058                 float4 rotate = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
1059                 xml_read_float4(&rotate, node, "rotate");
1060                 tfm = tfm * transform_rotate(DEG2RADF(rotate.x), make_float3(rotate.y, rotate.z, rotate.w));
1061         }
1062
1063         if(node.attribute("scale")) {
1064                 float3 scale = make_float3(0.0f, 0.0f, 0.0f);
1065                 xml_read_float3(&scale, node, "scale");
1066                 tfm = tfm * transform_scale(scale);
1067         }
1068 }
1069
1070 /* State */
1071
1072 static void xml_read_state(XMLReadState& state, pugi::xml_node node)
1073 {
1074         /* read shader */
1075         string shadername;
1076
1077         if(xml_read_string(&shadername, node, "shader")) {
1078                 int i = 0;
1079                 bool found = false;
1080
1081                 foreach(Shader *shader, state.scene->shaders) {
1082                         if(shader->name == shadername) {
1083                                 state.shader = i;
1084                                 found = true;
1085                                 break;
1086                         }
1087
1088                         i++;
1089                 }
1090
1091                 if(!found)
1092                         fprintf(stderr, "Unknown shader \"%s\".\n", shadername.c_str());
1093         }
1094
1095         xml_read_float(&state.dicing_rate, node, "dicing_rate");
1096
1097         /* read smooth/flat */
1098         if(xml_equal_string(node, "interpolation", "smooth"))
1099                 state.smooth = true;
1100         else if(xml_equal_string(node, "interpolation", "flat"))
1101                 state.smooth = false;
1102
1103         /* read displacement method */
1104         if(xml_equal_string(node, "displacement_method", "true"))
1105                 state.displacement_method = Mesh::DISPLACE_TRUE;
1106         else if(xml_equal_string(node, "displacement_method", "bump"))
1107                 state.displacement_method = Mesh::DISPLACE_BUMP;
1108         else if(xml_equal_string(node, "displacement_method", "both"))
1109                 state.displacement_method = Mesh::DISPLACE_BOTH;
1110 }
1111
1112 /* Scene */
1113
1114 static void xml_read_include(const XMLReadState& state, const string& src);
1115
1116 static void xml_read_scene(const XMLReadState& state, pugi::xml_node scene_node)
1117 {
1118         for(pugi::xml_node node = scene_node.first_child(); node; node = node.next_sibling()) {
1119                 if(string_iequals(node.name(), "film")) {
1120                         xml_read_film(state, node);
1121                 }
1122                 else if(string_iequals(node.name(), "integrator")) {
1123                         xml_read_integrator(state, node);
1124                 }
1125                 else if(string_iequals(node.name(), "camera")) {
1126                         xml_read_camera(state, node);
1127                 }
1128                 else if(string_iequals(node.name(), "shader")) {
1129                         xml_read_shader(state, node);
1130                 }
1131                 else if(string_iequals(node.name(), "background")) {
1132                         xml_read_background(state, node);
1133                 }
1134                 else if(string_iequals(node.name(), "mesh")) {
1135                         xml_read_mesh(state, node);
1136                 }
1137                 else if(string_iequals(node.name(), "patch")) {
1138                         xml_read_patch(state, node);
1139                 }
1140                 else if(string_iequals(node.name(), "light")) {
1141                         xml_read_light(state, node);
1142                 }
1143                 else if(string_iequals(node.name(), "transform")) {
1144                         XMLReadState substate = state;
1145
1146                         xml_read_transform(node, substate.tfm);
1147                         xml_read_scene(substate, node);
1148                 }
1149                 else if(string_iequals(node.name(), "state")) {
1150                         XMLReadState substate = state;
1151
1152                         xml_read_state(substate, node);
1153                         xml_read_scene(substate, node);
1154                 }
1155                 else if(string_iequals(node.name(), "include")) {
1156                         string src;
1157
1158                         if(xml_read_string(&src, node, "src"))
1159                                 xml_read_include(state, src);
1160                 }
1161                 else
1162                         fprintf(stderr, "Unknown node \"%s\".\n", node.name());
1163         }
1164 }
1165
1166 /* Include */
1167
1168 static void xml_read_include(const XMLReadState& state, const string& src)
1169 {
1170         /* open XML document */
1171         pugi::xml_document doc;
1172         pugi::xml_parse_result parse_result;
1173
1174         string path = path_join(state.base, src);
1175         parse_result = doc.load_file(path.c_str());
1176
1177         if(parse_result) {
1178                 XMLReadState substate = state;
1179                 substate.base = path_dirname(path);
1180
1181                 xml_read_scene(substate, doc);
1182         }
1183         else {
1184                 fprintf(stderr, "%s read error: %s\n", src.c_str(), parse_result.description());
1185                 exit(EXIT_FAILURE);
1186         }
1187 }
1188
1189 /* File */
1190
1191 void xml_read_file(Scene *scene, const char *filepath)
1192 {
1193         XMLReadState state;
1194
1195         state.scene = scene;
1196         state.tfm = transform_identity();
1197         state.shader = scene->default_surface;
1198         state.smooth = false;
1199         state.dicing_rate = 0.1f;
1200         state.base = path_dirname(filepath);
1201
1202         xml_read_include(state, path_filename(filepath));
1203
1204         scene->params.bvh_type = SceneParams::BVH_STATIC;
1205 }
1206
1207 CCL_NAMESPACE_END
1208