hw3file.cpp 9.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346
  1. /*
  2. * DoRayMe - a quick and dirty Raytracer
  3. * Hw3file implementation
  4. *
  5. * Created by Manoël Trapier
  6. * Copyright (c) 2020 986-Studio.
  7. *
  8. */
  9. /* Don't build for now */
  10. /* This file is parsing a text format from another raytracer I made in the past. */
  11. #include <stdio.h>
  12. #include <string.h>
  13. #include <ctype.h>
  14. #include <worldbuilder.h>
  15. #include <sphere.h>
  16. #include <matrix.h>
  17. #include <transformation.h>
  18. #define IS_CMD(_cmd) (strncmp(buffer, _cmd, sizeof(_cmd)) == 0)
  19. typedef void (*cmdFunc)(Hw3File *w, uint32_t curLine, double argv[15]);
  20. typedef struct cmd_def
  21. {
  22. const char *name;
  23. int8_t numparam; /* -1 == one string, else >0 = number of argv */
  24. cmdFunc f;
  25. } cmd_def;
  26. static void cmdCamera (Hw3File *w, uint32_t curLine, double argv[15])
  27. {
  28. w->cam = viewTransform(Point(argv[0], argv[1], argv[2]),
  29. Point(argv[3], argv[4], argv[5]),
  30. Vector(argv[6], argv[7], argv[8]));
  31. w->camFoV = deg_to_rad(argv[9]);
  32. }
  33. /* 0: X, 1: Y, 2: Z
  34. * 3: Radius
  35. */
  36. static void cmdSphere (Hw3File *w, uint32_t curLine, double argv[15])
  37. {
  38. printf("Adding a sphere...\n");
  39. /* Instanciate a sphere */
  40. Sphere *shape = new Sphere();
  41. Matrix pos = translation(argv[0], argv[1], argv[2]) * scaling(argv[3], argv[3], argv[3]);
  42. shape->setTransform(w->getTransformMatrix() * pos);
  43. shape->material.ambient = w->currentAmbient;
  44. shape->material.reflective = w->currentReflective;
  45. shape->material.shininess = w->currentShininess;
  46. shape->material.specular = w->currentSpecular;
  47. shape->material.diffuse = w->currentDiffuse;
  48. shape->material.colour = w->currentColour;
  49. shape->material.transparency = w->currentTransparency;
  50. shape->material.refractiveIndex = w->currentRefIndex;
  51. w->addObject(shape);
  52. }
  53. static void cmdCube (Hw3File *w, uint32_t curLine, double argv[15])
  54. {
  55. }
  56. static void cmdTrans (Hw3File *w, uint32_t curLine, double argv[15])
  57. {
  58. Matrix m = translation(argv[0], argv[1], argv[2]);
  59. w->applyTransformMatrix(m);
  60. }
  61. static void cmdRotate (Hw3File *w, uint32_t curLine, double argv[15])
  62. {
  63. Matrix m = Matrix4().identity();
  64. if (argv[2] != 0)
  65. {
  66. m = m * rotationZ(argv[3]);
  67. }
  68. if (argv[1] != 0)
  69. {
  70. m = m * rotationY(argv[3]);
  71. }
  72. if (argv[0] != 0)
  73. {
  74. m = m * rotationX(argv[3]);
  75. }
  76. w->applyTransformMatrix(m);
  77. }
  78. static void cmdScale (Hw3File *w, uint32_t curLine, double argv[15])
  79. {
  80. Matrix m = scaling(argv[0], argv[1], argv[2]);
  81. w->applyTransformMatrix(m);
  82. }
  83. static void cmdPushT (Hw3File *w, uint32_t curLine, double argv[15])
  84. {
  85. w->pushTransformMatrix();
  86. }
  87. static void cmdPopT (Hw3File *w, uint32_t curLine, double argv[15])
  88. {
  89. w->popTransformMatrix();
  90. }
  91. static void cmdLPoint (Hw3File *w, uint32_t curLine, double argv[15])
  92. {
  93. /* create point light */
  94. Light *l = new Light(POINT_LIGHT, Point(argv[0], argv[1], argv[2]), Colour(argv[3], argv[4], argv[5]));
  95. w->addLight(l);
  96. }
  97. static void cmdAmbient (Hw3File *w, uint32_t curLine, double argv[15])
  98. {
  99. //w->currentAmbient = (argv[0] + argv[1] + argv[2]) / 3;
  100. w->currentColour = Colour(argv[0], argv[1], argv[2]);
  101. }
  102. static void cmdColour (Hw3File *w, uint32_t curLine, double argv[15])
  103. {
  104. w->currentColour = Colour(argv[0], argv[1], argv[2]);
  105. }
  106. static void cmdDiffuse (Hw3File *w, uint32_t curLine, double argv[15])
  107. {
  108. w->currentDiffuse = (argv[0] + argv[1] + argv[2]) / 3;
  109. }
  110. static void cmdSpecular (Hw3File *w, uint32_t curLine, double argv[15])
  111. {
  112. w->currentSpecular = (argv[0] + argv[1] + argv[2]) / 3;
  113. }
  114. static void cmdShine (Hw3File *w, uint32_t curLine, double argv[15])
  115. {
  116. w->currentReflective = argv[0];
  117. }
  118. static void cmdEmission (Hw3File *w, uint32_t curLine, double argv[15])
  119. {
  120. w->currentEmission = (argv[0] + argv[1] + argv[2]) / 3;
  121. }
  122. #if 0
  123. static void cmdLDire (Hw3File *w, uint32_t curLine, double argv[15])
  124. {
  125. /* create directional light */
  126. light *cur = new light();
  127. cur->type = LIGHT_DIRECTIONAL;
  128. cur->attenuation = sc->attenuation;
  129. cur->position.set(argv[0], argv[1], argv[2]);
  130. cur->lightcolor.set(argv[3], argv[4], argv[5]);
  131. sc->l[sc->l_count] = cur;
  132. sc->l_count++;
  133. }
  134. static void cmdAtten (Hw3File *w, uint32_t curLine, double argv[15])
  135. {
  136. sc->attenuation = Vector(argv[0], argv[1], argv[2]);
  137. }
  138. static void cmdMaxVerts (Hw3File *w, uint32_t curLine, double argv[15])
  139. {
  140. sc->vertexCount = (uint32_t) argv[0];
  141. sc->vertex = new point[sc->vertexCount];
  142. sc->curVertex = 0;
  143. }
  144. static void cmdMaxVertN (Hw3File *w, uint32_t curLine, double argv[15])
  145. {
  146. /* ignore for now */
  147. }
  148. static void cmdVertex (Hw3File *w, uint32_t curLine, double argv[15])
  149. {
  150. sc->vertex[sc->curVertex].set(argv[0], argv[1], argv[2]);
  151. sc->curVertex++;
  152. }
  153. static void cmdVertexN (Hw3File *w, uint32_t curLine, double argv[15])
  154. {
  155. /* ignore for now */
  156. }
  157. static void cmdTri (Hw3File *w, uint32_t curLine, double argv[15])
  158. {
  159. /* arg are vertex numbers */
  160. triangle *tr = new triangle(sc->vertex[(int)argv[0]], sc->vertex[(int)argv[1]], sc->vertex[(int)argv[2]], sc->getMatrix());
  161. tr->ambient = sc->ambient;
  162. tr->diffuse = sc->diffuse;
  163. tr->specular = sc->specular;
  164. tr->emission = sc->emission;
  165. tr->shininess = sc->shininess;
  166. tr->sourceLine = curLine;
  167. sc->o[sc->o_count] = tr;
  168. sc->o_count++;
  169. }
  170. #endif
  171. static cmd_def commandList[] =
  172. {
  173. /* Camera */
  174. {"camera", 10, cmdCamera},
  175. /* Geometry */
  176. {"sphere", 4, cmdSphere},
  177. //{ "maxverts", 1, cmdMaxVerts },
  178. //{ "maxvertnorms", 1, cmdMaxVertN },
  179. //{ "vertex", 3, cmdVertex },
  180. //{ "vertexnormal", 6, cmdVertexN },
  181. //{ "tri", 3, cmdTri },
  182. //{ "trinormal", 3, cmdTriN },
  183. //{ "cube", 1, cmdCube },
  184. /* transformation */
  185. {"translate", 3, cmdTrans},
  186. {"rotate", 4, cmdRotate},
  187. {"scale", 3, cmdScale},
  188. {"pushTransform", 0, cmdPushT},
  189. {"popTransform", 0, cmdPopT},
  190. /* Lights */
  191. //{ "directional", 6, cmdLDire },
  192. {"point", 6, cmdLPoint},
  193. //{ "attenuation", 3, cmdAtten },
  194. /* Materials */
  195. {"color", 3, cmdColour},
  196. {"ambient", 3, cmdAmbient},
  197. {"diffuse", 3, cmdDiffuse},
  198. {"specular", 3, cmdSpecular},
  199. {"shininess", 1, cmdShine},
  200. {"emission", 3, cmdEmission},
  201. };
  202. #define CMD_COUNT (sizeof(commandList) / sizeof(cmd_def))
  203. Hw3File::Hw3File(const char *filename) : transStackCount(0), currentColour(Colour(1, 1, 1)),
  204. currentEmission(0), currentShininess(200), currentAmbient(0.1),
  205. currentDiffuse(0.9), currentSpecular(0.9), camFoV(0)
  206. {
  207. FILE *fp;
  208. this->popTransformMatrix();
  209. fp = fopen(filename, "rt");
  210. if (fp != NULL)
  211. {
  212. char buffer[512];
  213. int line = 0;
  214. while(!feof(fp))
  215. {
  216. uint32_t i;
  217. line++;
  218. memset(buffer, 0, 512);
  219. fgets(buffer, 512, fp);
  220. if ((buffer[0] == '#') || (strlen(buffer) < 2))
  221. {
  222. continue; /* Ingore empty line or commented lines */
  223. }
  224. for (i = 0; i < CMD_COUNT; i++)
  225. {
  226. if (strncmp(buffer, commandList[i].name, strlen(commandList[i].name)) == 0)
  227. {
  228. char first[512];
  229. double value[15];
  230. if (commandList[i].numparam != 0)
  231. {
  232. size_t j;
  233. int k = 0, l = 0;
  234. char buff[512];
  235. for(j = strlen(commandList[i].name); j < strlen(buffer); j++)
  236. {
  237. if (!isspace(buffer[j]))
  238. {
  239. buff[l++] = buffer[j];
  240. }
  241. else
  242. {
  243. buff[l] = 0;
  244. l = 0;
  245. if (k == 0)
  246. {
  247. strcpy(first, buff);
  248. }
  249. if (strlen(buff) > 0)
  250. {
  251. value[k++] = atof(buff);
  252. }
  253. }
  254. }
  255. if (k != abs(commandList[i].numparam))
  256. {
  257. printf("line %d malformed: given %d parameter, expected %d\n%s", line, k, abs(commandList[i].numparam), buffer);
  258. goto exit;
  259. }
  260. }
  261. commandList[i].f(this, line, value);
  262. break;
  263. }
  264. }
  265. }
  266. }
  267. exit:
  268. return;
  269. }
  270. Matrix Hw3File::getTransformMatrix()
  271. {
  272. return this->transformStack[this->transStackCount];
  273. }
  274. void Hw3File::popTransformMatrix()
  275. {
  276. if (this->transStackCount == 0)
  277. {
  278. this->transformStack[0] = Matrix4().identity();
  279. }
  280. else
  281. {
  282. this->transformStack[this->transStackCount] = Matrix4().identity();
  283. this->transStackCount --;
  284. }
  285. }
  286. void Hw3File::pushTransformMatrix()
  287. {
  288. this->transStackCount ++;
  289. this->transformStack[this->transStackCount] = this->transformStack[this->transStackCount - 1];
  290. }
  291. void Hw3File::applyTransformMatrix(Matrix t)
  292. {
  293. this->transformStack[this->transStackCount] = this->transformStack[this->transStackCount] * t;
  294. }