cppfw / svgdom

:house: SVG document object model in C++
MIT License
49 stars 17 forks source link

Implement class attribute and Element type #32

Closed JaimeIvanCervantes closed 4 years ago

JaimeIvanCervantes commented 4 years ago

Hi @igagis, here is a suggestion for 2 new features that would be somewhat easy to implement, but would go a long way for your developers:

  1. Implement class attribute: https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/class

  2. Implement a method to return the Element type (eg: Element::Type getType()). Eg, for the PathElement this method would return Element::Type::Path.

This information would be helpful if your developers need to access an Element by class or type (or already supported id), through Javascript or through a CSS selector.

I don't know for sure, but depending on my schedule, I might be able to help out ;).

igagis commented 4 years ago
  1. This is in the backlog for some time, it's a complex task, I haven't had time to implement it so far.
  2. one can implement Visitor for that purpose.
JaimeIvanCervantes commented 4 years ago

Oh, for (1) I was not referring to full <style> support, I do understand that this would be a major effort. I am only talking about having a std::vector<string> classes member as part of an Element for example, to complement the already supported id: https://github.com/igagis/svgdom/blob/master/src/svgdom/elements/Element.hpp#L17

For (2), I am referring more to a getType() method that would return a static element type, instead of doing this dynamically with a Visitor, since we already know the type at compile time. Maybe Element could have a virtual Element::Type getType() const method, and this method would be implemented per element.

igagis commented 4 years ago

1) Ok, this looks simple.

2) Visitor is actually made to add custom virtual methods to Element objects, so this virtual getType() can be implemented using Visitor. The other question is why do you want to know the element type, do you want to make some kind of switch(element_type)? The Visitor pattern is there to be able to perform custom actions on elements depending on their type, and to avoid those switch/case.

JaimeIvanCervantes commented 4 years ago

I understand your suggestion on using Visitor, but my use-case is completely different: (2) would be necessary to support CSS stylesheets, or any other type of selector capabilities. If CSS selectors, for instance, have to be stored in a vector, you're going to end up storing selectors in a data structure similar to this vector<variant<ElementType, Id, vector<Class>>> (this is very simplified). So, in other words, I don't want to "perform custom actions on elements", but instead, I would like to store element types on some selector structure :).

The Element type, combined with IDs and Classes, would be a stepping stone to future CSS support. Also, if you are interested, here is a real implementation of CSS selector parsing, that requires element type, classes, and IDs: https://github.com/emweb/wt/blob/master/src/Wt/Render/CssData_p.h#L18

igagis commented 4 years ago
  1. Done
  2. Added const std::string& get_tag() method to styleable and added the CSS support.