Advertisement
topless_banana

maldrebort

Apr 30th, 2018
118
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 10.10 KB | None | 0 0
  1. #include <SFML/Graphics.hpp>
  2. #include <Windows.h>
  3. #include <string>
  4. #include <thread>
  5. #include <vector>
  6. #include <iostream>
  7. #include <complex>
  8. #include <chrono>
  9. #include <mutex>
  10.  
  11. using std::vector;
  12. using std::thread;
  13. vector<thread> thrd;
  14. using std::complex;
  15.  
  16. using std::chrono::duration_cast;
  17. using std::chrono::milliseconds;
  18. using std::cout;
  19. using std::endl;
  20. using std::ofstream;
  21.  
  22. typedef std::chrono::steady_clock the_clock;
  23.  
  24. bool released = false;
  25.  
  26. int WIDTH = 1024;
  27. int HIGHT = 600;
  28. int MAX_ITERATIONS = 200;
  29.  
  30. long double left = -2.5;
  31. long double right = 1.25;
  32. long double top = -1.2;
  33. long double bottom = -1.125;
  34. long double factor = 1;
  35. //double MinRe = -2.5;
  36. //double MaxRe = 1.25;
  37. //double MinIm = -1.2;
  38. //(-2.0, 1.0, 1.125, -1.125)
  39. //1024, 600
  40. sf::VertexArray varray(sf::Points);
  41. sf::Vertex vertex;
  42. sf::Mutex mutex, mutex2;
  43.  
  44. //color?
  45. //zoom?
  46. //cores scatter?
  47.  
  48. void compute_mandelbrot(double left, double right, double top, double bottom, double start, double end) //original mandelbort
  49. {
  50. //mutex.lock();
  51. int r = 0x00, g = 0x00, b = 0x00;
  52. for (int y = start; y < end; ++y)
  53. {
  54. for (int x = 0; x < WIDTH; ++x)
  55. {
  56. // Work out the point in the complex plane that
  57. // corresponds to this pixel in the output image.
  58. complex<double> c(left + (x * (right - left) / WIDTH),
  59. top + (y * (bottom - top) / HIGHT));
  60.  
  61. // Start off z at (0, 0).
  62. complex<double> z(0.0, 0.0);
  63.  
  64. // Iterate z = z^2 + c until z moves more than 2 units
  65. // away from (0, 0), or we've iterated too many times.
  66. int iterations = 0;
  67. while (abs(z) < 2.0 && iterations < MAX_ITERATIONS)
  68. {
  69. z = (z * z) + c;
  70.  
  71. ++iterations;
  72. }
  73.  
  74. if (r <= MAX_ITERATIONS)
  75. r = iterations;
  76.  
  77. unsigned int colour = r | (r << 8) | (r << 16);
  78.  
  79. vertex.color = sf::Color(r, g, b, 255);
  80. //vertex.color = sf::Color(6525, 1111, 222, 255);
  81. vertex.position = sf::Vector2f(x, y);
  82. mutex.lock();
  83. varray.append(vertex);
  84. mutex.unlock();
  85.  
  86. }
  87. }
  88. //mutex.unlock();
  89. }
  90.  
  91. void compute_mandelbrot2(double left, double right, double top, double bottom, double start, double end) //improved mandelbort following a tutorial
  92. {
  93. double ImageHeight = 960;
  94. double ImageWidth = 960;
  95.  
  96. //double MinRe = -2.5;
  97. //double MaxRe = 1.25;
  98. //double MinIm = -1.2;
  99. double MinRe = left;
  100. double MaxRe = right;
  101. double MinIm = top;
  102. double MaxIm = MinIm + (MaxRe - MinRe)*ImageHeight / ImageWidth;
  103. double Re_factor = (MaxRe - MinRe) / (ImageWidth - 1);
  104. double Im_factor = (MaxIm - MinIm) / (ImageHeight - 1);
  105. //unsigned MAX_ITERATIONS = 100;
  106.  
  107. /*int r = 0x00, g = 0x00, b = 0x00;*/
  108.  
  109.  
  110.  
  111.  
  112.  
  113.  
  114. for (unsigned y = 0; y<ImageHeight; ++y)
  115. {
  116. double c_im = MaxIm - y*Im_factor;
  117. for (unsigned x = 0; x<ImageWidth; ++x)
  118. {
  119. double c_re = MinRe + x*Re_factor;
  120.  
  121. double Z_re = c_re, Z_im = c_im;
  122. bool isInside = true;
  123. for (unsigned n = 0; n<MAX_ITERATIONS; ++n)
  124. {
  125. double Z_re2 = Z_re*Z_re, Z_im2 = Z_im*Z_im;
  126. if (Z_re2 + Z_im2 > 4)
  127. {
  128. isInside = false;
  129. break;
  130. }
  131. Z_im = 2 * Z_re*Z_im + c_im;
  132. Z_re = Z_re2 - Z_im2 + c_re;
  133.  
  134. //unsigned int colour = r | (r << 8) | (r << 16);
  135. //if (n < MAX_ITERATIONS / 2)
  136. // vertex.color = sf::Color(0, 153, 68, 255);
  137. if (n > MAX_ITERATIONS / 2)
  138. vertex.color = sf::Color(220, 53, 168, 255);
  139. }
  140.  
  141. if (isInside)
  142. {
  143.  
  144. //vertex.color = sf::Color(r, g, b, 255);
  145.  
  146. vertex.position = sf::Vector2f(x, y);
  147. mutex.lock();
  148. varray.append(vertex);
  149. mutex.unlock();
  150. }
  151. }
  152. }
  153.  
  154.  
  155.  
  156. }
  157. void compute_mandelbrot3(double left, double right, double top, double start, double end)
  158. {
  159. double ImageHeight = 960;
  160. double ImageWidth = 960;
  161.  
  162. //double MinRe = -2.5;
  163. //double MaxRe = 1.25;
  164. //double MinIm = -1.2;
  165. double MinRe = left;
  166. double MaxRe = right;
  167. double MinIm = top;
  168. double MaxIm = MinIm + (MaxRe - MinRe)*ImageHeight / ImageWidth;
  169. double Re_factor = (MaxRe - MinRe) / (ImageWidth - 1);
  170. double Im_factor = (MaxIm - MinIm) / (ImageHeight - 1);
  171. //unsigned MAX_ITERATIONS = 100;
  172.  
  173. /*int r = 0x00, g = 0x00, b = 0x00;*/
  174.  
  175.  
  176. for (unsigned y = start; y<end; ++y)
  177. {
  178. double c_im = MaxIm - y*Im_factor;
  179. for (unsigned x = 0; x<ImageWidth; ++x)
  180. {
  181. double c_re = MinRe + x*Re_factor;
  182.  
  183. double Z_re = c_re, Z_im = c_im;
  184. bool isInside = true;
  185. for (unsigned n = 0; n<MAX_ITERATIONS; ++n)
  186. {
  187. double Z_re2 = Z_re*Z_re, Z_im2 = Z_im*Z_im;
  188. if (Z_re2 + Z_im2 > 4)
  189. {
  190. isInside = false;
  191. break;
  192. }
  193. Z_im = 2 * Z_re*Z_im + c_im;
  194. Z_re = Z_re2 - Z_im2 + c_re;
  195.  
  196. //unsigned int colour = r | (r << 8) | (r << 16);
  197. //if (n < MAX_ITERATIONS / 2)
  198. // vertex.color = sf::Color(0, 153, 68, 255);
  199. if (n > MAX_ITERATIONS / 2)
  200. vertex.color = sf::Color(220, 53, 168, 255);
  201. }
  202.  
  203. if (isInside)
  204. {
  205.  
  206. //vertex.color = sf::Color(r, g, b, 255);
  207.  
  208. vertex.position = sf::Vector2f(x, y);
  209. mutex.lock();
  210. varray.append(vertex);
  211. mutex.unlock();
  212. }
  213. }
  214. }
  215.  
  216.  
  217.  
  218. }
  219.  
  220. void slicer(double left, double right, double top, double bottom)
  221. {
  222. int test = -1;
  223. double start = 0, end = 0;
  224. const size_t nthreads = std::thread::hardware_concurrency(); //detect how many threads cpu has
  225. {
  226. int sliceSize = 800 / nthreads;
  227.  
  228. std::cout << "CPU has " << nthreads << " threads" << std::endl;
  229. std::vector<std::thread> threads(nthreads);
  230.  
  231. for (int t = 0; t < nthreads; t++)
  232. {
  233.  
  234.  
  235.  
  236. threads[t] = std::thread(std::bind(
  237. [&]()
  238. {
  239. //std::cout << "test: " << t << "\n";
  240. mutex2.lock();
  241. test++;
  242.  
  243. start = (test) * sliceSize;
  244. end = ((test + 1) * sliceSize);
  245. std::cout << "start: " << start << "\n";
  246. std::cout << "end: " << end << "\n";
  247. mutex2.unlock();
  248.  
  249.  
  250. compute_mandelbrot(left, right, top, bottom, start, end);
  251.  
  252.  
  253. }));
  254. }
  255. std::for_each(threads.begin(), threads.end(), [](std::thread& x) {x.join(); }); //join threads
  256. }
  257. }
  258.  
  259.  
  260. void oldSlicer(double left, double right, double top, double bottom, int slices)
  261. {
  262. int sliceSize = 960 / slices;
  263. double start = 0, end = 0;
  264. for (int i = 0; i < slices; i++)
  265. {
  266. start = i * sliceSize;
  267. end = ((1 + i) * sliceSize);
  268.  
  269. //sf::Thread thread(std::bind(&compute_mandelbrot, left, right, top, bottom, start, end));
  270. //std::cout << "I am thread " << i+1 << std::endl;
  271. //thread.launch();
  272. //thread.wait();
  273.  
  274. thrd.push_back(thread(compute_mandelbrot, left, right, top, bottom, start, end));
  275.  
  276. }
  277.  
  278. for (int i = 0; i < slices; i++)
  279. {
  280. thrd[i].join();
  281. }
  282. thrd.clear();
  283.  
  284. compute_mandelbrot(left, right, top, bottom, 0, 800);
  285. }
  286. void handleInmput()
  287. {
  288. if (sf::Keyboard::isKeyPressed(sf::Keyboard::Z))
  289. {
  290. varray.clear();
  291.  
  292. //left += 0.15 * factor;
  293. //right -= 0.1 * factor;
  294. //top -= 0.1 * factor;
  295. //bottom += 0.15 * factor;
  296. //factor *= 0.9349;
  297. //MAX_ITERATIONS += 5;
  298.  
  299. left += 0.15 * factor;
  300. right -= 0.1 * factor;
  301. top += 0.1 * factor;
  302. factor *= 0.9349;
  303. //bottom += 0.15 * factor;
  304. compute_mandelbrot2(left, right, top, 1, 1, 1);
  305. //compute_mandelbrot2(left, right, top, 1, 1, 1);
  306.  
  307. //MAX_ITERATIONS += 1;
  308.  
  309. cout << "iter: " << MAX_ITERATIONS << endl;
  310. cout << "left: " << left << endl;
  311. cout << "right: " << right << endl;
  312. cout << "top: " << top << endl << endl;
  313.  
  314. //the_clock::time_point start = the_clock::now();
  315. ////slicer((-2.0 + i), (1.0 - i), (1.125 - i), (-1.125 + i), 8); //slicer
  316. ////slicer((-0.751085), (-0.734975), (0.118378), (0.134488));
  317. ////slicer(-2.0, 1.0, 1.125, -1.125); //slicer
  318. ////slicer(left, right, 1.125, -1.125); //slicer
  319. //slicer(left, right, top, bottom); //slicer
  320. //the_clock::time_point end = the_clock::now();
  321. //auto time_taken = duration_cast<milliseconds>(end - start).count();
  322. //cout << "Computing the Mandelbrot set took " << time_taken << " ms." << endl;
  323.  
  324. }
  325. else if (sf::Keyboard::isKeyPressed(sf::Keyboard::X)) //zoom in
  326. {
  327. left += 0.15 * factor;
  328. right -= 0.1 * factor;
  329. top += 0.1 * factor;
  330. factor *= 0.9349;
  331.  
  332. cout << "iter: " << MAX_ITERATIONS << endl;
  333. cout << "left: " << left << endl;
  334. cout << "right: " << right << endl;
  335. cout << "top: " << top << endl << endl;
  336. }
  337. else if (sf::Keyboard::isKeyPressed(sf::Keyboard::C)) //add iterations for clarity
  338. {
  339. //the_clock::time_point start = the_clock::now();
  340.  
  341. //compute_mandelbrot2(left, right, top, 1, 1, 1);
  342.  
  343. //the_clock::time_point end = the_clock::now();
  344. //auto time_taken = duration_cast<milliseconds>(end - start).count();
  345. //cout << "Computing the Mandelbrot set took " << time_taken << " ms." << endl;
  346. MAX_ITERATIONS += 10;
  347.  
  348.  
  349. cout << "iter: " << MAX_ITERATIONS << endl;
  350. //sf::Keyboard::is
  351. }
  352. else if (sf::Keyboard::isKeyPressed(sf::Keyboard::V)) //set different parameters
  353. {
  354. left = -3;
  355. right = 1.5;
  356. top = -1.2;
  357.  
  358. MAX_ITERATIONS = 20;
  359.  
  360. //left = -0.195853;
  361. //right = -0.286098;
  362. //top = 0.336098;
  363.  
  364. //MAX_ITERATIONS = 20;
  365. }
  366. else if (sf::Keyboard::isKeyPressed(sf::Keyboard::N))
  367. {
  368. varray.clear();
  369. the_clock::time_point start = the_clock::now();
  370. compute_mandelbrot2(left, right, top, 1, 1, 1); //without slicer
  371. the_clock::time_point end = the_clock::now();
  372. auto time_taken = duration_cast<milliseconds>(end - start).count();
  373. cout << "Computing the Mandelbrot set took " << time_taken << " ms." << endl;
  374. }
  375. else if (sf::Keyboard::isKeyPressed(sf::Keyboard::M))
  376. {
  377. varray.clear();
  378. the_clock::time_point start = the_clock::now();
  379. slicer(left, right, top, bottom); //with slicer
  380. the_clock::time_point end = the_clock::now();
  381. auto time_taken = duration_cast<milliseconds>(end - start).count();
  382. cout << "Computing the Mandelbrot set took " << time_taken << " ms." << endl;
  383. }
  384. }
  385.  
  386.  
  387. int main(int argc, char* argv[])
  388. {
  389.  
  390.  
  391. sf::RenderWindow window(sf::VideoMode(960, 960), "SFML-Mandelbrot");
  392.  
  393. compute_mandelbrot2(left, right, top, 1, 1, 1);
  394.  
  395. while (window.isOpen())
  396. {
  397. sf::Event event;
  398. while (window.pollEvent(event))
  399. {
  400. if (event.type == sf::Event::Closed)
  401. {
  402.  
  403. window.close();
  404. }
  405. }
  406.  
  407. handleInmput();
  408.  
  409.  
  410. window.clear();
  411. window.draw(varray);
  412. window.display();
  413.  
  414.  
  415.  
  416. }
  417. return 0;
  418. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement