Tip on Lua controlled Tube (use for sorting)

Ruggila
New member
 
Posts: 4
Joined: Fri Aug 31, 2018 09:29
In-game: Ruggila

Tip on Lua controlled Tube (use for sorting)

by Ruggila » Sat Sep 01, 2018 14:51

When playing minetest, I like to have an automatic sorter:

    * I put all my mined thing into a chest
    * a stackwise Filter-Injector pulls them out, powered by a blinky plant
    * then things go into a sorter network
    * exits are of course grinder, furnace, centrifuge, battery box (to recharge), workshop
    * and of course lots of chests

I've seen similar setups by other players. However, most of the other players just used the "Sorting Pneumatic Tube Segment". I use them, too. But I also use "Lua controlled Tube". And here is how:

The tubes are event driven, so I need to react to events. Here is an example of my first Lua controlled tube after my incoming chest:

Code: Select all
if event.type == "item" then
   local s = event.item.name

   -- grinder
   if s == "default:copper_lump" or
      s == "default:gold_lump" or
      s == "default:iron_lump" or
      s == "forge:slag" or
      s == "moreores:mithril_lump" or
      s == "moreores:silver_lump" or
      s == "moreores:tin_lump" or
      s == "technic:chromium_lump" or
      s == "technic:uranium_lump" or
      s == "technic:zinc_lump" or
      s == "technic_aluminum:alumina_lump" then
       return "green"
   end

   -- furnace
   if s == "forge:slag" or
      s == "mobs:rotten_flesh" or
      s == "technic:chromium_dust" or
      s == "technic:copper_dust" or
      s == "technic:gold_dust" or
      s == "technic:mithril_dust" or
      s == "technic:silver_dust" or
      s == "technic:tin_dust" or
      s == "technic:wrought_iron_dust" or
      s == "technic:zinc_dust" or
      s == "technic_aluminum:aluminum_dust" or
      s == "technic_aluminum:bauxite_lump" then
       return "black"
   end

   -- small centrifuge
   if s == "technic_aluminum:alumina_dust" then
       return "yellow"
   end

   return "red"
end


The Lua controlled tubes have colored connections, and you simply return the color of where you want the specific item to end up.

The second Lua controlled tube is done like this:

Code: Select all
if event.type == "item" then
   local s = event.item.name

   -- workshop
   if s == "bones:bone_scythe" or
      s == "cottages:hammer" or
      s == "default:axe_diamond" or
      s == "default:axe_mese" or
      s == "default:pick_diamond" or
      s == "default:pick_mese" or
      s == "default:axe_diamond" or
      s == "default:axe_mese" or
      s == "default:hoe_diamond" or
      s == "default:hoe_mese" or
      s == "default:shovel_diamond" or
      s == "default:shovel_mese" or
      s == "default:sword_diamond" or     
      s == "default:sword_mese" or
      s == "technic:treetap" or
      s == "technic_aluminum:sword_aluminum" or
      s == "screwdriver:screwdriver" or
      s:sub(1,8) == "3d_armor" or
      s:sub(1,6) == "shield" or
      s:sub(1,9) == "stairpick" then
       return "black"
   end

   -- charger
   if s == "technic:chainsaw" or
      s == "technic:prospector" or
      s == "technic:sonic_screwdriver" or
      s == "teletool:teletool_technic" or
      s:sub(1,13) == "technic:laser" or
      s:sub(1,20) == "technic:mining_drill" then
      return "yellow"
   end

   -- go-box
   if s == "bridgetool:bridge_tool" or
      s == "carts:cart" or
      s == "default:torch" or
      s == "default:ladder_wood" or
      s == "farming:corn" or
      s == "landrush:landclaim" or
      s == "more_chests:wifi" or
      s == "protector:protect" or
      s == "travelnet:elevator" or
      s:sub(1,11) == "bridgetool:" then
       return "white"
   end

   --- sort1
   return "red"
end


Here you already see the use of
Code: Select all
s:sub(start,end)
idiom to test on substrings. I use this because them item name sometimes changes, e.g. the drill has several modes of operation. So I only search at the start of the string for the decision if the item should go to the battery box for recharging.

Substrings can also be used to have chests that get items from a whole mod. With normal pneumatic sorter tubes this is almost impossible, they only can select by 6 items. But to check if an item is from a mod is a single instruction in Lua:

Code: Select all
if event.type == "item" then
   local s = event.item.name

   if s:sub(1,7) == "technic" then
     return "black"
   end

   return "red"
end
 

silvery_magnus
New member
 
Posts: 1
Joined: Wed May 11, 2016 10:29
 

User avatar
DS-minetest
Member
 
Posts: 1117
Joined: Thu Jun 19, 2014 19:49
Location: I'm scared that if this is too exact, I will be unable to use my keyboard.
GitHub: DS-Minetest
In-game: DS

Re: Tip on Lua controlled Tube (use for sorting)

by DS-minetest » Sun Nov 11, 2018 09:41

Do not call me -minetest.
Call me DS or DS-minetest.
I am German, so you don't have to pm me English if you are also German.
The background is a lie.
 

Vince
Member
 
Posts: 12
Joined: Fri May 20, 2016 02:58
GitHub: vaggrippino
IRC: Vince
In-game: Vince

Re: Tip on Lua controlled Tube (use for sorting)

by Vince » Sat Jul 13, 2019 10:17

This was great to get me started. I wanted to expand upon the idea using pattern matching for what I think of as a Tree Chest, but I can't seem to get it working. I have some experience with regular expressions and I did some reading to get the syntax right. I even did some basic testing using an online repl. But I just can't get it to work. Everything goes in the chest attached to the blue output.

Here's the latest iteration of what I've been trying:
Code: Select all
-- Tree Box
if event.type == "item" then
  local itemName = event.item.name
  if (string.match(itemName, 'default:.*tree') ~= nil) or
    (string.match(itemName, 'default:.*wood') ~= nil) or
    (string.match(itemName, 'moretrees:.*planks') ~= nil) or
    (string.match(itemName, 'default:.*sapling') ~= nil) or
    (string.match(itemName, 'moretrees:.*sapling') ~= nil) or
    itemName == 'bakedclay:thistle' or
    itemName == 'bakedclay:lazarus' or
    itemName == 'bakedclay:mannagrass' or
    itemName == 'bakedclay:delphinium' or
    (string.match(itemName, '^flowers:') ~= nil)
  then
    return "blue"
  end
  return "white"
end
 

ShadMOrdre
Member
 
Posts: 544
Joined: Mon Dec 29, 2014 08:07
Location: USA
GitHub: ShadMOrdre
In-game: shadmordre

Re: Tip on Lua controlled Tube (use for sorting)

by ShadMOrdre » Sat Jul 13, 2019 18:23

Vince,

It looks like you are trying to find a substring that includes the "wildcard" charcter.

The following

Code: Select all
string.match(itemName, 'default:.*tree')


is actually looking for the substring "default:.*tree" which always returns nil, because there is no node named "default:.*tree". "default:tree", AFAIK, is the name of the default tree trunk node, so you should be able to just:

Code: Select all
string.match(itemName, 'tree')


There may be other issues, and I have not really coded for the Lua controller, but the above seemed an obvious Lua syntax issue.

Hope this helps.

Shad
MY MODS: lib_ecology lib_materials lib_clouds lib_node_shapes ---- Inspired By: Open Source Virtual World Simulator Opensimulator.
 

Vince
Member
 
Posts: 12
Joined: Fri May 20, 2016 02:58
GitHub: vaggrippino
IRC: Vince
In-game: Vince

Re: Tip on Lua controlled Tube (use for sorting)

by Vince » Sat Jul 13, 2019 20:12

ShadMOrdre wrote:Vince,

It looks like you are trying to find a substring that includes the "wildcard" charcter.

The following

Code: Select all
string.match(itemName, 'default:.*tree')


is actually looking for the substring "default:.*tree" which always returns nil, because there is no node named "default:.*tree". "default:tree", AFAIK, is the name of the default tree trunk node, so you should be able to just:

Code: Select all
string.match(itemName, 'tree')


There may be other issues, and I have not really coded for the Lua controller, but the above seemed an obvious Lua syntax issue.

Hope this helps.

Shad


Thanks Shad.

According to the documentation for string.match, the second argument isn't just a regular string. It's a pattern. This is known as a "regular expression", or regex in many programming languages. In this context, .* isn't a wildcard as it is in the DOS / Windows command line. These characters are special in a pattern. The dot represents one of any character and the asterisk means 0 or more of the preceding character.

The result should match default:tree as well as default:aspen_tree and default:pine_tree.

I think that the Lua syntax used for the in-game controllers and tubes may be a little bit different from what the documentation shows and what works in a REPL. I should have realized it when I saw s:sub(1,13) instead of string.sub(s, 1, 13). I might be able to correct my first attempt using this syntax, but I haven't tried yet because I found sort of a work-around:

Code: Select all
-- Tree Box, substrings
if event.type == 'item'
then
  local itemName = event.item.name

  if
    -- trunks
    (itemName:sub(1,7) == 'default' and itemName:sub(-4) == 'tree') or
    (itemName:sub(1,9) == 'moretrees' and itemName:sub(-5) == 'trunk') or

    -- planks
    (itemName:sub(1,7) == 'default' and itemName:sub(-4) == 'wood') or
    (itemName:sub(1,9) == 'moretrees' and itemName:sub(-6) == 'planks') or

    -- saplings
    itemName:sub(-7) == 'sapling' or

    -- flowers
    itemName == 'bakedclay:thistle' or
    itemName == 'bakedclay:lazarus' or
    itemName == 'bakedclay:mannagrass' or
    itemName == 'bakedclay:delphinium' or
    itemName:sub(1,7) == 'flowers' or

    -- grass
    itemName:sub(1,13) == 'default:grass' or
    itemName:sub(1,17) == 'default:dry_grass' or
    itemName == 'default:junglegrass' or

    -- bonemeal
    itemName:sub(1,8) == 'bonemeal' or
    itemName == 'bones:bones' or

    -- farming (includes seeds)
    itemName:sub(1,7) == 'farming' or

    -- dyes
    itemName:sub(1,3) == 'dye'
  then
    return 'blue'
  end
  return 'white'
end
 

User avatar
DS-minetest
Member
 
Posts: 1117
Joined: Thu Jun 19, 2014 19:49
Location: I'm scared that if this is too exact, I will be unable to use my keyboard.
GitHub: DS-Minetest
In-game: DS

Re: Tip on Lua controlled Tube (use for sorting)

by DS-minetest » Sat Jul 13, 2019 22:08

Do not call me -minetest.
Call me DS or DS-minetest.
I am German, so you don't have to pm me English if you are also German.
The background is a lie.
 

Vince
Member
 
Posts: 12
Joined: Fri May 20, 2016 02:58
GitHub: vaggrippino
IRC: Vince
In-game: Vince

Re: Tip on Lua controlled Tube (use for sorting)

by Vince » Sun Jul 14, 2019 00:59

I figured out pattern matching for the Lua tubes. The second argument to the match is indeed a pattern rather than a regular string. I was just using the wrong syntax.

It might be something peculiar about the Lua implementation in Minetest, but I suspect it's just that Minetest's Lua implementation doesn't include the String Manipulation standard library.

I have experience with some other programming languages, but this was my first attempt at writing anything in Lua.

I did read the code comments regarding the DoS potential for pattern matching with find, but it wasn't clear to me whether or not that extended to match. In any case, the pattern matching with match does seem to work for the server I'm playing on.

Here's the code that works with pattern matching:
Code: Select all
-- Tree Box
if event.type == "item"
then
  local itemName = event.item.name
  if
    -- trunks
    itemName:match('default:.*tree') ~= nil or
    itemName:match('moretrees:.*trunk') ~= nil or

    -- planks
    itemName:match('default:.*wood') ~= nil or
    itemName:match('moretrees:.*planks') ~= nil or

    -- saplings
    itemName:match('sapling$') ~= nil or

    -- flowers
    itemName == 'bakedclay:thistle' or
    itemName == 'bakedclay:lazarus' or
    itemName == 'bakedclay:mannagrass' or
    itemName == 'bakedclay:delphinium' or
    itemName:match('^flowers:') ~= nil or

    -- grass
    itemName:match('^default:grass') or
    itemName:match('^default:dry_grass') or
    itemName == 'default:junglegrass' or

    -- bonemeal
    itemName:match('^bonemeal') or
    itemName == 'bones:bones' or

    -- farming (includes seeds)
    itemName:match('^farming:') or

    -- dyes
    itemName:match('^dye:')
  then
    return "blue"
  end
  return "white"
end
 


Return to General Discussion



Who is online

Users browsing this forum: DS-minetest, MSN [Bot] and 4 guests