From eb8b8a37ccd46e89cd3c9263c35363d4778ce38d Mon Sep 17 00:00:00 2001 From: UnknownShadow200 Date: Sat, 16 Jan 2016 18:45:57 +1100 Subject: [PATCH] Allow using .zips for texture packs, also allow changing cloud height for clients that support EnvMapAppearance v2. --- Commands/Information/CmdMapInfo.cs | 8 +- Commands/World/CmdEnvironment.cs | 113 +++++++++++++++-------------- Commands/World/CmdTexture.cs | 97 +++++++++++++++++++++++++ Commands/other/CmdTexture.cs | 77 -------------------- Levels/IO/LvlProperties.cs | 9 ++- Levels/Level.cs | 5 +- MCGalaxy_.csproj | 2 +- Network/Player.Networking.cs | 20 ++++- Player/Player.CPE.cs | 44 ++++++----- Player/Player.cs | 2 +- Server/Properties.cs | 55 +++++++------- Server/Server.cs | 2 +- 12 files changed, 241 insertions(+), 193 deletions(-) create mode 100644 Commands/World/CmdTexture.cs delete mode 100644 Commands/other/CmdTexture.cs diff --git a/Commands/Information/CmdMapInfo.cs b/Commands/Information/CmdMapInfo.cs index fb324eb05..fe175e544 100644 --- a/Commands/Information/CmdMapInfo.cs +++ b/Commands/Information/CmdMapInfo.cs @@ -54,10 +54,10 @@ namespace MCGalaxy.Commands { Player.SendMessage(p, "No backups for this map exist yet."); } - if (lvl.textureUrl != "") { - Player.SendMessage(p, "TexturePack: %b" + lvl.textureUrl); - } else if (lvl == Server.mainLevel && Server.defaultTextureUrl != "") { - Player.SendMessage(p, "TexturePack: " + Server.defaultTextureUrl); + if (lvl.terrainUrl != "") { + Player.SendMessage(p, "TexturePack: %b" + lvl.terrainUrl); + } else if (lvl == Server.mainLevel && Server.defaultTerrainUrl != "") { + Player.SendMessage(p, "TexturePack: " + Server.defaultTerrainUrl); } else { Player.SendMessage(p, "No textures for this map exist yet."); } diff --git a/Commands/World/CmdEnvironment.cs b/Commands/World/CmdEnvironment.cs index 944f537e2..59bc08f49 100644 --- a/Commands/World/CmdEnvironment.cs +++ b/Commands/World/CmdEnvironment.cs @@ -29,11 +29,11 @@ namespace MCGalaxy.Commands { public CmdEnvironment() { } public override void Use(Player p, string message) { - message = message.ToLower(); - if (message == "l preset" || message == "level preset") { - SendPresetsMessage(p); - return; - } + message = message.ToLower(); + if (message == "l preset" || message == "level preset") { + SendPresetsMessage(p); + return; + } string[] args = null; if (message == "" || (args = message.Split(' ')).Length < 3) { Help(p); return; @@ -55,61 +55,57 @@ namespace MCGalaxy.Commands { void Handle(Player p, string group, string variable, string value) { bool level = group == "l"; + Level lvl = p.level; + switch (variable) { case "fog": - SetEnvColour(p, value, 2, "fog", ref p.level.FogColor, level); - break; + SetEnvColour(p, value, 2, "fog", ref lvl.FogColor, level); break; case "cloud": case "clouds": - SetEnvColour(p, value, 1, "cloud", ref p.level.CloudColor, level); - break; + SetEnvColour(p, value, 1, "cloud", ref lvl.CloudColor, level); break; case "sky": - SetEnvColour(p, value, 0, "sky", ref p.level.SkyColor, level); - break; + SetEnvColour(p, value, 0, "sky", ref lvl.SkyColor, level); break; case "dark": case "shadow": - SetEnvColour(p, value, 3, "shadow", ref p.level.ShadowColor, level); - break; + SetEnvColour(p, value, 3, "shadow", ref lvl.ShadowColor, level); break; case "sun": case "light": case "sunlight": - SetEnvColour(p, value, 4, "sunlight", ref p.level.LightColor, level); - break; + SetEnvColour(p, value, 4, "sunlight", ref lvl.LightColor, level); break; case "weather": - SetEnvWeather(p, value, ref p.level.weather, level); - break; - + SetEnvWeather(p, value, ref lvl.weather, level); break; + case "cloudsheight": + case "cloudheight": + if (!level) { + p.SendMessage("This feature is not available for 'player' target"); return; + } + SetEnvMapAppearanceS(p, value, "clouds height", (short)(lvl.height + 2), ref lvl.CloudsHeight); break; + case "waterlevel": + case "edgelevel": case "level": if (!level) { - p.SendMessage("This feature is not available for 'player' target"); - return; + p.SendMessage("This feature is not available for 'player' target"); return; } - byte ignored = 0; - SetEnvMapAppearance(p, value, "water level", false, 0, ref ignored ); - break; + SetEnvMapAppearanceS(p, value, "water level", (short)(lvl.height / 2), ref lvl.EdgeLevel); break; case "horizon": case "edge": case "water": if (!level) { p.SendMessage("This feature is not available for 'player' target"); return; } - SetEnvMapAppearance(p, value, "edge block", true, Block.waterstill, ref p.level.HorizonBlock); - break; + SetEnvMapAppearance(p, value, "edge block", Block.waterstill, ref lvl.HorizonBlock); break; case "side": case "border": case "bedrock": if (!level) { p.SendMessage("This feature is not available for 'player' target"); return; } - SetEnvMapAppearance(p, value, "sides block", true, Block.blackrock, ref p.level.EdgeBlock); - break; + SetEnvMapAppearance(p, value, "sides block", Block.blackrock, ref lvl.EdgeBlock); break; case "preset": - if (!SetPreset(p, value, level)) - return; + if (!SetPreset(p, value, level)) return; break; default: - Help(p); - return; + Help(p); return; } if (level) @@ -178,12 +174,11 @@ namespace MCGalaxy.Commands { } if (weather > 2) { - p.SendMessage("Please use a valid integer (0,1,2) or string (sun,rain,snow)"); - return; + p.SendMessage("Please use a valid integer (0,1,2) or string (sun,rain,snow)"); return; } } - if( level ) + if (level) p.level.weather = weather; string weatherType = weather == 0 ? "&sSun" : (weather == 1 ? "&1Rain" : "&fSnow"); p.SendMessage(string.Format("&aSet weather for {0}&a to {1} ({2}&a)", target, weather, weatherType)); @@ -191,33 +186,39 @@ namespace MCGalaxy.Commands { // Send the changed colour to all players affected by the command. if (level) { foreach (Player pl in Player.players) { - if (pl.level == p.level && pl.HasCpeExt(CpeExt.EnvWeatherType)) { + if (pl.level == p.level && pl.HasCpeExt(CpeExt.EnvWeatherType)) pl.SendSetMapWeather(weather); - } } } else if (p.HasCpeExt(CpeExt.EnvWeatherType)) { p.SendSetMapWeather(weather); } } - void SetEnvMapAppearance(Player p, string value, string variable, - bool block, byte defValue, ref byte modifyBlock) { + void SetEnvMapAppearance(Player p, string value, string variable, byte defValue, ref byte target) { if (IsResetString(value)) { p.SendMessage(string.Format("Reset {0} for {0}&S to normal", variable, p.level.name)); - if( block ) - modifyBlock = defValue; - else - p.level.EdgeLevel = (short)(p.level.Height / 2); + target = defValue; } else { - if (block && !CheckBlock(p, value, variable, ref modifyBlock)) - return; - if( !block && !CheckShort(p, value, variable, ref p.level.EdgeLevel)) - return; + if (!CheckBlock(p, value, variable, ref target)) return; } - + SendCurrentMapAppearance(p.level); + } + + void SetEnvMapAppearanceS(Player p, string value, string variable, short defValue, ref short target) { + if (IsResetString(value)) { + p.SendMessage(string.Format("Reset {0} for {0}&S to normal", variable, p.level.name)); + target = defValue; + } else { + if (!CheckShort(p, value, variable, ref target)) return; + } + SendCurrentMapAppearance(p.level); + } + + void SendCurrentMapAppearance(Level lvl) { foreach (Player pl in Player.players) { - if (pl.HasCpeExt(CpeExt.EnvMapAppearance) && pl.level == p.level) - pl.SendCurrentMapAppearance(); + bool hasExt = pl.HasCpeExt(CpeExt.EnvMapAppearance) || pl.HasCpeExt(CpeExt.EnvMapAppearance, 2); + if (hasExt && pl.level == lvl) + pl.SendCurrentMapAppearance(); } } @@ -292,7 +293,7 @@ namespace MCGalaxy.Commands { } return true; } else { - SendPresetsMessage(p); + SendPresetsMessage(p); return false; } } @@ -328,16 +329,16 @@ namespace MCGalaxy.Commands { } static void SendPresetsMessage(Player p) { - p.SendMessage("/env l preset [type] -- Uses an env preset on your map"); + p.SendMessage("/env l preset [type] -- Uses an env preset on your map"); p.SendMessage("Valid types: Cartoon/Midnight/Midnight2/Noir/Normal/Trippy/Watery/Sunset/Gloomy/Cloudy"); } public override void Help(Player p) { - p.SendMessage("%T/env [target] [variable] [value]"); - p.SendMessage("%H Valid targets: player or p, level or l"); - p.SendMessage("%H Valid variables: fog, cloud, sky, sun, shadow, weather"); - p.SendMessage("%H level only variables: level, horizon, border, preset"); - p.SendMessage("%HUsing 'normal' as a value will reset the variable"); + Player.SendMessage(p, "%T/env [target] [variable] [value]"); + Player.SendMessage(p, "%H Valid targets: player or p, level or l"); + Player.SendMessage(p, "%H Valid variables: fog, cloud, sky, sun, shadow, weather"); + Player.SendMessage(p, "%H level only: level, cloudsheight, horizon, border, preset"); + Player.SendMessage(p, "%HUsing 'normal' as a value will reset the variable"); } } } diff --git a/Commands/World/CmdTexture.cs b/Commands/World/CmdTexture.cs new file mode 100644 index 000000000..9f8c8f417 --- /dev/null +++ b/Commands/World/CmdTexture.cs @@ -0,0 +1,97 @@ +/* + Copyright 2011 MCGalaxy + + Dual-licensed under the Educational Community License, Version 2.0 and + the GNU General Public License, Version 3 (the "Licenses"); you may + not use this file except in compliance with the Licenses. You may + obtain a copy of the Licenses at + + http://www.opensource.org/licenses/ecl2.php + http://www.gnu.org/licenses/gpl-3.0.html + + Unless required by applicable law or agreed to in writing, + software distributed under the Licenses are distributed on an "AS IS" + BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express + or implied. See the Licenses for the specific language governing + permissions and limitations under the Licenses. + */ + +namespace MCGalaxy.Commands { + + public sealed class CmdTexture : Command { + + public override string name { get { return "texture"; } } + public override string shortcut { get { return ""; } } + public override string type { get { return CommandTypes.Other; } } + public override bool museumUsable { get { return true; } } + public override LevelPermission defaultRank { get { return LevelPermission.Operator; } } + public CmdTexture() { } + + public override void Use(Player p, string message) { + if (message == "") { Help(p); return; } + string[] args = message.Split(' '); + if (args.Length != 2) { Help(p); return; } + string scope = args[0].ToLower(); + string url = args[1]; + + if (url.ToLower() == "normal" || url.ToLower() == "reset") { + url = ""; + } else if (!(url.StartsWith("http://") || url.StartsWith("https://"))) { + p.SendMessage("Please use http:// or https:// in front of your URL"); return; + } + + if ((scope == "global" || scope == "level") && !url.EndsWith(".png")) { + p.SendMessage("The terrain URL must end in a .png"); return; + } + if ((scope == "globalzip" || scope == "levelzip") && !url.EndsWith(".zip")) { + p.SendMessage("The texture pack URL must end in a .zip"); return; + } + + if (scope == "global") { + Server.defaultTerrainUrl = url; + p.SendMessage("Set server's default terrain to " + args[1]); + UpdateGlobally(p, false); + } else if (scope == "level") { + p.level.terrainUrl = url; + p.SendMessage("Set level's terrain to " + args[1]); + UpdateLevel(p, false); + } else if (scope == "globalzip") { + Server.defaultTexturePackUrl = url; + p.SendMessage("Set server's default texture pack to " + args[1]); + UpdateGlobally(p, true); + } else if (scope == "levelzip") { + p.level.texturePackUrl = url; + p.SendMessage("Set level's texture pack to " + args[1]); + UpdateLevel(p, true); + } + } + + void UpdateGlobally(Player p, bool zip) { + foreach (Player pl in Player.players) { + bool hasExt = pl.HasCpeExt(CpeExt.EnvMapAppearance) || pl.HasCpeExt(CpeExt.EnvMapAppearance, 2); + string url = zip ? pl.level.texturePackUrl : pl.level.terrainUrl; + if (hasExt && url == "") + pl.SendCurrentMapAppearance(); + } + SrvProperties.Save("properties/server.properties"); + } + + void UpdateLevel(Player p, bool zip) { + foreach (Player pl in Player.players) { + bool hasExt = pl.HasCpeExt(CpeExt.EnvMapAppearance) || pl.HasCpeExt(CpeExt.EnvMapAppearance, 2); + if (hasExt && pl.level == p.level) + pl.SendCurrentMapAppearance(); + } + p.level.Save(); + Level.SaveSettings(p.level); + } + + public override void Help(Player p) { + Player.SendMessage(p, "%T/texture [scope] [url]"); + Player.SendMessage(p, "%H global/globalzip scope: Changes server's default texture."); + Player.SendMessage(p, "%H level/levelzip scope: Changes current level's texture."); + Player.SendMessage(p, "%HUsing 'reset' as a url will reset the texture to default."); + Player.SendMessage(p, "%HNote: zip texture packs are not supported by all clients."); + } + } +} diff --git a/Commands/other/CmdTexture.cs b/Commands/other/CmdTexture.cs deleted file mode 100644 index bb18f8b8f..000000000 --- a/Commands/other/CmdTexture.cs +++ /dev/null @@ -1,77 +0,0 @@ -/* - Copyright 2011 MCGalaxy - - Dual-licensed under the Educational Community License, Version 2.0 and - the GNU General Public License, Version 3 (the "Licenses"); you may - not use this file except in compliance with the Licenses. You may - obtain a copy of the Licenses at - - http://www.opensource.org/licenses/ecl2.php - http://www.gnu.org/licenses/gpl-3.0.html - - Unless required by applicable law or agreed to in writing, - software distributed under the Licenses are distributed on an "AS IS" - BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express - or implied. See the Licenses for the specific language governing - permissions and limitations under the Licenses. - */ - -namespace MCGalaxy.Commands { - - public sealed class CmdTexture : Command { - - public override string name { get { return "texture"; } } - public override string shortcut { get { return ""; } } - public override string type { get { return CommandTypes.Other; } } - public override bool museumUsable { get { return true; } } - public override LevelPermission defaultRank { get { return LevelPermission.Operator; } } - public CmdTexture() { } - - public override void Use(Player p, string message) { - if (message == "") { Help(p); return; } - string[] args = message.Split(' '); - if (args.Length != 2) { Help(p); return; } - string scope = args[0].ToLower(); - string url = args[1]; - - if (url.ToLower() == "normal" || url.ToLower() == "reset") { - url = ""; - } else { - if (!url.StartsWith("http://") && !args[1].StartsWith("https://")) { - p.SendMessage("Please use http:// or https:// in front of your URL"); return; - } - if (!url.EndsWith(".png")) { - p.SendMessage("Please make sure your URL ends in .png"); return; - } - } - - if (scope == "global") { - Server.defaultTextureUrl = url; - p.SendMessage("Set server's default texture to " + args[1]); - foreach (Player pl in Player.players) { - if (pl.HasCpeExt(CpeExt.EnvMapAppearance) && pl.level.textureUrl == "") { - pl.SendSetMapAppearance(Server.defaultTextureUrl, p.level.EdgeBlock, p.level.HorizonBlock, p.level.EdgeLevel); - } - } - SrvProperties.Save("properties/server.properties"); - } else if (scope == "level") { - p.level.textureUrl = url; - p.SendMessage("Set level's texture to " + args[1]); - - foreach (Player pl in Player.players) { - if (pl.HasCpeExt(CpeExt.EnvMapAppearance) && pl.level == p.level) { - pl.SendSetMapAppearance(p.level.textureUrl, p.level.EdgeBlock, p.level.HorizonBlock, p.level.EdgeLevel); - } - } - p.level.Save(); - Level.SaveSettings(p.level); - } - } - - public override void Help(Player p) { - p.SendMessage("/texture global [texture url] - Changes the server default texture"); - p.SendMessage("/texture level [texture url] - Changes current level's texture"); - p.SendMessage("Using 'reset' for the texture url will reset the texture to default."); - } - } -} diff --git a/Levels/IO/LvlProperties.cs b/Levels/IO/LvlProperties.cs index 78c448c10..89ca6800d 100644 --- a/Levels/IO/LvlProperties.cs +++ b/Levels/IO/LvlProperties.cs @@ -74,7 +74,8 @@ namespace MCGalaxy.Levels.IO { writer.WriteLine("RandomFlow = " + level.randomFlow); writer.WriteLine("GrowTrees = " + level.growTrees); writer.WriteLine("Weather = " + level.weather); - writer.WriteLine("Texture = " + level.textureUrl); + writer.WriteLine("Texture = " + level.terrainUrl); + writer.WriteLine("TexturePack = " + level.texturePackUrl); } static string GetName(LevelPermission perm) { @@ -96,6 +97,7 @@ namespace MCGalaxy.Levels.IO { writer.WriteLine("FogColor = " + level.FogColor); writer.WriteLine("EdgeLevel = " + level.EdgeLevel); + writer.WriteLine("CloudsHeight = " + level.CloudsHeight); writer.WriteLine("EdgeBlock = " + level.EdgeBlock); writer.WriteLine("HorizonBlock = " + level.HorizonBlock); } @@ -137,6 +139,7 @@ namespace MCGalaxy.Levels.IO { case "lightcolor": level.LightColor = value; break; case "edgeblock": level.EdgeBlock = byte.Parse(value); break; case "edgelevel": level.EdgeLevel = short.Parse(value); break; + case "cloudsheight": level.CloudsHeight = short.Parse(value); break; case "horizonblock": level.HorizonBlock = byte.Parse(value); break; } } catch { @@ -200,7 +203,9 @@ namespace MCGalaxy.Levels.IO { case "weather": level.weather = byte.Parse(value); break; case "texture": - level.textureUrl = value; break; + level.terrainUrl = value; break; + case "texturepack": + level.texturePackUrl = value; break; case "buildable": level.Buildable = bool.Parse(value); break; case "deletable": diff --git a/Levels/Level.cs b/Levels/Level.cs index 8ec824701..71fc3ac4b 100644 --- a/Levels/Level.cs +++ b/Levels/Level.cs @@ -96,7 +96,7 @@ namespace MCGalaxy public bool Buildable = true, Deletable = true; public byte weather; - public string textureUrl = ""; + public string terrainUrl = "", texturePackUrl = ""; public bool cancelsave1; public bool cancelunload; @@ -141,6 +141,8 @@ namespace MCGalaxy /// Elevation of the "ocean" that surrounds maps. Set to -1 to use client default (halfway up the map). public short EdgeLevel = -1; + + public short CloudsHeight = -1; /// The block which will be displayed on the horizon. public byte HorizonBlock = Block.water; @@ -213,6 +215,7 @@ namespace MCGalaxy Length = 16; name = n; + CloudsHeight = (short)(y + 2); blocks = new byte[Width * Height * Length]; ChunksX = (Width + 15) >> 4; ChunksY = (Height + 15) >> 4; diff --git a/MCGalaxy_.csproj b/MCGalaxy_.csproj index d4dfe61f8..a5a5d54ae 100644 --- a/MCGalaxy_.csproj +++ b/MCGalaxy_.csproj @@ -375,7 +375,6 @@ - @@ -413,6 +412,7 @@ + diff --git a/Network/Player.Networking.cs b/Network/Player.Networking.cs index 96d1d06a2..aedc5592c 100644 --- a/Network/Player.Networking.cs +++ b/Network/Player.Networking.cs @@ -82,6 +82,11 @@ namespace MCGalaxy { void HandleExtInfo( byte[] message ) { appName = enc.GetString( message, 0, 64 ).Trim(); extensionCount = message[65]; + // NOTE: Workaround as ClassiCube violates the CPE specification here. + // If server sends version 2, the client should reply with version 1. + // Except ClassiCube just doesn't reply at all if server sends version 2. + if (appName == "ClassiCube Client") + EnvMapAppearance = 1; } void HandleExtEntry( byte[] message ) { @@ -384,7 +389,7 @@ namespace MCGalaxy { SendSetMapWeather(level.weather); if (HasCpeExt(CpeExt.EnvColors)) SendCurrentEnvColors(); - if (HasCpeExt(CpeExt.EnvMapAppearance)) + if (HasCpeExt(CpeExt.EnvMapAppearance) || HasCpeExt(CpeExt.EnvMapAppearance, 2)) SendCurrentMapAppearance(); if ( OnSendMap != null ) OnSendMap(this, buffer); @@ -636,12 +641,25 @@ namespace MCGalaxy { byte[] buffer = new byte[69]; buffer[0] = Opcode.CpeEnvSetMapApperance; NetUtils.WriteAscii(url, buffer, 1); + Server.s.Log(url + "," + ((char)buffer[1])); buffer[65] = sideblock; buffer[66] = edgeblock; NetUtils.WriteI16(sidelevel, buffer, 67); SendRaw(buffer); } + public void SendSetMapAppearanceV2( string url, byte sideblock, byte edgeblock, short sidelevel, short cloudHeight) { + byte[] buffer = new byte[73]; + buffer[0] = Opcode.CpeEnvSetMapApperance; + NetUtils.WriteAscii(url, buffer, 1); + buffer[65] = sideblock; + buffer[66] = edgeblock; + NetUtils.WriteI16(sidelevel, buffer, 67); + NetUtils.WriteI16(cloudHeight, buffer, 69); + // TODO: allow changing max view distance + SendRaw(buffer); + } + public void SendSetMapWeather( byte weather ) { // 0 - sunny; 1 - raining; 2 - snowing SendRaw(Opcode.CpeEnvWeatherType, weather); } diff --git a/Player/Player.CPE.cs b/Player/Player.CPE.cs index 3b2e8ab48..ad061119c 100644 --- a/Player/Player.CPE.cs +++ b/Player/Player.CPE.cs @@ -106,7 +106,6 @@ namespace MCGalaxy } break;*/ case CpeExt.EnvColors: - SendCurrentEnvColors(); EnvColors = version; break; case CpeExt.SelectionCuboid: SelectionCuboid = version; break; @@ -116,10 +115,8 @@ namespace MCGalaxy UpdateModels(); ChangeModel = version; break; case CpeExt.EnvMapAppearance: - SendCurrentMapAppearance(); EnvMapAppearance = version; break; case CpeExt.EnvWeatherType: - SendSetMapWeather(level.weather); EnvWeatherType = version; break; case CpeExt.HackControl: HackControl = version; break; @@ -180,8 +177,15 @@ namespace MCGalaxy } public void SendCurrentMapAppearance() { - string url = level.textureUrl == "" ? Server.defaultTextureUrl : level.textureUrl; - SendSetMapAppearance(url, level.EdgeBlock, level.HorizonBlock, level.EdgeLevel); + if (EnvMapAppearance == 2) { + string url = level.texturePackUrl == "" ? level.terrainUrl : level.texturePackUrl; + if (url == "") + url = Server.defaultTexturePackUrl == "" ? Server.defaultTerrainUrl : Server.defaultTexturePackUrl; + SendSetMapAppearanceV2(url, level.EdgeBlock, level.HorizonBlock, level.EdgeLevel, level.CloudsHeight); + } else { + string url = level.terrainUrl == "" ? Server.defaultTerrainUrl : level.terrainUrl; + SendSetMapAppearance(url, level.EdgeBlock, level.HorizonBlock, level.EdgeLevel); + } } public void SendCurrentEnvColors() { @@ -202,21 +206,21 @@ namespace MCGalaxy } public void SendCurrentBlockPermissions() { - byte count = hasCustomBlocks ? Block.CpeCount : Block.OriginalCount; - for (byte i = 0; i < count; i++) { - bool canPlace = Block.canPlace(this, i); - bool canDelete = canPlace; - - if (!level.Buildable) canPlace = false; - if (!level.Deletable) canDelete = false; - SendSetBlockPermission(i, canPlace, canDelete); - } - - if (!HasCpeExt(CpeExt.BlockDefinitions)) return; - for (int i = count; i < 256; i++) { - if (BlockDefinition.GlobalDefinitions[i] == null) continue; - SendSetBlockPermission((byte)i, level.Buildable, level.Deletable); - } + byte count = hasCustomBlocks ? Block.CpeCount : Block.OriginalCount; + for (byte i = 0; i < count; i++) { + bool canPlace = Block.canPlace(this, i); + bool canDelete = canPlace; + + if (!level.Buildable) canPlace = false; + if (!level.Deletable) canDelete = false; + SendSetBlockPermission(i, canPlace, canDelete); + } + + if (!HasCpeExt(CpeExt.BlockDefinitions)) return; + for (int i = count; i < 256; i++) { + if (BlockDefinition.GlobalDefinitions[i] == null) continue; + SendSetBlockPermission((byte)i, level.Buildable, level.Deletable); + } } } diff --git a/Player/Player.cs b/Player/Player.cs index 920b96b3c..c4ac08f69 100644 --- a/Player/Player.cs +++ b/Player/Player.cs @@ -680,7 +680,7 @@ namespace MCGalaxy { SendExtEntry(CpeExt.BlockPermissions, 1); SendExtEntry(CpeExt.ChangeModel, 1); - SendExtEntry(CpeExt.EnvMapAppearance, 1); + SendExtEntry(CpeExt.EnvMapAppearance, 2); SendExtEntry(CpeExt.EnvWeatherType, 1); SendExtEntry(CpeExt.HackControl, 1); diff --git a/Server/Properties.cs b/Server/Properties.cs index bea844631..65d0af946 100644 --- a/Server/Properties.cs +++ b/Server/Properties.cs @@ -88,16 +88,16 @@ namespace MCGalaxy { catch { Server.s.Log("port invalid! setting to default."); } break; case "verify-names": - Server.verify = ( value.ToLower() == "true" ) ? true : false; + Server.verify = value.ToLower() == "true"; break; case "public": - Server.pub = ( value.ToLower() == "true" ) ? true : false; + Server.pub = value.ToLower() == "true"; break; case "world-chat": - Server.worldChat = ( value.ToLower() == "true" ) ? true : false; + Server.worldChat = value.ToLower() == "true"; break; //case "guest-goto": - // Server.guestGoto = (value.ToLower() == "true") ? true : false; + // Server.guestGoto = value.ToLower() == "true"; // break; case "max-players": try { @@ -140,10 +140,10 @@ namespace MCGalaxy { } break; case "irc": - Server.irc = ( value.ToLower() == "true" ) ? true : false; + Server.irc = value.ToLower() == "true"; break; case "irc-colorsenable": - Server.ircColorsEnable = ( value.ToLower() == "true" ) ? true : false; + Server.ircColorsEnable = value.ToLower() == "true"; break; case "irc-server": Server.ircServer = value; @@ -188,7 +188,7 @@ namespace MCGalaxy { case "report-back": - Server.reportBack = ( value.ToLower() == "true" ) ? true : false; + Server.reportBack = value.ToLower() == "true"; break; case "backup-time": if ( Convert.ToInt32(value) > 1 ) { Server.backupInterval = Convert.ToInt32(value); } @@ -197,20 +197,14 @@ namespace MCGalaxy { if ( !value.Contains("System.Windows.Forms.TextBox, Text:") ) Server.backupLocation = value; break; - - //case "console-only": // Never used - // Server.console = (value.ToLower() == "true") ? true : false; - // break; - case "physicsrestart": - Server.physicsRestart = ( value.ToLower() == "true" ) ? true : false; + Server.physicsRestart = value.ToLower() == "true"; break; case "deathcount": - Server.deathcount = ( value.ToLower() == "true" ) ? true : false; + Server.deathcount = value.ToLower() == "true"; break; - case "usemysql": - Server.useMySQL = ( value.ToLower() == "true" ) ? true : false; + Server.useMySQL = value.ToLower() == "true"; break; case "host": Server.MySQLHost = value; @@ -354,13 +348,13 @@ namespace MCGalaxy { catch { Server.s.Log("Invalid " + key + ". Using default."); break; } break; case "auto-update": - Server.autoupdate = ( value.ToLower() == "true" ) ? true : false; + Server.autoupdate = value.ToLower() == "true"; break; case "use-beta-version": - Server.DownloadBeta = (value.ToLower() == "true") ? true : false; + Server.DownloadBeta = value.ToLower() == "true"; break; case "in-game-update-notify": - Server.notifyPlayers = ( value.ToLower() == "true" ) ? true : false; + Server.notifyPlayers = value.ToLower() == "true"; break; case "update-countdown": try { Server.restartcountdown = Convert.ToInt32(value).ToString(); } @@ -383,13 +377,13 @@ namespace MCGalaxy { catch { Server.s.Log("Invalid " + key + ". Using default."); break; } break; case "use-whitelist": - Server.useWhitelist = ( value.ToLower() == "true" ) ? true : false; + Server.useWhitelist = value.ToLower() == "true"; break; case "premium-only": - Server.PremiumPlayersOnly = ( value.ToLower() == "true" ) ? true : false; + Server.PremiumPlayersOnly = value.ToLower() == "true"; break; case "allow-tp-to-higher-ranks": - Server.higherranktp = ( value.ToLower() == "true" ) ? true : false; + Server.higherranktp = value.ToLower() == "true"; break; case "agree-to-rules-on-entry": try { Server.agreetorulesonentry = bool.Parse(value); } @@ -405,13 +399,15 @@ namespace MCGalaxy { break; case "default-texture-url": if (!value.StartsWith("http://") && !value.StartsWith("https://")) - { - Server.defaultTextureUrl = ""; - } + Server.defaultTerrainUrl = ""; else - { - Server.defaultTextureUrl = value; - } + Server.defaultTerrainUrl = value; + break; + case "default-texture-pack-url": + if (!value.StartsWith("http://") && !value.StartsWith("https://")) + Server.defaultTexturePackUrl = ""; + else + Server.defaultTexturePackUrl = value; break; case "dollar-before-dollar": try { Server.dollardollardollar = bool.Parse(value); } @@ -772,7 +768,8 @@ namespace MCGalaxy { w.WriteLine("restart-on-error = " + Server.restartOnError); w.WriteLine("menu-style = " + Server.menustyle.ToString()); w.WriteLine("main-name = " + Server.level); - w.WriteLine("default-texture-url = " + Server.defaultTextureUrl); + w.WriteLine("default-texture-url = " + Server.defaultTerrainUrl); + w.WriteLine("default-texture-pack-url = " + Server.defaultTexturePackUrl); //w.WriteLine("guest-goto = " + Server.guestGoto); w.WriteLine(); w.WriteLine("# irc bot options"); diff --git a/Server/Server.cs b/Server/Server.cs index e3e673d95..3432d2cf1 100644 --- a/Server/Server.cs +++ b/Server/Server.cs @@ -353,7 +353,7 @@ namespace MCGalaxy public static bool guestLimitNotify = false; public static bool guestJoinNotify = true; public static bool guestLeaveNotify = true; - public static string defaultTextureUrl = ""; + public static string defaultTerrainUrl = "", defaultTexturePackUrl = ""; public static bool flipHead = false;