🔍 s&box Package Code Search
Search C# source code, UI razor templates, shaders, and configs across s&box packages.
🔗 Raw Facepunch API Link: https://public.facepunch.com/sbox/code/search/1/?ident=notathreat.crosshairbuilder&take=20
Showing code results for query:
*
(7 total matches found)
Editor
library
using Editor;
public static class MyEditorMenu
{
[Menu( "Editor", "CrosshairBuilder/My Menu Option" )]
public static void OpenMyMenu()
{
EditorUtility.DisplayDialog( "It worked!", "This is being called from your library's editor code!" );
}
}
Game
library
@using System;
@using Sandbox;
@using Sandbox.UI;
@inherits PanelComponent
<root>
<div class="crosshair" style="
position: absolute;
left: @( IsPercentage ? $"{Position.x}%" : Position.x );
top: @( IsPercentage ? $"{Position.y}%" : Position.y );
transform: translate(-50%, -50%);
">
<div class="center-dot-border-wrapper" style="
display: @(CenterDot ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
z-index: 100;
">
<div class="center-dot" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(CenterDotOpacity));
padding: @(CenterDotThickness)px;
"></div>
</div>
<div class="inner-top-border-wrapper" style="
position: absolute;
top: -@(InnerLinesOffset)px;
left: 50%;
transform: translateX(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line top" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-left: @(InnerLineThickness)px;
padding-top: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-bottom-border-wrapper" style="
position: absolute;
bottom: -@(InnerLinesOffset)px;
left: 50%;
transform: translateX(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line bottom" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-left: @(InnerLineThickness)px;
padding-bottom: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-left-border-wrapper" style="
position: absolute;
left: -@(InnerLinesOffset)px;
top: 50%;
transform: translateY(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line left" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-top: @(InnerLineThickness)px;
padding-left: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-right-border-wrapper" style="
position: absolute;
right: -@(InnerLinesOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line right" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-top: @(InnerLineThickness)px;
padding-right: @(InnerLineLenght)px;
"></div>
</div>
<div class="outer-top-border-wrapper" style="
position: absolute;
top: -@(OuterLineOffset)px;
left: 50%;
transform: translateX(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line top" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-left: @(OuterLineThickness)px;
padding-top: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-bottom-border-wrapper" style="
position: absolute;
bottom: -@(OuterLineOffset)px;
left: 50%;
transform: translateX(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line bottom" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-left: @(OuterLineThickness)px;
padding-bottom: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-left-border-wrapper" style="
position: absolute;
left: -@(OuterLineOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line left" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-top: @(OuterLineThickness)px;
padding-left: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-right-border-wrapper" style="
position: absolute;
right: -@(OuterLineOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line right" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-top: @(OuterLineThickness)px;
padding-right: @(OuterLineLenght)px;
"></div>
</div>
</div>
</root>
@code
{
// Position properties
[Property]
[Category("Position")] public bool IsPercentage { get; set; } = true;
[Property]
[Category("Position")] public Vector2 Position { get; set; } = new Vector2(50, 50);
// Crosshair properties
[Property]
[Category("Crosshair")] public Color Color { get; set; } = Color.FromRgb(0x2EFF00);
[Property]
[Category("Crosshair")] public bool Outline { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Crosshair")] public float OutlineOpacity { get; set; } = 1f;
[Property]
[Range(1, 10, 1)]
[Category("Crosshair")] public int OutlineThickness { get; set; } = 2;
[Property]
[Category("Crosshair")] public bool CenterDot { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Crosshair")] public float CenterDotOpacity { get; set; } = 1f;
[Property]
[Range(1, 10, 1)]
[Category("Crosshair")] public int CenterDotThickness { get; set; } = 1;
// Inner Lines properties
[Property]
[Category("Inner Lines")] public bool ShowInnerLines { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Inner Lines")] public float InnerLineOpacity { get; set; } = 1f;
[Property]
[Range(0, 20, 1)]
[Category("Inner Lines")] public int InnerLineLenght { get; set; } = 10;
[Property]
[Range(0, 10, 1)]
[Category("Inner Lines")] public int InnerLineThickness { get; set; } = 1;
[Property]
[Range(0, 20, 1)]
[Category("Inner Lines")] public int InnerLinesOffset { get; set; } = 2;
// Outer Lines properties
[Property]
[Category("Outer Lines")] public bool ShowOuterLines { get; set; } = false;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Outer Lines")] public float OuterLineOpacity { get; set; } = 0.5f;
[Property]
[Range(0, 20, 1)]
[Category("Outer Lines")] public int OuterLineLenght { get; set; }
[Property]
[Range(0, 10, 1)]
[Category("Outer Lines")] public int OuterLineThickness { get; set; }
[Property]
[Range(0, 20, 1)]
[Category("Outer Lines")] public int OuterLineOffset { get; set; }
// Code properties
[Property]
[Category("Code")] public string Code { get; set; }
// Member variables
private string _cachedCode = null;
public string EncodeCrosshairParameters()
{
// Convert boolean values to 1 or 0
string EncodeBool(bool value) => value ? "1" : "0";
// Convert float values to a shortened string representation (up to 2 decimal places)
string EncodeFloat(float value) => Math.Round(value, 2).ToString("0.##");
// Convert integers directly to string
string EncodeInt(int value) => value.ToString();
// Concatenate all parameters into a shortened format
var parameters = $"{EncodeBool(IsPercentage)}," +
$"{EncodeFloat(Position.x)},{EncodeFloat(Position.y)}," +
$"{EncodeFloat(Color.r)},{EncodeFloat(Color.g)},{EncodeFloat(Color.b)}," +
$"{EncodeBool(Outline)},{EncodeFloat(OutlineOpacity)},{EncodeInt(OutlineThickness)}," +
$"{EncodeBool(CenterDot)},{EncodeFloat(CenterDotOpacity)},{EncodeInt(CenterDotThickness)}," +
$"{EncodeBool(ShowInnerLines)},{EncodeFloat(InnerLineOpacity)},{EncodeInt(InnerLineLenght)}," +
$"{EncodeInt(InnerLineThickness)},{EncodeInt(InnerLinesOffset)}," +
$"{EncodeBool(ShowOuterLines)},{EncodeFloat(OuterLineOpacity)},{EncodeInt(OuterLineLenght)}," +
$"{EncodeInt(OuterLineThickness)},{EncodeInt(OuterLineOffset)}";
return parameters;
}
public void DecodeCrosshairParameters(string encodedString)
{
var parameters = encodedString.Split(',');
// Convert "1" or "0" back to boolean
bool DecodeBool(string value) => value == "1";
// Convert string back to float
float DecodeFloat(string value) => float.Parse(value);
// Convert string back to int
int DecodeInt(string value) => int.Parse(value);
// Assign the decoded values back to the properties
IsPercentage = DecodeBool(parameters[0]);
Position = new Vector2(DecodeFloat(parameters[1]), DecodeFloat(parameters[2]));
Color = new Color(DecodeFloat(parameters[3]), DecodeFloat(parameters[4]), DecodeFloat(parameters[5]));
Outline = DecodeBool(parameters[6]);
OutlineOpacity = DecodeFloat(parameters[7]);
OutlineThickness = DecodeInt(parameters[8]);
CenterDot = DecodeBool(parameters[9]);
CenterDotOpacity = DecodeFloat(parameters[10]);
CenterDotThickness = DecodeInt(parameters[11]);
ShowInnerLines = DecodeBool(parameters[12]);
InnerLineOpacity = DecodeFloat(parameters[13]);
InnerLineLenght = DecodeInt(parameters[14]);
InnerLineThickness = DecodeInt(parameters[15]);
InnerLinesOffset = DecodeInt(parameters[16]);
ShowOuterLines = DecodeBool(parameters[17]);
OuterLineOpacity = DecodeFloat(parameters[18]);
OuterLineLenght = DecodeInt(parameters[19]);
OuterLineThickness = DecodeInt(parameters[20]);
OuterLineOffset = DecodeInt(parameters[21]);
}
protected override void OnStart()
{
if (Code == null)
{
Code = EncodeCrosshairParameters();
}
DecodeCrosshairParameters(Code);
_cachedCode = Code;
}
protected override void OnUpdate()
{
if (Code != _cachedCode)
{
DecodeCrosshairParameters(Code);
}
Code = EncodeCrosshairParameters();
_cachedCode = Code;
}
/// <summary>
/// the hash determines if the system should be rebuilt. If it changes, it will be rebuilt
/// </summary>
protected override int BuildHash()
{
var positionHash = System.HashCode.Combine(
IsPercentage,
Position
);
var crosshairHash = System.HashCode.Combine(
Color,
Outline,
OutlineOpacity,
OutlineThickness,
CenterDot,
CenterDotOpacity,
CenterDotThickness
);
var innerLinesHash = System.HashCode.Combine(
ShowInnerLines,
InnerLineOpacity,
InnerLineLenght,
InnerLineThickness,
InnerLinesOffset
);
var outerLinesHash = System.HashCode.Combine(
ShowOuterLines,
OuterLineOpacity,
OuterLineLenght,
OuterLineThickness,
OuterLineOffset
);
var codeHash = Code.GetHashCode();
return System.HashCode.Combine(
positionHash,
crosshairHash,
innerLinesHash,
outerLinesHash,
codeHash
);
}
}
Game
library
@using System;
@using Sandbox;
@using Sandbox.UI;
@inherits PanelComponent
<root>
<div class="crosshair" style="
position: absolute;
left: @( IsPercentage ? $"{Position.x}%" : Position.x );
top: @( IsPercentage ? $"{Position.y}%" : Position.y );
transform: translate(-50%, -50%);
">
<div class="center-dot-border-wrapper" style="
display: @(CenterDot ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
z-index: 100;
">
<div class="center-dot" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(CenterDotOpacity));
padding: @(CenterDotThickness)px;
"></div>
</div>
<div class="inner-top-border-wrapper" style="
position: absolute;
top: -@(InnerLinesOffset)px;
left: 50%;
transform: translateX(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line top" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-left: @(InnerLineThickness)px;
padding-top: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-bottom-border-wrapper" style="
position: absolute;
bottom: -@(InnerLinesOffset)px;
left: 50%;
transform: translateX(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line bottom" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-left: @(InnerLineThickness)px;
padding-bottom: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-left-border-wrapper" style="
position: absolute;
left: -@(InnerLinesOffset)px;
top: 50%;
transform: translateY(-50%);
display:@(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line left" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-top: @(InnerLineThickness)px;
padding-left: @(InnerLineLenght)px;
"></div>
</div>
<div class="inner-right-border-wrapper" style="
position: absolute;
right: -@(InnerLinesOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowInnerLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="inner-line right" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));
padding-top: @(InnerLineThickness)px;
padding-right: @(InnerLineLenght)px;
"></div>
</div>
<div class="outer-top-border-wrapper" style="
position: absolute;
top: -@(OuterLineOffset)px;
left: 50%;
transform: translateX(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line top" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-left: @(OuterLineThickness)px;
padding-top: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-bottom-border-wrapper" style="
position: absolute;
bottom: -@(OuterLineOffset)px;
left: 50%;
transform: translateX(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line bottom" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-left: @(OuterLineThickness)px;
padding-bottom: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-left-border-wrapper" style="
position: absolute;
left: -@(OuterLineOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line left" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-top: @(OuterLineThickness)px;
padding-left: @(OuterLineLenght)px;
"></div>
</div>
<div class="outer-right-border-wrapper" style="
position: absolute;
right: -@(OuterLineOffset)px;
top: 50%;
transform: translateY(-50%);
display: @(ShowOuterLines ? "flex" : "none");
border: @(Outline ? $"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})" : "none");
">
<div class="outer-line right" style="
background-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));
padding-top: @(OuterLineThickness)px;
padding-right: @(OuterLineLenght)px;
"></div>
</div>
</div>
</root>
@code
{
// Position properties
[Property]
[Category("Position")] public bool IsPercentage { get; set; } = true;
[Property]
[Category("Position")] public Vector2 Position { get; set; } = new Vector2(50, 50);
// Crosshair properties
[Property]
[Category("Crosshair")] public Color Color { get; set; } = Color.FromRgb(0x2EFF00);
[Property]
[Category("Crosshair")] public bool Outline { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Crosshair")] public float OutlineOpacity { get; set; } = 1f;
[Property]
[Range(1, 10, 1)]
[Category("Crosshair")] public int OutlineThickness { get; set; } = 2;
[Property]
[Category("Crosshair")] public bool CenterDot { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Crosshair")] public float CenterDotOpacity { get; set; } = 1f;
[Property]
[Range(1, 10, 1)]
[Category("Crosshair")] public int CenterDotThickness { get; set; } = 1;
// Inner Lines properties
[Property]
[Category("Inner Lines")] public bool ShowInnerLines { get; set; } = true;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Inner Lines")] public float InnerLineOpacity { get; set; } = 1f;
[Property]
[Range(0, 20, 1)]
[Category("Inner Lines")] public int InnerLineLenght { get; set; } = 10;
[Property]
[Range(0, 10, 1)]
[Category("Inner Lines")] public int InnerLineThickness { get; set; } = 1;
[Property]
[Range(0, 20, 1)]
[Category("Inner Lines")] public int InnerLinesOffset { get; set; } = 2;
// Outer Lines properties
[Property]
[Category("Outer Lines")] public bool ShowOuterLines { get; set; } = false;
[Property]
[Range(0f, 1f, 0.001f)]
[Category("Outer Lines")] public float OuterLineOpacity { get; set; } = 0.5f;
[Property]
[Range(0, 20, 1)]
[Category("Outer Lines")] public int OuterLineLenght { get; set; }
[Property]
[Range(0, 10, 1)]
[Category("Outer Lines")] public int OuterLineThickness { get; set; }
[Property]
[Range(0, 20, 1)]
[Category("Outer Lines")] public int OuterLineOffset { get; set; }
// Code properties
[Property]
[Category("Code")] public string Code { get; set; }
// Member variables
private string _cachedCode = null;
public string EncodeCrosshairParameters()
{
// Convert boolean values to 1 or 0
string EncodeBool(bool value) => value ? "1" : "0";
// Convert float values to a shortened string representation (up to 2 decimal places)
string EncodeFloat(float value) => Math.Round(value, 2).ToString("0.##");
// Convert integers directly to string
string EncodeInt(int value) => value.ToString();
// Concatenate all parameters into a shortened format
var parameters = $"{EncodeBool(IsPercentage)}," +
$"{EncodeFloat(Position.x)},{EncodeFloat(Position.y)}," +
$"{EncodeFloat(Color.r)},{EncodeFloat(Color.g)},{EncodeFloat(Color.b)}," +
$"{EncodeBool(Outline)},{EncodeFloat(OutlineOpacity)},{EncodeInt(OutlineThickness)}," +
$"{EncodeBool(CenterDot)},{EncodeFloat(CenterDotOpacity)},{EncodeInt(CenterDotThickness)}," +
$"{EncodeBool(ShowInnerLines)},{EncodeFloat(InnerLineOpacity)},{EncodeInt(InnerLineLenght)}," +
$"{EncodeInt(InnerLineThickness)},{EncodeInt(InnerLinesOffset)}," +
$"{EncodeBool(ShowOuterLines)},{EncodeFloat(OuterLineOpacity)},{EncodeInt(OuterLineLenght)}," +
$"{EncodeInt(OuterLineThickness)},{EncodeInt(OuterLineOffset)}";
return parameters;
}
public void DecodeCrosshairParameters(string encodedString)
{
var parameters = encodedString.Split(',');
// Convert "1" or "0" back to boolean
bool DecodeBool(string value) => value == "1";
// Convert string back to float
float DecodeFloat(string value) => float.Parse(value);
// Convert string back to int
int DecodeInt(string value) => int.Parse(value);
// Assign the decoded values back to the properties
IsPercentage = DecodeBool(parameters[0]);
Position = new Vector2(DecodeFloat(parameters[1]), DecodeFloat(parameters[2]));
Color = new Color(DecodeFloat(parameters[3]), DecodeFloat(parameters[4]), DecodeFloat(parameters[5]));
Outline = DecodeBool(parameters[6]);
OutlineOpacity = DecodeFloat(parameters[7]);
OutlineThickness = DecodeInt(parameters[8]);
CenterDot = DecodeBool(parameters[9]);
CenterDotOpacity = DecodeFloat(parameters[10]);
CenterDotThickness = DecodeInt(parameters[11]);
ShowInnerLines = DecodeBool(parameters[12]);
InnerLineOpacity = DecodeFloat(parameters[13]);
InnerLineLenght = DecodeInt(parameters[14]);
InnerLineThickness = DecodeInt(parameters[15]);
InnerLinesOffset = DecodeInt(parameters[16]);
ShowOuterLines = DecodeBool(parameters[17]);
OuterLineOpacity = DecodeFloat(parameters[18]);
OuterLineLenght = DecodeInt(parameters[19]);
OuterLineThickness = DecodeInt(parameters[20]);
OuterLineOffset = DecodeInt(parameters[21]);
}
protected override void OnStart()
{
if (Code == null)
{
Code = EncodeCrosshairParameters();
}
DecodeCrosshairParameters(Code);
_cachedCode = Code;
}
protected override void OnUpdate()
{
if (Code != _cachedCode)
{
DecodeCrosshairParameters(Code);
}
Code = EncodeCrosshairParameters();
_cachedCode = Code;
}
/// <summary>
/// the hash determines if the system should be rebuilt. If it changes, it will be rebuilt
/// </summary>
protected override int BuildHash()
{
var positionHash = System.HashCode.Combine(
IsPercentage,
Position
);
var crosshairHash = System.HashCode.Combine(
Color,
Outline,
OutlineOpacity,
OutlineThickness,
CenterDot,
CenterDotOpacity,
CenterDotThickness
);
var innerLinesHash = System.HashCode.Combine(
ShowInnerLines,
InnerLineOpacity,
InnerLineLenght,
InnerLineThickness,
InnerLinesOffset
);
var outerLinesHash = System.HashCode.Combine(
ShowOuterLines,
OuterLineOpacity,
OuterLineLenght,
OuterLineThickness,
OuterLineOffset
);
var codeHash = Code.GetHashCode();
return System.HashCode.Combine(
positionHash,
crosshairHash,
innerLinesHash,
outerLinesHash,
codeHash
);
}
}
UnitTest
library
using Sandbox;
[TestClass]
public partial class LibraryTests
{
[TestMethod]
public void SceneTest()
{
var scene = new Scene();
using ( scene.Push() )
{
var go = new GameObject();
Assert.AreEqual( 1, scene.Directory.GameObjectCount );
}
}
}
Game
library
global using Microsoft.AspNetCore.Components; global using Microsoft.AspNetCore.Components.Rendering;
Game
library
global using static Sandbox.Internal.GlobalGameNamespace;
[assembly: global::System.Reflection.AssemblyMetadata( "AddonTitle", "CrosshairBuilder" )]
[assembly: global::System.Reflection.AssemblyMetadata( "AddonIdent", "crosshairbuilder" )]
[assembly: global::System.Reflection.AssemblyMetadata( "OrgIdent", "notathreat" )]
[assembly: global::System.Reflection.AssemblyMetadata( "Ident", "notathreat.crosshairbuilder" )]
[assembly: global::System.Reflection.AssemblyMetadata( "CompileTime", "8/19/2024 3:47:41 PM" )]
[assembly: global::System.Reflection.AssemblyMetadata( "EngineVersion", "17" )]
[assembly: global::System.Reflection.AssemblyMetadata( "EngineMinorVersion", "1" )]
[assembly: System.Runtime.Versioning.TargetFramework( ".NETCoreApp,Version=v7.0", FrameworkDisplayName = ".NET 7.0" )]
[assembly: global::System.Reflection.AssemblyVersion("0.0.121.0")]
[assembly: global::System.Reflection.AssemblyFileVersion("0.0.121.0")]
UnitTest
library
global using Microsoft.VisualStudio.TestTools.UnitTesting;
[TestClass]
public class TestInit
{
[AssemblyInitialize]
public static void ClassInitialize( TestContext context )
{
Sandbox.Application.InitUnitTest();
}
}
Debug: View Raw JSON Response
{
"TotalCount": 7,
"Files": [
{
"Ident": "notathreat.crosshairbuilder",
"Path": "Editor/MyEditorMenu.cs",
"FileName": "MyEditorMenu.cs",
"PackageType": "library",
"CodeKind": "Editor",
"AssetVersionId": 67301,
"Code": "using Editor;\r\n\r\npublic static class MyEditorMenu\r\n{\r\n\t[Menu( \"Editor\", \"CrosshairBuilder/My Menu Option\" )]\r\n\tpublic static void OpenMyMenu()\r\n\t{\r\n\t\tEditorUtility.DisplayDialog( \"It worked!\", \"This is being called from your library's editor code!\" );\r\n\t}\r\n}\r\n"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": "Code/CrosshairBuilder.razor",
"FileName": "CrosshairBuilder.razor",
"PackageType": "library",
"CodeKind": "Game",
"AssetVersionId": 67301,
"Code": "@using System;\r\n@using Sandbox;\r\n@using Sandbox.UI;\r\n@inherits PanelComponent\r\n\r\n<root>\r\n <div class=\"crosshair\" style=\"\r\n\t\tposition: absolute;\r\n\t\tleft: @( IsPercentage ? $\"{Position.x}%\" : Position.x );\r\n\t\ttop: @( IsPercentage ? $\"{Position.y}%\" : Position.y );\r\n\t\ttransform: translate(-50%, -50%);\r\n\t\">\r\n\t\t<div class=\"center-dot-border-wrapper\" style=\"\r\n\t\t\tdisplay: @(CenterDot ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\tz-index: 100;\r\n\t\t\">\r\n\t\t\t<div class=\"center-dot\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(CenterDotOpacity));\r\n\t\t\t\tpadding: @(CenterDotThickness)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-top-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n \t\ttop: -@(InnerLinesOffset)px;\r\n \t\tleft: 50%;\r\n \t\ttransform: translateX(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line top\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-left: @(InnerLineThickness)px;\r\n \t\t\tpadding-top: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-bottom-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n \t\tbottom: -@(InnerLinesOffset)px;\r\n \t\tleft: 50%;\r\n \t\ttransform: translateX(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line bottom\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-left: @(InnerLineThickness)px;\r\n \t\t\tpadding-bottom: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-left-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tleft: -@(InnerLinesOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line left\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-top: @(InnerLineThickness)px;\r\n\t\t\t\tpadding-left: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-right-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tright: -@(InnerLinesOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line right\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-top: @(InnerLineThickness)px;\r\n\t\t\t\tpadding-right: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-top-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\ttop: -@(OuterLineOffset)px;\r\n\t\t\tleft: 50%;\r\n\t\t\ttransform: translateX(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line top\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-left: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-top: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-bottom-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tbottom: -@(OuterLineOffset)px;\r\n\t\t\tleft: 50%;\r\n\t\t\ttransform: translateX(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line bottom\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-left: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-bottom: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-left-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tleft: -@(OuterLineOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line left\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-top: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-left: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-right-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tright: -@(OuterLineOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line right\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-top: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-right: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n </div>\r\n</root>\r\n\r\n@code\r\n{\r\n\t// Position properties\r\n\t[Property] \r\n\t[Category(\"Position\")] public bool IsPercentage { get; set; } = true;\r\n\t[Property]\r\n\t[Category(\"Position\")] public Vector2 Position { get; set; } = new Vector2(50, 50);\r\n\r\n\t// Crosshair properties\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public Color Color { get; set; } = Color.FromRgb(0x2EFF00);\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public bool Outline { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Crosshair\")] public float OutlineOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(1, 10, 1)]\r\n\t[Category(\"Crosshair\")] public int OutlineThickness { get; set; } = 2;\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public bool CenterDot { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Crosshair\")] public float CenterDotOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(1, 10, 1)]\r\n\t[Category(\"Crosshair\")] public int CenterDotThickness { get; set; } = 1;\r\n\r\n\t// Inner Lines properties\r\n\t[Property]\r\n\t[Category(\"Inner Lines\")] public bool ShowInnerLines { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Inner Lines\")] public float InnerLineOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLineLenght { get; set; } = 10;\r\n\t[Property]\r\n\t[Range(0, 10, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLineThickness { get; set; } = 1;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLinesOffset { get; set; } = 2;\r\n\r\n\t// Outer Lines properties\r\n\t[Property]\r\n\t[Category(\"Outer Lines\")] public bool ShowOuterLines { get; set; } = false;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Outer Lines\")] public float OuterLineOpacity { get; set; } = 0.5f;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineLenght { get; set; }\r\n\t[Property]\r\n\t[Range(0, 10, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineThickness { get; set; }\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineOffset { get; set; }\r\n\r\n\t// Code properties\r\n\t[Property]\r\n\t[Category(\"Code\")] public string Code { get; set; }\r\n\r\n\t// Member variables\r\n\tprivate string _cachedCode = null;\r\n\r\n\tpublic string EncodeCrosshairParameters()\r\n\t{\r\n\t\t// Convert boolean values to 1 or 0\r\n\t\tstring EncodeBool(bool value) => value ? \"1\" : \"0\";\r\n\t\t// Convert float values to a shortened string representation (up to 2 decimal places)\r\n\t\tstring EncodeFloat(float value) => Math.Round(value, 2).ToString(\"0.##\");\r\n\t\t// Convert integers directly to string\r\n\t\tstring EncodeInt(int value) => value.ToString();\r\n\r\n\t\t// Concatenate all parameters into a shortened format\r\n\t\tvar parameters = $\"{EncodeBool(IsPercentage)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeFloat(Position.x)},{EncodeFloat(Position.y)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeFloat(Color.r)},{EncodeFloat(Color.g)},{EncodeFloat(Color.b)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(Outline)},{EncodeFloat(OutlineOpacity)},{EncodeInt(OutlineThickness)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(CenterDot)},{EncodeFloat(CenterDotOpacity)},{EncodeInt(CenterDotThickness)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(ShowInnerLines)},{EncodeFloat(InnerLineOpacity)},{EncodeInt(InnerLineLenght)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeInt(InnerLineThickness)},{EncodeInt(InnerLinesOffset)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(ShowOuterLines)},{EncodeFloat(OuterLineOpacity)},{EncodeInt(OuterLineLenght)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeInt(OuterLineThickness)},{EncodeInt(OuterLineOffset)}\";\r\n\t\treturn parameters;\r\n\t}\r\n\r\n\tpublic void DecodeCrosshairParameters(string encodedString)\r\n\t{\r\n\t\tvar parameters = encodedString.Split(',');\r\n\r\n\t\t// Convert \"1\" or \"0\" back to boolean\r\n\t\tbool DecodeBool(string value) => value == \"1\";\r\n\t\t// Convert string back to float\r\n\t\tfloat DecodeFloat(string value) => float.Parse(value);\r\n\t\t// Convert string back to int\r\n\t\tint DecodeInt(string value) => int.Parse(value);\r\n\r\n\t\t// Assign the decoded values back to the properties\r\n\t\tIsPercentage = DecodeBool(parameters[0]);\r\n\t\tPosition = new Vector2(DecodeFloat(parameters[1]), DecodeFloat(parameters[2]));\r\n\t\tColor = new Color(DecodeFloat(parameters[3]), DecodeFloat(parameters[4]), DecodeFloat(parameters[5]));\r\n\t\tOutline = DecodeBool(parameters[6]);\r\n\t\tOutlineOpacity = DecodeFloat(parameters[7]);\r\n\t\tOutlineThickness = DecodeInt(parameters[8]);\r\n\t\tCenterDot = DecodeBool(parameters[9]);\r\n\t\tCenterDotOpacity = DecodeFloat(parameters[10]);\r\n\t\tCenterDotThickness = DecodeInt(parameters[11]);\r\n\t\tShowInnerLines = DecodeBool(parameters[12]);\r\n\t\tInnerLineOpacity = DecodeFloat(parameters[13]);\r\n\t\tInnerLineLenght = DecodeInt(parameters[14]);\r\n\t\tInnerLineThickness = DecodeInt(parameters[15]);\r\n\t\tInnerLinesOffset = DecodeInt(parameters[16]);\r\n\t\tShowOuterLines = DecodeBool(parameters[17]);\r\n\t\tOuterLineOpacity = DecodeFloat(parameters[18]);\r\n\t\tOuterLineLenght = DecodeInt(parameters[19]);\r\n\t\tOuterLineThickness = DecodeInt(parameters[20]);\r\n\t\tOuterLineOffset = DecodeInt(parameters[21]);\r\n\t}\r\n\r\n\tprotected override void OnStart()\r\n\t{\r\n\t\tif (Code == null)\r\n\t\t{\r\n\t\t\tCode = EncodeCrosshairParameters();\r\n\t\t}\r\n\t\tDecodeCrosshairParameters(Code);\r\n\t\t_cachedCode = Code;\r\n\t}\r\n\r\n\tprotected override void OnUpdate()\r\n\t{\r\n\t\tif (Code != _cachedCode)\r\n\t\t{\r\n\t\t\tDecodeCrosshairParameters(Code);\r\n\t\t}\r\n\t\tCode = EncodeCrosshairParameters();\r\n\t\t_cachedCode = Code;\r\n\t}\r\n\r\n\t/// <summary>\r\n\t/// the hash determines if the system should be rebuilt. If it changes, it will be rebuilt\r\n\t/// </summary>\r\n\tprotected override int BuildHash()\r\n\t{\r\n\t\tvar positionHash = System.HashCode.Combine( \r\n\t\t\tIsPercentage,\r\n\t\t\tPosition\r\n\t\t);\r\n\r\n\t\tvar crosshairHash = System.HashCode.Combine( \r\n\t\t\tColor,\r\n\t\t\tOutline,\r\n\t\t\tOutlineOpacity,\r\n\t\t\tOutlineThickness,\r\n\t\t\tCenterDot,\r\n\t\t\tCenterDotOpacity,\r\n\t\t\tCenterDotThickness\r\n\t\t);\r\n\r\n\t\tvar innerLinesHash = System.HashCode.Combine(\r\n\t\t\tShowInnerLines,\r\n\t\t\tInnerLineOpacity,\r\n\t\t\tInnerLineLenght,\r\n\t\t\tInnerLineThickness,\r\n\t\t\tInnerLinesOffset\r\n\t\t);\r\n\r\n\t\tvar outerLinesHash = System.HashCode.Combine(\r\n\t\t\tShowOuterLines,\r\n\t\t\tOuterLineOpacity,\r\n\t\t\tOuterLineLenght,\r\n\t\t\tOuterLineThickness,\r\n\t\t\tOuterLineOffset\r\n\t\t);\r\n\r\n\t\tvar codeHash = Code.GetHashCode();\r\n\t\t\r\n\t\treturn System.HashCode.Combine(\r\n\t\t\tpositionHash,\r\n\t\t\tcrosshairHash,\r\n\t\t\tinnerLinesHash,\r\n\t\t\touterLinesHash,\r\n\t\t\tcodeHash\r\n\t\t);\r\n\t}\r\n}\r\n"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": "CrosshairBuilder.razor",
"FileName": "CrosshairBuilder.razor",
"PackageType": "library",
"CodeKind": "Game",
"AssetVersionId": 67301,
"Code": "@using System;\r\n@using Sandbox;\r\n@using Sandbox.UI;\r\n@inherits PanelComponent\r\n\r\n<root>\r\n <div class=\"crosshair\" style=\"\r\n\t\tposition: absolute;\r\n\t\tleft: @( IsPercentage ? $\"{Position.x}%\" : Position.x );\r\n\t\ttop: @( IsPercentage ? $\"{Position.y}%\" : Position.y );\r\n\t\ttransform: translate(-50%, -50%);\r\n\t\">\r\n\t\t<div class=\"center-dot-border-wrapper\" style=\"\r\n\t\t\tdisplay: @(CenterDot ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\tz-index: 100;\r\n\t\t\">\r\n\t\t\t<div class=\"center-dot\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(CenterDotOpacity));\r\n\t\t\t\tpadding: @(CenterDotThickness)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-top-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n \t\ttop: -@(InnerLinesOffset)px;\r\n \t\tleft: 50%;\r\n \t\ttransform: translateX(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line top\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-left: @(InnerLineThickness)px;\r\n \t\t\tpadding-top: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-bottom-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n \t\tbottom: -@(InnerLinesOffset)px;\r\n \t\tleft: 50%;\r\n \t\ttransform: translateX(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line bottom\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-left: @(InnerLineThickness)px;\r\n \t\t\tpadding-bottom: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-left-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tleft: -@(InnerLinesOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay:@(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line left\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-top: @(InnerLineThickness)px;\r\n\t\t\t\tpadding-left: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"inner-right-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tright: -@(InnerLinesOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowInnerLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"inner-line right\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(InnerLineOpacity));\r\n\t\t\t\tpadding-top: @(InnerLineThickness)px;\r\n\t\t\t\tpadding-right: @(InnerLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-top-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\ttop: -@(OuterLineOffset)px;\r\n\t\t\tleft: 50%;\r\n\t\t\ttransform: translateX(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line top\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-left: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-top: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-bottom-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tbottom: -@(OuterLineOffset)px;\r\n\t\t\tleft: 50%;\r\n\t\t\ttransform: translateX(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line bottom\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-left: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-bottom: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-left-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tleft: -@(OuterLineOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line left\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-top: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-left: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n\t\t<div class=\"outer-right-border-wrapper\" style=\"\r\n\t\t\tposition: absolute;\r\n\t\t\tright: -@(OuterLineOffset)px;\r\n\t\t\ttop: 50%;\r\n\t\t\ttransform: translateY(-50%);\r\n\t\t\tdisplay: @(ShowOuterLines ? \"flex\" : \"none\");\r\n\t\t\tborder: @(Outline ? $\"{OutlineThickness}px solid rgba(0, 0, 0, {OutlineOpacity})\" : \"none\");\r\n\t\t\">\r\n\t\t\t<div class=\"outer-line right\" style=\"\r\n\t\t\t\tbackground-color: rgba(@(Color.r * 255), @(Color.g * 255), @(Color.b * 255), @(OuterLineOpacity));\r\n\t\t\t\tpadding-top: @(OuterLineThickness)px;\r\n\t\t\t\tpadding-right: @(OuterLineLenght)px;\r\n\t\t\t\"></div>\r\n\t\t</div>\r\n </div>\r\n</root>\r\n\r\n@code\r\n{\r\n\t// Position properties\r\n\t[Property] \r\n\t[Category(\"Position\")] public bool IsPercentage { get; set; } = true;\r\n\t[Property]\r\n\t[Category(\"Position\")] public Vector2 Position { get; set; } = new Vector2(50, 50);\r\n\r\n\t// Crosshair properties\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public Color Color { get; set; } = Color.FromRgb(0x2EFF00);\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public bool Outline { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Crosshair\")] public float OutlineOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(1, 10, 1)]\r\n\t[Category(\"Crosshair\")] public int OutlineThickness { get; set; } = 2;\r\n\t[Property]\r\n\t[Category(\"Crosshair\")] public bool CenterDot { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Crosshair\")] public float CenterDotOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(1, 10, 1)]\r\n\t[Category(\"Crosshair\")] public int CenterDotThickness { get; set; } = 1;\r\n\r\n\t// Inner Lines properties\r\n\t[Property]\r\n\t[Category(\"Inner Lines\")] public bool ShowInnerLines { get; set; } = true;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Inner Lines\")] public float InnerLineOpacity { get; set; } = 1f;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLineLenght { get; set; } = 10;\r\n\t[Property]\r\n\t[Range(0, 10, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLineThickness { get; set; } = 1;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Inner Lines\")] public int InnerLinesOffset { get; set; } = 2;\r\n\r\n\t// Outer Lines properties\r\n\t[Property]\r\n\t[Category(\"Outer Lines\")] public bool ShowOuterLines { get; set; } = false;\r\n\t[Property]\r\n\t[Range(0f, 1f, 0.001f)]\r\n\t[Category(\"Outer Lines\")] public float OuterLineOpacity { get; set; } = 0.5f;\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineLenght { get; set; }\r\n\t[Property]\r\n\t[Range(0, 10, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineThickness { get; set; }\r\n\t[Property]\r\n\t[Range(0, 20, 1)]\r\n\t[Category(\"Outer Lines\")] public int OuterLineOffset { get; set; }\r\n\r\n\t// Code properties\r\n\t[Property]\r\n\t[Category(\"Code\")] public string Code { get; set; }\r\n\r\n\t// Member variables\r\n\tprivate string _cachedCode = null;\r\n\r\n\tpublic string EncodeCrosshairParameters()\r\n\t{\r\n\t\t// Convert boolean values to 1 or 0\r\n\t\tstring EncodeBool(bool value) => value ? \"1\" : \"0\";\r\n\t\t// Convert float values to a shortened string representation (up to 2 decimal places)\r\n\t\tstring EncodeFloat(float value) => Math.Round(value, 2).ToString(\"0.##\");\r\n\t\t// Convert integers directly to string\r\n\t\tstring EncodeInt(int value) => value.ToString();\r\n\r\n\t\t// Concatenate all parameters into a shortened format\r\n\t\tvar parameters = $\"{EncodeBool(IsPercentage)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeFloat(Position.x)},{EncodeFloat(Position.y)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeFloat(Color.r)},{EncodeFloat(Color.g)},{EncodeFloat(Color.b)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(Outline)},{EncodeFloat(OutlineOpacity)},{EncodeInt(OutlineThickness)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(CenterDot)},{EncodeFloat(CenterDotOpacity)},{EncodeInt(CenterDotThickness)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(ShowInnerLines)},{EncodeFloat(InnerLineOpacity)},{EncodeInt(InnerLineLenght)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeInt(InnerLineThickness)},{EncodeInt(InnerLinesOffset)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeBool(ShowOuterLines)},{EncodeFloat(OuterLineOpacity)},{EncodeInt(OuterLineLenght)},\" +\r\n\t\t\t\t\t\t\t$\"{EncodeInt(OuterLineThickness)},{EncodeInt(OuterLineOffset)}\";\r\n\t\treturn parameters;\r\n\t}\r\n\r\n\tpublic void DecodeCrosshairParameters(string encodedString)\r\n\t{\r\n\t\tvar parameters = encodedString.Split(',');\r\n\r\n\t\t// Convert \"1\" or \"0\" back to boolean\r\n\t\tbool DecodeBool(string value) => value == \"1\";\r\n\t\t// Convert string back to float\r\n\t\tfloat DecodeFloat(string value) => float.Parse(value);\r\n\t\t// Convert string back to int\r\n\t\tint DecodeInt(string value) => int.Parse(value);\r\n\r\n\t\t// Assign the decoded values back to the properties\r\n\t\tIsPercentage = DecodeBool(parameters[0]);\r\n\t\tPosition = new Vector2(DecodeFloat(parameters[1]), DecodeFloat(parameters[2]));\r\n\t\tColor = new Color(DecodeFloat(parameters[3]), DecodeFloat(parameters[4]), DecodeFloat(parameters[5]));\r\n\t\tOutline = DecodeBool(parameters[6]);\r\n\t\tOutlineOpacity = DecodeFloat(parameters[7]);\r\n\t\tOutlineThickness = DecodeInt(parameters[8]);\r\n\t\tCenterDot = DecodeBool(parameters[9]);\r\n\t\tCenterDotOpacity = DecodeFloat(parameters[10]);\r\n\t\tCenterDotThickness = DecodeInt(parameters[11]);\r\n\t\tShowInnerLines = DecodeBool(parameters[12]);\r\n\t\tInnerLineOpacity = DecodeFloat(parameters[13]);\r\n\t\tInnerLineLenght = DecodeInt(parameters[14]);\r\n\t\tInnerLineThickness = DecodeInt(parameters[15]);\r\n\t\tInnerLinesOffset = DecodeInt(parameters[16]);\r\n\t\tShowOuterLines = DecodeBool(parameters[17]);\r\n\t\tOuterLineOpacity = DecodeFloat(parameters[18]);\r\n\t\tOuterLineLenght = DecodeInt(parameters[19]);\r\n\t\tOuterLineThickness = DecodeInt(parameters[20]);\r\n\t\tOuterLineOffset = DecodeInt(parameters[21]);\r\n\t}\r\n\r\n\tprotected override void OnStart()\r\n\t{\r\n\t\tif (Code == null)\r\n\t\t{\r\n\t\t\tCode = EncodeCrosshairParameters();\r\n\t\t}\r\n\t\tDecodeCrosshairParameters(Code);\r\n\t\t_cachedCode = Code;\r\n\t}\r\n\r\n\tprotected override void OnUpdate()\r\n\t{\r\n\t\tif (Code != _cachedCode)\r\n\t\t{\r\n\t\t\tDecodeCrosshairParameters(Code);\r\n\t\t}\r\n\t\tCode = EncodeCrosshairParameters();\r\n\t\t_cachedCode = Code;\r\n\t}\r\n\r\n\t/// <summary>\r\n\t/// the hash determines if the system should be rebuilt. If it changes, it will be rebuilt\r\n\t/// </summary>\r\n\tprotected override int BuildHash()\r\n\t{\r\n\t\tvar positionHash = System.HashCode.Combine( \r\n\t\t\tIsPercentage,\r\n\t\t\tPosition\r\n\t\t);\r\n\r\n\t\tvar crosshairHash = System.HashCode.Combine( \r\n\t\t\tColor,\r\n\t\t\tOutline,\r\n\t\t\tOutlineOpacity,\r\n\t\t\tOutlineThickness,\r\n\t\t\tCenterDot,\r\n\t\t\tCenterDotOpacity,\r\n\t\t\tCenterDotThickness\r\n\t\t);\r\n\r\n\t\tvar innerLinesHash = System.HashCode.Combine(\r\n\t\t\tShowInnerLines,\r\n\t\t\tInnerLineOpacity,\r\n\t\t\tInnerLineLenght,\r\n\t\t\tInnerLineThickness,\r\n\t\t\tInnerLinesOffset\r\n\t\t);\r\n\r\n\t\tvar outerLinesHash = System.HashCode.Combine(\r\n\t\t\tShowOuterLines,\r\n\t\t\tOuterLineOpacity,\r\n\t\t\tOuterLineLenght,\r\n\t\t\tOuterLineThickness,\r\n\t\t\tOuterLineOffset\r\n\t\t);\r\n\r\n\t\tvar codeHash = Code.GetHashCode();\r\n\t\t\r\n\t\treturn System.HashCode.Combine(\r\n\t\t\tpositionHash,\r\n\t\t\tcrosshairHash,\r\n\t\t\tinnerLinesHash,\r\n\t\t\touterLinesHash,\r\n\t\t\tcodeHash\r\n\t\t);\r\n\t}\r\n}\r\n"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": "UnitTests/LibraryTest.cs",
"FileName": "LibraryTest.cs",
"PackageType": "library",
"CodeKind": "UnitTest",
"AssetVersionId": 67301,
"Code": "using Sandbox;\r\n\r\n[TestClass]\r\npublic partial class LibraryTests\r\n{\r\n\t[TestMethod]\r\n\tpublic void SceneTest()\r\n\t{\r\n\t\tvar scene = new Scene();\r\n\t\tusing ( scene.Push() )\r\n\t\t{\r\n\t\t\tvar go = new GameObject();\r\n\r\n\t\t\tAssert.AreEqual( 1, scene.Directory.GameObjectCount );\r\n\t\t}\r\n\t}\r\n\r\n}\r\n"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": "__gen_RazorNamespace.cs",
"FileName": "__gen_RazorNamespace.cs",
"PackageType": "library",
"CodeKind": "Game",
"AssetVersionId": 67301,
"Code": "global using Microsoft.AspNetCore.Components; \nglobal using Microsoft.AspNetCore.Components.Rendering;\n"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": ".obj/__compiler_extra.cs",
"FileName": "__compiler_extra.cs",
"PackageType": "library",
"CodeKind": "Game",
"AssetVersionId": 67301,
"Code": "global using static Sandbox.Internal.GlobalGameNamespace;\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"AddonTitle\", \"CrosshairBuilder\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"AddonIdent\", \"crosshairbuilder\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"OrgIdent\", \"notathreat\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"Ident\", \"notathreat.crosshairbuilder\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"CompileTime\", \"8/19/2024 3:47:41 PM\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"EngineVersion\", \"17\" )]\r\n[assembly: global::System.Reflection.AssemblyMetadata( \"EngineMinorVersion\", \"1\" )]\r\n\r\n[assembly: System.Runtime.Versioning.TargetFramework( \".NETCoreApp,Version=v7.0\", FrameworkDisplayName = \".NET 7.0\" )]\r\n[assembly: global::System.Reflection.AssemblyVersion(\"0.0.121.0\")]\r\n[assembly: global::System.Reflection.AssemblyFileVersion(\"0.0.121.0\")]"
},
{
"Ident": "notathreat.crosshairbuilder",
"Path": "UnitTests/UnitTest.cs",
"FileName": "UnitTest.cs",
"PackageType": "library",
"CodeKind": "UnitTest",
"AssetVersionId": 67301,
"Code": "global using Microsoft.VisualStudio.TestTools.UnitTesting;\r\n\r\n[TestClass]\r\npublic class TestInit\r\n{\r\n\t[AssemblyInitialize]\r\n\tpublic static void ClassInitialize( TestContext context )\r\n\t{\r\n\t\tSandbox.Application.InitUnitTest();\r\n\t}\r\n}\r\n"
}
]
}