blob: 4b9677d9f4439fd4e6df96ed15fb8e9df7b34704 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
|
using System;
using System.Text.RegularExpressions;
using ICU4N.Text;
namespace Jellyfin.Extensions
{
/// <summary>
/// Provides extensions methods for <see cref="string" />.
/// </summary>
public static partial class StringExtensions
{
private static readonly Lazy<string> _transliteratorId = new(() =>
Environment.GetEnvironmentVariable("JELLYFIN_TRANSLITERATOR_ID")
?? "Any-Latin; Latin-Ascii; Lower; NFD; [:Nonspacing Mark:] Remove; [:Punctuation:] Remove;");
private static readonly Lazy<Transliterator?> _transliterator = new(() =>
{
try
{
return Transliterator.GetInstance(_transliteratorId.Value);
}
catch (ArgumentException)
{
return null;
}
});
// Matches non-conforming unicode chars
// https://mnaoumov.wordpress.com/2014/06/14/stripping-invalid-characters-from-utf-16-strings/
[GeneratedRegex("([\ud800-\udbff](?![\udc00-\udfff]))|((?<![\ud800-\udbff])[\udc00-\udfff])|(�)")]
private static partial Regex NonConformingUnicodeRegex();
/// <summary>
/// Removes the diacritics character from the strings.
/// </summary>
/// <param name="text">The string to act on.</param>
/// <returns>The string without diacritics character.</returns>
public static string RemoveDiacritics(this string text)
=> Diacritics.Extensions.StringExtensions.RemoveDiacritics(
NonConformingUnicodeRegex().Replace(text, string.Empty));
/// <summary>
/// Checks whether or not the specified string has diacritics in it.
/// </summary>
/// <param name="text">The string to check.</param>
/// <returns>True if the string has diacritics, false otherwise.</returns>
public static bool HasDiacritics(this string text)
=> Diacritics.Extensions.StringExtensions.HasDiacritics(text)
|| NonConformingUnicodeRegex().IsMatch(text);
/// <summary>
/// Counts the number of occurrences of [needle] in the string.
/// </summary>
/// <param name="value">The haystack to search in.</param>
/// <param name="needle">The character to search for.</param>
/// <returns>The number of occurrences of the [needle] character.</returns>
public static int Count(this ReadOnlySpan<char> value, char needle)
{
var count = 0;
var length = value.Length;
for (var i = 0; i < length; i++)
{
if (value[i] == needle)
{
count++;
}
}
return count;
}
/// <summary>
/// Returns the part on the left of the <c>needle</c>.
/// </summary>
/// <param name="haystack">The string to seek.</param>
/// <param name="needle">The needle to find.</param>
/// <returns>The part left of the <paramref name="needle" />.</returns>
public static ReadOnlySpan<char> LeftPart(this ReadOnlySpan<char> haystack, char needle)
{
if (haystack.IsEmpty)
{
return ReadOnlySpan<char>.Empty;
}
var pos = haystack.IndexOf(needle);
return pos == -1 ? haystack : haystack[..pos];
}
/// <summary>
/// Returns the part on the right of the <c>needle</c>.
/// </summary>
/// <param name="haystack">The string to seek.</param>
/// <param name="needle">The needle to find.</param>
/// <returns>The part right of the <paramref name="needle" />.</returns>
public static ReadOnlySpan<char> RightPart(this ReadOnlySpan<char> haystack, char needle)
{
if (haystack.IsEmpty)
{
return ReadOnlySpan<char>.Empty;
}
var pos = haystack.LastIndexOf(needle);
if (pos == -1)
{
return haystack;
}
if (pos == haystack.Length - 1)
{
return ReadOnlySpan<char>.Empty;
}
return haystack[(pos + 1)..];
}
/// <summary>
/// Returns a transliterated string which only contain ascii characters.
/// </summary>
/// <param name="text">The string to act on.</param>
/// <returns>The transliterated string.</returns>
public static string Transliterated(this string text)
{
return (_transliterator.Value is null) ? text : _transliterator.Value.Transliterate(text);
}
}
}
|