Index: openacs-4/packages/assessment/tcl/as-qti-procs.tcl =================================================================== RCS file: /usr/local/cvsroot/openacs-4/packages/assessment/tcl/as-qti-procs.tcl,v diff -u -r1.14 -r1.15 --- openacs-4/packages/assessment/tcl/as-qti-procs.tcl 16 Dec 2004 09:27:17 -0000 1.14 +++ openacs-4/packages/assessment/tcl/as-qti-procs.tcl 24 Dec 2004 15:32:38 -0000 1.15 @@ -118,220 +118,226 @@ } ad_proc -private as::qti::parse_item {qtiNode section_id basepath} { Parse items from a XML QTI file } { - set as_item_section_map__sort_order 0 - #get all elements - set itemNodes [$qtiNode selectNodes {item}] - foreach item $itemNodes { - # Order of the item_choices - set sort_order 0 - set as_items__title [$item getAttribute {title} {Item}] - array set as_item_choices__correct_answer_p {} - array set as_item_choices__score {} - set as_items__feedback_right {} - set as_items__feedback_wrong {} - set as_items__description {} - # - set objectivesNodes [$item selectNodes {objectives}] - foreach objectives $objectivesNodes { - set mattextNodes [$objectives selectNodes {material/mattext/text()}] - foreach mattext $mattextNodes { - set as_items__description [$mattext nodeValue] + set as_item_section_map__sort_order 0 + #get all elements + set itemNodes [$qtiNode selectNodes {item}] + foreach item $itemNodes { + # Order of the item_choices + set sort_order 0 + set as_items__title [$item getAttribute {title} {Item}] + array set as_item_choices__correct_answer_p {} + array set as_item_choices__score {} + set as_items__feedback_right {} + set as_items__feedback_wrong {} + set as_items__description {} + # + set objectivesNodes [$item selectNodes {objectives}] + foreach objectives $objectivesNodes { + set mattextNodes [$objectives selectNodes {material/mattext/text()}] + foreach mattext $mattextNodes { + set as_items__description [$mattext nodeValue] + } + } + + # + set resprocessingNodes [$item selectNodes {resprocessing}] + foreach resprocessing $resprocessingNodes { + # + set respconditionNodes [$resprocessing selectNodes {respcondition}] + foreach respcondition $respconditionNodes { + set title [$respcondition getAttribute {title} {Correct}] + if {$title == {Correct}} { + # get the correct answer + set correctNodes [$respcondition selectNodes {conditionvar/and/varequal/text()}] + foreach correct $correctNodes { + set as_item_choices__correct_answer_p([string trim [$correct nodeValue]]) {t} + } + } + if {$title == {adjustscore}} { + set choice {} + set score {} + set scoreNodes [$respcondition selectNodes {conditionvar/varequal/text()}] + foreach correct $scoreNodes { + set choice [string trim [$correct nodeValue]] + } + # get score + set scoreNodes [$respcondition selectNodes {setvar[@varname='SCORE']/text()}] + foreach scorenode $scoreNodes { + set score [string trim [$scorenode nodeValue]] + } + set as_item_choices__score($choice) $score + } + # + set displayfeedbackNodes [$respcondition selectNodes {displayfeedback}] + if {[llength $displayfeedbackNodes]>0} { + set displayfeedbackelement [lindex $displayfeedbackNodes 0] + set displayfeedback__ident [$displayfeedbackelement getAttribute {linkrefid}] + # + set itemfeedbackNodes [$item selectNodes {itemfeedback}] + foreach itemfeedback $itemfeedbackNodes { + # wrong feedback + if {[string compare [$itemfeedback getAttribute {ident}] $displayfeedback__ident] == 0} { + set feedback_textNodes [$itemfeedback selectNodes {.//mattext/text()}] + set as_items__feedback_wrong [[lindex $feedback_textNodes 0] nodeValue] + # right feedback + } else { + set feedback_textNodes [$itemfeedback selectNodes {.//mattext/text()}] + set as_items__feedback_right [[lindex $feedback_textNodes 0] nodeValue] } + } } + } + } - # - set resprocessingNodes [$item selectNodes {resprocessing}] - foreach resprocessing $resprocessingNodes { - # - set respconditionNodes [$resprocessing selectNodes {respcondition}] - foreach respcondition $respconditionNodes { - set title [$respcondition getAttribute {title} {Correct}] - if {$title == {Correct}} { - # get the correct answer - set correctNodes [$respcondition selectNodes {conditionvar/and/varequal/text()}] - foreach correct $correctNodes { - set as_item_choices__correct_answer_p([string trim [$correct nodeValue]]) {t} - } - } - if {$title == {adjustscore}} { - set choice {} - set score {} - set scoreNodes [$respcondition selectNodes {conditionvar/varequal/text()}] - foreach correct $scoreNodes { - set choice [string trim [$correct nodeValue]] - } - # get score - set scoreNodes [$respcondition selectNodes {setvar[@varname='SCORE']/text()}] - foreach scorenode $scoreNodes { - set score [string trim [$scorenode nodeValue]] - } - set as_item_choices__score($choice) $score - } - # - set displayfeedbackNodes [$respcondition selectNodes {displayfeedback}] - if {[llength $displayfeedbackNodes]>0} { - set displayfeedbackelement [lindex $displayfeedbackNodes 0] - set displayfeedback__ident [$displayfeedbackelement getAttribute {linkrefid}] - # - set itemfeedbackNodes [$item selectNodes {itemfeedback}] - foreach itemfeedback $itemfeedbackNodes { - # wrong feedback - if {[string compare [$itemfeedback getAttribute {ident}] $displayfeedback__ident] == 0} { - set feedback_textNodes [$itemfeedback selectNodes {.//mattext/text()}] - set as_items__feedback_wrong [[lindex $feedback_textNodes 0] nodeValue] - # right feedback - } else { - set feedback_textNodes [$itemfeedback selectNodes {.//mattext/text()}] - set as_items__feedback_right [[lindex $feedback_textNodes 0] nodeValue] - } - } - } + # element + set presentationNodes [$item selectNodes {presentation}] + foreach presentation $presentationNodes { + # or or (some presentation's children) + set presentationChildNodes [$presentation selectNodes {.//material|.//response_str|.//response_num}] + # + set materialNodes [$presentation selectNodes {.//material}] + set material [lindex $materialNodes 0] + # Initialize in case it doesn't exist + set as_items__title {} + if {[$material nodeName] == {material}} { + set mattextNodes [$material selectNodes {mattext/text()}] + set mattext [lindex $mattextNodes 0] + set as_items__title [$mattext nodeValue] + } + # + set render_fibNodes [$presentation selectNodes {.//render_fib}] + if {[llength $render_fibNodes] > 0} { + set as_items__title {} + # fillinblank or shortanswer + set render_fib [lindex $render_fibNodes 0] + # fillinblank (textbox) + # this is the default + set as_item_display_id {} + #if render_fib element has the attribute rows then we suppose it's a shortanswer item + if {[$render_fib hasAttribute {rows}]} { + # shortanswer (textarea) + set rows [$render_fib getAttribute {rows} {15}] + set cols [$render_fib getAttribute {columns} {55}] + # we need the size of textarea (values of rows and cols) + set html "rows $rows cols $cols" + # insert as_item_display_ta in the CR (and in the as_item_display_ta table) getting the revision_id (item_display_id) + set as_item_display_id [as::item_display_ta::new -html_display_options $html] + foreach node $presentationChildNodes { + # get the title of item + if {[$node nodeName] == {material}} { + set mattextNodes [$node selectNodes {mattext/text()}] + foreach mattext $mattextNodes { + append as_items__title [ad_quotehtml [$mattext nodeValue]] + append as_items__title " " + } } - } - # element - set presentationNodes [$item selectNodes {presentation}] - foreach presentation $presentationNodes { - # or or (some presentation's children) - set presentationChildNodes [$presentation selectNodes {.//material|.//response_str|.//response_num}] - # - set materialNodes [$presentation selectNodes {.//material}] - set material [lindex $materialNodes 0] - # Initialize in case it doesn't exist - set as_items__title {} - if {[$material nodeName] == {material}} { - set mattextNodes [$material selectNodes {mattext/text()}] - set mattext [lindex $mattextNodes 0] - set as_items__title [$mattext nodeValue] + } + # insert as_item_type_oq (shortanswer) + set as_item_type_id [as::item_type_oq::new] + # if render_fib element has not the attribute rows then it's a fill in blank item + } else { + # textbox + set as_item_display_id [as::item_display_tb::new] + + # multiple choice + set as_item_type_id [as::item_type_mc::new] + + foreach node $presentationChildNodes { + if {[$node nodeName] == {material}} { + set mattextNodes [$node selectNodes {mattext/text()}] + foreach mattext $mattextNodes { + append as_items__title [ad_quotehtml [$mattext nodeValue]] + append as_items__title " " + } + } elseif {[$node nodeName] == {response_str} || [$node nodeName] == {response_num} } { + set as_item_choices__ident [$node getAttribute {ident}] + # get the correct response + set as_item_choices__choice_text_nodes [$node selectNodes "//conditionvar/or/varequal\[@respident='$as_item_choices__ident'\]/text()"] + set as_item_choices__choice_text {} + # get the title of each choice + foreach respident $as_item_choices__choice_text_nodes { + lappend as_item_choices__choice_text [string trim [$respident nodeValue]] + } + # Insert as_item_choice + set as_item_choice_id [as::item_choice::new -mc_id $as_item_type_id -title $as_item_choices__choice_text -sort_order $sort_order] + # order of the item_choices + incr sort_order + append as_items__title " " } - # - set render_fibNodes [$presentation selectNodes {.//render_fib}] - if {[llength $render_fibNodes] > 0} { - set as_items__title {} - # fillinblank or shortanswer - set render_fib [lindex $render_fibNodes 0] - # fillinblank (textbox) - # this is the default - set as_item_display_id {} - #if render_fib element has the attribute rows then we suppose it's a shortanswer item - if {[$render_fib hasAttribute {rows}]} { - # shortanswer (textarea) - set rows [$render_fib getAttribute {rows} {15}] - set cols [$render_fib getAttribute {columns} {55}] - # we need the size of textarea (values of rows and cols) - set html "rows $rows cols $cols" - # insert as_item_display_ta in the CR (and in the as_item_display_ta table) getting the revision_id (item_display_id) - set as_item_display_id [as::item_display_ta::new -html_display_options $html] - foreach node $presentationChildNodes { - # get the title of item - if {[$node nodeName] == {material}} { - set mattextNodes [$node selectNodes {mattext/text()}] - foreach mattext $mattextNodes { - append as_items__title [ad_quotehtml [$mattext nodeValue]] - append as_items__title " " - } - } - } - # insert as_item_type_oq (shortanswer) in the CR (and in the as_item_type_oq table) getting the revision_id (item_type_id) - set as_item_type_id [as::item_type_oq::new] - # if render_fib element has not the attribute rows then it's a fill in blank item - } else { - # insert as_item_display_tb in the CR (and in the as_item_display_tb table) getting the revision_id (item_display_id) - set as_item_display_id [as::item_display_tb::new] - # insert as_item_type_mc (multiple choice and multiple response) in the CR (and in the as_item_type_mc table) getting the revision_id (item_type_id) - set as_item_type_id [as::item_type_mc::new] - foreach node $presentationChildNodes { - if {[$node nodeName] == {material}} { - set mattextNodes [$node selectNodes {mattext/text()}] - foreach mattext $mattextNodes { - append as_items__title [ad_quotehtml [$mattext nodeValue]] - append as_items__title " " - } - } elseif {[$node nodeName] == {response_str} || [$node nodeName] == {response_num} } { - set as_item_choices__ident [$node getAttribute {ident}] - # get the correct response - set as_item_choices__choice_text_nodes [$node selectNodes "//conditionvar/or/varequal\[@respident='$as_item_choices__ident'\]/text()"] - set as_item_choices__choice_text {} - # get the title of each choice - foreach respident $as_item_choices__choice_text_nodes { - lappend as_item_choices__choice_text [string trim [$respident nodeValue]] - } - # Insert as_item_choice in the CR (and as_item_choices table) getting the revision_id (choice_id) - set as_item_choice_id [as::item_choice::new -mc_id $as_item_type_id -title $as_item_choices__choice_text -sort_order $sort_order] - # order of the item_choices - incr sort_order - append as_items__title " " - } - } - } - # Insert as_item in the CR (and as_items table) getting the revision_id (as_item_id) - set as_item_id [as::item::new -title $as_items__title -feedback_right $as_items__feedback_right -feedback_wrong $as_items__feedback_wrong] - # set the relation between as_items and as_item_type tables - as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_type_id -type as_item_type_rel - # set the relation between as_items and as_item_display tables - as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_display_id -type as_item_display_rel - } else { - set response_lidNodes [$presentation selectNodes {.//response_lid}] - # The first node of the list. It may not be a good idea if it doesn't exist - set response_lid [lindex $response_lidNodes 0] - set as_items__rcardinality [$response_lid getAttribute {rcardinality} {Single}] - - # multiple choice either text (remember it can be internationalized or changed), images, sounds, videos - # this is the default - set as_item_display_id {} - if {$as_items__rcardinality == {Multiple}} { - # multiple response (checkbox) either text (remember it can be internationalized or changed), images, sounds, videos - # insert as_item_display_cb in the CR (and in the as_item_display_cb table) getting the revision_id (as_item_display) - set as_item_display_id [as::item_display_cb::new] - } else { - # multiple choice (radiobutton) - # insert as_item_display_rb in the CR (and in the as_item_display_rb table) getting the revision_id (as_item_display) - set as_item_display_id [as::item_display_rb::new] - } - # insert as_item_type_mc in the CR (and in the as_item_type_mc table) getting the revision_id (as_item_type) - set as_item_type_id [as::item_type_mc::new] - # Insert as_item in the CR (and as_items table) getting the revision_id (as_item_id) - set as_item_id [as::item::new -title $as_items__title -feedback_right $as_items__feedback_right -feedback_wrong $as_items__feedback_wrong] - # set the relation between as_items and as_item_type tables - as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_type_id -type as_item_type_rel - # set the relation between as_items and as_item_display tables - as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_display_id -type as_item_display_rel - # (each choice) - set response_labelNodes [$presentation selectNodes {.//response_label}] - foreach response_label $response_labelNodes { - set as_item_choices__ident [$response_label getAttribute {ident}] - set mattextNodes [$response_label selectNodes {material/mattext/text()}] - set as_item_choices__choice_text [db_null] - # get the title of each choice - foreach mattext $mattextNodes { - set as_item_choices__choice_text [$mattext nodeValue] - } - # for multimedia items - set matmediaNodes [$response_label selectNodes {material/matimage[@uri]}] - set as_item_choices__content_value [db_null] - foreach matmedia $matmediaNodes { - set mediabasepath $basepath - append mediabasepath {/} - append mediabasepath [$matmedia getAttribute {uri}] - # insert as_file in the CR (and in the as_file table) getting the content value - set as_item_choices__content_value [as::file::new -file_pathname $mediabasepath] - } - # Insert as_item_choice in the CR (and as_item_choices table) getting the revision_id (choice_id) - set as_item_choices__correct_answer_p($as_item_choices__ident) [expr [info exists as_item_choices__correct_answer_p($as_item_choices__ident)]?{t}:{f}] - if {![info exists as_item_choices__score($as_item_choices__ident)]} { - set as_item_choices__score($as_item_choices__ident) 0 - } - # insert as_item_choice in the CR (and as_item_choices table) - as::item_choice::new -mc_id $as_item_type_id -title $as_item_choices__choice_text -sort_order $sort_order -correct_answer_p $as_item_choices__correct_answer_p($as_item_choices__ident) -percent_score $as_item_choices__score($as_item_choices__ident) -content_value $as_item_choices__content_value - # order of the item_choices - incr sort_order - } - } + } } - # Relation between as_items and as_sections - if {$section_id != 0} { - db_dml as_item_section_map_insert {} - incr as_item_section_map__sort_order + # Insert as_item + set as_item_id [as::item::new -title $as_items__title -feedback_right $as_items__feedback_right -feedback_wrong $as_items__feedback_wrong] + # set the relation between as_items and as_item_type tables + as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_type_id -type as_item_type_rel + # set the relation between as_items and as_item_display tables + as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_display_id -type as_item_display_rel + } else { + set response_lidNodes [$presentation selectNodes {.//response_lid}] + # The first node of the list. It may not be a good idea if it doesn't exist + set response_lid [lindex $response_lidNodes 0] + set as_items__rcardinality [$response_lid getAttribute {rcardinality} {Single}] + + # multiple choice either text (remember it can be internationalized or changed), images, sounds, videos + # this is the default + set as_item_display_id {} + if {$as_items__rcardinality == {Multiple}} { + # multiple response (checkbox) either text (remember it can be internationalized or changed), images, sounds, videos + # insert as_item_display_cb + set as_item_display_id [as::item_display_cb::new] + } else { + # multiple choice (radiobutton) + # insert as_item_display_rb + set as_item_display_id [as::item_display_rb::new] } + + # insert as_item_type_mc + set as_item_type_id [as::item_type_mc::new] + + # Insert as_item + set as_item_id [as::item::new -title $as_items__title -feedback_right $as_items__feedback_right -feedback_wrong $as_items__feedback_wrong] + + # set the relation between as_items and as_item_type tables + as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_type_id -type as_item_type_rel + # set the relation between as_items and as_item_display tables + as::item_rels::new -item_rev_id $as_item_id -target_rev_id $as_item_display_id -type as_item_display_rel + # (each choice) + set response_labelNodes [$presentation selectNodes {.//response_label}] + foreach response_label $response_labelNodes { + set as_item_choices__ident [$response_label getAttribute {ident}] + set mattextNodes [$response_label selectNodes {material/mattext/text()}] + set as_item_choices__choice_text [db_null] + # get the title of each choice + foreach mattext $mattextNodes { + set as_item_choices__choice_text [$mattext nodeValue] + } + # for multimedia items + set matmediaNodes [$response_label selectNodes {material/matimage[@uri]}] + set as_item_choices__content_value [db_null] + foreach matmedia $matmediaNodes { + set mediabasepath $basepath + append mediabasepath {/} + append mediabasepath [$matmedia getAttribute {uri}] + # insert as_file in the CR (and in the as_file table) getting the content value + set as_item_choices__content_value [as::file::new -file_pathname $mediabasepath] + } + # Insert as_item_choice + set as_item_choices__correct_answer_p($as_item_choices__ident) [expr [info exists as_item_choices__correct_answer_p($as_item_choices__ident)]?{t}:{f}] + if {![info exists as_item_choices__score($as_item_choices__ident)]} { + set as_item_choices__score($as_item_choices__ident) 0 + } + # insert as_item_choice + as::item_choice::new -mc_id $as_item_type_id -title $as_item_choices__choice_text -sort_order $sort_order -correct_answer_p $as_item_choices__correct_answer_p($as_item_choices__ident) -percent_score $as_item_choices__score($as_item_choices__ident) -content_value $as_item_choices__content_value + # order of the item_choices + incr sort_order + } + } } - return 1 + # Relation between as_items and as_sections + if {$section_id != 0} { + db_dml as_item_section_map_insert {} + incr as_item_section_map__sort_order + } + } + return 1 }