Skip to main content
Home  › ... Razor

RazorBlade Tutorials

Tutorial HomeRazorBlade

RazorBlade Text Operations

RazorBlade helps with many helper functions to optimize working with string variables, also when they contain html. 

RazorBlade Text.Crop(...) and Text.Ellipsis(...) v1.1

These demos show how to crop text properly, because Razor Blade handles a lot of issues you'll usually have cropping text.

Example Text

Original which visually has 31 characters:

  • The human view - how it looks for users:
    We love Tokyo, Zürich & München
    123456789-123456789-123456789-1
  • The truth - how the string looks internally:
    We love Tokyo, Zürich & München
    123456789-1234567.....89-123....456.....789-1
This demonstrates how strings are cut off in the middle of words if we don't use razor blade. It also breaks html entities like & (the & character) or umlauts because ü = ü.
Using C# Method Razor Blade
Len C# Substring Text.Crop(...) Text.Ellipsis(...)
1 W... W W…
2 We... We We…
3 We ... We We…
4 We l... We We…
5 We lo... We We…
6 We lov... We We…
7 We love... We love We love…
8 We love ... We love We love…
9 We love T... We love We love…
10 We love To... We love We love…
11 We love Tok... We love We love…
12 We love Toky... We love We love…
13 We love Tokyo... We love Tokyo We love Tokyo…
14 We love Tokyo,... We love Tokyo We love Tokyo…
15 We love Tokyo, ... We love Tokyo We love Tokyo…
16 We love Tokyo, Z... We love Tokyo We love Tokyo…
17 We love Tokyo, Z&... We love Tokyo We love Tokyo…
18 We love Tokyo, Z&u... We love Tokyo We love Tokyo…
19 We love Tokyo, Z&uu... We love Tokyo We love Tokyo…
20 We love Tokyo, Z&uum... We love Tokyo We love Tokyo…
21 We love Tokyo, Z&uuml... We love Tokyo, Zürich We love Tokyo, Zürich…
22 We love Tokyo, Zü... We love Tokyo, Zürich We love Tokyo, Zürich…
23 We love Tokyo, Zür... We love Tokyo, Zürich & We love Tokyo, Zürich &…
24 We love Tokyo, Züri... We love Tokyo, Zürich & We love Tokyo, Zürich &…
25 We love Tokyo, Züric... We love Tokyo, Zürich & We love Tokyo, Zürich &…
26 We love Tokyo, Zürich... We love Tokyo, Zürich & We love Tokyo, Zürich &…
27 We love Tokyo, Zürich ... We love Tokyo, Zürich & We love Tokyo, Zürich &…
28 We love Tokyo, Zürich &... We love Tokyo, Zürich & We love Tokyo, Zürich &…
29 We love Tokyo, Zürich &a... We love Tokyo, Zürich & We love Tokyo, Zürich &…
30 We love Tokyo, Zürich &am... We love Tokyo, Zürich & We love Tokyo, Zürich &…
31 We love Tokyo, Zürich &amp... We love Tokyo, Zürich & München We love Tokyo, Zürich & München
32 We love Tokyo, Zürich &... We love Tokyo, Zürich & München We love Tokyo, Zürich & München
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var sample1 = "We love Tokyo, Zürich & München";
  var realLength = 31;
}
<table class="table table-hover table-sm">
<!-- headers -->
<tr>
    <th></th>
    <th><em>Using C# Method</em></th>
    <th colspan="2"><em>Razor Blade</em></th>
</tr>
<tr>
    <th>Len</th>
    <th>C# Substring</th>
    <th>Text.Crop(...)</th>
    <th>Text.Ellipsis(...)</th>
</tr>
<!-- the code --> 
@for(var len = 1; len <= 32; len++) {
  <tr>
    <td>@len</td>
    <td>@sample1.Substring(0, len)...</td>
    <td>@Html.Raw(Text.Crop(sample1, len))</td>
    <td>@Html.Raw(Text.Ellipsis(sample1, len))</td>
  </tr>
      }
</table>

RazorBlade Text.Has(...) v1.1

These demos show how to really check if a variable has text using Text.Has. This combines checks for...

  • null
  • empty
  • only html-nbsp
  • only html character #160 (also nbsp)
  • only new-line

Note that these examples use functions, emojis and RazorBlade Fluent API so click on the links if you don't understand that.

Result

Test Code Result ...when html counts
Null valueText.Has(null)
Just spacesText.Has(" ")
text with only line breaksText.Has("\n\n")
tabs, spaces and line breaksText.Has("\n\t \n")
only nbsp charactersText.Has("&nbsp; &nbsp;")✔️
char-code of nbsp charactersText.Has("&#160;")✔️
real textText.Has("real text")✔️✔️
Real text with nbps etc.Text.Has("real\n text &nbsp;")✔️✔️
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@functions {
  // Quick helper to convert true/false into emojis
  string Boolmoji(bool value) { return value ? "✔️" : "❌"; }

  // Create a row (TR) containing data about a Text.Has example
  object RowEmojified(string label, string value) {
    var valueForShowing = value == null 
      ? "null" 
      : "\"" + value.Replace("\n", "\\n").Replace("\t", "\\t") + "\"";
    return Tag.Tr(
      Tag.Td(label),
      Tag.Td("Text.Has(" + Tags.Encode(valueForShowing) + ")"),
      Tag.Td(Boolmoji(Text.Has(value))),
      Tag.Td(Boolmoji(Text.Has(value, false)))
    );
  }
}

<table class="demo table table-hover">
  <tr>
    <th>Test</th>
    <th>Code</th>
    <th>Result</th>
    <th>...when html counts</th>
  </tr>
  @RowEmojified("Null value", null)
  @RowEmojified("Just spaces", "     ")
  @RowEmojified("text with only line breaks", "\n\n")
  @RowEmojified("tabs, spaces and line breaks", "\n\t  \n")
  @RowEmojified("only nbsp characters", "&nbsp; &nbsp;")
  @RowEmojified("char-code of nbsp characters", "&#160;")
  @RowEmojified("real text", "real text")
  @RowEmojified("Real text with nbps etc.", "real\n text &nbsp;")
</table>

<!-- unimportant stuff, hidden -->

  • If your string is like Text.Has("<br>") it will be: True
  • If you want to ignore BRs, combine it with Tags.Br2Nl(...)
  • ...resulting in:

⬇️ Result | Source ➡️

False
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@Text.Has(Tags.Br2Nl("<br>"))
Requirements

RazorBlade Text.First(...) v3

These demos show how to get the first real text of a series of values. Basically it will ignore nulls, empty texts, space-strings and even combinations containing empty lines, html-nbsps and more. 

⬇️ Result | Source ➡️

  1. Text.First(null, John) ⇒ John
  2. Text.First(null, null)
  3. Text.First(John, Michael) ⇒ John
  4. Text.First(" " = 3 spaces, John) ⇒ John
  5. Text.First(null, please-enter-name) ⇒ please-enter-name
  6. Text.First(&nbsp;, please-enter-name) ⇒ please-enter-name
  7. Text.First(false, &nbsp;, please-enter-name) ⇒ &nbsp;
    "false" at the end means don't treat html-whitespace as whitespace, so &nbsp; will be treated as a real value
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
// Initial Code
//The following code runs at the beginning and creates some variables/services used in the following samples.
  var val1 = "John";
  var val2 = "Michael";
  var spc = "   ";
  var fallback = "please-enter-name";
  var nbsp = "&nbsp;";
}

<ol>
  <li>
    <code>Text.First(null, @val1)</code> 
    ⇒ @Text.First(null, val1)
  </li>
  <li>
    <code>Text.First(null, null)</code> 
    ⇒ @Text.First(null, null)
  </li>
  <li>
    <code>Text.First(@val1, @val2)</code> 
    ⇒ @Text.First(val1, val2)
  </li>
  <li>
    <code>Text.First("@spc" = 3 spaces, @val1)</code> 
    ⇒ @Text.First(spc, val1)
  </li>
  <li>
    <code>Text.First(null, @fallback)</code> 
    ⇒ @Text.First(null, fallback)
  </li>
  <li>
    <code>Text.First(@nbsp, @fallback)</code>
    ⇒ @Text.First(nbsp, fallback)
  </li>
  <li>
    <code>Text.First(false, @nbsp, @fallback)</code> 
    ⇒ @Text.First(false, nbsp, fallback) <br>
      <em></em>"false" at the end means don't treat html-whitespace as whitespace, so @nbsp will be treated as a real value</em>
  </li>
</ol>

Text.First has overloads (multiple signatures) for up to 5 values, and another one accepting an array of string objects so you can even use it for 10 values if you really need it.

⬇️ Result | Source ➡️

  1. Text.First(null, John, please-enter-name) ⇒ John
  2. Text.First(null, John, Michael, please-enter-name) ⇒ John
  3. Text.First(null, &nbsp;, John, Michael, please-enter-name) ⇒ John
  4. Text.First(false, null, &nbsp;, John, Michael, please-enter-name) ⇒ &nbsp;
  5. Text.First(null, null, &nbsp;, John, Michael, " ", please-enter-name) ⇒ John
  6. Text.First(false, null, null, &nbsp;, John, Michael, " ", please-enter-name) ⇒ &nbsp;
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
// Initial Code
//The following code runs at the beginning and creates some variables/services used in the following samples.
  var val1 = "John";
  var val2 = "Michael";
  var spc = "   ";
  var fallback = "please-enter-name";
  var nbsp = "&nbsp;";
}

<ol>
    <li>
      <code>Text.First(null, @val1, @fallback)</code> 
      ⇒ @Text.First(null, val1, fallback)
    </li>
    <li>
      <code>Text.First(null, @val1, @val2, @fallback)</code> 
      ⇒ @Text.First(null, val1, val2, fallback)
    </li>
    <li>
      <code>Text.First(null, @nbsp, @val1, @val2, @fallback)</code> 
      ⇒ @Text.First(null, nbsp, val1, val2, fallback)
    </li>
    <li>
      <code>Text.First(false, null, @nbsp, @val1, @val2, @fallback)</code> 
      ⇒ @Text.First(false, null, nbsp, val1, val2, fallback)
    </li>
    <li>
      <code>Text.First(null, null, @nbsp, @val1, @val2, "@spc", @fallback)</code> 
      ⇒ @Text.First(null, null, nbsp, val1, val2, spc, fallback)
    </li>
    <li>
      <code>Text.First(false, null, null, @nbsp, @val1, @val2, "@spc", @fallback)</code> 
      ⇒ @Text.First(false, null, null, nbsp, val1, val2, spc, fallback)
    </li>
  </ol>
Requirements
Resources

RazorBlade Text.Zip(...) v1.1

These demos show how to Zip (clean/compress) text properly, because Razor Blade handles a lot of issues you'll usually have cleaning up text. Scenarios might be:

  • Multi-line text
  • Cleane-up html, which may have more spaces and line-breaks than expected
  • Just any text pasted from somewhere, which could even contain surprise white-space

 The example texts which have invisible problem characters:

⬇️ Result | Source ➡️

  1. This        contains multi-spaces and ↦↦↦ tabs
  2. This has ↵  ↵ line-breaks
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var samples = new string[] {
    "This        contains multi-spaces and \t\t\t tabs",
    "This has \n  \n line-breaks"
  };
}

<ol>
  @foreach (var s in samples) {
    <li>
      <code>@Html.Raw(ShowHiddenCharacters(s))</code>
    </li>
  }
</ol>

<!-- unimportant stuff, hidden -->

Result

Html output hides the problems Whitespace output showing problems Length Output using Text.Zip(...) Zip Length
This contains multi-spaces and tabs This contains multi-spaces and tabs 46 This contains multi-spaces and tabs 35
This has line-breaks This has line-breaks 25 This has line-breaks 20
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var samples = new string[] {
    "This        contains multi-spaces and \t\t\t tabs",
    "This has \n  \n line-breaks"
  };
}

@{
    samples = new string[] {
    "This        contains multi-spaces and \t\t\t tabs",
    "This has \n  \n line-breaks"
  };
}
<table class="table table-hover" width="100%">
<!-- table header -->
<tr>
  <th>Html output hides the problems</th>
  <th class="table-warning">Whitespace output showing problems</th>
  <th>Length</th>
  <th class="table-success">Output using Text.Zip(...)</th>
  <th>Zip Length</th>
</tr>
<!-- the real code -->
@foreach (var s in samples) {
<tr>
  <td>@s </td>
  <td  class="table-warning" style="white-space: pre-wrap;">@s</td>
  <td>@s.Length </td>
  <td class="table-success" style="white-space: pre-wrap;">@Text.Zip(s)</td>
  <td>@Text.Zip(s).Length</td>
</tr>
  }
</table>

RazorBlade .After(), .AfterLast(), .Before(), .BeforeLast(), .Between()

For this to work please install RazorBlade 3.09 or 2sxc 13.02. These demos show how to split text properly. Scenarios might be:

Using Text.After(text, key) only the text after the first found occurence of the key will be shown.

⬇️ Result | Source ➡️

Result: this will be shown
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var afterExample = "This won't be shown @ this will be shown";
}
<strong>Result:</strong> @Text.After(afterExample, "@")

Using Text.AfterLast(text, key) only the text after the last found occurence of the key will be shown.

⬇️ Result | Source ➡️

Result: this will be shown
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var afterLastExample = "This won't be shown @ this won't be shown @ this will be shown";
}
<strong>Result:</strong> @Text.AfterLast(afterLastExample, "@")

Using Text.Before(text, key) only the text before the first found occurence of the key will be shown.

⬇️ Result | Source ➡️

Result: This will be shown
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var beforeExample = "This will be shown @ this won't be shown";
}
<strong>Result:</strong> @Text.Before(beforeExample, "@")

Using Text.BeforeLast(text, key) only the text before the last found occurence of the key will be shown.

⬇️ Result | Source ➡️

Result: This will be shown @ this will be shown
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var beforeLastExample = "This will be shown @ this will be shown @ this won't be shown";
}
<strong>Result:</strong> @Text.BeforeLast(beforeLastExample, "@")

Using Text.Between(text, key1, key2, goToEndIfEndNotFound = false) only the text between key1 and key2 will be shown. With goToEndIfEndNotFound set to true, the text selection will grow till the end if the ending key can't be found.

⬇️ Result | Source ➡️

Result: this will be shown
Result: this will be shown # this won't be shown
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var betweenExample = "This won't be shown @ this will be shown # this won't be shown";
}
<strong>Result:</strong> @Text.Between(betweenExample, "@", "#")
<br><strong>Result:</strong> @Text.Between(betweenExample, "@", "notInText", true)

RazorBlade Tags BR/NewLine Conversions v1.1

These demos show how to convert BR tags to spaces, New-Lines or New-Lines to BRs.

⬇️ Result | Source ➡️

This is... Shown as plain text Shown as HTML
Original This is a text. Second line. Third line.
Converting with Tags.Nl2Br(...) This is a text.
Second line.
Third line.
Convert the br back with Tags.Br2Nl This is a text. Second line. Third line.
Cleaning BR as Space with Tags.Br2Space This is a text. Second line. Third line.
@inherits Custom.Hybrid.Razor14
@using ToSic.Razor.Blade

@{
  var val1 = "This is a text.\nSecond line.\nThird line.";
  var val1br = Tags.Nl2Br(val1);
  var val1Back = Tags.Br2Nl(val1br);
  var val1Space = Tags.Br2Space(val1br);
}
<table class="table table-hover">
  <tr>
    <th class="w-25">This is...</th>
    <th class="w-33">Shown as plain text</th>
    <th class="w-33">Shown as HTML</th>
  </tr>
  <tr>
    <td>Original</td>
    <td><textarea rows="4">@val1</textarea></td>
    <td>@val1</td>
  </tr>
  <tr>
    <td>Converting with Tags.Nl2Br(...)</td>
    <td><textarea rows="4">@val1br</textarea></td>
    <td>@Html.Raw(val1br)</td>
  </tr>
  <tr>
    <td>Convert the br back with Tags.Br2Nl</td>
    <td><textarea rows="4">@val1Back</textarea></td>
    <td>@val1Back</td>
  </tr>
  <tr>
    <td>Cleaning BR as Space with Tags.Br2Space</td>
    <td><textarea rows="4">@val1Space</textarea></td>
    <td>@val1Space</td>
  </tr>
</table>

<!-- unimportant stuff, hidden -->