00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include <lib3ds/material.h>
00023 #include <lib3ds/chunk.h>
00024 #include <lib3ds/io.h>
00025 #include <stdlib.h>
00026 #include <math.h>
00027 #include <string.h>
00028
00029
00035 static void
00036 initialize_texture_map(Lib3dsTextureMap *map)
00037 {
00038 map->flags = 0x10;
00039 map->percent = 1.0f;
00040 map->scale[0] = 1.0f;
00041 map->scale[1] = 1.0f;
00042 }
00043
00044
00055 Lib3dsMaterial*
00056 lib3ds_material_new()
00057 {
00058 Lib3dsMaterial *mat;
00059
00060 mat = (Lib3dsMaterial*)calloc(sizeof(Lib3dsMaterial), 1);
00061 if (!mat) {
00062 return(0);
00063 }
00064
00065 mat->ambient[0] = mat->ambient[1] = mat->ambient[2] = 0.588235f;
00066 mat->diffuse[0] = mat->diffuse[1] = mat->diffuse[2] = 0.588235f;
00067 mat->specular[0] = mat->specular[1] = mat->specular[2] = 0.898039f;
00068 mat->shininess = 0.1f;
00069 mat->wire_size = 1.0f;
00070 mat->shading = 3;
00071
00072 initialize_texture_map(&mat->texture1_map);
00073 initialize_texture_map(&mat->texture1_mask);
00074 initialize_texture_map(&mat->texture2_map);
00075 initialize_texture_map(&mat->texture2_mask);
00076 initialize_texture_map(&mat->opacity_map);
00077 initialize_texture_map(&mat->opacity_mask);
00078 initialize_texture_map(&mat->bump_map);
00079 initialize_texture_map(&mat->bump_mask);
00080 initialize_texture_map(&mat->specular_map);
00081 initialize_texture_map(&mat->specular_mask);
00082 initialize_texture_map(&mat->shininess_map);
00083 initialize_texture_map(&mat->shininess_mask);
00084 initialize_texture_map(&mat->self_illum_map);
00085 initialize_texture_map(&mat->self_illum_mask);
00086 initialize_texture_map(&mat->reflection_map);
00087 initialize_texture_map(&mat->reflection_mask);
00088
00089 return(mat);
00090 }
00091
00092
00096 void
00097 lib3ds_material_free(Lib3dsMaterial *material)
00098 {
00099 memset(material, 0, sizeof(Lib3dsMaterial));
00100 free(material);
00101 }
00102
00103
00104 static Lib3dsBool
00105 color_read(Lib3dsRgba rgb, Lib3dsIo *io)
00106 {
00107 Lib3dsChunk c;
00108 Lib3dsWord chunk;
00109 Lib3dsBool have_lin=LIB3DS_FALSE;
00110
00111 if (!lib3ds_chunk_read_start(&c, 0, io)) {
00112 return(LIB3DS_FALSE);
00113 }
00114
00115 while ((chunk=lib3ds_chunk_read_next(&c, io))!=0) {
00116 switch (chunk) {
00117 case LIB3DS_LIN_COLOR_24:
00118 {
00119 int i;
00120 for (i=0; i<3; ++i) {
00121 rgb[i]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00122 }
00123 rgb[3]=1.0f;
00124 }
00125 have_lin=LIB3DS_TRUE;
00126 break;
00127 case LIB3DS_COLOR_24:
00128
00129
00130 if (!have_lin) {
00131 int i;
00132 for (i=0; i<3; ++i) {
00133 rgb[i]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00134 }
00135 rgb[3]=1.0f;
00136 }
00137 break;
00138 case LIB3DS_LIN_COLOR_F:
00139 {
00140 int i;
00141 for (i=0; i<3; ++i) {
00142 rgb[i]=lib3ds_io_read_float(io);
00143 }
00144 rgb[3]=1.0f;
00145 }
00146 have_lin=LIB3DS_TRUE;
00147 break;
00148 case LIB3DS_COLOR_F:
00149 if (!have_lin) {
00150 int i;
00151 for (i=0; i<3; ++i) {
00152 rgb[i]=lib3ds_io_read_float(io);
00153 }
00154 rgb[3]=1.0f;
00155 }
00156 break;
00157 default:
00158 lib3ds_chunk_unknown(chunk);
00159 }
00160 }
00161
00162 lib3ds_chunk_read_end(&c, io);
00163 return(LIB3DS_TRUE);
00164 }
00165
00166
00167 static Lib3dsBool
00168 int_percentage_read(Lib3dsFloat *p, Lib3dsIo *io)
00169 {
00170 Lib3dsChunk c;
00171 Lib3dsWord chunk;
00172
00173 if (!lib3ds_chunk_read_start(&c, 0, io)) {
00174 return(LIB3DS_FALSE);
00175 }
00176
00177 while ((chunk=lib3ds_chunk_read_next(&c, io))!=0) {
00178 switch (chunk) {
00179 case LIB3DS_INT_PERCENTAGE:
00180 {
00181 Lib3dsIntw i=lib3ds_io_read_intw(io);
00182 *p=(Lib3dsFloat)(1.0*i/100.0);
00183 }
00184 break;
00185 default:
00186 lib3ds_chunk_unknown(chunk);
00187 }
00188 }
00189
00190 lib3ds_chunk_read_end(&c, io);
00191 return(LIB3DS_TRUE);
00192 }
00193
00194
00195 static Lib3dsBool
00196 texture_map_read(Lib3dsTextureMap *map, Lib3dsIo *io)
00197 {
00198 Lib3dsChunk c;
00199 Lib3dsWord chunk;
00200
00201 if (!lib3ds_chunk_read_start(&c, 0, io)) {
00202 return(LIB3DS_FALSE);
00203 }
00204
00205 while ((chunk=lib3ds_chunk_read_next(&c, io))!=0) {
00206 switch (chunk) {
00207 case LIB3DS_INT_PERCENTAGE:
00208 {
00209 map->percent=1.0f*lib3ds_io_read_intw(io)/100.0f;
00210 }
00211 break;
00212 case LIB3DS_MAT_MAPNAME:
00213 {
00214 if (!lib3ds_io_read_string(io, map->name, 64)) {
00215 return(LIB3DS_FALSE);
00216 }
00217 lib3ds_chunk_dump_info(" NAME=%s", map->name);
00218 }
00219 break;
00220 case LIB3DS_MAT_MAP_TILING:
00221 {
00222 map->flags=lib3ds_io_read_word(io);
00223 }
00224 break;
00225 case LIB3DS_MAT_MAP_TEXBLUR:
00226 {
00227 map->blur=lib3ds_io_read_float(io);
00228 }
00229 break;
00230 case LIB3DS_MAT_MAP_USCALE:
00231 {
00232 map->scale[0]=lib3ds_io_read_float(io);
00233 }
00234 break;
00235 case LIB3DS_MAT_MAP_VSCALE:
00236 {
00237 map->scale[1]=lib3ds_io_read_float(io);
00238 }
00239 break;
00240 case LIB3DS_MAT_MAP_UOFFSET:
00241 {
00242 map->offset[0]=lib3ds_io_read_float(io);
00243 }
00244 break;
00245 case LIB3DS_MAT_MAP_VOFFSET:
00246 {
00247 map->offset[1]=lib3ds_io_read_float(io);
00248 }
00249 break;
00250 case LIB3DS_MAT_MAP_ANG:
00251 {
00252 map->rotation=lib3ds_io_read_float(io);
00253 }
00254 break;
00255 case LIB3DS_MAT_MAP_COL1:
00256 {
00257 map->tint_1[0]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00258 map->tint_1[1]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00259 map->tint_1[2]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00260 }
00261 break;
00262 case LIB3DS_MAT_MAP_COL2:
00263 {
00264 map->tint_2[0]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00265 map->tint_2[1]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00266 map->tint_2[2]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00267 }
00268 break;
00269 case LIB3DS_MAT_MAP_RCOL:
00270 {
00271 map->tint_r[0]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00272 map->tint_r[1]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00273 map->tint_r[2]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00274 }
00275 break;
00276 case LIB3DS_MAT_MAP_GCOL:
00277 {
00278 map->tint_g[0]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00279 map->tint_g[1]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00280 map->tint_g[2]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00281 }
00282 break;
00283 case LIB3DS_MAT_MAP_BCOL:
00284 {
00285 map->tint_b[0]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00286 map->tint_b[1]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00287 map->tint_b[2]=1.0f*lib3ds_io_read_byte(io)/255.0f;
00288 }
00289 break;
00290 default:
00291 lib3ds_chunk_unknown(chunk);
00292 }
00293 }
00294
00295 lib3ds_chunk_read_end(&c, io);
00296 return(LIB3DS_TRUE);
00297 }
00298
00299
00303 static void
00304 texture_dump(const char *maptype, Lib3dsTextureMap *texture)
00305 {
00306 ASSERT(texture);
00307 if (strlen(texture->name)==0) {
00308 return;
00309 }
00310 printf(" %s:\n", maptype);
00311 printf(" name: %s\n", texture->name);
00312 printf(" flags: %X\n", (unsigned)texture->flags);
00313 printf(" percent: %f\n", texture->percent);
00314 printf(" blur: %f\n", texture->blur);
00315 printf(" scale: (%f, %f)\n", texture->scale[0], texture->scale[1]);
00316 printf(" offset: (%f, %f)\n", texture->offset[0], texture->offset[1]);
00317 printf(" rotation: %f\n", texture->rotation);
00318 printf(" tint_1: (%f, %f, %f)\n",
00319 texture->tint_1[0], texture->tint_1[1], texture->tint_1[2]);
00320 printf(" tint_2: (%f, %f, %f)\n",
00321 texture->tint_2[0], texture->tint_2[1], texture->tint_2[2]);
00322 printf(" tint_r: (%f, %f, %f)\n",
00323 texture->tint_r[0], texture->tint_r[1], texture->tint_r[2]);
00324 printf(" tint_g: (%f, %f, %f)\n",
00325 texture->tint_g[0], texture->tint_g[1], texture->tint_g[2]);
00326 printf(" tint_b: (%f, %f, %f)\n",
00327 texture->tint_b[0], texture->tint_b[1], texture->tint_b[2]);
00328 }
00329
00330
00334 void
00335 lib3ds_material_dump(Lib3dsMaterial *material)
00336 {
00337 ASSERT(material);
00338 printf(" name: %s\n", material->name);
00339 printf(" ambient: (%f, %f, %f)\n",
00340 material->ambient[0], material->ambient[1], material->ambient[2]);
00341 printf(" diffuse: (%f, %f, %f)\n",
00342 material->diffuse[0], material->diffuse[1], material->diffuse[2]);
00343 printf(" specular: (%f, %f, %f)\n",
00344 material->specular[0], material->specular[1], material->specular[2]);
00345 printf(" shininess: %f\n", material->shininess);
00346 printf(" shin_strength: %f\n", material->shin_strength);
00347 printf(" use_blur: %s\n", material->use_blur ? "yes" : "no");
00348 printf(" blur: %f\n", material->blur);
00349 printf(" falloff: %f\n", material->falloff);
00350 printf(" additive: %s\n", material->additive ? "yes" : "no");
00351 printf(" use_falloff: %s\n", material->use_falloff ? "yes" : "no");
00352 printf(" self_illum: %s\n", material->self_illum ? "yes" : "no");
00353 printf(" self_ilpct: %f\n", material->self_ilpct);
00354 printf(" shading: %d\n", material->shading);
00355 printf(" soften: %s\n", material->soften ? "yes" : "no");
00356 printf(" face_map: %s\n", material->face_map ? "yes" : "no");
00357 printf(" two_sided: %s\n", material->two_sided ? "yes" : "no");
00358 printf(" map_decal: %s\n", material->map_decal ? "yes" : "no");
00359 printf(" use_wire: %s\n", material->use_wire ? "yes" : "no");
00360 printf(" use_wire_abs: %s\n", material->use_wire_abs ? "yes" : "no");
00361 printf(" wire_size: %f\n", material->wire_size);
00362 texture_dump("texture1_map", &material->texture1_map);
00363 texture_dump("texture1_mask", &material->texture1_mask);
00364 texture_dump("texture2_map", &material->texture2_map);
00365 texture_dump("texture2_mask", &material->texture2_mask);
00366 texture_dump("opacity_map", &material->opacity_map);
00367 texture_dump("opacity_mask", &material->opacity_mask);
00368 texture_dump("bump_map", &material->bump_map);
00369 texture_dump("bump_mask", &material->bump_mask);
00370 texture_dump("specular_map", &material->specular_map);
00371 texture_dump("specular_mask", &material->specular_mask);
00372 texture_dump("shininess_map", &material->shininess_map);
00373 texture_dump("shininess_mask", &material->shininess_mask);
00374 texture_dump("self_illum_map", &material->self_illum_map);
00375 texture_dump("self_illum_mask", &material->self_illum_mask);
00376 texture_dump("reflection_map", &material->reflection_map);
00377 texture_dump("reflection_mask", &material->reflection_mask);
00378 printf(" autorefl_map:\n");
00379 printf(" flags %X\n", (unsigned)material->autorefl_map.flags);
00380 printf(" level %d\n", (int)material->autorefl_map.level);
00381 printf(" size %d\n", (int)material->autorefl_map.size);
00382 printf(" frame_step %d\n", (int)material->autorefl_map.frame_step);
00383 printf("\n");
00384 }
00385
00386
00390 Lib3dsBool
00391 lib3ds_material_read(Lib3dsMaterial *material, Lib3dsIo *io)
00392 {
00393 Lib3dsChunk c;
00394 Lib3dsWord chunk;
00395
00396 ASSERT(material);
00397 if (!lib3ds_chunk_read_start(&c, LIB3DS_MAT_ENTRY, io)) {
00398 return(LIB3DS_FALSE);
00399 }
00400
00401 while ((chunk=lib3ds_chunk_read_next(&c, io))!=0) {
00402 switch (chunk) {
00403 case LIB3DS_MAT_NAME:
00404 {
00405 if (!lib3ds_io_read_string(io, material->name, 64)) {
00406 return(LIB3DS_FALSE);
00407 }
00408 lib3ds_chunk_dump_info(" NAME=%s", material->name);
00409 }
00410 break;
00411 case LIB3DS_MAT_AMBIENT:
00412 {
00413 lib3ds_chunk_read_reset(&c, io);
00414 if (!color_read(material->ambient, io)) {
00415 return(LIB3DS_FALSE);
00416 }
00417 }
00418 break;
00419 case LIB3DS_MAT_DIFFUSE:
00420 {
00421 lib3ds_chunk_read_reset(&c, io);
00422 if (!color_read(material->diffuse, io)) {
00423 return(LIB3DS_FALSE);
00424 }
00425 }
00426 break;
00427 case LIB3DS_MAT_SPECULAR:
00428 {
00429 lib3ds_chunk_read_reset(&c, io);
00430 if (!color_read(material->specular, io)) {
00431 return(LIB3DS_FALSE);
00432 }
00433 }
00434 break;
00435 case LIB3DS_MAT_SHININESS:
00436 {
00437 lib3ds_chunk_read_reset(&c, io);
00438 if (!int_percentage_read(&material->shininess, io)) {
00439 return(LIB3DS_FALSE);
00440 }
00441 }
00442 break;
00443 case LIB3DS_MAT_SHIN2PCT:
00444 {
00445 lib3ds_chunk_read_reset(&c, io);
00446 if (!int_percentage_read(&material->shin_strength, io)) {
00447 return(LIB3DS_FALSE);
00448 }
00449 }
00450 break;
00451 case LIB3DS_MAT_TRANSPARENCY:
00452 {
00453 lib3ds_chunk_read_reset(&c, io);
00454 if (!int_percentage_read(&material->transparency, io)) {
00455 return(LIB3DS_FALSE);
00456 }
00457 }
00458 break;
00459 case LIB3DS_MAT_XPFALL:
00460 {
00461 lib3ds_chunk_read_reset(&c, io);
00462 if (!int_percentage_read(&material->falloff, io)) {
00463 return(LIB3DS_FALSE);
00464 }
00465 }
00466 break;
00467 case LIB3DS_MAT_SELF_ILPCT:
00468 {
00469 lib3ds_chunk_read_reset(&c, io);
00470 if (!int_percentage_read(&material->self_ilpct, io)) {
00471 return(LIB3DS_FALSE);
00472 }
00473 }
00474 break;
00475 case LIB3DS_MAT_USE_XPFALL:
00476 {
00477 material->use_falloff=LIB3DS_TRUE;
00478 }
00479 break;
00480 case LIB3DS_MAT_REFBLUR:
00481 {
00482 lib3ds_chunk_read_reset(&c, io);
00483 if (!int_percentage_read(&material->blur, io)) {
00484 return(LIB3DS_FALSE);
00485 }
00486 }
00487 break;
00488 case LIB3DS_MAT_USE_REFBLUR:
00489 {
00490 material->use_blur=LIB3DS_TRUE;
00491 }
00492 break;
00493 case LIB3DS_MAT_SHADING:
00494 {
00495 material->shading=lib3ds_io_read_intw(io);
00496 }
00497 break;
00498 case LIB3DS_MAT_SELF_ILLUM:
00499 {
00500 material->self_illum=LIB3DS_TRUE;
00501 }
00502 break;
00503 case LIB3DS_MAT_TWO_SIDE:
00504 {
00505 material->two_sided=LIB3DS_TRUE;
00506 }
00507 break;
00508 case LIB3DS_MAT_DECAL:
00509 {
00510 material->map_decal=LIB3DS_TRUE;
00511 }
00512 break;
00513 case LIB3DS_MAT_ADDITIVE:
00514 {
00515 material->additive=LIB3DS_TRUE;
00516 }
00517 break;
00518 case LIB3DS_MAT_FACEMAP:
00519 {
00520 material->face_map=LIB3DS_TRUE;
00521 }
00522 break;
00523 case LIB3DS_MAT_PHONGSOFT:
00524 {
00525 material->soften=LIB3DS_TRUE;
00526 }
00527 break;
00528 case LIB3DS_MAT_WIRE:
00529 {
00530 material->use_wire=LIB3DS_TRUE;
00531 }
00532 break;
00533 case LIB3DS_MAT_WIREABS:
00534 {
00535 material->use_wire_abs=LIB3DS_TRUE;
00536 }
00537 break;
00538 case LIB3DS_MAT_WIRE_SIZE:
00539 {
00540 material->wire_size=lib3ds_io_read_float(io);
00541 }
00542 break;
00543 case LIB3DS_MAT_TEXMAP:
00544 {
00545 lib3ds_chunk_read_reset(&c, io);
00546 if (!texture_map_read(&material->texture1_map, io)) {
00547 return(LIB3DS_FALSE);
00548 }
00549 }
00550 break;
00551 case LIB3DS_MAT_TEXMASK:
00552 {
00553 lib3ds_chunk_read_reset(&c, io);
00554 if (!texture_map_read(&material->texture1_mask, io)) {
00555 return(LIB3DS_FALSE);
00556 }
00557 }
00558 break;
00559 case LIB3DS_MAT_TEX2MAP:
00560 {
00561 lib3ds_chunk_read_reset(&c, io);
00562 if (!texture_map_read(&material->texture2_map, io)) {
00563 return(LIB3DS_FALSE);
00564 }
00565 }
00566 break;
00567 case LIB3DS_MAT_TEX2MASK:
00568 {
00569 lib3ds_chunk_read_reset(&c, io);
00570 if (!texture_map_read(&material->texture2_mask, io)) {
00571 return(LIB3DS_FALSE);
00572 }
00573 }
00574 break;
00575 case LIB3DS_MAT_OPACMAP:
00576 {
00577 lib3ds_chunk_read_reset(&c, io);
00578 if (!texture_map_read(&material->opacity_map, io)) {
00579 return(LIB3DS_FALSE);
00580 }
00581 }
00582 break;
00583 case LIB3DS_MAT_OPACMASK:
00584 {
00585 lib3ds_chunk_read_reset(&c, io);
00586 if (!texture_map_read(&material->opacity_mask, io)) {
00587 return(LIB3DS_FALSE);
00588 }
00589 }
00590 break;
00591 case LIB3DS_MAT_BUMPMAP:
00592 {
00593 lib3ds_chunk_read_reset(&c, io);
00594 if (!texture_map_read(&material->bump_map, io)) {
00595 return(LIB3DS_FALSE);
00596 }
00597 }
00598 break;
00599 case LIB3DS_MAT_BUMPMASK:
00600 {
00601 lib3ds_chunk_read_reset(&c, io);
00602 if (!texture_map_read(&material->bump_mask, io)) {
00603 return(LIB3DS_FALSE);
00604 }
00605 }
00606 break;
00607 case LIB3DS_MAT_SPECMAP:
00608 {
00609 lib3ds_chunk_read_reset(&c, io);
00610 if (!texture_map_read(&material->specular_map, io)) {
00611 return(LIB3DS_FALSE);
00612 }
00613 }
00614 break;
00615 case LIB3DS_MAT_SPECMASK:
00616 {
00617 lib3ds_chunk_read_reset(&c, io);
00618 if (!texture_map_read(&material->specular_mask, io)) {
00619 return(LIB3DS_FALSE);
00620 }
00621 }
00622 break;
00623 case LIB3DS_MAT_SHINMAP:
00624 {
00625 lib3ds_chunk_read_reset(&c, io);
00626 if (!texture_map_read(&material->shininess_map, io)) {
00627 return(LIB3DS_FALSE);
00628 }
00629 }
00630 break;
00631 case LIB3DS_MAT_SHINMASK:
00632 {
00633 lib3ds_chunk_read_reset(&c, io);
00634 if (!texture_map_read(&material->shininess_mask, io)) {
00635 return(LIB3DS_FALSE);
00636 }
00637 }
00638 break;
00639 case LIB3DS_MAT_SELFIMAP:
00640 {
00641 lib3ds_chunk_read_reset(&c, io);
00642 if (!texture_map_read(&material->self_illum_map, io)) {
00643 return(LIB3DS_FALSE);
00644 }
00645 }
00646 break;
00647 case LIB3DS_MAT_SELFIMASK:
00648 {
00649 lib3ds_chunk_read_reset(&c, io);
00650 if (!texture_map_read(&material->self_illum_mask, io)) {
00651 return(LIB3DS_FALSE);
00652 }
00653 }
00654 break;
00655 case LIB3DS_MAT_REFLMAP:
00656 {
00657 lib3ds_chunk_read_reset(&c, io);
00658 if (!texture_map_read(&material->reflection_map, io)) {
00659 return(LIB3DS_FALSE);
00660 }
00661 }
00662 break;
00663 case LIB3DS_MAT_REFLMASK:
00664 {
00665 lib3ds_chunk_read_reset(&c, io);
00666 if (!texture_map_read(&material->reflection_mask, io)) {
00667 return(LIB3DS_FALSE);
00668 }
00669 }
00670 break;
00671 case LIB3DS_MAT_ACUBIC:
00672 {
00673 lib3ds_io_read_intb(io);
00674 material->autorefl_map.level=lib3ds_io_read_intb(io);
00675 material->autorefl_map.flags=lib3ds_io_read_intw(io);
00676 material->autorefl_map.size=lib3ds_io_read_intd(io);
00677 material->autorefl_map.frame_step=lib3ds_io_read_intd(io);
00678 }
00679 break;
00680 default:
00681 lib3ds_chunk_unknown(chunk);
00682 }
00683 }
00684
00685 lib3ds_chunk_read_end(&c, io);
00686 return(LIB3DS_TRUE);
00687 }
00688
00689
00690 static Lib3dsBool
00691 color_write(Lib3dsRgba rgb, Lib3dsIo *io)
00692 {
00693 Lib3dsChunk c;
00694
00695 c.chunk=LIB3DS_COLOR_24;
00696 c.size=9;
00697 lib3ds_chunk_write(&c,io);
00698 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[0]+0.5));
00699 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[1]+0.5));
00700 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[2]+0.5));
00701
00702 c.chunk=LIB3DS_LIN_COLOR_24;
00703 c.size=9;
00704 lib3ds_chunk_write(&c,io);
00705 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[0]+0.5));
00706 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[1]+0.5));
00707 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*rgb[2]+0.5));
00708
00709 return(LIB3DS_TRUE);
00710 }
00711
00712
00713 static Lib3dsBool
00714 int_percentage_write(Lib3dsFloat p, Lib3dsIo *io)
00715 {
00716 Lib3dsChunk c;
00717
00718 c.chunk=LIB3DS_INT_PERCENTAGE;
00719 c.size=8;
00720 lib3ds_chunk_write(&c,io);
00721 lib3ds_io_write_intw(io, (Lib3dsByte)floor(100.0*p+0.5));
00722
00723 return(LIB3DS_TRUE);
00724 }
00725
00726
00727 static Lib3dsBool
00728 texture_map_write(Lib3dsWord chunk, Lib3dsTextureMap *map, Lib3dsIo *io)
00729 {
00730 Lib3dsChunk c;
00731
00732 if (strlen(map->name)==0) {
00733 return(LIB3DS_TRUE);
00734 }
00735 c.chunk=chunk;
00736 if (!lib3ds_chunk_write_start(&c,io)) {
00737 return(LIB3DS_FALSE);
00738 }
00739
00740 int_percentage_write(map->percent,io);
00741
00742 {
00743 Lib3dsChunk c;
00744 c.chunk=LIB3DS_MAT_MAPNAME;
00745 c.size=6+(Lib3dsDword)strlen(map->name)+1;
00746 lib3ds_chunk_write(&c,io);
00747 lib3ds_io_write_string(io, map->name);
00748 }
00749
00750 {
00751 Lib3dsChunk c;
00752 c.chunk=LIB3DS_MAT_MAP_TILING;
00753 c.size=8;
00754 lib3ds_chunk_write(&c,io);
00755 lib3ds_io_write_word(io, (Lib3dsWord)map->flags);
00756 }
00757
00758 {
00759 Lib3dsChunk c;
00760 c.chunk=LIB3DS_MAT_MAP_TEXBLUR;
00761 c.size=10;
00762 lib3ds_chunk_write(&c,io);
00763 lib3ds_io_write_float(io, map->blur);
00764 }
00765
00766 {
00767 Lib3dsChunk c;
00768 c.chunk=LIB3DS_MAT_MAP_USCALE;
00769 c.size=10;
00770 lib3ds_chunk_write(&c,io);
00771 lib3ds_io_write_float(io, map->scale[0]);
00772 }
00773
00774 {
00775 Lib3dsChunk c;
00776 c.chunk=LIB3DS_MAT_MAP_VSCALE;
00777 c.size=10;
00778 lib3ds_chunk_write(&c,io);
00779 lib3ds_io_write_float(io, map->scale[1]);
00780 }
00781
00782 {
00783 Lib3dsChunk c;
00784 c.chunk=LIB3DS_MAT_MAP_UOFFSET;
00785 c.size=10;
00786 lib3ds_chunk_write(&c,io);
00787 lib3ds_io_write_float(io, map->offset[0]);
00788 }
00789
00790 {
00791 Lib3dsChunk c;
00792 c.chunk=LIB3DS_MAT_MAP_VOFFSET;
00793 c.size=10;
00794 lib3ds_chunk_write(&c,io);
00795 lib3ds_io_write_float(io, map->offset[1]);
00796 }
00797
00798 {
00799 Lib3dsChunk c;
00800 c.chunk=LIB3DS_MAT_MAP_ANG;
00801 c.size=10;
00802 lib3ds_chunk_write(&c,io);
00803 lib3ds_io_write_float(io, map->rotation);
00804 }
00805
00806 {
00807 Lib3dsChunk c;
00808 c.chunk=LIB3DS_MAT_MAP_COL1;
00809 c.size=9;
00810 lib3ds_chunk_write(&c,io);
00811 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_1[0]+0.5));
00812 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_1[1]+0.5));
00813 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_1[2]+0.5));
00814 }
00815
00816 {
00817 Lib3dsChunk c;
00818 c.chunk=LIB3DS_MAT_MAP_COL2;
00819 c.size=9;
00820 lib3ds_chunk_write(&c,io);
00821 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_2[0]+0.5));
00822 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_2[1]+0.5));
00823 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_2[2]+0.5));
00824 }
00825
00826 {
00827 Lib3dsChunk c;
00828 c.chunk=LIB3DS_MAT_MAP_RCOL;
00829 c.size=9;
00830 lib3ds_chunk_write(&c,io);
00831 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_r[0]+0.5));
00832 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_r[1]+0.5));
00833 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_r[2]+0.5));
00834 }
00835
00836 {
00837 Lib3dsChunk c;
00838 c.chunk=LIB3DS_MAT_MAP_GCOL;
00839 c.size=9;
00840 lib3ds_chunk_write(&c,io);
00841 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_g[0]+0.5));
00842 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_g[1]+0.5));
00843 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_g[2]+0.5));
00844 }
00845
00846 {
00847 Lib3dsChunk c;
00848 c.chunk=LIB3DS_MAT_MAP_BCOL;
00849 c.size=9;
00850 lib3ds_chunk_write(&c,io);
00851 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_b[0]+0.5));
00852 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_b[1]+0.5));
00853 lib3ds_io_write_byte(io, (Lib3dsByte)floor(255.0*map->tint_b[2]+0.5));
00854 }
00855
00856 if (!lib3ds_chunk_write_end(&c,io)) {
00857 return(LIB3DS_FALSE);
00858 }
00859 return(LIB3DS_TRUE);
00860 }
00861
00862
00866 Lib3dsBool
00867 lib3ds_material_write(Lib3dsMaterial *material, Lib3dsIo *io)
00868 {
00869 Lib3dsChunk c;
00870
00871 c.chunk=LIB3DS_MAT_ENTRY;
00872 if (!lib3ds_chunk_write_start(&c,io)) {
00873 return(LIB3DS_FALSE);
00874 }
00875
00876 {
00877 Lib3dsChunk c;
00878 c.chunk=LIB3DS_MAT_NAME;
00879 c.size=6+(Lib3dsDword)strlen(material->name)+1;
00880 lib3ds_chunk_write(&c,io);
00881 lib3ds_io_write_string(io, material->name);
00882 }
00883
00884 {
00885 Lib3dsChunk c;
00886 c.chunk=LIB3DS_MAT_AMBIENT;
00887 c.size=24;
00888 lib3ds_chunk_write(&c,io);
00889 color_write(material->ambient,io);
00890 }
00891
00892 {
00893 Lib3dsChunk c;
00894 c.chunk=LIB3DS_MAT_DIFFUSE;
00895 c.size=24;
00896 lib3ds_chunk_write(&c,io);
00897 color_write(material->diffuse,io);
00898 }
00899
00900 {
00901 Lib3dsChunk c;
00902 c.chunk=LIB3DS_MAT_SPECULAR;
00903 c.size=24;
00904 lib3ds_chunk_write(&c,io);
00905 color_write(material->specular,io);
00906 }
00907
00908 {
00909 Lib3dsChunk c;
00910 c.chunk=LIB3DS_MAT_SHININESS;
00911 c.size=14;
00912 lib3ds_chunk_write(&c,io);
00913 int_percentage_write(material->shininess,io);
00914 }
00915
00916 {
00917 Lib3dsChunk c;
00918 c.chunk=LIB3DS_MAT_SHIN2PCT;
00919 c.size=14;
00920 lib3ds_chunk_write(&c,io);
00921 int_percentage_write(material->shin_strength,io);
00922 }
00923
00924 {
00925 Lib3dsChunk c;
00926 c.chunk=LIB3DS_MAT_TRANSPARENCY;
00927 c.size=14;
00928 lib3ds_chunk_write(&c,io);
00929 int_percentage_write(material->transparency,io);
00930 }
00931
00932 {
00933 Lib3dsChunk c;
00934 c.chunk=LIB3DS_MAT_XPFALL;
00935 c.size=14;
00936 lib3ds_chunk_write(&c,io);
00937 int_percentage_write(material->falloff,io);
00938 }
00939
00940 if (material->use_falloff) {
00941 Lib3dsChunk c;
00942 c.chunk=LIB3DS_MAT_USE_XPFALL;
00943 c.size=6;
00944 lib3ds_chunk_write(&c,io);
00945 }
00946
00947 {
00948 Lib3dsChunk c;
00949 c.chunk=LIB3DS_MAT_SHADING;
00950 c.size=8;
00951 lib3ds_chunk_write(&c,io);
00952 lib3ds_io_write_intw(io, material->shading);
00953 }
00954
00955 {
00956 Lib3dsChunk c;
00957 c.chunk=LIB3DS_MAT_REFBLUR;
00958 c.size=14;
00959 lib3ds_chunk_write(&c,io);
00960 int_percentage_write(material->blur,io);
00961 }
00962
00963 if (material->use_blur) {
00964 Lib3dsChunk c;
00965 c.chunk=LIB3DS_MAT_USE_REFBLUR;
00966 c.size=6;
00967 lib3ds_chunk_write(&c,io);
00968 }
00969
00970 if (material->self_illum) {
00971 Lib3dsChunk c;
00972 c.chunk=LIB3DS_MAT_SELF_ILLUM;
00973 c.size=6;
00974 lib3ds_chunk_write(&c,io);
00975 }
00976
00977 if (material->two_sided) {
00978 Lib3dsChunk c;
00979 c.chunk=LIB3DS_MAT_TWO_SIDE;
00980 c.size=6;
00981 lib3ds_chunk_write(&c,io);
00982 }
00983
00984 if (material->map_decal) {
00985 Lib3dsChunk c;
00986 c.chunk=LIB3DS_MAT_DECAL;
00987 c.size=6;
00988 lib3ds_chunk_write(&c,io);
00989 }
00990
00991 if (material->additive) {
00992 Lib3dsChunk c;
00993 c.chunk=LIB3DS_MAT_ADDITIVE;
00994 c.size=6;
00995 lib3ds_chunk_write(&c,io);
00996 }
00997
00998 if (material->use_wire) {
00999 Lib3dsChunk c;
01000 c.chunk=LIB3DS_MAT_WIRE;
01001 c.size=6;
01002 lib3ds_chunk_write(&c,io);
01003 }
01004
01005 if (material->use_wire_abs) {
01006 Lib3dsChunk c;
01007 c.chunk=LIB3DS_MAT_WIREABS;
01008 c.size=6;
01009 lib3ds_chunk_write(&c,io);
01010 }
01011
01012 {
01013 Lib3dsChunk c;
01014 c.chunk=LIB3DS_MAT_WIRE_SIZE;
01015 c.size=10;
01016 lib3ds_chunk_write(&c,io);
01017 lib3ds_io_write_float(io, material->wire_size);
01018 }
01019
01020 if (material->face_map) {
01021 Lib3dsChunk c;
01022 c.chunk=LIB3DS_MAT_FACEMAP;
01023 c.size=6;
01024 lib3ds_chunk_write(&c,io);
01025 }
01026
01027 if (material->soften) {
01028 Lib3dsChunk c;
01029 c.chunk=LIB3DS_MAT_PHONGSOFT;
01030 c.size=6;
01031 lib3ds_chunk_write(&c,io);
01032 }
01033
01034 if (!texture_map_write(LIB3DS_MAT_TEXMAP, &material->texture1_map, io)) {
01035 return(LIB3DS_FALSE);
01036 }
01037 if (!texture_map_write(LIB3DS_MAT_TEXMASK, &material->texture1_mask, io)) {
01038 return(LIB3DS_FALSE);
01039 }
01040 if (!texture_map_write(LIB3DS_MAT_TEX2MAP, &material->texture2_map, io)) {
01041 return(LIB3DS_FALSE);
01042 }
01043 if (!texture_map_write(LIB3DS_MAT_TEX2MASK, &material->texture2_mask, io)) {
01044 return(LIB3DS_FALSE);
01045 }
01046 if (!texture_map_write(LIB3DS_MAT_OPACMAP, &material->opacity_map, io)) {
01047 return(LIB3DS_FALSE);
01048 }
01049 if (!texture_map_write(LIB3DS_MAT_OPACMASK, &material->opacity_mask, io)) {
01050 return(LIB3DS_FALSE);
01051 }
01052 if (!texture_map_write(LIB3DS_MAT_BUMPMAP, &material->bump_map, io)) {
01053 return(LIB3DS_FALSE);
01054 }
01055 if (!texture_map_write(LIB3DS_MAT_BUMPMASK, &material->bump_mask, io)) {
01056 return(LIB3DS_FALSE);
01057 }
01058 if (!texture_map_write(LIB3DS_MAT_SPECMAP, &material->specular_map, io)) {
01059 return(LIB3DS_FALSE);
01060 }
01061 if (!texture_map_write(LIB3DS_MAT_SPECMASK, &material->specular_mask, io)) {
01062 return(LIB3DS_FALSE);
01063 }
01064 if (!texture_map_write(LIB3DS_MAT_SHINMAP, &material->shininess_map, io)) {
01065 return(LIB3DS_FALSE);
01066 }
01067 if (!texture_map_write(LIB3DS_MAT_SHINMASK, &material->shininess_mask, io)) {
01068 return(LIB3DS_FALSE);
01069 }
01070 if (!texture_map_write(LIB3DS_MAT_SELFIMAP, &material->self_illum_map, io)) {
01071 return(LIB3DS_FALSE);
01072 }
01073 if (!texture_map_write(LIB3DS_MAT_SELFIMASK, &material->self_illum_mask, io)) {
01074 return(LIB3DS_FALSE);
01075 }
01076 if (!texture_map_write(LIB3DS_MAT_REFLMAP, &material->reflection_map, io)) {
01077 return(LIB3DS_FALSE);
01078 }
01079 if (!texture_map_write(LIB3DS_MAT_REFLMASK, &material->reflection_mask, io)) {
01080 return(LIB3DS_FALSE);
01081 }
01082
01083 if (!lib3ds_chunk_write_end(&c,io)) {
01084 return(LIB3DS_FALSE);
01085 }
01086 return(LIB3DS_TRUE);
01087 }
01088
01089