Proyectos de Subversion Moodle

Rev

| Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
<?php
2
 
3
class H5PReportXAPIData {
4
 
5
  private $statement, $onlyScore, $children, $parentID;
6
 
7
  /**
8
   * @param object $data Containing 'statement' and 'children'
9
   * @param int $parentID Optional parent identifier
10
   */
11
  public function __construct($data, $parentID = NULL) {
12
    // Keep track of statement and children
13
    if (isset($data->statement)) {
14
      $this->statement = $data->statement;
15
    }
16
    else if (isset($data->onlyScore)) {
17
      $this->onlyScore = $data->onlyScore;
18
    }
19
 
20
    $this->parentID = $parentID;
21
 
22
    if (!empty($data->children)) {
23
      $this->children = $data->children;
24
    }
25
  }
26
 
27
  /**
28
   * Check if the interaction has sub interactions with scoring.
29
   *
30
   * @return boolean
31
   */
32
  public function isCompound() {
33
    return ($this->getInteractionType() === 'compound');
34
  }
35
 
36
  /**
37
   * Get list of children with given parentID
38
   *
39
   * @param int $parentID
40
   * @return array
41
   */
42
  public function getChildren($parentID=NULL) {
43
    $children = array();
44
 
45
    // Parse children data
46
    if (!empty($this->children)) {
47
      foreach ($this->children as $child) {
48
        $children[] = new H5PReportXAPIData($child, $parentID);
49
      }
50
    }
51
 
52
    return $children;
53
  }
54
 
55
  /**
56
   * Get the ID of the parent statement.
57
   * Only works for statements part of a compound interaction.
58
   *
59
   * @return int
60
   */
61
  public function getParentID() {
62
    return $this->parentID;
63
  }
64
 
65
  /**
66
   * Get score of given type from statement result
67
   *
68
   * @param string $type
69
   * @return float
70
   */
71
  private function getScore($type) {
72
    return (isset($this->statement->result->score->{$type}) ? (float) $this->statement->result->score->{$type} : NULL);
73
  }
74
 
75
  /**
76
   * Get the optional scaled score.
77
   * Must be between -1 and 1.
78
   *
79
   * @return float
80
   */
81
  public function getScoreScaled() {
82
    if (isset($this->onlyScore)) {
83
      // Special case if we only have the scaled score.
84
 
85
      $score = 0.;
86
      if ($this->onlyScore !== 1 && is_numeric($this->onlyScore)) {
87
        // Let's "decrypt" it…
88
        $score = $this->onlyScore / 1.234 - 32.17;
89
      }
90
      if ($score < 0 || $score > 1) {
91
        // Invalid score
92
        $score = 0.;
93
      }
94
      return $score;
95
    }
96
 
97
    $score = $this->getScore('scaled');
98
 
99
    if ($score !== NULL) {
100
      if ($score < -1) {
101
        $score = -1.;
102
      }
103
      elseif ($score > 1) {
104
        $score = 1.;
105
      }
106
    }
107
 
108
    return $score;
109
  }
110
 
111
  /**
112
   * Get the required raw score for the interaction.
113
   * Can be anything between min and max.
114
   *
115
   * @return float
116
   */
117
  public function getScoreRaw() {
118
    return $this->getScore('raw');
119
  }
120
 
121
  /**
122
   * Get the optional min. score
123
   *
124
   * @return float
125
   */
126
  public function getScoreMin() {
127
    return $this->getScore('min');
128
  }
129
 
130
  /**
131
   * Get the optional max. score
132
   *
133
   * @return float
134
   */
135
  public function getScoreMax() {
136
    return $this->getScore('max');
137
  }
138
 
139
  /**
140
   * Get object definition property or default value if not set.
141
   *
142
   * @param string $property
143
   * @param mixed $default If not set. Default default is blank string.
144
   * @return mixed
145
   */
146
  private function getObjectDefinition($property, $default = '') {
147
    return (isset($this->statement->object->definition->{$property}) ? $this->statement->object->definition->{$property} : $default);
148
  }
149
 
150
  /**
151
   * Get the type of interaction.
152
   *
153
   * @return string
154
   */
155
  public function getInteractionType() {
156
    // Can be any string
157
    return $this->getObjectDefinition('interactionType');
158
  }
159
 
160
  /**
161
   * Get the description of the interaction.
162
   *
163
   * @return string
164
   */
165
  public function getDescription() {
166
    $description = $this->getObjectDefinition('description');
167
    if ($description !== '') {
168
      $description = (isset($description->{'en-US'}) ? $description->{'en-US'} : '');
169
    }
170
 
171
    return $description;
172
  }
173
 
174
  /**
175
   * Get the correct reponse patterns.
176
   *
177
   * @return string
178
   */
179
  public function getCorrectResponsesPattern() {
180
    $correctResponsesPattern = $this->getObjectDefinition('correctResponsesPattern');
181
    if (is_array($correctResponsesPattern)) {
182
      return json_encode($correctResponsesPattern);
183
    }
184
 
185
    return '';
186
  }
187
 
188
  /**
189
   * Get the user reponse.
190
   *
191
   * @return string
192
   */
193
  public function getResponse() {
194
    return (isset($this->statement->result->response) ? $this->statement->result->response : '');
195
  }
196
 
197
  /**
198
   * Get additonal data for some interaction types.
199
   *
200
   * @return string JSON
201
   */
202
  public function getAdditionals() {
203
    $additionals = array();
204
 
205
    switch ($this->getInteractionType()) {
206
      case 'choice':
207
        $additionals['choices'] = $this->getObjectDefinition('choices', array());
208
        $additionals['extensions'] = $this->getObjectDefinition('extensions', (object)array());
209
        break;
210
 
211
      case 'long-choice':
212
        $additionals['choices'] = $this->getObjectDefinition('choices', array());
213
        $additionals['extensions'] = $this->getObjectDefinition('extensions', (object)array());
214
        break;
215
 
216
      case 'matching':
217
        $additionals['source'] = $this->getObjectDefinition('source', array());
218
        $additionals['target'] = $this->getObjectDefinition('target', array());
219
        break;
220
 
221
      case 'long-fill-in':
222
        $additionals['longfillin'] = true;
223
        $additionals['extensions'] = $this->getObjectDefinition('extensions', (object)array());
224
        break;
225
 
226
      default:
227
        $additionals['extensions'] = $this->getObjectDefinition('extensions', (object)array());
228
    }
229
 
230
    // Add context extensions
231
    $additionals['contextExtensions'] = isset($this->statement->context->extensions)
232
      ? $this->statement->context->extensions : new stdClass();
233
 
234
    return (empty($additionals) ? '' : json_encode($additionals));
235
  }
236
 
237
  /**
238
   * Checks if data is valid
239
   *
240
   * @return bool True if valid data
241
   */
242
  public function validateData() {
243
 
244
    if ($this->getInteractionType() === '') {
245
      return false;
246
    }
247
 
248
    // Validate children
249
    $children = $this->getChildren();
250
    foreach ($children as $child) {
251
      if (!$child->validateData()) {
252
        return false;
253
      }
254
    }
255
 
256
    return true;
257
  }
258
}