VoidParts v2.1.1 | FallenPartsDestroyHeight mimic with customization

VoidParts

FallenPartsDestroyHeight mimic with customization

Get the module here


How to use:

  1. Make sure you’ve disabled FallenPartsDestroyHeight by running this in the console: workspace.FallenPartsDestroyHeight = 0/0
  2. Require the module and call the initialize function in a server script
  3. Customize the behavior in the Config module inside VoidParts!

How it works:

VoidParts uses a “monitoring” system where it has a constantly updating table of supported parts utilizing workspace.DescendantAdded and workspace.DescendantRemoving.

Every second (by default) the table gets looped through to check if any part in that table is below the destroy height.

A part is unsupported (thus won’t be in the table) if it’s either:

  • Anchored (unless DestroyAnchoredParts is enabled in settings)
  • Has one of the exclusion tags in settings

Supported parts that become supported won’t reappear in the table (e.g. unanchoring an anchored part)
To fix this, you need to manually call VoidParts.MonitorPart(Part, true) in another script (otherwise it’ll fall forever and cause a memory leak!)


Each setting is documented inside the Config module inside VoidParts.
I used to list them here, but there’s way too many settings now


I’m surprised something like this hasn’t been made before. I honestly had a lot of fun coding this as well

Feedback and suggestions appreciated!

6 Likes

I really am curious if this is a performant way to do it.
image

2 Likes

I figured that it’d be more efficient to make my own parts table and update its contents by using workspace.DescendantAdded and DescendantRemoving, and not just loop through the entire workspace each heartbeat.

If your question is more about… my code just being bad, then take a look at this answer to a thread asking about GetPropertyChangedSignal(“Position”) not working. Unfortunately, it seems like there’s no better way to do this.

3 Likes

The least you can do is throttle execution little bit, you don’t really need to check all of parts each every frame.

3 Likes

Good idea. I’ll implement this hopefully tomorrow as it’s late right now for me

1 Like

I think you can disable this officially using workspace.FallHeightEnabled now

1 Like

It doesn’t actually do anything right now

1 Like

DestroyHeight v1.1 Changelog:

  • Fixed a lot of bugs, memory leaks, etc. (I’m kind of ashamed that I released DestroyHeight at such a raw state honestly)
  • Removed option to fully destroy humanoid models as you wouldn’t be able to respawn if it’s turned on
  • Added a delay option that delays the height check loop
    (Suggested by @UniDevx)
  • Added an option to not destroy non-humanoid ancestors of monitored parts that are direct children of Workspace (For anyone who sorts their Workspace by models like me)
  • Added a debug option
1 Like

DestroyHeight v1.2 Changelog:

  • Removed leftover unused code
  • Optimized the isSupportedPart and isSupportedAncestor functions a bit by putting a guard clause
  • When a player is found, now it checks if the part is the character’s primary part instead of checking if the name is “HumanoidRootPart”
  • Parts table and the DestroyLogic function can now be accessed by other scripts
  • Removed the empty task.wait() in the parts table loop

DestroyHeight v1.3 Changelog:

  • Now if a part has changed from being supported to unsupported, it will be removed from the parts table. This fixes a potential memory leak
  • Settings have been moved to a module under DestroyHeight
  • More guard clauses because I think they’re pretty

DestroyHeight v1.4 Changelog:

  • Fixed a bug where non player humanoid models would get all their parts monitored instead of their primary part
  • Added more comments to a few functions and elaborated on a few more things
  • Absolutely microscopic code changes

These few things have been bothering me, but hopefully this is the last update :pray: (Because these updates are useless at this point)

I recently found out that FallenPartsDestroyHeight removes joint connected parts of a part when it falls into the void. Whoops

DestroyHeight v1.5 Changelog:

  • Parts that don’t have their root part set as themselves won’t be monitored
  • When destroying a part, it will also call DestroyLogic to every connected part
  • Removed tons of code related to humanoids as they’re irrelevant and stupid
  • Instead of checking for a humanoid for the ExcludeWorkspaceChildren setting, it now uses players:GetPlayerFromCharacter()
  • Removed useless MonitorPart calls
  • With debug enabled, DestroyHeight will print a table of connected parts that it’s about to destroy

DestroyHeight v1.6 Changelog:

  • A part will now be supported if its root part doesn’t equal to itself (made this change because when a player uses a seat the hrp assemblyrootpart changes)

Nothing else just one single major bug fix

What is the point of using this over the roblox’s built in?

1 Like

My game had a problem where I didn’t want specific parts to get sucked up by the void, so I made this module to include an “exception tag” setting that wouldn’t destroy a part if it has a specific tag and lots of other settings for people that might need them.

If you’d read the post carefully, I already made a remark on the exception tags being the reason why this module exists in the first place

2 Likes

DestroyHeight v1.7 Changelog:

  • MonitorPart now accepts a monitor bool argument, instead of making a guess based on whether the part is inside the parts table or not. The code has been changed accordingly to use the monitor argument
  • Cleaned up the code and added comments
  • Replaced asserts with if statements (I’ve heard asserts are evil)
  • Improved performance of isSupported functions
  • Changed default Delay setting from 0.25 seconds to 1 second

I don’t know if I’m committing a sin by bumping this with changelogs

1 Like

DestroyHeight v1.8 Changelog:

  • New BeforeDestroy setting, which is a function that runs in DestroyLogic before the part gets destroyed
  • Rearranged the code and turned all global functions to local
  • Turned some variables into module variables to support initializing and stopping from two different scripts instead of just one
  • Replaced if statement errors with warns to declutter the console
  • Removed isSupportedAncestor function as it was used only once in the code
1 Like

VoidParts v1.9 Changelog

  • Renamed from DestroyHeight to VoidParts to not get mixed up with the workspace property FallenPartsDestroyHeight
  • Improved accuracy of the ancestor destroying logic to mimic the default FallenPartsDestroyHeight behavior better
1 Like

VoidParts v2.0 Changelog

  • Restructured the code again

  • Slightly changed the way garbage gets cleaned

  • Added more debug messages

  • Unnecessary checks in the IsSupportedPart function have been moved elsewhere to improve performance (which is also why there’s a new IsPart function)

  • The BeforeDestroy setting has been changed to OnBelowDestroyHeight, where it handles the entire destroying logic instead
    Previously, if you didn’t want to destroy a part when it gets below the destroy height, you had to edit the VoidParts module itself, which is not good

  • New ExcludeTagsDescendants setting (turned on by default, make sure this doesn’t break anything in your game if you used an older VoidParts version)
    When turned on, if an instance has an exclusion tag, all its descendants will also be excluded

  • New DestroyHumanoidAncestors setting inside the OnBelowDestroyHeight function that is turned off by default
    When turned on, will fully destroy player character or NPC models that have a humanoid in them
    You’ll have to implement your own player character respawning system
    If it destroys a player character, it won’t set the player .Character property to nil either
    This option was actually in v1.0 but I removed it in v1.1. Now it’s back!!!


VoidParts v2.1 Changelog (I decided to just edit the reply this time)

  • Removed printing the parts table since it no longer worked and there was an empty space instead of the parts table
  • Renamed Parts table to MonitoredParts for better readability
  • Optimized MonitorPart function
  • New UnsureMonitor function, since MonitorPart now doesn’t double-check if a part is/isn’t already monitored (Used in the Workspace.DescendantRemoving connection, and now in OnBelowDestroyHeight)
  • ProcessMonitoredPart function is now smaller
  • MonitorPart(part, false) was moved to the OnBelowDestroyHeight function setting (and was also changed to UnsureMonitor for reasons I already documented inside the code)

VoidParts v2.1.1 Changelog

  • The anxiety of having to choose between UnsureMonitor and MonitorPart is not worth the 0.01% performance increase. UnsureMonitor has been removed and MonitorPart has been reverted to how it was before
1 Like

None of those ways work. Using nil will error (and set FallenPartsDestroyHeight to 0) and -math.huge will result in FallenPartsDestroyHeight being -50000 instead