Load saved svg shapes and access them through javascript - javascript

I am trying to draw svg shapes, add events(click, drag etc.) and properties to the shapes and save them to server from my web application. I also want to load these saved shapes from the server and access their events and properties from my web application.
My Problems are:
A. I can not load a previously saved svg shape while I am drawing new ones at the same time. I am trying to load saved svg blocks by using .html(). I have tried using append also with same results.
In this JSFiddle link I have tried to create a similar scenario. Once you click Load Annotation Button, an svg block renders. But it erases the previous element.
B. Before loading the saved annotations, if you click the existing line, you will find that the element is being selected (alert message with the id of element). But after you add saved annotations to the svg block, you cannot find the elements by clicking on them.
there must be something I am doing wrong. Can you point it out please?

Related

Modify SVG in the background

I have SVG icons of some elements. These elements are for example road signals on the level crossing. If a road signal is shining RED light, I change the appropriate SVG element's fill to red.
Now I have these elements in a menu, and I want each of them to have it's icon, but also that this icon represents its lamp state. So when the lamp state changes, the icon at the appropriate element also changes.
I did this before in Java (GWT) and I did it by loading the icon into a variable in a helper class (SvgHelper) and then anytime I wanted to display icon of particular element anywhere, I called svgHelper.getIcon(element) and it modified the svg, that it has stored in a variable, (in the background) and then returned me new cloned SVGImage that I could the put anywhere. So I only had one icon, changed its state, cloned it and returned.
Now when I want to do it in javascript, it seems, that to work with the SVG in any way, it has to be in the DOM first.
Is there a way to work with the SVG "in the background" so that it is not in the DOM? Because I would rather change multiple SVG properties and once finished then put the SVG in the DOM. Also I target the elements by ID and there can be multiple of those icons on a single page, so the IDs would collide.
I tried using svg.js and import my svg from string, but from what I understood the library actually requires some div to work in, so it adds it to the DOM.
In java I was doing it using this library and since it is in the end compiled to JS, there should be a way to do it.
Since even the GWT library adds the SVG to the DOM, I ended up doing just that. So I have some object which I have in a DOM somewhere outside of the screen, target the element by ID, change its properties. Onec the SVG is ready, I put it in its destination using vuejs's v-html directive.

xml to svg dynamically

I have been searching for months now about this subject, but I can't find anything about it. What I'm looking for: I have sheetmusic on my screen, which is xml converted to svg with javascript. Now I want to make buttons with which I can manipulate the SVG that's displayed on the screen. For example: the music has lyrics underneath the notes and chords above it. Let's say I want to replace or remove them with an onclick button. All this temporarily, only on the screen.
I am currently working on a similar project. You have 2 approaches:
Directly modify SVG (hmmm not cool if you have complex objects)
Find out which SVG element is to be modified, find the corresponding id
in the XML structure, modify the XML node, "recompile" XML to SVG.
As a more performant way, you may compile only the node that changed and
then insert it in the SVG.
In order to select the element you want to apply an action on, you can set
a 'click' event listener on each selectable element.

fabricjs set image as background

I'm looking for a way for placing an object permanently to the back of the canvas.
I see that the various
canvas.sendBackwards(myObject)
canvas.sendToBack(myObject)
will send the object to the back of the canvas but if I add a new element and then send it backwards it will go beneath the other image and I need to avoid this. I cannot use canvas.setBackgroundImage because I'm creating a custom image class and setting it as backgroundImage will make me loose some functionality. I would like to set something like a z-index on the newly created image. For example, while initializing a new image I can set lockMovementX (and many others) to false or true, isn't there nothing like this for z-index of every canvas element, or do I have to push my background element to the back every time there's a change on the canvas?
I've run into the same situation - I want an image as a background layer yet don't want to apply it as a background image due to restricted functionality.
I did write a function for my application that re-stacks layers every-time there is new layer added. I set the name attribute to this layer so I could quickly identify what layer it is that needs to be sent to the back.
While this may seen inefficient, I've never had any performance issues related to this function. But also in my application I typically only have about 5 to 20 layers - typically on the lower end of that range.

multiple svg images in one file breaks text

I have a web app that uses SVG files to map various sorts of data onto our underlying experimental dataset. Each SVG file represents a mapping of one type of data to the experimental dataset and, in most of the pages on the site, they are displayed one at a time, with the various nodes carrying tooltips to make the maps more informative and links to associated data.
I would like to add a page where maps can be compared side-by-side, which means having multiple self-contained SVG's all on the same page. When I do this, however, the files seem to step on each others' toes in that only the first SVG on the page displays the correct text in the labels and axes. The rest appear to inherit the alphabet used in the first image, leaving the axes and labels garbled and nonsensical.
The snippet below shows how I am currently embedding the SVG's in the page. The object blocks are loaded up with SVG content via javascript/ajax when the user chooses a map on a dropdown menu. Everything functions correctly except for the noted problem with the SVG text.
<object id="map" name="map" class="compBuild" width=800 height=460></object>
Javascript:
$(document).on("change", ".db_field", function(e) {
var tmp = this.name.split("_");
var field = "map_" + tmp[1];
$(document.getElementById(field)).load(getSvgUrl($(this).val()));
// getSvgUrl just makes a Jquery AJAX call to obtain the location of
// the SVG file.
})
Maybe not obvious from the code given, but what actually happens on the page is that the menus and object blocks are dynamically generated, so the actual drop-downs and object blocks are addressed as mapSelect_X map_X, where X is a number appended when the block is created. (code not shown for the sake of brevity!)
I am wondering if there is a workaround for this as I would rather not convert the SVG files to images, since I would lose the functionality in the SVG's. Any help would be appreciated. Thanks!
Check that there are no duplicate id attributes in the two SVGs. ids must be unique on the page, otherwise any SVG features that use id references (like <use>, gradients etc) can't be trusted to point to the right thing.
Since Chrome and FF handle duplicate ids differently, a quick way to check this is the cause would be to see if the two browsers render the two-svg page differently.

Ajax calls to the server from canvas tag?

I have a rails server that has a page with canvas tag containing some images and user interface. Some objects inside the canvas have on mouse click events assigned. I wonder if it's possible to execute ajax calls on clicking the item then processing some data inside the ruby on the rails server and comeback to canvas changing some objects there inside? Like removing or changing their state etc? Once the canvas is initialized it looks like I can't access the objects inside anymore. I'm not quite profi in html5 :(
any advice is appreciated,
Thanks
Canvas is just an image created programmatically, therefore if you want specific regions of the canvas clickable my suggestion would be to position another html element ovetop of the canvas on a higher zindex. For example you could bind a click event to a div tag and then when you get your response from the server back you could update the canvas.

Categories

Resources