Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding "Export SVG" button #269

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open

Conversation

denilsonsa
Copy link

This is a very basic implementation of SVG export.

It looks into DOM elements to figure out the positions and dimensions,
and then re-creates the tables as plain SVG and .

Works fine on both Firefox and Chrome.

Known issues:

  • The positions are incorrect if the browser has some zoom applied. In
    fact, the display is already incorrect in the browser itself (the SVG
    paths are not correctly aligned with the elements).
  • Rounded corners are not supported. Implementing that (properly) would
    require SVG clipping or some extra tricks. Not worth the extra trouble
    for now.
  • The borders are 2-pixel wide because otherwise they would not align to
    the pixel grid (1-pixel border would cover two half pixels).
  • There are no translations for other languages.

Related issues:

This is a very basic implementation of SVG export.

It looks into DOM elements to figure out the positions and dimensions,
and then re-creates the tables as plain SVG <rect> and <text>.

Works fine on both Firefox and Chrome.

Known issues:

* The positions are incorrect if the browser has some zoom applied. In
fact, the display is already incorrect in the browser itself (the SVG
paths are not correctly aligned with the elements).
* Rounded corners are not supported. Implementing that (properly) would
require SVG clipping or some extra tricks. Not worth the extra trouble
for now.
* The borders are 2-pixel wide because otherwise they would not align to
the pixel grid (1-pixel border would cover two half pixels).
* There are no translations for other languages.

Related issues:

* ondras#131
* ondras#132
@denilsonsa
Copy link
Author

Idea for future refactoring (that I am not going to do):

Completely replace the HTML elements (the <div class="table"> and <table>) with SVG ones. This way, the display would always be correct, independent of the zoom, and exporting to SVG would become trivial.

For editing a table, we still need HTML elements, and that could be handled by a modal window. This way, the "diagram" will be 100% rendered through SVG, while the interactions are still HTML.

As bonus, it would be trivial (using the <use> element) to generate the minimap and keep it in-sync.

This may help further processing or editing, for whoever opens the SVG
file.

I've also added some CSS classes and some data attributes to the <g>
elements, as those can come handy if someone tries to process the SVG
through code.
@ondras
Copy link
Owner

ondras commented Jul 4, 2018

Hi @denilsonsa,

thanks a lot! This looks great. I am now packing for vacation, so I will completely review and merge this PR once I return.

Some initial observations:

The borders are 2-pixel wide because otherwise they would not align to
the pixel grid (1-pixel border would cover two half pixels).

What about the trick with 1-pixel border and positions offset by 0.5 pixels?

Completely replace the HTML elements (the <div class="table"> and <table>) with SVG ones. This way, the display would always be correct, independent of the zoom, and exporting to SVG would become trivial.

Yes, this would be the best approach. This is probably the first thing to do if I had time to maintain this more.

For editing a table, we still need HTML elements, and that could be handled by a modal window. This way, the "diagram" will be 100% rendered through SVG, while the interactions are still HTML.

Perhaps the <foreignElement> SVG feature would enable inline HTML?

@denilsonsa
Copy link
Author

denilsonsa commented Jul 4, 2018

Perhaps the <foreignElement> SVG feature would enable inline HTML?

<foreignObject>? Never used it, but seems like a good idea.

What about the trick with 1-pixel border and positions offset by 0.5 pixels?

I forgot to try that. But maybe that can/should be done if/when the entire rendering is moved to SVG.

I also forgot to add stroke-linejoin="round", that should make the border a bit rounded.

if I had time to maintain this more.

I know that feeling. ;)

Makes it easier to find them through JavaScript or CSS.
According to the following links, getBoundingClientRect() method returns
a DOMRect, which contains the x, y, width, height attributes. Thus, the
code will now avoid using left, top, bottom, right.

https://drafts.csswg.org/cssom-view/#dom-element-getboundingclientrect
https://drafts.fxtf.org/geometry-1/#domrect
Much better. Much less empty space. Much more useful.
@Zeldri
Copy link

Zeldri commented Jul 3, 2020

Any news on it ? Would be a cool feature :D

@ondras
Copy link
Owner

ondras commented Jul 13, 2020

Any news on it ? Would be a cool feature :D

Dammit, I have completely forgotten about this. @denilsonsa, is your code still working agains the current master branch? Is is safe to merge this?

@denilsonsa
Copy link
Author

It's been two years since I last touched the code, so I don't know. We have to rebase/merge the code and test. I'm not gonna do that right now, so feel free to check it if you have some time.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants