feat(admin): full legacy controller set in scene-inputs editor
Build backend images / build content-svc (push) Failing after 2m19s
Build backend images / build file-svc (push) Failing after 1m18s
Build backend images / build gateway (push) Failing after 2m38s
Build backend images / build identity-svc (push) Failing after 6m44s
Build backend images / build notification-svc (push) Failing after 1m0s
Build backend images / build render-svc (push) Failing after 58s
Build backend images / build studio-svc (push) Failing after 59s

The V2 scene-inputs editor only exposed ~15 of the content model's
~40 fields. Restore full parity with the legacy admin controller.

content-svc:
- SaveContentElementRequest + ContentElementResponse widened to the
  complete field set (text/font, direction/RTL, media, advanced, DP)
- ApplyElement / ToElementResponse map every field 1:1
  (Enum.TryParse for JustifyKind + AiInputType)

frontend (SceneInputsEditor):
- common fields up top; an "advanced" toggle reveals grouped sections:
  Text and Font, Direction (RTL/LTR), Media, Advanced, Design-Presets (DP)
- editing an element loads the full field set; rows show font/hidden badges
- nullable numbers sent as null, enums as named values (snake_case body)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
soroush.asadi
2026-06-07 21:37:58 +03:30
parent bf6c04aba3
commit da3f92fbe8
3 changed files with 217 additions and 116 deletions
@@ -211,25 +211,60 @@ public class SceneColorService(ContentDbContext db)
{
e.Key = req.Key;
e.Title = req.Title;
e.LocalizedTitle = req.LocalizedTitle;
e.Hint = req.Hint;
e.Type = Enum.TryParse<ContentElementType>(req.Type, true, out var t) ? t : ContentElementType.Text;
e.DefaultValue = req.DefaultValue;
e.PositionInContainer = req.PositionInContainer;
// text + font
e.IsTextBox = req.IsTextBox;
e.MaxSize = req.MaxSize;
e.FontSize = req.FontSize;
e.DefaultFontSize = req.DefaultFontSize;
e.FontFace = req.FontFace;
e.FontFaceName = req.FontFaceName;
e.DefaultFontFace = req.DefaultFontFace;
e.IsFontChangeable = req.IsFontChangeable;
e.IsFontSizeChangeable = req.IsFontSizeChangeable;
if (req.Justify != null && Enum.TryParse<JustifyKind>(req.Justify, true, out var j)) e.Justify = j;
e.CanJustify = req.CanJustify;
// direction / RTL
e.DirectionLayerKey = req.DirectionLayerKey;
e.DirectionLayerValue = req.DirectionLayerValue;
// media
e.VideoSupport = req.VideoSupport;
e.Width = req.Width;
e.Height = req.Height;
e.Thumbnail = req.Thumbnail;
e.MinDurationSec = req.MinDurationSec;
e.MaxDurationSec = req.MaxDurationSec;
// advanced
e.MappedList = req.MappedList;
e.CounterMode = req.CounterMode;
if (req.AiInputType != null && Enum.TryParse<AiInputType>(req.AiInputType, true, out var ai)) e.AiInputType = ai;
e.IsHidden = req.IsHidden;
e.IsFocused = req.IsFocused;
e.OpacityControllerKey = req.OpacityControllerKey;
e.VirtualCount = req.VirtualCount;
// design-preset variants
e.Dp1Image = req.Dp1Image; e.Dp1Title = req.Dp1Title;
e.Dp2Image = req.Dp2Image; e.Dp2Title = req.Dp2Title;
e.Dp3Image = req.Dp3Image; e.Dp3Title = req.Dp3Title;
e.Dp4Image = req.Dp4Image; e.Dp4Title = req.Dp4Title;
}
private static ContentElementResponse ToElementResponse(SceneContentElement e) => new(
e.Id, e.SceneId, e.Key, e.Title, e.Hint, e.Type.ToString(), e.DefaultValue,
e.PositionInContainer, e.IsTextBox, e.MaxSize, e.FontSize, e.IsFontChangeable,
e.IsFontSizeChangeable, e.VideoSupport, e.Width, e.Height, e.Thumbnail);
e.Id, e.SceneId, e.Key, e.Title, e.LocalizedTitle, e.Hint, e.Type.ToString(), e.DefaultValue,
e.PositionInContainer,
e.IsTextBox, e.MaxSize, e.FontSize, e.DefaultFontSize,
e.FontFace, e.FontFaceName, e.DefaultFontFace,
e.IsFontChangeable, e.IsFontSizeChangeable, e.Justify.ToString(), e.CanJustify,
e.DirectionLayerKey, e.DirectionLayerValue,
e.VideoSupport, e.Width, e.Height, e.Thumbnail, e.MinDurationSec, e.MaxDurationSec,
e.MappedList, e.CounterMode, e.AiInputType.ToString(),
e.IsHidden, e.IsFocused, e.OpacityControllerKey, e.VirtualCount,
e.Dp1Image, e.Dp1Title, e.Dp2Image, e.Dp2Title,
e.Dp3Image, e.Dp3Title, e.Dp4Image, e.Dp4Title);
// ── helpers ─────────────────────────────────────────────────────────────
@@ -52,17 +52,39 @@ public record SaveColorPresetRequest(
// ── Scene content elements (the editable inputs inside a scene) ───────────────
public record ContentElementResponse(
Guid Id, Guid SceneId, string Key, string Title, string? Hint,
Guid Id, Guid SceneId, string Key, string Title, string? LocalizedTitle, string? Hint,
string Type, string? DefaultValue, int PositionInContainer,
bool IsTextBox, int? MaxSize, int? FontSize, bool IsFontChangeable,
bool IsFontSizeChangeable, bool VideoSupport, int? Width, int? Height,
string? Thumbnail
// text + font
bool IsTextBox, int? MaxSize, int? FontSize, int? DefaultFontSize,
string? FontFace, string? FontFaceName, string? DefaultFontFace,
bool IsFontChangeable, bool IsFontSizeChangeable, string Justify, bool CanJustify,
// direction / RTL
string? DirectionLayerKey, int DirectionLayerValue,
// media
bool VideoSupport, int? Width, int? Height, string? Thumbnail,
decimal? MinDurationSec, decimal? MaxDurationSec,
// advanced
string? MappedList, string? CounterMode, string AiInputType,
bool IsHidden, bool IsFocused, string? OpacityControllerKey, int VirtualCount,
// design-preset (dp) variants
string? Dp1Image, string? Dp1Title, string? Dp2Image, string? Dp2Title,
string? Dp3Image, string? Dp3Title, string? Dp4Image, string? Dp4Title
);
public record SaveContentElementRequest(
Guid SceneId, string Key, string Title, string? Hint,
string Type, string? DefaultValue, int PositionInContainer,
bool IsTextBox, int? MaxSize, int? FontSize,
bool IsFontChangeable, bool IsFontSizeChangeable,
bool VideoSupport, int? Width, int? Height, string? Thumbnail
Guid SceneId, string Key, string Title, string Type,
string? LocalizedTitle = null, string? Hint = null, string? DefaultValue = null,
int PositionInContainer = 0,
bool IsTextBox = false, int? MaxSize = null, int? FontSize = null, int? DefaultFontSize = null,
string? FontFace = null, string? FontFaceName = null, string? DefaultFontFace = null,
bool IsFontChangeable = false, bool IsFontSizeChangeable = false,
string? Justify = null, bool CanJustify = true,
string? DirectionLayerKey = null, int DirectionLayerValue = 0,
bool VideoSupport = false, int? Width = null, int? Height = null, string? Thumbnail = null,
decimal? MinDurationSec = null, decimal? MaxDurationSec = null,
string? MappedList = null, string? CounterMode = null, string? AiInputType = null,
bool IsHidden = false, bool IsFocused = false, string? OpacityControllerKey = null,
int VirtualCount = 1,
string? Dp1Image = null, string? Dp1Title = null, string? Dp2Image = null, string? Dp2Title = null,
string? Dp3Image = null, string? Dp3Title = null, string? Dp4Image = null, string? Dp4Title = null
);