Иногда полезно знать, куда, именно на сайте, кликают пользователи. Например, в какое место картинки или статичного элемента DIV
прошел клик.
Благодаря данному соображению и был спроектирован HeatMap: класс MooTools, позволяющий вам следить, загружать, сохранять и отображать точки данной области, куда кликнул пользователь.
CSS
На самом деле нужно только одно объявление класса в CSS. Этот класс отвечает за отображение точек. Пример кода CSS для отображения точки представлен ниже:
1 2 3 4 5 6 7 8 9 10 11 |
.heatmap-spot { width:6px; height:6px; margin-top:-3px; margin-left:-3px; -webkit-border-radius:4px; -moz-border-radius:4px; background:#fff; position:absolute; /* important! */ z-index:200; } |
Обратите внимание на то, что вы можете управлять размерами точек. Уменьшая или увеличивая margins
, вы увеличиваете или уменьшаете точку.
MooTools JavaScript
Класс достаточно компактен. HeatMap позволяет просто загружать и сохранять точки с минимальным JS кодом:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 |
var HeatMap = new Class({ options: { event: 'click', load: { // request settings here }, method: 'get', save: { // request settings here }, spotClass: 'heatmap-spot', zone: ''/*, onClick: $empty, onSpot: $empty */ }, Implements: [Options,Events], initialize: function(element,options) { this.element = document.id(element).setStyle('position','relative'); this.setOptions(options); this.newClicks = []; this.oldClicks = []; this.attachEvents(); }, attachEvents: function() { var self = this; this.clickEvent = function(e) { var obj = self.getRelativePosition(e.page.x,e.page.y); obj.spot = self.createSpot(obj.x,obj.y); self.newClicks.push(obj); }; this.element.addEvent(this.options.event,this.clickEvent); }, detachEvents: function() { this.element.removeEvent(this.options.event, this.clickEvent); }, getRelativePosition: function(x,y) { var position = this.element.getPosition(); return { x: x - position.x, y: y - position.y }; }, load: function() { if(!this.loadRequest) this.loadRequest = new Request.JSON(this.options.load); if(!this.options.load.onSuccess && !this.loadSuccess) { this.loadSuccess = function(json) { json.each(function(click,i) { json[i].spot = this.createSpot(click.x,click.y); this.oldClicks.push(json[i]); },this); }.bind(this); this.loadRequest.addEvent('success',this.loadSuccess); } this.loadRequest[this.options.method]({ load: 1, zone: this.options.zone }); return this; }, save: function(data) { if(!this.sendRequest) this.sendRequest = new Request.JSON(this.options.save); if(this.newClicks.length) { this.sendRequest.addEvent('success',function() { this.newClicks.each(function(click) { this.oldClicks.push(this.createSpot({ x: click.x, y:click.y })); },this); this.newClicks = []; }.bind(this)); this.sendRequest[this.options.method]({ save: 1, zone: this.options.zone, data: this.newClicks }); } return this; }, createSpot: function(x,y) { var spot = new Element('div',{ 'class': this.options.spotClass, styles: { top: y.toInt(), left: x.toInt() } }).inject(this.element); this.fireEvent('spot',[spot,x,y]); return spot; } }); |
Аргументы для HeatMap:
- element: элемент на котором будет висеть «прослушка» кликов
- options: опции для экземпляра класса
Опции для HeatMap:
- event: (строка, по умолчанию событие) событие для прослушки — по умолчанию, клик мыши
- load: (объект, по умолчанию {}) Request.JSON объект для загрузки точек
- method: (строка, по умолчанию «get») Request.JSON тип запроса
- save: (объект, по умолчанию {}) Request.JSON объект для сохранения точек
- spotClass: (строка, по умолчанию 'heatmap-spot') класс CSS для стилизации точки
- zone: (строка, по умолчанию '') «зона» на которой был сделан клик мыши; особенно важно, если зон на странице несколько.
События для HeatMap:
- onSpot: инициализируется, когда создается точка.
Относительно простой класс. Его можно было бы сделать и сложнее, но оставим его таким, чтобы можно было бы использовать для итераций.
Использование HeatMap
Использование довольно просто:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
/* использование */ window.addEvent('domready',function() { map = new HeatMap('ricci-map',{ zone: 'cricci', save: { url: 'heat-map.php' }, load: { url: 'heat-map.php' }, onSpot: function(spot) { spot.setStyle('opacity',0).fade(1); } }); document.id('loader').addEvent('click',function() { map.load(); }); document.id('saver').addEvent('click',function() { map.save(); }); }); |
Намного проще, чем вы могли себе представить! Мы советуем использовать события click
, потому как другие типы событий могут ввести в заблуждение пользователей и создать громадное количество данных, например, для событий mouseenter
.
MySQL таблица
Выглядит следующим образом:
1 2 3 4 5 6 7 8 |
CREATE TABLE `example_heatmap` ( `click_id` mediumint(6) NOT NULL auto_increment, `zone` varchar(60) NOT NULL default '', `x` smallint(5) NOT NULL default '0', `y` smallint(5) NOT NULL default '0', `date_clicked` datetime NOT NULL, PRIMARY KEY (`click_id`) ) ENGINE=MyISAM AUTO_INCREMENT=22 DEFAULT CHARSET=utf8; |
Скрипт PHP
Мы хотели отметить несколько вещей относительно серверной части кода:
- Вы можете использовать любой серверный язык для облегчения загрузки и экономии места. Мы использовали PHP потому, что он знаком нам более всего.
- Важно ваше мнение об использовании скрипта сохранения точек.
Ниже PHP код для сохранения и загрузки точек:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 |
/* загрузка */ if(isset($_GET['load'])) { /* переменные */ $spots = array(); /* подключение к БД */ $connection = mysql_connect('localhost','dbuser','dbpass'); mysql_select_db('dbname',$connection); /* Загрузка точек */ $query = 'SELECT * FROM example_heatmap WHERE zone = \''.mysql_escape_string($_GET['zone']).'\' LIMIT 2000'; $result = mysql_query($query,$connection); while($record = mysql_fetch_assoc($result)) { $spots[] = $record; } /* закрытие подключения к БД */ mysql_close($connection); /* возврат результатов */ $json = json_encode($spots); echo $json; die(); } /* сохранение */ elseif(isset($_GET['save']) && isset($_GET['data']) && count($_GET['data'])) { /* переменные */ $query = 'INSERT INTO example_heatmap (zone,x,y,date_clicked) VALUES '; $queryRecords = array(); $records = 0; /* подключение к БД */ $connection = mysql_connect('localhost','dbuser','dbpass'); mysql_select_db('dbname',$connection); /* cохранение */ foreach($_GET['data'] as $data) { $queryRecords[] = '(\''.mysql_escape_string($_GET['zone']).'\','.mysql_escape_string($data['x']).', '.mysql_escape_string($data['y']).',NOW())'; $records++; } /* выполняем запрос и закрываем */ $query.= implode(',',$queryRecords); mysql_query($query,$connection); mysql_close($connection); /* возврат результатов */ die(count($records)); } |
Предпочтение отдано компактности кода и общей функциональности в одном файле.
Принесите много тепла!
MooTools HeatMap является занимательной и веселой штукой. Вы сами можете придумать, как и где использовать этот класс. Достаточно посмотреть на пример и вам станет все понятно. Удачи в реализации!