summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNiels Breuker <niels.breuker@hotmail.nl>2023-03-30 17:18:18 +0200
committerNiels Breuker <niels.breuker@hotmail.nl>2023-03-30 17:18:18 +0200
commit4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d (patch)
tree7bd7ef103724e6bed9c2cb79dadb50e88c901a89
parentAdded small embedded devices to README (diff)
downloadcuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar.gz
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar.bz2
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar.lz
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar.xz
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.tar.zst
cuberite-4af1f3ac35f6a7fe7ac2bfe625bad9abaf2e868d.zip
-rw-r--r--Server/Prefabs/PieceStructures/NetherFort.cubeset119
-rw-r--r--src/Generating/PieceGeneratorBFSTree.cpp112
-rw-r--r--src/Generating/PieceGeneratorBFSTree.h6
-rw-r--r--src/Generating/PiecePool.h3
-rw-r--r--src/Generating/PrefabPiecePool.cpp41
-rw-r--r--src/Generating/PrefabPiecePool.h4
-rw-r--r--src/Generating/VillageGen.cpp7
7 files changed, 246 insertions, 46 deletions
diff --git a/Server/Prefabs/PieceStructures/NetherFort.cubeset b/Server/Prefabs/PieceStructures/NetherFort.cubeset
index 2fad9d773..ec8496fac 100644
--- a/Server/Prefabs/PieceStructures/NetherFort.cubeset
+++ b/Server/Prefabs/PieceStructures/NetherFort.cubeset
@@ -1773,7 +1773,124 @@ Cubeset =
},
}, -- BlazePlatformOverhang
-
+ {
+ OriginData =
+ {
+ ExportName = "ClosurePiece",
+ },
+ Size =
+ {
+ x = 5,
+ y = 2,
+ z = 1
+ },
+ Hitbox =
+ {
+ MinX = 0,
+ MinY = 0,
+ MinZ = 0,
+ MaxX = 4,
+ MaxY = 2,
+ MaxZ = 0,
+ },
+ Connectors =
+ {
+ {
+ Type = 0,
+ RelX = 2,
+ RelY = 1,
+ RelZ = 0,
+ Direction = 2,
+ }
+ },
+ Metadata =
+ {
+ ["AddWeightIfSame"] = "0",
+ ["AllowedRotations"] = "7",
+ ["DefaultWeight"] = "100",
+ ["DepthWeight"] = "",
+ ["ExpandFloorStrategy"] = "none",
+ ["IsClosurePiece"] = "1",
+ ["MergeStrategy"] = "msSpongePrint",
+ ["MoveToGround"] = "0",
+ ["VerticalStrategy"] = "Range|40|100",
+ },
+ BlockDefinitions =
+ {
+ ".:112:0",
+ "a:113:0",
+ },
+ BlockData =
+ {
+ ".....",
+ ".aaa.",
+ }
+ }, -- End Piece Connector
+
+ {
+ OriginData =
+ {
+ ExportName = "ClosurePiece",
+ },
+ Size =
+ {
+ x = 5,
+ y = 6,
+ z = 1
+ },
+ Hitbox =
+ {
+ MinX = 0,
+ MinY = 0,
+ MinZ = 0,
+ MaxX = 4,
+ MaxY = 4,
+ MaxZ = 0,
+ },
+ Connectors =
+ {
+ {
+ Type = 1,
+ RelX = 2,
+ RelY = 1,
+ RelZ = 0,
+ Direction = 2,
+ },
+ {
+ Type = -1,
+ RelX = 2,
+ RelY = 1,
+ RelZ = 0,
+ Direction = 2,
+ }
+ },
+ Metadata =
+ {
+ ["AddWeightIfSame"] = "0",
+ ["AllowedRotations"] = "7",
+ ["DefaultWeight"] = "100",
+ ["DepthWeight"] = "",
+ ["ExpandFloorStrategy"] = "RepeatBottomTillSolid",
+ ["IsClosurePiece"] = "1",
+ ["MergeStrategy"] = "msSpongePrint",
+ ["MoveToGround"] = "0",
+ ["VerticalStrategy"] = "Range|40|100",
+ },
+ BlockDefinitions =
+ {
+ ".:112:0",
+ "a:113:0",
+ },
+ BlockData =
+ {
+ ".....",
+ ".aaa.",
+ ".aaa.",
+ ".aaa.",
+ ".aaa.",
+ ".....",
+ }
+ }, -- End Piece Connector
{
OriginData =
diff --git a/src/Generating/PieceGeneratorBFSTree.cpp b/src/Generating/PieceGeneratorBFSTree.cpp
index 2e26463f2..cf6e82ca3 100644
--- a/src/Generating/PieceGeneratorBFSTree.cpp
+++ b/src/Generating/PieceGeneratorBFSTree.cpp
@@ -101,16 +101,80 @@ bool cPieceGeneratorBFSTree::TryPlacePieceAtConnector(
const cPlacedPiece & a_ParentPiece,
const cPiece::cConnector & a_Connector,
cPlacedPieces & a_OutPieces,
- cPieceGeneratorBFSTree::cFreeConnectors & a_OutConnectors
+ cPieceGeneratorBFSTree::cFreeConnectors & a_OutConnectors,
+ bool a_OnlyClosurePieces
)
{
// Get a list of available connections:
cConnections Connections;
int WantedConnectorType = -a_Connector.m_Type;
- cPieces AvailablePieces = m_PiecePool.GetPiecesWithConnector(WantedConnectorType);
+ cPieces AvailablePieces;
+ if (a_OnlyClosurePieces)
+ {
+ AvailablePieces = m_PiecePool.GetClosurePiecesWithConnector(WantedConnectorType);
+ }
+ else
+ {
+ AvailablePieces = m_PiecePool.GetPiecesWithConnector(WantedConnectorType);
+ }
Connections.reserve(AvailablePieces.size());
Vector3i ConnPos = cPiece::cConnector::AddDirection(a_Connector.m_Pos, a_Connector.m_Direction); // The position at which the new connector should be placed - 1 block away from the current connector
int WeightTotal = 0;
+ FindPieceForConnector(AvailablePieces, a_ParentPiece, a_Connector, WantedConnectorType, ConnPos, a_OutPieces, Connections, WeightTotal);
+ if (Connections.empty())
+ {
+ // If there are no available connections try to place a closure connector.
+ AvailablePieces = m_PiecePool.GetClosurePiecesWithConnector(WantedConnectorType);
+ FindPieceForConnector(AvailablePieces, a_ParentPiece, a_Connector, WantedConnectorType, ConnPos, a_OutPieces, Connections, WeightTotal);
+ if (Connections.empty())
+ {
+ // No available connections, bail out
+ return false;
+ }
+ }
+ ASSERT(WeightTotal > 0);
+
+ // Choose a random connection from the list, based on the weights:
+ int rnd = (m_Noise.IntNoise3DInt(a_Connector.m_Pos.x, a_Connector.m_Pos.y, a_Connector.m_Pos.z) / 7) % WeightTotal;
+ size_t ChosenIndex = 0;
+ for (cConnections::const_iterator itr = Connections.begin(), end = Connections.end(); itr != end; ++itr, ++ChosenIndex)
+ {
+ rnd -= itr->m_Weight;
+ if (rnd <= 0)
+ {
+ // This is the piece to choose
+ break;
+ }
+ }
+ cConnection & Conn = Connections[ChosenIndex];
+
+ // Place the piece:
+ Vector3i NewPos = Conn.m_Piece->RotatePos(Conn.m_Connector.m_Pos, Conn.m_NumCCWRotations);
+ ConnPos -= NewPos;
+ auto PlacedPiece = std::make_unique<cPlacedPiece>(&a_ParentPiece, *(Conn.m_Piece), ConnPos, Conn.m_NumCCWRotations);
+
+ // Add the new piece's connectors to the list of free connectors:
+ cPiece::cConnectors Connectors = Conn.m_Piece->GetConnectors();
+ for (cPiece::cConnectors::const_iterator itr = Connectors.begin(), end = Connectors.end(); itr != end; ++itr)
+ {
+ if (itr->m_Pos.Equals(Conn.m_Connector.m_Pos))
+ {
+ // This is the connector through which we have been connected to the parent, don't add
+ continue;
+ }
+ a_OutConnectors.emplace_back(PlacedPiece.get(), Conn.m_Piece->RotateMoveConnector(*itr, Conn.m_NumCCWRotations, ConnPos.x, ConnPos.y, ConnPos.z));
+ }
+ a_OutPieces.push_back(std::move(PlacedPiece));
+
+ return true;
+}
+
+
+
+
+
+void cPieceGeneratorBFSTree::FindPieceForConnector(cPieces& AvailablePieces, const cPlacedPiece& a_ParentPiece, const cPiece::cConnector& a_Connector, int WantedConnectorType, Vector3i& ConnPos, cPlacedPieces& a_OutPieces, cPieceGeneratorBFSTree::cConnections& Connections, int& WeightTotal)
+{
for (cPieces::iterator itrP = AvailablePieces.begin(), endP = AvailablePieces.end(); itrP != endP; ++itrP)
{
// Get the relative chance of this piece being generated in this path:
@@ -153,46 +217,6 @@ bool cPieceGeneratorBFSTree::TryPlacePieceAtConnector(
WeightTotal += Weight;
} // for itrC - Connectors[]
} // for itrP - AvailablePieces[]
- if (Connections.empty())
- {
- // No available connections, bail out
- return false;
- }
- ASSERT(WeightTotal > 0);
-
- // Choose a random connection from the list, based on the weights:
- int rnd = (m_Noise.IntNoise3DInt(a_Connector.m_Pos.x, a_Connector.m_Pos.y, a_Connector.m_Pos.z) / 7) % WeightTotal;
- size_t ChosenIndex = 0;
- for (cConnections::const_iterator itr = Connections.begin(), end = Connections.end(); itr != end; ++itr, ++ChosenIndex)
- {
- rnd -= itr->m_Weight;
- if (rnd <= 0)
- {
- // This is the piece to choose
- break;
- }
- }
- cConnection & Conn = Connections[ChosenIndex];
-
- // Place the piece:
- Vector3i NewPos = Conn.m_Piece->RotatePos(Conn.m_Connector.m_Pos, Conn.m_NumCCWRotations);
- ConnPos -= NewPos;
- auto PlacedPiece = std::make_unique<cPlacedPiece>(&a_ParentPiece, *(Conn.m_Piece), ConnPos, Conn.m_NumCCWRotations);
-
- // Add the new piece's connectors to the list of free connectors:
- cPiece::cConnectors Connectors = Conn.m_Piece->GetConnectors();
- for (cPiece::cConnectors::const_iterator itr = Connectors.begin(), end = Connectors.end(); itr != end; ++itr)
- {
- if (itr->m_Pos.Equals(Conn.m_Connector.m_Pos))
- {
- // This is the connector through which we have been connected to the parent, don't add
- continue;
- }
- a_OutConnectors.emplace_back(PlacedPiece.get(), Conn.m_Piece->RotateMoveConnector(*itr, Conn.m_NumCCWRotations, ConnPos.x, ConnPos.y, ConnPos.z));
- }
- a_OutPieces.push_back(std::move(PlacedPiece));
-
- return true;
}
@@ -274,6 +298,10 @@ void cPieceGeneratorBFSTree::PlacePieces(int a_BlockX, int a_BlockZ, int a_MaxDe
//*/
}
}
+ else
+ {
+ TryPlacePieceAtConnector(*Conn.m_Piece, Conn.m_Connector, a_OutPieces, ConnectorPool, true);
+ }
NumProcessed++;
if (NumProcessed > 1000)
{
diff --git a/src/Generating/PieceGeneratorBFSTree.h b/src/Generating/PieceGeneratorBFSTree.h
index 33d2e5350..c7d85c44a 100644
--- a/src/Generating/PieceGeneratorBFSTree.h
+++ b/src/Generating/PieceGeneratorBFSTree.h
@@ -73,9 +73,13 @@ protected:
const cPlacedPiece & a_ParentPiece, // The existing piece to a new piece should be placed
const cPiece::cConnector & a_Connector, // The existing connector (world-coords) to which a new piece should be placed
cPlacedPieces & a_OutPieces, // Already placed pieces, to be checked for intersections
- cFreeConnectors & a_OutConnectors // List of free connectors to which the new connectors will be placed
+ cFreeConnectors & a_OutConnectors, // List of free connectors to which the new connectors will be placed
+ bool a_OnlyClosurePieces = false
);
+ /** Searches through the provided list for pieces that will fit the parent piece */
+ void FindPieceForConnector(cPieces & AvailablePieces, const cPlacedPiece & a_ParentPiece, const cPiece::cConnector & a_Connector, int WantedConnectorType, Vector3i & ConnPos, cPlacedPieces & a_OutPieces, cPieceGeneratorBFSTree::cConnections & Connections, int & WeightTotal);
+
/** Checks if the specified piece would fit with the already-placed pieces, using the specified connector
and number of CCW rotations.
a_ExistingConnector is in world-coords and is already rotated properly
diff --git a/src/Generating/PiecePool.h b/src/Generating/PiecePool.h
index 5897f32c7..2e027e354 100644
--- a/src/Generating/PiecePool.h
+++ b/src/Generating/PiecePool.h
@@ -284,6 +284,9 @@ public:
The cPiece pointers returned are managed by the pool and the caller doesn't free them. */
virtual cPieces GetPiecesWithConnector(int a_ConnectorType) = 0;
+ /** Returns a list of closure pieces that contain the specified connector type. */
+ virtual cPieces GetClosurePiecesWithConnector(int a_ConnectorType) = 0;
+
/** Returns the pieces that should be used as the starting point.
Multiple starting points are supported, one of the returned piece will be chosen. */
virtual cPieces GetStartingPieces(void) = 0;
diff --git a/src/Generating/PrefabPiecePool.cpp b/src/Generating/PrefabPiecePool.cpp
index 4deee38ef..b78251d78 100644
--- a/src/Generating/PrefabPiecePool.cpp
+++ b/src/Generating/PrefabPiecePool.cpp
@@ -84,6 +84,11 @@ void cPrefabPiecePool::Clear(void)
delete *itr;
}
m_StartingPieces.clear();
+ for (cPieces::iterator itr = m_ClosurePieces.begin(), end = m_ClosurePieces.end(); itr != end; ++itr)
+ {
+ delete* itr;
+ }
+ m_ClosurePieces.clear();
}
@@ -345,8 +350,18 @@ bool cPrefabPiecePool::LoadCubesetPieceVer1(const AString & a_FileName, cLuaStat
else
{
auto p = prefab.release();
- m_AllPieces.push_back(p);
- AddToPerConnectorMap(p);
+
+ int IsClosurePiece = 0;
+ a_LuaState.GetNamedValue("Metadata.IsClosurePiece", IsClosurePiece);
+ if (IsClosurePiece != 0)
+ {
+ m_ClosurePieces.push_back(p);
+ }
+ else
+ {
+ m_AllPieces.push_back(p);
+ AddToPerConnectorMap(p);
+ }
}
return true;
@@ -758,6 +773,28 @@ cPieces cPrefabPiecePool::GetPiecesWithConnector(int a_ConnectorType)
+cPieces cPrefabPiecePool::GetClosurePiecesWithConnector(int a_ConnectorType)
+{
+ cPieces pieces;
+ for (auto& piece : m_ClosurePieces)
+ {
+ auto connectors = piece->GetConnectors();
+ for (auto& connector : connectors)
+ {
+ if (connector.m_Type == a_ConnectorType)
+ {
+ pieces.push_back(piece);
+ break;
+ }
+ }
+ }
+ return pieces;
+}
+
+
+
+
+
cPieces cPrefabPiecePool::GetStartingPieces(void)
{
if (m_StartingPieces.empty())
diff --git a/src/Generating/PrefabPiecePool.h b/src/Generating/PrefabPiecePool.h
index 708b9be57..36aaf8bae 100644
--- a/src/Generating/PrefabPiecePool.h
+++ b/src/Generating/PrefabPiecePool.h
@@ -112,6 +112,7 @@ public:
// cPiecePool overrides:
virtual cPieces GetPiecesWithConnector(int a_ConnectorType) override;
+ virtual cPieces GetClosurePiecesWithConnector(int a_ConnectorType) override;
virtual cPieces GetStartingPieces(void) override;
virtual int GetPieceWeight(const cPlacedPiece & a_PlacedPiece, const cPiece::cConnector & a_ExistingConnector, const cPiece & a_NewPiece) override;
virtual int GetStartingPieceWeight(const cPiece & a_NewPiece) override;
@@ -132,6 +133,9 @@ protected:
This list is not shared and the pieces need deallocation. */
cPieces m_StartingPieces;
+ /** The pieces that can be used when no other piece will be placed. */
+ cPieces m_ClosurePieces;
+
/** The map that has all pieces by their connector types
The pieces are copies out of m_AllPieces and shouldn't be ever delete-d. */
cPiecesMap m_PiecesByConnector;
diff --git a/src/Generating/VillageGen.cpp b/src/Generating/VillageGen.cpp
index 6575b2f3a..281d49541 100644
--- a/src/Generating/VillageGen.cpp
+++ b/src/Generating/VillageGen.cpp
@@ -258,6 +258,13 @@ protected:
}
+ virtual cPieces GetClosurePiecesWithConnector(int a_ConnectorType) override
+ {
+ cPieces pieces;
+ return pieces;
+ }
+
+
virtual cPieces GetStartingPieces(void) override
{
return m_Prefabs.GetStartingPieces();