2 ///////////////////////////////////////////////////////////////////////////
4 // NOTICE OF COPYRIGHT //
6 // Moodle - Modular Object-Oriented Dynamic Learning Environment //
7 // http://moodle.org //
9 // Copyright (C) 1999-onwards Moodle Pty Ltd http://moodle.com //
11 // This program is free software; you can redistribute it and/or modify //
12 // it under the terms of the GNU General Public License as published by //
13 // the Free Software Foundation; either version 2 of the License, or //
14 // (at your option) any later version. //
16 // This program is distributed in the hope that it will be useful, //
17 // but WITHOUT ANY WARRANTY; without even the implied warranty of //
18 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
19 // GNU General Public License for more details: //
21 // http://www.gnu.org/copyleft/gpl.html //
23 ///////////////////////////////////////////////////////////////////////////
25 class data_field_latlong
extends data_field_base
{
27 var $type = 'latlong';
29 // This is an array of URL schemes for linking out to services, using the float values of lat and long.
30 // In each scheme, the special markers @lat@ and @long@ will be replaced by the float values.
31 // The config options for the field store each service name that should be displayed, in a comma-separated
32 // field. Therefore please DO NOT include commas in the service names if you are adding extra services.
33 var $linkoutservices = array(
34 "Google Maps" => "http://maps.google.com/maps?q=@lat@,+@long@&iwloc=A&hl=en",
35 "Google Earth" => "@wwwroot@/mod/data/field/latlong/kml.php?d=@dataid@&fieldid=@fieldid@&rid=@recordid@",
36 "Geabios" => "http://www.geabios.com/html/services/maps/PublicMap.htm?lat=@lat@&lon=@long@&fov=0.3&title=Moodle%20data%20item",
37 "OpenStreetMap" => "http://www.openstreetmap.org/index.html?lat=@lat@&lon=@long@&zoom=11",
38 "Multimap" => "http://www.multimap.com/map/browse.cgi?scale=200000&lon=@long@&lat=@lat@&icon=x"
40 // Other map sources listed at http://kvaleberg.com/extensions/mapsources/index.php?params=51_30.4167_N_0_7.65_W_region:earth
44 // Parameter data used:
45 // "param1" is a comma-separated list of the linkout service names that are enabled for this instance
46 // "param2" indicates the label that will be used in generating Google Earth KML files: -1 for item #, -2 for lat/long, positive number for the (text) field to use.
50 function data_field_latlong($field=0, $data=0) {
51 parent
::data_field_base($field, $data);
54 function display_add_field($recordid=0){
61 if ($content = get_record('data_content', 'fieldid', $this->field
->id
, 'recordid', $recordid)) {
62 $lat = $content->content
;
63 $long = $content->content1
;
67 $str = '<div title="'.s($this->field
->description
).'">';
68 $str .= '<fieldset><legend><span class="accesshide">'.$this->field
->name
.'</span></legend>';
69 $str .= '<table><tr><td align="right">';
70 $str .= '<label for="field_'.$this->field
->id
.'_0">' . get_string('latitude', 'data') . '</label></td><td><input type="text" name="field_'.$this->field
->id
.'_0" id="field_'.$this->field
->id
.'_0" value="'.s($lat).'" size="10" />°N</td></tr>';
71 $str .= '<tr><td align="right"><label for="field_'.$this->field
->id
.'_1">' . get_string('longitude', 'data') . '</label></td><td><input type="text" name="field_'.$this->field
->id
.'_1" id="field_'.$this->field
->id
.'_1" value="'.s($long).'" size="10" />°E</td></tr>';
73 $str .= '</fieldset>';
79 function display_search_field($value = '') {
81 $lats = get_records_sql_menu('SELECT id, content from '.$CFG->prefix
.'data_content WHERE fieldid='.$this->field
->id
.' GROUP BY content ORDER BY content');
82 $longs = get_records_sql_menu('SELECT id, content1 from '.$CFG->prefix
.'data_content WHERE fieldid='.$this->field
->id
.' GROUP BY content ORDER BY content');
84 if(!empty($lats) && !empty($longs)) {
85 $options[''] = ''; //Make first index blank.
86 foreach($lats as $key => $temp) {
87 $options[$temp.','.$longs[$key]] = $temp.','.$longs[$key];
90 return choose_from_menu($options, 'f_'.$this->field
->id
, $value, 'choose', '', 0, true);
93 function parse_search_field() {
94 return optional_param('f_'.$this->field
->id
, '', PARAM_NOTAGS
);
97 function generate_sql($tablealias, $value) {
100 $latlong = explode (',', $value, 2);
101 return " ({$tablealias}.fieldid = {$this->field->id} AND {$tablealias}.content = '$latlong[0]' AND {$tablealias}.content1 = '$latlong[1]') ";
104 function display_browse_field($recordid, $template) {
106 if ($content = get_record('data_content', 'fieldid', $this->field
->id
, 'recordid', $recordid)){
107 $lat = empty($content->content
)?
'':$content->content
;
108 $long = empty($content->content1
)?
'':$content->content1
;
110 if (empty($lat) or empty($long)) {
115 $compasslat = "" . sprintf('%01.4f', 0 - $lat) . '°S';
117 $compasslat = "" . sprintf('%01.4f', $lat) . "°N";
120 $compasslong = "" . sprintf('%01.4f', 0 - $long) . '°W';
122 $compasslong = "" . sprintf('%01.4f', $long) . "°E";
125 $str = '<form style="display:inline;">';
126 $str.= "$compasslat, $compasslong";
129 // Now let's create the jump-to-services link
130 $servicesshown = explode(',', $this->field
->param1
);
132 // These are the different things that can be magically inserted into URL schemes
133 $urlreplacements = array(
136 '@wwwroot@'=> $CFG->wwwroot
,
137 '@contentid@'=> $content->id
,
138 '@dataid@'=> $this->data
->id
,
139 '@courseid@'=> $this->data
->course
,
140 '@fieldid@'=> $content->fieldid
,
141 '@recordid@'=> $content->recordid
,
144 if(sizeof($servicesshown)==1 && $servicesshown[0]) {
146 . str_replace(array_keys($urlreplacements), array_values($urlreplacements), $this->linkoutservices
[$servicesshown[0]])
147 ."'>$servicesshown[0]</a> ";
148 } elseif (sizeof($servicesshown)>1) {
149 $str .= "\n<select name='jumpto'>";
151 foreach($servicesshown as $servicename){
152 // Add a link to a service
153 $str .= "\n <option value='"
154 . str_replace(array_keys($urlreplacements), array_values($urlreplacements), $this->linkoutservices
[$servicename])
155 . "'>".htmlspecialchars($servicename)."</option>";
157 // NB! If you are editing this, make sure you don't break the javascript reference "previousSibling"
158 // which allows the "Go" button to refer to the drop-down selector.
159 $str .= "\n</select><input type='button' value='" . get_string('go') . "' onclick='if(previousSibling.value){self.location=previousSibling.value}'/>";
169 function update_content($recordid, $value, $name='') {
170 $content = new object;
171 $content->fieldid
= $this->field
->id
;
172 $content->recordid
= $recordid;
174 $names = explode('_', $name);
176 case 0: // update lat
177 $content->content
= (float)$value;
179 case 1: // update long
180 $content->content1
= (float)$value;
186 if ($oldcontent = get_record('data_content','fieldid', $this->field
->id
, 'recordid', $recordid)) {
187 $content->id
= $oldcontent->id
;
188 return update_record('data_content', $content);
190 return insert_record('data_content', $content);
194 function get_sort_sql($fieldname) {
197 switch ($CFG->dbfamily
) {
198 case 'mysql': // string in an arithmetic operation is converted to a floating-point number
199 return '('.$fieldname.'+0.0)';
200 case 'postgres': //cast is for PG
201 return 'CAST('.$fieldname.' AS REAL)';
202 default: //Return just the fieldname. TODO: Look behaviour under MSSQL and Oracle