如何使用Jquery和显示元素以每个加载的随机顺序ONCE获取XML文件?

时间:2012-05-27 16:43:50

标签: javascript jquery

我一直在尝试使用Ajax构建问答应用程序。我需要帮助创建一个特定的功能。我创建了具有不同问题和答案的XML文件。基本思想是使用“get”函数来(1)加载XML问题文件和(2)使用“display”和“math.random”函数来显示随机“问题”元素(相应的“答案”)元素将同时显示,但是通过Javascript隐藏。)这是我正在使用的XML文件的格式。这些节点由父节点Words ..

包围

<WordQuestions>
    <Question>Question1</Question>
    <Answer>Answer1</Answer>
</WordQuestions>

<WordQuestions>
    <Question>Question2</Question>
    <Answer>Answer2</Answer>
</WordQuestions>

我需要创建一个可以选择问题的功能。从XML文件中随机回答元素,将其显示给用户,但不会在用户的后续点击中再次显示。因此,一旦向用户显示问题,就需要从下一次单击时向用户显示的问题列表中删除该问题。有人知道怎么做吗?

我创造了一个类似于魅力的类似功能,但它的限制在于它太随意了 - 一个问题&amp;可能永远不会选择answer元素向用户显示,或者可以选择不成比例的次数。用户需要练习所有问题。这是此功能的精简版。

<script language = "javascript">


  function getCategory()
  {
    var XMLHttpRequestObject = false; 

    if (window.XMLHttpRequest) {
      XMLHttpRequestObject = new XMLHttpRequest();
      XMLHttpRequestObject.overrideMimeType("text/xml");
    } else if (window.ActiveXObject) {
      XMLHttpRequestObject = new 
        ActiveXObject("Microsoft.XMLHTTP");
    }


    if(XMLHttpRequestObject) {

    var P = document.LoadCategory.Load.value;
    if (P == "Category1") {XMLHttpRequestObject.open("GET", "Catgory1.xml", true)}
    if (P == "Category2") {XMLHttpRequestObject.open("GET", "Category2.xml", true)} 
    if (P == "Category3") {XMLHttpRequestObject.open("GET", "Category3.xml", true)}


      XMLHttpRequestObject.onreadystatechange = function() 
      { 
        if (XMLHttpRequestObject.readyState == 4 && 
          XMLHttpRequestObject.status == 200) { 
        var xmlDocument = XMLHttpRequestObject.responseXML;
        displayCategory(xmlDocument);
        } 
      } 

      XMLHttpRequestObject.send(null); 
    }
  }

  function displayCategory (xmldoc)
  {

    Questionnodes = xmldoc.getElementsByTagName("Question");
    Answernodes = xmldoc.getElementsByTagName("Answer");
    var i = Math.floor((Math.random()*1000)%Questionnodes.length);
    var i = Math.floor((Math.random()*1000)%Answernodes.length);        

    var displayText1 =
      Questionnodes[i].firstChild.nodeValue;

    var target = document.getElementById("targetDiv1");
    target.innerHTML=displayText1;        


    var displayText2 =
      Answernodes[i].firstChild.nodeValue;

    var target = document.getElementById("targetDiv2");
    target.innerHTML=displayText2;

  }

</script>

现在,我不知道我是否能够改变这段代码来获得我想要的功能。我尝试将XML文件解析为javascript数组(然后随机选择并删除一个元素)但是无处可去。如果有人提出一些建议,我将非常感激。再一次,我想要一个可以随机选择问题的功能。从XML文件中回答元素,但只向用户显示它ONCE。 干杯伙计们。 (对不起,这太啰嗦了)。

2 个答案:

答案 0 :(得分:0)

写一个带有var hasbeenshown,hasbeenanswered,useranswer,function getquestion,function getanswer的类。

instanciated类,在加载时填充xml文件中的值,可以添加到数组中并使用随机数来选择随机问题。

答案 1 :(得分:0)

这里有一个示例链接,说明我将如何处理您尝试的内容:http://jsfiddle.net/dievardump/xL5mg/4/

我评论了代码的某些部分,并且我'模拟'您的getCategory方法。

注意:从我的代码中,我认为无法做的是'pickRandom'方法。我认为你几乎只需要做其他部分。

我在代码中做了什么:

  • 我有一系列问题和答案
  • 我有一个QuestionAndAnswer构造函数

当服务器结果到来时,我'解析'xml文件并用QuestionAndAnswer对象填充集合。

在HTML中是“加载问题”按钮。单击它时,它会调用displayQuestion方法。

此方法从集合中选择(获取和删除)随机QandA对象,然后显示问题和按钮以查看相关答案。

就像我在评论中所说的那样,我决定一个接一个地添加问题,但是你可以通过只有一个问题和响应处理程序并修改其内容来改变它。

如果有一天jsfiddle决定不再工作,这是代码:

Javascript

(function() {   
// Question and Answer collection
var oQandACollection = {
    collection : [],
    length : 0,

    // get a QandA object
    get : function(i) {
        if (i < this.length) {
            return this.collection[i];
        }      
        return null;
    },

    // add a QandA object
    add : function(qanda) {
         this.collection.push(qanda);
         this.length++;
    },

    // remove a QandA object
    remove : function(i) {
        if (typeof this.collection[i] !== 'undefined') {
            this.collection.splice(i, 1);
            this.length--;
        }
    },

    // randomly pick an object from the collection
    pickRandom : function() {
        if (this.length === 0) return null; // return null if there is no object in the collection
        var i = Math.floor(Math.random() * this.length);
        var qanda = this.get(i);
        this.remove(i);
        return qanda;
    }

};

// Question and Answer Object
var QandA = function(xmlNode) {

    var question = xmlNode.getElementsByTagName('Question')[0] || null;
    var answer = xmlNode.getElementsByTagName('Answer')[0] || null;
    if (question && answer) {
        this.question = question.textContent;
        this.answer = answer.textContent;
    } else {
        return null;   
    }  
};

// function to use as ajax request handler
function fillQandA(xmlDoc) {
    // get all WordQuestions elements
    var wrappers = xmlDoc.getElementsByTagName('WordQuestions');
    for(var i = 0, l = wrappers.length, qanda = null; i < l; i++) {
        // create a new question from the current wrapper
        // we could have perfom the getElementsByTagName('Question') here
        // but since the code is really specific to your example i putted it in the constructor of QandA
        // You can change it
        qanda = new QandA(wrappers[i]);
        if (qanda) {
            oQandACollection.add(qanda);  
        }
    }
};


var eList = document.getElementById('qa-list'),
    eLoadQuestion = document.getElementById('load-qanda');

// functions to display a question
// i choosed to add question the one after the others,
// so i re-create html elements at every display
// but you also can modify it to have just one question at a time
// matter of choice
function displayQuestion() {
    var qanda = oQandACollection.pickRandom(); // get a question

    if (qanda) { // if there is a question

        // create elements
        var eQuestion = document.createElement('p'),
            eAnswer = document.createElement('p'),
            eBtn = document.createElement('button');

        eQuestion.textContent = qanda.question;
        eAnswer.textContent = qanda.answer;

        eQuestion.classNAme += ' question';
        eAnswer.className += ' answer';
        eBtn.textContent = 'Show Answer';


        // add click event listener to the button to show the answer
        eBtn.addEventListener('click', function() {
            eAnswer.style.display = 'block';
            eList.removeChild(eBtn);
        }, false);

        eList.appendChild(eQuestion);
        eList.appendChild(eAnswer);
        eList.appendChild(eBtn);
    }
};

// add click event handler on display
eLoadQuestion.addEventListener('click', displayQuestion, false);



// simulate xhr request
function getCategory() {
    // fill fake Q&A xml document
    var xmlDoc = document.createElement('root');
    for(var i = 0, wrapper = null, question = null, answer = null; i < 10; i++) {
        wrapper = document.createElement('WordQuestions');                   
        question = document.createElement('Question');
        question.textContent = 'Question ' + (i+1);                  
        answer = document.createElement('Answer');
        answer.textContent = 'Answer ' + (i+1);

        wrapper.appendChild(question);
        wrapper.appendChild(answer);

        xmlDoc.appendChild(wrapper);

    }   

    // us as xhr request handler like : fillQandA(XMLHttpRequestObject.responseXML);
    fillQandA(xmlDoc);        
}

getCategory();

// test function
function test() {
    for(var i = oQandACollection.length; i--; ) {
        displayQuestion();
    }
}

//test();
})();

<强> HTML

<div class="wrapper">
<div id="qa-list">
</div>
<button id="load-qanda" value="Load new question">Load new question</button>

</div>

<强> CSS

    .wrapper {
    width : 500px;      
}

.wrapper > div {
    position : relative;
    width : 100%    
}

.answer {
    display : none;    
}