2012-09-23 11 views
6

यूट्यूब api // onStateChange कॉलबैक फ़ंक्शंस के लिए इसकी आवश्यकता है!एक जावास्क्रिप्ट फ़ंक्शन प्रोग्रामेटिक रूप से

मैं प्रोग्रामेटिक रूप से ऐसे फ़ंक्शन बनाना चाहता हूं जो कई यूट्यूब प्लेयर द्वारा उत्सर्जित "ऑनस्टेट चेंज" ईवेंट सुनेंगे। श्रोता जोड़ना पहले से ही काम करता है:

function onYouTubePlayerReady(playerId) { 
    var ytpStateManager = playerId +"_StateManager"; 
    document.getElementById(playerId).addEventListener("onStateChange", ytpStateManager); 
... 

समारोह मैं playerId चर ("ytp_1", "ytp_2", ...) के आधार पर बनाने की जरूरत

function ytpStateManager(newState) { 
    ytpStateHelper(playerId , newState); 
} 

तो के लिए परिणाम है भी

function ytp_1_StateManager(newState) { 
    ytpStateHelper("ytp_1", newState); 
} 

वर्क्स लेकिन अभी मैं उनके प्रत्येक खिलाड़ी के लिए मैन्युअल रूप से जोड़ने के लिए है, जो कि मैं क्या करने की जरूरत नहीं है की जरूरत है: playerId "ytp_1" इस प्रकार दिखाई देगा। जब कोई नया खिलाड़ी तैयार स्टार्ट इवेंट भेजता है तो मैं उन्हें स्वचालित रूप से बनाना चाहता हूं।

मेरी समस्या यह है कि ऐसा लगता है कि इन कार्यों को ठीक से काम करने के लिए वैश्विक कार्यों की आवश्यकता है। मैंने दिनों के लिए कई विकल्पों की कोशिश की। मेरी समस्या यह है कि मुझे नहीं पता कि वैश्विक कार्य को परिभाषित करने के लिए (यदि कोई तरीका है), सहित। फ़ंक्शन नाम, प्रोग्रामेटिक रूप से, किसी अन्य चर के आधार पर।

यह एक बमर है कि ytp किसी ईवेंट को उत्सर्जित नहीं करता है जिसमें राज्य और खिलाड़ी/लक्ष्य शामिल होता है। चीजों को और अधिक आसान बना देगा। यह सब मूल रूप से कामकाज है क्योंकि मुझे सभी राज्यों पर सामान करने की ज़रूरत है।

यदि कोई बेहतर/सरल तरीका है, तो कृपया मुझे बताएं :) अन्यथा इस प्रश्न का समाधान अत्यधिक स्वागत है।

शायद इसे "सुलभ" बनाने के लिए ईवेंट को फिर से शुरू करने का कोई तरीका है?

मैंने इस spec में पढ़ा है कि .addEventListener भी एक वस्तु लेता है, इसलिए मैंने ईवेंट को समर्पित ऑब्जेक्ट में बांधने की कोशिश की। लेकिन फिर, यह ट्रिगर नहीं हुआ था। लगता है जैसे मैं सब कुछ परीक्षण किया ...

अद्यतन मैं अब (swfObject से) आइफ्रेम खिलाड़ी का उपयोग करने जा रहा हूँ, क्योंकि यह है कि एक एक घटना है जो playerId और राज्य शामिल प्रदान करता है: डी yeahhh !! गलत ytplayer के साथ सप्ताह बिताने के बाद यह एक महान प्रगति की तरह लगता है। ऐसा लगता है कि वाईटी चाहता है कि हम आईफ्रेम प्लेयर का उपयोग करें जो समर्थित होने पर एचटीएमएल 5 का गतिशील रूप से उपयोग कर सके।

उत्तर

4

आप एक समारोह एक फ़ंक्शन कि बनाने के लिए:

जब घटना श्रोता की स्थापना
function createStateManager(playerId) { 
    return function (newState) { 
     ytpStateHelper(playerId , newState); 
    } 
} 

तो फिर आप अपने समारोह कारखाने फोन:

var player = document.getElementById(playerId); 
player.addEventListener("onStateChange", createStateManager(playerId)); 

डिबगिंग

मुझे यकीन नहीं है कि यह क्यों काम नहीं कर रहा है, लेकिन यहां है एक डीबगिंग सुझाव। मुझे संदेह है कि आपको अपने onYouTubePlayerReady हैंडलर पर playerId नहीं मिल रहा है।

function onYouTubePlayerReady(playerId) { 
    console.log('Player ready. The player id is: ' + playerId); 
    var ytpStateManager = playerId +"_StateManager"; 
    var player = document.getElementById(playerId); 
    player.addEventListener("onStateChange", createStateManager(playerId)); 
} 

function createStateManager(playerId) { 
    return function (newState) { 
     console.log('State changed for player ' + playerId + '. New state is ' + newState); 
     ytpStateHelper(playerId , newState); 
    } 
} 

आपको लगता है कि कोशिश करते हैं, और क्या आप दोनों console.log कॉल से प्राप्त कर पोस्ट कर सकते हैं?

+0

मैंने पहले और अभी यह कोशिश की लेकिन यह मेरे लिए काम नहीं कर रहा है। प्वाइंट उस समय "createStateManager" को "playerId" कहा जाता है और "ytpStateHelper" चर पैरेंट फ़ंक्शन से आते हैं लेकिन उस समय newState परिभाषित नहीं किया जाता है क्योंकि यह ईवेंट ट्रिगर होने पर ytp स्थिति होगा। –

+0

यह काम करना चाहिए ... क्या आपने पोस्ट किए गए अंतिम संस्करण का परीक्षण किया था (मैंने पोस्ट करने के तुरंत बाद कोड संपादित किया था)। – bfavaretto

+0

जब मैं कारखाने को राज्य परिवर्तन पर बुलाता हूं तो इसके परिणामस्वरूप बहुत सारे कार्य होंगे लेकिन कोई भी ट्रिगर नहीं होगा। कॉलबैक को फ़ंक्शन नाम होना चाहिए और इस नाम के साथ एक फ़ंक्शन स्वचालित रूप से बनाया जाना चाहिए। अन्यथा ट्रिगर काम नहीं करेगा क्योंकि मैंने इसे दिनों के लिए परीक्षण किया है। इसका परीक्षण किया, काम नहीं करता है। अब मैं sth परीक्षण कर रहा हूँ। उस दिशा में। –

0
window["foo"+"bar"] = function(){ console.log("foobar is called"); } 
+0

यह सिर्फ प्रोग्रामेटिक रूप से इसका नाम है, यह एक ऐसा फ़ंक्शन नहीं बनाता है जिसमें प्रोग्रामेटिक रूप से परिभाषित व्यवहार हो, जो पोस्टर पूछ रहा है। –

+0

ताकि आप इसे फ़ंक्शन के अंदर चिपके रहें! उत्तर उपयोगकर्ता द्वारा पूछे जाने वाले 100% होने की आवश्यकता नहीं है। इसके अलावा यह विधि महान नहीं है क्योंकि यह नामस्थान में बाढ़ आ रही है। यह वास्तव में अलग-अलग फ़ंक्शंस नहीं होना चाहिए, लेकिन एक से अधिक फ़ंक्शन कई मामलों को संभाल सकता है। – epascarello

+0

जैसा कि bfavaretto के लिए एक टिप्पणी में उल्लेख किया गया है यह काम नहीं करेगा। किसी कारण से "addEventListener" विंडो [चर] संदर्भ को संभाल नहीं सकता है। यह काम करना चाहिए, मैंने दो बार से अधिक कोशिश की, यह नहीं है। –

2

1) आप समारोह वस्तु बना सकते हैं new Function([params], "BODY") तो तुम शरीर अपने कार्य की स्ट्रिंग चर के रूप में गठबंधन और शरीर के रूप में

उदाहरण में डाल सकता है: = नया फंक्शन ("x" वर twoNumAverage, " y "," वापसी (x + y)/2 ") console.log (twoNumAverage (3,7))

2) और नया गतिशील बना सकते हैं नाम और शरीर

उदाहरण

var globalObject ={}; 
var nameFn ='MyNewFunction'; 

var createFn = function(object,functionName, Body){ 
    object[functionName]= new Function(Body); 
} 

createFn(globalObject,nameFn,"return (arguments[0] + arguments[1])/2"); 

आप अपने नए फ़ंक्शन को कॉल कर सकते हैं:

globalObject[nameFn](10,20); 

परिणाम: 15

कृपया शरीर में ध्यान दें कि आपके समारोह आप संग्रह arguments

+0

विचार के लिए धन्यवाद लेकिन समस्या यह है कि मुझे प्रोग्राम नाम को प्रोग्रामेटिक रूप से परिभाषित करने की आवश्यकता है। कहा जाता है कि समारोह के आधार पर मुझे पता है कि कौन सा ytp कहा जाता है। बस आईफ्रेम एपीआई की जांच की गई और ऐसा लगता है कि यह घटना बेहतर है क्योंकि ईवेंट राज्य और खिलाड़ी आईडी प्रदान करता है, जो मुझे चाहिए। –

+0

कृपया अपडेट देखें, मुझे आशा है कि यह आपकी मदद करेगा –

0

यहाँ के माध्यम से परम प्राप्त कर सकते हैं के लिए एक रास्ता है एक नामित प्रॉक्सी फ़ंक्शन बनाएं जो आपके द्वारा प्रदान किए जाने वाले संदर्भ के साथ एक और फ़ंक्शन निष्पादित करता है।

function createNamedProxy(name, fn, context) { 
    var template = [ 
      '(function @name() {', 
      ' @name.fn.apply(@name.context || window, arguments);', 
      '})' 
     ].join('').replace(/@name/g, name), 

    result = eval(template); 
    result.fn = fn; 
    result.context = context; 

    return result; 
} 

// Example Usage 
var anonymous = function() { alert(document === this); }, 
    named = createNamedProxy('Named', anonymous, document); 

// Will alert 'true' 
named(); 

ऊपर समाधान एक समारोह है कि बना सकते हैं और एक नामित समारोह है कि मार डाला जो कुछ भी आप चाहें तो लौट सकते हैं बनाता है। यदि आप संदर्भ की आपूर्ति नहीं करते हैं, तो यह सामान्य ऑब्जेक्ट फ़ंक्शन की तरह विंडो ऑब्जेक्ट को मान लेगा। समाधान बनाने के लिए आप चाहते थे कि आप ऐसा करेंगे:

var varName = 'ytp_1'; 
window[varName + '_StateManager'] = 
    createNamedProxy(varName + '_StateManager', function(newState) { 
     ytpStateHelper(varName, newState); 
    }); 

जहां varName कोई प्रोग्रामेटिक उपसर्ग हो सकता है जो आप चाहें। Ytp_1_StateManager() का आविष्कार करते समय आप अपने नए स्टेटस मान में गुजरेंगे और कोड आपके चर नाम और न्यूस्टेट के साथ ytpStateHelper को कॉल करेगा।

उम्मीद है कि इससे मदद मिलती है।

संबंधित मुद्दे