-
Notifications
You must be signed in to change notification settings - Fork 211
Reuters tutorial: step 8
- Reuters tutorial
- Step 1: Talk to Solr
- Step 2: Add a results widget
- Step 3: Add a pager widget
- Step 4: Add a tagcloud widget
- Step 5: Display the current filters
- Step 6: Add a free-text widget
- Step 7: Add an autocomplete widget
- Step 8: Add a map widget
- Step 9: Add a calendar widget
- Step 10: Extra credit
We want to allow the user to explore the Reuters business news by place of origin. In a first stage, we will allow the user to use the facet data for filtering. In a second stage, we will allow the user to see the facet data displayed via a map using the Google Chart API.
First, update the Solr parameters for faceting in reuters.js:
var params = { ... 'facet.field': [ 'topics', 'organisations', 'exchanges', 'countryCodes' ], ... 'f.countryCodes.facet.limit': -1, ... };
The facet.limit parameter for countryCodes is set to a negative value so that Solr returns all facet values.
Create a new widget, CountryCodeWidget.js, inheriting from AbstractFacetWidget, as for the tagcloud:
(function ($) { AjaxSolr.CountryCodeWidget = AjaxSolr.AbstractFacetWidget.extend({ }); })(jQuery);
Add the JavaScript file:
<script src="widgets/CountryCodeWidget.js"></script>
And add an instance of the widget to the Manager in reuters.js:
Manager.addWidget(new AjaxSolr.CountryCodeWidget({ id: 'countries', target: '#countries', field: 'countryCodes' }));
We will need the following utility function to implement the widget, so add it to reuters.js:
$.fn.showIf = function (condition) { if (condition) { return this.show(); } else { return this.hide(); } }
Now, we’re ready to implement afterRequest. Below, we keep track of the largest facet count, because we will need it in the second stage outlined above:
afterRequest: function () { var self = this; $(this.target).empty(); var maxCount = 0; var options = { '': '--select--' }; for (var facet in this.manager.response.facet_counts.facet_fields[this.field]) { if (facet.length == 2) { // only display country codes var count = this.manager.response.facet_counts.facet_fields[this.field][facet]; if (count > maxCount) { maxCount = count; } options[facet] = facet + ' (' + count + ')'; } } $(this.target).append(this.template('country', options)); $(this.target).find('#country').change(function () { var value = $(this).val(); if (value && self.add(value)) { self.doRequest(); } }); }, template: function (name, container) { var options = []; for (var value in container) { options.push('<option value="' + value +'">' + container[value] + '</option>'); } return '<select id="' + name + '" name="' + name + '">' + options.join('\n') + '</select>'; }
Within the afterRequest method, in the first block of code after emptying the target, we compile a list of options for a select tag, and append to the target a select tag with an id of #country with those options. The rest of this first block should be familiar.
In the second block of code, as in the free-text widget, we use the AbstractFacetWidget add API method directly.
Now, let’s display the facet data with a map visualization. First, create a drop-down list with which the user may select which part of the world to focus on. Add the following code right after emptying the target:
var maps = { world: 'view the World', africa: 'view Africa', asia: 'view Asia', europe: 'view Europe', middle_east: 'view the Middle East', south_america: 'view South America', usa: 'view North America' }; $(this.target).append(this.template('region', maps)); $(this.target).find('#region').change(function () { $(self.target).find('img').hide(); $('#' + self.id + $(this).val()).show(); });
The change function will control which part of the world we display to the user. Now, we can create those maps by adding the following code before the end of the afterRequest method:
var chd = []; var chld = ''; for (var facet in this.manager.response.facet_counts.facet_fields[this.field]) { if (facet.length == 2) { // only display country codes chd.push(parseInt(this.manager.response.facet_counts.facet_fields[this.field][facet] / maxCount * 100) + '.0'); chld += facet; } } for (var value in maps) { var src = 'http://chart.apis.google.com/chart?chco=f5f5f5,edf0d4,6c9642,365e24,13390a&chd=t:' + chd.join(',') + '&chf=bg,s,eaf7fe&chtm=' + value + '&chld=' + chld + '&chs=350x180&cht=t'; $('<img>').attr('id', this.id + value).showIf(value == 'world').attr('src', src).appendTo(this.target); }
The above code has almost nothing to do with AJAX Solr. I include it only to show that it is very easy to create fancy visualizations with AJAX Solr. Congrats, you now have a map widget!