00001
00002
00003
00004
00005
00006
00007
00008
00009
00010 #include <stdio.h>
00011 #include <math.h>
00012 #include <string.h>
00013 #include <stdlib.h>
00014
00015 #include "molfile_plugin.h"
00016
00017 typedef struct {
00018 FILE *fd;
00019 molfile_graphics_t *graphics;
00020 } handle_t;
00021
00022 static void *open_file_read(const char *filepath, const char *filetype,
00023 int *natoms) {
00024 FILE *fd;
00025 handle_t *handle;
00026
00027 fd = fopen(filepath, "rt");
00028 if (!fd)
00029 return NULL;
00030 handle = new handle_t;
00031 handle->fd = fd;
00032 handle->graphics = NULL;
00033 *natoms = 0;
00034 return handle;
00035 }
00036
00037 static void next_elem(int &n, int &max, molfile_graphics_t *& graphics) {
00038 ++n;
00039 if (n == max) {
00040 max *= 2;
00041 graphics = (molfile_graphics_t *)realloc(graphics, max*sizeof(molfile_graphics_t));
00042 }
00043 }
00044
00045
00046 static int get_line(int &line, char *buf, int len, FILE *f) {
00047 do {
00048 line++;
00049 if (!fgets(buf, len - 1, f)) return 0;
00050 } while (buf[0] == '#');
00051 return 1;
00052 }
00053
00054 static int read_rawgraphics(void *v, int *nelem,
00055 const molfile_graphics_t **gdata) {
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096 int futureVersion = 0;
00097 int line = 0;
00098
00099 int count, i;
00100 char buffer[200];
00101 float mat[16];
00102 FILE *infile;
00103
00104 handle_t *handle = (handle_t *)v;
00105 infile = handle->fd;
00106
00107 int maxelem = 10;
00108 int n = 0;
00109 molfile_graphics_t *graphics = (molfile_graphics_t *)malloc(
00110 maxelem*sizeof(molfile_graphics_t));
00111
00112
00113 if (!get_line(line, buffer, 199, infile)) {
00114 fprintf(stderr, "Raster3D input: error reading file header (line %d)\n",
00115 line);
00116 return MOLFILE_ERROR;
00117 }
00118
00119
00120 for (i = strlen(buffer) - 1; i >= 0 &&
00121 (buffer[i] == 10 || buffer[i] == 13); i--) buffer[i] = 0;
00122 printf("Raster3D input: scene title: '%s'\n", buffer);
00123
00124
00125
00126
00127 for (count = 0; count < 11; count++) {
00128 if (!get_line(line, buffer, 199, infile)) {
00129 fprintf(stderr,
00130 "Raster3D input: error reading file header (line %d)\n", line);
00131 return MOLFILE_ERROR;
00132 }
00133 }
00134
00135
00136
00137
00138 for (i=0; i<4; i++) {
00139 get_line(line, buffer, 199, infile);
00140 if (sscanf(buffer, "%f %f %f %f",
00141 &mat[4*i], &mat[4*i+1], &mat[4*i+2], &mat[4*i+3])<4) {
00142 fprintf(stderr, "Raster3D input: invalid format in file (line %d)\n",
00143 line);
00144 return MOLFILE_ERROR;
00145 }
00146 }
00147
00148 get_line(line, buffer, 199, infile);
00149 if (sscanf(buffer, "%d", &i) < 1) {
00150 fprintf(stderr,
00151 "Raster3D input: error reading object input mode (line %d)\n", line);
00152 return MOLFILE_ERROR;
00153 }
00154
00155 if (i != 3) {
00156 fprintf(stderr,
00157 "Raster3D input: the specified file is in an unsupported format\n");
00158 fprintf(stderr,
00159 "(object input mode %d). Aborting.\n", i);
00160 return MOLFILE_ERROR;
00161 }
00162
00163 float data[15];
00164 float normals[15];
00165 float tricolors[9];
00166 float color[9];
00167
00168
00169
00170
00171 for (count = 0; count < 3; count++) {
00172 get_line(line, buffer, 199, infile);
00173 for (i = strlen(buffer) - 1; i >= 0 && (buffer[i] == 10 || buffer[i] == 13); i--)
00174 buffer[i] = 0;
00175 if (strcmp(buffer, "*")) break;
00176 }
00177 if (count < 3) {
00178 fprintf(stderr, "Raster3D input: Warning: this file contains input in a nonstandard\n");
00179 fprintf(stderr, "Fortran format. This is generally not supported, and the read may fail.\n");
00180 }
00181 count = 0;
00182
00183 while (!feof(infile) && !ferror(infile)) {
00184 int objtype = -1;
00185
00186 if (!get_line(line, buffer, 199, infile)) continue;
00187
00188 if (sscanf(buffer, "%d", &objtype) != 1) {
00189 fprintf(stderr, "Raster3D input: bad data in file (line %d)\n",
00190 line);
00191 return MOLFILE_ERROR;
00192 }
00193
00194 switch(objtype) {
00195
00196 case 1:
00197 char buffer2[200];
00198 int have_normals;
00199 int have_tricolors;
00200 long fpos;
00201
00202 have_normals = 0;
00203 have_tricolors = 0;
00204
00205 get_line(line, buffer, 127, infile);
00206 if (feof(infile)) {
00207
00208
00209 return MOLFILE_ERROR;
00210 }
00211
00212 if (sscanf(buffer, "%f %f %f %f %f %f %f %f %f %f %f %f",
00213 data , data+1, data+2,
00214 data+3, data+4, data+5,
00215 data+6, data+7, data+8,
00216 data+9, data+10, data+11) < 12) {
00217
00218
00219 continue;
00220 }
00221
00222 while (!feof(infile) && !ferror(infile)) {
00223
00224 fpos = ftell(infile);
00225 if (!get_line(line, buffer2, 199, infile)) {
00226 fseek(infile, fpos, SEEK_SET);
00227 break;
00228 }
00229
00230 if (sscanf(buffer2, "%d", &objtype) != 1) {
00231
00232
00233 return MOLFILE_ERROR;
00234 }
00235
00236 switch (objtype) {
00237 case 7:
00238
00239 if (!get_line(line, buffer2, 199, infile)) {
00240
00241
00242 return MOLFILE_ERROR;
00243 }
00244
00245 if (sscanf(buffer2, "%f %f %f %f %f %f %f %f %f",
00246 normals , normals+1, normals+2,
00247 normals+3, normals+4, normals+5,
00248 normals+6, normals+7, normals+8 ) < 9) {
00249
00250
00251 continue;
00252 }
00253
00254 have_normals = 1;
00255
00256 break;
00257
00258 case 17:
00259
00260 if (!get_line(line, buffer2, 199, infile)) {
00261
00262
00263 return MOLFILE_ERROR;
00264 }
00265
00266 if (sscanf(buffer2, "%f %f %f %f %f %f %f %f %f",
00267 tricolors, tricolors+ 1, tricolors + 2,
00268 tricolors + 3, tricolors + 4, tricolors + 5,
00269 tricolors + 6, tricolors + 7, tricolors + 8) < 9) {
00270
00271
00272 continue;
00273 }
00274
00275 have_tricolors = 1;
00276
00277 break;
00278
00279 default:
00280
00281 fseek(infile, fpos, SEEK_SET);
00282 fpos = 0;
00283 break;
00284
00285 }
00286
00287 if (!fpos) break;
00288 }
00289
00290 if (ferror(infile)) {
00291
00292
00293 return MOLFILE_ERROR;
00294 }
00295
00296 graphics[n].type = MOLFILE_COLOR;
00297 graphics[n].data[0] = sqrt(data[9]);
00298 graphics[n].data[1] = sqrt(data[10]);
00299 graphics[n].data[2] = sqrt(data[11]);
00300 next_elem(n, maxelem, graphics);
00301
00302 if (have_tricolors) {
00303 for (int qq=0; qq<9; qq++) color[qq] = sqrt(tricolors[qq]);
00304 }
00305
00306 if (!have_normals && !have_tricolors) {
00307 graphics[n].type = MOLFILE_TRIANGLE;
00308 memcpy(graphics[n].data, data, 3*sizeof(float));
00309 next_elem(n, maxelem, graphics);
00310
00311 } else if (have_normals && !have_tricolors) {
00312 graphics[n].type = MOLFILE_TRINORM;
00313 memcpy(graphics[n].data, data, 9*sizeof(float));
00314 next_elem(n, maxelem, graphics);
00315 graphics[n].type = MOLFILE_NORMS;
00316 memcpy(graphics[n].data, normals, 9*sizeof(float));
00317 next_elem(n, maxelem, graphics);
00318 } else if (have_tricolors && !have_normals) {
00319 #if 0
00320
00321 float tmp1[3], tmp2[3], tmp3[3];
00322 int j;
00323 for (j = 0; j < 3; j++) {
00324 tmp1[j] = data[3 + j] - data[j];
00325 tmp2[j] = data[6 + j] - data[3 + j];
00326 }
00327 cross_prod(tmp3, tmp1, tmp2);
00328 vec_normalize(tmp3);
00329 triclr.putdata(data, data+3, data+6,
00330 tmp3, tmp3, tmp3,
00331 colorIndices[0], colorIndices[1], colorIndices[2], cmdList);
00332 #else
00333
00334 graphics[n].type = MOLFILE_COLOR;
00335 graphics[n].data[0] = (color[0]+color[3]+color[6])/3.0f;
00336 graphics[n].data[1] = (color[1]+color[4]+color[7])/3.0f;
00337 graphics[n].data[2] = (color[2]+color[5]+color[8])/3.0f;
00338 next_elem(n, maxelem, graphics);
00339 graphics[n].type = MOLFILE_TRIANGLE;
00340 memcpy(graphics[n].data, data, 3*sizeof(float));
00341 next_elem(n, maxelem, graphics);
00342
00343 #endif
00344 } else {
00345
00346 #if 0
00347 triclr.putdata(data, data+3, data+6,
00348 normals, normals+3, normals+6,
00349 colorIndices[0], colorIndices[1], colorIndices[2], cmdList);
00350 #else
00351 graphics[n].type = MOLFILE_TRICOLOR;
00352 memcpy(graphics[n].data, data, 9*sizeof(float));
00353 next_elem(n, maxelem, graphics);
00354 graphics[n].type = MOLFILE_NORMS;
00355 memcpy(graphics[n].data, normals, 9*sizeof(float));
00356 next_elem(n, maxelem, graphics);
00357 graphics[n].type = MOLFILE_COLOR;
00358 memcpy(graphics[n].data, color, 9*sizeof(float));
00359 next_elem(n, maxelem, graphics);
00360 #endif
00361 }
00362
00363 break;
00364
00365 case 2:
00366
00367 if (!get_line(line, buffer, 199, infile)) {
00368
00369
00370 return MOLFILE_ERROR;
00371 }
00372
00373 if (sscanf(buffer, "%f %f %f %f %f %f %f",
00374 data, data + 1, data + 2, data + 3,
00375 data + 4, data + 5, data + 6) != 7) {
00376
00377
00378 continue;
00379 }
00380 graphics[n].type = MOLFILE_COLOR;
00381 color[0] = sqrt(data[4]);
00382 color[1] = sqrt(data[5]);
00383 color[2] = sqrt(data[6]);
00384 memcpy(graphics[n].data, color, 3*sizeof(float));
00385 next_elem(n, maxelem, graphics);
00386 graphics[n].type = MOLFILE_SPHERE;
00387 graphics[n].size = data[3];
00388 graphics[n].style = 12;
00389 memcpy(graphics[n].data, data, 3*sizeof(float));
00390 next_elem(n, maxelem, graphics);
00391 break;
00392
00393 case 3:
00394 case 5:
00395
00396 if (!get_line(line, buffer, 199, infile)) {
00397
00398
00399 return MOLFILE_ERROR;
00400 }
00401
00402 if (sscanf(buffer, "%f %f %f %f %f %f %f %f %f %f %f",
00403 data, data + 1, data + 2, data + 3, data + 4,
00404 data + 5, data + 6, data + 7, data + 8, data + 9,
00405 data + 10) != 11) {
00406
00407
00408 continue;
00409 }
00410 graphics[n].type = MOLFILE_COLOR;
00411 color[0] = sqrt(data[8]);
00412 color[1] = sqrt(data[9]);
00413 color[2] = sqrt(data[10]);
00414 memcpy(graphics[n].data, color, 3*sizeof(float));
00415 next_elem(n, maxelem, graphics);
00416 graphics[n].type = MOLFILE_CYLINDER;
00417 graphics[n].size = data[3];
00418 graphics[n].style = 12;
00419 memcpy(graphics[n].data, data, 3*sizeof(float));
00420 memcpy(graphics[n].data+3, data+4, 3*sizeof(float));
00421 next_elem(n, maxelem, graphics);
00422
00423
00424 if (objtype == 3) {
00425 graphics[n].type = MOLFILE_SPHERE;
00426 graphics[n].size = data[3];
00427 graphics[n].style = 12;
00428 memcpy(graphics[n].data, data, 3*sizeof(float));
00429 next_elem(n, maxelem, graphics);
00430 graphics[n].type = MOLFILE_SPHERE;
00431 graphics[n].size = data[3];
00432 graphics[n].style = 12;
00433 memcpy(graphics[n].data, data+4, 3*sizeof(float));
00434 next_elem(n, maxelem, graphics);
00435 }
00436
00437 break;
00438
00439 case 9:
00440 break;
00441
00442 case 6: case 8: case 10: case 11: case 12: case 13: case 15: case 19:
00443
00444
00445 get_line(line, buffer, 199, infile);
00446
00447 break;
00448
00449 case 7:
00450
00451
00452
00453 break;
00454
00455 case 17:
00456
00457
00458 break;
00459
00460 case 0:
00461 break;
00462
00463
00464
00465 default:
00466 if (!futureVersion) {
00467
00468
00469
00470
00471 futureVersion = 1;
00472 }
00473 break;
00474
00475 }
00476
00477
00478 if (objtype == 0) break;
00479
00480 }
00481
00482 if (ferror(infile)) {
00483
00484
00485 return MOLFILE_ERROR;
00486 }
00487
00488
00489 *nelem = n;
00490 handle->graphics = graphics;
00491 *gdata = graphics;
00492 return MOLFILE_SUCCESS;
00493 }
00494
00495 static void close_file_read(void *v) {
00496 handle_t *handle = (handle_t *)v;
00497 fclose(handle->fd);
00498 handle->fd = NULL;
00499 delete [] handle->graphics;
00500 handle->graphics = NULL;
00501 delete handle;
00502 }
00503
00504
00505
00506
00507
00508 static molfile_plugin_t plugin = {
00509 vmdplugin_ABIVERSION,
00510 MOLFILE_PLUGIN_TYPE,
00511 "raster3d",
00512 "Raster3d Scene File",
00513 "Justin Gullingsrud",
00514 0,
00515 1,
00516 VMDPLUGIN_THREADSAFE,
00517 "r3d"
00518 };
00519
00520 VMDPLUGIN_API int VMDPLUGIN_init(void) { return VMDPLUGIN_SUCCESS; }
00521 VMDPLUGIN_API int VMDPLUGIN_fini(void) { return VMDPLUGIN_SUCCESS; }
00522 VMDPLUGIN_API int VMDPLUGIN_register(void *v, vmdplugin_register_cb cb) {
00523 plugin.open_file_read = open_file_read;
00524 plugin.read_rawgraphics = read_rawgraphics;
00525 plugin.close_file_read = close_file_read;
00526 (*cb)(v, (vmdplugin_t *)&plugin);
00527 return VMDPLUGIN_SUCCESS;
00528 }
00529
00530