Commit 81eb23f25652c0b7608b267a62d10d3d768d06e2
1 parent
523e0c1b
Exists in
master
and in
29 other branches
Add MapBalloonController
Map balloons are now loaded by Ajax and have their own controller and views.
Showing
8 changed files
with
146 additions
and
120 deletions
Show diff stats
... | ... | @@ -0,0 +1,28 @@ |
1 | +class MapBalloonController < PublicController | |
2 | + | |
3 | + before_filter :profile, :only => [:person, :enterprise, :community] | |
4 | + | |
5 | + def product | |
6 | + @product = Product.find(params[:id]) | |
7 | + render :action => 'product', :layout => false | |
8 | + end | |
9 | + | |
10 | + def person | |
11 | + render :action => 'profile', :layout => false | |
12 | + end | |
13 | + | |
14 | + def enterprise | |
15 | + render :action => 'profile', :layout => false | |
16 | + end | |
17 | + | |
18 | + def community | |
19 | + render :action => 'profile', :layout => false | |
20 | + end | |
21 | + | |
22 | + protected | |
23 | + | |
24 | + def profile | |
25 | + @profile = Profile.find(params[:id]) | |
26 | + end | |
27 | + | |
28 | +end | ... | ... |
app/helpers/search_helper.rb
... | ... | @@ -33,62 +33,6 @@ module SearchHelper |
33 | 33 | content_tag('div', data[:toggle] + (render :partial => data[:partial]), :class => "map-or-list-search-results #{data[:class]}") |
34 | 34 | end |
35 | 35 | |
36 | - def display_item_map_info(item) | |
37 | - if item.kind_of?(Profile) | |
38 | - display_profile_info(item) | |
39 | - elsif item.kind_of?(Product) | |
40 | - display_product_info(item) | |
41 | - end | |
42 | - end | |
43 | - | |
44 | - def display_profile_info(profile) | |
45 | - data = '' | |
46 | - unless profile.contact_email.nil? | |
47 | - data << content_tag('strong', _('E-Mail: ')) + profile.contact_email + '<br/>' | |
48 | - end | |
49 | - unless profile.contact_phone.nil? | |
50 | - data << content_tag('strong', _('Phone(s): ')) + profile.contact_phone + '<br/>' | |
51 | - end | |
52 | - unless profile.region.nil? | |
53 | - data << content_tag('strong', _('Location: ')) + profile.region.name + '<br/>' | |
54 | - end | |
55 | - unless profile.address.nil? | |
56 | - data << content_tag('strong', _('Address: ')) + profile.address + '<br/>' | |
57 | - end | |
58 | - unless profile.products.empty? | |
59 | - data << content_tag('strong', _('Products/Services: ')) + profile.products.map{|i| link_to(i.name, :controller => 'manage_products', :profile => profile.identifier, :action => 'show', :id => i.id)}.join(', ') + '<br/>' | |
60 | - end | |
61 | - if profile.respond_to?(:distance) and !profile.distance.nil? | |
62 | - data << content_tag('strong', _('Distance: ')) + "%.2f%" % profile.distance + '<br/>' | |
63 | - end | |
64 | - content_tag('table', | |
65 | - content_tag('tr', | |
66 | - content_tag('td', content_tag('div', profile_image(profile, :thumb), :class => 'profile-info-picture')) + | |
67 | - content_tag('td', content_tag('strong', link_to(profile.name, url_for(profile.url))) + '<br/>' + data | |
68 | - ) | |
69 | - ), | |
70 | - :class => 'profile-info' | |
71 | - ) | |
72 | - end | |
73 | - | |
74 | - def display_product_info(product) | |
75 | - data = '' | |
76 | - unless product.price.nil? | |
77 | - data << content_tag('strong', _('Price: ')) + product.price + '<br/>' | |
78 | - end | |
79 | - unless product.enterprise.nil? | |
80 | - data << content_tag('strong', _('Provider: ')) + link_to_profile(product.enterprise.name, product.enterprise.identifier) | |
81 | - end | |
82 | - unless product.product_category.nil? | |
83 | - data << content_tag('strong', _('Category: ')) + link_to(product.product_category.name, :controller => 'search', :action => 'assets', :asset => 'products', :product_category => product.product_category.id) | |
84 | - end | |
85 | - content_tag('table', | |
86 | - content_tag('tr', | |
87 | - content_tag('td', content_tag('div', image_tag(product.image ? product.image.public_filename(:thumb) : '/images/icons-app/product-default-pic-portrait.png'), :class => 'profile-info-picture')) + | |
88 | - content_tag('td', content_tag('strong', link_to(product.name, :controller => 'catalog', :profile => product.enterprise.identifier, :id => product.id)) + '<br/>' + data) | |
89 | - ), :class => 'profile-info') | |
90 | - end | |
91 | - | |
92 | 36 | def product_categories_menu(asset, product_category, object_ids = nil) |
93 | 37 | cats = ProductCategory.menu_categories(@product_category, environment) |
94 | 38 | cats += cats.select { |c| c.children_count > 0 }.map(&:children).flatten | ... | ... |
... | ... | @@ -0,0 +1,28 @@ |
1 | +<div id="balloon"> | |
2 | + <table class='profile-info'> | |
3 | + <tr> | |
4 | + <td><div class='profile-info-picture'><%= profile_image(@profile, :thumb) %></div></td> | |
5 | + <td> | |
6 | + <strong><%= link_to(@profile.name, url_for(@profile.url)) %></strong><br/> | |
7 | + <% unless @profile.contact_email.nil? %> | |
8 | + <strong><%= _('E-Mail: ') + @profile.contact_email %></strong><br/> | |
9 | + <% end %> | |
10 | + <% unless @profile.contact_phone.nil? %> | |
11 | + <strong><%= _('Phone(s): ') + @profile.contact_phone %></strong><br/> | |
12 | + <% end %> | |
13 | + <% unless @profile.region.nil? %> | |
14 | + <strong><%= _('Location: ') + @profile.region.name %></strong><br/> | |
15 | + <% end %> | |
16 | + <% unless @profile.address.nil? %> | |
17 | + <strong><%= _('Address: ') + @profile.address %></strong><br/> | |
18 | + <% end %> | |
19 | + <% unless @profile.products.empty? %> | |
20 | + <strong><%= _('Products/Services: ') + @profile.products.map{|i| link_to(i.name, :controller => 'manage_products', :profile => @profile.identifier, :action => 'show', :id => i.id)}.join(', ') %></strong><br/> | |
21 | + <% end %> | |
22 | + <% if @profile.respond_to?(:distance) and !@profile.distance.nil? %> | |
23 | + <strong><%= _('Distance: ') + "%.2f%" % @profile.distance %></strong><br/> | |
24 | + <% end %> | |
25 | + </td> | |
26 | + </tr> | |
27 | + </table> | |
28 | +</div> | ... | ... |
app/views/search/_google_maps.rhtml
1 | -<%= content_tag('script', '', :src => GoogleMaps.api_url(environment.default_hostname), :type => 'text/javascript') %> | |
2 | - | |
3 | - | |
1 | +<br style="clear: both;"/> | |
4 | 2 | <div style='text-align: center;'> |
5 | 3 | <div id="map"></div> |
6 | 4 | </div> |
7 | 5 | |
8 | -<script type='text/javascript'> | |
9 | -var points = {}; | |
10 | - | |
11 | -function putMarker(lat, lng, title, summary) { | |
12 | - var point_str = lat + ":" + lng; | |
13 | - | |
14 | - if (points[point_str]) { | |
15 | - lng += (Math.random() - 0.5) * 0.02; | |
16 | - lat += (Math.random() - 0.5) * 0.02; | |
17 | - } else { | |
18 | - points[point_str] = true; | |
19 | - } | |
20 | - | |
21 | - var point = new GLatLng(lat, lng); | |
22 | - var options = { 'title' : title, 'icon' : icon }; | |
23 | - var marker = new GMarker(point, options); | |
24 | - map.addOverlay(marker); | |
25 | - GEvent.addListener(marker, 'click', function() { | |
26 | - map.openInfoWindowHtml(point, summary); | |
27 | - }); | |
28 | - bounds.extend(point); | |
29 | -} | |
30 | - | |
31 | -window.unload = function() { | |
32 | - GUnload(); | |
33 | -}; | |
34 | - | |
35 | -if (GBrowserIsCompatible()) { | |
36 | - var map = new GMap2(document.getElementById("map")); | |
37 | - | |
38 | - new GKeyboardHandler(map); | |
39 | - map.addControl(new GLargeMapControl()); | |
40 | - map.addControl(new GMapTypeControl()); | |
41 | - | |
42 | - centerPoint = new GLatLng(-15.0, -50.1419); | |
43 | - map.setCenter(centerPoint, <%= GoogleMaps.initial_zoom.to_json %>); | |
44 | - var bounds = new GLatLngBounds(); | |
45 | - | |
46 | - var baseIcon = new GIcon(); | |
47 | - baseIcon.iconSize=new GSize(32,32); | |
48 | - baseIcon.shadowSize=new GSize(36,32); | |
49 | - baseIcon.iconAnchor=new GPoint(16,32); | |
50 | - baseIcon.infoWindowAnchor=new GPoint(16,0); | |
51 | - <% | |
52 | - icon = default_or_themed_icon("/images/icons-map/enterprise.png") | |
53 | - icon_shadow = default_or_themed_icon("/images/icons-map/enterprise_shadow.png") | |
54 | - %> | |
55 | - var icon = new GIcon(baseIcon, "<%= icon %>", null, "<%= icon_shadow %>"); | |
6 | +<%= content_tag('script', '', :src => GoogleMaps.api_url(environment.default_hostname), :type => 'text/javascript') %> | |
7 | +<%= javascript_include_tag('google_maps') %> | |
56 | 8 | |
57 | 9 | <% |
58 | - @results.each do |name,results| | |
59 | - results.each do |item| | |
60 | - if item.lat && item.lng | |
61 | - %> | |
62 | - putMarker(<%= item.lat.to_json %>, <%= item.lng.to_json %>, <%= item.name.to_json %>, <%= display_item_map_info(item).to_json %>); | |
63 | - <% | |
64 | - end | |
65 | - end | |
66 | - end | |
10 | + icon = default_or_themed_icon("/images/icons-map/enterprise.png") | |
11 | + icon_shadow = default_or_themed_icon("/images/icons-map/enterprise_shadow.png") | |
67 | 12 | %> |
68 | -} | |
69 | 13 | |
70 | - map.setZoom(map.getBoundsZoomLevel(bounds)); | |
71 | - map.setCenter(bounds.getCenter()); | |
14 | +<script type='text/javascript'> | |
15 | + mapLoad(<%= GoogleMaps.initial_zoom.to_json %>); | |
16 | + | |
17 | + mapBaseIcon = new GIcon(); | |
18 | + mapBaseIcon.iconSize=new GSize(32,32); | |
19 | + mapBaseIcon.shadowSize=new GSize(36,32); | |
20 | + mapBaseIcon.iconAnchor=new GPoint(16,32); | |
21 | + mapBaseIcon.infoWindowAnchor=new GPoint(16,0); | |
22 | + icon = new GIcon(mapBaseIcon, "<%= icon %>", null, "<%= icon_shadow %>"); | |
23 | + | |
24 | + <% @results.each do |name,results| %> | |
25 | + <% results.each do |item| %> | |
26 | + <% if item.lat && item.lng %> | |
27 | + mapPutMarker(<%= item.lat.to_json %>, <%= item.lng.to_json %>, <%= item.name.to_json %>, icon, | |
28 | + '<%= url_for(:controller => :map_balloon, :action => name.to_s.singularize, :id => item.id) %>'); | |
29 | + <% end %> | |
30 | + <% end %> | |
31 | + <% end %> | |
32 | + | |
33 | + mapCenter(); | |
72 | 34 | </script> | ... | ... |
app/views/search/_product.rhtml
config/routes.rb
... | ... | @@ -80,6 +80,9 @@ ActionController::Routing::Routes.draw do |map| |
80 | 80 | # contact |
81 | 81 | map.contact 'contact/:profile/:action/:id', :controller => 'contact', :action => 'index', :id => /.*/, :profile => /#{Noosfero.identifier_format}/ |
82 | 82 | |
83 | + # map balloon | |
84 | + map.contact 'map_balloon/:action/:id', :controller => 'map_balloon', :id => /.*/ | |
85 | + | |
83 | 86 | # chat |
84 | 87 | map.chat 'chat/:action/:id', :controller => 'chat' |
85 | 88 | map.chat 'chat/:action', :controller => 'chat' | ... | ... |
... | ... | @@ -0,0 +1,58 @@ |
1 | +var map; | |
2 | +var mapPoints = {}; | |
3 | +var mapBounds; | |
4 | +var mapDefaultIcon = new GIcon(G_DEFAULT_ICON); | |
5 | + | |
6 | +function mapPutMarker(lat, lng, title, _icon, url) { | |
7 | + var point_str = lat + ":" + lng; | |
8 | + | |
9 | + var icon = _icon == null ? mapDefaultIcon : _icon; | |
10 | + | |
11 | + if (mapPoints[point_str]) { | |
12 | + lng += (Math.random() - 0.5) * 0.02; | |
13 | + lat += (Math.random() - 0.5) * 0.02; | |
14 | + } else { | |
15 | + mapPoints[point_str] = true; | |
16 | + } | |
17 | + | |
18 | + var point = new GLatLng(lat, lng); | |
19 | + var options = { 'title' : title, 'icon' : icon }; | |
20 | + var marker = new GMarker(point, options); | |
21 | + map.addOverlay(marker); | |
22 | + | |
23 | + GEvent.addListener(marker, 'click', function() { | |
24 | + if (url) { | |
25 | + jQuery.ajax({url: url, | |
26 | + success: function(data) { | |
27 | + map.openInfoWindowHtml(point, jQuery(data).html()); | |
28 | + } | |
29 | + }); | |
30 | + } | |
31 | + }); | |
32 | + mapBounds.extend(point); | |
33 | + | |
34 | + return marker; | |
35 | +} | |
36 | + | |
37 | +window.unload = function() { | |
38 | + GUnload(); | |
39 | +}; | |
40 | + | |
41 | +function mapLoad(initial_zoom) { | |
42 | + if (GBrowserIsCompatible()) { | |
43 | + map = new GMap2(document.getElementById("map")); | |
44 | + | |
45 | + new GKeyboardHandler(map); | |
46 | + map.addControl(new GLargeMapControl()); | |
47 | + map.addControl(new GMapTypeControl()); | |
48 | + | |
49 | + centerPoint = new GLatLng(-15.0, -50.1419); | |
50 | + map.setCenter(centerPoint, initial_zoom); | |
51 | + mapBounds = new GLatLngBounds(); | |
52 | + } | |
53 | +} | |
54 | + | |
55 | +function mapCenter(latlng) { | |
56 | + map.setZoom(map.getBoundsZoomLevel(mapBounds)); | |
57 | + map.setCenter(latlng ? latlng : mapBounds.getCenter()); | |
58 | +} | ... | ... |