Completed
Push — master ( 56f811...7c79ce )
by Lars
17:26
created

Stringy::substr()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 11

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
nc 1
nop 2
dl 0
loc 11
ccs 0
cts 2
cp 0
crap 2
rs 9.9
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Stringy;
6
7
use voku\helper\AntiXSS;
8
use voku\helper\EmailCheck;
9
use voku\helper\URLify;
10
use voku\helper\UTF8;
11
12
/**
13
 * Class Stringy
14
 *
15
 * @package Stringy
16
 */
17
class Stringy implements \Countable, \IteratorAggregate, \ArrayAccess
18
{
19
  /**
20
   * An instance's string.
21
   *
22
   * @var string
23
   */
24
  protected $str;
25
26
  /**
27
   * The string's encoding, which should be one of the mbstring module's
28
   * supported encodings.
29
   *
30
   * @var string
31
   */
32
  protected $encoding;
33
34
  /**
35
   * Initializes a Stringy object and assigns both str and encoding properties
36
   * the supplied values. $str is cast to a string prior to assignment, and if
37
   * $encoding is not specified, it defaults to mb_internal_encoding(). Throws
38
   * an InvalidArgumentException if the first argument is an array or object
39
   * without a __toString method.
40
   *
41
   * @param mixed  $str      [optional] <p>Value to modify, after being cast to string. Default: ''</p>
42
   * @param string $encoding [optional] <p>The character encoding. Fallback: 'UTF-8'</p>
43
   *
44
   * @throws \InvalidArgumentException <p>if an array or object without a
45
   *         __toString method is passed as the first argument</p>
46
   */
47 319
  public function __construct($str = '', string $encoding = null)
48
  {
49 319
    if (\is_array($str)) {
50 1
      throw new \InvalidArgumentException(
51 1
          'Passed value cannot be an array'
52
      );
53
    }
54
55
    if (
56 318
        \is_object($str)
57
        &&
58 318
        !\method_exists($str, '__toString')
59
    ) {
60 1
      throw new \InvalidArgumentException(
61 1
          'Passed object must have a __toString method'
62
      );
63
    }
64
65 317
    $this->str = (string)$str;
66
67 317
    if ($encoding && $encoding !== 'UTF-8') {
0 ignored issues
show
Bug Best Practice introduced by
The expression $encoding of type null|string is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== null instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
68
      $this->encoding = UTF8::normalize_encoding($encoding);
69
    } else {
70 317
      $this->encoding = 'UTF-8';
71
    }
72 317
  }
73
74
  /**
75
   * Returns the value in $str.
76
   *
77
   * @return string <p>The current value of the $str property.</p>
78
   */
79 29
  public function __toString()
80
  {
81 29
    return (string)$this->str;
82
  }
83
84
  /**
85
   * Gets the substring after the first occurrence of a separator.
86
   * If no match is found returns new empty Stringy object.
87
   *
88
   * @param string $separator
89
   *
90
   * @return static
91
   */
92
  public function afterFirst(string $separator): self
93
  {
94
    return static::create(
95
        UTF8::str_substr_after_first_separator(
96
            $this->str,
97
            $separator,
98
            $this->encoding
99
        )
100
    );
101
  }
102
103
  /**
104
   * Gets the substring after the first occurrence of a separator.
105
   * If no match is found returns new empty Stringy object.
106
   *
107
   * @param string $separator
108
   *
109
   * @return static
110
   */
111
  public function afterFirstIgnoreCase(string $separator): self
112
  {
113
    return static::create(
114
        UTF8::str_isubstr_after_first_separator(
115
            $this->str,
116
            $separator,
117
            $this->encoding
118
        )
119
    );
120
  }
121
122
  /**
123
   * Gets the substring after the last occurrence of a separator.
124
   * If no match is found returns new empty Stringy object.
125
   *
126
   * @param string $separator
127
   *
128
   * @return static
129
   */
130
  public function afterLast(string $separator): self
131
  {
132
    return static::create(
133
        UTF8::str_substr_after_last_separator(
134
            $this->str,
135
            $separator,
136
            $this->encoding
137
        )
138
    );
139
  }
140
141
  /**
142
   * Gets the substring after the last occurrence of a separator.
143
   * If no match is found returns new empty Stringy object.
144
   *
145
   * @param string $separator
146
   *
147
   * @return static
148
   */
149
  public function afterLastIgnoreCase(string $separator): self
150
  {
151
    return static::create(
152
        UTF8::str_isubstr_after_last_separator(
153
            $this->str,
154
            $separator,
155
            $this->encoding
156
        )
157
    );
158
  }
159
160
  /**
161
   * Returns a new string with $string appended.
162
   *
163
   * @param string $string <p>The string to append.</p>
164
   *
165
   * @return static <p>Object with appended $string.</p>
166
   */
167 2
  public function append(string $string): self
168
  {
169 2
    return static::create($this->str . $string, $this->encoding);
170
  }
171
172
  /**
173
   * Append an password (limited to chars that are good readable).
174
   *
175
   * @param int $length <p>Length of the random string.</p>
176
   *
177
   * @return static <p>Object with appended password.</p>
178
   */
179
  public function appendPassword(int $length): self
180
  {
181
    $possibleChars = '2346789bcdfghjkmnpqrtvwxyzBCDFGHJKLMNPQRTVWXYZ!?_#';
182
183
    return $this->appendRandomString($length, $possibleChars);
184
  }
185
186
  /**
187
   * Append an random string.
188
   *
189
   * @param int    $length        <p>Length of the random string.</p>
190
   * @param string $possibleChars [optional] <p>Characters string for the random selection.</p>
191
   *
192
   * @return static <p>Object with appended random string.</p>
193
   */
194
  public function appendRandomString(int $length, string $possibleChars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'): self
195
  {
196
    $str = UTF8::get_random_string($length, $possibleChars);
197
198
    return $this->append($str);
199
  }
200
201
  /**
202
   * Append an unique identifier.
203
   *
204
   * @param string|int $entropyExtra [optional] <p>Extra entropy via a string or int value.</p>
205
   * @param bool       $md5          [optional] <p>Return the unique identifier as md5-hash? Default: true</p>
206
   *
207
   * @return static <p>Object with appended unique identifier as md5-hash.</p>
208
   */
209
  public function appendUniqueIdentifier($entropyExtra = '', bool $md5 = true): self
210
  {
211
    $uniqueString = UTF8::get_unique_string($entropyExtra, $md5);
212
213
    return $this->append($uniqueString);
214
  }
215
216
  /**
217
   * Returns the character at $index, with indexes starting at 0.
218
   *
219
   * @param int $index <p>Position of the character.</p>
220
   *
221
   * @return static <p>The character at $index.</p>
222
   */
223
  public function at(int $index): self
224
  {
225
    $chr = UTF8::char_at($this->str, $index);
226
227
    return static::create($chr, $this->encoding);
228
  }
229
230
  /**
231
   * Gets the substring before the first occurrence of a separator.
232
   * If no match is found returns new empty Stringy object.
233
   *
234
   * @param string $separator
235
   *
236
   * @return static
237
   */
238
  public function beforeFirst(string $separator): self
239
  {
240
    return static::create(
241
        UTF8::str_substr_before_first_separator(
242
            $this->str,
243
            $separator,
244
            $this->encoding
245
        )
246
    );
247
  }
248
249
  /**
250
   * Gets the substring before the first occurrence of a separator.
251
   * If no match is found returns new empty Stringy object.
252
   *
253
   * @param string $separator
254
   *
255
   * @return static
256
   */
257
  public function beforeFirstIgnoreCase(string $separator): self
258
  {
259
    return static::create(
260
        UTF8::str_isubstr_before_first_separator(
261
            $this->str,
262
            $separator,
263
            $this->encoding
264
        )
265
    );
266
  }
267
268
  /**
269
   * Gets the substring before the last occurrence of a separator.
270
   * If no match is found returns new empty Stringy object.
271
   *
272
   * @param string $separator
273
   *
274
   * @return static
275
   */
276
  public function beforeLast(string $separator): self
277
  {
278
    return static::create(
279
        UTF8::str_substr_before_last_separator(
280
            $this->str,
281
            $separator,
282
            $this->encoding
283
        )
284
    );
285
  }
286
287
  /**
288
   * Gets the substring before the last occurrence of a separator.
289
   * If no match is found returns new empty Stringy object.
290
   *
291
   * @param string $separator
292
   *
293
   * @return static
294
   */
295
  public function beforeLastIgnoreCase(string $separator): self
296
  {
297
    return static::create(
298
        UTF8::str_isubstr_before_last_separator(
299
            $this->str,
300
            $separator,
301
            $this->encoding
302
        )
303
    );
304
  }
305
306
  /**
307
   * Returns the substring between $start and $end, if found, or an empty
308
   * string. An optional offset may be supplied from which to begin the
309
   * search for the start string.
310
   *
311
   * @param string $start  <p>Delimiter marking the start of the substring.</p>
312
   * @param string $end    <p>Delimiter marking the end of the substring.</p>
313
   * @param int    $offset [optional] <p>Index from which to begin the search. Default: 0</p>
314
   *
315
   * @return static <p>Object whose $str is a substring between $start and $end.</p>
316
   */
317
  public function between(string $start, string $end, int $offset = 0): self
318
  {
319
    $str = UTF8::between(
320
        $this->str,
321
        $start,
322
        $end,
323
        $offset,
324
        $this->encoding
325
    );
326
327
    return static::create($str, $this->encoding);
328
  }
329
330
  /**
331
   * Returns a camelCase version of the string. Trims surrounding spaces,
332
   * capitalizes letters following digits, spaces, dashes and underscores,
333
   * and removes spaces, dashes, as well as underscores.
334
   *
335
   * @return static <p>Object with $str in camelCase.</p>
336
   */
337
  public function camelize(): self
338
  {
339
    return static::create(
340
        UTF8::str_camelize($this->str, $this->encoding),
341
        $this->encoding
342
    );
343
  }
344
345
  /**
346
   * Returns the string with the first letter of each word capitalized,
347
   * except for when the word is a name which shouldn't be capitalized.
348
   *
349
   * @return static <p>Object with $str capitalized.</p>
350
   */
351
  public function capitalizePersonalName(): self
352
  {
353
    return static::create(
354
        UTF8::str_capitalize_name($this->str),
355
        $this->encoding
356
    );
357
  }
358
359
  /**
360
   * Returns an array consisting of the characters in the string.
361
   *
362
   * @return array <p>An array of string chars.</p>
363
   */
364
  public function chars(): array
365
  {
366
    return UTF8::chars($this->str);
367
  }
368
369
  /**
370
   * Trims the string and replaces consecutive whitespace characters with a
371
   * single space. This includes tabs and newline characters, as well as
372
   * multibyte whitespace such as the thin space and ideographic space.
373
   *
374
   * @return static <p>Object with a trimmed $str and condensed whitespace.</p>
375
   */
376 1
  public function collapseWhitespace(): self
377
  {
378 1
    $str = UTF8::collapse_whitespace($this->str);
379
380
    return static::create($str, $this->encoding);
381
  }
382
383
  /**
384
   * Returns true if the string contains $needle, false otherwise. By default
385
   * the comparison is case-sensitive, but can be made insensitive by setting
386
   * $caseSensitive to false.
387
   *
388
   * @param string $needle        <p>Substring to look for.</p>
389
   * @param bool   $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
390
   *
391
   * @return bool <p>Whether or not $str contains $needle.</p>
392
   */
393
  public function contains(string $needle, bool $caseSensitive = true): bool
394
  {
395
    return UTF8::str_contains(
396
        $this->str,
397
        $needle,
398
        $caseSensitive,
399
        $this->encoding
400
    );
401
  }
402
403
  /**
404
   * Returns true if the string contains all $needles, false otherwise. By
405
   * default the comparison is case-sensitive, but can be made insensitive by
406
   * setting $caseSensitive to false.
407
   *
408
   * @param array $needles       <p>SubStrings to look for.</p>
409
   * @param bool  $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
410
   *
411
   * @return bool <p>Whether or not $str contains $needle.</p>
412
   */
413
  public function containsAll(array $needles, bool $caseSensitive = true): bool
414
  {
415
    return UTF8::str_contains_all(
416
        $this->str,
417
        $needles,
418
        $caseSensitive,
419
        $this->encoding
420
    );
421
  }
422
423
  /**
424
   * Returns true if the string contains any $needles, false otherwise. By
425
   * default the comparison is case-sensitive, but can be made insensitive by
426
   * setting $caseSensitive to false.
427
   *
428
   * @param array $needles       <p>SubStrings to look for.</p>
429
   * @param bool  $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
430
   *
431
   * @return bool <p>Whether or not $str contains $needle.</p>
432
   */
433
  public function containsAny(array $needles, bool $caseSensitive = true): bool
434
  {
435
    return UTF8::str_contains_any(
436
        $this->str,
437
        $needles,
438
        $caseSensitive,
439
        $this->encoding
440
    );
441
  }
442
443
  /**
444
   * Returns the length of the string, implementing the countable interface.
445
   *
446
   * @return int <p>The number of characters in the string, given the encoding.</p>
447
   */
448 1
  public function count(): int
449
  {
450 1
    return $this->length();
451
  }
452
453
  /**
454
   * Returns the number of occurrences of $substring in the given string.
455
   * By default, the comparison is case-sensitive, but can be made insensitive
456
   * by setting $caseSensitive to false.
457
   *
458
   * @param string $substring     <p>The substring to search for.</p>
459
   * @param bool   $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
460
   *
461
   * @return int|false <p>This functions returns an integer or false if there isn't a string.</p>
462
   */
463
  public function countSubstr(string $substring, bool $caseSensitive = true)
464
  {
465
    return UTF8::substr_count_simple(
466
        $this->str,
467
        $substring,
468
        $caseSensitive,
469
        $this->encoding
470
    );
471
  }
472
473
  /**
474
   * Creates a Stringy object and assigns both str and encoding properties
475
   * the supplied values. $str is cast to a string prior to assignment, and if
476
   * $encoding is not specified, it defaults to mb_internal_encoding(). It
477
   * then returns the initialized object. Throws an InvalidArgumentException
478
   * if the first argument is an array or object without a __toString method.
479
   *
480
   * @param mixed  $str      [optional] <p>Value to modify, after being cast to string. Default: ''</p>
481
   * @param string $encoding [optional] <p>The character encoding. Fallback: 'UTF-8'</p>
482
   *
483
   * @return static <p>A Stringy object.</p>
484
   *
485
   * @throws \InvalidArgumentException <p>if an array or object without a
486
   *         __toString method is passed as the first argument</p>
487
   */
488 309
  public static function create($str = '', string $encoding = null): self
489
  {
490 309
    if ($encoding && $encoding !== 'UTF-8') {
0 ignored issues
show
Bug Best Practice introduced by
The expression $encoding of type null|string is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== null instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
491
      $encoding = UTF8::normalize_encoding($encoding);
492
    } else {
493 309
      $encoding = 'UTF-8';
494
    }
495
496 309
    return new static($str, $encoding);
497
  }
498
499
  /**
500
   * Returns a lowercase and trimmed string separated by dashes. Dashes are
501
   * inserted before uppercase characters (with the exception of the first
502
   * character of the string), and in place of spaces as well as underscores.
503
   *
504
   * @return static <p>Object with a dasherized $str</p>
505
   */
506
  public function dasherize(): self
507
  {
508
    $str = UTF8::str_dasherize($this->str);
509
510
    return static::create($str, $this->encoding);
511
  }
512
513
  /**
514
   * Returns a lowercase and trimmed string separated by the given delimiter.
515
   * Delimiters are inserted before uppercase characters (with the exception
516
   * of the first character of the string), and in place of spaces, dashes,
517
   * and underscores. Alpha delimiters are not converted to lowercase.
518
   *
519
   * @param string $delimiter <p>Sequence used to separate parts of the string.</p>
520
   *
521
   * @return static <p>Object with a delimited $str.</p>
522
   */
523
  public function delimit(string $delimiter): self
524
  {
525
    $str = UTF8::str_delimit($this->str, $delimiter);
526
527
    return static::create($str, $this->encoding);
528
  }
529
530
  /**
531
   * Returns true if the string ends with $substring, false otherwise. By
532
   * default, the comparison is case-sensitive, but can be made insensitive
533
   * by setting $caseSensitive to false.
534
   *
535
   * @param string $substring     <p>The substring to look for.</p>
536
   * @param bool   $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
537
   *
538
   * @return bool <p>Whether or not $str ends with $substring.</p>
539
   */
540 11
  public function endsWith(string $substring, bool $caseSensitive = true): bool
541
  {
542 11
    if ($caseSensitive) {
543 7
      return UTF8::str_ends_with($this->str, $substring);
544
    }
545
546 4
    return UTF8::str_iends_with($this->str, $substring);
547
  }
548
549
  /**
550
   * Returns true if the string ends with any of $substrings, false otherwise.
551
   * By default, the comparison is case-sensitive, but can be made insensitive
552
   * by setting $caseSensitive to false.
553
   *
554
   * @param string[] $substrings    <p>Substrings to look for.</p>
555
   * @param bool     $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
556
   *
557
   * @return bool     <p>Whether or not $str ends with $substring.</p>
558
   */
559
  public function endsWithAny(array $substrings, bool $caseSensitive = true): bool
560
  {
561
    if ($caseSensitive) {
562
      return UTF8::str_ends_with_any($this->str, $substrings);
563
    }
564
565
    return UTF8::str_iends_with_any($this->str, $substrings);
566
  }
567
568
  /**
569
   * Ensures that the string begins with $substring. If it doesn't, it's
570
   * prepended.
571
   *
572
   * @param string $substring <p>The substring to add if not present.</p>
573
   *
574
   * @return static <p>Object with its $str prefixed by the $substring.</p>
575
   */
576
  public function ensureLeft(string $substring): self
577
  {
578
    $str = UTF8::str_ensure_left($this->str, $substring);
579
580
    return static::create($str, $this->encoding);
581
  }
582
583
  /**
584
   * Ensures that the string ends with $substring. If it doesn't, it's appended.
585
   *
586
   * @param string $substring <p>The substring to add if not present.</p>
587
   *
588
   * @return static <p>Object with its $str suffixed by the $substring.</p>
589
   */
590
  public function ensureRight(string $substring): self
591
  {
592
    $str = UTF8::str_ensure_right($this->str, $substring);
593
594
    return static::create($str, $this->encoding);
595
  }
596
597
  /**
598
   * Create a escape html version of the string via "UTF8::htmlspecialchars()".
599
   *
600
   * @return static
601
   */
602 6
  public function escape(): self
603
  {
604 6
    $str = UTF8::htmlspecialchars(
605 6
        $this->str,
606 6
        ENT_QUOTES | ENT_SUBSTITUTE,
607 6
        $this->encoding
608
    );
609
610 6
    return static::create($str, $this->encoding);
611
  }
612
613
  /**
614
   * Create an extract from a sentence, so if the search-string was found, it try to centered in the output.
615
   *
616
   * @param string   $search
617
   * @param int|null $length                 [optional] <p>Default: null === text->length / 2</p>
618
   * @param string   $replacerForSkippedText [optional] <p>Default: …</p>
619
   *
620
   * @return static
621
   */
622
  public function extractText(string $search = '', int $length = null, string $replacerForSkippedText = '…'): self
623
  {
624
    $extract = UTF8::extract_text(
625
        $this->str,
626
        $search,
627
        $length,
628
        $replacerForSkippedText,
629
        $this->encoding
630
    );
631
632
    return static::create($extract, $this->encoding);
633
  }
634
635
  /**
636
   * Returns the first $n characters of the string.
637
   *
638
   * @param int $n <p>Number of characters to retrieve from the start.</p>
639
   *
640
   * @return static <p>Object with its $str being the first $n chars.</p>
641
   */
642
  public function first(int $n): self
643
  {
644
    $str = UTF8::first_char($this->str, $n);
645
646
    return static::create($str, $this->encoding);
647
  }
648
649
  /**
650
   * Returns the encoding used by the Stringy object.
651
   *
652
   * @return string <p>The current value of the $encoding property.</p>
653
   */
654 3
  public function getEncoding(): string
655
  {
656 3
    return $this->encoding;
657
  }
658
659
  /**
660
   * Returns a new ArrayIterator, thus implementing the IteratorAggregate
661
   * interface. The ArrayIterator's constructor is passed an array of chars
662
   * in the multibyte string. This enables the use of foreach with instances
663
   * of Stringy\Stringy.
664
   *
665
   * @return \ArrayIterator <p>An iterator for the characters in the string.</p>
666
   */
667
  public function getIterator(): \ArrayIterator
668
  {
669
    return new \ArrayIterator($this->chars());
670
  }
671
672
  /**
673
   * Returns true if the string contains a lower case char, false otherwise.
674
   *
675
   * @return bool <p>Whether or not the string contains a lower case character.</p>
676
   */
677
  public function hasLowerCase(): bool
678
  {
679
    return UTF8::has_lowercase($this->str);
680
  }
681
682
  /**
683
   * Returns true if the string contains an upper case char, false otherwise.
684
   *
685
   * @return bool <p>Whether or not the string contains an upper case character.</p>
686
   */
687
  public function hasUpperCase(): bool
688
  {
689
    return UTF8::has_uppercase($this->str);
690
  }
691
692
  /**
693
   * Convert all HTML entities to their applicable characters.
694
   *
695
   * @param int $flags       [optional] <p>
696
   *                         A bitmask of one or more of the following flags, which specify how to handle quotes and
697
   *                         which document type to use. The default is ENT_COMPAT.
698
   *                         <table>
699
   *                         Available <i>flags</i> constants
700
   *                         <tr valign="top">
701
   *                         <td>Constant Name</td>
702
   *                         <td>Description</td>
703
   *                         </tr>
704
   *                         <tr valign="top">
705
   *                         <td><b>ENT_COMPAT</b></td>
706
   *                         <td>Will convert double-quotes and leave single-quotes alone.</td>
707
   *                         </tr>
708
   *                         <tr valign="top">
709
   *                         <td><b>ENT_QUOTES</b></td>
710
   *                         <td>Will convert both double and single quotes.</td>
711
   *                         </tr>
712
   *                         <tr valign="top">
713
   *                         <td><b>ENT_NOQUOTES</b></td>
714
   *                         <td>Will leave both double and single quotes unconverted.</td>
715
   *                         </tr>
716
   *                         <tr valign="top">
717
   *                         <td><b>ENT_HTML401</b></td>
718
   *                         <td>
719
   *                         Handle code as HTML 4.01.
720
   *                         </td>
721
   *                         </tr>
722
   *                         <tr valign="top">
723
   *                         <td><b>ENT_XML1</b></td>
724
   *                         <td>
725
   *                         Handle code as XML 1.
726
   *                         </td>
727
   *                         </tr>
728
   *                         <tr valign="top">
729
   *                         <td><b>ENT_XHTML</b></td>
730
   *                         <td>
731
   *                         Handle code as XHTML.
732
   *                         </td>
733
   *                         </tr>
734
   *                         <tr valign="top">
735
   *                         <td><b>ENT_HTML5</b></td>
736
   *                         <td>
737
   *                         Handle code as HTML 5.
738
   *                         </td>
739
   *                         </tr>
740
   *                         </table>
741
   *                         </p>
742
   *
743
   * @return static <p>Object with the resulting $str after being html decoded.</p>
744
   */
745 5 View Code Duplication
  public function htmlDecode(int $flags = ENT_COMPAT): self
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...
746
  {
747 5
    $str = UTF8::html_entity_decode(
748 5
        $this->str,
749 5
        $flags,
750 5
        $this->encoding
751
    );
752
753 5
    return static::create($str, $this->encoding);
754
  }
755
756
  /**
757
   * Convert all applicable characters to HTML entities.
758
   *
759
   * @param int $flags       [optional] <p>
760
   *                         A bitmask of one or more of the following flags, which specify how to handle quotes and
761
   *                         which document type to use. The default is ENT_COMPAT.
762
   *                         <table>
763
   *                         Available <i>flags</i> constants
764
   *                         <tr valign="top">
765
   *                         <td>Constant Name</td>
766
   *                         <td>Description</td>
767
   *                         </tr>
768
   *                         <tr valign="top">
769
   *                         <td><b>ENT_COMPAT</b></td>
770
   *                         <td>Will convert double-quotes and leave single-quotes alone.</td>
771
   *                         </tr>
772
   *                         <tr valign="top">
773
   *                         <td><b>ENT_QUOTES</b></td>
774
   *                         <td>Will convert both double and single quotes.</td>
775
   *                         </tr>
776
   *                         <tr valign="top">
777
   *                         <td><b>ENT_NOQUOTES</b></td>
778
   *                         <td>Will leave both double and single quotes unconverted.</td>
779
   *                         </tr>
780
   *                         <tr valign="top">
781
   *                         <td><b>ENT_HTML401</b></td>
782
   *                         <td>
783
   *                         Handle code as HTML 4.01.
784
   *                         </td>
785
   *                         </tr>
786
   *                         <tr valign="top">
787
   *                         <td><b>ENT_XML1</b></td>
788
   *                         <td>
789
   *                         Handle code as XML 1.
790
   *                         </td>
791
   *                         </tr>
792
   *                         <tr valign="top">
793
   *                         <td><b>ENT_XHTML</b></td>
794
   *                         <td>
795
   *                         Handle code as XHTML.
796
   *                         </td>
797
   *                         </tr>
798
   *                         <tr valign="top">
799
   *                         <td><b>ENT_HTML5</b></td>
800
   *                         <td>
801
   *                         Handle code as HTML 5.
802
   *                         </td>
803
   *                         </tr>
804
   *                         </table>
805
   *                         </p>
806
   *
807
   * @return static <p>Object with the resulting $str after being html encoded.</p>
808
   */
809 5 View Code Duplication
  public function htmlEncode(int $flags = ENT_COMPAT): self
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...
810
  {
811 5
    $str = UTF8::htmlentities(
812 5
        $this->str,
813 5
        $flags,
814 5
        $this->encoding
815
    );
816
817 5
    return static::create($str, $this->encoding);
818
  }
819
820
  /**
821
   * Capitalizes the first word of the string, replaces underscores with
822
   * spaces, and strips '_id'.
823
   *
824
   * @return static <p>Object with a humanized $str.</p>
825
   */
826
  public function humanize(): self
827
  {
828
    $str = UTF8::str_humanize($this->str);
829
830
    return static::create($str, $this->encoding);
831
  }
832
833
  /**
834
   * Returns the index of the first occurrence of $needle in the string,
835
   * and false if not found. Accepts an optional offset from which to begin
836
   * the search.
837
   *
838
   * @param string $needle <p>Substring to look for.</p>
839
   * @param int    $offset [optional] <p>Offset from which to search. Default: 0</p>
840
   *
841
   * @return int|false <p>The occurrence's <strong>index</strong> if found, otherwise <strong>false</strong>.</p>
842
   */
843 10
  public function indexOf(string $needle, int $offset = 0)
844
  {
845 10
    return UTF8::strpos(
846 10
        $this->str,
847 10
        $needle,
848 10
        $offset,
849 10
        $this->encoding
850
    );
851
  }
852
853
  /**
854
   * Returns the index of the first occurrence of $needle in the string,
855
   * and false if not found. Accepts an optional offset from which to begin
856
   * the search.
857
   *
858
   * @param string $needle <p>Substring to look for.</p>
859
   * @param int    $offset [optional] <p>Offset from which to search. Default: 0</p>
860
   *
861
   * @return int|false <p>The occurrence's <strong>index</strong> if found, otherwise <strong>false</strong>.</p>
862
   */
863
  public function indexOfIgnoreCase(string $needle, int $offset = 0)
864
  {
865
    return UTF8::stripos(
866
        $this->str,
867
        $needle,
868
        $offset,
869
        $this->encoding
870
    );
871
  }
872
873
  /**
874
   * Returns the index of the last occurrence of $needle in the string,
875
   * and false if not found. Accepts an optional offset from which to begin
876
   * the search. Offsets may be negative to count from the last character
877
   * in the string.
878
   *
879
   * @param string $needle <p>Substring to look for.</p>
880
   * @param int    $offset [optional] <p>Offset from which to search. Default: 0</p>
881
   *
882
   * @return int|false <p>The last occurrence's <strong>index</strong> if found, otherwise <strong>false</strong>.</p>
883
   */
884 10
  public function indexOfLast(string $needle, int $offset = 0)
885
  {
886 10
    return UTF8::strrpos(
887 10
        $this->str,
888 10
        $needle,
889 10
        $offset,
890 10
        $this->encoding
891
    );
892
  }
893
894
  /**
895
   * Returns the index of the last occurrence of $needle in the string,
896
   * and false if not found. Accepts an optional offset from which to begin
897
   * the search. Offsets may be negative to count from the last character
898
   * in the string.
899
   *
900
   * @param string $needle <p>Substring to look for.</p>
901
   * @param int    $offset [optional] <p>Offset from which to search. Default: 0</p>
902
   *
903
   * @return int|false <p>The last occurrence's <strong>index</strong> if found, otherwise <strong>false</strong>.</p>
904
   */
905
  public function indexOfLastIgnoreCase(string $needle, int $offset = 0)
906
  {
907
    return UTF8::strripos(
908
        $this->str,
909
        $needle,
910
        $offset,
911
        $this->encoding
912
    );
913
  }
914
915
  /**
916
   * Inserts $substring into the string at the $index provided.
917
   *
918
   * @param string $substring <p>String to be inserted.</p>
919
   * @param int    $index     <p>The index at which to insert the substring.</p>
920
   *
921
   * @return static <p>Object with the resulting $str after the insertion.</p>
922
   */
923
  public function insert(string $substring, int $index): self
924
  {
925
    $str = UTF8::str_insert(
926
        $this->str,
927
        $substring,
928
        $index,
929
        $this->encoding
930
    );
931
932
    return static::create($str, $this->encoding);
933
  }
934
935
  /**
936
   * Returns true if the string contains the $pattern, otherwise false.
937
   *
938
   * WARNING: Asterisks ("*") are translated into (".*") zero-or-more regular
939
   * expression wildcards.
940
   *
941
   * @credit Originally from Laravel, thanks Taylor.
942
   *
943
   * @param string $pattern <p>The string or pattern to match against.</p>
944
   *
945
   * @return bool <p>Whether or not we match the provided pattern.</p>
946
   */
947 1
  public function is(string $pattern): bool
948
  {
949 1
    if ($this->toString() === $pattern) {
950 1
      return true;
951
    }
952
953
    $quotedPattern = \preg_quote($pattern, '/');
954
    $replaceWildCards = \str_replace('\*', '.*', $quotedPattern);
955
956
    return $this->matchesPattern('^' . $replaceWildCards . '\z');
957
  }
958
959
  /**
960
   * Returns true if the string contains only alphabetic chars, false otherwise.
961
   *
962
   * @return bool <p>Whether or not $str contains only alphabetic chars.</p>
963
   */
964
  public function isAlpha(): bool
965
  {
966
    return UTF8::is_alpha($this->str);
967
  }
968
969
  /**
970
   * Returns true if the string contains only alphabetic and numeric chars, false otherwise.
971
   *
972
   * @return bool <p>Whether or not $str contains only alphanumeric chars.</p>
973
   */
974
  public function isAlphanumeric(): bool
975
  {
976
    return UTF8::is_alphanumeric($this->str);
977
  }
978
979
  /**
980
   * Returns true if the string is base64 encoded, false otherwise.
981
   *
982
   * @return bool <p>Whether or not $str is base64 encoded.</p>
983
   */
984 7
  public function isBase64(): bool
985
  {
986 7
    return UTF8::is_base64($this->str);
987
  }
988
989
  /**
990
   * Returns true if the string contains only whitespace chars, false otherwise.
991
   *
992
   * @return bool <p>Whether or not $str contains only whitespace characters.</p>
993
   */
994
  public function isBlank(): bool
995
  {
996
    return UTF8::is_blank($this->str);
997
  }
998
999
  /**
1000
   * Returns true if the string contains a valid E-Mail address, false otherwise.
1001
   *
1002
   * @param bool $useExampleDomainCheck   [optional] <p>Default: false</p>
1003
   * @param bool $useTypoInDomainCheck    [optional] <p>Default: false</p>
1004
   * @param bool $useTemporaryDomainCheck [optional] <p>Default: false</p>
1005
   * @param bool $useDnsCheck             [optional] <p>Default: false</p>
1006
   *
1007
   * @return bool <p>Whether or not $str contains a valid E-Mail address.</p>
1008
   */
1009 1
  public function isEmail(bool $useExampleDomainCheck = false, bool $useTypoInDomainCheck = false, bool $useTemporaryDomainCheck = false, bool $useDnsCheck = false): bool
1010
  {
1011 1
    return EmailCheck::isValid($this->str, $useExampleDomainCheck, $useTypoInDomainCheck, $useTemporaryDomainCheck, $useDnsCheck);
1012
  }
1013
1014
  /**
1015
   * Determine whether the string is considered to be empty.
1016
   *
1017
   * A variable is considered empty if it does not exist or if its value equals FALSE.
1018
   * empty() does not generate a warning if the variable does not exist.
1019
   *
1020
   * @return bool <p>Whether or not $str is empty().</p>
1021
   */
1022
  public function isEmpty(): bool
1023
  {
1024
    return UTF8::is_empty($this->str);
1025
  }
1026
1027
  /**
1028
   * Returns true if the string contains only hexadecimal chars, false otherwise.
1029
   *
1030
   * @return bool <p>Whether or not $str contains only hexadecimal chars.</p>
1031
   */
1032
  public function isHexadecimal(): bool
1033
  {
1034
    return UTF8::is_hexadecimal($this->str);
1035
  }
1036
1037
  /**
1038
   * Returns true if the string contains HTML-Tags, false otherwise.
1039
   *
1040
   * @return bool <p>Whether or not $str contains HTML-Tags.</p>
1041
   */
1042 1
  public function isHtml(): bool
1043
  {
1044 1
    return UTF8::is_html($this->str);
1045
  }
1046
1047
  /**
1048
   * Returns true if the string is JSON, false otherwise. Unlike json_decode
1049
   * in PHP 5.x, this method is consistent with PHP 7 and other JSON parsers,
1050
   * in that an empty string is not considered valid JSON.
1051
   *
1052
   * @return bool <p>Whether or not $str is JSON.</p>
1053
   */
1054 20
  public function isJson(): bool
1055
  {
1056 20
    return UTF8::is_json($this->str);
1057
  }
1058
1059
  /**
1060
   * Returns true if the string contains only lower case chars, false otherwise.
1061
   *
1062
   * @return bool <p>Whether or not $str contains only lower case characters.</p>
1063
   */
1064
  public function isLowerCase(): bool
1065
  {
1066
    return UTF8::is_lowercase($this->str);
1067
  }
1068
1069
  /**
1070
   * Returns true if the string is serialized, false otherwise.
1071
   *
1072
   * @return bool <p>Whether or not $str is serialized.</p>
1073
   */
1074
  public function isSerialized(): bool
1075
  {
1076
    return UTF8::is_serialized($this->str);
1077
  }
1078
1079
  /**
1080
   * Returns true if the string contains only lower case chars, false
1081
   * otherwise.
1082
   *
1083
   * @return bool <p>Whether or not $str contains only lower case characters.</p>
1084
   */
1085
  public function isUpperCase(): bool
1086
  {
1087
    return UTF8::is_uppercase($this->str);
1088
  }
1089
1090
  /**
1091
   * Returns the last $n characters of the string.
1092
   *
1093
   * @param int $n <p>Number of characters to retrieve from the end.</p>
1094
   *
1095
   * @return static <p>Object with its $str being the last $n chars.</p>
1096
   */
1097
  public function last(int $n): self
1098
  {
1099
    $str = UTF8::str_last_char(
1100
        $this->str,
1101
        $n,
1102
        $this->encoding
1103
    );
1104
1105
    return static::create($str, $this->encoding);
1106
  }
1107
1108
  /**
1109
   * Gets the substring after (or before via "$beforeNeedle") the last occurrence of the "$needle".
1110
   * If no match is found returns new empty Stringy object.
1111
   *
1112
   * @param string $needle       <p>The string to look for.</p>
1113
   * @param bool   $beforeNeedle [optional] <p>Default: false</p>
1114
   *
1115
   * @return static
1116
   */
1117
  public function lastSubstringOf(string $needle, bool $beforeNeedle = false): self
1118
  {
1119
    $str = UTF8::str_substr_last($this->str, $needle, $beforeNeedle, $this->encoding);
1120
1121
    return static::create($str, $this->encoding);
1122
  }
1123
1124
  /**
1125
   * Gets the substring after (or before via "$beforeNeedle") the last occurrence of the "$needle".
1126
   * If no match is found returns new empty Stringy object.
1127
   *
1128
   * @param string $needle       <p>The string to look for.</p>
1129
   * @param bool   $beforeNeedle [optional] <p>Default: false</p>
1130
   *
1131
   * @return static
1132
   */
1133
  public function lastSubstringOfIgnoreCase(string $needle, bool $beforeNeedle = false): self
1134
  {
1135
    $str = UTF8::str_isubstr_last($this->str, $needle, $beforeNeedle, $this->encoding);
1136
1137
    return static::create($str, $this->encoding);
1138
  }
1139
1140
  /**
1141
   * Returns the length of the string.
1142
   *
1143
   * @return int <p>The number of characters in $str given the encoding.</p>
1144
   */
1145 5
  public function length(): int
1146
  {
1147 5
    return UTF8::strlen($this->str, $this->encoding);
1148
  }
1149
1150
  /**
1151
   * Line-Wrap the string after $limit, but also after the next word.
1152
   *
1153
   * @param int $limit
1154
   *
1155
   * @return static
1156
   */
1157
  public function lineWrapAfterWord(int $limit): self
1158
  {
1159
    $str = UTF8::wordwrap_per_line($this->str, $limit);
1160
1161
    return static::create($str, $this->encoding);
1162
  }
1163
1164
  /**
1165
   * Splits on newlines and carriage returns, returning an array of Stringy
1166
   * objects corresponding to the lines in the string.
1167
   *
1168
   * @return static[] <p>An array of Stringy objects.</p>
1169
   */
1170
  public function lines(): array
1171
  {
1172
    $array = UTF8::str_to_lines($this->str);
1173
1174
    foreach ($array as $i => &$value) {
1175
      $value = static::create($value, $this->encoding);
1176
    }
1177
1178
    return $array;
1179
  }
1180
1181
  /**
1182
   * Returns the longest common prefix between the string and $otherStr.
1183
   *
1184
   * @param string $otherStr <p>Second string for comparison.</p>
1185
   *
1186
   * @return static <p>Object with its $str being the longest common prefix.</p>
1187
   */
1188
  public function longestCommonPrefix(string $otherStr): self
1189
  {
1190
    $str = UTF8::str_longest_common_prefix(
1191
        $this->str,
1192
        $otherStr,
1193
        $this->encoding
1194
    );
1195
1196
    return static::create($str, $this->encoding);
1197
  }
1198
1199
  /**
1200
   * Returns the longest common substring between the string and $otherStr.
1201
   * In the case of ties, it returns that which occurs first.
1202
   *
1203
   * @param string $otherStr <p>Second string for comparison.</p>
1204
   *
1205
   * @return static <p>Object with its $str being the longest common substring.</p>
1206
   */
1207
  public function longestCommonSubstring(string $otherStr): self
1208
  {
1209
    $longestCommonSubstring = UTF8::str_longest_common_substring(
1210
        $this->str,
1211
        $otherStr,
1212
        $this->encoding
1213
    );
1214
1215
    return static::create($longestCommonSubstring, $this->encoding);
1216
  }
1217
1218
  /**
1219
   * Returns the longest common suffix between the string and $otherStr.
1220
   *
1221
   * @param string $otherStr <p>Second string for comparison.</p>
1222
   *
1223
   * @return static <p>Object with its $str being the longest common suffix.</p>
1224
   */
1225
  public function longestCommonSuffix(string $otherStr): self
1226
  {
1227
    $longestCommonSuffix = UTF8::str_longest_common_suffix(
1228
        $this->str,
1229
        $otherStr,
1230
        $this->encoding
1231
    );
1232
1233
    return static::create($longestCommonSuffix, $this->encoding);
1234
  }
1235
1236
  /**
1237
   * Converts the first character of the string to lower case.
1238
   *
1239
   * @return static <p>Object with the first character of $str being lower case.</p>
1240
   */
1241 5
  public function lowerCaseFirst(): self
1242
  {
1243 5
    $str = UTF8::lcfirst($this->str, $this->encoding);
1244
1245 5
    return static::create($str, $this->encoding);
1246
  }
1247
1248
  /**
1249
   * Returns true if $str matches the supplied pattern, false otherwise.
1250
   *
1251
   * @param string $pattern <p>Regex pattern to match against.</p>
1252
   *
1253
   * @return bool <p>Whether or not $str matches the pattern.</p>
1254
   */
1255
  protected function matchesPattern(string $pattern): bool
1256
  {
1257
    return UTF8::str_matches_pattern($this->str, $pattern);
1258
  }
1259
1260
  /**
1261
   * Returns whether or not a character exists at an index. Offsets may be
1262
   * negative to count from the last character in the string. Implements
1263
   * part of the ArrayAccess interface.
1264
   *
1265
   * @param int $offset <p>The index to check.</p>
1266
   *
1267
   * @return boolean <p>Whether or not the index exists.</p>
1268
   */
1269
  public function offsetExists($offset): bool
1270
  {
1271
    return UTF8::str_offset_exists(
1272
        $this->str,
1273
        $offset,
1274
        $this->encoding
1275
    );
1276
  }
1277
1278
  /**
1279
   * Returns the character at the given index. Offsets may be negative to
1280
   * count from the last character in the string. Implements part of the
1281
   * ArrayAccess interface, and throws an OutOfBoundsException if the index
1282
   * does not exist.
1283
   *
1284
   * @param int $offset <p>The <strong>index</strong> from which to retrieve the char.</p>
1285
   *
1286
   * @return string <p>The character at the specified index.</p>
1287
   *
1288
   * @throws \OutOfBoundsException <p>If the positive or negative offset does not exist.</p>
1289
   */
1290 1
  public function offsetGet($offset): string
1291
  {
1292 1
    return UTF8::str_offset_get($this->str, $offset, $this->encoding);
1293
  }
1294
1295
  /**
1296
   * Implements part of the ArrayAccess interface, but throws an exception
1297
   * when called. This maintains the immutability of Stringy objects.
1298
   *
1299
   * @param int   $offset <p>The index of the character.</p>
1300
   * @param mixed $value  <p>Value to set.</p>
1301
   *
1302
   * @throws \Exception <p>When called.</p>
1303
   */
1304 1
  public function offsetSet($offset, $value)
1305
  {
1306
    // Stringy is immutable, cannot directly set char
1307
    /** @noinspection ThrowRawExceptionInspection */
1308 1
    throw new \Exception('Stringy object is immutable, cannot modify char');
1309
  }
1310
1311
  /**
1312
   * Implements part of the ArrayAccess interface, but throws an exception
1313
   * when called. This maintains the immutability of Stringy objects.
1314
   *
1315
   * @param int $offset <p>The index of the character.</p>
1316
   *
1317
   * @throws \Exception <p>When called.</p>
1318
   */
1319 1
  public function offsetUnset($offset)
1320
  {
1321
    // Don't allow directly modifying the string
1322
    /** @noinspection ThrowRawExceptionInspection */
1323 1
    throw new \Exception('Stringy object is immutable, cannot unset char');
1324
  }
1325
1326
  /**
1327
   * Pads the string to a given length with $padStr. If length is less than
1328
   * or equal to the length of the string, no padding takes places. The
1329
   * default string used for padding is a space, and the default type (one of
1330
   * 'left', 'right', 'both') is 'right'. Throws an InvalidArgumentException
1331
   * if $padType isn't one of those 3 values.
1332
   *
1333
   * @param int    $length  <p>Desired string length after padding.</p>
1334
   * @param string $padStr  [optional] <p>String used to pad, defaults to space. Default: ' '</p>
1335
   * @param string $padType [optional] <p>One of 'left', 'right', 'both'. Default: 'right'</p>
1336
   *
1337
   * @return static <p>Object with a padded $str.</p>
1338
   *
1339
   * @throws \InvalidArgumentException <p>If $padType isn't one of 'right', 'left' or 'both'.</p>
1340
   */
1341 1
  public function pad(int $length, string $padStr = ' ', string $padType = 'right'): self
1342
  {
1343 1
    return static::create(
1344 1
        UTF8::str_pad(
1345 1
            $this->str,
1346 1
            $length,
1347 1
            $padStr,
1348 1
            $padType,
1349 1
            $this->encoding
1350
        )
1351
    );
1352
  }
1353
1354
  /**
1355
   * Returns a new string of a given length such that both sides of the
1356
   * string are padded. Alias for pad() with a $padType of 'both'.
1357
   *
1358
   * @param int    $length <p>Desired string length after padding.</p>
1359
   * @param string $padStr [optional] <p>String used to pad, defaults to space. Default: ' '</p>
1360
   *
1361
   * @return static <p>String with padding applied.</p>
1362
   */
1363
  public function padBoth(int $length, string $padStr = ' '): self
1364
  {
1365
    return static::create(
1366
        UTF8::str_pad_both(
1367
            $this->str,
1368
            $length,
1369
            $padStr,
1370
            $this->encoding
1371
        )
1372
    );
1373
  }
1374
1375
  /**
1376
   * Returns a new string of a given length such that the beginning of the
1377
   * string is padded. Alias for pad() with a $padType of 'left'.
1378
   *
1379
   * @param int    $length <p>Desired string length after padding.</p>
1380
   * @param string $padStr [optional] <p>String used to pad, defaults to space. Default: ' '</p>
1381
   *
1382
   * @return static <p>String with left padding.</p>
1383
   */
1384
  public function padLeft(int $length, string $padStr = ' '): self
1385
  {
1386
    return static::create(
1387
        UTF8::str_pad_left(
1388
            $this->str,
1389
            $length,
1390
            $padStr,
1391
            $this->encoding
1392
        )
1393
    );
1394
  }
1395
1396
  /**
1397
   * Returns a new string of a given length such that the end of the string
1398
   * is padded. Alias for pad() with a $padType of 'right'.
1399
   *
1400
   * @param int    $length <p>Desired string length after padding.</p>
1401
   * @param string $padStr [optional] <p>String used to pad, defaults to space. Default: ' '</p>
1402
   *
1403
   * @return static <p>String with right padding.</p>
1404
   */
1405
  public function padRight(int $length, string $padStr = ' '): self
1406
  {
1407
    return static::create(
1408
        UTF8::str_pad_right(
1409
            $this->str,
1410
            $length,
1411
            $padStr,
1412
            $this->encoding
1413
        )
1414
    );
1415
  }
1416
1417
  /**
1418
   * Returns a new string starting with $string.
1419
   *
1420
   * @param string $string <p>The string to append.</p>
1421
   *
1422
   * @return static <p>Object with appended $string.</p>
1423
   */
1424 2
  public function prepend(string $string): self
1425
  {
1426 2
    return static::create($string . $this->str, $this->encoding);
1427
  }
1428
1429
  /**
1430
   * Replaces all occurrences of $pattern in $str by $replacement.
1431
   *
1432
   * @param string $pattern     <p>The regular expression pattern.</p>
1433
   * @param string $replacement <p>The string to replace with.</p>
1434
   * @param string $options     [optional] <p>Matching conditions to be used.</p>
1435
   * @param string $delimiter   [optional] <p>Delimiter the the regex. Default: '/'</p>
1436
   *
1437
   * @return static <p>Object with the result2ing $str after the replacements.</p>
1438
   */
1439
  public function regexReplace(string $pattern, string $replacement, string $options = '', string $delimiter = '/'): self
1440
  {
1441
    $str = UTF8::regex_replace(
1442
        $this->str,
1443
        $pattern,
1444
        $replacement,
1445
        $options,
1446
        $delimiter
1447
    );
1448
1449
    return static::create($str, $this->encoding);
1450
  }
1451
1452
  /**
1453
   * Remove html via "strip_tags()" from the string.
1454
   *
1455
   * @param string $allowableTags [optional] <p>You can use the optional second parameter to specify tags which should
1456
   *                              not be stripped. Default: null
1457
   *                              </p>
1458
   *
1459
   * @return static
1460
   */
1461
  public function removeHtml(string $allowableTags = null): self
1462
  {
1463
    $str = UTF8::remove_html($this->str, $allowableTags);
1464
1465
    return static::create($str, $this->encoding);
1466
  }
1467
1468
  /**
1469
   * Remove all breaks [<br> | \r\n | \r | \n | ...] from the string.
1470
   *
1471
   * @param string $replacement [optional] <p>Default is a empty string.</p>
1472
   *
1473
   * @return static
1474
   */
1475
  public function removeHtmlBreak(string $replacement = ''): self
1476
  {
1477
    $str = UTF8::remove_html_breaks($this->str, $replacement);
1478
1479
    return static::create($str, $this->encoding);
1480
  }
1481
1482
  /**
1483
   * Returns a new string with the prefix $substring removed, if present.
1484
   *
1485
   * @param string $substring <p>The prefix to remove.</p>
1486
   *
1487
   * @return static <p>Object having a $str without the prefix $substring.</p>
1488
   */
1489
  public function removeLeft(string $substring): self
1490
  {
1491
    $str = UTF8::remove_left($this->str, $substring, $this->encoding);
1492
1493
    return static::create($str, $this->encoding);
1494
  }
1495
1496
  /**
1497
   * Returns a new string with the suffix $substring removed, if present.
1498
   *
1499
   * @param string $substring <p>The suffix to remove.</p>
1500
   *
1501
   * @return static <p>Object having a $str without the suffix $substring.</p>
1502
   */
1503
  public function removeRight(string $substring): self
1504
  {
1505
    $str = UTF8::remove_right($this->str, $substring, $this->encoding);
1506
1507
    return static::create($str, $this->encoding);
1508
1509
  }
1510
1511
  /**
1512
   * Try to remove all XSS-attacks from the string.
1513
   *
1514
   * @return static
1515
   */
1516 6
  public function removeXss(): self
1517
  {
1518 6
    static $antiXss = null;
1519
1520 6
    if ($antiXss === null) {
1521 1
      $antiXss = new AntiXSS();
1522
    }
1523
1524 6
    $str = $antiXss->xss_clean($this->str);
1525
1526 6
    return static::create($str, $this->encoding);
1527
  }
1528
1529
  /**
1530
   * Returns a repeated string given a multiplier.
1531
   *
1532
   * @param int $multiplier <p>The number of times to repeat the string.</p>
1533
   *
1534
   * @return static <p>Object with a repeated str.</p>
1535
   */
1536 7
  public function repeat(int $multiplier): self
1537
  {
1538 7
    $repeated = UTF8::str_repeat($this->str, $multiplier);
1539
1540 7
    return static::create($repeated, $this->encoding);
1541
  }
1542
1543
  /**
1544
   * Replaces all occurrences of $search in $str by $replacement.
1545
   *
1546
   * @param string $search        <p>The needle to search for.</p>
1547
   * @param string $replacement   <p>The string to replace with.</p>
1548
   * @param bool   $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
1549
   *
1550
   * @return static <p>Object with the resulting $str after the replacements.</p>
1551
   */
1552 28 View Code Duplication
  public function replace(string $search, string $replacement, bool $caseSensitive = true): self
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...
1553
  {
1554 28
    if ($caseSensitive) {
1555 21
      $return = UTF8::str_replace($search, $replacement, $this->str);
1556
    } else {
1557 7
      $return = UTF8::str_ireplace($search, $replacement, $this->str);
1558
    }
1559
1560 28
    return static::create($return, $this->encoding);
1561
  }
1562
1563
  /**
1564
   * Replaces all occurrences of $search in $str by $replacement.
1565
   *
1566
   * @param array        $search        <p>The elements to search for.</p>
1567
   * @param string|array $replacement   <p>The string to replace with.</p>
1568
   * @param bool         $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
1569
   *
1570
   * @return static <p>Object with the resulting $str after the replacements.</p>
1571
   */
1572 30 View Code Duplication
  public function replaceAll(array $search, $replacement, bool $caseSensitive = true): self
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...
1573
  {
1574 30
    if ($caseSensitive) {
1575 23
      $return = UTF8::str_replace($search, $replacement, $this->str);
1576
    } else {
1577 7
      $return = UTF8::str_ireplace($search, $replacement, $this->str);
1578
    }
1579
1580 30
    return static::create($return, $this->encoding);
1581
  }
1582
1583
  /**
1584
   * Replaces first occurrences of $search from the beginning of string with $replacement.
1585
   *
1586
   * @param string $search      <p>The string to search for.</p>
1587
   * @param string $replacement <p>The replacement.</p>
1588
   *
1589
   * @return static <p>Object with the resulting $str after the replacements.</p>
1590
   */
1591
  public function replaceFirst(string $search, string $replacement): self
1592
  {
1593
    $str = UTF8::str_replace_first($this->str, $search, $replacement);
1594
1595
    return static::create($str, $this->encoding);
1596
  }
1597
1598
  /**
1599
   * Replaces last occurrences of $search from the ending of string with $replacement.
1600
   *
1601
   * @param string $search      <p>The string to search for.</p>
1602
   * @param string $replacement <p>The replacement.</p>
1603
   *
1604
   * @return static <p>Object with the resulting $str after the replacements.</p>
1605
   */
1606
  public function replaceLast(string $search, string $replacement): self
1607
  {
1608
    $str = UTF8::str_replace_last($this->str, $search, $replacement);
1609
1610
    return static::create($str, $this->encoding);
1611
  }
1612
1613
  /**
1614
   * Replaces all occurrences of $search from the beginning of string with $replacement.
1615
   *
1616
   * @param string $search      <p>The string to search for.</p>
1617
   * @param string $replacement <p>The replacement.</p>
1618
   *
1619 5
   * @return static <p>Object with the resulting $str after the replacements.</p>
1620
   */
1621 5
  public function replaceBeginning(string $search, string $replacement): self
1622
  {
1623 5
    $str = UTF8::str_replace_beginning($this->str, $search, $replacement);
1624
1625
    return static::create($str, $this->encoding);
1626
  }
1627
1628
  /**
1629
   * Replaces all occurrences of $search from the ending of string with $replacement.
1630
   *
1631
   * @param string $search      <p>The string to search for.</p>
1632
   * @param string $replacement <p>The replacement.</p>
1633
   *
1634
   * @return static <p>Object with the resulting $str after the replacements.</p>
1635
   */
1636
  public function replaceEnding(string $search, string $replacement): self
1637
  {
1638
    $str = UTF8::str_replace_ending($this->str, $search, $replacement);
1639
1640
    return static::create($str, $this->encoding);
1641
  }
1642
1643
  /**
1644
   * Returns a reversed string. A multibyte version of strrev().
1645
   *
1646
   * @return static <p>Object with a reversed $str.</p>
1647
   */
1648
  public function reverse(): self
1649
  {
1650
    $reversed = UTF8::strrev($this->str);
1651
1652 4
    return static::create($reversed, $this->encoding);
1653
  }
1654 4
1655
  /**
1656 4
   * Truncates the string to a given length, while ensuring that it does not
1657
   * split words. If $substring is provided, and truncating occurs, the
1658
   * string is further truncated so that the substring may be appended without
1659
   * exceeding the desired length.
1660
   *
1661
   * @param int    $length    <p>Desired length of the truncated string.</p>
1662
   * @param string $substring [optional] <p>The substring to append if it can fit. Default: ''</p>
1663
   *
1664
   * @return static <p>Object with the resulting $str after truncating.</p>
1665 3
   */
1666
  public function safeTruncate(int $length, string $substring = ''): self
1667 3
  {
1668
    $str = UTF8::str_truncate_safe($this->str, $length, $substring, $this->encoding);
1669 3
1670
    return static::create($str, $this->encoding);
1671
  }
1672
1673
  /**
1674
   * Shorten the string after $length, but also after the next word.
1675
   *
1676
   * @param int    $length
1677
   * @param string $strAddOn [optional] <p>Default: '…'</p>
1678
   *
1679
   * @return static
1680
   */
1681
  public function shortenAfterWord(int $length, string $strAddOn = '…'): self
1682
  {
1683
    $string = UTF8::str_limit_after_word($this->str, $length, $strAddOn);
1684
1685
    return static::create($string, $this->encoding);
1686
  }
1687
1688
  /**
1689
   * A multibyte string shuffle function. It returns a string with its
1690
   * characters in random order.
1691
   *
1692
   * @return static <p>Object with a shuffled $str.</p>
1693
   */
1694
  public function shuffle(): self
1695
  {
1696
    $shuffledStr = UTF8::str_shuffle($this->str);
1697
1698
    return static::create($shuffledStr, $this->encoding);
1699
  }
1700
1701
  /**
1702
   * Returns the substring beginning at $start, and up to, but not including
1703 15
   * the index specified by $end. If $end is omitted, the function extracts
1704
   * the remaining string. If $end is negative, it is computed from the end
1705 15
   * of the string.
1706
   *
1707 15
   * @param int $start <p>Initial index from which to begin extraction.</p>
1708
   * @param int $end   [optional] <p>Index at which to end extraction. Default: null</p>
1709
   *
1710
   * @return static <p>Object with its $str being the extracted substring.</p>
1711
   */
1712
  public function slice(int $start, int $end = null): self
1713
  {
1714
    $str = UTF8::str_slice($this->str, $start, $end, $this->encoding);
1715
1716
    return static::create($str, $this->encoding);
1717
  }
1718
1719
  /**
1720
   * Converts the string into an URL slug. This includes replacing non-ASCII
1721
   * characters with their closest ASCII equivalents, removing remaining
1722
   * non-ASCII and non-alphanumeric characters, and replacing whitespace with
1723
   * $replacement. The replacement defaults to a single dash, and the string
1724
   * is also converted to lowercase.
1725
   *
1726
   * @param string $replacement [optional] <p>The string used to replace whitespace. Default: '-'</p>
1727
   * @param string $language    [optional] <p>The language for the url. Default: 'de'</p>
1728
   * @param bool   $strToLower  [optional] <p>string to lower. Default: true</p>
1729
   *
1730
   * @return static <p>Object whose $str has been converted to an URL slug.</p>
1731
   */
1732
  public function slugify(string $replacement = '-', string $language = 'de', bool $strToLower = true): self
1733
  {
1734
    $slug = URLify::slug($this->str, $language, $replacement, $strToLower);
1735
1736
    return static::create($slug, $this->encoding);
1737
  }
1738
1739
  /**
1740
   * Convert a string to e.g.: "snake_case"
1741
   *
1742
   * @return static <p>Object with $str in snake_case.</p>
1743
   */
1744
  public function snakeize(): self
1745
  {
1746
    $str = UTF8::str_snakeize($this->str, $this->encoding);
1747
1748
    return static::create($str, $this->encoding);
1749
  }
1750
1751
  /**
1752
   * Splits the string with the provided regular expression, returning an
1753 11
   * array of Stringy objects. An optional integer $limit will truncate the
1754
   * results.
1755 11
   *
1756 7
   * @param string $pattern <p>The regex with which to split the string.</p>
1757
   * @param int    $limit   [optional] <p>Maximum number of results to return. Default: -1 === no limit</p>
1758
   *
1759 4
   * @return static[] <p>An array of Stringy objects.</p>
1760
   */
1761
  public function split(string $pattern, int $limit = -1): array
1762
  {
1763
    $array = UTF8::str_split_pattern($this->str, $pattern, $limit);
1764
1765
    foreach ($array as $i => &$value) {
1766
      $value = static::create($value, $this->encoding);
1767
    }
1768
1769
    return $array;
1770
  }
1771
1772
  /**
1773
   * Returns true if the string begins with $substring, false otherwise. By
1774
   * default, the comparison is case-sensitive, but can be made insensitive
1775
   * by setting $caseSensitive to false.
1776
   *
1777
   * @param string $substring     <p>The substring to look for.</p>
1778
   * @param bool   $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
1779
   *
1780
   * @return bool <p>Whether or not $str starts with $substring.</p>
1781
   */
1782
  public function startsWith(string $substring, bool $caseSensitive = true): bool
1783
  {
1784
    if ($caseSensitive) {
1785
      return UTF8::str_starts_with($this->str, $substring);
1786
    }
1787 12
1788
    return UTF8::str_istarts_with($this->str, $substring);
1789 12
  }
1790
1791 12
  /**
1792
   * Returns true if the string begins with any of $substrings, false otherwise.
1793
   * By default the comparison is case-sensitive, but can be made insensitive by
1794
   * setting $caseSensitive to false.
1795
   *
1796
   * @param array $substrings    <p>Substrings to look for.</p>
1797
   * @param bool  $caseSensitive [optional] <p>Whether or not to enforce case-sensitivity. Default: true</p>
1798
   *
1799
   * @return bool  <p>Whether or not $str starts with $substring.</p>
1800
   */
1801
  public function startsWithAny(array $substrings, bool $caseSensitive = true): bool
1802
  {
1803
    if ($caseSensitive) {
1804
      return UTF8::str_starts_with_any($this->str, $substrings);
1805
    }
1806
1807
    return UTF8::str_istarts_with_any($this->str, $substrings);
1808
  }
1809
1810
  /**
1811
   * Strip all whitespace characters. This includes tabs and newline characters,
1812
   * as well as multibyte whitespace such as the thin space and ideographic space.
1813
   *
1814
   * @return static
1815
   */
1816
  public function stripWhitespace(): self
1817
  {
1818
    $str = UTF8::strip_whitespace($this->str);
1819
1820
    return static::create($str, $this->encoding);
1821
  }
1822
1823
  /**
1824
   * Remove css media-queries.
1825
   *
1826
   * @return static
1827
   */
1828
  public function stripeCssMediaQueries(): self
1829
  {
1830 9
    $str = UTF8::css_stripe_media_queries($this->str);
1831
1832 9
    return static::create($str, $this->encoding);
1833 9
  }
1834 9
1835 9
  /**
1836 9
   * Remove empty html-tag.
1837
   *
1838
   * e.g.: <tag></tag>
1839 9
   *
1840
   * @return static
1841
   */
1842
  public function stripeEmptyHtmlTags(): self
1843
  {
1844
    $str = UTF8::html_stripe_empty_tags($this->str);
1845
1846
    return static::create($str, $this->encoding);
1847
  }
1848
1849
  /**
1850
   * Returns the substring beginning at $start with the specified $length.
1851
   * It differs from the UTF8::substr() function in that providing a $length of
1852
   * null will return the rest of the string, rather than an empty string.
1853
   *
1854
   * @param int $start  <p>Position of the first character to use.</p>
1855
   * @param int $length [optional] <p>Maximum number of characters used. Default: null</p>
1856
   *
1857
   * @return static <p>Object with its $str being the substring.</p>
1858
   */
1859
  public function substr(int $start, int $length = null): self
1860
  {
1861
    $str = UTF8::substr(
1862
        $this->str,
1863
        $start,
1864
        $length,
1865
        $this->encoding
1866
    );
1867
1868
    return static::create($str, $this->encoding);
1869
  }
1870
1871
  /**
1872
   * Gets the substring after (or before via "$beforeNeedle") the first occurrence of the "$needle".
1873
   * If no match is found returns new empty Stringy object.
1874
   *
1875
   * @param string $needle       <p>The string to look for.</p>
1876
   * @param bool   $beforeNeedle [optional] <p>Default: false</p>
1877
   *
1878
   * @return static
1879
   */
1880
  public function substringOf(string $needle, bool $beforeNeedle = false): self
1881
  {
1882
    $str = UTF8::str_substr_first($this->str, $needle, $beforeNeedle, $this->encoding);
1883
1884
    return static::create($str, $this->encoding);
1885
  }
1886
1887
  /**
1888
   * Gets the substring after (or before via "$beforeNeedle") the first occurrence of the "$needle".
1889
   * If no match is found returns new empty Stringy object.
1890
   *
1891
   * @param string $needle       <p>The string to look for.</p>
1892
   * @param bool   $beforeNeedle [optional] <p>Default: false</p>
1893 4
   *
1894
   * @return static
1895 4
   */
1896
  public function substringOfIgnoreCase(string $needle, bool $beforeNeedle = false): self
1897 4
  {
1898
    $str = UTF8::str_isubstr_first($this->str, $needle, $beforeNeedle, $this->encoding);
1899
1900
    return static::create($str, $this->encoding);
1901
  }
1902
1903
  /**
1904
   * Surrounds $str with the given substring.
1905
   *
1906
   * @param string $substring <p>The substring to add to both sides.</P>
1907 4
   *
1908
   * @return static <p>Object whose $str had the substring both prepended and appended.</p>
1909 4
   */
1910
  public function surround(string $substring): self
1911 4
  {
1912
    $str = UTF8::str_surround($this->str, $substring);
1913
1914
    return static::create($str, $this->encoding);
1915
  }
1916
1917
  /**
1918
   * Returns a case swapped version of the string.
1919
   *
1920
   * @return static <p>Object whose $str has each character's case swapped.</P>
1921
   */
1922
  public function swapCase(): self
1923
  {
1924
    $str = UTF8::swapCase($this->str, $this->encoding);
1925
1926
    return static::create($str, $this->encoding);
1927
  }
1928
1929
  /**
1930
   * Returns a string with smart quotes, ellipsis characters, and dashes from
1931
   * Windows-1252 (commonly used in Word documents) replaced by their ASCII
1932
   * equivalents.
1933
   *
1934
   * @return static <p>Object whose $str has those characters removed.</p>
1935
   */
1936
  public function tidy(): self
1937
  {
1938
    $str = UTF8::normalize_msword($this->str);
1939
1940
    return static::create($str, $this->encoding);
1941
  }
1942
1943
  /**
1944
   * Returns a trimmed string with the first letter of each word capitalized.
1945
   * Also accepts an array, $ignore, allowing you to list words not to be
1946
   * capitalized.
1947
   *
1948
   * @param array|null $ignore [optional] <p>An array of words not to capitalize or null. Default: null</p>
1949
   *
1950
   * @return static <p>Object with a titleized $str.</p>
1951
   */
1952
  public function titleize(array $ignore = null): self
1953
  {
1954
    $str = UTF8::str_titleize($this->str, $ignore, $this->encoding);
1955
1956
    return static::create($str, $this->encoding);
1957
  }
1958
1959
  /**
1960
   * Returns a trimmed string in proper title case.
1961 16
   *
1962
   * Also accepts an array, $ignore, allowing you to list words not to be
1963 16
   * capitalized.
1964
   *
1965 16
   * Adapted from John Gruber's script.
1966
   *
1967
   * @see https://gist.github.com/gruber/9f9e8650d68b13ce4d78
1968
   *
1969
   * @param array $ignore <p>An array of words not to capitalize.</p>
1970
   *
1971
   * @return static <p>Object with a titleized $str</p>
1972
   */
1973
  public function titleizeForHumans(array $ignore = []): self
1974
  {
1975
    $str = UTF8::str_titleize_for_humans($this->str, $ignore, $this->encoding);
1976
1977
    return static::create($str, $this->encoding);
1978
  }
1979
1980
  /**
1981
   * Returns an ASCII version of the string. A set of non-ASCII characters are
1982
   * replaced with their closest ASCII counterparts, and the rest are removed
1983
   * unless instructed otherwise.
1984
   *
1985
   * @param bool $strict [optional] <p>Use "transliterator_transliterate()" from PHP-Intl | WARNING: bad performance |
1986
   *                     Default: false</p>
1987
   *
1988
   * @return static <p>Object whose $str contains only ASCII characters.</p>
1989 7
   */
1990
  public function toAscii(bool $strict = false): self
1991 7
  {
1992
    $str = UTF8::to_ascii($this->str, '?', $strict);
1993 7
1994
    return static::create($str, $this->encoding);
1995
  }
1996
1997
  /**
1998
   * Returns a boolean representation of the given logical string value.
1999
   * For example, 'true', '1', 'on' and 'yes' will return true. 'false', '0',
2000
   * 'off', and 'no' will return false. In all instances, case is ignored.
2001
   * For other numeric strings, their sign will determine the return value.
2002
   * In addition, blank strings consisting of only whitespace will return
2003
   * false. For all other strings, the return value is a result of a
2004
   * boolean cast.
2005
   *
2006
   * @return bool <p>A boolean value for the string.</p>
2007
   */
2008
  public function toBoolean(): bool
2009
  {
2010
    return UTF8::to_boolean($this->str);
2011
  }
2012
2013
  /**
2014
   * Converts all characters in the string to lowercase.
2015
   *
2016 271
   * @return static <p>Object with all characters of $str being lowercase.</p>
2017
   */
2018 271
  public function toLowerCase(): self
2019
  {
2020
    $str = UTF8::strtolower($this->str, $this->encoding);
2021
2022
    return static::create($str, $this->encoding);
2023
  }
2024
2025
  /**
2026
   * Converts each tab in the string to some number of spaces, as defined by
2027
   * $tabLength. By default, each tab is converted to 4 consecutive spaces.
2028
   *
2029
   * @param int $tabLength [optional] <p>Number of spaces to replace each tab with. Default: 4</p>
2030
   *
2031
   * @return static <p>Object whose $str has had tabs switched to spaces.</p>
2032
   */
2033
  public function toSpaces(int $tabLength = 4): self
2034
  {
2035
    $str = UTF8::tabs_to_spaces($this->str, $tabLength);
2036
2037
    return static::create($str, $this->encoding);
2038
  }
2039
2040
  /**
2041
   * Return Stringy object as string, but you can also use (string) for automatically casting the object into a string.
2042
   *
2043
   * @return string
2044
   */
2045
  public function toString(): string
2046
  {
2047
    return (string)$this->str;
2048
  }
2049
2050
  /**
2051
   * Converts each occurrence of some consecutive number of spaces, as
2052
   * defined by $tabLength, to a tab. By default, each 4 consecutive spaces
2053
   * are converted to a tab.
2054
   *
2055 5
   * @param int $tabLength [optional] <p>Number of spaces to replace with a tab. Default: 4</p>
2056
   *
2057 5
   * @return static <p>Object whose $str has had spaces switched to tabs.</p>
2058
   */
2059 5
  public function toTabs(int $tabLength = 4): self
2060
  {
2061
    $str = UTF8::spaces_to_tabs($this->str, $tabLength);
2062
2063
    return static::create($str, $this->encoding);
2064
  }
2065
2066
  /**
2067
   * Converts the first character of each word in the string to uppercase
2068
   * and all other chars to lowercase.
2069
   *
2070
   * @return static <p>Object with all characters of $str being title-cased.</p>
2071 12
   */
2072
  public function toTitleCase(): self
2073 12
  {
2074
    $str = UTF8::titlecase($this->str, $this->encoding);
2075 12
2076
    return static::create($str, $this->encoding);
2077
  }
2078
2079
  /**
2080
   * Converts all characters in the string to uppercase.
2081
   *
2082
   * @return static <p>Object with all characters of $str being uppercase.</p>
2083
   */
2084
  public function toUpperCase(): self
2085
  {
2086
    $str = UTF8::strtoupper($this->str, $this->encoding);
2087 13
2088
    return static::create($str, $this->encoding);
2089 13
  }
2090
2091 13
  /**
2092
   * Returns a string with whitespace removed from the start and end of the
2093
   * string. Supports the removal of unicode whitespace. Accepts an optional
2094
   * string of characters to strip instead of the defaults.
2095
   *
2096
   * @param string $chars [optional] <p>String of characters to strip. Default: null</p>
2097
   *
2098
   * @return static <p>Object with a trimmed $str.</p>
2099
   */
2100
  public function trim(string $chars = null): self
2101
  {
2102
    $str = UTF8::trim($this->str, $chars);
2103 13
2104
    return static::create($str, $this->encoding);
2105 13
  }
2106
2107 13
  /**
2108
   * Returns a string with whitespace removed from the start of the string.
2109
   * Supports the removal of unicode whitespace. Accepts an optional
2110
   * string of characters to strip instead of the defaults.
2111
   *
2112
   * @param string $chars [optional] <p>Optional string of characters to strip. Default: null</p>
2113
   *
2114
   * @return static <p>Object with a trimmed $str.</p>
2115
   */
2116
  public function trimLeft(string $chars = null): self
2117
  {
2118
    $str = UTF8::ltrim($this->str, $chars);
2119
2120
    return static::create($str, $this->encoding);
2121
  }
2122
2123
  /**
2124
   * Returns a string with whitespace removed from the end of the string.
2125
   * Supports the removal of unicode whitespace. Accepts an optional
2126
   * string of characters to strip instead of the defaults.
2127
   *
2128
   * @param string $chars [optional] <p>Optional string of characters to strip. Default: null</p>
2129
   *
2130
   * @return static <p>Object with a trimmed $str.</p>
2131
   */
2132
  public function trimRight(string $chars = null): self
2133
  {
2134
    $str = UTF8::rtrim($this->str, $chars);
2135
2136
    return static::create($str, $this->encoding);
2137
  }
2138
2139
  /**
2140
   * Truncates the string to a given length. If $substring is provided, and
2141
   * truncating occurs, the string is further truncated so that the substring
2142
   * may be appended without exceeding the desired length.
2143
   *
2144
   * @param int    $length    <p>Desired length of the truncated string.</p>
2145
   * @param string $substring [optional] <p>The substring to append if it can fit. Default: ''</p>
2146
   *
2147
   * @return static <p>Object with the resulting $str after truncating.</p>
2148
   */
2149
  public function truncate(int $length, string $substring = ''): self
2150
  {
2151
    $str = UTF8::str_truncate($this->str, $length, $substring, $this->encoding);
2152
2153
    return static::create($str, $this->encoding);
2154
  }
2155
2156
  /**
2157
   * Returns a lowercase and trimmed string separated by underscores.
2158
   * Underscores are inserted before uppercase characters (with the exception
2159 5
   * of the first character of the string), and in place of spaces as well as
2160
   * dashes.
2161 5
   *
2162
   * @return static <p>Object with an underscored $str.</p>
2163 5
   */
2164
  public function underscored(): self
2165
  {
2166
    return $this->delimit('_');
2167
  }
2168
2169
  /**
2170
   * Returns an UpperCamelCase version of the supplied string. It trims
2171 1
   * surrounding spaces, capitalizes letters following digits, spaces, dashes
2172
   * and underscores, and removes spaces, dashes, underscores.
2173 1
   *
2174
   * @return static  <p>Object with $str in UpperCamelCase.</p>
2175 1
   */
2176
  public function upperCamelize(): self
2177
  {
2178
    $str = UTF8::str_upper_camelize($this->str, $this->encoding);
2179
2180
    return static::create($str, $this->encoding);
2181
  }
2182
2183
  /**
2184
   * Converts the first character of the supplied string to upper case.
2185
   *
2186
   * @return static <p>Object with the first character of $str being upper case.</p>
2187
   */
2188
  public function upperCaseFirst(): self
2189
  {
2190
    $str = UTF8::ucfirst($this->str, $this->encoding);
2191
2192
    return static::create($str, $this->encoding);
2193
  }
2194
2195
  /**
2196
   * Converts the string into an valid UTF-8 string.
2197
   *
2198
   * @return static
2199
   */
2200
  public function utf8ify(): self
2201
  {
2202
    $str = UTF8::cleanup($this->str);
2203
2204
    return static::create($str, $this->encoding);
2205
  }
2206
}
2207