namespace Holo.Virtual.Rooms { using Holo; using Holo.Managers; using Holo.Virtual.Rooms.Bots; using Holo.Virtual.Rooms.Games; using Holo.Virtual.Rooms.Items; using Holo.Virtual.Rooms.Pathfinding; using Holo.Virtual.Users; using Ion.Storage; using System; using System.Collections; using System.Collections.Generic; using System.Data; using System.Runtime.CompilerServices; using System.Text; using System.Threading; public class virtualRoom { private HashSet _activeGroups; private Hashtable _Bots; private string _Heightmap; private string _publicroomItems; private Thread _statusHandler; private StringBuilder _statusUpdates; private Hashtable _Users; private int doorH; internal int doorX; internal int doorY; private byte doorZ; internal string emitter; internal FloorItemManager floorItemManager; internal bool hasSwimmingPool; internal bool isPublicroom; internal gameLobby Lobby; internal int roomID; private Thread specialCastHandler; public byte[,] sqFLOORHEIGHT; private double[,] sqITEMHEIGHT; private byte[,] sqITEMROT; private furnitureStack[,] sqSTACK; private squareState[,] sqSTATE; private squareTrigger[,] sqTRIGGER; public bool[,] sqUNIT; internal WallItemManager wallItemManager; public virtualRoom(int roomID, bool isPublicroom) { string roomModel; DataRow dRow; DatabaseClient dbClient; DataTable dTable; this.roomID = roomID; this.isPublicroom = isPublicroom; using (dbClient = Eucalypt.dbManager.GetClient()) { roomModel = dbClient.getString("SELECT model FROM rooms WHERE id = '" + roomID + "'"); dRow = dbClient.getRow("SELECT door_x,door_y,door_h,door_z,heightmap,publicroom_items, swimmingpool FROM room_modeldata WHERE model = '" + roomModel + "'"); } this.doorX = Convert.ToInt32(dRow["door_x"]); this.doorY = Convert.ToInt32(dRow["door_y"]); this.doorH = Convert.ToInt32(dRow["door_h"]); this.doorZ = Convert.ToByte(dRow["door_z"]); this._Heightmap = Convert.ToString(dRow["heightmap"]); string[] tmpHeightmap = this._Heightmap.Split(new char[] { Convert.ToChar(13) }); int colX = tmpHeightmap[0].Length; int colY = tmpHeightmap.Length - 1; this.sqSTATE = new squareState[colX, colY]; this.sqFLOORHEIGHT = new byte[colX, colY]; this.sqITEMROT = new byte[colX, colY]; this.sqITEMHEIGHT = new double[colX, colY]; this.sqUNIT = new bool[colX, colY]; this.sqSTACK = new furnitureStack[colX, colY]; this.sqTRIGGER = new squareTrigger[colX, colY]; for (int y = 0; y < colY; y++) { for (int x = 0; x < colX; x++) { string _SQ = tmpHeightmap[y].Substring(x, 1).Trim().ToLower(); if (_SQ == "x") { this.sqSTATE[x, y] = squareState.Blocked; } else { this.sqSTATE[x, y] = squareState.Open; try { this.sqFLOORHEIGHT[x, y] = byte.Parse(_SQ); } catch { } } } } if (isPublicroom) { string[] Items = Convert.ToString(dRow["publicroom_items"]).Split("\n".ToCharArray()); for (int i = 0; i < Items.Length; i++) { string[] itemData = Items[i].Split(new char[] { ' ' }); int X = int.Parse(itemData[2]); int Y = int.Parse(itemData[3]); squareState sType = (squareState) int.Parse(itemData[6]); this.sqSTATE[X, Y] = sType; if (sType == squareState.Seat) { this.sqITEMROT[X, Y] = byte.Parse(itemData[5]); this.sqITEMHEIGHT[X, Y] = 1.0; } object CS$0$0002 = this._publicroomItems; this._publicroomItems = string.Concat(new object[] { CS$0$0002, itemData[0], " ", itemData[1], " ", itemData[2], " ", itemData[3], " ", itemData[4], " ", itemData[5], Convert.ToChar(13) }); } using (dbClient = Eucalypt.dbManager.GetClient()) { dTable = dbClient.getTable("SELECT object,x,y,goalx,goaly,stepx,stepy,roomid,state FROM room_modeldata_triggers WHERE model = '" + roomModel + "'"); } foreach (DataRow dbRow in dTable.Rows) { this.sqTRIGGER[Convert.ToInt32(dbRow["x"]), Convert.ToInt32(dbRow["y"])] = new squareTrigger(Convert.ToString(dbRow["object"]), Convert.ToInt32(dbRow["goalx"]), Convert.ToInt32(dbRow["goaly"]), Convert.ToInt32(dbRow["stepx"]), Convert.ToInt32(dbRow["stepy"]), Convert.ToInt32(dbRow["state"]) == 1, Convert.ToInt32(dbRow["roomid"])); } bool result = false; using (dbClient = Eucalypt.dbManager.GetClient()) { result = dbClient.findsResult("SELECT specialcast_interval FROM room_modeldata WHERE model = '" + roomModel + "' AND specialcast_interval > 0"); } if (result) { this.specialCastHandler = new Thread(new ParameterizedThreadStart(this.handleSpecialCasts)); this.specialCastHandler.Priority = ThreadPriority.Lowest; this.specialCastHandler.Start(roomModel); } using (dbClient = Eucalypt.dbManager.GetClient()) { int swimmingPool; this.hasSwimmingPool = int.TryParse(Convert.ToString(dRow["swimmingpool"]), out swimmingPool); result = dbClient.findsResult("SELECT id FROM games_lobbies WHERE id = '" + roomID + "'"); } if (result) { using (dbClient = Eucalypt.dbManager.GetClient()) { dRow = dbClient.getRow("SELECT type,rank FROM games_lobbies WHERE id = '" + roomID + "'"); } this.Lobby = new gameLobby(this, Convert.ToString(dRow["type"]) == "bb", Convert.ToString(dRow["rank"])); } } else { this.floorItemManager = new FloorItemManager(this); this.wallItemManager = new WallItemManager(this); using (dbClient = Eucalypt.dbManager.GetClient()) { dTable = dbClient.getTable("SELECT furniture.id, furniture.tid, furniture.x, furniture.y, furniture.z, furniture.h, furniture.var, furniture.wallpos FROM rooms, furniture WHERE furniture.roomid = rooms.id AND rooms.id = '" + roomID + "' ORDER BY rooms.id ASC"); } foreach (DataRow dbRow in dTable.Rows) { if (Convert.ToString(dbRow["wallpos"]) == "") { this.floorItemManager.addItem(Convert.ToInt32(dbRow["id"]), Convert.ToInt32(dbRow["tid"]), Convert.ToInt32(dbRow["x"]), Convert.ToInt32(dbRow["y"]), Convert.ToInt32(dbRow["z"]), Convert.ToDouble(dbRow["h"]), Convert.ToString(dbRow["var"])); } else { this.wallItemManager.addItem(Convert.ToInt32(dbRow["id"]), Convert.ToInt32(dbRow["tid"]), Convert.ToString(dbRow["wallpos"]), Convert.ToString(dbRow["var"]), false); } } } this._Users = new Hashtable(); this._Bots = new Hashtable(); this.loadBots(); this._activeGroups = new HashSet(); this._statusUpdates = new StringBuilder(); this._statusHandler = new Thread(new ThreadStart(this.cycleStatuses)); this._statusHandler.Start(); this.sqSTATE[this.doorX, this.doorY] = squareState.Open; } internal void addUser(virtualUser User) { if ((User._teleporterID != 0) || (User._ROOMACCESS_PRIMARY_OK && User._ROOMACCESS_SECONDARY_OK)) { DatabaseClient dbClient; User.statusManager = new virtualRoomUserStatusManager(User.userID, this.roomID); User.roomUser = new virtualRoomUser(User.userID, this.roomID, this.getFreeRoomIdentifier(), User, User.statusManager); if (User._teleporterID == 0) { User.roomUser.X = this.doorX; User.roomUser.Y = this.doorY; User.roomUser.Z1 = this.doorZ; User.roomUser.Z2 = this.doorZ; User.roomUser.H = this.doorH; } else { floorItem Teleporter = this.floorItemManager.getItem(User._teleporterID); User.roomUser.X = Teleporter.X; User.roomUser.Y = Teleporter.Y; User.roomUser.H = Teleporter.H; User.roomUser.Z1 = Teleporter.Z; User.roomUser.Z2 = Teleporter.Z; User._teleporterID = 0; this.sendData(string.Concat(new object[] { @"A\", Teleporter.ID, "/", User._Username, "/", Teleporter.Sprite })); } User.roomUser.goalX = -1; this._Users.Add(User.roomUser.roomUID, User.roomUser); if (!this.isPublicroom) { if (User._hasRights && !User._isOwner) { User.statusManager.addStatus("flatctrl", "onlyfurniture"); } if (User._isOwner) { User.statusManager.addStatus("flatctrl", "useradmin"); } using (dbClient = Eucalypt.dbManager.GetClient()) { User.roomUser.hasVoted = dbClient.findsResult(string.Concat(new object[] { "SELECT userid FROM room_votes WHERE userid = '", User.userID, "' AND roomid = '", this.roomID, "'" })); } } else { if (this.hasSwimmingPool) { using (dbClient = Eucalypt.dbManager.GetClient()) { User.roomUser.swimOutfit = dbClient.getString("SELECT figure_swim FROM users WHERE id = '" + User.userID + "'"); } } if (this.Lobby != null) { using (dbClient = Eucalypt.dbManager.GetClient()) { User.roomUser.gamePoints = dbClient.getInt(string.Concat(new object[] { "SELECT ", this.Lobby.Type, "_totalpoints FROM users WHERE id = '", User.userID, "'" })); } this.sendData(string.Concat(new object[] { "CzI", Encoding.encodeVL64(User.roomUser.roomUID), User.roomUser.gamePoints, Convert.ToChar(2), rankManager.getGameRankTitle(this.Lobby.isBattleBall, User.roomUser.gamePoints), Convert.ToChar(2) })); } } this.sendData(@"@\" + User.roomUser.detailsString); if ((User._groupID > 0) && !this._activeGroups.Contains(User._groupID)) { string groupBadge; using (dbClient = Eucalypt.dbManager.GetClient()) { groupBadge = dbClient.getString("SELECT badge FROM groups_details WHERE id = '" + User._groupID + "'"); } this.sendData(string.Concat(new object[] { "DuI", Encoding.encodeVL64(User._groupID), groupBadge, Convert.ToChar(2) })); this._activeGroups.Add(User._groupID); } roomManager.updateRoomVisitorCount(this.roomID, this._Users.Count); } } internal void checkEmotion(virtualRoomUser sourceUser, string Message) { string[] GestureList = new string[] { "sml", "agr", "sad", "srp" }; string[] Gestures_sml = new string[] { ":)", ":D" }; string[] Gestures_agr = new string[] { ">:(", ":@", ":/" }; string[] Gestures_sad = new string[] { ":(", ":'(" }; string[] Gestures_srp = new string[] { ":o", ":O", ":0" }; string[][] Gestures = new string[][] { Gestures_sml, Gestures_agr, Gestures_sad, Gestures_srp }; for (int i = 0; i < Gestures.Length; i++) { string[] currentGestures = Gestures[i]; if (Message.Split(currentGestures, StringSplitOptions.None).Length > 1) { string Gesture = GestureList[i]; sourceUser.statusManager.handleStatus("gest", Gesture, 0x1388); break; } } } internal bool containsUser(int roomUID) { return this._Users.ContainsKey(roomUID); } internal void Crash() { try { try { foreach (virtualRoomUser roomUser in this._Users.Values) { roomUser.User.sendData("@R"); roomUser.User.statusManager.Clear(); roomUser.User.statusManager = null; roomUser.User._roomID = 0; roomUser.User._inPublicroom = false; roomUser.User._ROOMACCESS_PRIMARY_OK = false; roomUser.User._ROOMACCESS_SECONDARY_OK = false; roomUser.User._isOwner = false; roomUser.User._hasRights = false; roomUser.User.Room = null; roomUser.User.roomUser = null; if (roomUser.User._tradePartnerRoomUID != -1) { roomUser.User.abortTrade(); } if (!((roomUser.User.gamePlayer == null) || roomUser.User.gamePlayer.enteringGame)) { roomUser.User.leaveGame(); } } } catch { } foreach (virtualBot roomBot in this._Bots.Values) { roomBot.Kill(); } this._Users.Clear(); this._Bots.Clear(); this._statusUpdates = null; if (!this.isPublicroom) { this.floorItemManager.Clear(); this.wallItemManager.Clear(); } else { try { this.specialCastHandler.Abort(); } catch { } if (this.Lobby != null) { this.Lobby.Clear(); } this.Lobby = null; } roomManager.removeRoom(this.roomID); this._statusHandler.Abort(); } catch { } } private void cycleStatuses() { List toRemove = new List(); while (true) { squareState[,] stateMap; int[] nextCoords; int nextX; int nextY; double nextHeight; try { foreach (virtualRoomUser roomUser in this._Users.Values) { if (roomUser.goalX == -1) { continue; } stateMap = (squareState[,]) this.sqSTATE.Clone(); try { if ((stateMap[roomUser.goalX, roomUser.goalY] == squareState.Seat) || (stateMap[roomUser.goalX, roomUser.goalY] == squareState.Bed)) { stateMap[roomUser.goalX, roomUser.goalY] = squareState.Open; } if (this.sqUNIT[roomUser.goalX, roomUser.goalY]) { stateMap[roomUser.goalX, roomUser.goalY] = squareState.Blocked; } } catch { } nextCoords = new Pathfinder(stateMap, this.sqFLOORHEIGHT, this.sqUNIT).getNext(roomUser.X, roomUser.Y, roomUser.goalX, roomUser.goalY); roomUser.statusManager.removeStatus("mv"); if (nextCoords == null) { roomUser.goalX = -1; if (this.sqTRIGGER[roomUser.X, roomUser.Y] != null) { squareTrigger Trigger = this.sqTRIGGER[roomUser.X, roomUser.Y]; if (this.hasSwimmingPool) { if ((Trigger.Object == "curtains1") || (Trigger.Object == "curtains2")) { roomUser.walkLock = true; roomUser.User.sendData("A`"); this.sendSpecialCast(Trigger.Object, "close"); } else if ((roomUser.swimOutfit != "") && Trigger.Object.Contains("Splash")) { this.sendData("AG" + Trigger.Object); if (Trigger.Object.Substring(8) == "enter") { roomUser.statusManager.dropCarrydItem(); roomUser.statusManager.addStatus("swim", ""); } else { roomUser.statusManager.removeStatus("swim"); } this.moveUser(roomUser, Trigger.stepX, Trigger.stepY, false); roomUser.goalX = Trigger.goalX; roomUser.goalY = Trigger.goalY; } } } else if (roomUser.walkDoor) { if (this._Users.Count <= 1) { this.removeUser(roomUser.roomUID, true, ""); return; } this.removeUser(roomUser.roomUID, true, ""); continue; } this._statusUpdates.Append(roomUser.statusString + Convert.ToChar(13)); } else { nextX = nextCoords[0]; nextY = nextCoords[1]; squareState nextState = this.sqSTATE[nextX, nextY]; this.sqUNIT[roomUser.X, roomUser.Y] = false; this.sqUNIT[nextX, nextY] = true; roomUser.Z1 = Rotation.Calculate(roomUser.X, roomUser.Y, nextX, nextY); roomUser.Z2 = roomUser.Z1; roomUser.statusManager.removeStatus("sit"); roomUser.statusManager.removeStatus("lay"); nextHeight = 0.0; if (nextState == squareState.Rug) { nextHeight = this.sqITEMHEIGHT[nextX, nextY]; } else { nextHeight = this.sqFLOORHEIGHT[nextX, nextY]; } roomUser.statusManager.addStatus("mv", string.Concat(new object[] { nextX, ",", nextY, ",", nextHeight.ToString().Replace(',', '.') })); this._statusUpdates.Append(roomUser.statusString + Convert.ToChar(13)); roomUser.X = nextX; roomUser.Y = nextY; roomUser.H = nextHeight; switch (nextState) { case squareState.Seat: roomUser.statusManager.removeStatus("dance"); roomUser.Z1 = this.sqITEMROT[nextX, nextY]; roomUser.Z2 = roomUser.Z1; roomUser.statusManager.addStatus("sit", this.sqITEMHEIGHT[nextX, nextY].ToString().Replace(',', '.')); break; case squareState.Bed: roomUser.statusManager.removeStatus("dance"); roomUser.Z1 = this.sqITEMROT[nextX, nextY]; roomUser.Z2 = roomUser.Z1; roomUser.statusManager.addStatus("lay", this.sqITEMHEIGHT[nextX, nextY].ToString().Replace(',', '.')); break; } } } foreach (int toKick in toRemove) { this.removeUser(toKick, true, ""); } toRemove.Clear(); } catch (Exception e) { Out.WriteError(e.Message); } foreach (virtualBot roomBot in this._Bots.Values) { if (roomBot.goalX == -1) { continue; } stateMap = (squareState[,]) this.sqSTATE.Clone(); try { if (stateMap[roomBot.goalX, roomBot.goalY] == squareState.Seat) { stateMap[roomBot.goalX, roomBot.goalY] = squareState.Open; } if (this.sqUNIT[roomBot.goalX, roomBot.goalY]) { stateMap[roomBot.goalX, roomBot.goalY] = squareState.Blocked; } } catch { } nextCoords = new Pathfinder(stateMap, this.sqFLOORHEIGHT, this.sqUNIT).getNext(roomBot.X, roomBot.Y, roomBot.goalX, roomBot.goalY); roomBot.removeStatus("mv"); if (nextCoords == null) { if ((roomBot.X == roomBot.goalX) && (roomBot.Y == roomBot.goalY)) { roomBot.checkOrders(); } roomBot.goalX = -1; this._statusUpdates.Append(roomBot.statusString + Convert.ToChar(13)); } else { nextX = nextCoords[0]; nextY = nextCoords[1]; this.sqUNIT[roomBot.X, roomBot.Y] = false; this.sqUNIT[nextX, nextY] = true; roomBot.Z1 = Rotation.Calculate(roomBot.X, roomBot.Y, nextX, nextY); roomBot.Z2 = roomBot.Z1; roomBot.removeStatus("sit"); nextHeight = this.sqFLOORHEIGHT[nextX, nextY]; if (this.sqSTATE[nextX, nextY] == squareState.Rug) { nextHeight = this.sqITEMHEIGHT[nextX, nextY]; } else { nextHeight = this.sqFLOORHEIGHT[nextX, nextY]; } roomBot.addStatus("mv", string.Concat(new object[] { nextX, ",", nextY, ",", nextHeight.ToString().Replace(',', '.') })); this._statusUpdates.Append(roomBot.statusString + Convert.ToChar(13)); roomBot.X = nextX; roomBot.Y = nextY; roomBot.H = nextHeight; if (this.sqSTATE[nextX, nextY] == squareState.Seat) { roomBot.removeStatus("dance"); roomBot.Z1 = this.sqITEMROT[nextX, nextY]; roomBot.Z2 = roomBot.Z1; roomBot.addStatus("sit", this.sqITEMHEIGHT[nextX, nextY].ToString().Replace(',', '.')); } } } try { if (this._statusUpdates.Length > 0) { this.sendData("@b" + this._statusUpdates.ToString()); this._statusUpdates = new StringBuilder(); } } catch { } Thread.Sleep(410); } } ~virtualRoom() { Out.WriteLine(".", Out.logFlags.ImportantAction, ConsoleColor.Cyan, ConsoleColor.DarkCyan); } private int getFreeRoomIdentifier() { int i = 0; while (true) { if (!(this._Bots.ContainsKey(i) || this._Users.ContainsKey(i))) { return i; } i++; } } internal int[] getMapBorders() { return new int[] { this.sqUNIT.GetUpperBound(0), this.sqUNIT.GetUpperBound(1) }; } private int getRandomRoomIdentifier() { if (this._Users.Count <= 0) { return -1; } while (true) { int rndID = new Random(DateTime.Now.Millisecond).Next(0, this._Users.Count); if (this._Bots.ContainsKey(rndID) || this._Users.ContainsKey(rndID)) { return rndID; } } } internal virtualRoomUser getRoomUser(int roomUID) { return (virtualRoomUser) this._Users[roomUID]; } internal squareTrigger getTrigger(int X, int Y) { try { return this.sqTRIGGER[X, Y]; } catch { return null; } } internal virtualUser getUser(int roomUID) { return ((virtualRoomUser) this._Users[roomUID]).User; } private void handleSpecialCasts(object o) { try { DataRow dRow; string Cast; bool CS$4$0000; using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dRow = dbClient.getRow("SELECT specialcast_emitter,specialcast_interval,specialcast_rnd_min, specialcast_rnd_max FROM room_modeldata WHERE model = '" + ((string) o) + "'"); } this.emitter = Convert.ToString(dRow["specialcast_emitter"]); int Interval = Convert.ToInt32(dRow["specialcast_interval"]); int rndMin = Convert.ToInt32(dRow["specialcast_rnd_min"]); int rndMax = Convert.ToInt32(dRow["specialcast_rnd_max"]); dRow = null; string prevCast = ""; goto Label_01E4; Label_0098: Cast = ""; int RND = new Random().Next(rndMin, rndMax + 1); if (this.emitter == "cam1") { int roomUID; switch (RND) { case 1: roomUID = this.getRandomRoomIdentifier(); if (roomUID != -1) { Cast = "targetcamera " + roomUID; } goto Label_019E; case 2: Cast = "setcamera 1"; goto Label_019E; case 3: Cast = "setcamera 2"; goto Label_019E; } roomUID = this.getRandomRoomIdentifier(); if (roomUID != -1) { Cast = "targetcamera " + roomUID; } } else if (this.emitter == "sf") { Cast = RND.ToString(); } else if (this.emitter == "lamp") { Cast = "setlamp " + RND; } Label_019E: if (Cast == "") { return; } if (Cast != prevCast) { this.sendSpecialCast(this.emitter, Cast); prevCast = Cast; } Thread.Sleep(Interval); Label_01E4: CS$4$0000 = true; } catch { } goto Label_0098; } public bool hasSpecialCasts(string emiterValue) { return ((this.emitter != null) && (this.emitter == emiterValue)); } internal void kickUsers(byte casterRank, string Message) { List remove = new List(); lock (this._Users) { foreach (virtualRoomUser roomUser in this._Users.Values) { if (roomUser.User._Rank < casterRank) { remove.Add(roomUser); } } foreach (virtualRoomUser roomUser in remove) { this.removeUser(roomUser.roomUID, true, Message); } } } internal void loadBots() { DataColumn dCol; using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dCol = dbClient.getColumn("SELECT id FROM roombots WHERE roomid = '" + this.roomID + "'"); } int[] IDs = dataHandling.dColToArray(dCol, null); for (int i = 0; i < IDs.Length; i++) { virtualBot roomBot = new virtualBot(IDs[i], this.getFreeRoomIdentifier(), this); roomBot.H = this.sqFLOORHEIGHT[roomBot.X, roomBot.Y]; this.sqUNIT[roomBot.X, roomBot.Y] = true; this._Bots.Add(roomBot.roomUID, roomBot); this.sendData(@"@\" + roomBot.detailsString); this.sendData("@b" + roomBot.statusString); } } internal void moveUser(virtualRoomUser roomUser, int toX, int toY, bool secondRefresh) { new userMover(this.MOVEUSER).BeginInvoke(roomUser, toX, toY, secondRefresh, null, null); } private void MOVEUSER(virtualRoomUser roomUser, int toX, int toY, bool secondRefresh) { try { this.sqUNIT[roomUser.X, roomUser.Y] = false; this.sqUNIT[toX, toY] = true; roomUser.Z1 = Rotation.Calculate(roomUser.X, roomUser.Y, toX, toY); roomUser.Z2 = roomUser.Z1; roomUser.statusManager.removeStatus("sit"); double nextHeight = 0.0; if (this.sqSTATE[toX, toY] == squareState.Rug) { nextHeight = this.sqITEMHEIGHT[toX, toY]; } else { nextHeight = this.sqFLOORHEIGHT[toX, toY]; } roomUser.statusManager.addStatus("mv", string.Concat(new object[] { toX, ",", toY, ",", nextHeight.ToString().Replace(',', '.') })); this.sendData("@b" + roomUser.statusString); Thread.Sleep(310); roomUser.X = toX; roomUser.Y = toY; roomUser.H = nextHeight; roomUser.statusManager.removeStatus("mv"); if (secondRefresh) { if (this.sqSTATE[toX, toY] == squareState.Seat) { roomUser.statusManager.removeStatus("dance"); roomUser.Z1 = this.sqITEMROT[toX, toY]; roomUser.Z2 = roomUser.Z1; roomUser.statusManager.addStatus("sit", this.sqITEMHEIGHT[toX, toY].ToString().Replace(',', '.')); roomUser.statusManager.removeStatus("mv"); } this.sendData("@b" + roomUser.statusString); } } catch { } } internal void muteUsers(byte casterRank, string Message) { Message = "BK" + stringManager.getString("scommand_muted") + "\r" + Message; foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if (!(roomUser.User._isMuted || (roomUser.User._Rank >= casterRank))) { roomUser.User._isMuted = true; roomUser.User.sendData(Message); } } } internal void Refresh(virtualBot roomBot) { try { if (roomBot.goalX == -1) { this._statusUpdates.Append(roomBot.statusString + Convert.ToChar(13)); } } catch { } } internal void Refresh(virtualRoomUser roomUser) { if (roomUser.goalX == -1) { this._statusUpdates.Append(roomUser.statusString + Convert.ToChar(13)); } } internal void refreshCoord(int X, int Y) { foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if ((roomUser.X == X) && (roomUser.Y == Y)) { if (this.sqSTATE[X, Y] == squareState.Seat) { if (!roomUser.statusManager.containsStatus("sit")) { roomUser.Z1 = this.sqITEMROT[X, Y]; roomUser.Z2 = roomUser.Z1; roomUser.statusManager.addStatus("sit", this.sqITEMHEIGHT[X, Y].ToString().Replace(',', '.')); this.Refresh(roomUser); } } else if (this.sqSTATE[X, Y] == squareState.Bed) { if (!roomUser.statusManager.containsStatus("bed")) { roomUser.Z1 = this.sqITEMROT[X, Y]; roomUser.Z2 = roomUser.Z1; roomUser.statusManager.addStatus("lay", this.sqITEMHEIGHT[X, Y].ToString().Replace(',', '.')); this.Refresh(roomUser); } } else { roomUser.statusManager.removeStatus("sit"); roomUser.statusManager.removeStatus("lay"); roomUser.H = this.sqFLOORHEIGHT[X, Y]; this.Refresh(roomUser); } break; } } } internal void removeUser(int roomUID, bool sendKick, string moderatorMessage) { if (!this._Users.Contains(roomUID)) { return; } virtualRoomUser roomUser = (virtualRoomUser) this._Users[roomUID]; if (sendKick) { roomUser.User.sendData("@R"); if (moderatorMessage != "") { roomUser.User.sendData(string.Concat(new object[] { "@a", moderatorMessage, Convert.ToChar(2), "holo.cast.modkick" })); } } this.sqUNIT[roomUser.X, roomUser.Y] = false; roomUser.User.statusManager.Clear(); roomUser.User.statusManager = null; roomUser.User._roomID = 0; roomUser.User._inPublicroom = false; roomUser.User._ROOMACCESS_PRIMARY_OK = false; roomUser.User._ROOMACCESS_SECONDARY_OK = false; roomUser.User._isOwner = false; roomUser.User._hasRights = false; roomUser.User.Room = null; roomUser.User.roomUser = null; if (roomUser.User._tradePartnerRoomUID != -1) { roomUser.User.abortTrade(); } if (!((roomUser.User.gamePlayer == null) || roomUser.User.gamePlayer.enteringGame)) { roomUser.User.leaveGame(); } this._Users.Remove(roomUID); if (this._Users.Count <= 0) { this._Users.Clear(); this._Bots.Clear(); this._statusUpdates = null; if (!this.isPublicroom) { this.floorItemManager.Clear(); this.wallItemManager.Clear(); } else { try { this.specialCastHandler.Abort(); } catch { } if (this.Lobby != null) { this.Lobby.Clear(); } this.Lobby = null; } roomManager.removeRoom(this.roomID); this._statusHandler.Abort(); return; } if (roomUser.User._groupID <= 0) { goto Label_0275; } bool removeBadge = true; try { foreach (virtualRoomUser rUser in this._Users.Values) { if ((rUser.roomUID != roomUser.roomUID) && (rUser.User._groupID == roomUser.User._groupID)) { removeBadge = false; goto Label_0254; } } } catch { } Label_0254: if (removeBadge) { this._activeGroups.Remove(roomUser.User._groupID); } Label_0275: this.sendData("@]" + roomUID); roomManager.updateRoomVisitorCount(this.roomID, this._Users.Count); } internal void sendData(string Data) { try { foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { roomUser.User.sendData(Data); } } catch { } } internal void sendData(int userID, string Data) { foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if (roomUser.userID == userID) { roomUser.User.sendData(Data); break; } } } internal void sendData(string Data, int msSleep) { new sendDataSleep(this.SENDDATASLEEP).BeginInvoke(Data, msSleep, null, null); } internal void sendData(string Username, string Data) { foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if (roomUser.User._Username == Username) { roomUser.User.sendData(Data); break; } } } private void SENDDATASLEEP(string Data, int msSleep) { Thread.Sleep(msSleep); foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { roomUser.User.sendData(Data); } } internal void sendDataToRights(string Data) { try { foreach (virtualRoomUser roomUser in this._Users.Values) { if ((roomUser.User._hasRights || roomUser.User._isOwner) || rankManager.containsRight(roomUser.User._Rank, "fuse_pick_up_any_furni", roomUser.userID)) { roomUser.User.sendData(Data); } } } catch { } } internal void sendNewVoteAmount(int voteAmount) { string Data = "EY" + Encoding.encodeVL64(voteAmount); lock (this._Users) { foreach (virtualRoomUser roomUser in this._Users.Values) { if (roomUser.hasVoted) { roomUser.User.sendData(Data); } } } } internal void sendSaying(virtualBot sourceBot, string Message) { string Data = string.Concat(new object[] { "@X", Encoding.encodeVL64(sourceBot.roomUID), Message, Convert.ToChar(2) }); foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if ((Math.Abs((int) (roomUser.X - sourceBot.X)) < 6) && (Math.Abs((int) (roomUser.Y - sourceBot.Y)) < 6)) { roomUser.User.sendData(Data); } } } internal void sendSaying(virtualRoomUser sourceUser, string Message) { this.checkEmotion(sourceUser, Message); if (sourceUser.isTyping) { this.sendData("Ei" + Encoding.encodeVL64(sourceUser.roomUID) + "H"); sourceUser.isTyping = false; } string Data = string.Concat(new object[] { "@X", Encoding.encodeVL64(sourceUser.roomUID), Message, Convert.ToChar(2) }); foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { if ((Math.Abs((int) (roomUser.X - sourceUser.X)) < 6) && (Math.Abs((int) (roomUser.Y - sourceUser.Y)) < 6)) { roomUser.User.sendData(Data); } } foreach (virtualBot roomBot in this._Bots.Values) { if ((Math.Abs((int) (roomBot.X - sourceUser.X)) < 6) && (Math.Abs((int) (roomBot.Y - sourceUser.Y)) < 6)) { roomBot.Interact(sourceUser, Message); } } } internal void sendShout(virtualBot sourceBot, string Message) { string Data = string.Concat(new object[] { "@Z", Encoding.encodeVL64(sourceBot.roomUID), Message, Convert.ToChar(2) }); lock (this._Users) { foreach (virtualRoomUser roomUser in this._Users.Values) { roomUser.User.sendData(Data); } } } internal void sendShout(virtualRoomUser sourceUser, string Message) { this.checkEmotion(sourceUser, Message); if (sourceUser.isTyping) { this.sendData("Ei" + Encoding.encodeVL64(sourceUser.roomUID) + "H"); sourceUser.isTyping = false; } sourceUser.statusManager.handleStatus("talk", "", Message.Length * 190); string Data = string.Concat(new object[] { "@Z", Encoding.encodeVL64(sourceUser.roomUID), Message, Convert.ToChar(2) }); Hashtable users = new Hashtable(); users = (Hashtable) this._Users.Clone(); foreach (virtualRoomUser roomUser in users.Values) { this._statusUpdates.Append(roomUser.statusString + Convert.ToChar(13)); roomUser.User.sendData(Data); } lock (this._Bots) { foreach (virtualBot roomBot in this._Bots.Values) { if (((Math.Abs((int) (roomBot.X - sourceUser.X)) < 6) && (Math.Abs((int) (roomBot.Y - sourceUser.Y)) < 6)) && (new Random(DateTime.Now.Millisecond).Next(0, 11) == 0)) { this.sendSaying(roomBot, roomBot.noShoutingMessage); } } } } internal void sendSpecialCast(string Emitter, string Cast) { this.sendData("AG" + Emitter + " " + Cast); } internal void sendWhisper(virtualRoomUser sourceUser, string Receiver, string Message) { this.checkEmotion(sourceUser, Message); if (sourceUser.isTyping) { this.sendData("Ei" + Encoding.encodeVL64(sourceUser.roomUID) + "H"); sourceUser.isTyping = false; } string Data = string.Concat(new object[] { "@Y", Encoding.encodeVL64(sourceUser.roomUID), Message, Convert.ToChar(2) }); Hashtable users = new Hashtable(); users = (Hashtable) this._Users.Clone(); foreach (virtualRoomUser roomUser in this._Users.Values) { if (roomUser.User._Username == Receiver) { sourceUser.User.sendData(Data); roomUser.User.sendData(Data); break; } } } internal void setSquareState(int X, int Y, int Length, int Width, squareState State) { for (int jX = X; jX < (X + Width); jX++) { for (int jY = Y; jY < (Y + Length); jY++) { this.sqSTATE[jX, jY] = State; } } } internal bool squareBlocked(int X, int Y, int Length, int Width) { for (int jX = X; jX < (X + Width); jX++) { for (int jY = Y; jY < (X + Length); jY++) { if (this.sqUNIT[jX, jY]) { return true; } } } return false; } internal void unmuteUsers(byte casterRank) { string Message = "BK" + stringManager.getString("scommand_unmuted"); Hashtable users = new Hashtable(); users = (Hashtable) this._Users.Clone(); try { foreach (virtualRoomUser roomUser in users.Values) { if (roomUser.User._isMuted && (roomUser.User._Rank < casterRank)) { roomUser.User._isMuted = false; roomUser.User.sendData(Message); } } } catch { } } internal string dynamicStatuses { get { StringBuilder Statuses = new StringBuilder(); foreach (virtualBot roomBot in this._Bots.Values) { Statuses.Append(roomBot.statusString + Convert.ToChar(13)); } foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { Statuses.Append(roomUser.statusString + Convert.ToChar(13)); } return Statuses.ToString(); } } internal string dynamicUnits { get { StringBuilder userList = new StringBuilder(); foreach (virtualBot roomBot in this._Bots.Values) { userList.Append(roomBot.detailsString); } foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { userList.Append(roomUser.detailsString); } return userList.ToString(); } } internal string Flooritems { get { if (this.isPublicroom) { return "H"; } return this.floorItemManager.Items; } } internal string Groups { get { DataTable dTable; StringBuilder listBuilder = new StringBuilder(Encoding.encodeVL64(this._activeGroups.Count)); StringBuilder sb = new StringBuilder(); foreach (int groupID in this._activeGroups) { sb.Append(" OR id = '" + groupID + "'"); } sb.Append(" OR"); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dbClient.AddParamWithValue("tablename", sb.ToString().Substring(3)); dTable = dbClient.getTable("SELECT id,badge FROM groups_details WHERE @tablename 'a' = 'b'"); } foreach (DataRow dRow in dTable.Rows) { listBuilder.Append(Encoding.encodeVL64(Convert.ToInt32(dRow["id"])) + Convert.ToString(dRow["badge"]) + Convert.ToChar(2)); } return listBuilder.ToString(); } } internal string Heightmap { get { return this._Heightmap; } } internal string PublicroomItems { get { return this._publicroomItems; } } internal string Userlist { get { StringBuilder listBuilder = new StringBuilder(Encoding.encodeVL64(this.roomID) + Encoding.encodeVL64(this._Users.Count)); foreach (virtualRoomUser roomUser in ((Hashtable) this._Users.Clone()).Values) { listBuilder.Append(roomUser.User._Username + Convert.ToChar(2)); } return listBuilder.ToString(); } } internal ICollection Users { get { return this._Users.Values; } } internal string Wallitems { get { if (this.isPublicroom) { return ""; } return this.wallItemManager.Items; } } internal class FloorItemManager { private Hashtable _Items = new Hashtable(); private virtualRoom _Room; internal int soundMachineID; public FloorItemManager(virtualRoom Room) { this._Room = Room; } internal void addItem(int itemID, int templateID, int X, int Y, int Z, double H, string Var) { try { catalogueManager.itemTemplate Template = catalogueManager.getTemplate(templateID); if (stringManager.getStringPart(Template.Sprite, 0, 13) == "sound_machine") { this.soundMachineID = itemID; } int Length = 0; int Width = 0; if ((Z == 2) || (Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } for (int jX = X; jX < (X + Width); jX++) { for (int jY = Y; jY < (Y + Length); jY++) { virtualRoom.furnitureStack Stack = this._Room.sqSTACK[jX, jY]; if (Stack == null) { if ((Template.typeID != 2) && (Template.typeID != 3)) { Stack = new virtualRoom.furnitureStack(); Stack.Add(itemID); } } else { Stack.Add(itemID); } this._Room.sqSTATE[jX, jY] = (virtualRoom.squareState) Template.typeID; if ((Template.typeID == 2) || (Template.typeID == 3)) { this._Room.sqITEMHEIGHT[jX, jY] = H + Template.topH; this._Room.sqITEMROT[jX, jY] = Convert.ToByte(Z); } else if (Template.typeID == 4) { this._Room.sqITEMHEIGHT[jX, jY] = H; } this._Room.sqSTACK[jX, jY] = Stack; } } if (Template.isDoor) { if (this._Room.squareBlocked(X, Y, Length, Width)) { return; } if (Var.ToLower() == "c") { this._Room.setSquareState(X, Y, Length, Width, virtualRoom.squareState.Blocked); } else if (Var.ToLower() == "o") { this._Room.setSquareState(X, Y, Length, Width, virtualRoom.squareState.Open); } else { this._Room.setSquareState(X, Y, Length, Width, virtualRoom.squareState.Blocked); } } floorItem Item = new floorItem(itemID, templateID, X, Y, Z, H, Var); this._Items.Add(itemID, Item); } catch (Exception ex) { Out.WriteError("[" + ex.Source + "] Exception Error - " + ex.Message); } } internal void Clear() { try { this._Items.Clear(); } catch { } this._Room = null; this._Items = null; } internal bool containsItem(int itemID) { return this._Items.ContainsKey(itemID); } internal floorItem getItem(int itemID) { return (floorItem) this._Items[itemID]; } internal void placeItem(int itemID, int templateID, int X, int Y, byte typeID, byte Z) { if (!this._Items.ContainsKey(itemID)) { try { catalogueManager.itemTemplate Template = catalogueManager.getTemplate(templateID); bool isSoundMachine = stringManager.getStringPart(Template.Sprite, 0, 13) == "sound_machine"; if (!isSoundMachine || (this.soundMachineID <= 0)) { floorItem topItem; int jX; int jY; string Var; int Length = 0; int Width = 0; if ((Z == 2) || (Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } double testH = this._Room.sqFLOORHEIGHT[X, Y]; double H = testH; if (this._Room.sqSTACK[X, Y] != null) { topItem = (floorItem) this._Items[this._Room.sqSTACK[X, Y].topItemID()]; H = topItem.H + catalogueManager.getTemplate(topItem.templateID).topH; } for (jX = X; jX < (X + Width); jX++) { jY = Y; while (jY < (Y + Length)) { if (this._Room.sqUNIT[jX, jY]) { return; } virtualRoom.squareState jState = this._Room.sqSTATE[jX, jY]; switch (jState) { case virtualRoom.squareState.Open: break; case virtualRoom.squareState.Blocked: { if (this._Room.sqSTACK[jX, jY] == null) { return; } topItem = (floorItem) this._Items[this._Room.sqSTACK[jX, jY].topItemID()]; catalogueManager.itemTemplate topItemTemplate = catalogueManager.getTemplate(topItem.templateID); if (((topItemTemplate.topH == 0.0) || (topItemTemplate.typeID == 2)) || (topItemTemplate.typeID == 3)) { return; } if ((topItem.H + topItemTemplate.topH) > H) { H = topItem.H + topItemTemplate.topH; } break; } default: { if ((jState != virtualRoom.squareState.Rug) || (this._Room.sqSTACK[jX, jY] == null)) { return; } double jH = ((floorItem) this._Items[this._Room.sqSTACK[jX, jY].topItemID()]).H + 0.1; if (jH > H) { H = jH; } break; } } jY++; } } if (H > Config.Items_Stacking_maxHeight) { H = Config.Items_Stacking_maxHeight; } for (jX = X; jX < (X + Width); jX++) { for (jY = Y; jY < (Y + Length); jY++) { virtualRoom.furnitureStack Stack = null; if (this._Room.sqSTACK[jX, jY] == null) { if (((Template.typeID == 1) && (Template.topH > 0.0)) || (Template.typeID == 4)) { Stack = new virtualRoom.furnitureStack(); Stack.Add(itemID); } } else { Stack = this._Room.sqSTACK[jX, jY]; Stack.Add(itemID); } this._Room.sqSTATE[jX, jY] = (virtualRoom.squareState) Template.typeID; this._Room.sqSTACK[jX, jY] = Stack; if ((Template.typeID == 2) || (Template.typeID == 3)) { this._Room.sqITEMHEIGHT[jX, jY] = H + Template.topH; this._Room.sqITEMROT[jX, jY] = Z; this._Room.sqITEMROT[jX, jY] = Z; if ((Template.typeID == 3) && ((jX != X) || (jY != Y))) { if (Width == 1) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Blocked; } else if (((Z == 2) && (jX != X)) || ((Z == 0) && (jY != Y))) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Blocked; } } } else if (Template.typeID == 4) { this._Room.sqITEMHEIGHT[jX, jY] = H; } } } using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { Var = dbClient.getString("SELECT var FROM furniture WHERE id = '" + itemID + "'"); dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET roomid = '", this._Room.roomID, "',x = '", X, "',y = '", Y, "',z = '", Z, "',h = '", H.ToString().Replace(',', '.'), "' WHERE id = '", itemID, "' LIMIT 1" })); } floorItem Item = new floorItem(itemID, templateID, X, Y, Z, H, Var); this._Items.Add(itemID, Item); this._Room.sendData("A]" + Item.ToString()); if (isSoundMachine) { this.soundMachineID = itemID; } } } catch { } } } internal void relocateItem(int itemID, int X, int Y, byte Z) { try { floorItem topItem; int jY; virtualRoom.furnitureStack Stack; floorItem Item = (floorItem) this._Items[itemID]; catalogueManager.itemTemplate Template = catalogueManager.getTemplate(Item.templateID); int Length = 0; int Width = 0; if ((Z == 2) || (Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } double baseFloorH = this._Room.sqFLOORHEIGHT[X, Y]; double H = baseFloorH; if (this._Room.sqSTACK[X, Y] != null) { topItem = (floorItem) this._Items[this._Room.sqSTACK[X, Y].topItemID()]; if (topItem != Item) { catalogueManager.itemTemplate topTemplate = catalogueManager.getTemplate(topItem.templateID); if (topTemplate.typeID == 1) { H = topItem.H + topTemplate.topH; } } else if (this._Room.sqSTACK[X, Y].Count > 1) { H = topItem.H; } } int jX = X; while (jX < (X + Width)) { jY = Y; while (jY < (Y + Length)) { if ((Template.typeID != 2) && this._Room.sqUNIT[jX, jY]) { return; } virtualRoom.squareState jState = this._Room.sqSTATE[jX, jY]; Stack = this._Room.sqSTACK[jX, jY]; if (jState != virtualRoom.squareState.Open) { if (Stack == null) { if ((jX != Item.X) || (jY != Item.Y)) { return; } } else { topItem = (floorItem) this._Items[Stack.topItemID()]; if (topItem != Item) { catalogueManager.itemTemplate topItemTemplate = catalogueManager.getTemplate(topItem.templateID); if ((topItemTemplate.typeID == 1) && (topItemTemplate.topH > 0.0)) { if ((topItem.H + topItemTemplate.topH) > H) { H = topItem.H + topItemTemplate.topH; } } else if (topItemTemplate.typeID == 2) { return; } } } } jY++; } jX++; } int oldLength = 1; int oldWidth = 1; if ((Template.Length > 1) || (Template.Width > 1)) { if ((Item.Z == 2) || (Item.Z == 6)) { oldLength = Template.Length; oldWidth = Template.Width; } else { oldLength = Template.Width; oldWidth = Template.Length; } } if (H > Config.Items_Stacking_maxHeight) { H = Config.Items_Stacking_maxHeight; } for (jX = Item.X; jX < (Item.X + oldWidth); jX++) { jY = Item.Y; while (jY < (Item.Y + oldLength)) { Stack = this._Room.sqSTACK[jX, jY]; if ((Stack == null) || (Stack.Count <= 1)) { goto Label_05AC; } if (itemID == Stack.bottomItemID()) { if (catalogueManager.getTemplate(((floorItem) this._Items[Stack.topItemID()]).templateID).typeID == 2) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Seat; } else { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Open; } } else if (itemID == Stack.topItemID()) { floorItem belowItem = (floorItem) this._Items[Stack.getBelowItemID(itemID)]; byte typeID = catalogueManager.getTemplate(belowItem.templateID).typeID; this._Room.sqSTATE[jX, jY] = (virtualRoom.squareState) typeID; switch (typeID) { case 2: case 3: this._Room.sqITEMROT[jX, jY] = belowItem.Z; this._Room.sqITEMHEIGHT[jX, jY] = belowItem.H + catalogueManager.getTemplate(belowItem.templateID).topH; if ((Template.typeID == 3) && ((jX != X) || (jY != Y))) { if (Width == 1) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Blocked; } else if (((Z == 2) && (jX != X)) || ((Z == 0) && (jY != Y))) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Blocked; } } goto Label_058A; } if (typeID == 4) { this._Room.sqITEMHEIGHT[jX, jY] = belowItem.H; } } Label_058A: Stack.Remove(itemID); this._Room.sqSTACK[jX, jY] = Stack; goto Label_060A; Label_05AC: this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Open; this._Room.sqITEMHEIGHT[jX, jY] = 0.0; this._Room.sqITEMROT[jX, jY] = 0; this._Room.sqSTACK[jX, jY] = null; Label_060A: if ((Template.typeID == 2) || (Template.typeID == 3)) { this._Room.refreshCoord(jX, jY); } jY++; } } Item.X = X; Item.Y = Y; Item.Z = Z; Item.H = H; this._Room.sendData("A_" + Item.ToString()); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET x = '", X, "',y = '", Y, "',z = '", Z, "',h = '", H.ToString().Replace(',', '.'), "' WHERE id = '", itemID, "' LIMIT 1" })); } for (jX = X; jX < (X + Width); jX++) { for (jY = Y; jY < (Y + Length); jY++) { Stack = null; if (this._Room.sqSTACK[jX, jY] == null) { if ((((Template.topH > 0.0) && (Template.typeID != 2)) && (Template.typeID != 3)) && (Template.typeID != 4)) { Stack = new virtualRoom.furnitureStack(); Stack.Add(itemID); } } else { Stack = this._Room.sqSTACK[jX, jY]; Stack.Add(itemID); } this._Room.sqSTATE[jX, jY] = (virtualRoom.squareState) Template.typeID; this._Room.sqSTACK[jX, jY] = Stack; if ((Template.typeID == 2) || (Template.typeID == 3)) { this._Room.sqITEMHEIGHT[jX, jY] = H + Template.topH; this._Room.sqITEMROT[jX, jY] = Z; this._Room.refreshCoord(jX, jY); } else if (Template.typeID == 4) { this._Room.sqITEMHEIGHT[jX, jY] = H; } } } } catch { } } internal void removeItem(int itemID, int ownerID) { if (this._Items.ContainsKey(itemID)) { floorItem Item = (floorItem) this._Items[itemID]; catalogueManager.itemTemplate Template = catalogueManager.getTemplate(Item.templateID); int Length = 0; int Width = 0; if ((Item.Z == 2) || (Item.Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } for (int jX = Item.X; jX < (Item.X + Width); jX++) { for (int jY = Item.Y; jY < (Item.Y + Length); jY++) { virtualRoom.furnitureStack Stack = this._Room.sqSTACK[jX, jY]; if ((Stack != null) && (Stack.Count > 1)) { if (itemID == Stack.bottomItemID()) { int topID = Stack.topItemID(); floorItem topItem = (floorItem) this._Items[topID]; if (catalogueManager.getTemplate(topItem.templateID).typeID == 2) { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Seat; } else { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Open; } } else if (itemID == Stack.topItemID()) { int belowID = Stack.getBelowItemID(itemID); floorItem belowItem = (floorItem) this._Items[belowID]; byte typeID = catalogueManager.getTemplate(belowItem.templateID).typeID; this._Room.sqSTATE[jX, jY] = (virtualRoom.squareState) typeID; switch (typeID) { case 2: case 3: this._Room.sqITEMROT[jX, jY] = belowItem.Z; this._Room.sqITEMHEIGHT[jX, jY] = belowItem.H + catalogueManager.getTemplate(belowItem.templateID).topH; break; case 4: this._Room.sqITEMHEIGHT[jX, jY] = belowItem.H; break; } } Stack.Remove(itemID); this._Room.sqSTACK[jX, jY] = Stack; } else { this._Room.sqSTATE[jX, jY] = virtualRoom.squareState.Open; this._Room.sqITEMHEIGHT[jX, jY] = 0.0; this._Room.sqITEMROT[jX, jY] = 0; this._Room.sqSTACK[jX, jY] = null; } if ((Template.typeID == 2) || (Template.typeID == 3)) { this._Room.refreshCoord(jX, jY); } } } if ((this.soundMachineID == 0) && (stringManager.getStringPart(Template.Sprite, 0, 13) == "sound_machine")) { this.soundMachineID = 0; } this._Room.sendData("A^" + itemID); this._Items.Remove(itemID); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { if (ownerID > 0) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET x = '0',y = '0',z = '0', h = '0', ownerid = '", ownerID, "',roomid = '0' WHERE id = '", itemID, "' LIMIT 1" })); } else { dbClient.runQuery("DELETE FROM furniture WHERE id = '" + itemID + "' LIMIT 1"); } } } } internal void rotateItem(int itemID, byte Z) { floorItem Item = (floorItem) this._Items[itemID]; catalogueManager.itemTemplate Template = catalogueManager.getTemplate(Item.templateID); int Length = 1; int Width = 1; if ((Template.Length > 1) && (Template.Width > 1)) { if ((Z == 2) || (Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } } for (int jX = Item.X; jX < (Item.X + Width); jX++) { for (int jY = Item.Y; jY < (Item.Y + Length); jY++) { virtualRoom.furnitureStack Stack = this._Room.sqSTACK[jX, jY]; if ((Stack != null) && (Stack.topItemID() != itemID)) { } } } } internal void toggleItemStatus(int itemID, string toStatus, bool hasRights) { if (this._Items.ContainsKey(itemID)) { floorItem Item = (floorItem) this._Items[itemID]; string itemSprite = Item.Sprite; if ((((itemSprite != "edice") && (itemSprite != "edicehc")) && (stringManager.getStringPart(itemSprite, 0, 11) != "prizetrophy")) && !(stringManager.getStringPart(itemSprite, 0, 7) == "present")) { using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dbClient.AddParamWithValue("var", toStatus); if ((toStatus.ToLower() == "c") || (toStatus.ToLower() == "o")) { if (hasRights) { catalogueManager.itemTemplate Template = catalogueManager.getTemplate(Item.templateID); if (Template.isDoor) { int Length = 1; int Width = 1; if ((Template.Length > 1) || (Template.Width > 1)) { if ((Item.Z == 2) || (Item.Z == 6)) { Length = Template.Length; Width = Template.Width; } else { Length = Template.Width; Width = Template.Length; } } if (toStatus.ToLower() == "c") { if (this._Room.squareBlocked(Item.X, Item.Y, Length, Width)) { return; } this._Room.setSquareState(Item.X, Item.Y, Length, Width, virtualRoom.squareState.Blocked); } else { this._Room.setSquareState(Item.X, Item.Y, Length, Width, virtualRoom.squareState.Open); } Item.Var = toStatus; this._Room.sendData(string.Concat(new object[] { "AX", itemID, Convert.ToChar(2), toStatus, Convert.ToChar(2) })); dbClient.runQuery("UPDATE furniture SET var = @var WHERE id = " + itemID + " LIMIT 1"); } } } else if (toStatus.Replace(Convert.ToChar(2), Convert.ToChar(0x20)) == toStatus) { Item.Var = toStatus; this._Room.sendData(string.Concat(new object[] { "AX", itemID, Convert.ToChar(2), toStatus, Convert.ToChar(2) })); dbClient.runQuery("UPDATE furniture SET var = @var WHERE id = " + itemID + " LIMIT 1"); } } } } } internal string Items { get { StringBuilder itemList = new StringBuilder(Encoding.encodeVL64(this._Items.Count)); foreach (floorItem Item in this._Items.Values) { itemList.Append(Item.ToString()); } return itemList.ToString(); } } } private class furnitureStack { private int[] _itemIDs = new int[20]; internal furnitureStack() { } internal void Add(int itemID) { for (int i = 0; i < 20; i++) { if (this._itemIDs[i] == 0) { this._itemIDs[i] = itemID; break; } } } internal int bottomItemID() { return this._itemIDs[0]; } internal bool Contains(int itemID) { foreach (int i in this._itemIDs) { if (i == itemID) { return true; } } return false; } internal int getAboveItemID(int aboveID) { for (int i = 0; i < 20; i++) { if (this._itemIDs[i] == aboveID) { return this._itemIDs[i + 1]; } } return 0; } internal int getBelowItemID(int belowID) { for (int i = 0; i < 20; i++) { if (this._itemIDs[i] == belowID) { return this._itemIDs[i - 1]; } } return 0; } internal void Remove(int itemID) { int i; for (i = 0; i < 20; i++) { if (this._itemIDs[i] == itemID) { this._itemIDs[i] = 0; break; } } int g = 0; int[] j = new int[20]; for (i = 0; i < 20; i++) { if (this._itemIDs[i] > 0) { j[g] = this._itemIDs[i]; g++; } } this._itemIDs = j; } internal int topItemID() { for (int i = 0; i < 20; i++) { if (this._itemIDs[i] == 0) { return this._itemIDs[i - 1]; } } return 0; } internal int Count { get { int j = 0; for (int i = 0; i < 20; i++) { if (this._itemIDs[i] > 0) { j++; } else { return j; } } return j; } } } private delegate void sendDataSleep(string Data, int msSleep); public enum squareState { Open, Blocked, Seat, Bed, Rug } internal class squareTrigger { internal readonly int goalX; internal readonly int goalY; internal readonly string Object; internal readonly int roomID; internal bool State; internal readonly int stepX; internal readonly int stepY; internal squareTrigger(string Object, int goalX, int goalY, int stepX, int stepY, bool State, int roomID) { this.Object = Object; this.goalX = goalX; this.goalY = goalY; this.stepX = stepX; this.stepY = stepY; this.roomID = roomID; this.State = State; } } private delegate void userMover(virtualRoomUser roomUser, int toX, int toY, bool secondRefresh); internal class WallItemManager { private Hashtable _Items = new Hashtable(); private virtualRoom _Room; public WallItemManager(virtualRoom Room) { this._Room = Room; } internal void addItem(int itemID, int templateID, string wallPosition, string Var, bool Place) { if (!this._Items.Contains(itemID)) { wallItem Item = new wallItem(itemID, templateID, wallPosition, Var); this._Items.Add(itemID, Item); if (Place) { this._Room.sendData("AS" + Item.ToString()); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET roomid = '", this._Room.roomID, "',wallpos = '", wallPosition, "' WHERE id = '", itemID, "' LIMIT 1" })); if (templateID == 0x3ea) { if (!dbClient.findsResult("SELECT roomid FROM furniture_moodlight WHERE id='" + itemID + "'")) { dbClient.runQuery(string.Concat(new object[] { "INSERT INTO furniture_moodlight VALUES ('", itemID, "','", this._Room.roomID, "','1','1,#000000,225','1,#000000,200','1,#000000,175')" })); } else { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture_moodlight SET roomid = '", this._Room.roomID, "' WHERE id= '", itemID, "'" })); } } } } } } internal void Clear() { try { this._Items.Clear(); } catch { } this._Room = null; this._Items = null; } internal bool containsItem(int itemID) { return this._Items.ContainsKey(itemID); } internal wallItem getItem(int itemID) { return (wallItem) this._Items[itemID]; } internal string moodLight_GetSettings(int roomID) { try { string[] itemSettings; using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { itemSettings = (string[]) dbClient.getRow("SELECT preset_cur,preset_1,preset_2,preset_3 FROM furniture_moodlight WHERE roomid ='" + roomID + "'").ItemArray; } string settingPack = Encoding.encodeVL64(3) + Encoding.encodeVL64(Convert.ToInt32(itemSettings[0])); for (int i = 1; i <= 3; i++) { string[] curPresetData = itemSettings[i].Split(new char[] { ',' }); settingPack = string.Concat(new object[] { settingPack, Encoding.encodeVL64(i), Encoding.encodeVL64(Convert.ToInt32(curPresetData[0])), curPresetData[1], Convert.ToChar(2), Encoding.encodeVL64(Convert.ToInt32(curPresetData[2])) }); } return settingPack; } catch { return ""; } } internal void moodLight_SetSettings(bool isEnabled, int presetID, int bgState, string presetColour, int alphaDarkF, int roomID) { int itemID; DatabaseClient dbClient; string newPresetValue; DataRow dRow; using (dbClient = Eucalypt.dbManager.GetClient()) { itemID = dbClient.getInt("SELECT id FROM furniture_moodlight WHERE roomid ='" + roomID + "'"); } if (!isEnabled) { string curPresetValue; using (dbClient = Eucalypt.dbManager.GetClient()) { curPresetValue = dbClient.getString("SELECT var FROM furniture WHERE id ='" + itemID + "'"); } if (curPresetValue.Substring(0, 1) == "2") { newPresetValue = "1" + curPresetValue.Substring(1); } else { newPresetValue = "2" + curPresetValue.Substring(1); } using (dbClient = Eucalypt.dbManager.GetClient()) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET var = '", newPresetValue, "' WHERE id ='", itemID, "' LIMIT 1" })); } } else { newPresetValue = string.Concat(new object[] { "2,", presetID, ",", bgState, ",", presetColour, ",", alphaDarkF }); using (dbClient = Eucalypt.dbManager.GetClient()) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET var ='", newPresetValue, "' WHERE id ='", itemID, "' LIMIT 1" })); dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture_moodlight SET preset_cur ='", presetID, "',preset_", presetID, " ='", bgState, ",", presetColour, ",", alphaDarkF, "' WHERE id = '", itemID, "' LIMIT 1" })); } } using (dbClient = Eucalypt.dbManager.GetClient()) { dRow = dbClient.getRow("SELECT wallpos,var FROM furniture WHERE id = '" + itemID + "'"); } string wallPosition = Convert.ToString(dRow["wallpos"]); this.refreshWallitem(itemID, "roomdimmer", wallPosition, Convert.ToString(dRow["var"])); } internal void refreshWallitem(int itemID, string cctName, string wallPosition, string itemVariable) { this._Room.sendData(string.Concat(new object[] { "AU", itemID, Convert.ToChar(9), cctName, Convert.ToChar(9), " ", wallPosition, Convert.ToChar(9), itemVariable })); } internal void removeItem(int itemID, int ownerID) { if (this._Items.ContainsKey(itemID)) { this._Room.sendData("AT" + itemID); this._Items.Remove(itemID); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { if (ownerID > 0) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET ownerid = '", ownerID, "',roomid = '0' WHERE id = '", itemID, "' LIMIT 1" })); } else { dbClient.runQuery("DELETE FROM furniture WHERE id = '" + itemID + "' LIMIT 1"); } } } } internal void toggleItemStatus(int itemID, int toStatus) { if (this._Items.ContainsKey(itemID)) { wallItem Item = (wallItem) this._Items[itemID]; string itemSprite = Item.Sprite; if (((((itemSprite != "roomdimmer") && (itemSprite != "post.it")) && ((itemSprite != "post.it.vd") && (itemSprite != "poster"))) && (itemSprite != "habbowheel")) && !(itemSprite == "ads_lin_wh_c")) { Item.Var = toStatus.ToString(); this._Room.sendData(string.Concat(new object[] { "AU", itemID, Convert.ToChar(9), itemSprite, Convert.ToChar(9), " ", Item.wallPosition, Convert.ToChar(9), Item.Var })); using (DatabaseClient dbClient = Eucalypt.dbManager.GetClient()) { dbClient.runQuery(string.Concat(new object[] { "UPDATE furniture SET var = '", toStatus, "' WHERE id = '", itemID, "' LIMIT 1" })); } } } } internal string Items { get { StringBuilder itemList = new StringBuilder(); try { foreach (wallItem Item in this._Items.Values) { itemList.Append(Item.ToString() + Convert.ToChar(13)); } } catch { } return itemList.ToString(); } } } } }