ด้วย JavaScript ฉันสามารถเปลี่ยนดัชนี / เลเยอร์ Z ขององค์ประกอบ SVG <g> ได้หรือไม่


86

สมมติว่าฉันมีรูปร่างประกอบสองสามแบบ ( <g>) ฉันต้องการที่จะสามารถคลิกและลากพวกเขาได้ แต่ฉันต้องการให้สิ่งที่ฉันกำลังลากอยู่ในขณะนี้ให้อยู่บนสุดของอีกอันในลำดับ Z ดังนั้นถ้าฉันลากมันไปทับอันอื่น หนึ่งควรถูกบดบัง



เป็นไปได้ที่จะซ้ำกันของSVG re-order z-index (Raphael optional)
Eliran Malka

คำตอบ:


114

ดัชนี Z ใน SVG ถูกกำหนดโดยลำดับที่องค์ประกอบที่ปรากฏในเอกสาร คุณจะต้องเปลี่ยนลำดับองค์ประกอบหากคุณต้องการนำรูปร่างที่เฉพาะเจาะจงไปไว้ด้านบน


1
@theonlygusti Elements ท้ายเอกสารจะอยู่ด้านบน หากคุณใช้ jQuery คุณควรจะสามารถใช้สิ่งต่างๆเช่น$('#thing-i-want-on-top').appendTo('#my-svg');
Adam Bradley

โดยพื้นฐานแล้วไม่มีทางลอยรูปร่างไปด้านบน (แกน z) เมื่อวางเมาส์เหนือ ... ?
chharvey

jQuery ไม่รองรับการเปลี่ยนลำดับของเส้นทาง SVG
Senthe

5
@chharvey คุณสามารถลอยสิ่งของขึ้นไปด้านบนได้โดยสั่งซื้อใหม่ - ต่อท้ายอีกครั้ง นี่คือตัวอย่างที่สวยงาม: codepen.io/osublake/pen/YXoEQe
Frazer Kirkman

36

อีกทางเลือกหนึ่งในการย้ายองค์ประกอบในต้นไม้คือการใช้<use>องค์ประกอบที่คุณเปลี่ยนxlink:hrefแอตทริบิวต์เพื่อให้คุณได้ลำดับ z ที่คุณต้องการ

นี่คือกระทู้เก่าในรายการส่งจดหมายsvg-developers ที่พูดถึงหัวข้อนี้ในบริบทที่ต้องการทำให้รูปร่างบางส่วนเคลื่อนไหว

อัปเดต:

<svg xmlns="http://www.w3.org/2000/svg" 
     xmlns:xlink="http://www.w3.org/1999/xlink"
     style="width:100%; height: 100%">
    <circle id="c1" cx="50" cy="50" r="40" fill="lime" />
    <rect id="r1" x="4" y="20" width="200" height="50" fill="cyan" />
    <circle id="c2" cx="70" cy="70" r="50" fill="fuchsia" />
    <use id="use" xlink:href="#c1" />
</svg>

ในตัวอย่างนี้องค์ประกอบ <use> เป็นองค์ประกอบสุดท้ายซึ่งทำให้เป็นองค์ประกอบที่อยู่หน้าสุด เราสามารถเลือกองค์ประกอบอื่น ๆ เพื่อทำหน้าที่เป็นส่วนหน้าได้ง่ายๆเพียงแค่เปลี่ยนxlink:hrefแอตทริบิวต์ ในตัวอย่างด้านบนเราเลือกวงกลมด้วยid="c1"ซึ่งทำให้ปรากฏเป็นองค์ประกอบที่อยู่บนสุด

ดูซอ .


1
คำตอบนี้จะเป็นมากมีประโยชน์มากขึ้นด้วยตัวอย่างหรือมีข้อมูลจากรายการทางไปรษณีย์ที่ (ซึ่งมีรั้วรอบขอบชิด)
Kyeotic

3
ใช้งานได้ แต่ทำให้คุณเพิ่มการใช้งานได้อย่างเหมาะสม หากคุณใช้คำแปล <use> จะไม่รู้เกี่ยวกับพวกเขา
Jochen Bedersdorfer

@JochenBedersdorfer ไม่แน่ใจว่าคุณหมายถึงอะไรคำแปลเกี่ยวข้องกับการสั่งซื้อ z อย่างไร
Erik Dahlström

ไม่ชัดเจนมากเกี่ยวกับเรื่องนั้น หากคุณใช้แท็ก <g> ซ้อนกับการแปลงคุณต้องแปลงพิกัดโดยใช้ getTransformToElement (.. ); (ดูเอกสาร SVG)
Jochen Bedersdorfer

3
xlink:hrefเลิกใช้แล้วตอนนี้เพิ่งhref
osvein

22

นี่เป็นคำถามเก่า แต่ ...

ใน FireFox (7+) และ Chrome (14+) คุณสามารถดึง svg_element ไปด้านบนได้ สิ่งนี้ไม่ได้ทำให้คุณมีอิสระในการควบคุมแกน z เต็มรูปแบบ แต่ก็ดีกว่าไม่มีอะไรเลย;)

เพียงต่อท้ายองค์ประกอบนั้นอีกครั้ง

var svg = doc.createElemNS('svg');
var circle = doc.createElemNS('circle');
var line = doc.createElemNS('line');

svg.appendChild(circle); // appends it
svg.appendChild(line);   // appends it over circle
svg.appendChild(circle); // redraws it over line now

ฉันคิดว่ามันจะเกิดข้อผิดพลาดหรืออะไรบางอย่าง

appendChild == แทนที่ตัวเอง == วาดใหม่


3
ไม่ใช่ข้อผิดพลาดเลย appendChildก่อนอื่นให้ลบออกจากพาเรนต์เก่าถ้ามีแม้ว่าจะเหมือนกับพาเรนต์ใหม่ก็ตามจากนั้นจึงเพิ่มไปยังรายการย่อยของพาเรนต์ใหม่
Potatoswatter

5

อีกวิธีหนึ่งที่ไม่ได้กล่าวถึงคือการใส่รายการ svg / ชุดของแต่ละรายการลงใน div คุณสามารถเปลี่ยน z-index ของ div ได้อย่างง่ายดาย

Fiddle: องค์ประกอบ SVG วนรอบด้วยดัชนี z สำหรับคอนเทนเนอร์

... กดปุ่มเพื่อ "ดัน" องค์ประกอบนั้นไปด้านหน้า (เทียบกับการทาสีใหม่ทั้งชุดและผลัก 1 องค์ประกอบไปด้านหน้า แต่ยังคงรักษาลำดับเดิมไว้ในโซลูชันที่ยอมรับ)

จะดีมากถ้ามีดัชนี z แบบสัมพัทธ์ ...

stackOverflow ต้องการให้ฉันใส่โค้ดถ้าเป็นลิงค์จาก jsfiddle? ... ook


5

ใช่คำสั่งคือสิ่งที่ระบุว่าวัตถุใดจะอยู่ตรงหน้าอีกฝ่าย ในการจัดการคำสั่งคุณจะต้องย้ายสิ่งต่างๆเกี่ยวกับ DOM มีตัวอย่างที่ดีในวิกิ SVG ที่https://www.w3.org/TR/SVG11/render.html#RenderingOrder


4
ลิงก์นั้นใช้งานไม่ได้อีกต่อไป ลิงค์นี้อธิบายแนวคิดเดียวกัน: ลิงค์
Steve


3

SVGใช้ "แบบจำลองจิตรกร" ในการเรนเดอร์ สีถูกนำไปใช้ในการดำเนินการต่อเนื่องกับอุปกรณ์เอาท์พุตเพื่อให้การดำเนินการแต่ละครั้งวาดลงบนพื้นที่บางส่วนของอุปกรณ์เอาต์พุต เมื่อพื้นที่ทับซ้อนกับพื้นที่ที่ทาสีไว้ก่อนหน้านี้สีใหม่บางส่วนหรือทั้งหมดจะบดบังสีเก่า - ลิงก์ไปยังสิ่งนี้


3

ใน SVG เพื่อให้ได้ดัชนี Z ที่ใหญ่ขึ้นคุณควรย้ายองค์ประกอบลงในโครงสร้าง DOM คุณสามารถทำได้ด้วย jQuery เลือกองค์ประกอบ SVG ลบออกแล้วต่อท้ายอีกครั้งในตำแหน่งที่คุณต้องการ:

$('g.element').remove().appendTo('svg');

2

ความคิดเห็นของ Adam Bradley ต่อคำตอบของ Sam นั้นตรงประเด็น มันใช้ jQuery แทน CSS เท่านั้น แต่เขาบอกว่า:

$('#thing-i-want-on-top').appendTo('#my-svg');

อย่างไรก็ตามสำหรับสิ่งที่ฉันกำลังสร้างฉันต้องการให้เส้นทาง SVG ของฉันอยู่เหนือเส้นทางอื่น ๆ ที่วางเมาส์เหนือ แต่ยังคงอยู่ใต้ข้อความ SVG ของฉัน นี่คือสิ่งที่ฉันคิดขึ้น:

$('#thing-i-want-on-top').insertBefore('#id-for-svg-text');

ทั้ง appendTo และ insertBefore จะย้ายองค์ประกอบของคุณไปยังตำแหน่งใหม่ทำให้คุณสามารถเปลี่ยนความลึกขององค์ประกอบ SVG ได้ตามต้องการ

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.