Completed
Push — master ( 2478d5...a209a4 )
by Thierry
01:46
created

Response::clearCommands()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
nc 1
nop 0
dl 0
loc 6
rs 10
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * Response.php - The Jaxon Response
5
 *
6
 * This class collects commands to be sent back to the browser in response to a jaxon request.
7
 * Commands are encoded and packaged in a format that is acceptable to the response handler
8
 * from the javascript library running on the client side.
9
 *
10
 * Common commands include:
11
 * - <Response->assign>: Assign a value to an element's attribute.
12
 * - <Response->append>: Append a value on to an element's attribute.
13
 * - <Response->script>: Execute a portion of javascript code.
14
 * - <Response->call>: Execute an existing javascript function.
15
 * - <Response->alert>: Display an alert dialog to the user.
16
 *
17
 * Elements are identified by the value of the HTML id attribute.
18
 * If you do not see your updates occuring on the browser side, ensure that you are using
19
 * the correct id in your response.
20
 *
21
 * @package jaxon-core
22
 * @author Jared White
23
 * @author J. Max Wilson
24
 * @author Joseph Woolley
25
 * @author Steffen Konerow
26
 * @author Thierry Feuzeu <[email protected]>
27
 * @copyright Copyright (c) 2005-2007 by Jared White & J. Max Wilson
28
 * @copyright Copyright (c) 2008-2010 by Joseph Woolley, Steffen Konerow, Jared White  & J. Max Wilson
29
 * @copyright 2016 Thierry Feuzeu <[email protected]>
30
 * @license https://opensource.org/licenses/BSD-3-Clause BSD 3-Clause License
31
 * @link https://github.com/jaxon-php/jaxon-core
32
 */
33
34
namespace Jaxon\Response;
35
36
use Jaxon\Jaxon;
37
38
class Response
39
{
40
    use \Jaxon\Utils\Traits\Config;
41
    use \Jaxon\Utils\Traits\Manager;
42
    use \Jaxon\Utils\Traits\Translator;
43
44
    /**
45
     * The response type
46
     *
47
     * @var string
48
     */
49
    public $sContentType = 'application/json';
50
51
    /**
52
     * The commands that will be sent to the browser in the response
53
     *
54
     * @var array
55
     */
56
    public $aCommands = [];
57
58
    /**
59
     * A string, array or integer value to be returned to the caller when using 'synchronous' mode requests.
60
     * See <jaxon->setMode> for details.
61
     *
62
     * @var mixed
63
     */
64
    private $returnValue;
65
66
    /**
67
     * Get the content type, which is always set to 'application/json'
68
     *
69
     * @return string
70
     */
71
    public function getContentType()
72
    {
73
        return $this->sContentType;
74
    }
75
76
    /**
77
     * Get the configured character encoding
78
     *
79
     * @return string
80
     */
81
    public function getCharacterEncoding()
82
    {
83
        return $this->getOption('core.encoding');
84
    }
85
86
    /**
87
     * Provides access to registered response plugins
88
     *
89
     * Pass the plugin name as the first argument and the plugin object will be returned.
90
     * You can then access the methods of the plugin directly.
91
     *
92
     * @param string        $sName                The name of the plugin
93
     *
94
     * @return null|\Jaxon\Plugin\Response
95
     */
96
    public function plugin($sName)
97
    {
98
        $xPlugin = $this->getPluginManager()->getResponsePlugin($sName);
99
        if(!$xPlugin)
100
        {
101
            return null;
102
        }
103
        $xPlugin->setResponse($this);
104
        return $xPlugin;
105
    }
106
107
    /**
108
     * Create a JQuery Element with a given selector, and link it to the current response.
109
     *
110
     * This is a shortcut to the JQuery plugin.
111
     *
112
     * @param string        $sSelector            The jQuery selector
113
     * @param string        $sContext             A context associated to the selector
114
     *
115
     * @return Jaxon\Response\Plugin\JQuery\Dom\Element
116
     */
117
    public function jq($sSelector = '', $sContext = '')
118
    {
119
        return $this->plugin('jquery')->element($sSelector, $sContext);
120
    }
121
122
    /**
123
     * Create a JQuery Element with a given selector, and link it to the current response.
124
     *
125
     * This is a shortcut to the JQuery plugin.
126
     *
127
     * @param string        $sSelector            The jQuery selector
128
     * @param string        $sContext             A context associated to the selector
129
     *
130
     * @return Jaxon\Response\Plugin\JQuery\Dom\Element
131
     */
132
    public function jQuery($sSelector = '', $sContext = '')
133
    {
134
        return $this->jq($sSelector, $sContext);
135
    }
136
137
    /**
138
     * Magic PHP function
139
     *
140
     * Used to permit plugins to be called as if they where native members of the Response instance.
141
     *
142
     * @param string        $sPluginName        The name of the plugin
143
     *
144
     * @return \Jaxon\Plugin\Response
145
     */
146
    public function __get($sPluginName)
147
    {
148
        return $this->plugin($sPluginName);
149
    }
150
151
    /**
152
     * Add a response command to the array of commands that will be sent to the browser
153
     *
154
     * @param array         $aAttributes        Associative array of attributes that will describe the command
155
     * @param mixed            $mData                The data to be associated with this command
156
     *
157
     * @return \Jaxon\Plugin\Response
158
     */
159
    public function addCommand($aAttributes, $mData)
160
    {
161
        /* merge commands if possible */
162
        if(in_array($aAttributes['cmd'], array('js', 'ap')))
163
        {
164
            if(($aLastCommand = array_pop($this->aCommands)))
165
            {
166
                if($aLastCommand['cmd'] == $aAttributes['cmd'])
167
                {
168
                    if($this->getOption('core.response.merge.js') &&
169
                            $aLastCommand['cmd'] == 'js')
170
                    {
171
                        $mData = $aLastCommand['data'].'; '.$mData;
172
                    }
173
                    elseif($this->getOption('core.response.merge.ap') &&
174
                            $aLastCommand['cmd'] == 'ap' &&
175
                            $aLastCommand['id'] == $aAttributes['id'] &&
176
                            $aLastCommand['prop'] == $aAttributes['prop'])
177
                    {
178
                        $mData = $aLastCommand['data'].' '.$mData;
179
                    }
180
                    else
181
                    {
182
                        $this->aCommands[] = $aLastCommand;
183
                    }
184
                }
185
                else
186
                {
187
                    $this->aCommands[] = $aLastCommand;
188
                }
189
            }
190
        }
191
        $aAttributes['data'] = $mData;
192
        $this->aCommands[] = $aAttributes;
193
194
        return $this;
195
    }
196
197
    /**
198
     * Clear all the commands already added to the response
199
     *
200
     * @return \Jaxon\Plugin\Response
201
     */
202
    public function clearCommands()
203
    {
204
        $this->aCommands[] = [];
205
206
        return $this;
207
    }
208
209
    /**
210
     * Add a response command that is generated by a plugin
211
     *
212
     * @param \Jaxon\Plugin\Plugin  $xPlugin            The plugin object
213
     * @param array                 $aAttributes        The attributes for this response command
214
     * @param mixed                 $mData              The data to be sent with this command
215
     *
216
     * @return \Jaxon\Plugin\Response
217
     */
218
    public function addPluginCommand($xPlugin, $aAttributes, $mData)
219
    {
220
        $aAttributes['plg'] = $xPlugin->getName();
221
        return $this->addCommand($aAttributes, $mData);
222
    }
223
224
    /**
225
     * Merge the response commands from the specified <Response> object with
226
     * the response commands in this <Response> object
227
     *
228
     * @param Response        $mCommands            The <Response> object
229
     * @param boolean        $bBefore            Add the new commands to the beginning of the list
230
     *
231
     * @return void
232
     */
233
    public function appendResponse($mCommands, $bBefore = false)
234
    {
235
        $aCommands = [];
236
        if($mCommands instanceof Response)
237
        {
238
            $this->returnValue = $mCommands->returnValue;
239
            $aCommands = $mCommands->aCommands;
240
        }
241
        elseif(is_array($mCommands))
242
        {
243
            $aCommands = $mCommands;
244
        }
245
        else
246
        {
247
            if(!empty($mCommands))
248
            {
249
                throw new \Jaxon\Exception\Error($this->trans('errors.response.data.invalid'));
250
            }
251
        }
252
253
        if(count($aCommands) > 0)
254
        {
255
            if($bBefore)
256
            {
257
                $this->aCommands = array_merge($aCommands, $this->aCommands);
258
            }
259
            else
260
            {
261
                $this->aCommands = array_merge($this->aCommands, $aCommands);
262
            }
263
        }
264
    }
265
266
    /**
267
     * Response command that prompts user with [ok] [cancel] style message box
268
     *
269
     * If the user clicks cancel, the specified number of response commands
270
     * following this one, will be skipped.
271
     *
272
     * @param integer        $iCmdNumber            The number of commands to skip upon cancel
273
     * @param string        $sMessage            The message to display to the user
274
     *
275
     * @return \Jaxon\Plugin\Response
276
     */
277
    public function confirmCommands($iCmdNumber, $sMessage)
278
    {
279
        return $this->addCommand(
280
            array(
281
                'cmd' => 'cc',
282
                'id' => $iCmdNumber
283
            ),
284
            trim((string)$sMessage, " \t\n")
285
        );
286
    }
287
288
    /**
289
     * Add a command to assign the specified value to the given element's attribute
290
     *
291
     * @param string        $sTarget              The id of the html element on the browser
292
     * @param string        $sAttribute           The attribute to be assigned
293
     * @param string        $sData                The value to be assigned to the attribute
294
     *
295
     * @return \Jaxon\Plugin\Response
296
     */
297 View Code Duplication
    public function assign($sTarget, $sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
298
    {
299
        return $this->addCommand(
300
            array(
301
                'cmd' => 'as',
302
                'id' => trim((string)$sTarget, " \t"),
303
                'prop' => trim((string)$sAttribute, " \t")
304
            ),
305
            trim((string)$sData, " \t\n")
306
        );
307
    }
308
309
    /**
310
     * Add a command to assign the specified HTML content to the given element
311
     *
312
     * This is a shortcut for assign() on the innerHTML attribute.
313
     *
314
     * @param string        $sTarget              The id of the html element on the browser
315
     * @param string        $sData                The value to be assigned to the attribute
316
     *
317
     * @return \Jaxon\Plugin\Response
318
     */
319
    public function html($sTarget, $sData)
320
    {
321
        return $this->assign($sTarget, 'innerHTML', $sData);
322
    }
323
324
    /**
325
     * Add a command to append the specified data to the given element's attribute
326
     *
327
     * @param string        $sTarget            The id of the element to be updated
328
     * @param string        $sAttribute            The name of the attribute to be appended to
329
     * @param string        $sData                The data to be appended to the attribute
330
     *
331
     * @return \Jaxon\Plugin\Response
332
     */
333 View Code Duplication
    public function append($sTarget, $sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
334
    {
335
        return $this->addCommand(
336
            array(
337
                'cmd' => 'ap',
338
                'id' => trim((string)$sTarget, " \t"),
339
                'prop' => trim((string)$sAttribute, " \t")
340
            ),
341
            trim((string)$sData, " \t\n")
342
        );
343
    }
344
345
    /**
346
     * Add a command to prepend the specified data to the given element's attribute
347
     *
348
     * @param string        $sTarget            The id of the element to be updated
349
     * @param string        $sAttribute            The name of the attribute to be prepended to
350
     * @param string        $sData                The value to be prepended to the attribute
351
     *
352
     * @return \Jaxon\Plugin\Response
353
     */
354 View Code Duplication
    public function prepend($sTarget, $sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
355
    {
356
        return $this->addCommand(
357
            array(
358
                'cmd' => 'pp',
359
                'id' => trim((string)$sTarget, " \t"),
360
                'prop' => trim((string)$sAttribute, " \t")
361
            ),
362
            trim((string)$sData, " \t\n")
363
        );
364
    }
365
366
    /**
367
     * Add a command to replace a specified value with another value within the given element's attribute
368
     *
369
     * @param string        $sTarget            The id of the element to update
370
     * @param string        $sAttribute            The attribute to be updated
371
     * @param string        $sSearch            The needle to search for
372
     * @param string        $sData                The data to use in place of the needle
373
     *
374
     * @return \Jaxon\Plugin\Response
375
     */
376
    public function replace($sTarget, $sAttribute, $sSearch, $sData)
377
    {
378
        return $this->addCommand(
379
            array(
380
                'cmd' => 'rp',
381
                'id' => trim((string)$sTarget, " \t"),
382
                'prop' => trim((string)$sAttribute, " \t")
383
            ),
384
            array(
385
                's' => trim((string)$sSearch, " \t\n"),
386
                'r' => trim((string)$sData, " \t\n")
387
            )
388
        );
389
    }
390
391
    /**
392
     * Add a command to clear the specified attribute of the given element
393
     *
394
     * @param string        $sTarget            The id of the element to be updated.
395
     * @param string        $sAttribute            The attribute to be cleared
396
     *
397
     * @return \Jaxon\Plugin\Response
398
     */
399
    public function clear($sTarget, $sAttribute)
400
    {
401
        return $this->assign(trim((string)$sTarget, " \t"), trim((string)$sAttribute, " \t"), '');
402
    }
403
404
    /**
405
     * Add a command to assign a value to a member of a javascript object (or element)
406
     * that is specified by the context member of the request
407
     *
408
     * The object is referenced using the 'this' keyword in the sAttribute parameter.
409
     *
410
     * @param string        $sAttribute            The attribute to be updated
411
     * @param string        $sData                The value to assign
412
     *
413
     * @return \Jaxon\Plugin\Response
414
     */
415 View Code Duplication
    public function contextAssign($sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
416
    {
417
        return $this->addCommand(
418
            array(
419
                'cmd' => 'c:as',
420
                'prop' => trim((string)$sAttribute, " \t")
421
            ),
422
            trim((string)$sData, " \t\n")
423
        );
424
    }
425
426
    /**
427
     * Add a command to append a value onto the specified member of the javascript
428
     * context object (or element) specified by the context member of the request
429
     *
430
     * The object is referenced using the 'this' keyword in the sAttribute parameter.
431
     *
432
     * @param string        $sAttribute            The attribute to be appended to
433
     * @param string        $sData                The value to append
434
     *
435
     * @return \Jaxon\Plugin\Response
436
     */
437 View Code Duplication
    public function contextAppend($sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
438
    {
439
        return $this->addCommand(
440
            array(
441
                'cmd' => 'c:ap',
442
                'prop' => trim((string)$sAttribute, " \t")
443
            ),
444
            trim((string)$sData, " \t\n")
445
        );
446
    }
447
448
    /**
449
     * Add a command to prepend the speicified data to the given member of the current
450
     * javascript object specified by context in the current request
451
     *
452
     * The object is access via the 'this' keyword in the sAttribute parameter.
453
     *
454
     * @param string        $sAttribute            The attribute to be updated
455
     * @param string        $sData                The value to be prepended
456
     *
457
     * @return \Jaxon\Plugin\Response
458
     */
459 View Code Duplication
    public function contextPrepend($sAttribute, $sData)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
460
    {
461
        return $this->addCommand(
462
            array(
463
                'cmd' => 'c:pp',
464
                'prop' => trim((string)$sAttribute, " \t")
465
            ),
466
            trim((string)$sData, " \t\n")
467
        );
468
    }
469
470
    /**
471
     * Add a command to to clear the value of the attribute specified in the sAttribute parameter
472
     *
473
     * The member is access via the 'this' keyword and can be used to update a javascript
474
     * object specified by context in the request parameters.
475
     *
476
     * @param string        $sAttribute            The attribute to be cleared
477
     *
478
     * @return \Jaxon\Plugin\Response
479
     */
480
    public function contextClear($sAttribute)
481
    {
482
        return $this->contextAssign(trim((string)$sAttribute, " \t"), '');
483
    }
484
485
    /**
486
     * Add a command to display an alert message to the user
487
     *
488
     * @param string        $sMessage            The message to be displayed
489
     *
490
     * @return \Jaxon\Plugin\Response
491
     */
492
    public function alert($sMessage)
493
    {
494
        return $this->addCommand(
495
            array(
496
                'cmd' => 'al'
497
            ),
498
            trim((string)$sMessage, " \t\n")
499
        );
500
    }
501
502
    /**
503
     * Add a command to display a debug message to the user
504
     *
505
     * @param string        $sMessage            The message to be displayed
506
     *
507
     * @return \Jaxon\Plugin\Response
508
     */
509
    public function debug($sMessage)
510
    {
511
        return $this->addCommand(
512
            array(
513
                'cmd' => 'dbg'
514
            ),
515
            trim((string)$sMessage, " \t\n")
516
        );
517
    }
518
519
    /**
520
     * Add a command to ask the browser to navigate to the specified URL
521
     *
522
     * @param string        $sURL                The relative or fully qualified URL
523
     * @param integer        $iDelay                Number of seconds to delay before the redirect occurs
524
     *
525
     * @return \Jaxon\Plugin\Response
526
     */
527
    public function redirect($sURL, $iDelay=0)
528
    {
529
        // we need to parse the query part so that the values are rawurlencode()'ed
530
        // can't just use parse_url() cos we could be dealing with a relative URL which
531
        // parse_url() can't deal with.
532
        $queryStart = strpos($sURL, '?', strrpos($sURL, '/'));
533
        if($queryStart !== false)
534
        {
535
            $queryStart++;
536
            $queryEnd = strpos($sURL, '#', $queryStart);
537
            if($queryEnd === false)
538
                $queryEnd = strlen($sURL);
539
            $queryPart = substr($sURL, $queryStart, $queryEnd-$queryStart);
540
            parse_str($queryPart, $queryParts);
541
            $newQueryPart = "";
542
            if($queryParts)
543
            {
544
                $first = true;
545
                foreach($queryParts as $key => $value)
546
                {
547
                    if($first)
548
                        $first = false;
549
                    else
550
                        $newQueryPart .= '&';
551
                    $newQueryPart .= rawurlencode($key).'='.rawurlencode($value);
552
                }
553
            } elseif($_SERVER['QUERY_STRING']) {
554
                    //couldn't break up the query, but there's one there
555
                    //possibly "http://url/page.html?query1234" type of query?
556
                    //just encode it and hope it works
557
                    $newQueryPart = rawurlencode($_SERVER['QUERY_STRING']);
558
                }
559
            $sURL = str_replace($queryPart, $newQueryPart, $sURL);
560
        }
561
        if($iDelay)
562
            $this->script('window.setTimeout("window.location = \'' . $sURL . '\';",' . ($iDelay*1000) . ');');
563
        else
564
            $this->script('window.location = "' . $sURL . '";');
565
        return $this;
566
    }
567
568
    /**
569
     * Add a command to execute a portion of javascript on the browser
570
     *
571
     * The script runs in it's own context, so variables declared locally, using the 'var' keyword,
572
     * will no longer be available after the call.
573
     * To construct a variable that will be accessable globally, even after the script has executed,
574
     * leave off the 'var' keyword.
575
     *
576
     * @param string        $sJS                The script to execute
577
     *
578
     * @return \Jaxon\Plugin\Response
579
     */
580
    public function script($sJS)
581
    {
582
        return $this->addCommand(
583
            array(
584
                'cmd' => 'js'
585
            ),
586
            trim((string)$sJS, " \t\n")
587
        );
588
    }
589
590
    /**
591
     * Add a command to call the specified javascript function with the given (optional) parameters
592
     *
593
     * @param string        $sFunc                The name of the function to call
594
     *
595
     * @return \Jaxon\Plugin\Response
596
     */
597
    public function call($sFunc)
598
    {
599
        $aArgs = func_get_args();
600
        array_shift($aArgs);
601
        return $this->addCommand(
602
            array(
603
                'cmd' => 'jc',
604
                'func' => $sFunc
605
            ),
606
            $aArgs
607
        );
608
    }
609
610
    /**
611
     * Add a command to remove an element from the document
612
     *
613
     * @param string        $sTarget            The id of the element to be removed
614
     *
615
     * @return \Jaxon\Plugin\Response
616
     */
617
    public function remove($sTarget)
618
    {
619
        return $this->addCommand(
620
            array(
621
                'cmd' => 'rm',
622
                'id' => trim((string)$sTarget, " \t")
623
            ),
624
            ''
625
        );
626
    }
627
628
    /**
629
     * Add a command to create a new element on the browser
630
     *
631
     * @param string        $sParent            The id of the parent element
632
     * @param string        $sTag                The tag name to be used for the new element
633
     * @param string        $sId                The id to assign to the new element
634
     *
635
     * @return \Jaxon\Plugin\Response
636
     */
637
    public function create($sParent, $sTag, $sId)
638
    {
639
        return $this->addCommand(
640
            array(
641
                'cmd' => 'ce',
642
                'id' => trim((string)$sParent, " \t"),
643
                'prop' => trim((string)$sId, " \t")
644
            ),
645
            trim((string)$sTag, " \t\n")
646
        );
647
    }
648
649
    /**
650
     * Add a command to insert a new element just prior to the specified element
651
     *
652
     * @param string        $sBefore            The id of the element used as a reference point for the insertion
653
     * @param string        $sTag               The tag name to be used for the new element
654
     * @param string        $sId                The id to assign to the new element
655
     *
656
     * @return \Jaxon\Plugin\Response
657
     */
658
    public function insert($sBefore, $sTag, $sId)
659
    {
660
        return $this->addCommand(
661
            array(
662
                'cmd' => 'ie',
663
                'id' => trim((string)$sBefore, " \t"),
664
                'prop' => trim((string)$sId, " \t")
665
            ),
666
            trim((string)$sTag, " \t\n")
667
        );
668
    }
669
670
    /**
671
     * Add a command to insert a new element after the specified
672
     *
673
     * @param string        $sAfter             The id of the element used as a reference point for the insertion
674
     * @param string        $sTag               The tag name to be used for the new element
675
     * @param string        $sId                The id to assign to the new element
676
     *
677
     * @return \Jaxon\Plugin\Response
678
     */
679
    public function insertAfter($sAfter, $sTag, $sId)
680
    {
681
        return $this->addCommand(
682
            array(
683
                'cmd' => 'ia',
684
                'id' => trim((string)$sAfter, " \t"),
685
                'prop' => trim((string)$sId, " \t")
686
            ),
687
            trim((string)$sTag, " \t\n")
688
        );
689
    }
690
691
    /**
692
     * Add a command to create an input element on the browser
693
     *
694
     * @param string        $sParent            The id of the parent element
695
     * @param string        $sType                The type of the new input element
696
     * @param string        $sName                The name of the new input element
697
     * @param string        $sId                The id of the new element
698
     *
699
     * @return \Jaxon\Plugin\Response
700
     */
701 View Code Duplication
    public function createInput($sParent, $sType, $sName, $sId)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
702
    {
703
        return $this->addCommand(
704
            array(
705
                'cmd' => 'ci',
706
                'id' => trim((string)$sParent, " \t"),
707
                'prop' => trim((string)$sId, " \t"),
708
                'type' => trim((string)$sType, " \t")
709
            ),
710
            trim((string)$sName, " \t\n")
711
        );
712
    }
713
714
    /**
715
     * Add a command to insert a new input element preceding the specified element
716
     *
717
     * @param string        $sBefore            The id of the element to be used as the reference point for the insertion
718
     * @param string        $sType                The type of the new input element
719
     * @param string        $sName                The name of the new input element
720
     * @param string        $sId                The id of the new element
721
     *
722
     * @return \Jaxon\Plugin\Response
723
     */
724 View Code Duplication
    public function insertInput($sBefore, $sType, $sName, $sId)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
725
    {
726
        return $this->addCommand(
727
            array(
728
                'cmd' => 'ii',
729
                'id' => trim((string)$sBefore, " \t"),
730
                'prop' => trim((string)$sId, " \t"),
731
                'type' => trim((string)$sType, " \t")
732
            ),
733
            trim((string)$sName, " \t\n")
734
        );
735
    }
736
737
    /**
738
     * Add a command to insert a new input element after the specified element
739
     *
740
     * @param string        $sAfter                The id of the element to be used as the reference point for the insertion
741
     * @param string        $sType                The type of the new input element
742
     * @param string        $sName                The name of the new input element
743
     * @param string        $sId                The id of the new element
744
     *
745
     * @return \Jaxon\Plugin\Response
746
     */
747 View Code Duplication
    public function insertInputAfter($sAfter, $sType, $sName, $sId)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
748
    {
749
        return $this->addCommand(
750
            array(
751
                'cmd' => 'iia',
752
                'id' => trim((string)$sAfter, " \t"),
753
                'prop' => trim((string)$sId, " \t"),
754
                'type' => trim((string)$sType, " \t")
755
            ),
756
            trim((string)$sName, " \t\n")
757
        );
758
    }
759
760
    /**
761
     * Add a command to set an event handler on the browser
762
     *
763
     * @param string        $sTarget            The id of the element that contains the event
764
     * @param string        $sEvent                The name of the event
765
     * @param string        $sScript            The javascript to execute when the event is fired
766
     *
767
     * @return \Jaxon\Plugin\Response
768
     */
769 View Code Duplication
    public function setEvent($sTarget, $sEvent, $sScript)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
770
    {
771
        return $this->addCommand(
772
            array(
773
                'cmd' => 'ev',
774
                'id' => trim((string)$sTarget, " \t"),
775
                'prop' => trim((string)$sEvent, " \t")
776
            ),
777
            trim((string)$sScript, " \t\n")
778
        );
779
    }
780
781
    /**
782
     * Add a command to set a click handler on the browser
783
     *
784
     * @param string        $sTarget            The id of the element that contains the event
785
     * @param string        $sScript            The javascript to execute when the event is fired
786
     *
787
     * @return \Jaxon\Plugin\Response
788
     */
789
    public function onClick($sTarget, $sScript)
790
    {
791
        return $this->setEvent($sTarget, 'onclick', $sScript);
792
    }
793
794
    /**
795
     * Add a command to install an event handler on the specified element
796
     *
797
     * You can add more than one event handler to an element's event using this method.
798
     *
799
     * @param string        $sTarget             The id of the element
800
     * @param string        $sEvent              The name of the event
801
     * @param string        $sHandler            The name of the javascript function to call when the event is fired
802
     *
803
     * @return \Jaxon\Plugin\Response
804
     */
805 View Code Duplication
    public function addHandler($sTarget, $sEvent, $sHandler)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
806
    {
807
        return $this->addCommand(
808
            array(
809
                'cmd' => 'ah',
810
                'id' => trim((string)$sTarget, " \t"),
811
                'prop' => trim((string)$sEvent, " \t")
812
            ),
813
            trim((string)$sHandler, " \t\n")
814
        );
815
    }
816
817
    /**
818
     * Add a command to remove an event handler from an element
819
     *
820
     * @param string        $sTarget             The id of the element
821
     * @param string        $sEvent              The name of the event
822
     * @param string        $sHandler            The name of the javascript function called when the event is fired
823
     *
824
     * @return \Jaxon\Plugin\Response
825
     */
826 View Code Duplication
    public function removeHandler($sTarget, $sEvent, $sHandler)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
827
    {
828
        return $this->addCommand(
829
            array(
830
                'cmd' => 'rh',
831
                'id' => trim((string)$sTarget, " \t"),
832
                'prop' => trim((string)$sEvent, " \t")
833
            ),
834
            trim((string)$sHandler, " \t\n")
835
        );
836
    }
837
838
    /**
839
     * Add a command to construct a javascript function on the browser
840
     *
841
     * @param string        $sFunction            The name of the function to construct
842
     * @param string        $sArgs                Comma separated list of parameter names
843
     * @param string        $sScript            The javascript code that will become the body of the function
844
     *
845
     * @return \Jaxon\Plugin\Response
846
     */
847 View Code Duplication
    public function setFunction($sFunction, $sArgs, $sScript)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
848
    {
849
        return $this->addCommand(
850
            array(
851
                'cmd' => 'sf',
852
                'func' => trim((string)$sFunction, " \t"),
853
                'prop' => trim((string)$sArgs, " \t")
854
            ),
855
            trim((string)$sScript, " \t\n")
856
        );
857
    }
858
859
    /**
860
     * Add a command to construct a wrapper function around an existing javascript function on the browser
861
     *
862
     * @param string        $sFunction            The name of the existing function to wrap
863
     * @param string        $sArgs                The comma separated list of parameters for the function
864
     * @param array            $aScripts            An array of javascript code snippets that will be used to build
865
     *                                             the body of the function
866
     *                                             The first piece of code specified in the array will occur before
867
     *                                             the call to the original function, the second will occur after
868
     *                                             the original function is called.
869
     * @param string        $sReturnValueVar    The name of the variable that will retain the return value
870
     *                                             from the call to the original function
871
     *
872
     * @return \Jaxon\Plugin\Response
873
     */
874 View Code Duplication
    public function wrapFunction($sFunction, $sArgs, $aScripts, $sReturnValueVar)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
875
    {
876
        return $this->addCommand(
877
            array(
878
                'cmd' => 'wpf',
879
                'func' => trim((string)$sFunction, " \t"),
880
                'prop' => trim((string)$sArgs, " \t"),
881
                'type' => trim((string)$sReturnValueVar, " \t")
882
            ),
883
            $aScripts
884
        );
885
    }
886
887
    /**
888
     * Add a command to load a javascript file on the browser
889
     *
890
     * @param string        $sFileName            The relative or fully qualified URI of the javascript file
891
     * @param string        $sType                Determines the script type. Defaults to 'text/javascript'
892
     *
893
     * @return \Jaxon\Plugin\Response
894
     */
895 View Code Duplication
    public function includeScript($sFileName, $sType = null, $sId = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
896
    {
897
        $command = array('cmd'  =>  'in');
898
899
        if(($sType))
900
            $command['type'] = trim((string)$sType, " \t");
901
902
        if(($sId))
903
            $command['elm_id'] = trim((string)$sId, " \t");
904
905
        return $this->addCommand($command, trim((string)$sFileName, " \t"));
906
    }
907
908
    /**
909
     * Add a command to include a javascript file on the browser if it has not already been loaded
910
     *
911
     * @param string        $sFileName            The relative or fully qualified URI of the javascript file
912
     * @param string        $sType                Determines the script type. Defaults to 'text/javascript'
913
     *
914
     * @return \Jaxon\Plugin\Response
915
     */
916 View Code Duplication
    public function includeScriptOnce($sFileName, $sType = null, $sId = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
917
    {
918
        $command = array('cmd' => 'ino');
919
920
        if(($sType))
921
            $command['type'] = trim((string)$sType, " \t");
922
923
        if(($sId))
924
            $command['elm_id'] = trim((string)$sId, " \t");
925
926
        return $this->addCommand($command, trim((string)$sFileName, " \t"));
927
    }
928
929
    /**
930
     * Add a command to remove a SCRIPT reference to a javascript file on the browser
931
     *
932
     * Optionally, you can call a javascript function just prior to the file being unloaded (for cleanup).
933
     *
934
     * @param string        $sFileName            The relative or fully qualified URI of the javascript file
935
     * @param string        $sUnload            Name of a javascript function to call prior to unlaoding the file
936
     *
937
     * @return \Jaxon\Plugin\Response
938
     */
939
    public function removeScript($sFileName, $sUnload = '')
940
    {
941
        return $this->addCommand(
942
            array(
943
                'cmd' => 'rjs',
944
                'unld' => trim((string)$sUnload, " \t")
945
            ),
946
            trim((string)$sFileName, " \t")
947
        );
948
    }
949
950
    /**
951
     * Add a command to include a LINK reference to the specified CSS file on the browser.
952
     *
953
     * This will cause the browser to load and apply the style sheet.
954
     *
955
     * @param string        $sFileName            The relative or fully qualified URI of the css file
956
     * @param string        $sMedia                The media type of the CSS file. Defaults to 'screen'
957
     *
958
     * @return \Jaxon\Plugin\Response
959
     */
960 View Code Duplication
    public function includeCSS($sFileName, $sMedia = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
961
    {
962
        $command = array('cmd' => 'css');
963
964
        if(($sMedia))
965
            $command['media'] = trim((string)$sMedia, " \t");
966
967
        return $this->addCommand($command, trim((string)$sFileName, " \t"));
968
    }
969
970
    /**
971
     * Add a command to remove a LINK reference to a CSS file on the browser
972
     *
973
     * This causes the browser to unload the style sheet, effectively removing the style changes it caused.
974
     *
975
     * @param string        $sFileName            The relative or fully qualified URI of the css file
976
     *
977
     * @return \Jaxon\Plugin\Response
978
     */
979 View Code Duplication
    public function removeCSS($sFileName, $sMedia = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
980
    {
981
        $command = array('cmd' => 'rcss');
982
983
        if(($sMedia))
984
            $command['media'] = trim((string)$sMedia, " \t");
985
986
        return $this->addCommand($command, trim((string)$sFileName, " \t"));
987
    }
988
989
    /**
990
     * Add a command to make Jaxon pause while the CSS files are loaded
991
     *
992
     * The browser is not typically a multi-threading application, with regards to javascript code.
993
     * Therefore, the CSS files included or removed with <Response->includeCSS> and
994
     * <Response->removeCSS> respectively, will not be loaded or removed until the browser regains
995
     * control from the script.
996
     * This command returns control back to the browser and pauses the execution of the response
997
     * until the CSS files, included previously, are loaded.
998
     *
999
     * @param integer        $iTimeout            The number of 1/10ths of a second to pause before timing out
1000
     *                                             and continuing with the execution of the response commands
1001
     *
1002
     * @return \Jaxon\Plugin\Response
1003
     */
1004
    public function waitForCSS($iTimeout = 600)
1005
    {
1006
        $sData = "";
1007
        return $this->addCommand(
1008
            array(
1009
                'cmd' => 'wcss',
1010
                'prop' => $iTimeout
1011
            ),
1012
            $sData
1013
        );
1014
    }
1015
1016
    /**
1017
     * Add a command to make Jaxon to delay execution of the response commands until a specified condition is met
1018
     *
1019
     * Note, this returns control to the browser, so that other script operations can execute.
1020
     * Jaxon will continue to monitor the specified condition and, when it evaulates to true,
1021
     * will continue processing response commands.
1022
     *
1023
     * @param string        $script                A piece of javascript code that evaulates to true or false
1024
     * @param integer        $tenths                The number of 1/10ths of a second to wait before timing out
1025
     *                                             and continuing with the execution of the response commands.
1026
     *
1027
     * @return \Jaxon\Plugin\Response
1028
     */
1029
    public function waitFor($script, $tenths)
1030
    {
1031
        return $this->addCommand(
1032
            array(
1033
                'cmd' => 'wf',
1034
                'prop' => $tenths
1035
            ),
1036
            trim((string)$script, " \t\n")
1037
        );
1038
    }
1039
1040
    /**
1041
     * Add a command to make Jaxon to pause execution of the response commands,
1042
     * returning control to the browser so it can perform other commands asynchronously.
1043
     *
1044
     * After the specified delay, Jaxon will continue execution of the response commands.
1045
     *
1046
     * @param integer        $tenths                The number of 1/10ths of a second to sleep
1047
     *
1048
     * @return \Jaxon\Plugin\Response
1049
     */
1050
    public function sleep($tenths)
1051
    {
1052
        return $this->addCommand(
1053
            array(
1054
                'cmd' => 's',
1055
                'prop' => $tenths
1056
            ),
1057
            ''
1058
        );
1059
    }
1060
1061
    /**
1062
     * Add a command to start a DOM response
1063
     *
1064
     * @return \Jaxon\Plugin\Response
1065
     */
1066
    public function domStartResponse()
1067
    {
1068
        $this->script('jxnElm = []');
1069
    }
1070
1071
    /**
1072
     * Add a command to create a DOM element
1073
     *
1074
     * @param string        $variable            The DOM element name (id or class)
1075
     * @param string        $tag                The HTML tag of the new DOM element
1076
     *
1077
     * @return \Jaxon\Plugin\Response
1078
     */
1079
    public function domCreateElement($variable, $tag)
1080
    {
1081
        return $this->addCommand(
1082
            array(
1083
                'cmd' => 'DCE',
1084
                'tgt' => $variable
1085
            ),
1086
            $tag
1087
        );
1088
    }
1089
1090
    /**
1091
     * Add a command to set an attribute on a DOM element
1092
     *
1093
     * @param string        $variable            The DOM element name (id or class)
1094
     * @param string        $key                The name of the attribute
1095
     * @param string        $value                The value of the attribute
1096
     *
1097
     * @return \Jaxon\Plugin\Response
1098
     */
1099
    public function domSetAttribute($variable, $key, $value)
1100
    {
1101
        return $this->addCommand(
1102
            array(
1103
                'cmd' => 'DSA',
1104
                'tgt' => $variable,
1105
                'key' => $key
1106
            ),
1107
            $value
1108
        );
1109
    }
1110
1111
    /**
1112
     * Add a command to remove children from a DOM element
1113
     *
1114
     * @param string        $parent                The DOM parent element
1115
     * @param string        $skip                The ??
1116
     * @param string        $remove                The ??
1117
     *
1118
     * @return \Jaxon\Plugin\Response
1119
     */
1120
    public function domRemoveChildren($parent, $skip = null, $remove = null)
1121
    {
1122
        $command = array('cmd' => 'DRC');
1123
1124
        if(($skip))
1125
            $command['skip'] = $skip;
1126
1127
        if(($remove))
1128
            $command['remove'] = $remove;
1129
1130
        return $this->addCommand($command, $parent);
1131
    }
1132
1133
    /**
1134
     * Add a command to append a child to a DOM element
1135
     *
1136
     * @param string        $parent                The DOM parent element
1137
     * @param string        $variable            The DOM element name (id or class)
1138
     *
1139
     * @return \Jaxon\Plugin\Response
1140
     */
1141
    public function domAppendChild($parent, $variable)
1142
    {
1143
        return $this->addCommand(
1144
            array(
1145
                'cmd' => 'DAC',
1146
                'par' => $parent
1147
            ),
1148
            $variable
1149
        );
1150
    }
1151
1152
    /**
1153
     * Add a command to insert a DOM element before another
1154
     *
1155
     * @param string        $target                The DOM target element
1156
     * @param string        $variable            The DOM element name (id or class)
1157
     *
1158
     * @return \Jaxon\Plugin\Response
1159
     */
1160
    public function domInsertBefore($target, $variable)
1161
    {
1162
        return $this->addCommand(
1163
            array(
1164
                'cmd' => 'DIB',
1165
                'tgt' => $target
1166
            ),
1167
            $variable
1168
        );
1169
    }
1170
1171
    /**
1172
     * Add a command to insert a DOM element after another
1173
     *
1174
     * @param string        $target                The DOM target element
1175
     * @param string        $variable            The DOM element name (id or class)
1176
     *
1177
     * @return \Jaxon\Plugin\Response
1178
     */
1179
    public function domInsertAfter($target, $variable)
1180
    {
1181
        return $this->addCommand(
1182
            array(
1183
                'cmd' => 'DIA',
1184
                'tgt' => $target
1185
            ),
1186
            $variable
1187
        );
1188
    }
1189
1190
    /**
1191
     * Add a command to append a text to a DOM element
1192
     *
1193
     * @param string        $parent                The DOM parent element
1194
     * @param string        $text                The HTML text to append
1195
     *
1196
     * @return \Jaxon\Plugin\Response
1197
     */
1198
    public function domAppendText($parent, $text)
1199
    {
1200
        return $this->addCommand(
1201
            array(
1202
                'cmd' => 'DAT',
1203
                'par' => $parent
1204
            ),
1205
            $text
1206
        );
1207
    }
1208
1209
    /**
1210
     * Add a command to end a DOM response
1211
     *
1212
     * @return \Jaxon\Plugin\Response
1213
     */
1214
    public function domEndResponse()
1215
    {
1216
        $this->script('jxnElm = []');
1217
    }
1218
1219
    /**
1220
     * Get the number of commands in the response
1221
     *
1222
     * @return integer
1223
     */
1224
    public function getCommandCount()
1225
    {
1226
        return count($this->aCommands);
1227
    }
1228
1229
    /**
1230
     * Stores a value that will be passed back as part of the response
1231
     *
1232
     * When making synchronous requests, the calling javascript can obtain this value
1233
     * immediately as the return value of the <jaxon.call> javascript function
1234
     *
1235
     * @param mixed        $value                Any value
1236
     *
1237
     * @return \Jaxon\Plugin\Response
1238
     */
1239
    public function setReturnValue($value)
1240
    {
1241
        $this->returnValue = $value;
1242
        return $this;
1243
    }
1244
1245
    /**
1246
     * Used internally to generate the response headers
1247
     *
1248
     * @return void
1249
     */
1250
    public function sendHeaders()
1251
    {
1252
        if($this->getRequesthandler()->getRequestMethod() == Jaxon::METHOD_GET)
1253
        {
1254
            header("Expires: Mon, 26 Jul 1997 05:00:00 GMT");
1255
            header("Last-Modified: " . gmdate("D, d M Y H:i:s") . " GMT");
1256
            header("Cache-Control: no-cache, must-revalidate");
1257
            header("Pragma: no-cache");
1258
        }
1259
1260
        $sCharacterSet = '';
1261
        $sCharacterEncoding = trim($this->getOption('core.encoding'));
1262
        if(($sCharacterEncoding) && strlen($sCharacterEncoding) > 0)
1263
        {
1264
            $sCharacterSet = '; charset="' . trim($sCharacterEncoding) . '"';
1265
        }
1266
1267
        header('content-type: ' . $this->sContentType . ' ' . $sCharacterSet);
1268
    }
1269
1270
    /**
1271
     * Return the output, generated from the commands added to the response, that will be sent to the browser
1272
     *
1273
     * @return string
1274
     */
1275
    public function getOutput()
1276
    {
1277
        $response = [];
1278
1279
        if(($this->returnValue))
1280
        {
1281
            $response['jxnrv'] = $this->returnValue;
1282
        }
1283
        $response['jxnobj'] = [];
1284
1285
        foreach($this->aCommands as $xCommand)
1286
        {
1287
            $response['jxnobj'][] = $xCommand;
1288
        }
1289
1290
        return json_encode($response);
1291
    }
1292
1293
    /**
1294
     * Print the output, generated from the commands added to the response, that will be sent to the browser
1295
     *
1296
     * @return void
1297
     */
1298
    public function printOutput()
1299
    {
1300
        print $this->getOutput();
1301
    }
1302
}
1303