blob: f30287b3c87e07079b7169f58ab570a64937182f [file] [log] [blame]
Akron99713ef2017-06-28 18:19:28 +02001/**
2 * Information about a match.
3 */
Nils Diewald7c8ced22015-04-15 19:21:00 +00004define([
5 'match/infolayer',
6 'match/table',
Akron41387d22018-02-02 18:10:06 +01007 'match/treehierarchy',
8 'match/treearc',
Akron151bc872018-02-02 14:04:15 +01009 'match/meta',
Nils Diewald7c8ced22015-04-15 19:21:00 +000010 'util'
11], function (infoLayerClass,
Akron3bb91bc2016-12-02 16:43:17 +010012 matchTableClass,
Akron41387d22018-02-02 18:10:06 +010013 matchTreeHierarchyClass,
14 matchTreeArcClass,
Akronb6685bb2018-02-04 00:44:47 +010015 matchMetaClass) {
Akron3bb91bc2016-12-02 16:43:17 +010016
Nils Diewald7148c6f2015-05-04 15:07:53 +000017 // Override
Nils Diewald0e6992a2015-04-14 20:13:52 +000018 KorAP.API.getMatchInfo = KorAP.API.getMatchInfo || function () {
19 KorAP.log(0, 'KorAP.API.getMatchInfo() not implemented')
20 return {};
21 };
22
Akron0b489ad2018-02-02 16:49:32 +010023 const loc = KorAP.Locale;
24 const d = document;
Nils Diewald0e6992a2015-04-14 20:13:52 +000025
Nils Diewald0e6992a2015-04-14 20:13:52 +000026 return {
Nils Diewald7148c6f2015-05-04 15:07:53 +000027
28 /**
29 * Create new match object
30 */
Nils Diewald0e6992a2015-04-14 20:13:52 +000031 create : function (match) {
32 return Object.create(this)._init(match);
33 },
34
Akron151bc872018-02-02 14:04:15 +010035
Nils Diewald0e6992a2015-04-14 20:13:52 +000036 /**
37 * Initialize object
38 */
39 _init : function (match) {
40 this._match = match;
Akronedbf33a2018-02-05 19:18:03 +010041 this._visibleTable = false;
42 this._visibleMeta = false;
Nils Diewald0e6992a2015-04-14 20:13:52 +000043 this.opened = false;
44 return this;
45 },
46
Akron151bc872018-02-02 14:04:15 +010047
Nils Diewald0e6992a2015-04-14 20:13:52 +000048 /**
49 * Get match object
50 */
51 match : function () {
52 return this._match;
53 },
54
Nils Diewald7148c6f2015-05-04 15:07:53 +000055
56 /**
57 * Open the information view,
58 * if closed, otherwise close.
59 */
Akronbd342982018-01-25 18:01:46 +010060 /*
Nils Diewald0e6992a2015-04-14 20:13:52 +000061 toggle : function () {
Akron3bb91bc2016-12-02 16:43:17 +010062
Akron08b82d62016-12-05 15:06:05 +010063 var elem = this._match.element();
Akron3bb91bc2016-12-02 16:43:17 +010064
65 if (this.opened == true) {
Akrond67d45b2017-05-18 21:47:38 +020066 elem.removeChild(
67 this.element()
68 );
69 this.opened = false;
Nils Diewald0e6992a2015-04-14 20:13:52 +000070 }
71 else {
Akrond67d45b2017-05-18 21:47:38 +020072 // Append element to match
Akron3bb91bc2016-12-02 16:43:17 +010073 elem.appendChild(
Akrond67d45b2017-05-18 21:47:38 +020074 this.element()
75 );
76 this.opened = true;
Nils Diewald0e6992a2015-04-14 20:13:52 +000077 };
78
79 return this.opened;
80 },
Akronbd342982018-01-25 18:01:46 +010081 */
Nils Diewald0e6992a2015-04-14 20:13:52 +000082
83
84 /**
Nils Diewald7148c6f2015-05-04 15:07:53 +000085 * Retrieve and parse snippet for table
86 * representation
Nils Diewald0e6992a2015-04-14 20:13:52 +000087 */
Akron151bc872018-02-02 14:04:15 +010088 getTableData : function (tokens, cb) {
Nils Diewald0e6992a2015-04-14 20:13:52 +000089 var focus = [];
90
91 // Get all tokens
92 if (tokens === undefined) {
Akrond67d45b2017-05-18 21:47:38 +020093 focus = this._match.getTokens();
Nils Diewald0e6992a2015-04-14 20:13:52 +000094 }
95
96 // Get only some tokens
97 else {
Akrond67d45b2017-05-18 21:47:38 +020098
99 // Push newly to focus array
100 for (var i = 0; i < tokens.length; i++) {
101 var term = tokens[i];
102 try {
103 // Create info layer objects
104 var layer = infoLayerClass.create(term);
105 layer.type = "tokens";
106 focus.push(layer);
107 }
108 catch (e) {
109 continue;
110 };
111 };
Nils Diewald0e6992a2015-04-14 20:13:52 +0000112 };
113
114 // No tokens chosen
115 if (focus.length == 0)
Akrond67d45b2017-05-18 21:47:38 +0200116 cb(null);
Nils Diewald0e6992a2015-04-14 20:13:52 +0000117
Akron4f791442018-02-12 13:25:47 +0100118 try {
119 // Get info (may be cached)
120 KorAP.API.getMatchInfo(
121 this._match,
122 { 'spans' : false, 'layer' : focus },
Akrond67d45b2017-05-18 21:47:38 +0200123
Akron4f791442018-02-12 13:25:47 +0100124 // Callback for retrieval
125 function (matchResponse) {
Akron3bb91bc2016-12-02 16:43:17 +0100126
Akron4f791442018-02-12 13:25:47 +0100127 if (matchResponse === undefined)
128 cb(null);
Akron515851a2017-05-02 12:53:17 +0200129
Akron4f791442018-02-12 13:25:47 +0100130 // Get snippet from match info
131 if (matchResponse["snippet"] !== undefined) {
132 this._table = matchTableClass.create(matchResponse["snippet"]);
133 cb(this._table);
134 };
135 }.bind(this)
136 );
137 }
138 catch (e) {
139 KorAP.log(0, e);
140 cb(null);
141 };
Nils Diewald0e6992a2015-04-14 20:13:52 +0000142
143 /*
144 // Todo: Store the table as a hash of the focus
145 return null;
146 */
147 },
Akronbd342982018-01-25 18:01:46 +0100148
149
Akron4f791442018-02-12 13:25:47 +0100150 /**
151 * Receive meta data from server.
152 */
Akron0ad7cd22018-02-08 18:03:06 +0100153 getMetaData : function (cb) {
Akronb5d05d72018-02-12 15:09:12 +0100154
155 var match = this._match;
156
Akron4f791442018-02-12 13:25:47 +0100157 try {
158 KorAP.API.getTextInfo(
Akronb5d05d72018-02-12 15:09:12 +0100159 match, {}, function (textResponse) {
160
Akron4f791442018-02-12 13:25:47 +0100161 if (textResponse === undefined) {
162 cb(null);
163 return;
164 };
Akron0ad7cd22018-02-08 18:03:06 +0100165
Akron4f791442018-02-12 13:25:47 +0100166 var doc = textResponse["document"];
Akron0ad7cd22018-02-08 18:03:06 +0100167
Akron4f791442018-02-12 13:25:47 +0100168 if (doc === undefined) {
169 cb(null);
170 return;
171 };
Akron0ad7cd22018-02-08 18:03:06 +0100172
Akron4f791442018-02-12 13:25:47 +0100173 var fields = doc["fields"];
174 if (fields === undefined) {
175 cb(null);
176 return;
177 };
Akron0ad7cd22018-02-08 18:03:06 +0100178
Akron4f791442018-02-12 13:25:47 +0100179 // Add metainfo to matchview
180 cb(matchMetaClass.create(
Akronb5d05d72018-02-12 15:09:12 +0100181 match, fields
Akron4f791442018-02-12 13:25:47 +0100182 ));
183 }
184 );
185 }
186 catch (e) {
187 KorAP.log(0, e);
188 cb(null);
189 };
Akronbd342982018-01-25 18:01:46 +0100190 },
Nils Diewald0e6992a2015-04-14 20:13:52 +0000191
192
193 /**
194 * Retrieve and parse snippet for tree representation
195 */
Akron151bc872018-02-02 14:04:15 +0100196 getTreeData : function (foundry, layer, type, cb) {
Nils Diewald0e6992a2015-04-14 20:13:52 +0000197 var focus = [];
Akron0ad7cd22018-02-08 18:03:06 +0100198
Akron4f791442018-02-12 13:25:47 +0100199 try {
200 // TODO: Support and cache multiple trees
201 KorAP.API.getMatchInfo(
202 this._match, {
203 'spans' : true,
204 'foundry' : foundry,
205 'layer' : layer
206 },
207 function (matchResponse) {
208 if (matchResponse === undefined) {
209 cb(null);
210 return;
211 };
Akronc56cf2d2016-11-09 22:02:38 +0100212
Akron4f791442018-02-12 13:25:47 +0100213 // Get snippet from match info
214 if (matchResponse["snippet"] !== undefined) {
215 // Todo: This should be cached somehow
216
217 if (type === "spans") {
218 cb(matchTreeHierarchyClass.create(matchResponse["snippet"]));
219 }
220 else if (type === "rels") {
221 cb(matchTreeArcClass.create(matchResponse["snippet"]));
222 }
223
224 // Unknown tree type
225 else {
226 cb(null);
227 };
Akron0988d882017-11-10 16:13:12 +0100228 }
Akron0988d882017-11-10 16:13:12 +0100229 else {
230 cb(null);
231 };
Akron4f791442018-02-12 13:25:47 +0100232 }.bind(this)
233 );
234 }
235 catch (e) {
236 KorAP.log(0, e);
237 cb(null);
238 };
Nils Diewald0e6992a2015-04-14 20:13:52 +0000239 },
240
Akron151bc872018-02-02 14:04:15 +0100241
Nils Diewald0e6992a2015-04-14 20:13:52 +0000242 /**
243 * Destroy this match information view.
244 */
245 destroy : function () {
246
247 // Remove circular reference
Akron8b592d42018-01-26 18:33:06 +0100248 /*
Nils Diewald0e6992a2015-04-14 20:13:52 +0000249 if (this._treeMenu !== undefined)
Akron99713ef2017-06-28 18:19:28 +0200250 delete this._treeMenu["info"];
Nils Diewald0e6992a2015-04-14 20:13:52 +0000251
252 this._treeMenu.destroy();
253 this._treeMenu = undefined;
Akron8b592d42018-01-26 18:33:06 +0100254 */
Nils Diewald0e6992a2015-04-14 20:13:52 +0000255 this._match = undefined;
Akron99713ef2017-06-28 18:19:28 +0200256 this._matchCreator = undefined;
Nils Diewald0e6992a2015-04-14 20:13:52 +0000257 // Element destroy
258 },
259
Akron151bc872018-02-02 14:04:15 +0100260
Nils Diewald0e6992a2015-04-14 20:13:52 +0000261 /**
262 * Add a new tree view to the list
263 */
Akron151bc872018-02-02 14:04:15 +0100264 showTree : function (foundry, layer, type, cb) {
Akron0b489ad2018-02-02 16:49:32 +0100265 var matchtree = d.createElement('div');
Akronc8eb4a12018-02-03 00:39:58 +0100266 matchtree.classList.add('matchtree', 'loading');
267
268 this.element().appendChild(matchtree);
Akrond67d45b2017-05-18 21:47:38 +0200269
Akron151bc872018-02-02 14:04:15 +0100270 // Add title line
271 var h6 = matchtree.addE('h6');
272 h6.addE('span').addT(foundry);
273 h6.addE('span').addT(layer);
274
275 var tree = matchtree.addE('div');
Nils Diewald0e6992a2015-04-14 20:13:52 +0000276
Akron151bc872018-02-02 14:04:15 +0100277 // Add close action button
Akronc8eb4a12018-02-03 00:39:58 +0100278 var actions = this._addButton('close', matchtree, function (e) {
279 this.parentNode.removeChild(this);
280 e.halt();
281 });
Nils Diewald0e6992a2015-04-14 20:13:52 +0000282
Akronc8eb4a12018-02-03 00:39:58 +0100283 // tree.classList.add('loading'); // alternatively
Nils Diewald0ec142f2015-05-05 00:29:23 +0000284
Nils Diewald0e6992a2015-04-14 20:13:52 +0000285 // Get tree data async
Akron151bc872018-02-02 14:04:15 +0100286 this.getTreeData(foundry, layer, type, function (treeObj) {
Akronc8eb4a12018-02-03 00:39:58 +0100287 matchtree.classList.remove('loading');
Nils Diewald0ec142f2015-05-05 00:29:23 +0000288
Akrond67d45b2017-05-18 21:47:38 +0200289 // Something went wrong - probably log!!!
Nils Diewald0ec142f2015-05-05 00:29:23 +0000290
Akrond67d45b2017-05-18 21:47:38 +0200291 if (treeObj === null) {
Akron151bc872018-02-02 14:04:15 +0100292 tree.addT('No data available.');
Akrond67d45b2017-05-18 21:47:38 +0200293 }
294 else {
295 tree.appendChild(treeObj.element());
Akron0988d882017-11-10 16:13:12 +0100296 treeObj.show();
Akron151bc872018-02-02 14:04:15 +0100297
Akrond67d45b2017-05-18 21:47:38 +0200298 // Reposition the view to the center
299 // (This may in a future release be a reposition
Akron151bc872018-02-02 14:04:15 +0100300 // to move the root to the actual match)
Akronc56cf2d2016-11-09 22:02:38 +0100301
Akron0988d882017-11-10 16:13:12 +0100302 // This is currently not supported by relations
303 if (type === "spans") {
Akron0b489ad2018-02-02 16:49:32 +0100304 var dl = d.createElement('li');
Akron0988d882017-11-10 16:13:12 +0100305 dl.className = 'download';
306 dl.addEventListener(
307 'click', function (e) {
Akron151bc872018-02-02 14:04:15 +0100308 var a = treeObj.downloadLink();
Akron0b489ad2018-02-02 16:49:32 +0100309 d.body.appendChild(a);
Akron0988d882017-11-10 16:13:12 +0100310 a.click();
Akron0b489ad2018-02-02 16:49:32 +0100311 d.body.removeChild(a)
Akron0988d882017-11-10 16:13:12 +0100312 e.halt();
313 }
314 );
315
316 actions.appendChild(dl);
317 };
318
Akronc56cf2d2016-11-09 22:02:38 +0100319 treeObj.center();
Akrond67d45b2017-05-18 21:47:38 +0200320 };
321
322 if (cb !== undefined)
323 cb(treeObj);
Nils Diewald0e6992a2015-04-14 20:13:52 +0000324 });
Akronc8eb4a12018-02-03 00:39:58 +0100325 matchtree.classList.remove('loading');
Nils Diewald0e6992a2015-04-14 20:13:52 +0000326 },
Akronbd342982018-01-25 18:01:46 +0100327
328
Akrone7679692018-01-26 12:06:33 +0100329 // Add meta information to match
Akron151bc872018-02-02 14:04:15 +0100330 showMeta : function () {
Akronedbf33a2018-02-05 19:18:03 +0100331
332 // Already visible
333 if (this._visibleMeta)
334 return;
335
336 this._visibleMeta = true;
337
Akronaeceda72018-02-02 20:44:06 +0100338 var metaTable = document.createElement('div');
Akronc8eb4a12018-02-03 00:39:58 +0100339 metaTable.classList.add('metatable', 'loading');
340 this.element().appendChild(metaTable);
Akronbd342982018-01-25 18:01:46 +0100341
Akron0ad7cd22018-02-08 18:03:06 +0100342 /*
343 * This was temporary
Akronbd342982018-01-25 18:01:46 +0100344 var metaInfo = this._match.element().getAttribute('data-info');
Akronbd342982018-01-25 18:01:46 +0100345 if (metaInfo)
346 metaInfo = JSON.parse(metaInfo);
Akron0ad7cd22018-02-08 18:03:06 +0100347 */
Akronedbf33a2018-02-05 19:18:03 +0100348 var that = this;
349
Akron0ad7cd22018-02-08 18:03:06 +0100350 this.getMetaData(function (meta) {
Akronb5d05d72018-02-12 15:09:12 +0100351
352 if (meta === null)
353 return;
354
Akronc8eb4a12018-02-03 00:39:58 +0100355 // Load data
356 metaTable.classList.remove('loading');
357
Akron0ad7cd22018-02-08 18:03:06 +0100358 metaTable.appendChild(meta.element());
Akronaeceda72018-02-02 20:44:06 +0100359
360 // Add button
Akron0ad7cd22018-02-08 18:03:06 +0100361 that._addButton('close', metaTable, function (e) {
Akronaeceda72018-02-02 20:44:06 +0100362 this.parentNode.removeChild(this);
Akronedbf33a2018-02-05 19:18:03 +0100363 that._visibleMeta = false;
Akronaeceda72018-02-02 20:44:06 +0100364 e.halt();
365 });
Akron0ad7cd22018-02-08 18:03:06 +0100366 });
Akron41387d22018-02-02 18:10:06 +0100367
Akron0ad7cd22018-02-08 18:03:06 +0100368 // Do not load any longer
Akronaeceda72018-02-02 20:44:06 +0100369 metaTable.classList.remove('loading');
Akronbd342982018-01-25 18:01:46 +0100370 },
371
Akron151bc872018-02-02 14:04:15 +0100372
Akronbd342982018-01-25 18:01:46 +0100373 // Add table
Akron151bc872018-02-02 14:04:15 +0100374 showTable : function () {
Akronbd342982018-01-25 18:01:46 +0100375
Akronedbf33a2018-02-05 19:18:03 +0100376 // Already visible
377 if (this._visibleTable)
378 return;
379
380 this._visibleTable = true;
381
Nils Diewald0e6992a2015-04-14 20:13:52 +0000382 // Append default table
Akron0b489ad2018-02-02 16:49:32 +0100383 var matchtable = d.createElement('div');
Akronc8eb4a12018-02-03 00:39:58 +0100384 matchtable.classList.add('matchtable', 'loading');
Akronaeceda72018-02-02 20:44:06 +0100385 var info = this.element();
386 info.appendChild(matchtable);
387
Akronedbf33a2018-02-05 19:18:03 +0100388 var that = this;
Nils Diewald0e6992a2015-04-14 20:13:52 +0000389
Akronb6685bb2018-02-04 00:44:47 +0100390 // TODO:
391 // Create try-catch-exception-handling
392
Nils Diewald0e6992a2015-04-14 20:13:52 +0000393 // Create the table asynchronous
Akron151bc872018-02-02 14:04:15 +0100394 this.getTableData(undefined, function (table) {
Akron3bb91bc2016-12-02 16:43:17 +0100395
Akronc8eb4a12018-02-03 00:39:58 +0100396 // Load data
397 matchtable.classList.remove('loading');
398
Akrond67d45b2017-05-18 21:47:38 +0200399 if (table !== null) {
Akron3bb91bc2016-12-02 16:43:17 +0100400 matchtable.appendChild(table.element());
401 };
Nils Diewald0e6992a2015-04-14 20:13:52 +0000402 });
Akronaeceda72018-02-02 20:44:06 +0100403
404 // Add button
405 this._addButton('close', matchtable, function (e) {
406 this.parentNode.removeChild(this);
Akronedbf33a2018-02-05 19:18:03 +0100407 that._visibleTable = false;
Akronaeceda72018-02-02 20:44:06 +0100408 e.halt();
409 });
410
411 // Load data
412 matchtable.classList.remove('loading');
Akronbd342982018-01-25 18:01:46 +0100413 },
414
Akronc8eb4a12018-02-03 00:39:58 +0100415 // Add action button
Akronaeceda72018-02-02 20:44:06 +0100416 _addButton : function (buttonType, element, cb) {
417 // TODO: Unless existent
418 var actions = document.createElement('ul');
419 actions.classList.add('action', 'image');
420 var b = actions.addE('li');
421 b.className = buttonType;
422 b.addE('span').addT(buttonType);
423 b.addEventListener(
424 'click', cb.bind(element)
425 );
426
427 element.appendChild(actions);
428 return actions;
429 },
430
431
Akronbd342982018-01-25 18:01:46 +0100432 /**
433 * Create match information view.
434 */
435 element : function () {
436
437 if (this._element !== undefined)
438 return this._element;
439
440 // Create info table
Akron0b489ad2018-02-02 16:49:32 +0100441 var info = d.createElement('div');
Akronbd342982018-01-25 18:01:46 +0100442 info.classList.add('matchinfo');
Nils Diewald0e6992a2015-04-14 20:13:52 +0000443
444 this._element = info;
445
Akronbd342982018-01-25 18:01:46 +0100446 return this._element;
Nils Diewald0e6992a2015-04-14 20:13:52 +0000447 }
448 };
449});