Passed
Push — master ( d4a4c3...abf44f )
by Vladimir
06:09
created

SocialShare::getLinkList()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 13
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 7
c 0
b 0
f 0
nc 3
nop 0
dl 0
loc 13
rs 9.4285
1
<?php
2
/**
3
 * @link https://github.com/yiimaker/yii2-social-share
4
 * @copyright Copyright (c) 2017 Yii Maker
5
 * @license BSD 3-Clause License
6
 */
7
8
namespace ymaker\social\share\widgets;
9
10
use Yii;
11
use yii\base\Widget;
12
use yii\di\Instance;
13
use yii\helpers\ArrayHelper;
14
use yii\helpers\Html;
15
use yii\helpers\Inflector;
16
use yii\helpers\Url;
17
use ymaker\social\share\assets\SocialIconsAsset;
18
use ymaker\social\share\configurators\Configurator;
19
use ymaker\social\share\configurators\ConfiguratorInterface;
20
21
/**
22
 * Widget for rendering the share links.
23
 *
24
 * @author Vladimir Kuprienko <[email protected]>
25
 * @since 1.0
26
 */
27
class SocialShare extends Widget
28
{
29
    /**
30
     * @var string|array|ConfiguratorInterface
31
     */
32
    public $configurator;
33
    /**
34
     * Absolute URL to the page.
35
     *
36
     * @var string
37
     */
38
    public $url = '';
39
    /**
40
     * Title for share.
41
     *
42
     * @var string
43
     */
44
    public $title = '';
45
    /**
46
     * Description for share.
47
     *
48
     * @var string
49
     */
50
    public $description = '';
51
    /**
52
     * Absolute URL to the image for share.
53
     *
54
     * @var string
55
     */
56
    public $imageUrl = '';
57
    /**
58
     * Special properties for specific driver.
59
     *
60
     * @var array
61
     * @since 1.4.0
62
     */
63
    public $driverProperties = [];
64
    /**
65
     * HTML options for links container tag.
66
     * If you won't to use it - set `tag` option to `false`.
67
     *
68
     * @var array
69
     */
70
    public $containerOptions = ['tag' => 'ul', 'class' => 'social-share'];
71
    /**
72
     * HTML options for link container tag.
73
     * If you won't to use it - set `tag` option to `false`.
74
     *
75
     * @var array
76
     */
77
    public $linkContainerOptions = ['tag' => 'li'];
78
79
80
    /**
81
     * Initialize the widget: gets configurator instance,
82
     * sets [[url]] property if empty. Triggers [[EVENT_INIT]] event after initialization.
83
     *
84
     * @throws \yii\base\InvalidConfigException
85
     */
86
    public function init()
87
    {
88
        $this->configurator = Instance::ensure($this->configurator, ConfiguratorInterface::class);
89
90
        if (empty($this->url)) {
91
            $this->url = Url::to('', true);
92
        }
93
94
        parent::init();
95
    }
96
97
    /**
98
     * @inheritdoc
99
     */
100
    public function run()
101
    {
102
        if ($this->enableDefaultIcons()) {
103
            $this->getView()->registerAssetBundle(SocialIconsAsset::class);
104
        }
105
106
        if ($this->isSeoEnabled()) {
107
            echo '<!--noindex-->';
108
        }
109
110
        $containerTag = ArrayHelper::remove($this->containerOptions, 'tag', false);
111
        if ($containerTag) {
112
            echo Html::beginTag($containerTag, $this->containerOptions);
113
        }
114
115
        $wrapTag = ArrayHelper::remove($this->linkContainerOptions, 'tag', false);
116
        foreach ($this->getLinkList() as $link) {
117
            echo $wrapTag ? Html::tag($wrapTag, $link, $this->linkContainerOptions) : $link;
118
        }
119
120
        if ($containerTag) {
121
            echo Html::endTag($containerTag);
122
        }
123
124
        if ($this->isSeoEnabled()) {
125
            echo '<!--/noindex-->';
126
        }
127
    }
128
129
    /**
130
     * @return bool
131
     */
132
    final protected function enableDefaultIcons()
133
    {
134
        return $this->configurator instanceof Configurator &&
135
            $this->configurator->enableDefaultIcons;
136
    }
137
138
    /**
139
     * @return bool
140
     * @since 1.4.1
141
     */
142
    final protected function isSeoEnabled()
143
    {
144
        return $this->configurator instanceof Configurator &&
145
            $this->configurator->enableSeoOptions;
146
    }
147
148
    /**
149
     * Build label for driver.
150
     *
151
     * @param array $driverConfig
152
     * @param string $defaultLabel
153
     * @return string
154
     */
155
    protected function getLinkLabel($driverConfig, $defaultLabel)
156
    {
157
        return $this->enableDefaultIcons()
158
            ? Html::tag('i', '', ['class' => $this->configurator->getIconSelector($driverConfig['class'])])
159
            : (isset($driverConfig['label']) ? $driverConfig['label'] : $defaultLabel);
160
    }
161
162
    /**
163
     * Creates driver instance.
164
     *
165
     * @param array $config Configuration for driver.
166
     * @return \ymaker\social\share\base\DriverAbstract
167
     * @throws \yii\base\InvalidConfigException
168
     */
169
    private function createDriver($config)
170
    {
171
        $fullConfig = ArrayHelper::merge(
172
            [
173
                'class'       => $config['class'],
174
                'url'         => $this->url,
175
                'title'       => $this->title,
176
                'description' => $this->description,
177
                'imageUrl'    => $this->imageUrl
178
            ],
179
            isset($config['config']) ? $config['config'] : [],
180
            isset($this->driverProperties[$config['class']]) ? $this->driverProperties[$config['class']] : []
181
        );
182
183
        return Yii::createObject($fullConfig);
184
    }
185
186
    /**
187
     * Combine global and custom HTML options.
188
     *
189
     * @param array $driverConfig
190
     * @return array
191
     */
192
    private function combineOptions($driverConfig)
193
    {
194
        $options = isset($driverConfig['options']) ? $driverConfig['options'] : [];
195
196
        $globalOptions = $this->configurator->getOptions();
197
        if (empty($globalOptions)) {
198
            return $options;
199
        }
200
201
        if (isset($options['class'])) {
202
            Html::addCssClass($globalOptions, $options['class']);
203
            unset($options['class']);
204
        }
205
206
        return ArrayHelper::merge($globalOptions, $options);
207
    }
208
209
    /**
210
     * Returns array with share links in <a> HTML tag.
211
     *
212
     * @return array
213
     * @throws \yii\base\InvalidConfigException
214
     */
215
    private function getLinkList()
216
    {
217
        $linkList = [];
218
219
        foreach ($this->configurator->getSocialNetworks() as $key => $socialNetwork) {
220
            if (isset($socialNetwork['class'])) {
221
                $linkOptions = $this->combineOptions($socialNetwork);
222
                $linkOptions['href'] = $this->createDriver($socialNetwork)->getLink();
223
                $linkList[] = Html::tag('a', $this->getLinkLabel($socialNetwork, Inflector::camel2words($key)), $linkOptions);
224
            }
225
        }
226
227
        return $linkList;
228
    }
229
}
230