• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

Destroying a chest should make items fall out

Sportacus

Intermediate OT User
Joined
Aug 3, 2008
Messages
718
Reaction score
104
Whenever you destroy a chest (by using a weapon on it) it should cause the items from inside of the chest to fall on the floor, on top of the rubbish made from breaking the chest (or any other container).


Not sure if this can be done, so I am requesting it.
 
here, to a test
LUA:
function destroyItem(cid, itemEx, toPosition)
	if(itemEx.uid <= 65535 or itemEx.actionid > 0) then
		return false
	end

	if(isInArray(SPIDER_WEB, itemEx.itemid)) then
		if math.random(3) == 1 then
			doTransformItem(itemEx.uid, (itemEx.itemid + 6))
			doDecayItem(itemEx.uid)
		end

		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end

	if(isInArray(BAMBOO_FENCE, itemEx.itemid)) then
		if math.random(3) == 1 then
			if(itemEx.itemid == BAMBOO_FENCE[1]) then
				doTransformItem(itemEx.uid, (itemEx.itemid + 161))
			elseif(itemEx.itemid == BAMBOO_FENCE[2]) then
				doTransformItem(itemEx.uid, (itemEx.itemid + 159))
			end
			doDecayItem(itemEx.uid)
		end

		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end

	if not(isInArray({1770, 2098, 1774, 2064, 2094, 2095, 1619, 2602, 3805, 3806}, itemEx.itemid) or
		(itemEx.itemid >= 1724 and itemEx.itemid <= 1741) or
		(itemEx.itemid >= 2581 and itemEx.itemid <= 2588) or
		(itemEx.itemid >= 1747 and itemEx.itemid <= 1753) or
		(itemEx.itemid >= 1714 and itemEx.itemid <= 1717) or
		(itemEx.itemid >= 1650 and itemEx.itemid <= 1653) or
		(itemEx.itemid >= 1666 and itemEx.itemid <= 1677) or
		(itemEx.itemid >= 1614 and itemEx.itemid <= 1616) or
		(itemEx.itemid >= 3798 and itemEx.itemid <= 3799) or
		(itemEx.itemid >= 3813 and itemEx.itemid <= 3820) or
		(itemEx.itemid >= 3807 and itemEx.itemid <= 3810) or
		(itemEx.itemid >= 2080 and itemEx.itemid <= 2085) or
		(itemEx.itemid >= 2116 and itemEx.itemid <= 2119)) then
		return false
	end

	if(math.random(1, 7) == 1) then
		if itemEx.uid == getPlayerItemById(cid, true, itemEx.id).uid then
			return doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
		end
		local items = {}
		local size = isContainer(itemEx.uid) and getContainerSize(itemEx.uid) or 0

		if(size > 0) then
			for i = 0, size do
				local tmp = getContainerItem(item.uid, i)
				if(tmp.itemid > 0) then
					table.insert(items, tmp)
				end
			end
		end
		size = table.maxn(items)
		if(size > 0) then
			for i = 1, size do
				local tmp = doCopyItem(items[i], true)
				doCreateItem(tmp.id, tmp.type or 1, toPosition)
			end
		end
		if(isInArray({1738, 1739, 1770, 2098, 1774, 1775, 2064}, itemEx.itemid) or
			(itemEx.itemid >= 2581 and itemEx.itemid <= 2588)) then
				doCreateItem(2250, 1, toPosition)
		elseif((itemEx.itemid >= 1747 and itemEx.itemid <= 1749) or itemEx.itemid == 1740) then
			doCreateItem(2251, 1, toPosition)
		elseif((itemEx.itemid >= 1714 and itemEx.itemid <= 1717)) then
			doCreateItem(2252, 1, toPosition)
		elseif((itemEx.itemid >= 1650 and itemEx.itemid <= 1653) or
			(itemEx.itemid >= 1666 and itemEx.itemid <= 1677) or
			(itemEx.itemid >= 1614 and itemEx.itemid <= 1616) or
			(itemEx.itemid >= 3813 and itemEx.itemid <= 3820) or
			(itemEx.itemid >= 3807 and itemEx.itemid <= 3810)) then
				doCreateItem(2253, 1, toPosition)
		elseif((itemEx.itemid >= 1724 and itemEx.itemid <= 1737) or
			(itemEx.itemid >= 2080 and itemEx.itemid <= 2085) or
			(itemEx.itemid >= 2116 and itemEx.itemid <= 2119) or
			isInArray({2094, 2095}, itemEx.itemid)) then
				doCreateItem(2254, 1, toPosition)
		elseif((itemEx.itemid >= 1750 and itemEx.itemid <= 1753) or isInArray({1619, 1741}, itemEx.itemid)) then
			doCreateItem(2255, 1, toPosition)
		elseif(itemEx.itemid == 2602) then
			doCreateItem(2257, 1, toPosition)
		elseif(itemEx.itemid == 3805 or itemEx.itemid == 3806) then
			doCreateItem(2259, 1, toPosition)
		elseif(itemEx.itemid == 3798) then
			doCreateItem(3959, 1, toPosition)
		elseif(itemEx.itemid == 3799) then
			doCreateItem(3958, 1, toPosition)
		end

		doRemoveItem(itemEx.uid, 1)
	end

	doSendMagicEffect(toPosition, CONST_ME_POFF)
	return true
end

-- edit
sorry, I wrote this for version 0.4tfs, I need to improve
 
Last edited:
Here is the error I get in the console:


[Error - Action Interface]
data/actions/scripts/default.lua:OnUse
Description:
data/actions/lib/actions.lua:94 attempt to index global 'item' (a nil value)
stack traceback:
data/actions/lib/actions.lua:94: in function <data/actions/lib/actions.lua:34>
<tail call>: ?




Line 94 says this:

local tmp = getContainerItem(item.uid, i)

(this is where you were trying to get the container items.)


Line 34 says this:

function destroyItem(cid, itemEx, toPosition)

(This is the start destroyItem function)
 
ech man


-->


and here


Thank you for helping out on this, but I found one small bug that we both probably overlooked.

It works fine with regular items, but if you have a bag (or any other container) inside of the chest that you break, it drops the bag but will be empty inside the bag even if you have items inside of it.

EDIT

Also if an item has a action or unique id, and is in the chest when you destroy it, it won't copy the action or unique id

Of course I will rep you for your help :)
 
Last edited:
I just wanted to post that I did get this to work in a completely different way, but it is a bit backwards but it works..

Let me show you.

First I added this function to my actions.lua

LUA:
function dropContainerItems(itemEx, toPosition)
	local tmp = getContainerItem(itemEx.uid, 0)
	if(tmp.itemid > 0) then
		doTeleportThing(tmp.uid, getTownTemplePosition(15), true)
		doRelocate(getTownTemplePosition(15), toPosition, false, false)
		return dropContainerItems(itemEx, toPosition)
	end
	return true
end



and then in the destroy item function I changed/added this

LUA:
	if(math.random(1, 7) == 1) then
		pos = toPosition
		pos2 = {x = pos.x, y = pos.y, z = pos.z, stackpos = 255}
		if itemEx.uid == getPlayerItemById(cid, true, itemEx.id).uid then
			return doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
		end
		
		local items = {}
		if isContainer(itemEx. nuid) then
			dropContainerItems(itemEx, pos2)
		else
			size = 0
		end



As you can see, I gave up on trying to copy the items because I ran into problems with action ids,unique ids, and items within containers (that were also in the chest) so I just had everything teleport to the town 15, an inaccessible place for players, and it teleports the contents back to the location of where you broke the chest.


Players will never notice that I did it this way and it works, I just know it can be done better than that and thats why this thread is still here.


and for anyone who wants to see my whole actions.lua here it is:


LUA:
SPOTS = {384, 418, 8278, 8592}
ROPABLE = { 294, 369, 370, 383, 392, 408, 409, 427, 428, 430, 462, 469, 470, 482, 484, 485, 489, 924, 3135, 3136, 7933, 7938, 8170, 8286, 8285,
	8284, 8281, 8280, 8279, 8277, 8276, 8323, 8380, 8567, 8585, 8596, 8595, 8249, 8250, 8251, 8252, 8253, 8254, 8255, 8256, 8972, 9606, 9625 }

HOLES = {468, 481, 483, 7932, 8579}
SAND_HOLES = {[9059] = 489, [8568] = 8567}
SAND = {231,9059}

JUNGLE_GRASS = {2782, 3985}
SPIDER_WEB = {7538, 7539}
BAMBOO_FENCE = {3798, 3799}
WILD_GROWTH = {1499, 11099}

PUMPKIN = 2683
PUMPKIN_HEAD = 2096

POOL = 2016

SPECIAL_FOODS = {
	[9992] = "Gulp.", [9993] = "Chomp.", [9994] = "Chomp.", [9995] = "Chomp.", [9997] = "Yum.",
	[9998] = "Munch.", [9999] = "Chomp.", [10000] = "Mmmm.", [10001] = "Smack.", [12540] = "Yum.", 
	[12542] = "Gulp.", [12543] = "?", [12544] = "Slurp!"
}

DOORS = {
        [1209] = 1211, [1212] = 1214, [1231] = 1233, [1234] = 1236, [1249] = 1251, [1252] = 1254, [3535] = 3537, [3544] = 3546, [4913] = 4915, [4916] = 4918,
        [5098] = 5100, [5107] = 5109, [5116] = 5118, [5125] = 5127, [5134] = 5136, [5137] = 5139, [5140] = 5142, [5143] = 5145, [5278] = 5280, [5281] = 5283,
        [5732] = 5734, [5735] = 5737, [6192] = 6194, [6195] = 6197, [6249] = 6251, [6252] = 6254, [6891] = 6893, [6900] = 6902, [7033] = 7035, [7042] = 7044,
        [8541] = 8543, [8544] = 8546, [9165] = 9167, [9168] = 9170, [9267] = 9269, [9270] = 9272, [10268] = 10270, [10271] = 10273, [10468] = 10470,
        [10477] = 10479, [10775] = 10777, [10784] = 10786, [12092] = 12094, [12099] = 12101, [12188] = 12190, [12197] = 12199

}
function dropContainerItems(itemEx, toPosition)
	local tmp = getContainerItem(itemEx.uid, 0)
	if(tmp.itemid > 0) then
		doTeleportThing(tmp.uid, getTownTemplePosition(15), true)
		doRelocate(getTownTemplePosition(15), toPosition, false, false)
		return dropContainerItems(itemEx, toPosition)
	end
	return true
end

function destroyItem(cid, itemEx, toPosition)
	if(itemEx.uid <= 65535 or itemEx.actionid > 0) then
		return false
	end

        if(isInArray(SPIDER_WEB, itemEx.itemid)) then
                if math.random(3) == 1 then
                        doTransformItem(itemEx.uid, (itemEx.itemid + 6))
                        doDecayItem(itemEx.uid)
                end
                doSendMagicEffect(toPosition, CONST_ME_POFF)
                return true
        end
        if(isInArray(BAMBOO_FENCE, itemEx.itemid)) then
                if math.random(3) == 1 then
                        if(itemEx.itemid == BAMBOO_FENCE[1]) then
                                doTransformItem(itemEx.uid, (itemEx.itemid + 161))
                        elseif(itemEx.itemid == BAMBOO_FENCE[2]) then
                                doTransformItem(itemEx.uid, (itemEx.itemid + 159))
                        end
                        doDecayItem(itemEx.uid)
                end
                doSendMagicEffect(toPosition, CONST_ME_POFF)
                return true
        end


	
	if not(isInArray({1442, 1446, 1447, 1770,1775, 2098, 1774, 2034, 2101, 2105, 2064, 2094, 2095, 1619, 2602, 3805, 3806, 5046, 11125, 11127, 11128}, itemEx.itemid) or
		(itemEx.itemid >= 1476 and itemEx.itemid <= 1478) or
		(itemEx.itemid >= 1724 and itemEx.itemid <= 1741) or
		(itemEx.itemid >= 2581 and itemEx.itemid <= 2588) or
		(itemEx.itemid >= 1747 and itemEx.itemid <= 1753) or
		(itemEx.itemid >= 1714 and itemEx.itemid <= 1717) or
		(itemEx.itemid >= 1650 and itemEx.itemid <= 1653) or
		(itemEx.itemid >= 1666 and itemEx.itemid <= 1677) or
		(itemEx.itemid >= 1614 and itemEx.itemid <= 1616) or
		(itemEx.itemid >= 3832 and itemEx.itemid <= 3835) or
		(itemEx.itemid >= 3813 and itemEx.itemid <= 3820) or
		(itemEx.itemid >= 3807 and itemEx.itemid <= 3810) or
		(itemEx.itemid >= 2080 and itemEx.itemid <= 2085) or
		(itemEx.itemid >= 5055 and itemEx.itemid <= 5056) or
		(itemEx.itemid >= 6109 and itemEx.itemid <= 6110) or
		(itemEx.itemid >= 6111 and itemEx.itemid <= 6112) or
		(itemEx.itemid >= 6356 and itemEx.itemid <= 6357) or
		(itemEx.itemid >= 6368 and itemEx.itemid <= 6371) or
		(itemEx.itemid >= 11129 and itemEx.itemid <= 11132) or
		(itemEx.itemid >= 11203 and itemEx.itemid <= 11204) or
		(itemEx.itemid >= 2116 and itemEx.itemid <= 2119)) then
		return false
	end

	if(math.random(1, 7) == 1) then
		pos = toPosition
		pos2 = {x = pos.x, y = pos.y, z = pos.z, stackpos = 255}
		if itemEx.uid == getPlayerItemById(cid, true, itemEx.id).uid then
			return doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
		end
		
		local items = {}
		if isContainer(itemEx.uid) then
			dropContainerItems(itemEx, pos2)
		else
			size = 0
		end
	
		if(isInArray({1738, 1739, 1770, 2098, 1774, 1775, 2064}, itemEx.itemid) or
			(itemEx.itemid >= 2581 and itemEx.itemid <= 2588)) then
				doCreateItem(2250, 1, toPosition)
		elseif((itemEx.itemid >= 1747 and itemEx.itemid <= 1749) or itemEx.itemid == 1740) then
			doCreateItem(2251, 1, toPosition)
		elseif((itemEx.itemid >= 1714 and itemEx.itemid <= 1717) or
				(itemEx.itemid >= 3832 and itemEx.itemid <= 3835)) then
			doCreateItem(2252, 1, toPosition)
		elseif((itemEx.itemid >= 1650 and itemEx.itemid <= 1653) or
			(itemEx.itemid >= 1666 and itemEx.itemid <= 1677) or
			(itemEx.itemid >= 1614 and itemEx.itemid <= 1616) or
			(itemEx.itemid >= 3813 and itemEx.itemid <= 3820) or
			(itemEx.itemid >= 3807 and itemEx.itemid <= 3810)) then
				doCreateItem(2253, 1, toPosition)
		elseif((itemEx.itemid >= 1724 and itemEx.itemid <= 1737) or
			(itemEx.itemid >= 2080 and itemEx.itemid <= 2085) or
			(itemEx.itemid >= 2116 and itemEx.itemid <= 2119) or
			isInArray({2094, 2095}, itemEx.itemid)) then
				doCreateItem(2254, 1, toPosition)
		elseif((itemEx.itemid >= 1750 and itemEx.itemid <= 1753) or 
		(itemEx.itemid >= 6368 and itemEx.itemid <= 6371) or
		(itemEx.itemid >= 6109 and itemEx.itemid <= 6110) or
		isInArray({1619, 1741}, itemEx.itemid)) then
			doCreateItem(2255, 1, toPosition)
		elseif((itemEx.itemid == 2602) or
		(itemEx.itemid == 5046) or
		(itemEx.itemid == 1442) or
		(itemEx.itemid >= 1476 and itemEx.itemid <= 1478) or
		(itemEx.itemid >= 5055 and itemEx.itemid <= 5056) or
		(itemEx.itemid >= 6111 and itemEx.itemid <= 6112) or
		(itemEx.itemid == 1447) or
		(itemEx.itemid == 1446)) then
			doCreateItem(2257, 1, toPosition)
		elseif(itemEx.itemid == 3805 or itemEx.itemid == 3806)or
		(itemEx.itemid == 2034) or
		(itemEx.itemid >= 6356 and itemEx.itemid <= 6357) or
		(itemEx.itemid >= 11127 and itemEx.itemid <= 11128) or
		(itemEx.itemid >= 11129 and itemEx.itemid <= 11132) or
		(itemEx.itemid >= 11203 and itemEx.itemid <= 11204) then
			doCreateItem(2259, 1, toPosition)
		elseif(itemEx.itemid == 2105) then
			doCreateItem(2245, 1, toPosition)
		elseif(itemEx.itemid == 11125) then
			doCreateItem(2111, 1, toPosition)
		elseif(itemEx.itemid == 2101) then
			doCreateItem(2244, 1, toPosition)
		end

		doRemoveItem(itemEx.uid, 1)
	end

	doSendMagicEffect(toPosition, CONST_ME_POFF)
	return true
end

TOOLS = {}
TOOLS.ROPE = function(cid, item, fromPosition, itemEx, toPosition)
	if(toPosition.x == CONTAINER_POSITION) then
		doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
		return true
	end

	toPosition.stackpos = STACKPOS_GROUND
	errors(false)
	local ground = getThingFromPos(toPosition)
	errors(true)
	if(isInArray(SPOTS, ground.itemid)) then
		doTeleportThing(cid, {x = toPosition.x, y = toPosition.y + 1, z = toPosition.z - 1}, false)
		return true
	elseif(isInArray(ROPABLE, itemEx.itemid)) then
		local canOnlyRopePlayers = getBooleanFromString(getConfigValue('canOnlyRopePlayers'))
		local hole = getThingFromPos({x = toPosition.x, y = toPosition.y, z = toPosition.z + 1, stackpos = STACKPOS_TOP_MOVEABLE_ITEM_OR_CREATURE})
		if(canOnlyRopePlayers) then
			if(isPlayer(hole.uid) and (not isPlayerGhost(hole.uid) or getPlayerGhostAccess(cid) >= getPlayerGhostAccess(hole.uid))) then
				doTeleportThing(hole.uid, {x = toPosition.x, y = toPosition.y + 1, z = toPosition.z}, false)
			else
				doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
			end
		else
			if(hole.itemid > 0) then
				doTeleportThing(hole.uid, {x = toPosition.x, y = toPosition.y + 1, z = toPosition.z}, false)
			else
				doPlayerSendDefaultCancel(cid, RETURNVALUE_NOTPOSSIBLE)
			end
		end

		return true
	end

	return false
end

TOOLS.PICK = function(cid, item, fromPosition, itemEx, toPosition)
	errors(false)
	local ground = getThingFromPos({x = toPosition.x, y = toPosition.y, z = toPosition.z + 1, stackpos = STACKPOS_GROUND})
	errors(true)
	if(itemEx.actionid == 100 and isInArray({354, 355}, itemEx.itemid)) then
		doTransformItem(itemEx.uid, 392)
		doDecayItem(itemEx.uid)

		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end

	if(itemEx.itemid == 7200) then
		doTransformItem(itemEx.uid, 7236)
		doSendMagicEffect(toPosition, CONST_ME_BLOCKHIT)
		return true
	end

	return false
end

TOOLS.MACHETE = function(cid, item, fromPosition, itemEx, toPosition, destroy)
	if(isInArray(JUNGLE_GRASS, itemEx.itemid)) then
		doTransformItem(itemEx.uid, itemEx.itemid - 1)
		doDecayItem(itemEx.uid)
		return true
	end

	if(isInArray(SPIDER_WEB, itemEx.itemid)) then
		if math.random(3) == 1 then
			doTransformItem(itemEx.uid, (itemEx.itemid + 6))
			doDecayItem(itemEx.uid)
		end
		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end
	
	if(isInArray(BAMBOO_FENCE, itemEx.itemid)) then
		if math.random(3) == 1 then
			if(itemEx.itemid == BAMBOO_FENCE[1]) then
				doTransformItem(itemEx.uid, (itemEx.itemid + 161))
			elseif(itemEx.itemid == BAMBOO_FENCE[2]) then
				doTransformItem(itemEx.uid, (itemEx.itemid + 159))
			end
			doDecayItem(itemEx.uid)
		end
		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end

	if(isInArray(WILD_GROWTH, itemEx.itemid)) then
		doSendMagicEffect(toPosition, CONST_ME_POFF)
		doRemoveItem(itemEx.uid)
		return true
	end

	return destroy and destroyItem(cid, itemEx, toPosition) or false
end

TOOLS.SHOVEL = function(cid, item, fromPosition, itemEx, toPosition)
	if(isInArray(HOLES, itemEx.itemid)) then
		if(itemEx.itemid ~= 8579) then
			itemEx.itemid = itemEx.itemid + 1
		else
			itemEx.itemid = 8585
		end

		doTransformItem(itemEx.uid, itemEx.itemid)
		doDecayItem(itemEx.uid)
		return true
	elseif(SAND_HOLES[itemEx.itemid] ~= nil) then
		doSendMagicEffect(toPosition, CONST_ME_POFF)
		doTransformItem(itemEx.uid, SAND_HOLES[itemEx.itemid])

		doDecayItem(itemEx.uid)
		return true
	elseif(isInArray(SAND,itemEx.itemid) and not isRookie(cid)) then
		local rand = math.random(1, 100)
		if(rand >= 1 and rand <= 5) then
			doCreateItem(ITEM_SCARAB_COIN, 1, toPosition)
		elseif(rand > 85) then
			doCreateMonster("Scarab", toPosition, false)
		end

		doSendMagicEffect(toPosition, CONST_ME_POFF)
		return true
	end

	return false
end

TOOLS.SCYTHE = function(cid, item, fromPosition, itemEx, toPosition, destroy)
	if(itemEx.itemid == 2739) then
		doTransformItem(itemEx.uid, 2737)
		doCreateItem(2694, 1, toPosition)

		doDecayItem(itemEx.uid)
		return true
	end

	return destroy and destroyItem(cid, itemEx, toPosition) or false
end

TOOLS.KNIFE = function(cid, item, fromPosition, itemEx, toPosition)
	if(itemEx.itemid ~= PUMPKIN) then
		return false
	end

	doTransformItem(itemEx.uid, PUMPKIN_HEAD)
	return true
end



Has alot of extra items to destroy, such as monkey statues and etc because on my server I have construction kits usable on normal ground so people can use them as mini traps, and having them as destroy-able (and the disintegrate rune) is the only way to make it fair.

Wanted to post this so people didn't think I am just begging for people to work for me, I just know this can be done better
 
Back
Top