/** Variante de primitives.h pour dessiner dans Jupyter, sans la SFML CAVEAT: Ceci est une pure rustine, du genre que l'on bricole entre minuit et 3h du mat pour sauver un TP, en attendant une solution pérenne: backend Jupyter pour SFML, utilisation de xcanvas (https://github.com/martinRenou/xcanvas) l'équivalent de ipycanvas (https://ipycanvas.readthedocs.io/) pour C++, ou possibilité de lancer des applications graphiques sur JupyterHub. NE PRENNEZ PAS EXEMPLE DESSUS! **/ #include <iostream> #include <sstream> #include <xwidgets/xhtml.hpp> /** Execute javascript code in the Jupyter window **/ void execute_javascript(std::string js) { nl::json mime_bundle; mime_bundle["application/javascript"] = js; ::xeus::get_interpreter().display_data(mime_bundle, nl::json::object(), nl::json::object()); } void load_javascript_library() { execute_javascript(R"js( document.primitives_get_context = function() { return document.primitives_canvas.getContext('2d'); } document.primitives_draw_rectangle = function(x, y, width, height, color) { var ctx = document.primitives_get_context(); ctx.strokeStyle = color; ctx.strokeRect(x, y, width, height); } document.primitives_draw_filled_rectangle = function(x, y, width, height, color) { var ctx = document.primitives_get_context(); ctx.fillStyle = color; ctx.fillRect(x, y, width, height); } document.primitives_draw_point = function(x, y, color) { document.primitives_draw_rectangle(x, y, 1, 1, color); } )js"); } namespace Color { using Color = std::string; Color White = "white"; Color Red = "red"; Color Yellow = "yellow"; Color Green = "#00FF00"; Color Black = "black"; } class Point { public: int x; int y; Point(int _x, int _y): x(_x), y(_y) {}; Point(double _x, double _y): x(_x), y(_y) {}; }; class VideoMode { public: int width; int height; VideoMode(int w, int h): width(w), height(h) {} }; class RenderWindow { xw::html html; VideoMode vm; public: // A buffer of javascript commands to execute std::ostringstream buffer; RenderWindow(VideoMode _vm, std::string s) : vm(_vm) { std::ostringstream canvas; // canvas << "<canvas id='primitives_canvas'" // << " width=" << vm.width << " height=" << vm.height // << " style='border:1px solid #000000;'></canvas>"; load_javascript_library(); buffer << "document.primitives_canvas = document.getElementById('primitives_canvas');"; buffer << "document.primitives_canvas.height = " << vm.height << ";"; buffer << "document.primitives_canvas.width = " << vm.width << ";"; buffer << "document.primitives_canvas.style = 'border:1px solid #000000';"; display(); // Disabled until xwidgets is functional again // For now, the canvas needs to be created in a markdown cell of the notebook // html.value = canvas.str(); // html.display(); } // Update the canvas by executing all javascript commands in the buffer void display() { execute_javascript(buffer.str()); buffer = std::ostringstream(); } // Clear the canvas with the given color void clear(Color::Color color) { buffer << "document.primitives_draw_filled_rectangle(0, 0, " << vm.width << ", " << vm.height << ", '" << color << "');"; display(); } }; void draw_point(RenderWindow &window, Point p, Color::Color color) { window.buffer << "document.primitives_draw_point(" << p.x << ", " << p.y << ", '" << color << "');"; }