Пример #1
0
        public ActorEditLogic(Widget widget, World world, WorldRenderer worldRenderer, Dictionary <string, MiniYaml> logicArgs)
        {
            this.worldRenderer  = worldRenderer;
            editorActorLayer    = world.WorldActor.Trait <EditorActorLayer>();
            editorActionManager = world.WorldActor.Trait <EditorActionManager>();

            editor         = widget.Parent.Get <EditorViewportControllerWidget>("MAP_EDITOR");
            actorEditPanel = editor.Get <BackgroundWidget>("ACTOR_EDIT_PANEL");

            typeLabel    = actorEditPanel.Get <LabelWidget>("ACTOR_TYPE_LABEL");
            actorIDField = actorEditPanel.Get <TextFieldWidget>("ACTOR_ID");

            initContainer   = actorEditPanel.Get("ACTOR_INIT_CONTAINER");
            buttonContainer = actorEditPanel.Get("BUTTON_CONTAINER");

            checkboxOptionTemplate = initContainer.Get("CHECKBOX_OPTION_TEMPLATE");
            sliderOptionTemplate   = initContainer.Get("SLIDER_OPTION_TEMPLATE");
            dropdownOptionTemplate = initContainer.Get("DROPDOWN_OPTION_TEMPLATE");
            initContainer.RemoveChildren();

            var deleteButton = actorEditPanel.Get <ButtonWidget>("DELETE_BUTTON");
            var cancelButton = actorEditPanel.Get <ButtonWidget>("CANCEL_BUTTON");
            var okButton     = actorEditPanel.Get <ButtonWidget>("OK_BUTTON");

            actorIDErrorLabel           = actorEditPanel.Get <LabelWidget>("ACTOR_ID_ERROR_LABEL");
            actorIDErrorLabel.IsVisible = () => actorIDStatus != ActorIDStatus.Normal;
            actorIDErrorLabel.GetText   = () => actorIDStatus == ActorIDStatus.Duplicate ?
                                          "Duplicate Actor ID" : "Enter an Actor ID";

            MiniYaml yaml;

            if (logicArgs.TryGetValue("EditPanelPadding", out yaml))
            {
                editPanelPadding = FieldLoader.GetValue <int>("EditPanelPadding", yaml.Value);
            }

            okButton.IsDisabled      = () => !IsValid() || !editActorPreview.IsDirty;
            okButton.OnClick         = Save;
            cancelButton.OnClick     = Cancel;
            deleteButton.OnClick     = Delete;
            actorEditPanel.IsVisible = () => CurrentActor != null &&
                                       editor.CurrentBrush == editor.DefaultBrush &&
                                       Game.RunTime > lastScrollTime + scrollVisibleTimeout;

            actorIDField.OnEscKey = () =>
            {
                actorIDField.YieldKeyboardFocus();
                return(true);
            };

            actorIDField.OnTextEdited = () =>
            {
                var actorId = actorIDField.Text.Trim();
                if (string.IsNullOrWhiteSpace(actorId))
                {
                    nextActorIDStatus = ActorIDStatus.Empty;
                    return;
                }

                // Check for duplicate actor ID
                if (CurrentActor.ID.Equals(actorId, StringComparison.OrdinalIgnoreCase))
                {
                    if (editorActorLayer[actorId] != null)
                    {
                        nextActorIDStatus = ActorIDStatus.Duplicate;
                        return;
                    }
                }

                SetActorID(actorId);
                nextActorIDStatus = ActorIDStatus.Normal;
            };

            actorIDField.OnLoseFocus = () =>
            {
                // Reset invalid IDs back to their starting value
                if (actorIDStatus != ActorIDStatus.Normal)
                {
                    SetActorID(initialActorID);
                }
            };
        }
Пример #2
0
        void SetActorID(string actorId)
        {
            editActorPreview.SetActorID(actorId);

            nextActorIDStatus = ActorIDStatus.Normal;
        }
Пример #3
0
        public override void Tick()
        {
            if (actorIDStatus != nextActorIDStatus)
            {
                if ((actorIDStatus & nextActorIDStatus) == 0)
                {
                    var offset = actorIDErrorLabel.Bounds.Height;
                    if (nextActorIDStatus == ActorIDStatus.Normal)
                    {
                        offset *= -1;
                    }

                    actorEditPanel.Bounds.Height += offset;
                    initContainer.Bounds.Y       += offset;
                    buttonContainer.Bounds.Y     += offset;
                }

                actorIDStatus = nextActorIDStatus;
            }

            var actor = editor.DefaultBrush.SelectedActor;

            if (actor != null)
            {
                var origin = worldRenderer.Viewport.WorldToViewPx(new int2(actor.Bounds.Right, actor.Bounds.Top));

                // If we scrolled, hide the edit box for a moment
                if (lastScrollPosition.X != origin.X || lastScrollPosition.Y != origin.Y)
                {
                    lastScrollTime     = Game.RunTime;
                    lastScrollPosition = origin;
                }

                // If we changed actor, move widgets
                if (CurrentActor != actor)
                {
                    lastScrollTime = 0;                     // Ensure visible
                    CurrentActor   = actor;

                    editActorPreview = new EditActorPreview(CurrentActor);

                    initialActorID = actorIDField.Text = actor.ID;

                    var font          = Game.Renderer.Fonts[typeLabel.Font];
                    var truncatedType = WidgetUtils.TruncateText(actor.DescriptiveName, typeLabel.Bounds.Width, font);
                    typeLabel.Text = truncatedType;

                    actorIDField.CursorPosition = actor.ID.Length;
                    nextActorIDStatus           = ActorIDStatus.Normal;

                    // Remove old widgets
                    var oldInitHeight = initContainer.Bounds.Height;
                    initContainer.Bounds.Height = 0;
                    initContainer.RemoveChildren();

                    // Add owner dropdown
                    var ownerContainer = dropdownOptionTemplate.Clone();
                    ownerContainer.Get <LabelWidget>("LABEL").GetText = () => "Owner";
                    var ownerDropdown = ownerContainer.Get <DropDownButtonWidget>("OPTION");
                    var selectedOwner = actor.Owner;

                    Action <EditorActorPreview, PlayerReference> updateOwner = (preview, reference) =>
                    {
                        preview.Owner = reference;
                        preview.ReplaceInit(new OwnerInit(reference.Name));
                    };

                    var ownerHandler = new EditorActorOptionActionHandle <PlayerReference>(updateOwner, actor.Owner);
                    editActorPreview.Add(ownerHandler);

                    Func <PlayerReference, ScrollItemWidget, ScrollItemWidget> setupItem = (option, template) =>
                    {
                        var item = ScrollItemWidget.Setup(template, () => selectedOwner == option, () =>
                        {
                            selectedOwner = option;
                            updateOwner(CurrentActor, selectedOwner);
                            ownerHandler.OnChange(option);
                        });

                        item.Get <LabelWidget>("LABEL").GetText = () => option.Name;
                        item.GetColor = () => option.Color;
                        return(item);
                    };

                    ownerDropdown.GetText  = () => selectedOwner.Name;
                    ownerDropdown.GetColor = () => selectedOwner.Color;
                    ownerDropdown.OnClick  = () =>
                    {
                        var owners = editorActorLayer.Players.Players.Values.OrderBy(p => p.Name);
                        ownerDropdown.ShowDropDown("LABEL_DROPDOWN_TEMPLATE", 270, owners, setupItem);
                    };

                    initContainer.Bounds.Height += ownerContainer.Bounds.Height;
                    initContainer.AddChild(ownerContainer);

                    // Add new children for inits
                    var options = actor.Info.TraitInfos <IEditorActorOptions>()
                                  .SelectMany(t => t.ActorOptions(actor.Info, worldRenderer.World))
                                  .OrderBy(o => o.DisplayOrder);

                    foreach (var o in options)
                    {
                        if (o is EditorActorCheckbox)
                        {
                            var co = (EditorActorCheckbox)o;
                            var checkboxContainer = checkboxOptionTemplate.Clone();
                            checkboxContainer.Bounds.Y   = initContainer.Bounds.Height;
                            initContainer.Bounds.Height += checkboxContainer.Bounds.Height;

                            var checkbox = checkboxContainer.Get <CheckboxWidget>("OPTION");
                            checkbox.GetText = () => co.Name;

                            var editorActionHandle = new EditorActorOptionActionHandle <bool>(co.OnChange, co.GetValue(actor));
                            editActorPreview.Add(editorActionHandle);

                            checkbox.IsChecked = () => co.GetValue(actor);
                            checkbox.OnClick   = () =>
                            {
                                var newValue = co.GetValue(actor) ^ true;
                                co.OnChange(actor, newValue);
                                editorActionHandle.OnChange(newValue);
                            };

                            initContainer.AddChild(checkboxContainer);
                        }
                        else if (o is EditorActorSlider)
                        {
                            var so = (EditorActorSlider)o;
                            var sliderContainer = sliderOptionTemplate.Clone();
                            sliderContainer.Bounds.Y     = initContainer.Bounds.Height;
                            initContainer.Bounds.Height += sliderContainer.Bounds.Height;
                            sliderContainer.Get <LabelWidget>("LABEL").GetText = () => so.Name;

                            var slider = sliderContainer.Get <SliderWidget>("OPTION");
                            slider.MinimumValue = so.MinValue;
                            slider.MaximumValue = so.MaxValue;
                            slider.Ticks        = so.Ticks;

                            var editorActionHandle = new EditorActorOptionActionHandle <float>(so.OnChange, so.GetValue(actor));
                            editActorPreview.Add(editorActionHandle);

                            slider.GetValue  = () => so.GetValue(actor);
                            slider.OnChange += value => so.OnChange(actor, value);
                            slider.OnChange += value => editorActionHandle.OnChange(value);

                            initContainer.AddChild(sliderContainer);
                        }
                        else if (o is EditorActorDropdown)
                        {
                            var ddo = (EditorActorDropdown)o;
                            var dropdownContainer = dropdownOptionTemplate.Clone();
                            dropdownContainer.Bounds.Y   = initContainer.Bounds.Height;
                            initContainer.Bounds.Height += dropdownContainer.Bounds.Height;
                            dropdownContainer.Get <LabelWidget>("LABEL").GetText = () => ddo.Name;

                            var editorActionHandle = new EditorActorOptionActionHandle <string>(ddo.OnChange, ddo.GetValue(actor));
                            editActorPreview.Add(editorActionHandle);

                            var dropdown = dropdownContainer.Get <DropDownButtonWidget>("OPTION");
                            Func <KeyValuePair <string, string>, ScrollItemWidget, ScrollItemWidget> dropdownSetup = (option, template) =>
                            {
                                var item = ScrollItemWidget.Setup(template,
                                                                  () => ddo.GetValue(actor) == option.Key,
                                                                  () =>
                                {
                                    ddo.OnChange(actor, option.Key);
                                    editorActionHandle.OnChange(option.Key);
                                });

                                item.Get <LabelWidget>("LABEL").GetText = () => option.Value;
                                return(item);
                            };

                            dropdown.GetText = () => ddo.Labels[ddo.GetValue(actor)];
                            dropdown.OnClick = () => dropdown.ShowDropDown("LABEL_DROPDOWN_TEMPLATE", 270, ddo.Labels, dropdownSetup);

                            initContainer.AddChild(dropdownContainer);
                        }
                    }

                    actorEditPanel.Bounds.Height += initContainer.Bounds.Height - oldInitHeight;
                    buttonContainer.Bounds.Y     += initContainer.Bounds.Height - oldInitHeight;
                }

                // Set the edit panel to the right of the selection border.
                actorEditPanel.Bounds.X = origin.X + editPanelPadding;
                actorEditPanel.Bounds.Y = origin.Y;
            }
            else
            {
                // Selected actor is null, hide the border and edit panel.
                actorIDField.YieldKeyboardFocus();
                CurrentActor = null;
            }
        }
Пример #4
0
 void SetActorID(World world, string actorId)
 {
     CurrentActor.ID   = actorId;
     nextActorIDStatus = ActorIDStatus.Normal;
 }