Jump to content
  • Sky
  • Blueberry
  • Slate
  • Blackcurrant
  • Watermelon
  • Strawberry
  • Orange
  • Banana
  • Apple
  • Emerald
  • Chocolate
  • Charcoal

iovoid

Members
  • Content Count

    5
  • Joined

  • Last visited

Posts posted by iovoid

  1. I once was in situation where I was close enough to getting away with using only Microcontroller, if not for their inability to interface with Adapter. EEPROM-only computer making harddrive noises is minor immersion break. Would be nice if they produced different idle sound if there's no harddrive or even entirely relied upon disk activity sounds that happen during actual disk IO.

  2. Bug I wanted to post for quite long time but was unable to:

    It appears that robots deal greatly reduced damage with held weapons and `swing()` since Minecraft's "Combat Update" introducing melee cooldown mechanic.
    Tested with `OpenComputers-MC1.8.9-1.7.0.175.jar` and `OpenComputers-MC1.9.4-1.7.0.132.jar` as only mods with respective MC version.

    Reproduction

    • Set up Minecraft 1.8.9 and Minecraft 1.9.4 instances with Forge and OpenComputers.
    • Create new creative world with default difficulty (Normal, `1.5` would be local difficulty).
    • Have Creatix wield wooden sword and count how many hits it takes to kill zombie.

    Setup:

    setup.thumb.jpg.ea2fcaeda17b1acb30125bccb6e45ebd.jpg

    In 1.8.9, it takes 5 hits:

    1.8.9.png.ce87b9848d299a4d059f9f9ed2ffe67c.png

    In 1.9.4, it takes whopping 27:

    1.9.4.png.1a8ed59f7b1501ffa37fdde3bfd57c54.png

  3. Once I wanted to automatically farm using OpenComputers. First I made robot, but 1.7.10's block update stutter made active robot annihilate framerate. Thus I opted for entity-based agent and made code to operate drone for autonomous farming.

    And now I decided to release the code for everyone to enjoy my work. Feel free to improve upon it, or use as is.

    Example setup:

    example_drone_farming_setup.png.fc8985710e0369e7956aa52c27e7cd49.png

    Inventory of active drone:

    example_drone_farming_inventory.png.e3bece7ec56bd17faa450d877b873347.png

    Drone minimum components:

    • Drone Case (Tier 1)
    • Geolyzer
    • Inventory Upgrade
    • Central Processing Unit (CPU) (Tier 1)
    • Memory (Tier 1)
    • EEPROM with code provided

    How to setup:

    Drone never changes altitude and operates on single square area that may not be permanently obstructed. You must till farm plot manually. Drones always use global axes for movement, there's no rotation to keep track of. Adjust localX and localZ variables at start of code to designate dock area, drone must always boot up at dock, on top of charger with my example setup. If drone starts beeping upon bootup, you messed up the setup, drone is unable to locate inventory (or it's full). Drone also will start beeping at dock if output is full, just collect your obscene amount of produce when that occurs. minX/minZ/maxX/maxZ similarly define corners of farm plot. On my example setup screenshot player is facing north-west (towards negative X and negative Z), dock is at (15, 15), while most remote corner of farm plot is (0, 0). no_farm table contains exceptions where no farming operation should ever occur, using same local coordinate system. keep_seeds should allow for few missing plants to be replanted (but drone won't be able to deal with trampled fields automatically due to inability to use tools), you might want higher value if plant you are working with has chance to not drop seeds. ensure_space should be set to maximum amount of item types mature plant yields on breaking (2 being value for wheat or potatoes), otherwise you will suffer minor item loss if drone overflows. If two outputs are common (wheat), either use value of 1 or add another inventory upgrade. As I understand Minecraft farming mechanics, monoculture farming would not be faster than farming two plant types at once with plants being in lines. plant() contains logic for seed slot selection, adjust if you want to farm more than two types at single plot, but beware inventory constraints of drone and multiple outputs.

    Code, goes into EEPROM of drone:

    local d = component.proxy(component.list("drone", true)())
    local g = component.proxy(component.list("geolyzer", true)())
    local c = computer
    
    d.setLightColor(0xff00ff)
    
    local no_farm = {
    [15] = { [15] = true, },
    [12] = { [3] = true, [12] = true, },
    [3] = { [3] = true, [12] = true, },
    }
    local to_collect = {
    ["minecraft:potatoes"] = true,
    ["minecraft:carrots"] = true,
    }
    local seed_slot = {
    [1] = true,
    [2] = true,
    }
    local keep_seeds = 4
    local ensure_space = 2
    local localX = 15
    local localZ = 15
    local minX = 0
    local minZ = 0
    local maxX = 15
    local maxZ = 15
    local inv_side = 1
    local inv_name = "minecraft:chest"
    
    local startX = localX
    local startZ = localZ
    
    local function sleep(sec)
      local dl = c.uptime() + sec
      repeat
        c.pullSignal(dl - computer.uptime())
      until c.uptime() >= dl
    end
    
    local function attn()
      c.beep(1500, 0.2)
      c.beep(1700, 0.2)
      c.beep(1300, 0.2)
      sleep(3)
    end
    
    local function plant()
      local slot = localX % 2 + 1
      if d.count(slot) > 1 then
        d.select(slot)
        if not d.place(0) then attn() end
      else
        attn()
      end
    end
    
    local first_free
    
    local function got_free_slots(wanted, no_heur)
      local found = 0
      for slot = first_free or 1, d.inventorySize() do
        if d.count(slot) == 0 then
          found = found + 1
          first_free = first_free or slot
        end
        if found >= wanted then
          return true
        end
      end
      if first_free and not no_heur then
        first_free = nil
        return got_free_slots(wanted, true)
      end
      return false
    end
    
    local function farm()
      local found, desc = d.detect(0)
      if not found and desc == "air" then
        plant()
      elseif found and desc == "passable" then
        local block = g.analyze(0)
        if block ~= nil and block.growth ~= nil then
          if block.growth == 1 and to_collect[block.name] then
            d.select(1)
            d.swing(0)
            plant()
          end
        else
          attn()
        end
      else
        attn()
      end
    end
    
    local function put_away_excess()
      while true do
        local found, desc = d.detect(inv_side)
        if found and desc == "solid" then
          local block = g.analyze(inv_side)
          if block ~= nil and block.name == inv_name then break end
        end
        attn()
      end
      repeat
        local done = true
        for slot = 1, d.inventorySize() do
          local amt = d.count(slot)
          if amt > 0 then
            d.select(slot)
            local to_drop = math.huge
            if seed_slot[slot] then to_drop = amt - keep_seeds end
            if to_drop > 0 and not d.drop(inv_side, to_drop) then done = false attn() break end
          end
        end
      until done
      first_free = nil
    end
    
    local function vec_len(oX, oZ)
      return math.sqrt(oX*oX + oZ*oZ)
    end
    
    local function move_to(tgtX, tgtZ, precise)
      local offX = tgtX - localX
      local offZ = tgtZ - localZ
      if offX == 0 and offZ == 0 then return end
      d.move(offX, 0, offZ)
      local moved
      local goaldist = 0.45
      local goalvel = 2
      local timemult = 1
      if precise then
        goaldist = 0.1
        goalvel = 0.1
        timemult = timemult * 2
      end
      local dl = c.uptime() + vec_len(offX, offZ) * timemult
      repeat
        moved = d.getOffset() <= goaldist and d.getVelocity() <= goalvel
        if c.uptime() >= dl then break end
      until moved
      if moved then
        localX = localX + offX
        localZ = localZ + offZ
      else
        d.move(-offX, 0, -offZ)
        attn()
      end
    end
    
    local workX = startX
    local workZ = startZ
    
    local function next_spot()
      if workX < maxX then
        workX = workX + 1
      else
        workX = minX
        if workZ < maxZ then
          workZ = workZ + 1
        else
          workZ = minZ
        end
      end
      if no_farm[workX] ~= nil and no_farm[workX][workZ] then
        next_spot()
      end
      return workX, workZ
    end
    
    local function dock(optional)
      if optional and c.energy() >= 500 and got_free_slots(ensure_space) then return end
      move_to(startX, startZ, true)
      put_away_excess()
      while c.energy() < c.maxEnergy() - 500 do sleep(3) end
    end
    
    dock(false)
    
    while true do
      dock(true)
      move_to(next_spot())
      farm()
    end

    License terms for my code:

    This is free and unencumbered software released into the public domain.
    
    Anyone is free to copy, modify, publish, use, compile, sell, or
    distribute this software, either in source code form or as a compiled
    binary, for any purpose, commercial or non-commercial, and by any
    means.
    
    In jurisdictions that recognize copyright laws, the author or authors
    of this software dedicate any and all copyright interest in the
    software to the public domain. We make this dedication for the benefit
    of the public at large and to the detriment of our heirs and
    successors. We intend this dedication to be an overt act of
    relinquishment in perpetuity of all present and future rights to this
    software under copyright law.
    
    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
    EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
    MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
    IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
    OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
    ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
    OTHER DEALINGS IN THE SOFTWARE.
    
    For more information, please refer to <https://unlicense.org/>

    Ideas for improvement:

    • More robust detection of drone actually being at new position without slowing down operation. I've been adjusting goaldist and goalvel until drone stopped failing farm(), with no strong theory for what should be ideal values;
    • Change scanlines pattern into zig-zag pattern for minor increase in farming speed;
    • Have companion robot craft away wheat and similar things into cubes and/or fix trampled field;
    • Handling of plants not exposing "growth" to geolyzer, like Immersive Engineering's hemp;
    • Handling of multi-tile plants, like said hemp;
    • Rotating between many plant types with just few being planted at given time;
    • Melon and pumpkin farming (will likely release drone for that soon, as I already got stutter-inducing robot doing this).
×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use and Privacy Policy.