private void StringList_SelectedIndexChanged(object sender,EventArgs e) { //change selected string var ind = SelectedStringInd; bool enableMod = (ind != -1); RemoveButton.Enabled = enableMod; UpButton.Enabled = enableMod; DownButton.Enabled = enableMod; NameBox.Enabled = enableMod; OwnChange = true; if (ind == -1) { ActiveItem = null; NameBox.Text = ""; } else { ActiveItem = ActiveSLOT.Chronological[ind]; NameBox.Enabled = (ActiveSLOTLabel != null); NameBox.Text = ActiveSLOTLabel?.GetString(ind) ?? ""; } UpdateSLOTItem(); OwnChange = false; }
public override VMPrimitiveExitCode Execute(VMStackFrame context, VMPrimitiveOperand args) { var operand = (VMGotoRelativePositionOperand)args; if (context.Thread.IsCheck) { return(VMPrimitiveExitCode.GOTO_FALSE); } var obj = context.StackObject; if (obj == null) { return(VMPrimitiveExitCode.GOTO_FALSE); } var avatar = (VMAvatar)context.Caller; if (obj.Position == LotTilePos.OUT_OF_WORLD) { return(VMPrimitiveExitCode.GOTO_FALSE); } var slot = new SLOTItem { Type = 3, Standing = 1 }; if (operand.Location != VMGotoRelativeLocation.OnTopOf) //default slot is on top of { if (operand.Location == VMGotoRelativeLocation.AnywhereNear) { slot.MinProximity = 16; slot.MaxProximity = 32; //diamond shaped slot.OptimalProximity = 16; slot.Rsflags |= (SLOTFlags)255; } else { slot.MinProximity = 16; slot.MaxProximity = 24; slot.Rsflags |= (SLOTFlags)(1 << (((int)operand.Location) % 8)); } } if (operand.Direction == VMGotoRelativeDirection.AnyDirection) { slot.Facing = SLOTFacing.FaceAnywhere; //TODO: verify. not sure where this came from? } else { slot.Facing = (SLOTFacing)operand.Direction; } var pathFinder = context.Thread.PushNewRoutingFrame(context, !operand.NoFailureTrees); var success = pathFinder.InitRoutes(slot, context.StackObject); return(VMPrimitiveExitCode.CONTINUE); }
private void NewButton_Click(object sender,EventArgs e) { int ind = -1; Content.Content.Get().Changes.BlockingResMod(new ResAction(() => { ind = ActiveSLOT.Chronological.Count; var item = new SLOTItem(); ActiveSLOT.Chronological.Add(item); if (!ActiveSLOT.Slots.ContainsKey(0)) { ActiveSLOT.Slots[0] = new List <SLOTItem>(); } ActiveSLOT.Slots[0].Add(item); },ActiveSLOT)); UpdateStrings(); SelectedStringInd = ind; }
public VMSlotParser(SLOTItem slot) { Slot = slot; Flags = slot.Rsflags; MinProximity = slot.MinProximity; MaxProximity = slot.MaxProximity; DesiredProximity = slot.OptimalProximity; if (MaxProximity == 0) { MaxProximity = MinProximity; } if (DesiredProximity == 0) { DesiredProximity = MinProximity; } }
public static void SerializeInto(SLOTItem item, BinaryWriter writer) { writer.Write(item.Type); writer.Write(item.Offset.X); writer.Write(item.Offset.Y); writer.Write(item.Offset.Z); writer.Write(item.Standing); writer.Write(item.Sitting); writer.Write(item.Ground); writer.Write((int)item.Rsflags); writer.Write(item.SnapTargetSlot); writer.Write(item.MinProximity); writer.Write(item.MaxProximity); writer.Write(item.OptimalProximity); writer.Write(item.Gradient); writer.Write((int)item.Facing); writer.Write(item.Resolution); writer.Write(item.Height); }
public static SLOTItem Deserialize(BinaryReader reader) { var result = new SLOTItem(); result.Type = reader.ReadUInt16(); result.Offset = new Vector3(); result.Offset.X = reader.ReadSingle(); result.Offset.Y = reader.ReadSingle(); result.Offset.Z = reader.ReadSingle(); result.Standing = reader.ReadInt32(); result.Sitting = reader.ReadInt32(); result.Ground = reader.ReadInt32(); result.Rsflags = (SLOTFlags)reader.ReadInt32(); result.SnapTargetSlot = reader.ReadInt32(); result.MinProximity = reader.ReadInt32(); result.MaxProximity = reader.ReadInt32(); result.OptimalProximity = reader.ReadInt32(); result.Gradient = reader.ReadSingle(); result.Facing = (SLOTFacing)reader.ReadInt32(); result.Resolution = reader.ReadInt32(); result.Height = reader.ReadInt32(); return(result); }
public override VMPrimitiveExitCode Execute(VMStackFrame context, VMPrimitiveOperand args) { var operand = (VMSnapOperand)args; var avatar = context.Caller; //todo, can sometimes be an object?? see roaches object tile movement, snaps to its own routing slot var obj = context.StackObject; if (obj == context.Caller) { foreach (var objSub in obj.MultitileGroup.Objects) { objSub.MovedSelf = true; } if (obj is VMGameObject) { if (VM.UseWorld) { // the object moving this object may not be the caller... // for instance, we can be moved with a call tree. // we want to use the idle timings for that thread rather than our own. var idleObjID = context.VM.Scheduler.CurrentObjectID; var idleObj = context.VM.GetObjectById(idleObjID) ?? obj; foreach (var obj2 in obj.MultitileGroup.Objects) { obj2.WorldUI.PrepareSnapInterpolation(idleObj.WorldUI); } } } } if (operand.OriginOnly) { } //origin only. unused? SLOTItem slot = null; switch (operand.Mode) { case VMSnapSlotScope.StackVariable: slot = VMMemory.GetSlot(context, VMSlotScope.StackVariable, operand.Index); break; case VMSnapSlotScope.BeContained: return((context.StackObject.PlaceInSlot(context.Caller, 0, true, context.VM.Context)) ? VMPrimitiveExitCode.GOTO_TRUE : VMPrimitiveExitCode.GOTO_FALSE); case VMSnapSlotScope.InFront: slot = new SLOTItem { Type = 3, Standing = 1, MinProximity = 16, Rsflags = SLOTFlags.NORTH }; break; case VMSnapSlotScope.Literal: slot = VMMemory.GetSlot(context, VMSlotScope.Literal, operand.Index); break; case VMSnapSlotScope.Global: slot = VMMemory.GetSlot(context, VMSlotScope.Global, operand.Index); break; } if (slot == null) { return(VMPrimitiveExitCode.GOTO_FALSE); } var dirSnap = (slot.Rsflags & SLOTFlags.SnapToDirection) > 0; if (operand.Mode != VMSnapSlotScope.BeContained) { var parser = new VMSlotParser(slot); var locations = parser.FindAvaliableLocations(obj, context.VM.Context, avatar); if (slot.SnapTargetSlot > -1) { if (!context.StackObject.PlaceInSlot(context.Caller, slot.SnapTargetSlot, true, context.VM.Context)) { return(VMPrimitiveExitCode.GOTO_FALSE); } if (locations.Count > 0) { avatar.RadianDirection = ((slot.Rsflags & SLOTFlags.SnapToDirection) > 0) ? locations[0].RadianDirection: avatar.RadianDirection; } } else { if (locations.Count > 0) { if (!SetPosition(avatar, locations[0].Position, (dirSnap) ? locations[0].RadianDirection : avatar.RadianDirection, operand.Shoo, context.VM.Context)) { //set direction regardless. TS1, experimental, breaks chairs snapping onto avatars. if this were correct, it also needs to be in the false branch. //if (dirSnap) avatar.RadianDirection = locations[0].RadianDirection; return(VMPrimitiveExitCode.GOTO_FALSE); } } else { if (parser.FailCode == Model.Routing.VMRouteFailCode.NoValidGoals) { avatar.SetValue(VMStackObjectVariable.PrimitiveResult, 2); } avatar.SetValue(VMStackObjectVariable.PrimitiveResultID, (parser.Blocker == null) ? (short)0 : parser.Blocker.ObjectID); return(VMPrimitiveExitCode.GOTO_FALSE); } } } return(VMPrimitiveExitCode.GOTO_TRUE); }
public override void Deserialize(BinaryReader reader) { base.Deserialize(reader); var roomN = reader.ReadInt32(); Rooms = new VMRoomPortal[roomN]; for (int i = 0; i < roomN; i++) { Rooms[i] = new VMRoomPortal(reader); } if (reader.ReadBoolean()) { CurrentPortal = new VMRoomPortal(reader); } var wtLen = reader.ReadInt32(); if (wtLen > -1) { WalkTo = new Point[wtLen]; for (int i = 0; i < wtLen; i++) { WalkTo[i] = new Point(reader.ReadInt32(), reader.ReadInt32()); } } WalkDirection = reader.ReadDouble(); TargetDirection = reader.ReadDouble(); IgnoreRooms = reader.ReadBoolean(); State = (VMRoutingFrameState)reader.ReadByte(); PortalTurns = reader.ReadInt32(); WaitTime = reader.ReadInt32(); Timeout = reader.ReadInt32(); Retries = reader.ReadInt32(); AttemptedChair = reader.ReadBoolean(); TurnTweak = reader.ReadSingle(); TurnFrames = reader.ReadInt32(); MoveTotalFrames = reader.ReadInt32(); MoveFrames = reader.ReadInt32(); Velocity = reader.ReadInt32(); CallFailureTrees = reader.ReadBoolean(); var igrN = reader.ReadInt32(); IgnoredRooms = new VMRoomPortal[igrN]; for (int i = 0; i < igrN; i++) { IgnoredRooms[i] = new VMRoomPortal(reader); } var avaN = reader.ReadInt32(); AvatarsToConsider = new short[avaN]; for (int i = 0; i < avaN; i++) { AvatarsToConsider[i] = reader.ReadInt16(); } PreviousPosition.Deserialize(reader); CurrentWaypoint.Deserialize(reader); RoomRouteInvalid = reader.ReadBoolean(); if (reader.ReadBoolean()) { Slot = SLOTItemSerializer.Deserialize(reader); } Target = reader.ReadInt16(); var chLen = reader.ReadInt32(); if (chLen > -1) { Choices = new VMFindLocationResultMarshal[chLen]; for (int i = 0; i < chLen; i++) { Choices[i] = new VMFindLocationResultMarshal(); Choices[i].Deserialize(reader); } } if (reader.ReadBoolean()) { CurRoute = new VMFindLocationResultMarshal(); CurRoute.Deserialize(reader); } if (Version > 29) { LastWalkStyle = reader.ReadInt16(); } }
public override VMPrimitiveExitCode Execute(VMStackFrame context, VMPrimitiveOperand args) { var operand = (VMSnapOperand)args; var avatar = context.Caller; //todo, can sometimes be an object?? see roaches object tile movement, snaps to its own routing slot var obj = context.StackObject; SLOTItem slot = null; switch (operand.Mode) { case VMSnapSlotScope.StackVariable: slot = VMMemory.GetSlot(context, VMSlotScope.StackVariable, operand.Index); break; case VMSnapSlotScope.BeContained: return((context.StackObject.PlaceInSlot(context.Caller, 0, true, context.VM.Context)) ? VMPrimitiveExitCode.GOTO_TRUE:VMPrimitiveExitCode.GOTO_FALSE); case VMSnapSlotScope.InFront: slot = new SLOTItem { Type = 3, Standing = 1, MinProximity = 16, Rsflags = SLOTFlags.NORTH }; break; case VMSnapSlotScope.Literal: slot = VMMemory.GetSlot(context, VMSlotScope.Literal, operand.Index); break; case VMSnapSlotScope.Global: slot = VMMemory.GetSlot(context, VMSlotScope.Global, operand.Index); break; } if (operand.Mode != VMSnapSlotScope.BeContained) { var parser = new VMSlotParser(slot); var locations = parser.FindAvaliableLocations(obj, context.VM.Context, avatar); if (slot.SnapTargetSlot > -1) { if (!context.StackObject.PlaceInSlot(context.Caller, slot.SnapTargetSlot, true, context.VM.Context)) { return(VMPrimitiveExitCode.GOTO_FALSE); } if (locations.Count > 0) { avatar.RadianDirection = ((slot.Rsflags & SLOTFlags.SnapToDirection) > 0) ? locations[0].RadianDirection: avatar.RadianDirection; } } else { if (locations.Count > 0) { if (!SetPosition(avatar, locations[0].Position, ((slot.Rsflags & SLOTFlags.SnapToDirection) > 0) ? locations[0].RadianDirection : avatar.RadianDirection, context.VM.Context)) { return(VMPrimitiveExitCode.GOTO_FALSE); } } else { avatar.SetValue(VMStackObjectVariable.PrimitiveResultID, (parser.Blocker == null) ? (short)0 : parser.Blocker.ObjectID); return(VMPrimitiveExitCode.GOTO_FALSE); } } } return(VMPrimitiveExitCode.GOTO_TRUE); }
/// <summary> /// This method will find all the avaliable locations within the criteria ordered by proximity to the optimal proximity /// External functions can then decide which is most desirable. E.g. the nearest slot to the object may be the longest route if /// its in another room. /// </summary> /// <param name="position"></param> /// <param name="flags"></param> /// <param name="minProximity"></param> /// <param name="maxProximity"></param> /// <param name="desiredProximity"></param> /// <returns></returns> public static List <VMFindLocationResult> FindAvaliableLocations(VMEntity obj, SLOTItem slot, VMContext context) { /** * Start at min proximity and circle around the object to find the avaliable locations. * Then pick the one nearest to the optimal value */ Vector2 center = new Vector2(obj.Position.X, obj.Position.Y); if (obj is VMAvatar) { center -= new Vector2(0.5f, 0.5f); } var rotOff = Vector3.Transform(slot.Offset, Matrix.CreateRotationZ(ObjectRotAsRad(obj.Direction))); center += new Vector2(rotOff.X / 16, rotOff.Y / 16); SLOTFlags flags = slot.Rsflags; if (slot.Facing == -3) { flags |= SLOTFlags.FacingAwayFromObject; } int minProximity = slot.MinProximity; int maxProximity = slot.MaxProximity; int desiredProximity = slot.OptimalProximity; if (maxProximity == 0) { maxProximity = minProximity; } if (desiredProximity == 0) { desiredProximity = minProximity; } var result = new List <VMFindLocationResult>(); if (flags == 0) { flags |= SLOTFlags.SOUTH; //if flags are not set, location is literally in the exact position (no proximity) flags = RotateByObjectDir(flags, obj.Direction, false); result.Add(new VMFindLocationResult { Flags = flags, Position = new Vector3(center.X + 0.5f, center.Y + 0.5f, 0), //force ground floor for now Proximity = 0 }); return(result); } var proximity = minProximity; var proximityIncrement = 16; var proximityNudge = proximityIncrement * 0.25f; var currentDepth = 1.0f; //rotate directional facing flags if slot flags are not "absolute". flags = RotateByObjectDir(flags, obj.Direction, false); while (proximity <= maxProximity) { var angle = 0.0f; /** Every time we move out by 1 tile in proximity, there will be more tiles to look at **/ var angleIncrement = 360.0f / (currentDepth * 8); while (angle < 360.0f) { var radians = angle * (Math.PI / 180.0f); var radius = proximity + proximityNudge; var xpos = Math.Round(radius * Math.Cos(radians)); var ypos = Math.Round(radius * Math.Sin(radians)); var tileX = (float)Math.Round(xpos / 16.0f) + center.X; var tileY = (float)Math.Round(ypos / 16.0f) + center.Y; if (!context.SolidToAvatars(new VMTilePos((short)(tileX + 0.5f), (short)(tileY + 0.5f), 1))) { //we want to find slots where ANDing the rotated direction against a criteria (eg, facing towards, away) results in a value that is not 0. SLOTFlags criteria = (SLOTFlags)255; if ((flags & SLOTFlags.FacingAwayFromObject) == SLOTFlags.FacingAwayFromObject) { criteria = GetDirection(center, new Vector2(tileX, tileY)); } else { criteria = GetDirection(new Vector2(tileX, tileY), center); } var temp = (flags & criteria); if (temp > 0 || (flags & SLOTFlags.FaceAnywhere) == SLOTFlags.FaceAnywhere) //criteria met, add this location { result.Add(new VMFindLocationResult { Flags = temp | (flags & unchecked ((SLOTFlags)0xFFFFFF00)), Position = new Vector3(tileX + 0.5f, tileY + 0.5f, 0), //force ground floor for now Proximity = proximity }); } } angle += angleIncrement; } proximity += proximityIncrement; } /** Sort by how close they are to desired proximity **/ //result.Sort(new VMProximitySorter(desiredProximity)); return(result); }
public override void Deserialize(BinaryReader reader) { base.Deserialize(reader); var bezierRouting = (Version > 31); var roomN = reader.ReadInt32(); Rooms = new VMRoomPortal[roomN]; for (int i = 0; i < roomN; i++) { Rooms[i] = new VMRoomPortal(reader); } if (reader.ReadBoolean()) { CurrentPortal = new VMRoomPortal(reader); } var wtLen = reader.ReadInt32(); Point[] points = null; if (wtLen > -1) { WalkTo = new VMIPathSegment[wtLen]; if (bezierRouting) { for (int i = 0; i < wtLen; i++) { WalkTo[i] = ReadGenericSegment(reader); } } else { //old point list. convert to line segments. points = new Point[wtLen]; for (int i = 0; i < wtLen; i++) { points[i] = new Point(reader.ReadInt32(), reader.ReadInt32()); } } } WalkDirection = reader.ReadDouble(); TargetDirection = reader.ReadDouble(); IgnoreRooms = reader.ReadBoolean(); State = (VMRoutingFrameState)reader.ReadByte(); PortalTurns = reader.ReadInt32(); WaitTime = reader.ReadInt32(); Timeout = reader.ReadInt32(); Retries = reader.ReadInt32(); AttemptedChair = reader.ReadBoolean(); TurnTweak = reader.ReadSingle(); TurnFrames = reader.ReadInt32(); MoveTotalFrames = reader.ReadInt32(); MoveFrames = reader.ReadInt32(); Velocity = reader.ReadInt32(); CallFailureTrees = reader.ReadBoolean(); var igrN = reader.ReadInt32(); IgnoredRooms = new VMRoomPortal[igrN]; for (int i = 0; i < igrN; i++) { IgnoredRooms[i] = new VMRoomPortal(reader); } var avaN = reader.ReadInt32(); AvatarsToConsider = new short[avaN]; for (int i = 0; i < avaN; i++) { AvatarsToConsider[i] = reader.ReadInt16(); } LotTilePos CurrentWaypoint = new LotTilePos(); PreviousPosition.Deserialize(reader); if (bezierRouting) { CurrentPath = ReadGenericSegment(reader); } else { //convert old format into new CurrentWaypoint.Deserialize(reader); CurrentPath = new VMPathLineSegment( new Point(PreviousPosition.x * 0x8000, PreviousPosition.y * 0x8000), new Point(CurrentWaypoint.x * 0x8000, CurrentWaypoint.y * 0x8000)); if (points != null) { if (points.Length > 0) { WalkTo = new VMIPathSegment[points.Length]; WalkTo[0] = new VMPathLineSegment( new Point(CurrentWaypoint.x * 0x8000, CurrentWaypoint.y * 0x8000), new Point(points[0].X * 0x8000, points[0].Y * 0x8000)); for (int i = 1; i < WalkTo.Length; i++) { WalkTo[i] = new VMPathLineSegment( new Point(points[i - 1].X * 0x8000, points[i - 1].Y * 0x8000), new Point(points[i].X * 0x8000, points[i].Y * 0x8000)); } } else { WalkTo = new VMIPathSegment[0]; } } else { WalkTo = null; } } CurrentPath.CalculateTotalFrames(); CurrentPath.UpdateTotalFrames(MoveTotalFrames); CurrentPath.ResetToFrame(MoveFrames); RoomRouteInvalid = reader.ReadBoolean(); if (reader.ReadBoolean()) { Slot = SLOTItemSerializer.Deserialize(reader); } Target = reader.ReadInt16(); var chLen = reader.ReadInt32(); if (chLen > -1) { Choices = new VMFindLocationResultMarshal[chLen]; for (int i = 0; i < chLen; i++) { Choices[i] = new VMFindLocationResultMarshal(); Choices[i].Deserialize(reader); } } if (reader.ReadBoolean()) { CurRoute = new VMFindLocationResultMarshal(); CurRoute.Deserialize(reader); } if (Version > 29) { LastWalkStyle = reader.ReadInt16(); } }