Index: trunk/extensions/SemanticMediaWiki/includes/SMW_DV_NAry.php |
— | — | @@ -1,284 +0,0 @@ |
2 | | -<?php |
3 | | -/** |
4 | | - * @file |
5 | | - * @ingroup SMWDataValues |
6 | | - */ |
7 | | - |
8 | | -/** |
9 | | - * SMWDataValue implements the handling of n-ary relations. |
10 | | - * @todo: support outputformat |
11 | | - * @todo: support "allows value" and "display units" |
12 | | - * |
13 | | - * @author Jörg Heizmann |
14 | | - * @author Markus Krötzsch |
15 | | - * @ingroup SMWDataValues |
16 | | - */ |
17 | | -class SMWNAryValue extends SMWDataValue { |
18 | | - |
19 | | - private $m_count = 0; |
20 | | - |
21 | | - ///The array of the data values within this container value |
22 | | - private $m_values = array(); |
23 | | - /// TypeObject as we received them when datafactory called us |
24 | | - private $m_type; |
25 | | - /// Should this DV operate on query syntax (special mode for parsing queries in a compatible fashion) |
26 | | - private $m_querysyntax = false; |
27 | | - /// Array of comparators as might be found in query strings (based on inputs like >, <, etc.) |
28 | | - private $m_comparators; |
29 | | - |
30 | | - protected function parseUserValue($value) { |
31 | | - $this->m_values = array(); |
32 | | - $this->m_comparators = array(); // only for query mode |
33 | | - if ($value == '') { |
34 | | - $this->addError('No values specified.'); |
35 | | - return; |
36 | | - } |
37 | | - |
38 | | - $types = $this->m_type->getTypeValues(); |
39 | | - $values = preg_split('/[\s]*;[\s]*/u', trim($value), $this->m_count); |
40 | | - $vi = 0; // index in value array |
41 | | - $empty = true; |
42 | | - for ($i = 0; $i < $this->m_count; $i++) { // iterate over slots |
43 | | - // special handling for supporting query parsing |
44 | | - if ($this->m_querysyntax) { |
45 | | - $comparator = SMW_CMP_EQ; |
46 | | - SMWQueryParser::prepareValue($values[$vi], $comparator); |
47 | | - } |
48 | | - // generating the DVs: |
49 | | - if ( (count($values) > $vi) && |
50 | | - ( ($values[$vi] == '') || ($values[$vi] == '?') ) ) { // explicit omission |
51 | | - $this->m_values[$i] = NULL; |
52 | | - $vi++; |
53 | | - } elseif (count($values) > $vi) { // some values left, try next slot |
54 | | - $dv = SMWDataValueFactory::newTypeObjectValue($types[$i], $values[$vi]); |
55 | | - if ($dv->isValid()) { // valid DV: keep |
56 | | - $this->m_values[$i] = $dv; |
57 | | - $vi++; |
58 | | - $empty = false; |
59 | | - if ($this->m_querysyntax) { // keep comparator for later querying |
60 | | - $this->m_comparators[$i] = $comparator; |
61 | | - } |
62 | | - } elseif ( (count($values)-$vi) == (count($types)-$i) ) { |
63 | | - // too many errors: keep this one to have enough slots left |
64 | | - $this->m_values[$i] = $dv; |
65 | | - $vi++; |
66 | | - } else { // assume implicit omission, reset to NULL |
67 | | - $this->m_values[$i] = NULL; |
68 | | - } |
69 | | - } else { // fill rest with NULLs |
70 | | - $this->m_values[$i] = NULL; |
71 | | - } |
72 | | - } |
73 | | - if ($empty) { |
74 | | - $this->addError('No values specified.'); |
75 | | - } |
76 | | - } |
77 | | - |
78 | | - public function setDBkeys($args) { |
79 | | - wfLoadExtensionMessages('SemanticMediaWiki'); |
80 | | - $this->addError(wfMsgForContent('smw_parseerror')); |
81 | | -// trigger_error("setDBkeys() cannot be used for initializing n-ary datavalues (SMWNAryValue). Use SMWNAryValue->setDVs() instead.", E_USER_WARNING); |
82 | | -// debug_print_backtrace(); |
83 | | -// die; |
84 | | - } |
85 | | - |
86 | | - /// Parsing from a value array is not supported for this datatype. Use setDVs() to initialize this datatype. |
87 | | - protected function parseDBkeys($args) {} |
88 | | - |
89 | | - /// No unstubbing required for this datatype. Contained data will be unstubbed if needed. |
90 | | - protected function unstub() {} |
91 | | - |
92 | | - public function getShortWikiText($linked = NULL) { |
93 | | - if ($this->m_caption !== false) { |
94 | | - return $this->m_caption; |
95 | | - } |
96 | | - return $this->makeOutputText(0, $linked); |
97 | | - } |
98 | | - |
99 | | - public function getShortHTMLText($linker = NULL) { |
100 | | - if ($this->m_caption !== false) { |
101 | | - return $this->m_caption; |
102 | | - } |
103 | | - return $this->makeOutputText(1, $linker); |
104 | | - } |
105 | | - |
106 | | - public function getLongWikiText($linked = NULL) { |
107 | | - return $this->makeOutputText(2, $linked); |
108 | | - } |
109 | | - |
110 | | - public function getLongHTMLText($linker = NULL) { |
111 | | - return $this->makeOutputText(3, $linker); |
112 | | - } |
113 | | - |
114 | | - private function makeOutputText($type = 0, $linker = NULL) { |
115 | | - if (!$this->isValid()) { |
116 | | - return ( ($type == 0)||($type == 1) )? '' : $this->getErrorText(); |
117 | | - } |
118 | | - $result = ''; |
119 | | - for ($i = 0; $i < $this->m_count; $i++) { |
120 | | - if ($i == 1) { |
121 | | - $result .= ' ('; |
122 | | - } elseif ($i > 1) { |
123 | | - $result .= ", "; |
124 | | - } |
125 | | - if ($this->m_values[$i] !== NULL) { |
126 | | - $result .= $this->makeValueOutputText($type, $i, $linker); |
127 | | - } else { |
128 | | - $result .= '?'; |
129 | | - } |
130 | | - if ($i == sizeof($this->m_values) - 1) { |
131 | | - $result .= ')'; |
132 | | - } |
133 | | - } |
134 | | - return $result; |
135 | | - } |
136 | | - |
137 | | - private function makeValueOutputText($type, $index, $linker) { |
138 | | - switch ($type) { |
139 | | - case 0: return $this->m_values[$index]->getShortWikiText($linker); |
140 | | - case 1: return $this->m_values[$index]->getShortHTMLText($linker); |
141 | | - case 2: return $this->m_values[$index]->getShortWikiText($linker); |
142 | | - case 3: return $this->m_values[$index]->getShortHTMLText($linker); |
143 | | - } |
144 | | - } |
145 | | - |
146 | | - /// @note This function does not return a useful result for n-ary values. Use getDVs() to access the individual values of this n-ary. |
147 | | - public function getDBkeys() { |
148 | | - return array(''); |
149 | | - } |
150 | | - |
151 | | - public function getWikiValue() { |
152 | | - $result = ''; |
153 | | - $first = true; |
154 | | - foreach ($this->m_values as $value) { |
155 | | - if ($first) { |
156 | | - $first = false; |
157 | | - } else { |
158 | | - $result .= "; "; |
159 | | - } |
160 | | - if ($value !== NULL) { |
161 | | - $result .= $value->getWikiValue(); |
162 | | - } else { |
163 | | - $result .= "?"; |
164 | | - } |
165 | | - } |
166 | | - return $result; |
167 | | - } |
168 | | - |
169 | | - public function getHash() { |
170 | | - $first = true; |
171 | | - $result = ''; |
172 | | - foreach ($this->m_values as $value) { |
173 | | - if ($first) { |
174 | | - $first = false; |
175 | | - } else { |
176 | | - $result .= ' - '; |
177 | | - } |
178 | | - if ($value !== NULL) { |
179 | | - $result .= str_replace('-', '--', $value->getHash()); |
180 | | - } |
181 | | - } |
182 | | - return $result; |
183 | | - } |
184 | | - |
185 | | -////// Custom functions for n-ary attributes |
186 | | - |
187 | | - public function getDVTypeIDs() { |
188 | | - return implode(';', $this->m_type->getTypeLabels()); |
189 | | - } |
190 | | - |
191 | | - public function getType() { |
192 | | - return $this->m_type; |
193 | | - } |
194 | | - |
195 | | - /** |
196 | | - * Set type array. Must be done before setting any values. |
197 | | - */ |
198 | | - public function setType($type) { |
199 | | - $this->m_type = $type; |
200 | | - $this->m_count = count($this->m_type->getTypeLabels()); |
201 | | - $this->m_values = array(); // careful: do not iterate to m_count if DV is not valid! |
202 | | - } |
203 | | - |
204 | | - /** |
205 | | - * Change to query syntax mode. |
206 | | - */ |
207 | | - public function acceptQuerySyntax() { |
208 | | - $this->m_querysyntax = true; |
209 | | - } |
210 | | - |
211 | | - public function getDVs() { |
212 | | - return $this->isValid() ? $this->m_values : NULL; |
213 | | - } |
214 | | - |
215 | | - /** |
216 | | - * Directly set the values to the given array of values. The given values |
217 | | - * should correspond to the types and arity of the nary container, with |
218 | | - * NULL as an indication for omitted values. |
219 | | - */ |
220 | | - public function setDVs($datavalues) { |
221 | | - $this->clearErrors(); // clear errors |
222 | | - $this->m_infolinks = array(); // clear links |
223 | | - $this->m_hasssearchlink = false; |
224 | | - $this->m_caption = false; |
225 | | - $typelabels = $this->m_type->getTypeLabels(); |
226 | | - for ($i = 0; $i < $this->m_count; $i++) { |
227 | | - if ( ($i < count($datavalues) ) && ($datavalues[$i] !== NULL) ) { |
228 | | - //&& ($datavalues[$i]->getTypeID() == SMWDataValueFactory::findTypeID($typelabels[$i])) ) { |
229 | | - ///TODO: is the above typcheck required, or can we assume responsible callers? |
230 | | - $this->m_values[$i] = $datavalues[$i]; |
231 | | - } else { |
232 | | - $this->m_values[$i] = NULL; |
233 | | - } |
234 | | - } |
235 | | - $this->m_isset = true; |
236 | | - } |
237 | | - |
238 | | - /** |
239 | | - * If valid and in querymode, build a suitable SMWValueList description from the |
240 | | - * given input or return NULL if no such description was given. This requires the |
241 | | - * input to be given to setUserValue(). Otherwise bad things will happen. |
242 | | - */ |
243 | | - public function getValueList() { |
244 | | - $vl = new SMWValueList(); |
245 | | - if (!$this->isValid() || !$this->m_querysyntax) { |
246 | | - return NULL; |
247 | | - } |
248 | | - for ($i=0; $i < $this->m_count; $i++) { |
249 | | - if ($this->m_values[$i] !== NULL) { |
250 | | - $vl->setDescription($i,new SMWValueDescription($this->m_values[$i], $this->m_comparators[$i])); |
251 | | - } |
252 | | - } |
253 | | - return $vl; |
254 | | - } |
255 | | - |
256 | | - public function getExportData() { |
257 | | - if (!$this->isValid()) return NULL; |
258 | | - |
259 | | - $result = new SMWExpData(new SMWExpElement('', $this)); // bnode |
260 | | - $ed = new SMWExpData(SMWExporter::getSpecialElement('swivt','Container')); |
261 | | - $result->addPropertyObjectValue(SMWExporter::getSpecialElement('rdf','type'), $ed); |
262 | | - $count = 0; |
263 | | - foreach ($this->m_values as $value) { |
264 | | - $count++; |
265 | | - if ( ($value === NULL) || (!$value->isValid()) ) { |
266 | | - continue; |
267 | | - } |
268 | | - if (($value->getTypeID() == '_wpg') || ($value->getTypeID() == '_uri') || ($value->getTypeID() == '_ema')) { |
269 | | - $result->addPropertyObjectValue( |
270 | | - SMWExporter::getSpecialElement('swivt','object' . $count), |
271 | | - $value->getExportData()); |
272 | | - } else { |
273 | | - $result->addPropertyObjectValue( |
274 | | - SMWExporter::getSpecialElement('swivt','value' . $count), |
275 | | - $value->getExportData()); |
276 | | - } |
277 | | - } |
278 | | - return $result; |
279 | | - } |
280 | | - |
281 | | - /// @todo Allowed values for multi-valued properties are not supported yet. |
282 | | - protected function checkAllowedValues() {} |
283 | | - |
284 | | -} |
285 | | - |
Index: trunk/extensions/SemanticMediaWiki/includes/SMW_DV_List.php |
— | — | @@ -0,0 +1,219 @@ |
| 2 | +<?php |
| 3 | +/** |
| 4 | + * @file |
| 5 | + * @ingroup SMWDataValues |
| 6 | + */ |
| 7 | + |
| 8 | +/** |
| 9 | + * SMWDataValue implements the handling of short lists of values, |
| 10 | + * where the order governs the type of each entry. |
| 11 | + * |
| 12 | + * @todo Enforce limitation of maximal number of values. |
| 13 | + * @todo Complete internationalisation. |
| 14 | + * |
| 15 | + * @author Markus Krötzsch |
| 16 | + * @ingroup SMWDataValues |
| 17 | + */ |
| 18 | +class SMWListValue extends SMWContainerValue { |
| 19 | + |
| 20 | + /// cache for datavalues of types belonging to this object |
| 21 | + private $m_typevalues = NULL; |
| 22 | + |
| 23 | + /// Should this DV operate on query syntax (special mode for parsing queries in a compatible fashion) |
| 24 | + private $m_querysyntax = false; |
| 25 | + /// Array of comparators as might be found in query strings (based on inputs like >, <, etc.) |
| 26 | + private $m_comparators; |
| 27 | + |
| 28 | + protected function parseUserValue($value) { |
| 29 | + $this->m_data->clear(); |
| 30 | + $this->m_comparators = array(); // only for query mode |
| 31 | + if ($value == '') { /// TODO internalionalize |
| 32 | + $this->addError('No values specified.'); |
| 33 | + return; |
| 34 | + } |
| 35 | + |
| 36 | + $types = $this->getTypeValues(); |
| 37 | + $values = preg_split('/[\s]*;[\s]*/u', trim($value)); |
| 38 | + $vi = 0; // index in value array |
| 39 | + $empty = true; |
| 40 | + for ($i = 0; $i < max(5,count($types)); $i++) { // iterate over slots |
| 41 | + // special handling for supporting query parsing |
| 42 | + if ($this->m_querysyntax) { |
| 43 | + $comparator = SMW_CMP_EQ; |
| 44 | + SMWQueryParser::prepareValue($values[$vi], $comparator); |
| 45 | + } |
| 46 | + // generating the DVs: |
| 47 | + if ( (count($values) > $vi) && |
| 48 | + ( ($values[$vi] == '') || ($values[$vi] == '?') ) ) { // explicit omission |
| 49 | + $vi++; |
| 50 | + } elseif (array_key_exists($vi,$values) && array_key_exists($i,$types)) { // some values left, try next slot |
| 51 | + $dv = SMWDataValueFactory::newTypeObjectValue($types[$i], $values[$vi]); |
| 52 | + if ($dv->isValid()) { // valid DV: keep |
| 53 | + $this->m_data->addPropertyObjectValue(SMWPropertyValue::makeProperty('_' . ($i+1)), $dv); |
| 54 | + $vi++; |
| 55 | + $empty = false; |
| 56 | + if ($this->m_querysyntax) { // keep comparator for later querying |
| 57 | + $this->m_comparators[$i] = $comparator; |
| 58 | + } |
| 59 | + } elseif ( (count($values)-$vi) == (count($types)-$i) ) { |
| 60 | + // too many errors: keep this one to have enough slots left |
| 61 | + $this->m_data->addPropertyObjectValue(SMWPropertyValue::makeProperty('_' . ($i+1)), $dv); |
| 62 | + $this->addError($dv->getErrors()); |
| 63 | + $vi++; |
| 64 | + } |
| 65 | + } |
| 66 | + } |
| 67 | + if ($empty) { /// TODO internalionalize |
| 68 | + $this->addError('No values specified.'); |
| 69 | + } |
| 70 | + } |
| 71 | + |
| 72 | + /** |
| 73 | + * This function resembles SMWContainerValue::parseDBkeys() but it already unstubs |
| 74 | + * the values instead of passing on initialisation strings. This is required since |
| 75 | + * the datatype of each entry is not determined by the property here (since we are |
| 76 | + * using generic _1, _2, ... properties that can have any type). |
| 77 | + */ |
| 78 | + protected function parseDBkeys($args) { |
| 79 | + $this->m_data->clear(); |
| 80 | + $types = $this->getTypeValues(); |
| 81 | + if (count($args)>0) { |
| 82 | + foreach (reset($args) as $value) { |
| 83 | + if (is_array($value) && (count($value)==2)) { |
| 84 | + $property = SMWPropertyValue::makeProperty(reset($value)); |
| 85 | + $pnum = intval(substr(reset($value),1)); // try to find the number of this property |
| 86 | + if (array_key_exists($pnum-1,$types)) { |
| 87 | + $dv = SMWDataValueFactory::newTypeObjectValue( $types[$pnum-1] ); |
| 88 | + $dv->setDBkeys(end($value)); |
| 89 | + $this->m_data->addPropertyObjectValue($property, $dv); |
| 90 | + } |
| 91 | + } |
| 92 | + } |
| 93 | + } |
| 94 | + } |
| 95 | + |
| 96 | + public function getShortWikiText($linked = NULL) { |
| 97 | + if ($this->m_caption !== false) { |
| 98 | + return $this->m_caption; |
| 99 | + } |
| 100 | + return $this->makeOutputText(0, $linked); |
| 101 | + } |
| 102 | + |
| 103 | + public function getShortHTMLText($linker = NULL) { |
| 104 | + if ($this->m_caption !== false) { |
| 105 | + return $this->m_caption; |
| 106 | + } |
| 107 | + return $this->makeOutputText(1, $linker); |
| 108 | + } |
| 109 | + |
| 110 | + public function getLongWikiText($linked = NULL) { |
| 111 | + return $this->makeOutputText(2, $linked); |
| 112 | + } |
| 113 | + |
| 114 | + public function getLongHTMLText($linker = NULL) { |
| 115 | + return $this->makeOutputText(3, $linker); |
| 116 | + } |
| 117 | + |
| 118 | + public function getWikiValue() { |
| 119 | + return $this->makeOutputText(4); |
| 120 | + } |
| 121 | + |
| 122 | + private function makeOutputText($type = 0, $linker = NULL) { |
| 123 | + if (!$this->isValid()) { |
| 124 | + return ( ($type == 0)||($type == 1) )? '' : $this->getErrorText(); |
| 125 | + } |
| 126 | + $result = ''; |
| 127 | + for ($i = 0; $i < count($this->getTypeValues()); $i++) { |
| 128 | + if ($i == 1) { |
| 129 | + $result .= ($type == 4)?'; ':' ('; |
| 130 | + } elseif ($i > 1) { |
| 131 | + $result .= ($type == 4)?'; ':", "; |
| 132 | + } |
| 133 | + $property = SMWPropertyValue::makeProperty('_' . ($i+1)); |
| 134 | + $dv = reset($this->m_data->getPropertyValues($property)); |
| 135 | + $result .= ($dv !== false)? $this->makeValueOutputText($type, $dv, $linker): '?'; |
| 136 | + } |
| 137 | + if ( ($i>1) && ($type != 4) ) $result .= ')'; |
| 138 | + return $result; |
| 139 | + } |
| 140 | + |
| 141 | + private function makeValueOutputText($type, $datavalue, $linker) { |
| 142 | + switch ($type) { |
| 143 | + case 0: return $datavalue->getShortWikiText($linker); |
| 144 | + case 1: return $datavalue->getShortHTMLText($linker); |
| 145 | + case 2: return $datavalue->getShortWikiText($linker); |
| 146 | + case 3: return $datavalue->getShortHTMLText($linker); |
| 147 | + case 4: return $datavalue->getWikiValue(); |
| 148 | + } |
| 149 | + } |
| 150 | + |
| 151 | + /// @todo Allowed values for multi-valued properties are not supported yet. |
| 152 | + protected function checkAllowedValues() {} |
| 153 | + |
| 154 | + /** |
| 155 | + * Make sure that the content is reset in this case. |
| 156 | + * @todo This is not a full reset yet (the case that property is changed after a value |
| 157 | + * was set does not occur in the normal flow of things, hence thishas low priority). |
| 158 | + */ |
| 159 | + public function setProperty(SMWPropertyValue $property) { |
| 160 | + parent::setProperty($property); |
| 161 | + $this->m_typevalues = NULL; |
| 162 | + } |
| 163 | + |
| 164 | + public function getExportData() { |
| 165 | + if (!$this->isValid()) return NULL; |
| 166 | + |
| 167 | + $result = new SMWExpData(new SMWExpElement('', $this)); // bnode |
| 168 | + $ed = new SMWExpData(SMWExporter::getSpecialElement('swivt','Container')); |
| 169 | + $result->addPropertyObjectValue(SMWExporter::getSpecialElement('rdf','type'), $ed); |
| 170 | + $count = 0; |
| 171 | + foreach ($this->m_values as $value) { |
| 172 | + $count++; |
| 173 | + if ( ($value === NULL) || (!$value->isValid()) ) { |
| 174 | + continue; |
| 175 | + } |
| 176 | + if (($value->getTypeID() == '_wpg') || ($value->getTypeID() == '_uri') || ($value->getTypeID() == '_ema')) { |
| 177 | + $result->addPropertyObjectValue( |
| 178 | + SMWExporter::getSpecialElement('swivt','object' . $count), |
| 179 | + $value->getExportData()); |
| 180 | + } else { |
| 181 | + $result->addPropertyObjectValue( |
| 182 | + SMWExporter::getSpecialElement('swivt','value' . $count), |
| 183 | + $value->getExportData()); |
| 184 | + } |
| 185 | + } |
| 186 | + return $result; |
| 187 | + } |
| 188 | + |
| 189 | +////// Custom functions for n-ary attributes |
| 190 | + |
| 191 | + /** |
| 192 | + * Change to query syntax mode. |
| 193 | + */ |
| 194 | + public function acceptQuerySyntax() { |
| 195 | + $this->m_querysyntax = true; |
| 196 | + } |
| 197 | + |
| 198 | + /** |
| 199 | + * Return the array (list) of datatypes that the individual entries of this datatype consist of. |
| 200 | + * @todo Add some check to account for maximal number of list entries (maybe this should go to a |
| 201 | + * variant of the SMWTypesValue). |
| 202 | + */ |
| 203 | + public function getTypeValues() { |
| 204 | + if ($this->m_typevalues !== NULL) return $this->m_typevalues; // local cache |
| 205 | + if ( ($this->m_property === NULL) || ($this->m_property->getWikiPageValue() === NULL) ) { |
| 206 | + $this->m_typevalues = array(); // no property known -> no types |
| 207 | + } else { // query for type values |
| 208 | + $typelist = smwfGetStore()->getPropertyValues($this->m_property->getWikiPageValue(), SMWPropertyValue::makeProperty('_LIST')); |
| 209 | + if (count($typelist) == 1) { |
| 210 | + $this->m_typevalues = reset($typelist)->getTypeValues(); |
| 211 | + } else { ///TODO internalionalize |
| 212 | + $this->addError('List type not properly specified for this property.'); |
| 213 | + $this->m_typevalues = array(); |
| 214 | + } |
| 215 | + } |
| 216 | + return $this->m_typevalues; |
| 217 | + } |
| 218 | + |
| 219 | +} |
| 220 | + |
Property changes on: trunk/extensions/SemanticMediaWiki/includes/SMW_DV_List.php |
___________________________________________________________________ |
Name: svn:eol-style |
1 | 221 | + native |
Index: trunk/extensions/SemanticMediaWiki/includes/SMW_DataValueFactory.php |
— | — | @@ -5,16 +5,18 @@ |
6 | 6 | */ |
7 | 7 | |
8 | 8 | /** |
9 | | - * Factory class for creating SMWDataValue objects for supplied types or properties |
10 | | - * and data values. |
| 9 | + * Factory class for creating SMWDataValue objects for supplied types or |
| 10 | + * properties and data values. |
11 | 11 | * |
12 | 12 | * The class has two main entry points: |
13 | | - * - newTypeObjectValue |
14 | | - * - newTypeIDValue |
15 | | - * These create new DV objects, possibly with preset user values, captions and property names. |
16 | | - * Further methods are used to conveniently create DVs for properties and special properties: |
17 | | - * - newPropertyObjectValue |
| 13 | + * - newTypeObjectValue() |
| 14 | + * - newTypeIDValue() |
18 | 15 | * |
| 16 | + * These create new DV objects, possibly with preset user values, captions and |
| 17 | + * property names. Further methods are used to conveniently create DVs for |
| 18 | + * properties and special properties: |
| 19 | + * - newPropertyObjectValue() |
| 20 | + * |
19 | 21 | * @ingroup SMWDataValues |
20 | 22 | */ |
21 | 23 | class SMWDataValueFactory { |
— | — | @@ -28,8 +30,8 @@ |
29 | 31 | |
30 | 32 | /** |
31 | 33 | * Create an SMWDataValue object that can hold values for the type that the |
32 | | - * given SMWTypesValue object specifies. If no $value is given, an empty container |
33 | | - * is created, the value of which can be set later on. |
| 34 | + * given SMWTypesValue object specifies. If no $value is given, an empty |
| 35 | + * container is created, the value of which can be set later on. |
34 | 36 | * @param $typevalue SMWTypesValue object representing the type of the object |
35 | 37 | * @param $value user value string, or false if unknown |
36 | 38 | * @param $caption user-defined caption or false if none given |
— | — | @@ -41,28 +43,12 @@ |
42 | 44 | $result->addError($typevalue->getErrors()); |
43 | 45 | return $result; |
44 | 46 | } |
45 | | - SMWDataValueFactory::initDatatypes(); |
46 | | - $typeid = $typevalue->getDBkey(); |
47 | | - if (array_key_exists($typeid, SMWDataValueFactory::$m_typeclasses)) { // basic type |
48 | | - $result = new SMWDataValueFactory::$m_typeclasses[$typeid]($typeid); |
49 | | - } elseif (!$typevalue->isUnary()) { // n-ary type |
50 | | - $result = new SMWDataValueFactory::$m_typeclasses['__nry']('__nry'); |
51 | | - $result->setType($typevalue); |
52 | | - } elseif (($typeid != '') && ($typeid{0} != '_')) { // custom type with linear conversion |
53 | | - $result = new SMWDataValueFactory::$m_typeclasses['__lin']($typeid); |
54 | | - } else { // type really unknown |
55 | | - wfLoadExtensionMessages('SemanticMediaWiki'); |
56 | | - return new SMWErrorValue(wfMsgForContent('smw_unknowntype', $typevalue->getWikiValue() ), $value, $caption); |
57 | | - } |
58 | | - if ($property !== NULL) $result->setProperty($property); |
59 | | - if ($value !== false) $result->setUserValue($value,$caption); |
60 | | - return $result; |
| 47 | + return SMWDataValueFactory::newTypeIDValue($typevalue->getDBkey(),$value,$vaption,$property); |
61 | 48 | } |
62 | 49 | |
63 | 50 | /** |
64 | | - * Create a value from a type id. If no $value is given, an empty container is created, the |
65 | | - * value of which can be set later on. This function is mostly a shortcut that avoids some of |
66 | | - * the more complex processing required for SMWDataValueFactory::newTypeObjectValue(). |
| 51 | + * Create a value from a type id. If no $value is given, an empty container |
| 52 | + * is created, the value of which can be set later on. |
67 | 53 | * @param $typeid id string for the given type |
68 | 54 | * @param $value user value string, or false if unknown |
69 | 55 | * @param $caption user-defined caption or false if none given |
— | — | @@ -72,39 +58,39 @@ |
73 | 59 | SMWDataValueFactory::initDatatypes(); |
74 | 60 | if (array_key_exists($typeid, SMWDataValueFactory::$m_typeclasses)) { // direct response for basic types |
75 | 61 | $result = new SMWDataValueFactory::$m_typeclasses[$typeid]($typeid); |
76 | | - if ($property !== NULL) $result->setProperty($property); |
77 | | - if ($value !== false) $result->setUserValue($value,$caption); |
78 | | - return $result; |
79 | | - } else { // create type value first (e.g. for n-ary type ids or user-defined types) |
80 | | - $typevalue = new SMWTypesValue('__typ'); |
81 | | - $typevalue->setDBkeys(array($typeid)); |
82 | | - return SMWDataValueFactory::newTypeObjectValue($typevalue, $value, $caption, $property); |
| 62 | + } elseif (($typeid != '') && ($typeid{0} != '_')) { // custom type with linear conversion |
| 63 | + $result = new SMWDataValueFactory::$m_typeclasses['__lin']($typeid); |
| 64 | + } else { // type really unknown |
| 65 | + wfLoadExtensionMessages('SemanticMediaWiki'); |
| 66 | + return new SMWErrorValue(wfMsgForContent('smw_unknowntype', $typevalue->getWikiValue() ), $value, $caption); |
83 | 67 | } |
| 68 | + if ($property !== NULL) $result->setProperty($property); |
| 69 | + if ($value !== false) $result->setUserValue($value,$caption); |
| 70 | + return $result; |
84 | 71 | } |
85 | 72 | |
86 | 73 | /** |
87 | | - * Create a value for the given property, provided as an SMWPropertyValue object. |
88 | | - * If no value is given, an empty container is created, the value of which can be |
89 | | - * set later on. |
| 74 | + * Create a value for the given property, provided as an SMWPropertyValue |
| 75 | + * object. If no value is given, an empty container is created, the value |
| 76 | + * of which can be set later on. |
90 | 77 | */ |
91 | 78 | static public function newPropertyObjectValue(SMWPropertyValue $property, $value=false, $caption=false) { |
92 | 79 | if ($property->isInverse()) { |
93 | 80 | return SMWDataValueFactory::newTypeIdValue('_wpg', $value, $caption, $property); |
94 | 81 | } else { |
95 | | - return SMWDataValueFactory::newTypeObjectValue($property->getTypesValue(), $value, $caption, $property); |
| 82 | + return SMWDataValueFactory::newTypeIDValue($property->getPropertyTypeID(), $value, $caption, $property); |
96 | 83 | } |
97 | 84 | } |
98 | 85 | |
99 | 86 | /** |
100 | | - * Gather all available datatypes and label<=>id<=>datatype associations. This method |
101 | | - * is called before most methods of this factory. |
| 87 | + * Gather all available datatypes and label<=>id<=>datatype associations. |
| 88 | + * This method is called before most methods of this factory. |
102 | 89 | */ |
103 | 90 | static protected function initDatatypes() { |
| 91 | + global $smwgContLang; |
104 | 92 | if (is_array(SMWDataValueFactory::$m_typelabels)) { |
105 | 93 | return; //init happened before |
106 | 94 | } |
107 | | - |
108 | | - global $smwgContLang; |
109 | 95 | SMWDataValueFactory::$m_typelabels = $smwgContLang->getDatatypeLabels(); |
110 | 96 | SMWDataValueFactory::$m_typealiases = $smwgContLang->getDatatypeAliases(); |
111 | 97 | // Setup built-in datatypes. |
— | — | @@ -128,6 +114,7 @@ |
129 | 115 | '_dat' => 'SMWTimeValue', // Time type |
130 | 116 | '_geo' => 'SMWGeoCoordsValue', // Geographic coordinates type |
131 | 117 | '_boo' => 'SMWBoolValue', // Boolean type |
| 118 | + '_lst' => 'SMWListValue', // Value list type (replacing former nary properties) |
132 | 119 | // Special types are not avaialble directly for users (and have no local language name): |
133 | 120 | '__typ' => 'SMWTypesValue', // Special type page type |
134 | 121 | '__con' => 'SMWConceptValue', // Special concept page type |
— | — | @@ -139,18 +126,16 @@ |
140 | 127 | '__sin' => 'SMWWikiPageValue', // Special instance of type |
141 | 128 | '__red' => 'SMWWikiPageValue', // Special redirect type |
142 | 129 | '__lin' => 'SMWLinearValue', // Special linear unit conversion type |
143 | | - '__nry' => 'SMWNAryValue', // Special multi-valued type |
144 | 130 | '__err' => 'SMWErrorValue', // Special error type |
145 | 131 | '__imp' => 'SMWImportValue', // Special import vocabulary type |
146 | 132 | '__pro' => 'SMWPropertyValue', // Property type (possibly predefined, no always based on a page) |
147 | 133 | ); |
148 | | - |
149 | 134 | wfRunHooks( 'smwInitDatatypes' ); |
150 | 135 | } |
151 | 136 | |
152 | 137 | /** |
153 | | - * A function for registering/overwriting datatypes for SMW. Should be called from |
154 | | - * within the hook 'smwInitDatatypes'. |
| 138 | + * A function for registering/overwriting datatypes for SMW. Should be |
| 139 | + * called from within the hook 'smwInitDatatypes'. |
155 | 140 | */ |
156 | 141 | static public function registerDatatype($id, $classname, $label=false) { |
157 | 142 | SMWDataValueFactory::$m_typeclasses[$id] = $classname; |
— | — | @@ -160,23 +145,24 @@ |
161 | 146 | } |
162 | 147 | |
163 | 148 | /** |
164 | | - * Add a new alias label to an existing datatype id. Note that every ID should have a primary |
165 | | - * label, either provided by SMW or registered with registerDatatype. This function should be |
166 | | - * called from within the hook 'smwInitDatatypes'. |
| 149 | + * Add a new alias label to an existing datatype id. Note that every ID |
| 150 | + * should have a primary label, either provided by SMW or registered with |
| 151 | + * registerDatatype(). This function should be called from within the hook |
| 152 | + * 'smwInitDatatypes'. |
167 | 153 | */ |
168 | 154 | static public function registerDatatypeAlias($id, $label) { |
169 | 155 | SMWDataValueFactory::$m_typealiases[$label] = $id; |
170 | 156 | } |
171 | 157 | |
172 | 158 | /** |
173 | | - * Look up the ID that identifies the datatype of the given label internally. |
174 | | - * This id is used for all internal operations. Compound types are not supported |
175 | | - * by this method (decomposition happens earlier). Custom types get their DBkeyed |
176 | | - * label as id. All ids are prefixed by an underscore in order to distinguish them |
177 | | - * from custom types. |
| 159 | + * Look up the ID that identifies the datatype of the given label |
| 160 | + * internally. This id is used for all internal operations. Compound types |
| 161 | + * are not supported by this method (decomposition happens earlier). Custom |
| 162 | + * types get their DBkeyed label as id. All ids are prefixed by an |
| 163 | + * underscore in order to distinguish them from custom types. |
178 | 164 | * |
179 | | - * This method may or may not take aliases into account. For unknown labels, the |
180 | | - * normalised (DB-version) label is used as an ID. |
| 165 | + * This method may or may not take aliases into account. For unknown |
| 166 | + * labels, the normalised (DB-version) label is used as an ID. |
181 | 167 | */ |
182 | 168 | static public function findTypeID($label, $useAlias = true) { |
183 | 169 | SMWDataValueFactory::initDatatypes(); |
— | — | @@ -192,8 +178,8 @@ |
193 | 179 | |
194 | 180 | /** |
195 | 181 | * Get the translated user label for a given internal ID. If the ID does |
196 | | - * not have a label associated with it in the current language, the ID itself |
197 | | - * is transformed into a label (appropriate for user defined types). |
| 182 | + * not have a label associated with it in the current language, the ID |
| 183 | + * itself is transformed into a label (appropriate for user defined types). |
198 | 184 | */ |
199 | 185 | static public function findTypeLabel($id) { |
200 | 186 | SMWDataValueFactory::initDatatypes(); |
— | — | @@ -201,7 +187,7 @@ |
202 | 188 | if (array_key_exists($id, SMWDataValueFactory::$m_typelabels)) { |
203 | 189 | return SMWDataValueFactory::$m_typelabels[$id]; |
204 | 190 | } else { //internal type without translation to user space; |
205 | | - //might also happen for historic types after upgrade -- |
| 191 | + //might also happen for historic types after an upgrade -- |
206 | 192 | //alas, we have no idea what the former label would have been |
207 | 193 | return str_replace('_', ' ', $id); |
208 | 194 | } |
— | — | @@ -213,8 +199,8 @@ |
214 | 200 | /** |
215 | 201 | * Return an array of all labels that a user might specify as the type of |
216 | 202 | * a property, and that are internal (i.e. not user defined). No labels are |
217 | | - * returned for internal types without user labels (e.g. the special types for |
218 | | - * some special properties), and for user defined types. |
| 203 | + * returned for internal types without user labels (e.g. the special types |
| 204 | + * for some special properties), and for user defined types. |
219 | 205 | */ |
220 | 206 | static public function getKnownTypeLabels() { |
221 | 207 | SMWDataValueFactory::initDatatypes(); |
Index: trunk/extensions/SemanticMediaWiki/includes/SMW_DV_Container.php |
— | — | @@ -0,0 +1,93 @@ |
| 2 | +<?php |
| 3 | +/** |
| 4 | + * @file |
| 5 | + * @ingroup SMWDataValues |
| 6 | + */ |
| 7 | + |
| 8 | +/** |
| 9 | + * Abstract datavalue class to implement a generic container for |
| 10 | + * complex values (internal objects) that do not have a single |
| 11 | + * value but a set of nested property-value pairs. |
| 12 | + * |
| 13 | + * @author Markus Krötzsch |
| 14 | + * @ingroup SMWDataValues |
| 15 | + */ |
| 16 | +abstract class SMWContainerValue extends SMWDataValue { |
| 17 | + |
| 18 | + protected $m_data; |
| 19 | + |
| 20 | + public function __construct($typeid) { |
| 21 | + parent::__construct($typeid); |
| 22 | + $this->m_data = new SMWSemanticData(NULL); |
| 23 | + } |
| 24 | + |
| 25 | + /** |
| 26 | + * We use the internal SMWSemanticData object to store some of this objects |
| 27 | + * data. Clone it to make sure that data can be modified independelty from |
| 28 | + * the original object's content. |
| 29 | + */ |
| 30 | + public function __clone() { |
| 31 | + $this->m_data = clone $this->m_data; // note that this is always set |
| 32 | + } |
| 33 | + |
| 34 | + /** |
| 35 | + * Containers have one DB key, so the value of this function should be an array with one |
| 36 | + * element. This one DB key should consist of an array of arbitrary length where each |
| 37 | + * entry encodes one property-value pair. The pairs are encoded as arrays of size two |
| 38 | + * that correspond to the input arguments of SMWSemanticData::addPropertyStubValue(): |
| 39 | + * a property DB key (string), and a value DB key array (array). |
| 40 | + */ |
| 41 | + protected function parseDBkeys($args) { |
| 42 | + $this->m_data->clear(); |
| 43 | + if (count($args)>0) { |
| 44 | + foreach (reset($args) as $value) { |
| 45 | + if (is_array($value) && (count($value)==2)) { |
| 46 | + $this->m_data->addPropertyStubValue(reset($value), end($value)); |
| 47 | + } |
| 48 | + } |
| 49 | + } |
| 50 | + } |
| 51 | + |
| 52 | + /** |
| 53 | + * Serialize data in the format described for parseDBkeys(). However, it is usually |
| 54 | + * expected that callers are aware of containers (this is the main purpose of this |
| 55 | + * abstract class) so they can use specific methods for accessing the data in a more |
| 56 | + * convenient form that contains the (probably available) information about property |
| 57 | + * and data *objects* (not just their plain strings). |
| 58 | + */ |
| 59 | + public function getDBkeys() { |
| 60 | + $data = array(); |
| 61 | + foreach ($this->m_data->getProperties() as $property) { |
| 62 | + foreach ($this->m_data->getPropertyValues($property) as $dv) { |
| 63 | + $data[] = array($property->getDBkey(), $dv->getDBkeys()); |
| 64 | + } |
| 65 | + } |
| 66 | + return array($data); |
| 67 | + } |
| 68 | + |
| 69 | + public function getHash() { |
| 70 | + if ( $this->isValid() ) { |
| 71 | + return $this->m_data->getHash(); |
| 72 | + } else { |
| 73 | + return implode("\t", $this->getErrors()); |
| 74 | + } |
| 75 | + } |
| 76 | + |
| 77 | + // Methods for parsing, serialisation, and display are not defined in this abstract class: |
| 78 | + // public function getShortWikiText($linked = NULL); |
| 79 | + // public function getShortHTMLText($linker = NULL); |
| 80 | + // public function getLongWikiText($linked = NULL); |
| 81 | + // public function getLongHTMLText($linker = NULL); |
| 82 | + // protected function parseUserValue($value); |
| 83 | + // public function getWikiValue(); |
| 84 | + |
| 85 | + /** |
| 86 | + * Return the stored data as a SMWSemanticData object. This is more conveniently to access than |
| 87 | + * what getDBkeys() gives, but intended only for reading. It may not be safe to write to the returned |
| 88 | + * object. |
| 89 | + */ |
| 90 | + public function getData() { |
| 91 | + return $this->m_data; |
| 92 | + } |
| 93 | + |
| 94 | +} |
Property changes on: trunk/extensions/SemanticMediaWiki/includes/SMW_DV_Container.php |
___________________________________________________________________ |
Name: svn:eol-style |
1 | 95 | + native |