Merge pull request #9920 from pchote/label-truncation
Truncate long user-defined strings.
This commit is contained in:
@@ -227,6 +227,22 @@ namespace OpenRA.Widgets
|
|||||||
return text;
|
return text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static string TruncateText(string text, int width, SpriteFont font)
|
||||||
|
{
|
||||||
|
var trimmedWidth = font.Measure(text).X;
|
||||||
|
if (trimmedWidth <= width)
|
||||||
|
return text;
|
||||||
|
|
||||||
|
var trimmed = text;
|
||||||
|
while (trimmedWidth > width && trimmed.Length > 3)
|
||||||
|
{
|
||||||
|
trimmed = text.Substring(0, trimmed.Length - 4) + "...";
|
||||||
|
trimmedWidth = font.Measure(trimmed).X;
|
||||||
|
}
|
||||||
|
|
||||||
|
return trimmed;
|
||||||
|
}
|
||||||
|
|
||||||
public static Action Once(Action a) { return () => { if (a != null) { a(); a = null; } }; }
|
public static Action Once(Action a) { return () => { if (a != null) { a(); a = null; } }; }
|
||||||
|
|
||||||
public static string ChooseInitialMap(string initialUid)
|
public static string ChooseInitialMap(string initialUid)
|
||||||
@@ -242,6 +258,32 @@ namespace OpenRA.Widgets
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class CachedTransform<T, U>
|
||||||
|
{
|
||||||
|
readonly Func<T, U> transform;
|
||||||
|
|
||||||
|
bool initialized;
|
||||||
|
T lastInput;
|
||||||
|
U lastOutput;
|
||||||
|
|
||||||
|
public CachedTransform(Func<T, U> transform)
|
||||||
|
{
|
||||||
|
this.transform = transform;
|
||||||
|
}
|
||||||
|
|
||||||
|
public U Update(T input)
|
||||||
|
{
|
||||||
|
if (initialized && ((input == null && lastInput == null) || input.Equals(lastInput)))
|
||||||
|
return lastOutput;
|
||||||
|
|
||||||
|
lastInput = input;
|
||||||
|
lastOutput = transform(input);
|
||||||
|
initialized = true;
|
||||||
|
|
||||||
|
return lastOutput;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
[Flags]
|
[Flags]
|
||||||
public enum PanelSides
|
public enum PanelSides
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -8,6 +8,7 @@
|
|||||||
*/
|
*/
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
using System;
|
||||||
using OpenRA.Network;
|
using OpenRA.Network;
|
||||||
using OpenRA.Widgets;
|
using OpenRA.Widgets;
|
||||||
|
|
||||||
@@ -28,17 +29,25 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
preview.OnMouseDown = mi => LobbyUtils.SelectSpawnPoint(orderManager, preview, lobby.Map, mi);
|
preview.OnMouseDown = mi => LobbyUtils.SelectSpawnPoint(orderManager, preview, lobby.Map, mi);
|
||||||
preview.SpawnOccupants = () => LobbyUtils.GetSpawnOccupants(orderManager.LobbyInfo, lobby.Map);
|
preview.SpawnOccupants = () => LobbyUtils.GetSpawnOccupants(orderManager.LobbyInfo, lobby.Map);
|
||||||
|
|
||||||
var title = available.GetOrNull<LabelWidget>("MAP_TITLE");
|
var titleLabel = available.GetOrNull<LabelWidget>("MAP_TITLE");
|
||||||
if (title != null)
|
if (titleLabel != null)
|
||||||
title.GetText = () => lobby.Map.Title;
|
{
|
||||||
|
var font = Game.Renderer.Fonts[titleLabel.Font];
|
||||||
|
var title = new CachedTransform<MapPreview, string>(m => WidgetUtils.TruncateText(m.Title, titleLabel.Bounds.Width, font));
|
||||||
|
titleLabel.GetText = () => title.Update(lobby.Map);
|
||||||
|
}
|
||||||
|
|
||||||
var type = available.GetOrNull<LabelWidget>("MAP_TYPE");
|
var typeLabel = available.GetOrNull<LabelWidget>("MAP_TYPE");
|
||||||
if (type != null)
|
if (typeLabel != null)
|
||||||
type.GetText = () => lobby.Map.Type;
|
typeLabel.GetText = () => lobby.Map.Type;
|
||||||
|
|
||||||
var author = available.GetOrNull<LabelWidget>("MAP_AUTHOR");
|
var authorLabel = available.GetOrNull<LabelWidget>("MAP_AUTHOR");
|
||||||
if (author != null)
|
if (authorLabel != null)
|
||||||
author.GetText = () => "Created by {0}".F(lobby.Map.Author);
|
{
|
||||||
|
var font = Game.Renderer.Fonts[authorLabel.Font];
|
||||||
|
var author = new CachedTransform<MapPreview, string>(m => WidgetUtils.TruncateText("Created by {0}".F(lobby.Map.Author), authorLabel.Bounds.Width, font));
|
||||||
|
authorLabel.GetText = () => author.Update(lobby.Map);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var invalid = widget.GetOrNull("MAP_INVALID");
|
var invalid = widget.GetOrNull("MAP_INVALID");
|
||||||
|
|||||||
@@ -291,7 +291,9 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
public static void SetupNameWidget(Widget parent, Session.Slot s, Session.Client c)
|
public static void SetupNameWidget(Widget parent, Session.Slot s, Session.Client c)
|
||||||
{
|
{
|
||||||
var name = parent.Get<LabelWidget>("NAME");
|
var name = parent.Get<LabelWidget>("NAME");
|
||||||
name.GetText = () => c.Name;
|
var font = Game.Renderer.Fonts[name.Font];
|
||||||
|
var label = WidgetUtils.TruncateText(c.Name, name.Bounds.Width, font);
|
||||||
|
name.GetText = () => label;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void SetupEditableSlotWidget(Widget parent, Session.Slot s, Session.Client c, OrderManager orderManager, Ruleset rules)
|
public static void SetupEditableSlotWidget(Widget parent, Session.Slot s, Session.Client c, OrderManager orderManager, Ruleset rules)
|
||||||
|
|||||||
@@ -235,7 +235,12 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
item.IsVisible = () => item.RenderBounds.IntersectsWith(scrollpanels[tab].RenderBounds);
|
item.IsVisible = () => item.RenderBounds.IntersectsWith(scrollpanels[tab].RenderBounds);
|
||||||
|
|
||||||
var titleLabel = item.Get<LabelWidget>("TITLE");
|
var titleLabel = item.Get<LabelWidget>("TITLE");
|
||||||
titleLabel.GetText = () => preview.Title;
|
if (titleLabel != null)
|
||||||
|
{
|
||||||
|
var font = Game.Renderer.Fonts[titleLabel.Font];
|
||||||
|
var title = WidgetUtils.TruncateText(preview.Title, titleLabel.Bounds.Width, font);
|
||||||
|
titleLabel.GetText = () => title;
|
||||||
|
}
|
||||||
|
|
||||||
var previewWidget = item.Get<MapPreviewWidget>("PREVIEW");
|
var previewWidget = item.Get<MapPreviewWidget>("PREVIEW");
|
||||||
previewWidget.Preview = () => preview;
|
previewWidget.Preview = () => preview;
|
||||||
@@ -246,7 +251,11 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
|
|
||||||
var authorWidget = item.GetOrNull<LabelWidget>("AUTHOR");
|
var authorWidget = item.GetOrNull<LabelWidget>("AUTHOR");
|
||||||
if (authorWidget != null)
|
if (authorWidget != null)
|
||||||
authorWidget.GetText = () => "Created by {0}".F(preview.Author);
|
{
|
||||||
|
var font = Game.Renderer.Fonts[authorWidget.Font];
|
||||||
|
var author = WidgetUtils.TruncateText("Created by {0}".F(preview.Author), authorWidget.Bounds.Width, font);
|
||||||
|
authorWidget.GetText = () => author;
|
||||||
|
}
|
||||||
|
|
||||||
var sizeWidget = item.GetOrNull<LabelWidget>("SIZE");
|
var sizeWidget = item.GetOrNull<LabelWidget>("SIZE");
|
||||||
if (sizeWidget != null)
|
if (sizeWidget != null)
|
||||||
|
|||||||
@@ -198,7 +198,12 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
|
|
||||||
var mapTitle = widget.GetOrNull<LabelWidget>("SELECTED_MAP");
|
var mapTitle = widget.GetOrNull<LabelWidget>("SELECTED_MAP");
|
||||||
if (mapTitle != null)
|
if (mapTitle != null)
|
||||||
mapTitle.GetText = () => currentMap != null ? currentMap.Title : "No Server Selected";
|
{
|
||||||
|
var font = Game.Renderer.Fonts[mapTitle.Font];
|
||||||
|
var title = new CachedTransform<MapPreview, string>(m => m == null ? "No Server Selected" :
|
||||||
|
WidgetUtils.TruncateText(m.Title, mapTitle.Bounds.Width, font));
|
||||||
|
mapTitle.GetText = () => title.Update(currentMap);
|
||||||
|
}
|
||||||
|
|
||||||
var ip = widget.GetOrNull<LabelWidget>("SELECTED_IP");
|
var ip = widget.GetOrNull<LabelWidget>("SELECTED_IP");
|
||||||
if (ip != null)
|
if (ip != null)
|
||||||
@@ -219,8 +224,11 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
if (modVersion != null)
|
if (modVersion != null)
|
||||||
{
|
{
|
||||||
modVersion.IsVisible = () => currentServer != null;
|
modVersion.IsVisible = () => currentServer != null;
|
||||||
modVersion.GetText = () => currentServer.ModLabel;
|
|
||||||
modVersion.GetColor = () => currentServer.IsCompatible ? modVersion.TextColor : incompatibleVersionColor;
|
modVersion.GetColor = () => currentServer.IsCompatible ? modVersion.TextColor : incompatibleVersionColor;
|
||||||
|
|
||||||
|
var font = Game.Renderer.Fonts[modVersion.Font];
|
||||||
|
var version = new CachedTransform<GameServer, string>(s => WidgetUtils.TruncateText(s.ModLabel, mapTitle.Bounds.Width, font));
|
||||||
|
modVersion.GetText = () => version.Update(currentServer);
|
||||||
}
|
}
|
||||||
|
|
||||||
var players = widget.GetOrNull<LabelWidget>("SELECTED_PLAYERS");
|
var players = widget.GetOrNull<LabelWidget>("SELECTED_PLAYERS");
|
||||||
@@ -358,7 +366,9 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
var title = item.GetOrNull<LabelWidget>("TITLE");
|
var title = item.GetOrNull<LabelWidget>("TITLE");
|
||||||
if (title != null)
|
if (title != null)
|
||||||
{
|
{
|
||||||
title.GetText = () => game.Name;
|
var font = Game.Renderer.Fonts[title.Font];
|
||||||
|
var label = WidgetUtils.TruncateText(game.Name, title.Bounds.Width, font);
|
||||||
|
title.GetText = () => label;
|
||||||
title.GetColor = () => canJoin ? title.TextColor : incompatibleGameColor;
|
title.GetColor = () => canJoin ? title.TextColor : incompatibleGameColor;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -71,9 +71,15 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
preview.SpawnOccupants = () => selectedSpawns;
|
preview.SpawnOccupants = () => selectedSpawns;
|
||||||
preview.Preview = () => selectedReplay != null ? selectedReplay.GameInfo.MapPreview : null;
|
preview.Preview = () => selectedReplay != null ? selectedReplay.GameInfo.MapPreview : null;
|
||||||
|
|
||||||
var title = panel.GetOrNull<LabelWidget>("MAP_TITLE");
|
var titleLabel = panel.GetOrNull<LabelWidget>("MAP_TITLE");
|
||||||
if (title != null)
|
if (titleLabel != null)
|
||||||
title.GetText = () => selectedReplay != null ? selectedReplay.GameInfo.MapPreview.Title : null;
|
{
|
||||||
|
titleLabel.IsVisible = () => selectedReplay != null;
|
||||||
|
|
||||||
|
var font = Game.Renderer.Fonts[titleLabel.Font];
|
||||||
|
var title = new CachedTransform<MapPreview, string>(m => WidgetUtils.TruncateText(m.Title, titleLabel.Bounds.Width, font));
|
||||||
|
titleLabel.GetText = () => title.Update(selectedReplay.GameInfo.MapPreview);
|
||||||
|
}
|
||||||
|
|
||||||
var type = panel.GetOrNull<LabelWidget>("MAP_TYPE");
|
var type = panel.GetOrNull<LabelWidget>("MAP_TYPE");
|
||||||
if (type != null)
|
if (type != null)
|
||||||
|
|||||||
@@ -52,7 +52,14 @@ namespace OpenRA.Mods.Common.Widgets.Logic
|
|||||||
};
|
};
|
||||||
|
|
||||||
panel.Get<MapPreviewWidget>("MAP_PREVIEW").Preview = () => preview;
|
panel.Get<MapPreviewWidget>("MAP_PREVIEW").Preview = () => preview;
|
||||||
panel.Get<LabelWidget>("MAP_NAME").GetText = () => preview.Title;
|
|
||||||
|
var mapTitle = panel.Get<LabelWidget>("MAP_NAME");
|
||||||
|
if (mapTitle != null)
|
||||||
|
{
|
||||||
|
var font = Game.Renderer.Fonts[mapTitle.Font];
|
||||||
|
var title = new CachedTransform<MapPreview, string>(m => WidgetUtils.TruncateText(m.Title, mapTitle.Bounds.Width, font));
|
||||||
|
mapTitle.GetText = () => title.Update(preview);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var serverName = panel.Get<TextFieldWidget>("SERVER_NAME");
|
var serverName = panel.Get<TextFieldWidget>("SERVER_NAME");
|
||||||
|
|||||||
@@ -89,25 +89,25 @@ Container@MAPCHOOSER_PANEL:
|
|||||||
IgnoreMouseOver: true
|
IgnoreMouseOver: true
|
||||||
IgnoreMouseInput: true
|
IgnoreMouseInput: true
|
||||||
Label@TITLE:
|
Label@TITLE:
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-48
|
Y: PARENT_BOTTOM-48
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
Align: Center
|
Align: Center
|
||||||
Label@DETAILS:
|
Label@DETAILS:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-34
|
Y: PARENT_BOTTOM-34
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
Label@AUTHOR:
|
Label@AUTHOR:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-22
|
Y: PARENT_BOTTOM-22
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
Label@SIZE:
|
Label@SIZE:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-10
|
Y: PARENT_BOTTOM-10
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
|
|||||||
@@ -60,25 +60,25 @@ Background@MAPCHOOSER_PANEL:
|
|||||||
IgnoreMouseOver: true
|
IgnoreMouseOver: true
|
||||||
IgnoreMouseInput: true
|
IgnoreMouseInput: true
|
||||||
Label@TITLE:
|
Label@TITLE:
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-53
|
Y: PARENT_BOTTOM-53
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
Align: Center
|
Align: Center
|
||||||
Label@DETAILS:
|
Label@DETAILS:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-37
|
Y: PARENT_BOTTOM-37
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
Label@AUTHOR:
|
Label@AUTHOR:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-25
|
Y: PARENT_BOTTOM-25
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
Label@SIZE:
|
Label@SIZE:
|
||||||
Width: PARENT_RIGHT-4
|
Width: PARENT_RIGHT-8
|
||||||
X: 2
|
X: 4
|
||||||
Y: PARENT_BOTTOM-13
|
Y: PARENT_BOTTOM-13
|
||||||
Align: Center
|
Align: Center
|
||||||
Font: Tiny
|
Font: Tiny
|
||||||
|
|||||||
Reference in New Issue
Block a user