Merge branch 'master' of NorbiPeti/GamecraftModdingAPI into master

This commit is contained in:
NGnius 2020-01-04 00:27:46 +00:00 committed by Gitea
commit 79a2f7c09c
5 changed files with 394 additions and 0 deletions

View file

@ -0,0 +1,17 @@
namespace GamecraftModdingAPI.Blocks
{
public enum BlockColors
{
Default = byte.MaxValue,
White = 0,
Pink,
Purple,
Blue,
Aqua,
Green,
Lime,
Yellow,
Orange,
Red
}
}

View file

@ -0,0 +1,174 @@
namespace GamecraftModdingAPI.Blocks
{
public enum BlockIDs
{
AluminiumCube,
AxleS,
Battery,
HingeS,
MotorS,
HingeM,
MotorM,
TyreM,
AxleM,
IronCube,
RubberCube,
OiledCube,
AluminiumConeSegment, //12
AluminiumCorner,
AluminiumRoundedCorner,
AluminiumSlicedCube,
AluminiumRoundedSlicedCube,
AluminiumCylinder,
AluminiumPyramidSegment,
AluminiumSlope,
AluminiumRoundedSlope,
AluminiumSphere,
RubberConeSegment, //22
RubberCorner,
RubberRoundedCorner,
RubberSlicedCube,
RubberRoundedSlicedCube,
RubberCylinder,
RubberPyramidSegment,
RubberSlope,
RubberRoundedSlope,
RubberSphere,
OiledConeSegment, //32
OiledCorner,
OiledRoundedCorner,
OiledSlicedCube,
OiledRoundedSlicedCube,
OiledCylinder,
OiledPyramidSegment,
OiledSlope,
OiledRoundedSlope,
OiledSphere,
IronConeSegment, //42
IronCorner,
IronRoundedCorner,
IronSlicedCube,
IronRoundedSlicedCube,
IronCylinder,
IronPyramidSegment,
IronSlope,
IronRoundedSlope,
IronSphere,
GlassCube, //52
GlassSlicedCube,
GlassSlope,
GlassCorner,
GlassPyramidSegment,
GlassRoundedSlicedCube,
GlassRoundedSlope,
GlassRoundedCorner,
GlassConeSegment,
GlassCylinder,
GlassSphere,
Lever,
Reactor, //64 - one ID is skipped
PlayerSpawn = 66, //Crashes without special handling
SmallSpawn,
MediumSpawn,
LargeSpawn,
BallJoint,
UniversalJoint,
ServoAxle,
ServoHinge,
StepperAxle,
StepperHinge,
TelescopicJoint,
DampedSpring,
ServoPiston,
StepperPiston,
PneumaticPiston,
PneumaticHinge,
PneumaticAxle, //82
PilotSeat = 90, //Might crash
PassengerSeat,
PilotControls,
GrassCube,
DirtCube,
GrassConeSegment,
GrassCorner,
GrassRoundedCorner,
GrassSlicedCube,
GrassRoundedSlicedCube,
GrassPyramidSegment,
GrassSlope,
GrassRoundedSlope,
DirtConeSegment,
DirtCorner,
DirtRoundedCorner,
DirtSlicedCube,
DirtRoundedSlicedCube,
DirtPyramidSegment,
DirtSlope,
DirtRoundedSlope,
RubberHemisphere,
AluminiumHemisphere,
GrassInnerCornerBulged,
DirtInnerCornerBulged,
IronHemisphere,
OiledHemisphere,
GlassHemisphere,
TyreS,
ThreeWaySwitch,
Dial, //120
CharacterOnEnterTrigger, //Probably crashes
CharacterOnLeaveTrigger,
CharacterOnStayTrigger,
ObjectOnEnterTrigger,
ObjectOnLeaveTrigger,
ObjectOnStayTrigger,
Button,
Switch,
TextBlock, //Brings up a screen
ConsoleBlock, //Brings up a screen
Door,
GlassDoor,
PoweredDoor,
PoweredGlassDoor,
AluminiumTubeCorner,
IronTubeCorner,
WoodCube,
WoodSlicedCube,
WoodSlope,
WoodCorner,
WoodPyramidSegment,
WoodConeSegment,
WoodRoundedSlicedCube,
WoodRoundedSlope,
WoodRoundedCorner,
WoodCylinder,
WoodHemisphere,
WoodSphere,
BrickCube, //149
BrickSlicedCube = 151,
BrickSlope,
BrickCorner,
ConcreteCube,
ConcreteSlicedCube,
ConcreteSlope,
ConcreteCorner,
BeachTree1 = 200,
BeachTree2,
BeachTree3,
Rock1,
Rock2,
Rock3,
Rock4,
BirchTree1,
BirchTree2,
BirchTree3,
PineTree1,
PineTree2,
PineTree3,
Flower1,
Flower2,
Flower3,
Shrub1,
Shrub2,
Shrub3
}
}

View file

@ -0,0 +1,46 @@
using System;
using GamecraftModdingAPI.Utility;
using GCMC;
using Unity.Mathematics;
namespace GamecraftModdingAPI.Blocks
{
/// <summary>
/// Common block movement operations
/// </summary>
public static class Placement
{
private static PlacementEngine placementEngine = new PlacementEngine();
/// <summary>
/// Place a block at the given position. If scaled, position means the center of the block. The default block size is 0.2 in terms of position.
/// Place blocks next to each other to connect them.
/// </summary>
/// <param name="block">The block's type</param>
/// <param name="color">The block's color</param>
/// <param name="darkness">The block color's darkness (0-9) - 0 is default color</param>
/// <param name="position">The block's position in the grid - default block size is 0.2</param>
/// <param name="rotation">The block's rotation</param>
/// <param name="uscale">The block's uniform scale - default scale is 1 (with 0.2 width)</param>
/// <param name="scale">The block's non-uniform scale - 0 means <paramref name="uscale"/> is used</param>
/// <param name="playerId">The player who placed the block</param>
/// <exception cref="Exception"></exception>
public static bool PlaceBlock(BlockIDs block, float3 position,
quaternion rotation = new quaternion(), BlockColors color = BlockColors.Default, byte darkness = 0,
int uscale = 1, float3 scale = new float3(), uint playerId = 0)
{
if (placementEngine.IsInGame && GameState.IsBuildMode())
{
placementEngine.PlaceBlock(block, color, darkness, position, uscale, scale, playerId, rotation);
return true;
}
return false;
}
public static void Init()
{
GameEngineManager.AddGameEngine(placementEngine);
}
}
}

View file

@ -0,0 +1,156 @@
using System;
using System.Reflection;
using DataLoader;
using GamecraftModdingAPI.Blocks;
using GamecraftModdingAPI.Utility;
using Harmony;
using JetBrains.Annotations;
using RobocraftX.Blocks;
using RobocraftX.Blocks.Ghost;
using RobocraftX.Blocks.Scaling;
using RobocraftX.Character;
using RobocraftX.CommandLine.Custom;
using RobocraftX.Common;
using RobocraftX.Common.Input;
using RobocraftX.Common.Utilities;
using RobocraftX.CR.MachineEditing;
using RobocraftX.StateSync;
using Svelto.ECS;
using Svelto.ECS.EntityStructs;
using Unity.Jobs;
using Unity.Mathematics;
using UnityEngine;
using uREPL;
namespace GCMC
{
public class PlacementEngine : IApiEngine
{
public bool IsInGame = false;
public void Dispose()
{
IsInGame = false;
}
public void Ready()
{
IsInGame = true;
}
public IEntitiesDB entitiesDB { get; set; }
internal static BlockEntityFactory _blockEntityFactory; //Injected from PlaceBlockEngine
/// <summary>
/// Places a block at the given position
/// </summary>
/// <param name="block">The block's type</param>
/// <param name="color">The block's color</param>
/// <param name="darkness">The block color's darkness - 0 is default color</param>
/// <param name="position">The block's position - default block size is 0.2</param>
/// <param name="uscale">The block's uniform scale - default scale is 1 (with 0.2 width)</param>
/// <param name="scale">The block's non-uniform scale - less than 1 means <paramref name="uscale"/> is used</param>
/// <param name="playerId">The player who placed the block</param>
/// <exception cref="Exception"></exception>
public void PlaceBlock(BlockIDs block, BlockColors color, byte darkness, float3 position, int uscale,
float3 scale, uint playerId, quaternion rotation)
{ //It appears that only the non-uniform scale has any visible effect, but if that's not given here it will be set to the uniform one
try
{
if (darkness > 9)
throw new Exception("That is too dark. Make sure to use 0-9 as darkness. (0 is default.)");
BuildBlock((ushort) block, (byte) (color + darkness * 10), position, uscale, scale, rotation).Init(
new BlockPlacementInfoStruct()
{
loadedFromDisk = false,
placedBy = playerId
});
}
catch (Exception e)
{
Console.WriteLine(e);
Log.Error(e.Message);
}
}
private EntityStructInitializer BuildBlock(ushort block, byte color, float3 position, int uscale, float3 scale, quaternion rot)
{
if (_blockEntityFactory == null)
throw new Exception("The factory is null.");
if (uscale < 1)
throw new Exception("Scale needs to be at least 1");
if (scale.x < 4e-5) scale.x = uscale;
if (scale.y < 4e-5) scale.y = uscale;
if (scale.z < 4e-5) scale.z = uscale;
//RobocraftX.CR.MachineEditing.PlaceBlockEngine
ScalingEntityStruct scaling = new ScalingEntityStruct {scale = scale};
RotationEntityStruct rotation = new RotationEntityStruct {rotation = quaternion.identity};
GridRotationStruct gridRotation = new GridRotationStruct
{position = float3.zero, rotation = quaternion.identity};
CubeCategoryStruct category = new CubeCategoryStruct
{category = CubeCategory.General, type = CubeType.Block};
uint dbid = block;
DBEntityStruct dbEntity = new DBEntityStruct {DBID = dbid};
uint num = PrefabsID.DBIDMAP[dbid];
GFXPrefabEntityStructGO gfx = new GFXPrefabEntityStructGO {prefabID = num};
BlockPlacementScaleEntityStruct placementScale = new BlockPlacementScaleEntityStruct
{
blockPlacementHeight = uscale, blockPlacementWidth = uscale, desiredScaleFactor = uscale,
snapGridScale = uscale,
unitSnapOffset = 0, isUsingUnitSize = true
};
EquippedColourStruct colour = new EquippedColourStruct {indexInPalette = color};
EGID egid2;
switch (category.category)
{
case CubeCategory.SpawnPoint:
case CubeCategory.BuildingSpawnPoint:
egid2 = MachineEditingGroups.NewSpawnPointBlockID;
break;
default:
egid2 = MachineEditingGroups.NewBlockID;
break;
}
int cubeId = PrefabsID.GenerateDBID((ushort) category.category, block);
EntityStructInitializer
structInitializer =
_blockEntityFactory.Build(egid2, (uint) cubeId); //The ghost block index is only used for triggers
if (colour.indexInPalette != byte.MaxValue)
structInitializer.Init(new ColourParameterEntityStruct
{
indexInPalette = colour.indexInPalette
});
structInitializer.Init(new GFXPrefabEntityStructGPUI(gfx.prefabID));
structInitializer.Init(new PhysicsPrefabEntityStruct(gfx.prefabID));
structInitializer.Init(dbEntity);
structInitializer.Init(new PositionEntityStruct {position = position});
structInitializer.Init(rotation);
structInitializer.Init(scaling);
structInitializer.Init(gridRotation);
structInitializer.Init(new UniformBlockScaleEntityStruct
{
scaleFactor = placementScale.desiredScaleFactor
});
return structInitializer;
}
public string Name { get; } = nameof(PlacementEngine);
[HarmonyPatch]
[UsedImplicitly]
public class FactoryObtainerPatch
{
static void Postfix(BlockEntityFactory blockEntityFactory)
{
_blockEntityFactory = blockEntityFactory;
Debug.Log("Block entity factory injected.");
}
static MethodBase TargetMethod(HarmonyInstance instance)
{
return typeof(PlaceBlockEngine).GetConstructors()[0];
}
}
}
}

View file

@ -61,6 +61,7 @@ namespace GamecraftModdingAPI
Blocks.Movement.Init(); Blocks.Movement.Init();
Blocks.Rotation.Init(); Blocks.Rotation.Init();
Blocks.Signals.Init(); Blocks.Signals.Init();
Blocks.Placement.Init();
Logging.MetaLog($"{currentAssembly.GetName().Name} v{currentAssembly.GetName().Version} initialized"); Logging.MetaLog($"{currentAssembly.GetName().Name} v{currentAssembly.GetName().Version} initialized");
} }