16 : mContext(
C), material(ma), effect(
nullptr), key_image_map(&key_image_map)
18 bNodeTree *new_ntree = prepare_material_nodetree();
23 add_link(shader_node, 0, output_node, 0);
28 COLLADAFW::EffectCommon *ef,
31 : mContext(
C), material(ma), effect(ef), uid_image_map(&uid_image_map)
33 prepare_material_nodetree();
36 std::map<std::string, bNode *> nmap;
46 add_link(ntree, nmap[
"emission"], 0, nmap[
"add"], 0);
47 add_link(ntree, nmap[
"main"], 0, nmap[
"add"], 1);
48 add_link(ntree, nmap[
"add"], 0, nmap[
"mix"], 1);
49 add_link(ntree, nmap[
"transparent"], 0, nmap[
"mix"], 2);
51 add_link(ntree, nmap[
"mix"], 0, nmap[
"out"], 0);
53 make_group(
C, ntree, nmap);
57 add_link(shader_node, 0, output_node, 0);
61void MaterialNode::setShaderType()
64 COLLADAFW::EffectCommon::ShaderType shader = ef->getShaderType();
69 if (shader == COLLADAFW::EffectCommon::SHADER_BLINN) {
70 ma->spec_shader = MA_SPEC_BLINN;
71 ma->spec = ef->getShininess().getFloatValue();
74 else if (shader == COLLADAFW::EffectCommon::SHADER_PHONG) {
75 ma->spec_shader = MA_SPEC_PHONG;
76 ma->har = ef->getShininess().getFloatValue();
79 else if (shader == COLLADAFW::EffectCommon::SHADER_LAMBERT) {
80 ma->diff_shader = MA_DIFF_LAMBERT;
84 ma->diff_shader = MA_DIFF_LAMBERT;
85 fprintf(stderr,
"Current shader type is not supported, default to lambert.\n");
90bNodeTree *MaterialNode::prepare_material_nodetree()
92 if (material->nodetree) {
93 ntree = material->nodetree;
98 nullptr, &material->id,
"Shader Nodetree",
"ShaderNodeTree");
99 material->use_nodes =
true;
100 ntree = material->nodetree;
109bNode *MaterialNode::add_node(
int node_type,
int locx,
int locy, std::string label)
113 if (label.length() > 0) {
120 node_map[label] = node;
124void MaterialNode::add_link(
bNode *from_node,
int from_index,
bNode *to_node,
int to_index)
132void MaterialNode::add_link(
bNode *from_node,
133 const char *from_label,
135 const char *to_label)
140 if (from_socket && to_socket) {
147 float reflectivity = val.getFloatValue();
148 if (reflectivity >= 0) {
151 material->metallic = reflectivity;
159 float roughness = val.getFloatValue();
160 if (roughness >= 0) {
169 float ior = val.getFloatValue();
172 "IOR of negative value is not allowed for materials (using Blender default value "
182 COLLADAFW::ColorOrTexture &cot,
183 COLLADAFW::FloatOrParam &val)
188 if (effect ==
nullptr) {
192 if (cot.isColor() || !cot.isValid()) {
195 float transparent_alpha;
197 COLLADAFW::Color
col = cot.getColor();
198 transparent_alpha =
col.getAlpha();
202 transparent_alpha = 1;
205 float transparency_alpha = val.getFloatValue();
206 if (transparency_alpha < 0) {
208 transparency_alpha = 1;
211 float alpha = transparent_alpha * transparency_alpha;
212 if (mode == COLLADAFW::EffectCommon::RGB_ZERO) {
220 else if (cot.isTexture()) {
221 int locy = -300 * (node_map.size() - 2);
222 add_texture_node(cot, -300, locy,
"Alpha");
228 int locy = -300 * (node_map.size() - 2);
230 if (cot.isTexture()) {
231 bNode *texture_node = add_texture_node(cot, -300, locy,
"Base Color");
232 if (texture_node !=
nullptr) {
233 add_link(texture_node, 0, shader_node, 0);
241 COLLADAFW::Color
col = cot.getColor();
242 fcol[0] = material->r =
col.getRed();
243 fcol[1] = material->g =
col.getGreen();
244 fcol[2] = material->b =
col.getBlue();
245 fcol[3] = material->a =
col.getAlpha();
249 fcol[0] = material->r = 0.0f;
250 fcol[1] = material->g = 0.0f;
251 fcol[2] = material->b = 0.0f;
252 fcol[3] = material->a = 1.0f;
259 ntree->ensure_topology_cache();
267 if (in_socket ==
nullptr) {
272 if (link ==
nullptr) {
293 fcol[0] =
col.getRed();
294 fcol[1] =
col.getGreen();
295 fcol[2] =
col.getBlue();
302 int locy = -300 * (node_map.size() - 2);
304 COLLADAFW::Color
col = cot.getColor();
310 else if (cot.isTexture()) {
311 add_texture_node(cot, -300, locy,
"Ambient");
318 int locy = -300 * (node_map.size() - 2);
320 COLLADAFW::Color
col = cot.getColor();
326 else if (cot.isTexture()) {
327 add_texture_node(cot, -300, locy,
"Reflective");
334 int locy = -300 * (node_map.size() - 2);
336 COLLADAFW::Color
col = cot.getColor();
340 fcol[0] =
col.getRed();
341 fcol[1] =
col.getGreen();
342 fcol[2] =
col.getBlue();
343 fcol[3] =
col.getAlpha();
346 else if (cot.isTexture()) {
347 bNode *texture_node = add_texture_node(cot, -300, locy,
"Emission Color");
348 if (texture_node !=
nullptr) {
349 add_link(texture_node,
"Color", shader_node,
"Emission Color");
361 if (effect ==
nullptr) {
365 int locy = -300 * (node_map.size() - 2);
367 COLLADAFW::Color
col = effect->getTransparent().getColor();
368 float alpha = effect->getTransparency().getFloatValue();
371 alpha *=
col.getAlpha();
378 else if (cot.isTexture()) {
379 add_texture_node(cot, -300, locy,
"Alpha");
386 bool has_specularity =
true;
387 int locy = -300 * (node_map.size() - 2);
389 COLLADAFW::Color
col = cot.getColor();
391 if (
col.getRed() == 0 &&
col.getGreen() == 0 &&
col.getBlue() == 0) {
392 has_specularity =
false;
400 else if (cot.isTexture()) {
401 add_texture_node(cot, -300, locy,
"Specular IOR Level");
406 has_specularity =
false;
409 if (!has_specularity) {
415 *shader_node,
SOCK_IN,
"Specular IOR Level");
420bNode *MaterialNode::add_texture_node(COLLADAFW::ColorOrTexture &cot,
425 if (effect ==
nullptr) {
431 COLLADAFW::Texture ctex = cot.getTexture();
433 COLLADAFW::SamplerPointerArray &samp_array = effect->getSamplerPointerArray();
434 COLLADAFW::Sampler *sampler = samp_array[ctex.getSamplerId()];
436 const COLLADAFW::UniqueId &ima_uid = sampler->getSourceImage();
438 if (image_map.find(ima_uid) == image_map.end()) {
439 fprintf(stderr,
"Couldn't find an image by UID.\n");
443 Image *ima = image_map[ima_uid];
445 texture_node->
id = &ima->
id;
Main * CTX_data_main(const bContext *C)
#define SH_NODE_MIX_SHADER
#define SH_NODE_TEX_IMAGE
#define SH_NODE_BSDF_PRINCIPLED
#define SH_NODE_ADD_SHADER
#define SH_NODE_BSDF_TRANSPARENT
#define SH_NODE_OUTPUT_MATERIAL
void BKE_ntree_update_after_single_tree_change(Main &bmain, bNodeTree &modified_tree, const NodeTreeUpdateExtraParams ¶ms={})
void * BLI_findlink(const ListBase *listbase, int number) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
char * STRNCPY(char(&dst)[N], const char *src)
struct bNodeSocket bNodeSocket
static bNodeSocket * set_color(bNode *node, COLLADAFW::Color col)
void set_reflectivity(COLLADAFW::FloatOrParam &val)
void set_shininess(COLLADAFW::FloatOrParam &val)
void set_specular(COLLADAFW::ColorOrTexture &cot)
void update_material_nodetree()
void set_ior(COLLADAFW::FloatOrParam &val)
void set_reflective(COLLADAFW::ColorOrTexture &cot)
void set_emission(COLLADAFW::ColorOrTexture &cot)
Image * get_diffuse_image()
MaterialNode(bContext *C, COLLADAFW::EffectCommon *ef, Material *ma, UidImageMap &uid_image_map)
void set_opacity(COLLADAFW::ColorOrTexture &cot)
void set_alpha(COLLADAFW::EffectCommon::OpaqueMode mode, COLLADAFW::ColorOrTexture &cot, COLLADAFW::FloatOrParam &val)
void set_diffuse(COLLADAFW::ColorOrTexture &cot)
void set_ambient(COLLADAFW::ColorOrTexture &cot)
constexpr const T & first() const
constexpr bool is_empty() const
std::map< std::string, Image * > KeyImageMap
std::map< COLLADAFW::UniqueId, Image * > UidImageMap
TEX_TEMPLATE DataVec texture(T, FltCoord, float=0.0f) RET
bNodeTree * node_tree_add_tree_embedded(Main *bmain, ID *owner_id, StringRefNull name, StringRefNull idname)
bNodeSocket * node_find_socket(bNode &node, eNodeSocketInOut in_out, StringRef identifier)
bNode * node_add_static_node(const bContext *C, bNodeTree &ntree, int type)
bNodeLink & node_add_link(bNodeTree &ntree, bNode &fromnode, bNodeSocket &fromsock, bNode &tonode, bNodeSocket &tosock)