Using the StackSplitter Script

What does this script do?

Sometimes, when you create and flatten a set of fur, short hair- or leaf cards, you end up with a single bunch of i.e. 8000 islands or more. (Unless you model hair old-school, then this script is of no use) Dividing these up by hand for texture variety before you send them into your texturing app is a hassle, as is sending it back to your modeler. So we made a script that does this for you, we divide all the islands by ten  - 10 - once. And then you repeat per group as you want. After many rounds of testing, we decided that a single iteration was the easiest, most hassle-free way to go, as you can always divide your existing group by ten for even smaller card sets.

How do I use it?
  • After you've loaded your model select all your cards.
  • If your cards are geometrically identical, it suffices to enter Island Mode (F4) select one island and press ALT+G
  • If they are not geometrically identical, adjust the slider. For non-symmetrical, and none-too-similar islands, try setting it to P and 0, then press ALT+G - you may have to adjust a little here and there.
  • Load the script as described
  • Click on Stack in the Island group box
  • You'll see it flashing in various colours - that means RizomUV is dividing and grouping them
  • Unselect the islands and hit P to pack
  • RizomUV will now pack the island-groups based on your settings
  • Rinse and repeat on a per group basis
Loading your script

Download the RizomUV Stacksplitter Script here:

There are three ways to load a script into RizomUV

  • Open the Script Log window via pressing L or going to Tools>Show Scriptlog Window and pasting in  your script from a script editor or the RizomUV log window
  • Open the Script Log window via pressing L or going to Tools>Show Scriptlog Window,opening your File Menu, and opening your script from Explorer
  • Using the Script slots in the toolbar, and loading a script from Explorer
  • For a detailed  overview on how to load scripts, please take a look at the RizomUV Script Page

Quick Tip:
If dragging your islands is slow, try using the Transform tools! Use Tu to move left- or right, and Tv to move the stacks up or down!

Meet The Script!
-- This script divides each selected island group into several groups by ten

divideFactor = 10
groupMinSize = 10

print("Divide Island Groups Script by Rizom-Lab")

function GetSelectedGroups()
-- the function returns 2 arrays:Tile and group names from the selected groups
	groupPaths = {}
	for i,childName in pairs(ZomItemNames("Lib.Mesh.RootGroup.Children")) do        -- Iterates over the items
		groupPath = "RootGroup.Children." .. childName

		if ZomGet("Lib.Mesh." .. groupPath .. ".IsTile") == true then               -- child is a tile
			for j,groupName in pairs(ZomItemNames("Lib.Mesh." .. groupPath .. ".Children")) do        -- Iterates over the groups inside the tile
				if ZomGet("Lib.Mesh." .. groupPath .. ".Children." .. groupName .. ".TopoStable.Selected") then
					table.insert(groupPaths, groupPath .. ".Children." .. groupName)
				end
			end
		else                                                                        -- child is a group
			if ZomGet("Lib.Mesh." .. groupPath ..  ".TopoStable.Selected") then
				table.insert(groupPaths, groupPath)
			end
		end
	end

	return groupPaths
end

groupPaths = GetSelectedGroups()

if #groupPaths == 0 then
	print("No island group selected, please select at least one group to divide")
end

for j,groupPath in pairs(groupPaths) do 
	-- Get islands indexes in the group and its properties
	islandIDs = ZomGet("Lib.Mesh." .. groupPath .. ".IslandIDs")
	groupProperties = {Pack=ZomGet("Lib.Mesh." .. groupPath .. ".TopoStable.Pack")} -- only take the Pack table member

	print("Island Group " .. groupPath .. " has " .. #islandIDs .. " islands...")

	-- Avoid too small groups
	if #islandIDs <= groupMinSize  then
		print("...this group is too small and so avoided.")
		goto continue
	end

	-- Delete the source group
	ZomIslandGroups({Mode="TransferToParent", WorkingSet="Visible", MergingPolicyString="A_ADD|AIB_ADD_A_VALUE_B|B_CLONE", AutoDelete=true, GroupPaths={ groupPath }})

	-- Compute the new group size after division
	groupSize = math.floor(#islandIDs / divideFactor)

	-- Subdivides the islandID sets so that each new group contains maximum groupSize elements
	ids = {}
	gid = 0
	for i,id in pairs(islandIDs) do
		table.insert(ids, id)
		if #ids == groupSize or i == #islandIDs then
			-- Create the divided group gid
			ZomIslandGroups({Mode="DefineGroup", WorkingSet="Visible", MergingPolicyString="A_ADD|AIB_ADD_A_VALUE_B|B_CLONE", IslandIDs=ids, GroupPath=groupPath .. "n" .. gid, AutoDelete=true, Properties=groupProperties})
			ids = {}
			gid = gid + 1
		end
	end
	::continue::
end