Projet

Général

Profil

Paste
Télécharger (18 ko) Statistiques
| Branche: | Révision:

root / htmltest / sites / all / modules / addthis / classes / AddThis.php @ c12e7e6a

1
<?php
2
/**
3
 * @file
4
 * An AddThis-class.
5
 */
6

    
7
class AddThis {
8

    
9
  const BLOCK_NAME = 'addthis_block';
10
  const DEFAULT_CUSTOM_CONFIGURATION_CODE = 'var addthis_config = {}';
11
  const DEFAULT_FORMATTER = 'addthis_default_formatter';
12
  const DEFAULT_NUMBER_OF_PREFERRED_SERVICES = 4;
13
  const FIELD_TYPE = 'addthis';
14
  const MODULE_NAME = 'addthis';
15
  const PERMISSION_ADMINISTER_ADDTHIS = 'administer addthis';
16
  const PERMISSION_ADMINISTER_ADVANCED_ADDTHIS = 'administer advanced addthis';
17
  const STYLE_KEY = 'addthis_style';
18
  const WIDGET_TYPE = 'addthis_button_widget';
19

    
20
  // AddThis attribute and parameter names (as defined in AddThis APIs).
21
  const PROFILE_ID_QUERY_PARAMETER = 'pubid';
22
  const TITLE_ATTRIBUTE = 'addthis:title';
23
  const URL_ATTRIBUTE = 'addthis:url';
24

    
25
  // Persistent variable keys.
26
  const ADDRESSBOOK_ENABLED_KEY = 'addthis_addressbook_enabled';
27
  const BLOCK_WIDGET_TYPE_KEY = 'addthis_block_widget_type';
28
  const BLOCK_WIDGET_SETTINGS_KEY = 'addthis_block_widget_settings';
29
  const BOOKMARK_URL_KEY = 'addthis_bookmark_url';
30
  const CLICKBACK_TRACKING_ENABLED_KEY = 'addthis_clickback_tracking_enabled';
31
  const CLICK_TO_OPEN_COMPACT_MENU_ENABLED_KEY = 'addthis_click_to_open_compact_menu_enabled';
32
  const CO_BRAND_KEY = 'addthis_co_brand';
33
  const COMPLIANT_508_KEY = 'addthis_508_compliant';
34
  const CUSTOM_CONFIGURATION_CODE_ENABLED_KEY = 'addthis_custom_configuration_code_enabled';
35
  const CUSTOM_CONFIGURATION_CODE_KEY = 'addthis_custom_configuration_code';
36
  const ENABLED_SERVICES_KEY = 'addthis_enabled_services';
37
  const GOOGLE_ANALYTICS_TRACKING_ENABLED_KEY = 'addthis_google_analytics_tracking_enabled';
38
  const GOOGLE_ANALYTICS_SOCIAL_TRACKING_ENABLED_KEY = 'addthis_google_analytics_social_tracking_enabled';
39
  const FACEBOOK_LIKE_COUNT_SUPPORT_ENABLED = 'addthis_facebook_like_count_support_enabled';
40
  const OPEN_WINDOWS_ENABLED_KEY = 'addthis_open_windows_enabled';
41
  const PROFILE_ID_KEY = 'addthis_profile_id';
42
  const SERVICES_CSS_URL_KEY = 'addthis_services_css_url';
43
  const SERVICES_JSON_URL_KEY = 'addthis_services_json_url';
44
  const STANDARD_CSS_ENABLED_KEY = 'addthis_standard_css_enabled';
45
  const UI_DELAY_KEY = 'addthis_ui_delay';
46
  const UI_HEADER_BACKGROUND_COLOR_KEY = 'addthis_ui_header_background_color';
47
  const UI_HEADER_COLOR_KEY = 'addthis_ui_header_color';
48
  const WIDGET_JS_URL_KEY = 'addthis_widget_js_url';
49
  const WIDGET_JS_LOAD_TYPE = 'addthis_widget_load_type';
50

    
51
  // Twitter.
52
  const TWITTER_VIA_KEY = 'addthis_twitter_via';
53
  const TWITTER_VIA_DEFAULT = 'AddThis';
54
  const TWITTER_TEMPLATE_KEY = 'addthis_twitter_template';
55
  const TWITTER_TEMPLATE_DEFAULT = '{{title}} {{url}} via @AddThis';
56

    
57
  // External resources.
58
  const DEFAULT_BOOKMARK_URL = 'http://www.addthis.com/bookmark.php?v=300';
59
  const DEFAULT_SERVICES_CSS_URL = 'http://cache.addthiscdn.com/icons/v1/sprites/services.css';
60
  const DEFAULT_SERVICES_JSON_URL = 'http://cache.addthiscdn.com/services/v1/sharing.en.json';
61
  const DEFAULT_WIDGET_JS_URL = 'http://s7.addthis.com/js/300/addthis_widget.js';
62
  const DEFAULT_WIDGET_JS_LOAD_TYPE = 'async';
63

    
64
  // Internal resources.
65
  const ADMIN_CSS_FILE = 'addthis.admin.css';
66
  const ADMIN_INCLUDE_FILE = 'includes/addthis.admin.inc';
67

    
68
  // Widget types.
69
  const WIDGET_TYPE_DISABLED = 'addthis_disabled';
70

    
71
  // Styles.
72
  const CSS_32x32 = 'addthis_32x32_style';
73
  const CSS_16x16 = 'addthis_16x16_style';
74

    
75
  private static $instance;
76

    
77
  /* @var AddThisJson */
78
  private $json;
79

    
80
  /**
81
   * Get the singleton instance of the AddThis class.
82
   *
83
   * @return AddThis
84
   *   Instance of AddThis.
85
   */
86
  public static function getInstance() {
87
    module_load_include('php', 'addthis', 'classes/AddThisJson');
88
    module_load_include('php', 'addthis', 'classes/AddThisWidgetJs');
89

    
90
    if (!isset(self::$instance)) {
91
      $add_this = new AddThis();
92
      $add_this->setJson(new AddThisJson());
93
      self::$instance = $add_this;
94
    }
95

    
96
    return self::$instance;
97
  }
98

    
99
  /**
100
   * Set the json object.
101
   */
102
  public function setJson(AddThisJson $json) {
103
    $this->json = $json;
104
  }
105

    
106
  public function getDefaultFormatterTypes() {
107
    return array(
108
      self::WIDGET_TYPE_DISABLED => t('Disabled'),
109
    );
110
  }
111

    
112
  public function getDisplayTypes() {
113
    $displays = array();
114
    foreach ($display_impl = _addthis_field_info_formatter_field_type() as $key => $display) {
115
      $displays[$key] = t(check_plain($display['label']));
116
    }
117
    return $displays;
118
  }
119

    
120
  /*
121
   * Get markup for a given display type.
122
   *
123
   * When $options does not contain #entity, link to the current URL.
124
   * When $options does not contain #display, use default settings.
125
   */
126
  public function getDisplayMarkup($display, $options = array()) {
127
    if (empty($display)) {
128
      return array();
129
    }
130

    
131
    $formatters = _addthis_field_info_formatter_field_type();
132

    
133
    if (!array_key_exists($display, $formatters)) {
134
      return array();
135
    }
136

    
137
    // Load resources.
138
    self::$instance->includeWidgetJs();
139
    self::$instance->addConfigurationOptionsJs();
140

    
141
    // The display type exists. Now get it and get the markup.
142
    $display_information = $formatters[$display];
143

    
144
    // Theme function might only give a display name and
145
    // render on default implementation.
146
    if (!isset($options['#display']) ||
147
        (isset($options['#display']['type']) && $options['#display']['type'] != $display)) {
148

    
149
      $options['#display'] = isset($options['#display']) ? $options['#display'] : array();
150
      $options['#display'] = array_merge($options['#display'], $display_information);
151
      $options['#display']['type'] = $display;
152

    
153
    }
154

    
155
    // When #entity and #entity_type exist, use the entity's URL.
156
    if (isset($options['#entity']) && isset($options['#entity_type'])) {
157
      $uri = entity_uri($options['#entity_type'], $options['#entity']);
158
      $uri['options'] += array(
159
        'absolute' => TRUE,
160
      );
161

    
162
      // @todo Add a hook to alter the uri also based on fields from the
163
      // entity (such as custom share link). Pass $options and $uri. Return
164
      // a uri object to which we can reset it. Maybe use the alter structure.
165

    
166
      $options['#url'] = url($uri['path'], $uri['options']);
167
    }
168
    // @todo Hash the options array and cache the markup.
169
    // This will save all the extra calls to modules and alters.
170

    
171
    // Allow other modules to alter markup options.
172
    drupal_alter('addthis_markup_options', $options);
173

    
174
    $markup = array(
175
      '#display' => $options['#display'],
176
    );
177
    // Get all hook implementation to verify later if we can call it.
178
    $addthis_display_markup_implementations = module_implements('addthis_display_markup');
179

    
180
    // Look for a targeted implementation to call.
181
    // This should be the default implementation that is called.
182
    if (function_exists($display_information['module'] . '_addthis_display_markup__' . $display)) {
183
      $markup += call_user_func_array($display_information['module'] . '_addthis_display_markup__' . $display, array($options));
184
    }
185
    elseif (in_array($display_information['module'], $addthis_display_markup_implementations)) {
186
      $markup += module_invoke($display_information['module'], 'addthis_display_markup', $display, $options);
187
    }
188
    // Allow other modules to alter markup.
189
    drupal_alter('addthis_markup', $markup);
190
    return $markup;
191
  }
192

    
193
  public function getServices() {
194
    $rows = array();
195
    $services = $this->json->decode($this->getServicesJsonUrl());
196
    if (empty($services)) {
197
      drupal_set_message(t('AddThis services could not be loaded from @service_url', array('@service_url', $this->getServicesJsonUrl())), 'warning');
198
    }
199
    else {
200
      foreach ($services['data'] as $service) {
201
        $serviceCode = check_plain($service['code']);
202
        $serviceName = check_plain($service['name']);
203
        $rows[$serviceCode] = '<span class="addthis_service_icon icon_' . $serviceCode . '"></span> ' . $serviceName;
204
      }
205
    }
206
    return $rows;
207
  }
208

    
209
  /**
210
   * Add the AddThis Widget JavaScript to the page.
211
   */
212
  public function addWidgetJs() {
213
    $widgetjs = new AddThisWidgetJs(self::getWidgetUrl());
214
    $widgetjs->addAttribute('pubid', $this->getProfileId());
215

    
216
    if (self::getWidgetJsLoadType() != 'include') {
217
      $widgetjs->addAttribute(self::getWidgetJsLoadType(), '1');
218
    }
219

    
220
    $url = $widgetjs->getFullUrl();
221

    
222
    switch (self::getWidgetJsLoadType()) {
223

    
224
      // Load as DOM is ready.
225
      case 'domready':
226
        drupal_add_js(
227
          array(
228
            'addthis' => array(
229
              'widget_url' => $url,
230
              'load_type' => self::getWidgetJsLoadType(),
231
            ),
232
          ),
233
          'setting'
234
        );
235
        break;
236

    
237
      // Load as async.
238
      case 'async':
239
        drupal_add_js(
240
          array(
241
            'addthis' => array(
242
              'load_type' => self::getWidgetJsLoadType(),
243
            ),
244
          ),
245
          'setting'
246
        );
247

    
248
        drupal_add_js(
249
          $url,
250
          array(
251
            'type' => 'external',
252
            'scope' => 'footer',
253
          )
254
        );
255
        break;
256

    
257
      // Load as include in the page.
258
      default:
259
        drupal_add_js(
260
          $url,
261
          array(
262
            'type' => 'external',
263
            'scope' => 'footer',
264
          )
265
        );
266
        break;
267
    }
268

    
269
    // Add local internal behaviours.
270
    drupal_add_js(
271
      drupal_get_path('module', 'addthis') . '/addthis.js',
272
      array(
273
        'type' => 'file',
274
        'scope' => 'footer',
275
      )
276
    );
277
  }
278

    
279
  /**
280
   * Load function for widget information.
281
   *
282
   * Loading widget information only once.
283
   */
284
  public function includeWidgetJs() {
285
    static $loaded;
286

    
287
    if (!isset($loaded)) {
288
      $loaded = TRUE;
289
      $this->addWidgetJs();
290

    
291
      return TRUE;
292
    }
293
    return FALSE;
294
  }
295

    
296
  public function addConfigurationOptionsJs() {
297
    if ($this->isCustomConfigurationCodeEnabled()) {
298
      $configurationOptionsJavascript = $this->getCustomConfigurationCode();
299
    }
300
    else {
301
      $enabledServices = $this->getServiceNamesAsCommaSeparatedString() . 'more';
302

    
303
      global $language;
304
      $configuration = array(
305
        'pubid' => $this->getProfileId(),
306
        'services_compact' => $enabledServices,
307
        'data_track_clickback' => $this->isClickbackTrackingEnabled(),
308
        'ui_508_compliant' => $this->get508Compliant(),
309
        'ui_click' => $this->isClickToOpenCompactMenuEnabled(),
310
        'ui_cobrand' => $this->getCoBrand(),
311
        'ui_delay' => $this->getUiDelay(),
312
        'ui_header_background' => $this->getUiHeaderBackgroundColor(),
313
        'ui_header_color' => $this->getUiHeaderColor(),
314
        'ui_open_windows' => $this->isOpenWindowsEnabled(),
315
        'ui_use_css' => $this->isStandardCssEnabled(),
316
        'ui_use_addressbook' => $this->isAddressbookEnabled(),
317
        'ui_language' => $language->language,
318
      );
319
      if (module_exists('googleanalytics')) {
320
        if ($this->isGoogleAnalyticsTrackingEnabled()) {
321
          $configuration['data_ga_property'] = variable_get('googleanalytics_account', '');
322
          $configuration['data_ga_social'] = $this->isGoogleAnalyticsSocialTrackingEnabled();
323
        }
324
      }
325
      $configuration['templates']['twitter'] = $this->getTwitterTemplate();
326
      drupal_alter('addthis_configuration', $configuration);
327

    
328
      $templates = array('templates' => $configuration['templates']);
329
      unset($configuration['templates']);
330
      $configurationOptionsJavascript = 'var addthis_config = ' . drupal_json_encode($configuration) . "\n";
331
      $configurationOptionsJavascript .= 'var addthis_share = ' . drupal_json_encode($templates);
332
    }
333
    drupal_add_js(
334
      $configurationOptionsJavascript,
335
      array(
336
      'type' => 'inline',
337
      'scope' => 'footer',
338
      'every_page' => TRUE,
339
    )
340
    );
341
  }
342

    
343
  public function getAddThisAttributesMarkup($options) {
344
    if (isset($options)) {
345
      $attributes = array();
346

    
347
      if (isset($options['#entity'])) {
348
        $attributes += $this->getAttributeTitle($options['#entity']);
349
      }
350
      $attributes += $this->getAttributeUrl($options);
351

    
352
      return $attributes;
353
    }
354
    return array();
355
  }
356

    
357
  /**
358
   * Get the type used for the block.
359
   */
360
  public function getBlockDisplayType() {
361
    return variable_get(self::BLOCK_WIDGET_TYPE_KEY, self::WIDGET_TYPE_DISABLED);
362
  }
363

    
364
  /**
365
   * Get the settings used by the block display.
366
   */
367
  public function getBlockDisplaySettings() {
368
    $settings = variable_get(self::BLOCK_WIDGET_SETTINGS_KEY, NULL);
369

    
370
    if ($settings == NULL && $this->getBlockDisplayType() != self::WIDGET_TYPE_DISABLED) {
371
      $settings = field_info_formatter_settings($this->getBlockDisplayType());
372
    }
373

    
374
    return $settings;
375
  }
376

    
377
  public function getProfileId() {
378
    return check_plain(variable_get(AddThis::PROFILE_ID_KEY));
379
  }
380

    
381
  public function getServicesCssUrl() {
382
    return check_url(variable_get(AddThis::SERVICES_CSS_URL_KEY, self::DEFAULT_SERVICES_CSS_URL));
383
  }
384

    
385
  public function getServicesJsonUrl() {
386
    return check_url(variable_get(AddThis::SERVICES_JSON_URL_KEY, self::DEFAULT_SERVICES_JSON_URL));
387
  }
388

    
389
  public function getEnabledServices() {
390
    return variable_get(self::ENABLED_SERVICES_KEY, array());
391
  }
392

    
393
  /**
394
   * Return the type of loading.
395
   *
396
   * @return string
397
   *   Retuns domready or async.
398
   */
399
  public function getWidgetJsLoadType() {
400
    return variable_get(self::WIDGET_JS_LOAD_TYPE, self::DEFAULT_WIDGET_JS_LOAD_TYPE);
401
  }
402

    
403
  public function isClickToOpenCompactMenuEnabled() {
404
    return (boolean) variable_get(self::CLICK_TO_OPEN_COMPACT_MENU_ENABLED_KEY, FALSE);
405
  }
406

    
407
  public function isOpenWindowsEnabled() {
408
    return (boolean) variable_get(self::OPEN_WINDOWS_ENABLED_KEY, FALSE);
409
  }
410

    
411
  public function getUiDelay() {
412
    return (int) check_plain(variable_get(self::UI_DELAY_KEY));
413
  }
414

    
415
  public function getUiHeaderColor() {
416
    return check_plain(variable_get(self::UI_HEADER_COLOR_KEY));
417
  }
418

    
419
  public function getUiHeaderBackgroundColor() {
420
    return check_plain(variable_get(self::UI_HEADER_BACKGROUND_COLOR_KEY));
421
  }
422

    
423
  public function isStandardCssEnabled() {
424
    return (boolean) variable_get(self::STANDARD_CSS_ENABLED_KEY, TRUE);
425
  }
426

    
427
  public function getCustomConfigurationCode() {
428
    return variable_get(self::CUSTOM_CONFIGURATION_CODE_KEY, self::DEFAULT_CUSTOM_CONFIGURATION_CODE);
429
  }
430

    
431
  public function isCustomConfigurationCodeEnabled() {
432
    return (boolean) variable_get(self::CUSTOM_CONFIGURATION_CODE_ENABLED_KEY, FALSE);
433
  }
434

    
435
  public function getBaseWidgetJsUrl() {
436
    return check_url(variable_get(self::WIDGET_JS_URL_KEY, self::DEFAULT_WIDGET_JS_URL));
437
  }
438

    
439
  public function getBaseBookmarkUrl() {
440
    return check_url(variable_get(self::BOOKMARK_URL_KEY, self::DEFAULT_BOOKMARK_URL));
441
  }
442

    
443
  public function getCoBrand() {
444
    return variable_get(self::CO_BRAND_KEY, '');
445
  }
446

    
447
  public function get508Compliant() {
448
    return (boolean) variable_get(self::COMPLIANT_508_KEY, FALSE);
449
  }
450

    
451
  public function getTwitterVia() {
452
    return variable_get(self::TWITTER_VIA_KEY, self::TWITTER_VIA_DEFAULT);
453
  }
454

    
455
  public function getTwitterTemplate() {
456
    return variable_get(self::TWITTER_TEMPLATE_KEY, self::TWITTER_TEMPLATE_DEFAULT);
457
  }
458

    
459
  public function isClickbackTrackingEnabled() {
460
    return (boolean) variable_get(self::CLICKBACK_TRACKING_ENABLED_KEY, FALSE);
461
  }
462

    
463
  public function isAddressbookEnabled() {
464
    return (boolean) variable_get(self::ADDRESSBOOK_ENABLED_KEY, FALSE);
465
  }
466

    
467
  public function isGoogleAnalyticsTrackingEnabled() {
468
    return (boolean) variable_get(self::GOOGLE_ANALYTICS_TRACKING_ENABLED_KEY, FALSE);
469
  }
470

    
471
  public function isGoogleAnalyticsSocialTrackingEnabled() {
472
    return (boolean) variable_get(self::GOOGLE_ANALYTICS_SOCIAL_TRACKING_ENABLED_KEY, FALSE);
473
  }
474

    
475
  public function isFacebookLikeCountSupportEnabled() {
476
    return (boolean) variable_get(self::FACEBOOK_LIKE_COUNT_SUPPORT_ENABLED, TRUE);
477
  }
478

    
479
  public function addStylesheets() {
480
    drupal_add_css($this->getServicesCssUrl(), 'external');
481
    drupal_add_css($this->getAdminCssFilePath(), 'file');
482
  }
483

    
484
  public function getFullBookmarkUrl() {
485
    return $this->getBaseBookmarkUrl() . $this->getProfileIdQueryParameterPrefixedWithAmp();
486
  }
487

    
488
  private function getAttributeTitle($entity) {
489
    if (isset($entity->title)) {
490
      return array(
491
        self::TITLE_ATTRIBUTE => (check_plain($entity->title) . ' - ' . variable_get('site_name')),
492
      );
493
    }
494
    return array();
495
  }
496

    
497
  private function getAttributeUrl($options) {
498
    if (isset($options['#url'])) {
499
      return array(
500
        self::URL_ATTRIBUTE => $options['#url'],
501
      );
502
    }
503
    return array();
504
  }
505

    
506
  private function getServiceNamesAsCommaSeparatedString() {
507
    $enabledServiceNames = array_values($this->getEnabledServices());
508
    $enabledServicesAsCommaSeparatedString = '';
509
    foreach ($enabledServiceNames as $enabledServiceName) {
510
      if ($enabledServiceName != '0') {
511
        $enabledServicesAsCommaSeparatedString .= $enabledServiceName . ',';
512
      }
513
    }
514
    return $enabledServicesAsCommaSeparatedString;
515
  }
516

    
517
  private function getAdminCssFilePath() {
518
    return drupal_get_path('module', self::MODULE_NAME) . '/' . self::ADMIN_CSS_FILE;
519
  }
520

    
521
  private function getProfileIdQueryParameter($prefix) {
522
    $profileId = $this->getProfileId();
523
    return !empty($profileId) ? $prefix . self::PROFILE_ID_QUERY_PARAMETER . '=' . $profileId : '';
524
  }
525

    
526
  private function getProfileIdQueryParameterPrefixedWithAmp() {
527
    return $this->getProfileIdQueryParameter('&');
528
  }
529

    
530
  private function getProfileIdQueryParameterPrefixedWithHash() {
531
    return $this->getProfileIdQueryParameter('#');
532
  }
533

    
534
  /**
535
   * Get the url for the AddThis Widget.
536
   */
537
  private function getWidgetUrl() {
538
    $url = ($this->currentlyOnHttps() ?
539
      $this->getBaseWidgetJsUrl() : // Not https url.
540
      $this->transformToSecureUrl($this->getBaseWidgetJsUrl()) // Transformed to https url.
541
    );
542
    return check_url($url);
543
  }
544

    
545
  /**
546
   * Request if we are currently on a https connection.
547
   *
548
   * @return True if we are currently on a https connection.
549
   */
550
  public function currentlyOnHttps() {
551
    global $base_root;
552
    return (strpos($base_root, 'https://') !== FALSE) ? TRUE : FALSE;
553
  }
554

    
555
  /**
556
   * Transform a url to secure url with https prefix.
557
   */
558
  public function transformToSecureUrl($url) {
559
    if ($this->currentlyOnHttps()) {
560
      $url = (strpos($url, 'http://') === 0 ? 'https://' . substr($url, 7) : $url);
561
    }
562
    return $url;
563
  }
564
}