Insanely huge initial commit

This commit is contained in:
2026-02-21 16:40:15 -08:00
parent 208d626100
commit f74c547a13
33825 changed files with 5213498 additions and 0 deletions

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 4fc41b06fa4ef8941a99db4e4015661b
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,201 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the alpha of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the alpha of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Alpha")]
public class MMFeedbackTMPAlpha : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum AlphaModes { Instant, Interpolate, ToDestination }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (AlphaMode == AlphaModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip(" TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Alpha")]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"Instant : the alpha will change instantly to the target one," +
"Curve : the alpha will be interpolated along the curve," +
"interpolate : lerps from the current color to the destination one ")]
public AlphaModes AlphaMode = AlphaModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate, (int)AlphaModes.ToDestination)]
public float Duration = 0.2f;
/// the alpha to apply when in instant mode
[Tooltip("the alpha to apply when in instant mode")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Instant)]
public float InstantAlpha = 1f;
/// the curve to use when interpolating towards the destination alpha
[Tooltip("the curve to use when interpolating towards the destination alpha")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate, (int)AlphaModes.ToDestination)]
public MMTweenType Curve = new MMTweenType(MMTween.MMTweenCurve.EaseInCubic);
/// the value to which the curve's 0 should be remapped
[Tooltip("the value to which the curve's 0 should be remapped")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate)]
public float CurveRemapZero = 0f;
/// the value to which the curve's 1 should be remapped
[Tooltip("the value to which the curve's 1 should be remapped")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate)]
public float CurveRemapOne = 1f;
/// the alpha to aim towards when in ToDestination mode
[Tooltip("the alpha to aim towards when in ToDestination mode")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.ToDestination)]
public float DestinationAlpha = 1f;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialAlpha;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial alpha
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(GameObject owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialAlpha = TargetTMPText.alpha;
#endif
}
/// <summary>
/// On Play we change our text's alpha
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (AlphaMode)
{
case AlphaModes.Instant:
TargetTMPText.alpha = InstantAlpha;
break;
case AlphaModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ChangeAlpha());
break;
case AlphaModes.ToDestination:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_initialAlpha = TargetTMPText.alpha;
_coroutine = StartCoroutine(ChangeAlpha());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeAlpha()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetAlpha(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetAlpha(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// Applies the alpha change
/// </summary>
/// <param name="time"></param>
protected virtual void SetAlpha(float time)
{
#if MM_TEXTMESHPRO
float newAlpha = 0f;
if (AlphaMode == AlphaModes.Interpolate)
{
newAlpha = MMTween.Tween(time, 0f, 1f, CurveRemapZero, CurveRemapOne, Curve);
}
else if (AlphaMode == AlphaModes.ToDestination)
{
newAlpha = MMTween.Tween(time, 0f, 1f, _initialAlpha, DestinationAlpha, Curve);
}
TargetTMPText.alpha = newAlpha;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: b24ba469292593e45a0432cf1c12811c
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,72 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the character spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the character spacing of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Character Spacing")]
public class MMFeedbackTMPCharacterSpacing : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Character Spacing")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType CharacterSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "characterSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = CharacterSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 5926e044a3d682342bf2ddef666089dc
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,195 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
using System.Collections;
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the color of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the color of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Color")]
public class MMFeedbackTMPColor : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum ColorModes { Instant, Gradient, Interpolate }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (ColorMode == ColorModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip(" TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Color")]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"None : nothing will happen," +
"gradient : evaluates the color over time on that gradient, from left to right," +
"interpolate : lerps from the current color to the destination one ")]
public ColorModes ColorMode = ColorModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate, (int)ColorModes.Gradient)]
public float Duration = 0.2f;
/// the color to apply
[Tooltip("the color to apply")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Instant)]
public Color InstantColor = Color.yellow;
/// the gradient to use to animate the color over time
[Tooltip("the gradient to use to animate the color over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Gradient)]
[GradientUsage(true)]
public Gradient ColorGradient;
/// the destination color when in interpolate mode
[Tooltip("the destination color when in interpolate mode")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public Color DestinationColor = Color.yellow;
/// the curve to use when interpolating towards the destination color
[Tooltip("the curve to use when interpolating towards the destination color")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public AnimationCurve ColorCurve = new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.5f, 1), new Keyframe(1, 0));
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected Color _initialColor;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial color
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(GameObject owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialColor = TargetTMPText.color;
#endif
}
/// <summary>
/// On Play we change our text's color
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (ColorMode)
{
case ColorModes.Instant:
TargetTMPText.color = InstantColor;
break;
case ColorModes.Gradient:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ChangeColor());
break;
case ColorModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ChangeColor());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeColor()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetColor(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetColor(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// Applies the color change
/// </summary>
/// <param name="time"></param>
protected virtual void SetColor(float time)
{
#if MM_TEXTMESHPRO
if (ColorMode == ColorModes.Gradient)
{
TargetTMPText.color = ColorGradient.Evaluate(time);
}
else if (ColorMode == ColorModes.Interpolate)
{
float factor = ColorCurve.Evaluate(time);
TargetTMPText.color = Color.LerpUnclamped(_initialColor, DestinationColor, factor);
}
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 95b169d46d63cf046ba0d25f314cae64
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,161 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you dilate a TMP text over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you dilate a TMP text over time.")]
[FeedbackPath("TextMesh Pro/TMP Dilate")]
public class MMFeedbackTMPDilate : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
/// the duration of this feedback is the duration of the transition, or 0 if instant
public override float FeedbackDuration { get { return (Mode == MMFeedbackBase.Modes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Dilate")]
/// whether or not values should be relative
[Tooltip("whether or not values should be relative")]
public bool RelativeValues = true;
/// the selected mode
[Tooltip("the selected mode")]
public MMFeedbackBase.Modes Mode = MMFeedbackBase.Modes.OverTime;
/// the duration of the feedback, in seconds
[Tooltip("the duration of the feedback, in seconds")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float Duration = 0.5f;
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType DilateCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0.5f), new Keyframe(0.3f, 1f), new Keyframe(1, 0.5f)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = -1f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantDilate;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialDilate;
protected Coroutine _coroutine;
/// <summary>
/// On init we grab our initial dilate value
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(GameObject owner)
{
base.CustomInitialization(owner);
if (!Active)
{
return;
}
#if MM_TEXTMESHPRO
_initialDilate = TargetTMPText.fontMaterial.GetFloat(ShaderUtilities.ID_FaceDilate);
#endif
}
/// <summary>
/// On Play we turn animate our transition
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
if (Active && FeedbackTypeAuthorized)
{
switch (Mode)
{
case MMFeedbackBase.Modes.Instant:
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_FaceDilate, InstantDilate);
TargetTMPText.UpdateMeshPadding();
break;
case MMFeedbackBase.Modes.OverTime:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ApplyValueOverTime());
break;
}
}
#endif
}
/// <summary>
/// Applies our dilate value over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ApplyValueOverTime()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetValue(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetValue(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield return null;
}
/// <summary>
/// Sets the Dilate value
/// </summary>
/// <param name="time"></param>
protected virtual void SetValue(float time)
{
#if MM_TEXTMESHPRO
float intensity = MMTween.Tween(time, 0f, 1f, RemapZero, RemapOne, DilateCurve);
float newValue = intensity;
if (RelativeValues)
{
newValue += _initialDilate;
}
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_FaceDilate, newValue);
TargetTMPText.UpdateMeshPadding();
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f196d96a384107b4c848b23fad5b65c1
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,72 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the font size of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the font size of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Font Size")]
public class MMFeedbackTMPFontSize : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Font Size")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType FontSizeCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "fontSize";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = FontSizeCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 7804b7eebcc3f0a45adf06111f70ddc1
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,74 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the line spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the line spacing of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Line Spacing")]
public class MMFeedbackTMPLineSpacing : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Paragraph Spacing")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType LineSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
#endif
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
#if MM_TEXTMESHPRO
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
#endif
receiver.TargetPropertyName = "lineSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = LineSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f638aa321997c484faa3b4ef3c9b6e45
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,199 @@
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the color of a target TMP's outline over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the color of a target TMP's outline over time.")]
[FeedbackPath("TextMesh Pro/TMP Outline Color")]
public class MMFeedbackTMPOutlineColor : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum ColorModes { Instant, Gradient, Interpolate }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (ColorMode == ColorModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Outline Color")]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"None : nothing will happen," +
"gradient : evaluates the color over time on that gradient, from left to right," +
"interpolate : lerps from the current color to the destination one ")]
public ColorModes ColorMode = ColorModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate, (int)ColorModes.Gradient)]
public float Duration = 0.2f;
/// the color to apply
[Tooltip("the color to apply")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Instant)]
public Color32 InstantColor = Color.yellow;
/// the gradient to use to animate the color over time
[Tooltip("the gradient to use to animate the color over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Gradient)]
[GradientUsage(true)]
public Gradient ColorGradient;
/// the destination color when in interpolate mode
[Tooltip("the destination color when in interpolate mode")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public Color32 DestinationColor = Color.yellow;
/// the curve to use when interpolating towards the destination color
[Tooltip("the curve to use when interpolating towards the destination color")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public AnimationCurve ColorCurve = new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.5f, 1), new Keyframe(1, 0));
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected Color _initialColor;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial outline color
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(GameObject owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialColor = TargetTMPText.outlineColor;
#endif
}
/// <summary>
/// On Play we change our text's outline's color
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (ColorMode)
{
case ColorModes.Instant:
TargetTMPText.outlineColor = InstantColor;
break;
case ColorModes.Gradient:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ChangeColor());
break;
case ColorModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ChangeColor());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text's outline over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeColor()
{
IsPlaying = true;
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetColor(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetColor(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Applies the color change
/// </summary>
/// <param name="time"></param>
protected virtual void SetColor(float time)
{
#if MM_TEXTMESHPRO
if (ColorMode == ColorModes.Gradient)
{
// we set our object inactive then active, otherwise for some reason outline color isn't applied.
TargetTMPText.gameObject.SetActive(false);
TargetTMPText.outlineColor = ColorGradient.Evaluate(time);
TargetTMPText.gameObject.SetActive(true);
}
else if (ColorMode == ColorModes.Interpolate)
{
float factor = ColorCurve.Evaluate(time);
TargetTMPText.gameObject.SetActive(false);
TargetTMPText.outlineColor = Color.LerpUnclamped(_initialColor, DestinationColor, factor);
TargetTMPText.gameObject.SetActive(true);
}
#endif
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
StopCoroutine(_coroutine);
_coroutine = null;
}
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: dc2b0a81c117dd64e9622dc44b1fb80f
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,72 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the outline width of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the outline width of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Outline Width")]
public class MMFeedbackTMPOutlineWidth : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Outline Width")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType OutlineWidthCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "outlineWidth";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = OutlineWidthCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 3e8bb33bf5bd48d4a953d89faddb2b55
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,72 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the paragraph spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the paragraph spacing of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Paragraph Spacing")]
public class MMFeedbackTMPParagraphSpacing : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Paragraph Spacing")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType ParagraphSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "paragraphSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = ParagraphSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 8cf438dda3f60fa4a8c97baf53a42021
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,154 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you tweak the softness of a TMP text over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you tweak the softness of a TMP text over time.")]
[FeedbackPath("TextMesh Pro/TMP Softness")]
public class MMFeedbackTMPSoftness : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
/// the duration of this feedback is the duration of the transition, or 0 if instant
public override float FeedbackDuration { get { return (Mode == MMFeedbackBase.Modes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Softness")]
/// whether or not values should be relative
[Tooltip("whether or not values should be relative")]
public bool RelativeValues = true;
/// the selected mode
[Tooltip("the selected mode")]
public MMFeedbackBase.Modes Mode = MMFeedbackBase.Modes.OverTime;
/// the duration of the feedback, in seconds
[Tooltip("the duration of the feedback, in seconds")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float Duration = 0.5f;
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType SoftnessCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0f), new Keyframe(0.3f, 1f), new Keyframe(1, 0f)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantSoftness;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialSoftness;
protected Coroutine _coroutine;
/// <summary>
/// On init we grab our initial softness
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(GameObject owner)
{
base.CustomInitialization(owner);
if (!Active)
{
return;
}
#if MM_TEXTMESHPRO
_initialSoftness = TargetTMPText.fontMaterial.GetFloat(ShaderUtilities.ID_FaceDilate);
#endif
}
/// <summary>
/// On Play we animate our softness
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
if (Active && FeedbackTypeAuthorized)
{
switch (Mode)
{
case MMFeedbackBase.Modes.Instant:
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_OutlineSoftness, InstantSoftness);
TargetTMPText.UpdateMeshPadding();
break;
case MMFeedbackBase.Modes.OverTime:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = StartCoroutine(ApplyValueOverTime());
break;
}
}
#endif
}
protected virtual IEnumerator ApplyValueOverTime()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetValue(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetValue(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield return null;
}
protected virtual void SetValue(float time)
{
#if MM_TEXTMESHPRO
float intensity = MMTween.Tween(time, 0f, 1f, RemapZero, RemapOne, SoftnessCurve);
float newValue = intensity;
if (RelativeValues)
{
newValue += _initialSoftness;
}
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_OutlineSoftness, newValue);
TargetTMPText.UpdateMeshPadding();
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: a86c047de3f401c489f911a2f1cbe03c
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,55 @@
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback will let you change the text of a target TMP text component
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback will let you change the text of a target TMP text component")]
[FeedbackPath("TextMesh Pro/TMP Text")]
public class MMFeedbackTMPText : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("TextMesh Pro")]
/// the target TMP_Text component we want to change the text on
[Tooltip("the target TMP_Text component we want to change the text on")]
public TMP_Text TargetTMPText;
#endif
/// the new text to replace the old one with
[Tooltip("the new text to replace the old one with")]
[TextArea]
public string NewText = "Hello World";
/// <summary>
/// On play we change the text of our target TMPText
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
TargetTMPText.text = NewText;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 7f993bc75a115264fa74dfdf907d4ed5
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,374 @@
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback will let you reveal words, lines, or characters in a target TMP, one at a time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback will let you reveal words, lines, or characters in a target TMP, one at a time")]
[FeedbackPath("TextMesh Pro/TMP Text Reveal")]
public class MMFeedbackTMPTextReveal : MMFeedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
#if UNITY_EDITOR
public override Color FeedbackColor
{
get { return MMFeedbacksInspectorColors.TMPColor; }
}
#endif
#if MM_TEXTMESHPRO
/// the duration of this feedback
public override float FeedbackDuration
{
get
{
if (DurationMode == DurationModes.TotalDuration)
{
return RevealDuration;
}
else
{
if ((TargetTMPText == null) || (TargetTMPText.textInfo == null))
{
return 0f;
}
switch (RevealMode)
{
case RevealModes.Character:
return RichTextLength(TargetTMPText.text) * IntervalBetweenReveals;
case RevealModes.Lines:
return TargetTMPText.textInfo.lineCount * IntervalBetweenReveals;
case RevealModes.Words:
return TargetTMPText.textInfo.wordCount * IntervalBetweenReveals;
}
return 0f;
}
}
set
{
if (DurationMode == DurationModes.TotalDuration)
{
RevealDuration = value;
}
else
{
if (TargetTMPText != null)
{
switch (RevealMode)
{
case RevealModes.Character:
IntervalBetweenReveals = value / RichTextLength(TargetTMPText.text);
break;
case RevealModes.Lines:
IntervalBetweenReveals = value / TargetTMPText.textInfo.lineCount;
break;
case RevealModes.Words:
IntervalBetweenReveals = value / TargetTMPText.textInfo.wordCount;
break;
}
}
}
}
}
#endif
/// the possible ways to reveal the text
public enum RevealModes
{
Character,
Lines,
Words
}
/// whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take
public enum DurationModes
{
Interval,
TotalDuration
}
#if MM_TEXTMESHPRO
[Header("TextMesh Pro")]
/// the target TMP_Text component we want to change the text on
[Tooltip("the target TMP_Text component we want to change the text on")]
public TMP_Text TargetTMPText;
#endif
[Header("Change Text")]
/// whether or not to replace the current TMP target's text on play
[Tooltip("whether or not to replace the current TMP target's text on play")]
public bool ReplaceText = false;
/// the new text to replace the old one with
[Tooltip("the new text to replace the old one with")] [TextArea]
public string NewText = "Hello World";
[Header("Reveal")]
/// the selected way to reveal the text (character by character, word by word, or line by line)
[Tooltip("the selected way to reveal the text (character by character, word by word, or line by line)")]
public RevealModes RevealMode = RevealModes.Character;
/// whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take
[Tooltip(
"whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take")]
public DurationModes DurationMode = DurationModes.Interval;
/// the interval (in seconds) between two reveals
[Tooltip("the interval (in seconds) between two reveals")]
[MMFEnumCondition("DurationMode", (int)DurationModes.Interval)]
public float IntervalBetweenReveals = 0.05f;
/// the total duration of the text reveal, in seconds
[Tooltip("the total duration of the text reveal, in seconds")]
[MMFEnumCondition("DurationMode", (int)DurationModes.TotalDuration)]
public float RevealDuration = 1f;
protected float _delay;
protected Coroutine _coroutine;
protected int _richTextLength;
/// <summary>
/// On play we change the text of our target TMPText
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
if (ReplaceText)
{
TargetTMPText.text = NewText;
TargetTMPText.ForceMeshUpdate();
}
_richTextLength = RichTextLength(TargetTMPText.text);
switch (RevealMode)
{
case RevealModes.Character:
_delay =
(DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / _richTextLength;
TargetTMPText.maxVisibleCharacters = 0;
_coroutine = StartCoroutine(RevealCharacters());
break;
case RevealModes.Lines:
_delay =
(DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / TargetTMPText.textInfo.lineCount;
TargetTMPText.maxVisibleLines = 0;
_coroutine = StartCoroutine(RevealLines());
break;
case RevealModes.Words:
_delay =
(DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / TargetTMPText.textInfo.wordCount;
TargetTMPText.maxVisibleWords = 0;
_coroutine = StartCoroutine(RevealWords());
break;
}
#endif
}
/// <summary>
/// Reveals characters one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealCharacters()
{
float startTime = (Timing.TimescaleMode == TimescaleModes.Scaled) ? Time.time : Time.unscaledTime;
int totalCharacters = _richTextLength;
int visibleCharacters = 0;
float lastCharAt = 0f;
IsPlaying = true;
while (visibleCharacters <= totalCharacters)
{
float deltaTime = (Timing.TimescaleMode == TimescaleModes.Scaled)
? Time.deltaTime
: Time.unscaledDeltaTime;
float time = (Timing.TimescaleMode == TimescaleModes.Scaled) ? Time.time : Time.unscaledTime;
if (time - lastCharAt < IntervalBetweenReveals)
{
yield return null;
}
#if MM_TEXTMESHPRO
TargetTMPText.maxVisibleCharacters = visibleCharacters;
#endif
visibleCharacters++;
lastCharAt = time;
// we adjust our delay
float delay = 0f;
if (DurationMode == DurationModes.Interval)
{
_delay = Mathf.Max(IntervalBetweenReveals, deltaTime);
delay = _delay - deltaTime;
}
else
{
int remainingCharacters = totalCharacters - visibleCharacters;
float elapsedTime = time - startTime;
if (remainingCharacters != 0)
{
_delay = (RevealDuration - elapsedTime) / remainingCharacters;
}
delay = _delay - deltaTime;
}
if (Timing.TimescaleMode == TimescaleModes.Scaled)
{
yield return MMFeedbacksCoroutine.WaitFor(delay);
}
else
{
yield return MMFeedbacksCoroutine.WaitForUnscaled(delay);
}
}
#if MM_TEXTMESHPRO
TargetTMPText.maxVisibleCharacters = _richTextLength;
#endif
IsPlaying = false;
}
/// <summary>
/// Reveals lines one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealLines()
{
#if MM_TEXTMESHPRO
int totalLines = TargetTMPText.textInfo.lineCount;
int visibleLines = 0;
IsPlaying = true;
while (visibleLines <= totalLines)
{
TargetTMPText.maxVisibleLines = visibleLines;
visibleLines++;
if (Timing.TimescaleMode == TimescaleModes.Scaled)
{
yield return MMFeedbacksCoroutine.WaitFor(_delay);
}
else
{
yield return MMFeedbacksCoroutine.WaitForUnscaled(_delay);
}
}
IsPlaying = false;
#else
yield return null;
#endif
}
/// <summary>
/// Reveals words one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealWords()
{
#if MM_TEXTMESHPRO
int totalWords = TargetTMPText.textInfo.wordCount;
int visibleWords = 0;
IsPlaying = true;
while (visibleWords <= totalWords)
{
TargetTMPText.maxVisibleWords = visibleWords;
visibleWords++;
if (Timing.TimescaleMode == TimescaleModes.Scaled)
{
yield return MMFeedbacksCoroutine.WaitFor(_delay);
}
else
{
yield return MMFeedbacksCoroutine.WaitForUnscaled(_delay);
}
}
IsPlaying = false;
#else
yield return null;
#endif
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// Returns the length of a rich text, excluding its tags
/// </summary>
/// <param name="richText"></param>
/// <returns></returns>
protected int RichTextLength(string richText)
{
int richTextLength = 0;
bool insideTag = false;
richText = richText.Replace("<br>", "-");
foreach (char character in richText)
{
if (character == '<')
{
insideTag = true;
continue;
}
else if (character == '>')
{
insideTag = false;
}
else if (!insideTag)
{
richTextLength++;
}
}
return richTextLength;
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 657eaab42efefee469fef875a199cd38
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,71 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the word spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the word spacing of a target TMP over time.")]
[FeedbackPath("TextMesh Pro/TMP Word Spacing")]
public class MMFeedbackTMPWordSpacing : MMFeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
#endif
#if MM_TEXTMESHPRO
[Header("Target")]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[Header("Word Spacing")]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType WordSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMFeedbackBaseTarget target = new MMFeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "wordSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = WordSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 028a5c105539fba49a4053b37f1632bb
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,227 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the alpha of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the alpha of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Alpha")]
#endif
public class MMF_TMPAlpha : MMF_Feedback
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum AlphaModes { Instant, Interpolate, ToDestination }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (AlphaMode == AlphaModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
public override bool HasCustomInspectors => true;
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip(" TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Alpha", true, 16)]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"Instant : the alpha will change instantly to the target one," +
"Curve : the alpha will be interpolated along the curve," +
"interpolate : lerps from the current color to the destination one ")]
public AlphaModes AlphaMode = AlphaModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate, (int)AlphaModes.ToDestination)]
public float Duration = 0.2f;
/// the alpha to apply when in instant mode
[Tooltip("the alpha to apply when in instant mode")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Instant)]
public float InstantAlpha = 1f;
/// the curve to use when interpolating towards the destination alpha
[Tooltip("the curve to use when interpolating towards the destination alpha")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate, (int)AlphaModes.ToDestination)]
public MMTweenType Curve = new MMTweenType(MMTween.MMTweenCurve.EaseInCubic);
/// the value to which the curve's 0 should be remapped
[Tooltip("the value to which the curve's 0 should be remapped")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate)]
public float CurveRemapZero = 0f;
/// the value to which the curve's 1 should be remapped
[Tooltip("the value to which the curve's 1 should be remapped")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.Interpolate)]
public float CurveRemapOne = 1f;
/// the alpha to aim towards when in ToDestination mode
[Tooltip("the alpha to aim towards when in ToDestination mode")]
[MMFEnumCondition("AlphaMode", (int)AlphaModes.ToDestination)]
public float DestinationAlpha = 1f;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialAlpha;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial alpha
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(MMF_Player owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialAlpha = TargetTMPText.alpha;
#endif
}
/// <summary>
/// On Play we change our text's alpha
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (AlphaMode)
{
case AlphaModes.Instant:
TargetTMPText.alpha = InstantAlpha;
break;
case AlphaModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ChangeAlpha());
break;
case AlphaModes.ToDestination:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_initialAlpha = TargetTMPText.alpha;
_coroutine = Owner.StartCoroutine(ChangeAlpha());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeAlpha()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetAlpha(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetAlpha(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
Owner.StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// Applies the alpha change
/// </summary>
/// <param name="time"></param>
protected virtual void SetAlpha(float time)
{
#if MM_TEXTMESHPRO
float newAlpha = 0f;
if (AlphaMode == AlphaModes.Interpolate)
{
newAlpha = MMTween.Tween(time, 0f, 1f, CurveRemapZero, CurveRemapOne, Curve);
}
else if (AlphaMode == AlphaModes.ToDestination)
{
newAlpha = MMTween.Tween(time, 0f, 1f, _initialAlpha, DestinationAlpha, Curve);
}
TargetTMPText.alpha = newAlpha;
#endif
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.alpha = _initialAlpha;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: a4be8a3950b608c4785907ebe6be06ab
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,83 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the character spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the character spacing of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Character Spacing")]
#endif
public class MMF_TMPCharacterSpacing : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Character Spacing", true, 16)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType CharacterSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "characterSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = CharacterSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f58aef5c589e998418e5d3ec374edefe
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,219 @@
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the color of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the color of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Color")]
#endif
public class MMF_TMPColor : MMF_Feedback
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum ColorModes { Instant, Gradient, Interpolate }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (ColorMode == ColorModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip(" TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Color", true, 16)]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"None : nothing will happen," +
"gradient : evaluates the color over time on that gradient, from left to right," +
"interpolate : lerps from the current color to the destination one ")]
public ColorModes ColorMode = ColorModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate, (int)ColorModes.Gradient)]
public float Duration = 0.2f;
/// the color to apply
[Tooltip("the color to apply")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Instant)]
public Color InstantColor = Color.yellow;
/// the gradient to use to animate the color over time
[Tooltip("the gradient to use to animate the color over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Gradient)]
[GradientUsage(true)]
public Gradient ColorGradient;
/// the destination color when in interpolate mode
[Tooltip("the destination color when in interpolate mode")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public Color DestinationColor = Color.yellow;
/// the curve to use when interpolating towards the destination color
[Tooltip("the curve to use when interpolating towards the destination color")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public AnimationCurve ColorCurve = new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.5f, 1), new Keyframe(1, 0));
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected Color _initialColor;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial color
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(MMF_Player owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialColor = TargetTMPText.color;
#endif
}
/// <summary>
/// On Play we change our text's color
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (ColorMode)
{
case ColorModes.Instant:
TargetTMPText.color = InstantColor;
break;
case ColorModes.Gradient:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ChangeColor());
break;
case ColorModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ChangeColor());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeColor()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetColor(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetColor(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
Owner.StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// Applies the color change
/// </summary>
/// <param name="time"></param>
protected virtual void SetColor(float time)
{
#if MM_TEXTMESHPRO
if (ColorMode == ColorModes.Gradient)
{
TargetTMPText.color = ColorGradient.Evaluate(time);
}
else if (ColorMode == ColorModes.Interpolate)
{
float factor = ColorCurve.Evaluate(time);
TargetTMPText.color = Color.LerpUnclamped(_initialColor, DestinationColor, factor);
}
#endif
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.color = _initialColor;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: cb001ad73daba6d49b6183ff4079ebb6
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,166 @@
using System.Collections;
using System.Collections.Generic;
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback will let you update a TMP text value over time, with a value going from A to B over time, on a curve
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback will let you update a TMP text value over time, with a value going from A to B over time, on a curve")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Count To")]
#endif
public class MMF_TMPCountTo : MMF_Feedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
/// the duration of this feedback is the duration of the scale animation
public override float FeedbackDuration { get { return ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("TextMeshPro Target Text", true, 12, true)]
/// the target TMP_Text component we want to change the text on
[Tooltip("the target TMP_Text component we want to change the text on")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Count Settings", true, 13)]
/// the value from which to count from
[Tooltip("the value from which to count from")]
public float CountFrom = 0f;
/// the value to count towards
[Tooltip("the value to count towards")]
public float CountTo = 10f;
/// the curve on which to animate the count
[Tooltip("the curve on which to animate the count")]
public MMTweenType CountingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the duration of the count, in seconds
[Tooltip("the duration of the count, in seconds")]
public float Duration = 5f;
/// the format with which to display the count
[Tooltip("the format with which to display the count")]
public string Format = "00.00";
/// whether or not value should be floored
[Tooltip("whether or not value should be floored")]
public bool FloorValues = true;
/// the minimum frequency (in seconds) at which to refresh the text field
[Tooltip("the minimum frequency (in seconds) at which to refresh the text field")]
public float MinRefreshFrequency = 0f;
protected string _newText;
protected float _startTime;
protected float _lastRefreshAt;
protected string _initialText;
/// <summary>
/// On play we change the text of our target TMPText over time
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialText = TargetTMPText.text;
#endif
Owner.StartCoroutine(CountCo());
}
/// <summary>
/// A coroutine used to animate the text
/// </summary>
/// <returns></returns>
protected virtual IEnumerator CountCo()
{
_lastRefreshAt = -float.MaxValue;
float currentValue = CountFrom;
_startTime = FeedbackTime;
while (FeedbackTime - _startTime <= Duration)
{
if (FeedbackTime - _lastRefreshAt >= MinRefreshFrequency)
{
currentValue = ProcessCount();
UpdateText(currentValue);
_lastRefreshAt = FeedbackTime;
}
yield return null;
}
UpdateText(CountTo);
}
/// <summary>
/// Updates the text of the target TMPText component with the updated value
/// </summary>
/// <param name="currentValue"></param>
protected virtual void UpdateText(float currentValue)
{
if (FloorValues)
{
_newText = Mathf.Floor(currentValue).ToString(Format);
}
else
{
_newText = currentValue.ToString(Format);
}
#if MM_TEXTMESHPRO
TargetTMPText.text = _newText;
#endif
}
/// <summary>
/// Computes the new value of the count for the current time
/// </summary>
/// <param name="currentValue"></param>
/// <returns></returns>
protected virtual float ProcessCount()
{
float currentTime = FeedbackTime - _startTime;
float currentValue = MMTween.Tween(currentTime, 0f, Duration, CountFrom, CountTo, CountingCurve);
return currentValue;
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.text = _initialText;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 76ee492955c4d2f4fa9c0dd9f9a59f12
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,192 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you dilate a TMP text over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you dilate a TMP text over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Dilate")]
#endif
public class MMF_TMPDilate : MMF_Feedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
public override bool HasCustomInspectors => true;
/// the duration of this feedback is the duration of the transition, or 0 if instant
public override float FeedbackDuration { get { return (Mode == MMFeedbackBase.Modes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Dilate", true, 16)]
/// whether or not values should be relative
[Tooltip("whether or not values should be relative")]
public bool RelativeValues = true;
/// the selected mode
[Tooltip("the selected mode")]
public MMFeedbackBase.Modes Mode = MMFeedbackBase.Modes.OverTime;
/// the duration of the feedback, in seconds
[Tooltip("the duration of the feedback, in seconds")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float Duration = 0.5f;
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType DilateCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0.5f), new Keyframe(0.3f, 1f), new Keyframe(1, 0.5f)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = -1f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantDilate;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialDilate;
protected Coroutine _coroutine;
/// <summary>
/// On init we grab our initial dilate value
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(MMF_Player owner)
{
base.CustomInitialization(owner);
if (!Active)
{
return;
}
#if MM_TEXTMESHPRO
_initialDilate = TargetTMPText.fontMaterial.GetFloat(ShaderUtilities.ID_FaceDilate);
#endif
}
/// <summary>
/// On Play we turn animate our transition
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
if (Active)
{
switch (Mode)
{
case MMFeedbackBase.Modes.Instant:
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_FaceDilate, InstantDilate);
TargetTMPText.UpdateMeshPadding();
break;
case MMFeedbackBase.Modes.OverTime:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ApplyValueOverTime());
break;
}
}
#endif
}
/// <summary>
/// Applies our dilate value over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ApplyValueOverTime()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetValue(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetValue(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield return null;
}
/// <summary>
/// Sets the Dilate value
/// </summary>
/// <param name="time"></param>
protected virtual void SetValue(float time)
{
#if MM_TEXTMESHPRO
float intensity = MMTween.Tween(time, 0f, 1f, RemapZero, RemapOne, DilateCurve);
float newValue = intensity;
if (RelativeValues)
{
newValue += _initialDilate;
}
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_FaceDilate, newValue);
TargetTMPText.UpdateMeshPadding();
#endif
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_FaceDilate, _initialDilate);
TargetTMPText.UpdateMeshPadding();
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: ce42aabd176ab5e4d8ba2a0dc416e78e
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,101 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the font size of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the font size of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Font Size")]
#endif
public class MMF_TMPFontSize : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor
{
get { return MMFeedbacksInspectorColors.TMPColor; }
}
public override string RequiresSetupText
{
get
{
return
"This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below.";
}
}
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup()
{
return (TargetTMPText == null);
}
public override string RequiredTargetText
{
get { return TargetTMPText != null ? TargetTMPText.name : ""; }
}
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Font Size", true, 16)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType FontSizeCurve =
new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "fontSize";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = FontSizeCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 0fffa36c603d1bd4ea253a17e4d17757
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,82 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the line spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the line spacing of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Line Spacing")]
#endif
public class MMF_TMPLineSpacing : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Paragraph Spacing", true, 37)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType LineSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "lineSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = LineSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 769890c09f9abdf42af40a0e8b1f8ea0
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,223 @@
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the color of a target TMP's outline over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the color of a target TMP's outline over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Outline Color")]
#endif
public class MMF_TMPOutlineColor : MMF_Feedback
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
public enum ColorModes { Instant, Gradient, Interpolate }
/// the duration of this feedback is the duration of the color transition, or 0 if instant
public override float FeedbackDuration { get { return (ColorMode == ColorModes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Outline Color", true, 16)]
/// the selected color mode :
/// None : nothing will happen,
/// gradient : evaluates the color over time on that gradient, from left to right,
/// interpolate : lerps from the current color to the destination one
[Tooltip("the selected color mode :" +
"None : nothing will happen," +
"gradient : evaluates the color over time on that gradient, from left to right," +
"interpolate : lerps from the current color to the destination one ")]
public ColorModes ColorMode = ColorModes.Interpolate;
/// how long the color of the text should change over time
[Tooltip("how long the color of the text should change over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate, (int)ColorModes.Gradient)]
public float Duration = 0.2f;
/// the color to apply
[Tooltip("the color to apply")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Instant)]
public Color32 InstantColor = Color.yellow;
/// the gradient to use to animate the color over time
[Tooltip("the gradient to use to animate the color over time")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Gradient)]
[GradientUsage(true)]
public Gradient ColorGradient;
/// the destination color when in interpolate mode
[Tooltip("the destination color when in interpolate mode")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public Color32 DestinationColor = Color.yellow;
/// the curve to use when interpolating towards the destination color
[Tooltip("the curve to use when interpolating towards the destination color")]
[MMFEnumCondition("ColorMode", (int)ColorModes.Interpolate)]
public AnimationCurve ColorCurve = new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.5f, 1), new Keyframe(1, 0));
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected Color _initialColor;
protected Coroutine _coroutine;
/// <summary>
/// On init we store our initial outline color
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(MMF_Player owner)
{
base.CustomInitialization(owner);
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialColor = TargetTMPText.outlineColor;
#endif
}
/// <summary>
/// On Play we change our text's outline's color
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
switch (ColorMode)
{
case ColorModes.Instant:
TargetTMPText.outlineColor = InstantColor;
break;
case ColorModes.Gradient:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ChangeColor());
break;
case ColorModes.Interpolate:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ChangeColor());
break;
}
#endif
}
/// <summary>
/// Changes the color of the text's outline over time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator ChangeColor()
{
IsPlaying = true;
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetColor(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetColor(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield break;
}
/// <summary>
/// Applies the color change
/// </summary>
/// <param name="time"></param>
protected virtual void SetColor(float time)
{
#if MM_TEXTMESHPRO
if (ColorMode == ColorModes.Gradient)
{
// we set our object inactive then active, otherwise for some reason outline color isn't applied.
TargetTMPText.gameObject.SetActive(false);
TargetTMPText.outlineColor = ColorGradient.Evaluate(time);
TargetTMPText.gameObject.SetActive(true);
}
else if (ColorMode == ColorModes.Interpolate)
{
float factor = ColorCurve.Evaluate(time);
TargetTMPText.gameObject.SetActive(false);
TargetTMPText.outlineColor = Color.LerpUnclamped(_initialColor, DestinationColor, factor);
TargetTMPText.gameObject.SetActive(true);
}
#endif
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
Owner.StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.gameObject.SetActive(false);
TargetTMPText.outlineColor = _initialColor;
TargetTMPText.gameObject.SetActive(true);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: e39702c3d8077294887f6c1ddec28589
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,93 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the outline width of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the outline width of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Outline Width")]
#endif
public class MMF_TMPOutlineWidth : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor
{
get { return MMFeedbacksInspectorColors.TMPColor; }
}
public override string RequiresSetupText
{
get
{
return
"This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below.";
}
}
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Outline Width", true, 22)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType OutlineWidthCurve =
new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")] [MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "outlineWidth";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = OutlineWidthCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 932d7950b01edc04d8d29d2669394cf5
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,82 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the paragraph spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the paragraph spacing of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Paragraph Spacing")]
#endif
public class MMF_TMPParagraphSpacing : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Paragraph Spacing", true, 21)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType ParagraphSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "paragraphSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = ParagraphSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 0be258710b59b254097822aef1c6820e
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,179 @@
using MoreMountains.Tools;
using UnityEngine;
using System.Collections;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you tweak the softness of a TMP text over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you tweak the softness of a TMP text over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Softness")]
#endif
public class MMF_TMPSoftness : MMF_Feedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
public override bool HasCustomInspectors => true;
/// the duration of this feedback is the duration of the transition, or 0 if instant
public override float FeedbackDuration { get { return (Mode == MMFeedbackBase.Modes.Instant) ? 0f : ApplyTimeMultiplier(Duration); } set { Duration = value; } }
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Softness", true, 13)]
/// whether or not values should be relative
[Tooltip("whether or not values should be relative")]
public bool RelativeValues = true;
/// the selected mode
[Tooltip("the selected mode")]
public MMFeedbackBase.Modes Mode = MMFeedbackBase.Modes.OverTime;
/// the duration of the feedback, in seconds
[Tooltip("the duration of the feedback, in seconds")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float Duration = 0.5f;
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType SoftnessCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0f), new Keyframe(0.3f, 1f), new Keyframe(1, 0f)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 1f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantSoftness;
/// if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over
[Tooltip("if this is true, calling that feedback will trigger it, even if it's in progress. If it's false, it'll prevent any new Play until the current one is over")]
public bool AllowAdditivePlays = false;
protected float _initialSoftness;
protected Coroutine _coroutine;
/// <summary>
/// On init we grab our initial softness
/// </summary>
/// <param name="owner"></param>
protected override void CustomInitialization(MMF_Player owner)
{
base.CustomInitialization(owner);
if (!Active)
{
return;
}
#if MM_TEXTMESHPRO
_initialSoftness = TargetTMPText.fontMaterial.GetFloat(ShaderUtilities.ID_FaceDilate);
#endif
}
/// <summary>
/// On Play we animate our softness
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
if (Active && FeedbackTypeAuthorized)
{
switch (Mode)
{
case MMFeedbackBase.Modes.Instant:
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_OutlineSoftness, InstantSoftness);
TargetTMPText.UpdateMeshPadding();
break;
case MMFeedbackBase.Modes.OverTime:
if (!AllowAdditivePlays && (_coroutine != null))
{
return;
}
_coroutine = Owner.StartCoroutine(ApplyValueOverTime());
break;
}
}
#endif
}
protected virtual IEnumerator ApplyValueOverTime()
{
float journey = NormalPlayDirection ? 0f : FeedbackDuration;
IsPlaying = true;
while ((journey >= 0) && (journey <= FeedbackDuration) && (FeedbackDuration > 0))
{
float remappedTime = MMFeedbacksHelpers.Remap(journey, 0f, FeedbackDuration, 0f, 1f);
SetValue(remappedTime);
journey += NormalPlayDirection ? FeedbackDeltaTime : -FeedbackDeltaTime;
yield return null;
}
SetValue(FinalNormalizedTime);
_coroutine = null;
IsPlaying = false;
yield return null;
}
protected virtual void SetValue(float time)
{
#if MM_TEXTMESHPRO
float intensity = MMTween.Tween(time, 0f, 1f, RemapZero, RemapOne, SoftnessCurve);
float newValue = intensity;
if (RelativeValues)
{
newValue += _initialSoftness;
}
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_OutlineSoftness, newValue);
TargetTMPText.UpdateMeshPadding();
#endif
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.fontMaterial.SetFloat(ShaderUtilities.ID_OutlineSoftness, _initialSoftness);
TargetTMPText.UpdateMeshPadding();
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: ef0aa39dbc6e77a4492bee30af779378
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,81 @@
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback will let you change the text of a target TMP text component
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback will let you change the text of a target TMP text component")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Text")]
#endif
public class MMF_TMPText : MMF_Feedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("TextMeshPro Change Text", true, 12, true)]
/// the target TMP_Text component we want to change the text on
[Tooltip("the target TMP_Text component we want to change the text on")]
public TMP_Text TargetTMPText;
/// the new text to replace the old one with
[Tooltip("the new text to replace the old one with")]
[TextArea]
public string NewText = "Hello World";
#endif
protected string _initialText;
/// <summary>
/// On play we change the text of our target TMPText
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
#if MM_TEXTMESHPRO
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
if (TargetTMPText == null)
{
return;
}
_initialText = TargetTMPText.text;
TargetTMPText.text = NewText;
#endif
}
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.text = _initialText;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: c3085c8741c1bb84ca7a609f2989b7e0
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,459 @@
using System;
using System.Collections;
using UnityEngine;
using UnityEngine.Events;
#if MM_TEXTMESHPRO
using MoreMountains.Tools;
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback will let you reveal words, lines, or characters in a target TMP, one at a time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback will let you reveal words, lines, or characters in a target TMP, one at a time")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Text Reveal")]
#endif
public class MMF_TMPTextReveal : MMF_Feedback
{
/// a static bool used to disable all feedbacks of this type at once
public static bool FeedbackTypeAuthorized = true;
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
protected string _originalText;
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
protected TMP_TextInfo _textInfo;
/// the duration of this feedback
public override float FeedbackDuration
{
get
{
if (DurationMode == DurationModes.TotalDuration)
{
return RevealDuration;
}
else
{
if ((TargetTMPText == null) || (TargetTMPText.textInfo == null))
{
return 0f;
}
float foundLength = 0f;
if (ReplaceText)
{
_originalText = TargetTMPText.text;
TargetTMPText.text = NewText;
}
switch (RevealMode)
{
case RevealModes.Character:
foundLength = RichTextLength(TargetTMPText.text) * IntervalBetweenReveals;
break;
case RevealModes.Lines:
foundLength = TargetTMPText.textInfo.lineCount * IntervalBetweenReveals;
break;
case RevealModes.Words:
foundLength = TargetTMPText.textInfo.wordCount * IntervalBetweenReveals;
break;
}
if (ReplaceText)
{
TargetTMPText.text = _originalText;
}
return foundLength;
}
}
set
{
if (DurationMode == DurationModes.TotalDuration)
{
RevealDuration = value;
}
else
{
if (TargetTMPText != null)
{
if (ReplaceText)
{
_originalText = TargetTMPText.text;
TargetTMPText.text = NewText;
}
switch (RevealMode)
{
case RevealModes.Character:
IntervalBetweenReveals = value / RichTextLength(TargetTMPText.text);
break;
case RevealModes.Lines:
IntervalBetweenReveals = value / TargetTMPText.textInfo.lineCount;
break;
case RevealModes.Words:
IntervalBetweenReveals = value / TargetTMPText.textInfo.wordCount;
break;
}
if (ReplaceText)
{
TargetTMPText.text = _originalText;
}
}
}
}
}
#endif
/// the possible ways to reveal the text
public enum RevealModes { Character, Lines, Words }
/// whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take
public enum DurationModes { Interval, TotalDuration }
#if MM_TEXTMESHPRO
[MMFInspectorGroup("Target", true, 12, true)]
/// the target TMP_Text component we want to change the text on
[Tooltip("the target TMP_Text component we want to change the text on")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Change Text", true, 13)]
/// whether or not to replace the current TMP target's text on play
[Tooltip("whether or not to replace the current TMP target's text on play")]
public bool ReplaceText = false;
/// the new text to replace the old one with
[Tooltip("the new text to replace the old one with")]
[TextArea]
public string NewText = "Hello World";
[MMFInspectorGroup("Reveal", true, 14)]
/// the selected way to reveal the text (character by character, word by word, or line by line)
[Tooltip("the selected way to reveal the text (character by character, word by word, or line by line)")]
public RevealModes RevealMode = RevealModes.Character;
/// whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take
[Tooltip("whether to define duration by the time interval between two unit reveals, or by the total duration the reveal should take")]
public DurationModes DurationMode = DurationModes.Interval;
/// the interval (in seconds) between two reveals
[Tooltip("the interval (in seconds) between two reveals")]
[MMFEnumCondition("DurationMode", (int)DurationModes.Interval)]
public float IntervalBetweenReveals = 0.05f;
/// the total duration of the text reveal, in seconds
[Tooltip("the total duration of the text reveal, in seconds")]
[MMFEnumCondition("DurationMode", (int)DurationModes.TotalDuration)]
public float RevealDuration = 1f;
/// a UnityEvent to invoke every time a reveal happens (word, line or character)
[Tooltip("a UnityEvent to invoke every time a reveal happens (word, line or character)")]
public UnityEvent OnReveal;
protected float _delay;
protected Coroutine _coroutine;
protected int _richTextLength;
protected int _totalCharacters;
protected int _totalLines;
protected int _totalWords;
protected string _initialText;
protected int _indexLastTime = -1;
/// <summary>
/// On play we change the text of our target TMPText
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomPlayFeedback(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
_initialText = TargetTMPText.text;
_textInfo = TargetTMPText.textInfo;
if (ReplaceText)
{
TargetTMPText.text = NewText;
TargetTMPText.ForceMeshUpdate();
}
_richTextLength = RichTextLength(TargetTMPText.text);
switch (RevealMode)
{
case RevealModes.Character:
_delay = (DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / _richTextLength;
TargetTMPText.maxVisibleCharacters = 0;
_coroutine = Owner.StartCoroutine(RevealCharacters());
break;
case RevealModes.Lines:
_delay = (DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / TargetTMPText.textInfo.lineCount;
TargetTMPText.maxVisibleLines = 0;
_coroutine = Owner.StartCoroutine(RevealLines());
break;
case RevealModes.Words:
_delay = (DurationMode == DurationModes.Interval) ? IntervalBetweenReveals : RevealDuration / TargetTMPText.textInfo.wordCount;
TargetTMPText.maxVisibleWords = 0;
_coroutine = Owner.StartCoroutine(RevealWords());
break;
}
#endif
}
#if MM_TEXTMESHPRO
/// <summary>
/// Reveals characters one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealCharacters()
{
float startTime = FeedbackTime;
_totalCharacters = _richTextLength;
int visibleCharacters = 0;
float lastCharAt = 0f;
IsPlaying = true;
while ((visibleCharacters <= _totalCharacters) && !Owner.SkippingToTheEnd)
{
float time = FeedbackTime;
if (time - lastCharAt < IntervalBetweenReveals)
{
yield return null;
}
TargetTMPText.maxVisibleCharacters = visibleCharacters;
InvokeRevealEvents();
visibleCharacters++;
lastCharAt = time;
// we adjust our delay
float delay = 0f;
if (DurationMode == DurationModes.Interval)
{
_delay = Mathf.Max(IntervalBetweenReveals, FeedbackDeltaTime);
delay = _delay - FeedbackDeltaTime;
}
else
{
int remainingCharacters = _totalCharacters - visibleCharacters;
float elapsedTime = time - startTime;
if (remainingCharacters != 0)
{
_delay = (RevealDuration - elapsedTime) / remainingCharacters;
}
delay = _delay - FeedbackDeltaTime;
}
yield return WaitFor(delay);
}
TargetTMPText.maxVisibleCharacters = _richTextLength;
IsPlaying = false;
}
/// <summary>
/// Reveals lines one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealLines()
{
_totalLines = TargetTMPText.textInfo.lineCount;
int visibleLines = 0;
IsPlaying = true;
while ((visibleLines <= _totalLines) && !Owner.SkippingToTheEnd)
{
TargetTMPText.maxVisibleLines = visibleLines;
InvokeRevealEvents();
visibleLines++;
yield return WaitFor(_delay);
}
TargetTMPText.maxVisibleLines = _totalLines;
IsPlaying = false;
}
/// <summary>
/// Reveals words one at a time
/// </summary>
/// <returns></returns>
protected virtual IEnumerator RevealWords()
{
_totalWords = TargetTMPText.textInfo.wordCount;
int visibleWords = 0;
IsPlaying = true;
while ((visibleWords <= _totalWords) && !Owner.SkippingToTheEnd)
{
TargetTMPText.maxVisibleWords = visibleWords;
InvokeRevealEvents();
visibleWords++;
yield return WaitFor(_delay);
}
TargetTMPText.maxVisibleWords = _totalWords;
IsPlaying = false;
}
/// <summary>
/// Invokes on reveal events
/// </summary>
protected virtual void InvokeRevealEvents()
{
if ( ((RevealMode == RevealModes.Character) && (TargetTMPText.maxVisibleCharacters == 0))
|| ((RevealMode == RevealModes.Character) && !IsNewVisibleCharacter())
|| ((RevealMode == RevealModes.Lines) && (TargetTMPText.maxVisibleLines == 0))
|| ((RevealMode == RevealModes.Words) && (TargetTMPText.maxVisibleWords == 0)) )
{
return;
}
OnReveal?.Invoke();
}
/// <summary>
/// Stops the animation if needed
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomStopFeedback(Vector3 position, float feedbacksIntensity = 1)
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
base.CustomStopFeedback(position, feedbacksIntensity);
IsPlaying = false;
if (_coroutine != null)
{
Owner.StopCoroutine(_coroutine);
_coroutine = null;
}
}
/// <summary>
/// On skip, we display our entire text
/// </summary>
/// <param name="position"></param>
/// <param name="feedbacksIntensity"></param>
protected override void CustomSkipToTheEnd(Vector3 position, float feedbacksIntensity = 1.0f)
{
if (!IsPlaying)
{
return;
}
switch (RevealMode)
{
case RevealModes.Character:
TargetTMPText.maxVisibleCharacters = _totalCharacters;
break;
case RevealModes.Lines:
TargetTMPText.maxVisibleLines = _totalLines;
break;
case RevealModes.Words:
TargetTMPText.maxVisibleWords = _totalWords;
break;
}
}
/// <summary>
/// Returns the length of a rich text, excluding its tags
/// </summary>
/// <param name="richText"></param>
/// <returns></returns>
protected int RichTextLength(string richText)
{
int richTextLength = 0;
bool insideTag = false;
richText = richText.Replace("<br>", "-");
foreach (char character in richText)
{
if (character == '<')
{
insideTag = true;
continue;
}
else if (character == '>')
{
insideTag = false;
}
else if (!insideTag)
{
richTextLength++;
}
}
return richTextLength;
}
/// <summary>
/// Returns true if the last visible letter of the TMP text is new and visible and a letter or digit
/// </summary>
/// <returns></returns>
protected virtual bool IsNewVisibleCharacter()
{
int lastVisibleCharIndex = -1;
_textInfo = TargetTMPText.GetTextInfo(TargetTMPText.text);
for (int i = 0; i < _textInfo.characterCount; i++)
{
if (_textInfo.characterInfo[i].isVisible)
{
lastVisibleCharIndex = i;
}
}
if ((lastVisibleCharIndex < 0)
|| (lastVisibleCharIndex > TargetTMPText.text.Length)
|| (lastVisibleCharIndex == _indexLastTime))
{
return false;
}
_indexLastTime = lastVisibleCharIndex;
return Char.IsLetterOrDigit(_textInfo.characterInfo[lastVisibleCharIndex].character);
}
#endif
/// <summary>
/// On restore, we put our object back at its initial position
/// </summary>
protected override void CustomRestoreInitialValues()
{
if (!Active || !FeedbackTypeAuthorized)
{
return;
}
#if MM_TEXTMESHPRO
TargetTMPText.text = _initialText;
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 45c7b8525ec6efc459e80a97bb09c688
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,82 @@
using MoreMountains.Tools;
using UnityEngine;
#if MM_TEXTMESHPRO
using TMPro;
#endif
namespace MoreMountains.Feedbacks
{
/// <summary>
/// This feedback lets you control the word spacing of a target TMP over time
/// </summary>
[AddComponentMenu("")]
[FeedbackHelp("This feedback lets you control the word spacing of a target TMP over time.")]
#if MM_TEXTMESHPRO
[FeedbackPath("TextMesh Pro/TMP Word Spacing")]
#endif
public class MMF_TMPWordSpacing : MMF_FeedbackBase
{
/// sets the inspector color for this feedback
#if UNITY_EDITOR
public override Color FeedbackColor { get { return MMFeedbacksInspectorColors.TMPColor; } }
public override string RequiresSetupText { get { return "This feedback requires that a TargetTMPText be set to be able to work properly. You can set one below."; } }
#endif
#if UNITY_EDITOR && MM_TEXTMESHPRO
public override bool EvaluateRequiresSetup() { return (TargetTMPText == null); }
public override string RequiredTargetText { get { return TargetTMPText != null ? TargetTMPText.name : ""; } }
#endif
#if MM_TEXTMESHPRO
public override bool HasAutomatedTargetAcquisition => true;
protected override void AutomateTargetAcquisition() => TargetTMPText = FindAutomatedTarget<TMP_Text>();
[MMFInspectorGroup("Target", true, 12, true)]
/// the TMP_Text component to control
[Tooltip("the TMP_Text component to control")]
public TMP_Text TargetTMPText;
#endif
[MMFInspectorGroup("Word Spacing", true, 15)]
/// the curve to tween on
[Tooltip("the curve to tween on")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public MMTweenType WordSpacingCurve = new MMTweenType(new AnimationCurve(new Keyframe(0, 0), new Keyframe(0.3f, 1f), new Keyframe(1, 0)));
/// the value to remap the curve's 0 to
[Tooltip("the value to remap the curve's 0 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapZero = 0f;
/// the value to remap the curve's 1 to
[Tooltip("the value to remap the curve's 1 to")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.OverTime)]
public float RemapOne = 10f;
/// the value to move to in instant mode
[Tooltip("the value to move to in instant mode")]
[MMFEnumCondition("Mode", (int)MMFeedbackBase.Modes.Instant)]
public float InstantFontSize;
protected override void FillTargets()
{
#if MM_TEXTMESHPRO
if (TargetTMPText == null)
{
return;
}
MMF_FeedbackBaseTarget target = new MMF_FeedbackBaseTarget();
MMPropertyReceiver receiver = new MMPropertyReceiver();
receiver.TargetObject = TargetTMPText.gameObject;
receiver.TargetComponent = TargetTMPText;
receiver.TargetPropertyName = "wordSpacing";
receiver.RelativeValue = RelativeValues;
target.Target = receiver;
target.LevelCurve = WordSpacingCurve;
target.RemapLevelZero = RemapZero;
target.RemapLevelOne = RemapOne;
target.InstantLevel = InstantFontSize;
_targets.Add(target);
#endif
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: bfe04c61ac8739b4eb65938198bcc344
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant: