Completed
Push — master ( 3c1969...5b5792 )
by Schlaefer
03:16 queued 10s
created

LayoutHelper::_touchIcon()   B

Complexity

Conditions 5
Paths 6

Size

Total Lines 41

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 5
nc 6
nop 2
dl 0
loc 41
rs 8.9528
c 0
b 0
f 0
1
<?php
2
/**
3
 * Saito - The Threaded Web Forum
4
 *
5
 * @copyright Copyright (c) the Saito Project Developers 2015
6
 * @link https://github.com/Schlaefer/Saito
7
 * @license http://opensource.org/licenses/MIT
8
 */
9
10
namespace App\View\Helper;
11
12
use Cake\Core\Configure;
13
use Cake\View\Helper;
14
use Cake\View\StringTemplateTrait;
15
16
class LayoutHelper extends AppHelper
17
{
18
    use StringTemplateTrait;
19
20
    public $helpers = ['Html', 'Url'];
21
22
    protected $_defaultConfig = [
23
        'templates' => [
24
            'dropdownMenuDivider' => '<div class="dropdown-divider"></div>',
25
            'dropdownMenu' => '<div class="dropdown" style="display: inline;">{{button}}<div id="{{id}}" class="dropdown-menu">{{menu}}</div></div>',
26
        ]
27
    ];
28
29
    /**
30
     * Generates page heading html
31
     *
32
     * @param string $heading heading
33
     * @param string $tag tag
34
     * @return string
35
     */
36
    public function pageHeading($heading, $tag = 'h1')
37
    {
38
        return $this->Html->tag(
39
            $tag,
40
            $heading,
41
            ['class' => 'pageHeading', 'escape' => true]
42
        );
43
    }
44
45
    /**
46
     * Generates intoText tag
47
     *
48
     * @param string $content content
49
     * @return string
50
     */
51
    public function infoText($content)
52
    {
53
        return $this->Html->tag('span', $content, ['class' => 'infoText']);
54
    }
55
56
    /**
57
     * text with icon
58
     *
59
     * @param string $text text
60
     * @param string $icon icon
61
     * @return string
62
     */
63
    public function textWithIcon($text, $icon): string
64
    {
65
        $html = "<i class=\"saito-icon fa fa-{$icon}\"></i>";
66
        if (!empty($text)) {
67
                $html .= '&nbsp;<span class="saito-icon-text">' . $text . '</span>';
68
        }
69
70
        return $html;
71
    }
72
73
    /**
74
     * dropt down menu
75
     *
76
     * @param array $menuItems items
77
     * @param array $options options
78
     * @return string
79
     */
80
    public function dropdownMenuButton(array $menuItems, array $options = [])
81
    {
82
        $options += ['class' => 'btn btn-primary'];
83
        $options['class'] = $options['class'] . ' dropdown-toggle';
84
        $menu = [];
85
        foreach ($menuItems as $menuItem) {
86
            if ($menuItem === 'divider') {
87
                $menu[] = $this->formatTemplate('dropdownMenuDivider', []);
88
            } else {
89
                $menu[] = $menuItem;
90
            }
91
        }
92
        $id = AppHelper::tagId();
93
        if (!isset($options['title'])) {
94
            $options['title'] = '<i class="fa fa-wrench"></i>';
95
        }
96
97
        $title = $options['title'];
98
        unset($options['title']);
99
100
        $button = $this->Html->tag(
101
            'button',
102
            $title,
103
            $options + [
104
                'escape' => false,
105
                'data-toggle' => 'dropdown',
106
            ]
107
        );
108
109
        $menu = implode("\n", $menu);
110
111
        return $this->formatTemplate('dropdownMenu', [
112
            'button' => $button,
113
            'id' => "d$id",
114
            'menu' => $menu,
115
        ]);
116
    }
117
118
    /**
119
     * Creates panel heading HTML-element
120
     *
121
     * @param mixed $content content
122
     * @param array $options options
123
     *  - `class` string [panel-heading] CSS class for element
124
     *  - `escape` bool [true] escape output
125
     *  - `pageHeading` bool [false]
126
     *  - `tag` string [h2]
127
     * @return string
128
     */
129
    public function panelHeading($content, array $options = [])
130
    {
131
        $options += [
132
            'class' => 'flex-bar-header panel-heading',
133
            'escape' => true,
134
            'pageHeading' => false,
135
            'tag' => 'h2'
136
        ];
137
        if ($options['pageHeading']) {
138
            $options['class'] .= ' pageTitle';
139
            $options['tag'] = 'h1';
140
        }
141
        if (is_string($content)) {
142
            $content = ['middle' => $content];
143
        }
144
145
        if ($options['escape']) {
146
            foreach ($content as $k => $v) {
0 ignored issues
show
Bug introduced by
The expression $content of type object|integer|double|array|boolean|null is not guaranteed to be traversable. How about adding an additional type check?

There are different options of fixing this problem.

  1. If you want to be on the safe side, you can add an additional type-check:

    $collection = json_decode($data, true);
    if ( ! is_array($collection)) {
        throw new \RuntimeException('$collection must be an array.');
    }
    
    foreach ($collection as $item) { /** ... */ }
    
  2. If you are sure that the expression is traversable, you might want to add a doc comment cast to improve IDE auto-completion and static analysis:

    /** @var array $collection */
    $collection = json_decode($data, true);
    
    foreach ($collection as $item) { /** .. */ }
    
  3. Mark the issue as a false-positive: Just hover the remove button, in the top-right corner of this issue for more options.

Loading history...
147
                $content[$k] = h($v);
148
            }
149
        }
150
151
        $content['middle'] = "<{$options['tag']}>{$content['middle']}</{$options['tag']}>";
152
153
        $options['escape'] = false;
154
155
        return $this->heading($content, $options);
156
    }
157
158
    /**
159
     * heading
160
     *
161
     * @param mixed $content content
162
     * @param array $options options
163
     * @return string
164
     */
165
    public function heading($content, array $options = [])
166
    {
167
        $options += ['id' => '', 'class' => '', 'escape' => true];
168
        if (is_string($content)) {
169
            $contentArray = ['middle' => $content];
170
        } else {
171
            $contentArray = $content;
172
        }
173
        $contentArray += ['first' => '', 'middle' => '', 'last' => ''];
174
        $out = '';
175
        foreach (['first', 'middle', 'last'] as $key) {
176
            $out .= '<div class="' . $key . '">';
177
            $out .= $options['escape'] ? h($contentArray[$key]) : $contentArray[$key];
178
            $out .= '</div>';
179
        }
180
181
        return "<div id=\"{$options['id']}\" class=\"{$options['class']}\">$out</div>";
182
    }
183
184
    /**
185
     * creates a navigation link for the navigation bar
186
     *
187
     * @param string $content link content
188
     * @param string $url link url
189
     * @param array $options allows options as HtmlHelper::link
190
     *    - 'class' a CSS class to apply to the navbar item
191
     *    - 'position' [left]|center|right
192
     * @return string navigation link
193
     */
194
    public function navbarItem($content, $url, array $options = [])
195
    {
196
        $defaults = [
197
            'class' => 'btn btn-link navbar-item',
198
            'position' => 'left'
199
        ];
200
        $class = '';
201
        if (isset($options['class'])) {
202
            $class = $options['class'];
203
            unset($options['class']);
204
        }
205
        $options += $defaults;
206
207
        $options['class'] .= " {$options['position']} $class";
208
        unset($class, $options['position']);
209
210
        return $this->Html->link($content, $url, $options);
211
    }
212
213
    /**
214
     * navbar back
215
     *
216
     * @param string $url url
217
     * @param string $title title
218
     * @param array $options options
219
     * @return string
220
     */
221
    public function navbarBack($url = null, $title = null, $options = [])
222
    {
223
        if ($title === null) {
224
            if ($url === null) {
225
                $title = __('back_to_forum_linkname');
226
            } else {
227
                $title = __('Back');
228
            }
229
        }
230
231
        if ($url === null) {
232
            $url = '/';
233
        }
234
        $options += ['escape' => false];
235
        $content = $this->textWithIcon(h($title), 'arrow-left');
236
237
        return $this->navbarItem($content, $url, $options);
238
    }
239
}
240