Class: DcAdRenderer

Inherits:
Object
  • Object
show all
Includes:
DcApplicationHelper
Defined in:
app/renderers/dc_ad_renderer.rb

Overview

Ads renderer. Typically ads renderer is defined in design like this.

<div id="ads-on-top">
   <%= dc_render(:dc_ad, position: 'top') %>
</div>

There can be more than one ad shown on the same position. Therefore Ads can be grouped by position they are displayed at. Position name can be any string. I suggest using top, right …

Ads may be prioritized. Higher priority means higher probability that ad will be selected for display.

Clicks on picture and flash can be intercepted and are saved into dc_ad_stat table. It is also possible to limit number of times ad will be displayed or clicked.

Instance Attribute Summary

Attributes included from DcApplicationHelper

#design, #form, #ids, #json_ld, #menu, #menu_item, #options, #page, #page_title, #part, #parts, #record, #record_footer, #site, #tables

Instance Method Summary collapse

Methods included from DcApplicationHelper

#_origin, #dc_add2_record_cookie, #dc_add_json_ld, #dc_add_meta_tag, #dc_big_table, #dc_choices4, #dc_choices4_all_collections, #dc_choices4_cmsmenu, #dc_choices4_folders_list, #dc_choices4_menu, #dc_choices4_site_policies, #dc_deprecate, #dc_document_path, #dc_dont?, #dc_edit_mode?, #dc_edit_title, #dc_error_messages_for, #dc_flash_messages, #dc_get_json_ld, #dc_get_seo_meta_tags, #dc_get_site, #dc_icon_for_link, #dc_iframe_edit, #dc_img_alt, #dc_img_alt_tag, #dc_internal_var, #dc_label_for, #dc_limit_string, #dc_link_for_create, #dc_link_for_edit, #dc_link_for_edit1, #dc_link_menu_tag, #dc_link_to, #dc_menu_class, #dc_new_title, #dc_page_bottom, #dc_page_class, #dc_page_edit_menu, #dc_page_top, #dc_render, #dc_render_design, #dc_render_design_part, #dc_render_from_site, #dc_render_partial, #dc_replace_in_design, #dc_submit_tag, #dc_table_title, #dc_user_can_view, #dc_user_has_role, #dc_warning_messages_for, #decamelize_type, #forms_merge

Constructor Details

#initialize(parent, opts = {}) ⇒ DcAdRenderer

Returns a new instance of DcAdRenderer.



45
46
47
48
49
50
# File 'app/renderers/dc_ad_renderer.rb', line 45

def initialize( parent, opts={} ) #:nodoc:
  @parent = parent
  @opts   = opts
  @css    = ''
  self
end

Instance Method Details

#defaultObject

Default method for rendering ads.



173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
# File 'app/renderers/dc_ad_renderer.rb', line 173

def default
  return '' if @parent.session[:is_robot] # don't bother if robot
  html = ''
  if (ad = find_ad_to_display)
# save to statistics, if not in cms
    if @opts[:edit_mode] < 1
      DcAdStat.create!(dc_ad_id: ad.id, ip: @parent.request.ip, type: 1 )
# save display counter  
      ad.displayed += 1
      ad.save
    end
    html << case ad.type
    when 1 then # picture
      picture_ad ad
    when 2 then # flash
      flash_ad ad
    when 3 then # script
      ad.script
    else
      'Error. Wrong ad type!'
    end
  end
  html
end

#find_ad_to_displayObject

Determines which add will be displayed next. Subroutine of default method.



120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
# File 'app/renderers/dc_ad_renderer.rb', line 120

def find_ad_to_display()
  ads = DcAd.where( dc_site_id: @parent.site._id, position: @opts[:position], active: true).to_a#, :valid_to.gt => Time.now, :valid_from.lt => Time.now).to_a
#p @opts, ads.size, '*-*-*-*'
  ads.delete_if { |ad| (ad.valid_to and ad.valid_to < Time.now) or 
                       (ad.valid_from and ad.valid_from > Time.now) or 
                       (ad.displays > 0 and ad.displayed >= ad.displays) or
                       (ad.clicks > 0 and ad.clicked >= ad.clicks) }
  return nil if ads.size == 0
# Determine ad to display, based on priority. This is of course not totaly accurate, 
# but it will have to do.
  sum = ads.inject(0) {|r, e| r += e.priority}
  rnd = Random.rand(sum)
  r = 0
  ads.each do |e|
    return e if rnd >= r and rnd < r + e.priority
    r += e.priority
  end
  ads.last # we really shouldn't be here
end

#find_ads_multiObject

Finds ads that will be rendered. Subroutine of multi method.



55
56
57
58
59
60
61
62
63
64
# File 'app/renderers/dc_ad_renderer.rb', line 55

def find_ads_multi() #:nodoc:
  ads = DcAd.where( position: @opts[:position], active: true).to_a#, :valid_to.gt => Time.now, :valid_from.lt => Time.now).to_a
#p @opts, ads.size, '*-*-*-*'
  ads.delete_if { |ad| (ad.valid_to and ad.valid_to < Time.now) or 
                       (ad.valid_from and ad.valid_from > Time.now) or 
                       (ad.displays > 0 and ad.displayed >= ad.displays) or
                       (ad.clicks > 0 and ad.clicked >= ad.clicks) }
                   
  ads
end

#flash_ad(ad) ⇒ Object

Code for flash ad.



143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
# File 'app/renderers/dc_ad_renderer.rb', line 143

def flash_ad(ad)
  click_tag = ad.link.to_s.size > 5 ? "flashvars=\"clickTag=#{ad.link}\"" : '' 
<<EOT
<div class="link_to_track" id="#{ad.id}">
  <object>
    <param name="wmode" value="transparent" />
    <embed width="#{ad.width}" height="#{ad.height}" src="#{ad.file}" #{click_tag}
           wmode=transparent allowfullscreen='true' allowscriptaccess='always' type="application/x-shockwave-flash"></embed>
  </object>
</div> 

<script type='text/javascript'>
$('##{ad.id}').mousedown(function (e){
    $.post('/dc_common/ad_click', { id: this.id });
    return true;
});
</script>     
EOT
end

#multiObject

This is an experiment of how to render multiple ads on same location simultaneously by fade in and out div on which ad resides.



70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
# File 'app/renderers/dc_ad_renderer.rb', line 70

def multi
  return '' if @parent.session[:is_robot] # don't bother if robot
  html = "<div id='ad-#{@opts[:position]}-div'>"
  n = 0
  find_ads_multi.each do |ad|
    div = "ad-#{@opts[:position]}-#{n+=1}"
    html << "<div id='#{div}' style='position: absolute; display: none;'>"
    # all except first are hidden
#    html << n == 1 ? '>' : 'style="display: none;">'
    html << case ad.type
    when 1 then # picture
      picture_link ad
    when 2 then # flash
      flash_link ad
    when 3 then # script
      ad.script
    else
      'Error. Wrong ad type!'
    end
    html << '</div>'
  end
# 
  html << '</div>'
  if n > 0
    js = <<EOJS
  dc_ad_next_slide = function(div, index, max, timeout) {
    index = index + 1;
    div_show = div + index.toString();
    index_h = index - 1;
    if (index_h == 0) index_h = max;
    div_hide = div + index_h.toString();
    $('#' + div_show).fadeIn(1500);
    $('#' + div_hide).fadeOut(1500);

    if (index == max) index = 0; 
    setTimeout( function () { dc_ad_next_slide(div, index, max, timeout); }, timeout);
}

  $(document).ready(function () {
    dc_ad_next_slide("ad-#{@opts[:position]}-", 0, #{n}, 5000)
  });       
EOJS
  html << @parent.javascript_tag(js)
  end
  html
end

#picture_ad(ad) ⇒ Object

Code for picture ad.



166
167
168
# File 'app/renderers/dc_ad_renderer.rb', line 166

def picture_ad(ad)
  @parent.link_to @parent.image_tag(ad.file), ad.link, id: ad.id, class: 'link_to_track', target: ad.link_target 
end

#render_cssObject

Render CSS. This method returns css part of code.



214
215
216
# File 'app/renderers/dc_ad_renderer.rb', line 214

def render_css
  @css
end

#render_htmlObject

Renderer dispatcher. Method returns HTML part of code.



201
202
203
204
205
206
207
208
209
# File 'app/renderers/dc_ad_renderer.rb', line 201

def render_html
  method = @opts[:method] || 'default'
  html = if method and self.respond_to?(method)
    send(method)
  else
    "DcAdRenderer: method #{method} not defined!"
  end
  html  
end