From 7fc04b4e4a855c89f6d79f0818c1af827d5b7b00 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Florian=20N=C3=BCcke?= Date: Fri, 10 Jan 2014 17:26:39 +0100 Subject: [PATCH] slots in computer cases are now tiered, closing #72. --- .../textures/items/icon_tier0.png | Bin 0 -> 157 bytes .../textures/items/icon_tier1.png | Bin 0 -> 156 bytes .../textures/items/icon_tier2.png | Bin 0 -> 157 bytes li/cil/oc/api/driver/Item.java | 16 ++++++- li/cil/oc/api/package-info.java | 2 +- .../oc/client/gui/DynamicGuiContainer.scala | 10 +++++ li/cil/oc/client/gui/Icons.scala | 8 ++++ li/cil/oc/client/gui/Robot.scala | 10 +++++ li/cil/oc/common/container/Case.scala | 6 +-- .../oc/common/container/ComponentSlot.scala | 4 +- li/cil/oc/common/container/Player.scala | 4 +- li/cil/oc/common/container/Robot.scala | 2 +- li/cil/oc/common/tileentity/Case.scala | 40 ++++++++++++++---- li/cil/oc/common/tileentity/Robot.scala | 2 +- li/cil/oc/server/driver/item/FileSystem.scala | 6 +++ .../oc/server/driver/item/GraphicsCard.scala | 6 +++ li/cil/oc/server/driver/item/Item.scala | 11 +++-- li/cil/oc/server/driver/item/Memory.scala | 13 ++++-- .../driver/item/WirelessNetworkCard.scala | 2 + 19 files changed, 116 insertions(+), 26 deletions(-) create mode 100644 assets/opencomputers/textures/items/icon_tier0.png create mode 100644 assets/opencomputers/textures/items/icon_tier1.png create mode 100644 assets/opencomputers/textures/items/icon_tier2.png diff --git a/assets/opencomputers/textures/items/icon_tier0.png b/assets/opencomputers/textures/items/icon_tier0.png new file mode 100644 index 0000000000000000000000000000000000000000..7fd7ebce68877213b3795dad983f7d376b4bfc56 GIT binary patch literal 157 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbL!WQl7;NpOBzNqJ&XDuZK6ep0G} zXKrG8YEWuoN@d~6R2!fowg8_HS95do|Ns9Viso?xiZGP~`33)Hc)H!d3&@lAba4!+ yxRsRP!p!6B)X><-=*!Biypm}~8Uv$410zGb7Q+tUj5PLg0jgy1boFyt=akR{0CPtu!~g&Q literal 0 HcmV?d00001 diff --git a/assets/opencomputers/textures/items/icon_tier2.png b/assets/opencomputers/textures/items/icon_tier2.png new file mode 100644 index 0000000000000000000000000000000000000000..2a45d446f12ed11638fcf65765e979654c22f7f8 GIT binary patch literal 157 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbL!WQl7;NpOBzNqJ&XDuZK6ep0G} zXKrG8YEWuoN@d~6R2!fowg8_HS95do|Ns9Viso?xiZGP~`33)Hc)H!d3&@lAba4!+ zxRsRP!pzeg*TBd$A;h3TQIly#nggRl10zEV2g9r1f8Q_yl`?p``njxgN@xNA&1@@L literal 0 HcmV?d00001 diff --git a/li/cil/oc/api/driver/Item.java b/li/cil/oc/api/driver/Item.java index 937610e14..5f64998e5 100644 --- a/li/cil/oc/api/driver/Item.java +++ b/li/cil/oc/api/driver/Item.java @@ -74,6 +74,20 @@ public interface Item { */ Slot slot(ItemStack stack); + /** + * The tier of the specified item this driver supports. + *

+ * This is used to determine into which slot of a computer the components + * this driver supports may go. This will only be called if a previous call + * to {@link #worksWith} with the same stack returned true. + *

+ * Important: tiers are zero-indexed. + * + * @param stack the item stack to get the tier for. + * @return the tier of the specified item. + */ + int tier(ItemStack stack); + /** * Get the tag compound based on the item stack to use for persisting the * environment associated with the specified item stack. @@ -91,7 +105,7 @@ public interface Item { * * @param stack the item to get the child tag from. * @return the tag to use for saving and loading, or null to use - * the default tag oc:data. + * the default tag oc:data. */ NBTTagCompound dataTag(ItemStack stack); } \ No newline at end of file diff --git a/li/cil/oc/api/package-info.java b/li/cil/oc/api/package-info.java index f89f581fd..80f4792b8 100644 --- a/li/cil/oc/api/package-info.java +++ b/li/cil/oc/api/package-info.java @@ -37,5 +37,5 @@ @cpw.mods.fml.common.API( owner = "OpenComputers", provides = "OpenComputersAPI", - apiVersion = "1.1.0") + apiVersion = "1.2.0") package li.cil.oc.api; \ No newline at end of file diff --git a/li/cil/oc/client/gui/DynamicGuiContainer.scala b/li/cil/oc/client/gui/DynamicGuiContainer.scala index e229661ea..8088688d6 100644 --- a/li/cil/oc/client/gui/DynamicGuiContainer.scala +++ b/li/cil/oc/client/gui/DynamicGuiContainer.scala @@ -1,9 +1,11 @@ package li.cil.oc.client.gui import li.cil.oc.Settings +import li.cil.oc.common.container.ComponentSlot import li.cil.oc.util.RenderState import net.minecraft.client.gui.inventory.GuiContainer import net.minecraft.client.renderer.Tessellator +import net.minecraft.client.renderer.texture.TextureMap import net.minecraft.inventory.{Container, Slot} import net.minecraft.util.{StatCollector, ResourceLocation} import org.lwjgl.opengl.GL11 @@ -30,8 +32,16 @@ abstract class DynamicGuiContainer(container: Container) extends GuiContainer(co GL11.glEnable(GL11.GL_LIGHTING) } RenderState.makeItBlend() + GL11.glDepthMask(false) super.drawSlotInventory(slot) + GL11.glDepthMask(true) GL11.glDisable(GL11.GL_BLEND) + if (!slot.getHasStack) slot match { + case component: ComponentSlot if component.tierIcon != null => + mc.getTextureManager.bindTexture(TextureMap.locationItemsTexture) + drawTexturedModelRectFromIcon(slot.xDisplayPosition, slot.yDisplayPosition, component.tierIcon, 16, 16) + case _ => + } } private def drawSlotBackground(x: Int, y: Int) { diff --git a/li/cil/oc/client/gui/Icons.scala b/li/cil/oc/client/gui/Icons.scala index 963752dc9..3bbb49c42 100644 --- a/li/cil/oc/client/gui/Icons.scala +++ b/li/cil/oc/client/gui/Icons.scala @@ -10,6 +10,8 @@ import scala.collection.mutable object Icons { private val bySlotType = mutable.Map.empty[Slot, Icon] + private val byTier = mutable.Map.empty[Int, Icon] + @ForgeSubscribe def onItemIconRegister(e: TextureStitchEvent.Pre) { val iconRegister = e.map @@ -20,8 +22,14 @@ object Icons { bySlotType += Slot.Memory -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_ram") bySlotType += Slot.Tool -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_tool") bySlotType += Slot.Upgrade -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_upgrade") + + byTier += 0 -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_tier0") + byTier += 1 -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_tier1") + byTier += 2 -> iconRegister.registerIcon(Settings.resourceDomain + ":icon_tier2") } } def get(slotType: Slot) = bySlotType.get(slotType).orNull + + def get(tier: Int) = byTier.get(tier).orNull } diff --git a/li/cil/oc/client/gui/Robot.scala b/li/cil/oc/client/gui/Robot.scala index 9cc80e0b2..0e26e78f6 100644 --- a/li/cil/oc/client/gui/Robot.scala +++ b/li/cil/oc/client/gui/Robot.scala @@ -17,6 +17,8 @@ import net.minecraft.inventory.Slot import net.minecraft.util.{StatCollector, ResourceLocation} import org.lwjgl.input.Keyboard import org.lwjgl.opengl.GL11 +import li.cil.oc.common.container.ComponentSlot +import net.minecraft.client.renderer.texture.TextureMap class Robot(playerInventory: InventoryPlayer, val robot: tileentity.Robot) extends GuiContainer(new container.Robot(playerInventory, robot)) with Buffer { xSize = 256 @@ -68,8 +70,16 @@ class Robot(playerInventory: InventoryPlayer, val robot: tileentity.Robot) exten override def drawSlotInventory(slot: Slot) { RenderState.makeItBlend() + GL11.glDepthMask(false) super.drawSlotInventory(slot) + GL11.glDepthMask(true) GL11.glDisable(GL11.GL_BLEND) + if (!slot.getHasStack) slot match { + case component: ComponentSlot if component.tierIcon != null => + mc.getTextureManager.bindTexture(TextureMap.locationItemsTexture) + drawTexturedModelRectFromIcon(slot.xDisplayPosition, slot.yDisplayPosition, component.tierIcon, 16, 16) + case _ => + } } def drawBuffer() { diff --git a/li/cil/oc/common/container/Case.scala b/li/cil/oc/common/container/Case.scala index 31c23ee94..8daa01944 100644 --- a/li/cil/oc/common/container/Case.scala +++ b/li/cil/oc/common/container/Case.scala @@ -6,15 +6,15 @@ import net.minecraft.entity.player.{EntityPlayer, InventoryPlayer} class Case(playerInventory: InventoryPlayer, computer: tileentity.Case) extends Player(playerInventory, computer) { for (i <- 0 to (if (computer.tier == 2) 2 else 1)) { - addSlotToContainer(98, 16 + i * slotSize, api.driver.Slot.Card) + addSlotToContainer(98, 16 + i * slotSize, api.driver.Slot.Card, computer.maxComponentTierForSlot(getInventory.size)) } for (i <- 0 to (if (computer.tier == 0) 0 else 1)) { - addSlotToContainer(120, 16 + i * slotSize, api.driver.Slot.Memory) + addSlotToContainer(120, 16 + i * slotSize, api.driver.Slot.Memory, computer.maxComponentTierForSlot(getInventory.size)) } for (i <- 0 to (if (computer.tier == 0) 0 else 1)) { - addSlotToContainer(142, 16 + i * slotSize, api.driver.Slot.HardDiskDrive) + addSlotToContainer(142, 16 + i * slotSize, api.driver.Slot.HardDiskDrive, computer.maxComponentTierForSlot(getInventory.size)) } if (computer.tier == 2) { diff --git a/li/cil/oc/common/container/ComponentSlot.scala b/li/cil/oc/common/container/ComponentSlot.scala index 514d52f97..88144be72 100644 --- a/li/cil/oc/common/container/ComponentSlot.scala +++ b/li/cil/oc/common/container/ComponentSlot.scala @@ -5,9 +5,11 @@ import li.cil.oc.client.gui.Icons import net.minecraft.inventory.{IInventory, Slot} import net.minecraft.item.ItemStack -class ComponentSlot(inventory: IInventory, index: Int, x: Int, y: Int, val slot: api.driver.Slot = api.driver.Slot.None) extends Slot(inventory, index, x, y) { +class ComponentSlot(inventory: IInventory, index: Int, x: Int, y: Int, val slot: api.driver.Slot = api.driver.Slot.None, val tier: Int = -1) extends Slot(inventory, index, x, y) { setBackgroundIcon(Icons.get(slot)) + val tierIcon = Icons.get(tier) + override def getSlotStackLimit = slot match { case api.driver.Slot.Tool | api.driver.Slot.None => super.getSlotStackLimit diff --git a/li/cil/oc/common/container/Player.scala b/li/cil/oc/common/container/Player.scala index ce6fb3dff..2c2c04061 100644 --- a/li/cil/oc/common/container/Player.scala +++ b/li/cil/oc/common/container/Player.scala @@ -97,9 +97,9 @@ abstract class Player(protected val playerInventory: InventoryPlayer, val otherI } } - def addSlotToContainer(x: Int, y: Int, slot: api.driver.Slot = api.driver.Slot.None) { + def addSlotToContainer(x: Int, y: Int, slot: api.driver.Slot = api.driver.Slot.None, tier: Int = -1) { val index = getInventory.size - addSlotToContainer(new ComponentSlot(otherInventory, index, x, y, slot)) + addSlotToContainer(new ComponentSlot(otherInventory, index, x, y, slot, tier)) } /** Render player inventory at the specified coordinates. */ diff --git a/li/cil/oc/common/container/Robot.scala b/li/cil/oc/common/container/Robot.scala index 07cdf4bdd..a7a056d64 100644 --- a/li/cil/oc/common/container/Robot.scala +++ b/li/cil/oc/common/container/Robot.scala @@ -7,7 +7,7 @@ import net.minecraft.entity.player.{EntityPlayer, InventoryPlayer} class Robot(playerInventory: InventoryPlayer, robot: tileentity.Robot) extends Player(playerInventory, robot) { addSlotToContainer(178 + 0 * slotSize, 218, api.driver.Slot.Tool) - addSlotToContainer(178 + 1 * slotSize, 218, api.driver.Slot.Card) + addSlotToContainer(178 + 1 * slotSize, 218, api.driver.Slot.Card, 1) addSlotToContainer(178 + 2 * slotSize, 218, api.driver.Slot.Disk) addSlotToContainer(178 + 3 * slotSize, 218, api.driver.Slot.Upgrade) diff --git a/li/cil/oc/common/tileentity/Case.scala b/li/cil/oc/common/tileentity/Case.scala index 3f447cfa0..97821bfeb 100644 --- a/li/cil/oc/common/tileentity/Case.scala +++ b/li/cil/oc/common/tileentity/Case.scala @@ -43,26 +43,48 @@ class Case(var tier: Int, isRemote: Boolean) extends Computer(isRemote) { def isItemValidForSlot(slot: Int, stack: ItemStack) = tier match { case 0 => (slot, Registry.itemDriverFor(stack)) match { case (_, None) => false // Invalid item. - case (0 | 1, Some(driver)) => driver.slot(stack) == Slot.Card - case (2, Some(driver)) => driver.slot(stack) == Slot.Memory - case (3, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive + case (0 | 1, Some(driver)) => driver.slot(stack) == Slot.Card && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (2, Some(driver)) => driver.slot(stack) == Slot.Memory && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (3, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive && driver.tier(stack) <= maxComponentTierForSlot(slot) case _ => false // Invalid slot. } case 1 => (slot, Registry.itemDriverFor(stack)) match { case (_, None) => false // Invalid item. - case (0 | 1, Some(driver)) => driver.slot(stack) == Slot.Card - case (2 | 3, Some(driver)) => driver.slot(stack) == Slot.Memory - case (4 | 5, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive + case (0 | 1, Some(driver)) => driver.slot(stack) == Slot.Card && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (2 | 3, Some(driver)) => driver.slot(stack) == Slot.Memory && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (4 | 5, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive && driver.tier(stack) <= maxComponentTierForSlot(slot) case _ => false // Invalid slot. } case 2 => (slot, Registry.itemDriverFor(stack)) match { case (_, None) => false // Invalid item. - case (0 | 1 | 2, Some(driver)) => driver.slot(stack) == Slot.Card - case (3 | 4, Some(driver)) => driver.slot(stack) == Slot.Memory - case (5 | 6, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive + case (0 | 1 | 2, Some(driver)) => driver.slot(stack) == Slot.Card && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (3 | 4, Some(driver)) => driver.slot(stack) == Slot.Memory && driver.tier(stack) <= maxComponentTierForSlot(slot) + case (5 | 6, Some(driver)) => driver.slot(stack) == Slot.HardDiskDrive && driver.tier(stack) <= maxComponentTierForSlot(slot) case (7, Some(driver)) => driver.slot(stack) == Slot.Disk case _ => false // Invalid slot. } case _ => false } + + def maxComponentTierForSlot(slot: Int) = tier match { + case 0 => 0 + case 1 => slot match { + case 0 => 1 + case 1 => 0 + case (2 | 3) => 1 + case 4 => 1 + case 5 => 0 + case _ => -1 // Invalid slot. + } + case 2 => slot match { + case 0 => 2 + case 1 | 2 => 1 + case (3 | 4) => 2 + case 5 => 2 + case 6 => 1 + case 7 => 0 + case _ => -1 // Invalid slot. + } + case _ => -1 + } } \ No newline at end of file diff --git a/li/cil/oc/common/tileentity/Robot.scala b/li/cil/oc/common/tileentity/Robot.scala index 6edd01ebe..8bbaff7c1 100644 --- a/li/cil/oc/common/tileentity/Robot.scala +++ b/li/cil/oc/common/tileentity/Robot.scala @@ -518,7 +518,7 @@ class Robot(isRemote: Boolean) extends Computer(isRemote) with ISidedInventory w def isItemValidForSlot(slot: Int, stack: ItemStack) = (slot, Registry.itemDriverFor(stack)) match { case (0, _) => true // Allow anything in the tool slot. - case (1, Some(driver)) => driver.slot(stack) == Slot.Card + case (1, Some(driver)) => driver.slot(stack) == Slot.Card && driver.tier(stack) < 2 case (2, Some(driver)) => driver.slot(stack) == Slot.Disk case (3, Some(driver)) => driver.slot(stack) == Slot.Upgrade case (i, _) if actualSlot(0) until getSizeInventory contains i => true // Normal inventory. diff --git a/li/cil/oc/server/driver/item/FileSystem.scala b/li/cil/oc/server/driver/item/FileSystem.scala index 032f090a2..4d8e97954 100644 --- a/li/cil/oc/server/driver/item/FileSystem.scala +++ b/li/cil/oc/server/driver/item/FileSystem.scala @@ -43,6 +43,12 @@ object FileSystem extends Item { case _ => throw new IllegalArgumentException() } + override def tier(stack: ItemStack) = + Items.multi.subItem(stack) match { + case Some(hdd: HardDiskDrive) => hdd.tier + case _ => 0 + } + private def createEnvironment(stack: ItemStack, capacity: Int) = { // We have a bit of a chicken-egg problem here, because we want to use the // node's address as the folder name... so we generate the address here, diff --git a/li/cil/oc/server/driver/item/GraphicsCard.scala b/li/cil/oc/server/driver/item/GraphicsCard.scala index 909f65936..1700e8e4d 100644 --- a/li/cil/oc/server/driver/item/GraphicsCard.scala +++ b/li/cil/oc/server/driver/item/GraphicsCard.scala @@ -22,4 +22,10 @@ object GraphicsCard extends Item { } override def slot(stack: ItemStack) = Slot.Card + + override def tier(stack: ItemStack) = + Items.multi.subItem(stack) match { + case Some(gpu: common.item.GraphicsCard) => gpu.tier + case _ => 0 + } } \ No newline at end of file diff --git a/li/cil/oc/server/driver/item/Item.scala b/li/cil/oc/server/driver/item/Item.scala index 705672a3d..fc08ab79d 100644 --- a/li/cil/oc/server/driver/item/Item.scala +++ b/li/cil/oc/server/driver/item/Item.scala @@ -1,18 +1,21 @@ package li.cil.oc.server.driver.item +import li.cil.oc.api.driver import li.cil.oc.common -import li.cil.oc.{Settings, Items, api} +import li.cil.oc.{Settings, Items} import net.minecraft.item.ItemStack import net.minecraft.nbt.NBTTagCompound -trait Item extends api.driver.Item { +trait Item extends driver.Item { + def tier(stack: ItemStack) = 0 + def dataTag(stack: ItemStack) = Item.dataTag(stack) protected def isOneOf(stack: ItemStack, items: common.item.Delegate*) = - stack.getItem == Items.multi && (Items.multi.subItem(stack) match { + Items.multi.subItem(stack) match { case None => false case Some(subItem) => items.contains(subItem) - }) + } } object Item { diff --git a/li/cil/oc/server/driver/item/Memory.scala b/li/cil/oc/server/driver/item/Memory.scala index 8a8fd2d09..3dc15558f 100644 --- a/li/cil/oc/server/driver/item/Memory.scala +++ b/li/cil/oc/server/driver/item/Memory.scala @@ -3,18 +3,25 @@ package li.cil.oc.server.driver.item import li.cil.oc.Items import li.cil.oc.api.driver import li.cil.oc.api.driver.Slot +import li.cil.oc.common.item import net.minecraft.item.ItemStack import net.minecraft.tileentity.{TileEntity => MCTileEntity} object Memory extends Item with driver.Memory { - def amount(stack: ItemStack) = if (stack.getItem == Items.multi) Items.multi.subItem(stack) match { - case Some(memory: li.cil.oc.common.item.Memory) => memory.kiloBytes * 1024 + def amount(stack: ItemStack) = Items.multi.subItem(stack) match { + case Some(memory: item.Memory) => memory.kiloBytes * 1024 case _ => 0 - } else 0 + } def worksWith(stack: ItemStack) = isOneOf(stack, Items.ram3, Items.ram1, Items.ram2) def createEnvironment(stack: ItemStack, container: MCTileEntity) = null def slot(stack: ItemStack) = Slot.Memory + + override def tier(stack: ItemStack) = + Items.multi.subItem(stack) match { + case Some(memory: item.Memory) => memory.tier + case _ => 0 + } } diff --git a/li/cil/oc/server/driver/item/WirelessNetworkCard.scala b/li/cil/oc/server/driver/item/WirelessNetworkCard.scala index 0515cd20b..e8bd7af10 100644 --- a/li/cil/oc/server/driver/item/WirelessNetworkCard.scala +++ b/li/cil/oc/server/driver/item/WirelessNetworkCard.scala @@ -13,4 +13,6 @@ object WirelessNetworkCard extends Item { if (container != null) new component.WirelessNetworkCard(container) else null def slot(stack: ItemStack) = Slot.Card + + override def tier(stack: ItemStack) = 1 }