Ich habe eine SVG defs Gruppe (erstellt mit Hilfe von d3js) verwendet, um ein komplexes Element zu erstellen, das ich instanziieren und dann ändern möchte, aber von all meinen Spielen und Recherchen ist die einzige Schlussfolgerung, die ich zeichnen kann ist eigentlich eine verknüpfte Instanz, keine unabhängige Instanz. Ich bin sicher, es gibt tief technische Computer-Science-Namen für diese, aber ich bin sicher, Sie wissen, was ich meine: o)Gibt es eine Möglichkeit, ein SVG USE nachträglich modifizierbar (oder eine andere Technik) zu machen?
Ich habe einige Beispielcode erstellt, um das Problem zu veranschaulichen, das ich habe. Es gibt eine Gruppe, die in einer SVG DEFS-Sektion definiert ist, die aus zwei Quadraten und einem Textelement besteht. Dann wird eine ähnliche Struktur unter dem SVG-Container erstellt. Schließlich habe ich mit Hilfe von USE + XLINK: HREF zwei Kopien der Gruppenelemente erstellt, die die zwei Quadrate und den Text enthalten. Ursprünglich hatten alle Deklarationen Klassen, die auch im Abschnitt STYLE angegeben wurden.
Um das Problem zu veranschaulichen und damit zu experimentieren, habe ich einige Elementmodifikationen hinzugefügt und auf die Objekte mit jQuery zugegriffen (ich fand es einfacher als d3 oder direkte Javascript-DOM-Manipulation). Es scheint mir verboten zu sein, innerhalb der Hierarchien, die von DEFS instanziiert wurden, mit USE abzufragen, aber ich kann auf die volle Hierarchie der direkt gezeichneten Bereiche zugreifen. Dies ist ein Problem in meinem Projekt, da ich eine Reihe kleinerer Formabweichungen bei häufig vorkommenden Unterelementen habe, die jedoch jeweils unterschiedlich gekennzeichnet sind. Ich möchte nicht jede lange Hand erstellen, es sei denn, ich muss sogar programmatisch. Im Idealfall möchte ich nur ein paar Unterkomponenten auf Opazität = 0 umschalten und Texte und Beschreibungen mit d3js einfügen. Welche Alternative zu DEFS/USE gibt es, die bedeutet, dass ich eine kopierte Instanz nicht zu einer verknüpften Instanz machen kann?
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>
Testing how to navigate 'DEFS' & 'USE' to change attributes of the elements in the instance
</title>
<script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script>
<script src="https://code.jquery.com/jquery-1.12.4.js"></script>
<!--script src="https://code.jquery.com/ui/1.12.0/jquery-ui.js"></script-->
<style>
.pinkBox {
fill: #fdc4fe;
stroke: black;
stroke-width: 2px;
stroke-linecap: square;
stroke-linejoin: round;
opacity: 1;
}
.redBox {
fill: #fb198e;
stroke: black;
stroke-width: 2px;
stroke-linecap: square;
stroke-linejoin: round;
opacity: 1;
}
.lightGreenBox {
fill: #bdf07c;
stroke: black;
stroke-width: 2px;
stroke-linecap: square;
stroke-linejoin: round;
opacity: 1;
}
.GreenBox {
fill: #4a9a03;
stroke: black;
stroke-width: 2px;
stroke-linecap: square;
stroke-linejoin: round;
opacity: 1;
}
.greyText{
font-family:sans-serif;
font-size: 12px;
fill: grey;
}
</style>
</head>
<body>
<script type="text/javascript">
var svgContainer = d3.select("body")
.append("svg")
.attr("width", 1024)
.attr("height", 768);
var BG = svgContainer.append("rect")
.attr("width", "100%")
.attr("height", "100%")
.attr("fill", "#2d2525");
var reusables = svgContainer.append("defs")
var USEgrp = reusables.append("g")
//.attr("id","Ugrp")
.attr("transform","translate(20,20)");
var RB = USEgrp.append("rect")
//.attr("id","RB")
.attr("x","10")
.attr("y","10")
.attr("height","100")
.attr("width","100")
.attr("rx","10")
.attr("ry","10")
//.attr("class","redBox")
;
var BB = USEgrp.append("rect")
//.attr("id","BB")
.attr("x","120")
.attr("y","10")
.attr("height","100")
.attr("width","100")
.attr("rx","10")
.attr("ry","10")
//.attr("class","blueBox")
;
var Txt = USEgrp.append("text")
//.attr("id","TxtU")
.attr("x",250)
.attr("y",70)
//.attr("class","greyText")
//.attr("fill","white")
.text("These boxes are 'USEed' from the prototype in the 'DEFS' section");
var canvasgrp = svgContainer.append("g")
.attr("id","Cgrp")
.attr("transform","translate(0,0)");
var GB = canvasgrp.append("rect")
.attr("id","GB")
.attr("x","30")
.attr("y","350")
.attr("height","100")
.attr("width","100")
.attr("rx","10")
.attr("ry","10")
.attr("class","greenBox")
;
var OB = canvasgrp.append("rect")
.attr("id","OB")
.attr("x","140")
.attr("y","350")
.attr("height","100")
.attr("width","100")
.attr("rx","10")
.attr("ry","10")
.attr("class","orangeBox")
;
var Txt2 = canvasgrp.append("text")
.attr("id","TxtC")
.attr("x",270)
.attr("y",400)
.attr("class","greyText")
.attr("fill","white")
.text("These boxes drawn directly to SVG canvas");
var inst1 = svgContainer.append("use")
.attr("xlink:href","#Ugrp")
.attr("id","inst1")
.attr("transform","translate(0,0)");
var inst2 = svgContainer.append("use")
.attr("xlink:href","#Ugrp")
.attr("id","inst1")
.attr("transform","translate(0,150)");
var USEbox1 = ($("g").filter("#Ugrp").children().first().attr("stroke","yellow").attr("stroke-width","6"));
var USEtext = ($("g").filter("#Ugrp").children().last().attr("fill","brown"));
var USEbox2 = ($("g").filter("#Ugrp").children().first().next().attr("style",".GreenBox"));
var SVGbox1 = ($("g").filter("#Cgrp").children().first().attr("stroke","pink").attr("stroke-width","6"));
var SVGtext = ($("g").filter("#Cgrp").children().last().attr("fill","cyan"));
var SVGbox2 = ($("g").filter("#Cgrp").children().first().next().attr("stroke","magenta").attr("stroke-width","1"));
</script>
verfügbar Sie wollen nicht verwenden, möchten Sie einige Basisobjekt in Javascript zu bekommen, es klonen und dann den Klon ändern. –
Robert, danke für deine schnelle Antwort (wie immer :-)). Bitte würdest du Code hinzufügen, um zu verdeutlichen, was du meinst? (oder einen Link zu einem Beispiel in?) Ich dachte, JS-Objekte könnten nützlich sein, aber ich kann das Zusammenspiel mit dem SVG nicht visualisieren! – Greg
getElementById ("Sache"). Clone() dann ändern Sie es und fügen Sie es mit appendChild an –