javascript - एचटीएमएल 5 कैनवास बनाम एसवीजी बनाम div




html5 svg (6)

फ्लाई पर तत्व बनाने और उन्हें चारों ओर स्थानांतरित करने में सक्षम होने के लिए सबसे अच्छा तरीका क्या है? उदाहरण के लिए, मान लें कि मैं एक आयत, सर्कल और बहुभुज बनाना चाहता हूं और फिर उन वस्तुओं का चयन करें और उन्हें चारों ओर ले जाएं।

मैं समझता हूं कि एचटीएमएल 5 तीन तत्व प्रदान करता है जो इसे संभव बना सकते हैं: svg , canvas और div । मैं जो करना चाहता हूं, उसके लिए कौन सा तत्व सर्वश्रेष्ठ प्रदर्शन प्रदान करेगा?

इन दृष्टिकोणों की तुलना करने के लिए, मैं तीन दृश्यमान समान वेब पेज बनाने की सोच रहा था जिनमें प्रत्येक के पास हेडर, पाद लेख, विजेट और टेक्स्ट सामग्री है। पहले पृष्ठ में विजेट पूरी तरह से canvas तत्व के साथ बनाया जाएगा, दूसरा पूरी तरह से svg तत्व के साथ, और तीसरा सादा div तत्व, HTML और CSS के साथ बनाया जाएगा।


संक्षिप्त उत्तर:

एसवीजी आपके लिए आसान होगा, क्योंकि चयन और इसे चारों ओर ले जाना पहले से ही बनाया गया है। एसवीजी ऑब्जेक्ट्स डोम ऑब्जेक्ट्स हैं, इसलिए उनके पास हैंडलर आदि पर क्लिक करें।

डीआईवी ठीक है लेकिन गुंजाइश है और बड़ी संख्या में भयानक प्रदर्शन लोड हो रहा है।

कैनवास का सर्वश्रेष्ठ प्रदर्शन हाथ से नीचे है, लेकिन आपको प्रबंधित स्थिति (ऑब्जेक्ट चयन, आदि) की सभी अवधारणाओं को स्वयं लागू करना होगा, या लाइब्रेरी का उपयोग करना होगा।

लंबा जवाब:

एचटीएमएल 5 कैनवास बस थोड़ा-मानचित्र के लिए एक ड्राइंग सतह है। आप आकर्षित करने के लिए सेट (एक रंग और रेखा मोटाई के साथ कहें), उस चीज़ को खींचें, और उसके बाद कैनवास को उस चीज़ का कोई ज्ञान नहीं है: यह नहीं पता कि यह कहां है या यह क्या है जिसे आपने अभी खींचा है, यह है बस पिक्सेल। यदि आप आयतों को आकर्षित करना चाहते हैं और उन्हें चारों ओर स्थानांतरित करना चाहते हैं या चयन करने योग्य हैं तो आपको उन सभी को स्क्रैच से कोड करना होगा, जिसमें याद रखना होगा कि आपने उन्हें आकर्षित किया है।

दूसरी ओर एसवीजी को प्रत्येक ऑब्जेक्ट के संदर्भों को बनाए रखना चाहिए जो इसे प्रस्तुत करता है। आपके द्वारा बनाए गए प्रत्येक एसवीजी / वीएमएल तत्व डीओएम में एक वास्तविक तत्व है। डिफ़ॉल्ट रूप से यह आपको आपके द्वारा बनाए गए तत्वों का अधिक बेहतर ट्रैक रखने की अनुमति देता है और डिफ़ॉल्ट रूप से माउस ईवेंट जैसी चीजों से निपटने में मदद करता है, लेकिन बड़ी संख्या में ऑब्जेक्ट्स होने पर यह महत्वपूर्ण रूप से धीमा हो जाता है

उन एसवीजी डोम संदर्भों का मतलब है कि आपके द्वारा खींची गई चीज़ों से निपटने के कुछ कदम आपके लिए किए जाते हैं। और वास्तव में बड़ी वस्तुओं को प्रस्तुत करते समय एसवीजी तेज होता है, लेकिन कई वस्तुओं को प्रस्तुत करते समय धीमा होता है।

कैनवास में शायद एक खेल तेज होगा। एसवीजी में शायद एक बड़ा नक्शा कार्यक्रम तेजी से होगा। यदि आप कैनवास का उपयोग करना चाहते हैं, तो मेरे पास चलने योग्य वस्तुओं को चलाने और here चलने पर कुछ ट्यूटोरियल here

तेजी से चीजों और भारी बिटमैप मैनिपुलेशन (एनीमेशन की तरह) के लिए कैनवास बेहतर होगा, लेकिन यदि आप बहुत सारी इंटरैक्टिविटी चाहते हैं तो अधिक कोड लेगा।

मैंने एचटीएमएल डीवी-निर्मित ड्राइंग बनाम कैनवास-निर्मित ड्राइंग पर संख्याओं का एक गुच्छा चलाया है। मैं प्रत्येक के लाभों के बारे में एक बड़ी पोस्ट कर सकता हूं, लेकिन मैं आपके विशिष्ट आवेदन के लिए विचार करने के लिए अपने परीक्षणों के कुछ प्रासंगिक परिणाम दूंगा:

मैंने कैनवास और एचटीएमएल डीआईवी टेस्ट पेज बनाए, दोनों में चलने योग्य "नोड्स" थे। कैनवास नोड्स वे ऑब्जेक्ट्स थे जिन्हें मैंने बनाया और जावास्क्रिप्ट में ट्रैक रखा। एचटीएमएल नोड्स चलने योग्य divs थे।

मैंने अपने दो परीक्षणों में से प्रत्येक को 100,000 नोड्स जोड़े। उन्होंने काफी अलग प्रदर्शन किया:

एचटीएमएल टेस्ट टैब हमेशा लोड होने के लिए लिया गया (5 मिनट से थोड़ा कम समय पर, क्रोम ने पहली बार पृष्ठ को मारने के लिए कहा)। क्रोम के टास्क मैनेजर का कहना है कि टैब 168 एमबी ले रहा है। जब मैं इसे देख रहा हूं, तो इसमें 0-13% CPU समय लगता है, 0% जब मैं नहीं देख रहा हूं।

कैनवास टैब एक सेकंड में लोड होता है और 30 एमबी लेता है। यह हर बार CPU समय का 13% भी लेता है, इस पर ध्यान दिए बिना कि कोई इसे देख रहा है या नहीं। (2013 संपादित करें: उन्होंने ज्यादातर तय किया है कि)

HTML पृष्ठ पर खींचना चिकना है, जिसे डिज़ाइन द्वारा अपेक्षित किया जाता है, क्योंकि वर्तमान सेटअप कैनवास परीक्षण में हर 30 मिलीसेकंड को फिर से निकालना है। इसके लिए कैनवास के लिए बहुत सारे अनुकूलन किए जा सकते हैं। (कैनवास अमान्यता सबसे आसान, क्लिपिंग क्षेत्र, चुनिंदा रीड्रॉइंग इत्यादि भी है .. यह इस बात पर निर्भर करता है कि आप कितना कार्यान्वित करना चाहते हैं)

इसमें कोई संदेह नहीं है कि आप कैनवास को उस सरल परीक्षण में divs के रूप में ऑब्जेक्ट मैनिपुलेशन पर तेजी से और लोड समय में बहुत तेज़ हो सकते हैं। कैनवास में ड्राइंग / लोडिंग तेज है और ऑप्टिमाइज़ेशन के लिए कहीं अधिक जगह है (यानी, ऑफ-स्क्रीन चीजों को छोड़कर बहुत आसान है)।

निष्कर्ष:

  • एसवीजी शायद कुछ वस्तुओं वाले अनुप्रयोगों और ऐप्स के लिए बेहतर है (1000 से कम? वास्तव में निर्भर करता है)
  • हजारों वस्तुओं और सावधानीपूर्वक हेरफेर के लिए कैनवास बेहतर है, लेकिन जमीन से बाहर निकलने के लिए बहुत अधिक कोड (या लाइब्रेरी) की आवश्यकता है।
  • एचटीएमएल डिव्स घबराए हुए हैं और स्केल नहीं करते हैं, गोलाकार कोनों के साथ एक सर्कल बनाना संभव है, जटिल आकार संभव है लेकिन सैकड़ों छोटे छोटे पिक्सेल-चौड़े divs शामिल हैं। पागलपन आता है।

Divs विकल्प के बारे में बस मेरे 2 सेंट।

प्रसिद्ध / कुख्यात और SamsaraJS (और संभवतः अन्य) पूरी तरह से स्थित गैर-नेस्टेड divs (गैर-तुच्छ HTML / CSS सामग्री के साथ) का उपयोग करते हैं, जो स्थिति और 2 डी / 3 डी रूपांतरणों के लिए matrix2d / matrix3d ​​के साथ संयुक्त होते हैं, और मध्यम मोबाइल हार्डवेयर पर स्थिर 60FPS प्राप्त करते हैं , तो मैं divs धीमी विकल्प होने के खिलाफ बहस करता हूं।

यूट्यूब और अन्य जगहों पर बहुत सारे स्क्रीन रिकॉर्डिंग हैं, ब्राउजर में चल रहे उच्च-प्रदर्शन 2 डी / 3 डी सामान के साथ सब कुछ एक डीओएम तत्व है जिसके साथ आप 60 एफपीएस पर एलिमेंट पर निरीक्षण कर सकते हैं (कुछ प्रभावों के लिए वेबजीएल के साथ मिश्रित, लेकिन नहीं प्रतिपादन का मुख्य हिस्सा)।


इसमें जोड़ने के लिए, मैं एक आरेख आवेदन कर रहा हूं, और शुरुआत में कैनवास के साथ शुरू हुआ। आरेख में कई नोड्स होते हैं, और वे काफी बड़े हो सकते हैं। उपयोगकर्ता आरेख में तत्वों को खींच सकता है।

जो मैंने पाया वह था कि मेरे मैक पर, बहुत बड़ी छवियों के लिए, एसवीजी बेहतर है। मेरे पास मैकबुक प्रो 2013 13 "रेटिना है, और यह काफी अच्छी तरह से नीचे की ओर चल रहा है। छवि 6000x6000 पिक्सेल है, और इसमें 1000 ऑब्जेक्ट्स हैं। कैनवास में एक समान निर्माण मेरे लिए एनिमेट करना असंभव था जब उपयोगकर्ता ऑब्जेक्ट्स को चारों ओर खींच रहा था आरेख।

आधुनिक डिस्प्ले पर आपको विभिन्न संकल्पों के लिए भी खाते हैं, और यहां एसवीजी आपको यह सब मुफ्त में देता है।

पहेली: http://jsfiddle.net/knutsi/PUcr8/16/

पूर्णस्क्रीन: http://jsfiddle.net/knutsi/PUcr8/16/embedded/result/

var wiggle_factor = 0.0;
nodes = [];

// create svg:
var svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
svg.setAttribute('style', 'border: 1px solid black');
svg.setAttribute('width', '6000');
svg.setAttribute('height', '6000');

svg.setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns:xlink",
    "http://www.w3.org/1999/xlink");

document.body.appendChild(svg);


function makeNode(wiggle) {
    var node = document.createElementNS("http://www.w3.org/2000/svg", "g");
    var node_x = (Math.random() * 6000);
    var node_y = (Math.random() * 6000);
    node.setAttribute("transform", "translate(" + node_x + ", " + node_y +")");

    // circle:
    var circ = document.createElementNS("http://www.w3.org/2000/svg", "circle");
    circ.setAttribute( "id","cir")
    circ.setAttribute( "cx", 0 + "px")
    circ.setAttribute( "cy", 0 + "px")
    circ.setAttribute( "r","100px");
    circ.setAttribute('fill', 'red');
    circ.setAttribute('pointer-events', 'inherit')

    // text:
    var text = document.createElementNS("http://www.w3.org/2000/svg", "text");
    text.textContent = "This is a test! ÅÆØ";

    node.appendChild(circ);
    node.appendChild(text);

    node.x = node_x;
    node.y = node_y;

    if(wiggle)
        nodes.push(node)
    return node;
}

// populate with 100 nodes:
for(var i = 0; i < 1000; i++) {
    var node = makeNode(true);
    svg.appendChild(node);
}

// make  one mapped to mouse:
var bnode = makeNode(false);
svg.appendChild(bnode);

document.body.onmousemove=function(event){
    bnode.setAttribute("transform","translate(" +
        (event.clientX + window.pageXOffset) + ", " +
        (event.clientY + window.pageYOffset) +")");
};

setInterval(function() {
    wiggle_factor += 1/60;
    nodes.forEach(function(node) {

        node.setAttribute("transform", "translate(" 
                          + (Math.sin(wiggle_factor) * 200 + node.x) 
                          + ", " 
                          + (Math.sin(wiggle_factor) * 200 + node.y) 
                          + ")");        
    })
},1000/60);

एसवीजी और कैनवास के बीच मतभेदों को जानना सही चुनने में सहायक होगा।

कैनवास

  • संकल्प निर्भर
  • घटना हैंडलर के लिए कोई समर्थन नहीं
  • खराब पाठ प्रतिपादन क्षमताओं
  • आप परिणामी छवि को .png या .jpg के रूप में सहेज सकते हैं
  • ग्राफिक-गहन खेलों के लिए उपयुक्त है

एसवीजी

  • संकल्प स्वतंत्र
  • घटना हैंडलर के लिए समर्थन
  • बड़े प्रतिपादन क्षेत्रों (Google मानचित्र) वाले अनुप्रयोगों के लिए सर्वश्रेष्ठ उपयुक्त
  • जटिल अगर धीमा प्रतिपादन (जो कुछ भी डीओएम का उपयोग करता है वह धीमा हो जाएगा)
  • खेल आवेदन के लिए उपयुक्त नहीं है

मैं साइमन सरिस के निष्कर्षों से सहमत हूं:

मैंने प्रोटीविस (एसवीजी) में प्रसंस्करण (कैनवास) में कुछ विज़ुअलाइजेशन की तुलना की है जो प्रदर्शित करता है> 2000 अंक और प्रोसेसज प्रोटोटाइस से बहुत तेज है।

एसवीजी के साथ घटनाओं को संभालना निश्चित रूप से बहुत आसान है क्योंकि आप उन्हें वस्तुओं से जोड़ सकते हैं। कैनवास में आपको इसे मैन्युअल रूप से करना होगा (माउस की स्थिति जांचें, आदि) लेकिन सरल बातचीत के लिए यह कठिन नहीं होना चाहिए।

डोजो टूलकिट की dojo.gfx लाइब्रेरी भी है। यह एक अमूर्त परत प्रदान करता है और आप रेंडरर (एसवीजी, कैनवास, सिल्वरलाइट) निर्दिष्ट कर सकते हैं। यह भी एक व्यवहार्य विकल्प हो सकता है हालांकि मुझे नहीं पता कि अतिरिक्त अबास्ट्रक्शन परत कितनी ओवरहेड जोड़ती है लेकिन यह इंटरैक्शन और एनिमेशन को कोड करना आसान बनाता है और रेंडरर-अज्ञेयवादी है।

यहां कुछ दिलचस्प मानक हैं:


हालांकि ऊपर दिए गए अधिकांश उत्तरों में अभी भी कुछ सच है, मुझे लगता है कि वे एक अद्यतन के लायक हैं:

सालों से एसवीजी के प्रदर्शन में काफी सुधार हुआ है और अब एसवीजी के लिए हार्डवेयर-त्वरित सीएसएस संक्रमण और एनिमेशन हैं जो जावास्क्रिप्ट प्रदर्शन पर निर्भर नहीं हैं। बेशक जावास्क्रिप्ट प्रदर्शन में भी सुधार हुआ है और इसके साथ ही कैनवास का प्रदर्शन भी है, लेकिन एसवीजी जितना अधिक नहीं है। इसके अलावा ब्लॉक पर एक "नया बच्चा" है जो आज लगभग सभी ब्राउज़रों में उपलब्ध है और यह वेबजीएल है । साइमन का उपयोग उसी शब्द का उपयोग करने के लिए: यह कैनवास और एसवीजी दोनों हाथों को धड़कता है । इसका मतलब यह नहीं है कि यह तकनीक के लिए जाना चाहिए, हालांकि, यह एक जानवर है जिसके साथ काम करना है और यह केवल विशिष्ट उपयोग-मामलों के लिए सच है।

आज के अधिकांश उपयोग मामलों के लिए आईएमएचओ, एसवीजी सर्वश्रेष्ठ प्रदर्शन / उपयोगिता अनुपात देता है। विजुअलाइजेशन को वास्तव में जटिल होना चाहिए (तत्वों की संख्या के संबंध में) और वास्तव में एक ही समय में (प्रति तत्व) सरल है ताकि कैनवास और इससे भी अधिक वेबग्ल वास्तव में चमक सके।

इस जवाब में एक समान प्रश्न के लिए मैं अधिक जानकारी प्रदान कर रहा हूं, मुझे क्यों लगता है कि सभी तीन तकनीकों का संयोजन कभी-कभी आपके पास सबसे अच्छा विकल्प होता है।





html5-canvas