gempyre  1.7.1
gempyre.h
Go to the documentation of this file.
1 #ifndef GEMPYRE_H
2 #define GEMPYRE_H
3 
4 #include <string>
5 #include <unordered_map>
6 #include <functional>
7 #include <memory>
8 #include <chrono>
9 #include <any>
10 #include <optional>
11 #include <vector>
12 #include <tuple>
13 #include <string_view>
14 #include <sstream>
15 #include <gempyre_types.h>
16 
30 using namespace std::chrono_literals;
31 
32 
33 namespace Gempyre {
34 
35  class Ui;
36  class Server;
37  class Semaphore;
38  class TimerMgr;
39  class GempyreInternal;
40  enum class CloseStatus;
41  enum class WindowType;
42  template <class T> class EventQueue;
43  template <class T> class IdList;
44  template <class K, class T> class EventMap;
45 
47  GEMPYRE_EX void set_debug(bool isDebug = true);
48 
50  GEMPYRE_EX void setJNIENV(void* env, void* obj);
52  GEMPYRE_EX std::tuple<int, int, int> version();
53 
54  struct Event;
55  class Element;
56 
57  class GEMPYRE_EX HtmlStream : public std::ostringstream {
58  public:
59  ~HtmlStream();
60  HtmlStream& flush();
61 
62  #ifdef AUTO_UINT8_STREAM // obviously works, but gives warnings
63  template<typename T>
64  HtmlStream& operator<<(T&& value) {
65  if constexpr (std::is_same_v<std::decay_t<T>, int8_t>) {
66  static_cast<std::ostringstream&>(*this) << static_cast<int>(value);
67  } else if constexpr (std::is_same_v<std::decay_t<T>, uint8_t>) {
68  static_cast<std::ostringstream&>(*this) << static_cast<unsigned int>(value);
69  } else {
70  static_cast<std::ostringstream&>(*this) << std::forward<T>(value);
71  }
72  return *this;
73  }
74  #endif
75 
76  private:
77  using FlushFunction = std::function<void (HtmlStream&)>;
78  friend Element;
79  HtmlStream(const FlushFunction& flush);
80  const FlushFunction m_flush;
81  };
82 
84  class GEMPYRE_EX Element {
85  public:
87  using Attributes = std::unordered_map<std::string, std::string>;
89  using Values = std::unordered_map<std::string, std::string>;
91  using Elements = std::vector<Element>;
93  using SubscribeFunction = std::function<void(const Event&)>;
96 
97  public:
99  Element(const Element& other) = default;
101  Element(Element&& other) = default;
103  Element& operator=(const Element& other) {m_ui = other.m_ui; m_id = other.m_id; return *this;}
105  Element& operator=(Element&& other) {m_ui = other.m_ui; m_id = std::move(other.m_id); return *this;}
106 
112  Element(Ui& ui, std::string_view id);
118  Element(Ui& ui, std::string_view id, std::string_view htmlElement, const Element& parent);
123  Element(Ui& ui, std::string_view htmlElement, const Element& parent);
125  virtual ~Element();
127  [[nodiscard]] const Ui& ui() const { return *m_ui; }
129  [[nodiscard]] Ui& ui() { return *m_ui;}
131  [[nodiscard]] std::string id() const {return m_id;}
142  Element& subscribe(std::string_view name, const SubscribeFunction& handler, const std::vector<std::string>& properties = {}, const std::chrono::milliseconds& throttle = 0ms);
146  Element& set_html(std::string_view htmlText);
154  Element& set_attribute(std::string_view attr, std::string_view value);
158  Element& set_attribute(std::string_view attr);
160  std::optional<Attributes> attributes() const;
165  Element& set_style(std::string_view style, std::string_view value);
169  Element& remove_attribute(std::string_view attr);
172  [[nodiscard]] std::optional<Values> styles(const std::vector<std::string>& keys) const;
174  [[nodiscard]] std::optional<Elements> children() const;
176  [[nodiscard]] std::optional<Values> values() const;
178  [[nodiscard]] std::optional<std::string> html() const;
180  void remove();
182  [[nodiscard]] std::optional<std::string> type() const;
184  [[nodiscard]] std::optional<Rect> rect() const;
186  [[nodiscard]] std::optional<Element> parent() const;
187  protected:
189  const GempyreInternal& ref() const;
190  GempyreInternal& ref();
191  static const std::string generateId(std::string_view prefix);
192  protected:
193  Ui* m_ui;
194  std::string m_id;
196  private:
197  friend class GempyreInternal;
198  };
199 
201  struct Event {
203  static constexpr auto MOUSE_MOVE = "mousemove";
205  static constexpr auto MOUSE_UP = "mouseup";
207  static constexpr auto MOUSE_DOWN = "mousedown";
209  static constexpr auto MOUSE_CLICK = "click";
211  static constexpr auto MOUSE_DBLCLICK = "dblclick";
213  static constexpr auto KEY_UP = "keyup";
215  static constexpr auto KEY_PRESS = "keypress";
217  static constexpr auto KEY_DOWN = "keydown";
219  static constexpr auto SCROLL = "scroll";
221  static constexpr auto CLICK = "click";
223  static constexpr auto CHANGE = "change";
225  static constexpr auto SELECT = "select";
227  static constexpr auto FOCUS = "focus";
229  static constexpr auto BLUR = "blur";
231  static constexpr auto FOCUS_IN = "focusin";
233  static constexpr auto FOCUS_OUT = "focusout";
235  static constexpr auto LOAD = "load";
237  static constexpr auto RESIZE = "resize";
240  static constexpr auto REMOVED = "element_removed";
241 
245  std::unordered_map<std::string, std::string> properties;
246  };
247 
249  class GEMPYRE_EX Ui {
250  public:
252  enum UiFlags : unsigned {
253  NoResize = 0x1,
254  FullScreen = 0x2,
255  Hidden = 0x4,
256  Frameless = 0x8,
257  Minimized = 0x10,
258  OnTop = 0x20,
259  ConfirmClose = 0x40,
260  TextSelect = 0x80,
261  EasyDrag = 0x100,
262  Transparent = 0x200
263  };
264 
266  using FileMap = std::vector<std::pair<std::string, std::string>>;
267 
269  using TimerId = int;
270  static constexpr unsigned short UseDefaultPort = 0; //zero means default port
271  static constexpr auto UseDefaultRoot = ""; //zero means default root
273 
279  Ui(const FileMap& filemap, std::string_view indexHtml, unsigned short port = UseDefaultPort, std::string_view root = UseDefaultRoot);
280 
288  Ui(const FileMap& filemap, std::string_view indexHtml, std::string_view browser, std::string_view browser_params, unsigned short port = UseDefaultPort, std::string_view root = UseDefaultRoot);
289 
300  Ui(const FileMap& filemap, std::string_view indexHtml, std::string_view title, int width, int height, unsigned flags = 0,
301  const std::unordered_map<std::string, std::string>& ui_params = {}, unsigned short port = UseDefaultPort, std::string_view root = UseDefaultRoot);
302 
304  ~Ui();
305  Ui(const Ui& other) = delete;
306  Ui(Ui&& other) = delete;
307 
309  void exit();
311  [[deprecated("Prefer exit")]] void close();
312 
314  using ExitFunction = std::function<void ()>;
316  using ReloadFunction = std::function<void ()>;
318  using OpenFunction = std::function<void ()>;
320  using ErrorFunction = std::function<void (const std::string& element, const std::string& info)>;
321 
322 
326  ExitFunction on_exit(const ExitFunction& onExitFunction);
327 
331  ReloadFunction on_reload(const ReloadFunction& onReloadFunction);
332 
338  OpenFunction on_open(const OpenFunction& onOpenFunction);
342  ErrorFunction on_error(const ErrorFunction& onErrorFunction);
343 
348  void run();
349 
352  void set_logging(bool logging);
355  void eval(std::string_view eval);
357  void debug(std::string_view msg);
359  void alert(std::string_view msg);
363  void open(std::string_view url, std::string_view name = "");
364 
369  TimerId start_periodic(const std::chrono::milliseconds& ms, const std::function<void (TimerId id)>& timerFunc);
374  TimerId start_periodic(const std::chrono::milliseconds& ms, const std::function<void ()>& timerFunc);
375 
380  TimerId after(const std::chrono::milliseconds& ms, const std::function<void (TimerId id)>& timerFunc);
381 
386  TimerId after(const std::chrono::milliseconds& ms, const std::function<void ()>& timerFunc);
387 
389  bool cancel_timer(TimerId timerId);
390 
391 
393  [[nodiscard]] Element root() const;
394 
396  [[nodiscard]] std::string address_of(std::string_view filepath) const;
397 
399  [[nodiscard]] std::optional<Element::Elements> by_class(std::string_view className) const;
400 
402  [[nodiscard]] std::optional<Element::Elements> by_name(std::string_view className) const;
403 
405  [[nodiscard]] std::optional<std::pair<std::chrono::microseconds, std::chrono::microseconds>> ping() const;
406 
408  // do extension call - document upon request
409  void extension_call(std::string_view callId, const std::unordered_map<std::string, std::any>& parameters);
410  // get value from extension - document upon request
411  [[nodiscard]] std::optional<std::any> extension_get(std::string_view callId, const std::unordered_map<std::string, std::any>& parameters);
413 
417  [[nodiscard]] std::optional<std::vector<uint8_t>> resource(std::string_view url) const;
418 
423  bool add_file(std::string_view url, std::string_view file);
424 
428  std::optional<std::string> add_file(std::string_view file);
429 
434  bool add_data(std::string_view url, const std::vector<uint8_t>& data);
435 
440  static std::optional<std::string> add_file(FileMap& map, std::string_view filename);
441 
443  void begin_batch();
444 
446  void end_batch();
447 
449  void set_timer_on_hold(bool on_hold);
450 
452  [[nodiscard]] bool is_timer_on_hold() const;
453 
455  [[nodiscard]] std::optional<double> device_pixel_ratio() const;
456 
458  void set_application_icon(const uint8_t* data, size_t dataLen, std::string_view type);
459 
461  void resize(int width, int height);
462 
464  void set_title(std::string_view name);
465 
467  static Ui::FileMap to_file_map(const std::vector<std::string>& filenames);
468 
470  void flush();
471 
473  bool available(std::string_view id) const;
474 
475 
477  // for testing
478  void resume();
479  // for testing
480  void suspend();
481  // for testing
482  bool ui_available() const;
484 
485  private:
486  Ui(const FileMap& filemap, std::string_view indexHtml,
487  unsigned short port, std::string_view root,
488  const std::unordered_map<std::string, std::string>& parameters, WindowType windowType);
489  const GempyreInternal& ref() const;
490  GempyreInternal& ref();
491  private:
492  friend class Element;
493  std::unique_ptr<GempyreInternal> m_ui;
494  };
495 }
496 
497 #endif // GEMPYRE_H
Represents all HTML elements on UI.
Definition: gempyre.h:84
std::function< void(const Event &)> SubscribeFunction
Callback function for event subscriptions.
Definition: gempyre.h:93
Element & operator=(const Element &other)
Copy operator.
Definition: gempyre.h:103
Element & remove_attribute(std::string_view attr)
Remove attribute.
Element & operator=(Element &&other)
Move operator.
Definition: gempyre.h:105
Element & set_attribute(std::string_view attr, std::string_view value)
Set HTML a attribute of this element.
Element(Ui &ui, std::string_view id, std::string_view htmlElement, const Element &parent)
Constructor for exiting elements.
virtual ~Element()
Destructor.
std::optional< Values > styles(const std::vector< std::string > &keys) const
Get element styles.
std::unordered_map< std::string, std::string > Attributes
Attribute key, value pairs.
Definition: gempyre.h:87
Element & subscribe(std::string_view name, const SubscribeFunction &handler, const std::vector< std::string > &properties={}, const std::chrono::milliseconds &throttle=0ms)
Subscribe UI event.
Element & set_html(std::string_view htmlText)
Set HTML text value of the element.
std::string id() const
Get id of element.
Definition: gempyre.h:131
std::optional< std::string > html() const
Get HTML value bound to this element (does not apply all elements)
std::optional< Attributes > attributes() const
Get this element attributes.
std::optional< std::string > type() const
Get this element type, mostly a HTML tag.
Element(Ui &ui, std::string_view htmlElement, const Element &parent)
Constructor for exiting elements.
std::optional< Values > values() const
Applies to form elements only - receive values bound to the element.
std::optional< Element > parent() const
Parent of this element. If query fails, element is root or parent id is not set, nullopt is returned.
Element & set_attribute(std::string_view attr)
Set HTML a attribute of this element.
std::optional< Rect > rect() const
Get this element UI rect. I.e area it occupies on screen (if applicable)
const Ui & ui() const
Get Ui.
Definition: gempyre.h:127
Ui & ui()
Get Ui.
Definition: gempyre.h:129
Element(Element &&other)=default
Move constructor.
Element & set_style(std::string_view style, std::string_view value)
Set CSS style of this element.
std::vector< Element > Elements
Vector of Elements.
Definition: gempyre.h:91
void remove()
Remove this element from UI.
Element(Ui &ui, std::string_view id)
Constructor for existing elements.
Element(const Element &other)=default
Copy constructor.
std::optional< Elements > children() const
Get element children.
std::unordered_map< std::string, std::string > Values
Value key, value pairs.
Definition: gempyre.h:89
HtmlStream html_stream()
get a stream that writes to html part of this element
Definition: gempyre.h:44
Definition: gempyre.h:42
Definition: gempyre.h:57
Definition: gempyre.h:43
The application UI.
Definition: gempyre.h:249
void exit()
Application gracefully finish the event loop and exits.
std::vector< std::pair< std::string, std::string > > FileMap
Resource map type.
Definition: gempyre.h:266
void flush()
Write pending requests to UI - e.g. when eventloop thread is blocked.
void set_timer_on_hold(bool on_hold)
Set all timers to hold. Can be used to pause UI actions.
void debug(std::string_view msg)
Send a debug message to UI. Message is get received is set_logging is true.
static Ui::FileMap to_file_map(const std::vector< std::string > &filenames)
Read list files as a maps.
bool add_data(std::string_view url, const std::vector< uint8_t > &data)
Add a data into Gempyre to be accessed via url.
void eval(std::string_view eval)
Executes eval string in UI context.
std::optional< double > device_pixel_ratio() const
Get an native UI device pixel ratio.
bool is_timer_on_hold() const
Tells if timers are on hold.
std::optional< std::vector< uint8_t > > resource(std::string_view url) const
Read a resource.
std::optional< std::pair< std::chrono::microseconds, std::chrono::microseconds > > ping() const
Test function to measure round trip time.
void run()
Starts the event loop.
UiFlags
UI flags for a Window UI.
Definition: gempyre.h:252
void resize(int width, int height)
Resize, fail silently if backend wont support.
TimerId start_periodic(const std::chrono::milliseconds &ms, const std::function< void(TimerId id)> &timerFunc)
Start a periodic timer.
std::function< void()> OpenFunction
Function called on open.x.
Definition: gempyre.h:318
TimerId after(const std::chrono::milliseconds &ms, const std::function< void()> &timerFunc)
Starts a single shot timer.
Ui(const FileMap &filemap, std::string_view indexHtml, std::string_view title, int width, int height, unsigned flags=0, const std::unordered_map< std::string, std::string > &ui_params={}, unsigned short port=UseDefaultPort, std::string_view root=UseDefaultRoot)
Create a window UI.
void open(std::string_view url, std::string_view name="")
Opens an url in the UI view.
void set_logging(bool logging)
Set browser to verbose mode.
void close()
Requires Client window to close (that cause the application to close).
bool cancel_timer(TimerId timerId)
Stop a timer.
std::optional< Element::Elements > by_name(std::string_view className) const
Get elements by name.
std::function< void()> ReloadFunction
Function called on reload. (page reload)
Definition: gempyre.h:316
std::optional< Element::Elements > by_class(std::string_view className) const
Get elements by class name.
TimerId start_periodic(const std::chrono::milliseconds &ms, const std::function< void()> &timerFunc)
Start a periodic timer.
ExitFunction on_exit(const ExitFunction &onExitFunction)
The callback is called before before the eventloop exit.
bool available(std::string_view id) const
test if Element can be accessed. Note that in false it's may be in HTML, but not available in DOM tre...
~Ui()
Destructor.
void set_application_icon(const uint8_t *data, size_t dataLen, std::string_view type)
Set application icon, fail silently if backend wont support.
TimerId after(const std::chrono::milliseconds &ms, const std::function< void(TimerId id)> &timerFunc)
Starts a single shot timer.
OpenFunction on_open(const OpenFunction &onOpenFunction)
The callback is called on UI open.
std::string address_of(std::string_view filepath) const
Get a local file path an URL, can be used with open.
void end_batch()
Ends an UI read batch, push all stored messages at once.
void begin_batch()
Starts an UI write batch, no messages are sent to USER until endBatch.
Element root() const
Get a (virtual) root element.
void set_title(std::string_view name)
Set title, fail silently if backend wont support.
bool add_file(std::string_view url, std::string_view file)
Add a file data into Gempyre to be accessed via url.
void alert(std::string_view msg)
Show an alert window.
static std::optional< std::string > add_file(FileMap &map, std::string_view filename)
Add file data into map to be added as a map.
std::function< void(const std::string &element, const std::string &info)> ErrorFunction
Function called on UI error.
Definition: gempyre.h:320
ErrorFunction on_error(const ErrorFunction &onErrorFunction)
The callback called on UI error.
Ui(const FileMap &filemap, std::string_view indexHtml, unsigned short port=UseDefaultPort, std::string_view root=UseDefaultRoot)
Create UI using default ui app or gempyre.conf.
Ui(const FileMap &filemap, std::string_view indexHtml, std::string_view browser, std::string_view browser_params, unsigned short port=UseDefaultPort, std::string_view root=UseDefaultRoot)
Create a browser UI using given ui app and command line.
std::optional< std::string > add_file(std::string_view file)
Add a file data into Gempyre to be accessed via url.
std::function< void()> ExitFunction
Function called on exit.
Definition: gempyre.h:314
ReloadFunction on_reload(const ReloadFunction &onReloadFunction)
The callback is called on UI reload.
GEMPYRE_EX void set_debug(bool isDebug=true)
set debugging on/off
GEMPYRE_EX void setJNIENV(void *env, void *obj)
Internal for Android.
GEMPYRE_EX std::tuple< int, int, int > version()
Return current version.
Gempyre::dataT type
pixel type
Definition: gempyre_bitmap.h:36
Event received.
Definition: gempyre.h:201
std::unordered_map< std::string, std::string > properties
List of requested properties.
Definition: gempyre.h:245
Element element
element that has emitted the event, the same that did subscription.
Definition: gempyre.h:243
Rect.
Definition: gempyre_types.h:24