DO NOT run this mod, and leave the server running. If the server is running, then the mod is ran, and someone cuts down a tree and tries to remove the stump, it will bug the stump and it must manually be removed via the f_addForestPatch for the correct GeoDataID and TerID of the stump. This mod will not find the bugged stump because it will be half removed.
This must be ran either while the LiF server is down, or immediately before a restart. I've not tested adding it to the tail of patch.sql (i.e. CALL p_cleanStumps();
Now that all that's out of the way, time to get to the mod itself.
I've left my logging code in this (CALL p_ModLog....) which it can be removed if you want.
This creates a procedure called p_cleanStumps. It only needs to be called via: CALL p_cleanStumps(); in any query.
- Code: Select all
delimiter $$
CREATE DEFINER=`root`@`localhost` PROCEDURE `p_cleanStumps`()
LANGUAGE SQL
NOT DETERMINISTIC
CONTAINS SQL
SQL SECURITY DEFINER
COMMENT ''
BEGIN
DECLARE done BOOLEAN DEFAULT FALSE;
DECLARE _TerID INT UNSIGNED;
DECLARE _GeoID INT UNSIGNED;
DECLARE cur CURSOR FOR
SELECT forest.geodataid _GeoID, fp_grouped.TerID _TerID
FROM forest
LEFT OUTER JOIN (SELECT GeoDataID, TerID, MAX(Version) AS Version FROM forest_patch GROUP BY GeoDataID, TerID) fp_grouped
ON fp_grouped.GeoDataId = forest.GeodataID
WHERE forest.quality = 0;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done := TRUE;
CALL p_ModLog('StumpRemoval','Opening Cursor');
/*The Cursor will contain the GeoID and TerID for every stump in the game.*/
OPEN cur;
ForestLoop:LOOP
FETCH cur INTO _GeoID,_TerID;
IF done THEN
CALL p_ModLog('StumpRemoval','Leaving Loop');
LEAVE ForestLoop;
END IF;
/* Restore the terrain to "blank"*/
CALL p_ModLog('StumpRemoval',CONCAT('Patching Forest with TerID:',_TerID,' GeoID:',_GeoID));
IF (f_addForestPatch(_TerID,3,_GeoID, NULL, NULL, NULL, NULL)) IS NOT NULL THEN /* If Success is Null, then we know the forest patch could not be updated and should not delete the stump data*/
CALL p_ModLog('StumpRemoval',CONCAT('Forest Patched, deleting stump with GeoID:',_GeoID));
/* Remove the stump from the forest table */
CALL p_deleteForestItem(_GeoID);
End IF;
END
LOOP ForestLoop;
CALL p_ModLog('StumpRemoval','Closing Cursor and exiting.');
CLOSE cur;
END
$$
During my tests on my dev box, i was able to cut down multiple trees, shut down the server, restart it, log back in and all stumps (that weren't glitched from my original testing) were all gone and the terrain was terraformable again.
Explanation of what this does.
First, it emulates what is done when someone removes a stump via Unroot. The cursor grabs all rows of the forest table that are quality 0 (stumps) and only if the forest_patch data is action 4 (tree cut down from what i can tell.) It then grabs the terrain ID (I'm not sure if it will ever be outside of 446, but i didn't take that chance) of where the stump is, then "patches" it in via f_addForestPatch, if that was sucessful (which is important so the stump does not "glitch" and become stuck in the world) it will call the p_deleteForestItem and remove the stumps data from the forest table.
This was made in response to many talking about how stumps negatively impact a servers performance. Our dedicated server has not cooked long enough to see if this make a performance difference. If someone uses this and has a stump problem, please post a reply, I'd like to know if it make a difference. I'm sure others would too.
EDIT:
Fixed cursor query so it only grabs the forest_patch row's latest version. The rest of the procedure has not changed, only the cursor's initial select statement. Thanks Arthenius!