use of mekanism.client.gui.element.window.GuiWindow in project Mekanism by mekanism.
the class GuiWindowCreatorTab method onClick.
@Override
public void onClick(double mouseX, double mouseY) {
GuiWindow window = createWindow();
window.setTabListeners(getCloseListener(), getReAttachListener());
disableTab();
gui().addWindow(window);
}
use of mekanism.client.gui.element.window.GuiWindow in project Mekanism by mekanism.
the class GuiMekanism method isMouseOverSlot.
@Override
protected boolean isMouseOverSlot(@Nonnull Slot slot, double mouseX, double mouseY) {
if (slot instanceof IVirtualSlot) {
// Virtual slots need special handling to allow for matching them to the window they may be attached to
IVirtualSlot virtualSlot = (IVirtualSlot) slot;
int xPos = virtualSlot.getActualX();
int yPos = virtualSlot.getActualY();
if (super.isHovering(xPos, yPos, 16, 16, mouseX, mouseY)) {
GuiWindow window = getWindowHovering(mouseX, mouseY);
// If we are hovering over a window, check if the virtual slot is a child of the window
if (window == null || window.childrenContainsElement(element -> element instanceof GuiVirtualSlot && ((GuiVirtualSlot) element).isElementForSlot(virtualSlot))) {
return overNoButtons(window, mouseX, mouseY);
}
}
return false;
}
return isHovering(slot.x, slot.y, 16, 16, mouseX, mouseY);
}
use of mekanism.client.gui.element.window.GuiWindow in project Mekanism by mekanism.
the class GuiMekanism method renderLabels.
@Override
protected void renderLabels(@Nonnull MatrixStack matrix, int mouseX, int mouseY) {
matrix.translate(0, 0, 300);
RenderSystem.translatef(-leftPos, -topPos, 0);
children().stream().filter(c -> c instanceof GuiElement).forEach(c -> ((GuiElement) c).onDrawBackground(matrix, mouseX, mouseY, MekanismRenderer.getPartialTick()));
RenderSystem.translatef(leftPos, topPos, 0);
drawForegroundText(matrix, mouseX, mouseY);
int xAxis = mouseX - leftPos;
int yAxis = mouseY - topPos;
// first render general foregrounds
maxZOffset = 200;
int zOffset = 200;
for (Widget widget : this.buttons) {
if (widget instanceof GuiElement) {
matrix.pushPose();
((GuiElement) widget).onRenderForeground(matrix, mouseX, mouseY, zOffset, zOffset);
matrix.popPose();
}
}
// now render overlays in reverse-order (i.e. back to front)
zOffset = maxZOffset;
for (LRU<GuiWindow>.LRUIterator iter = getWindowsDescendingIterator(); iter.hasNext(); ) {
GuiWindow overlay = iter.next();
zOffset += 150;
matrix.pushPose();
overlay.onRenderForeground(matrix, mouseX, mouseY, zOffset, zOffset);
if (iter.hasNext()) {
// if this isn't the focused window, render a 'blur' effect over it
overlay.renderBlur(matrix);
}
matrix.popPose();
}
// then render tooltips, translating above max z offset to prevent clashing
GuiElement tooltipElement = getWindowHovering(mouseX, mouseY);
if (tooltipElement == null) {
for (int i = buttons.size() - 1; i >= 0; i--) {
Widget widget = buttons.get(i);
if (widget instanceof GuiElement && widget.isMouseOver(mouseX, mouseY)) {
tooltipElement = (GuiElement) widget;
break;
}
}
}
// translate forwards using RenderSystem. this should never have to happen as we do all the necessary translations with MatrixStacks,
// but Minecraft has decided to not fully adopt MatrixStacks for many crucial ContainerScreen render operations. should be re-evaluated
// when mc updates related logic on their end (IMPORTANT)
RenderSystem.translatef(0, 0, maxZOffset);
if (tooltipElement != null) {
tooltipElement.renderToolTip(matrix, xAxis, yAxis);
}
// render item tooltips
RenderSystem.translatef(-leftPos, -topPos, 0);
renderTooltip(matrix, mouseX, mouseY);
RenderSystem.translatef(leftPos, topPos, 0);
// IMPORTANT: additional hacky translation so held items render okay. re-evaluate as discussed above
RenderSystem.translatef(0, 0, 200);
}
use of mekanism.client.gui.element.window.GuiWindow in project Mekanism by mekanism.
the class GuiMekanism method findSlot.
@Nullable
@Override
// Don't use directly, this is normally private in ContainerScreen
@Deprecated
protected Slot findSlot(double mouseX, double mouseY) {
// We override the implementation we have in VirtualSlotContainerScreen so that we can cache getting our window
// and have some general performance improvements given we can batch a bunch of lookups together
boolean checkedWindow = false;
boolean overNoButtons = false;
GuiWindow window = null;
for (Slot slot : menu.slots) {
boolean virtual = slot instanceof IVirtualSlot;
int xPos = slot.x;
int yPos = slot.y;
if (virtual) {
// Virtual slots need special handling to allow for matching them to the window they may be attached to
IVirtualSlot virtualSlot = (IVirtualSlot) slot;
xPos = virtualSlot.getActualX();
yPos = virtualSlot.getActualY();
}
if (super.isHovering(xPos, yPos, 16, 16, mouseX, mouseY)) {
if (!checkedWindow) {
// Only lookup the window once
checkedWindow = true;
window = getWindowHovering(mouseX, mouseY);
overNoButtons = overNoButtons(window, mouseX, mouseY);
}
if (overNoButtons && slot.isActive()) {
if (window == null) {
return slot;
} else if (virtual && window.childrenContainsElement(element -> element instanceof GuiVirtualSlot && ((GuiVirtualSlot) element).isElementForSlot((IVirtualSlot) slot))) {
return slot;
}
}
}
}
return null;
}
use of mekanism.client.gui.element.window.GuiWindow in project Mekanism by mekanism.
the class GhostIngredientHandler method getTargets.
@Override
public <INGREDIENT> List<Target<INGREDIENT>> getTargets(GUI gui, INGREDIENT ingredient, boolean doStart) {
boolean hasTargets = false;
int depth = 0;
Int2ObjectLinkedOpenHashMap<List<TargetInfo<INGREDIENT>>> depthBasedTargets = new Int2ObjectLinkedOpenHashMap<>();
Int2ObjectMap<List<Rectangle2d>> layerIntersections = new Int2ObjectOpenHashMap<>();
List<TargetInfo<INGREDIENT>> ghostTargets = getTargets(gui.children(), ingredient);
if (!ghostTargets.isEmpty()) {
// If we found any targets increment the layer count and add them to our depth based target list
depthBasedTargets.put(depth, ghostTargets);
hasTargets = true;
}
// Now gather the targets for the windows in reverse-order (i.e. back to front)
for (LRU<GuiWindow>.LRUIterator iter = gui.getWindowsDescendingIterator(); iter.hasNext(); ) {
GuiWindow window = iter.next();
depth++;
if (hasTargets) {
// If we have at least one layer with targets grab the intersection information for this window's layer
List<Rectangle2d> areas = new ArrayList<>();
areas.add(new Rectangle2d(window.x, window.y, window.getWidth(), window.getHeight()));
areas.addAll(GuiElementHandler.getAreasFor(window.x, window.y, window.getWidth(), window.getHeight(), window.children()));
layerIntersections.put(depth, areas);
}
ghostTargets = getTargets(window.children(), ingredient);
if (!ghostTargets.isEmpty()) {
// If we found any targets increment the layer count and add them to our depth based target list
depthBasedTargets.put(depth, ghostTargets);
hasTargets = true;
}
}
if (!hasTargets) {
// If we don't have any layers with elements in them just return
return Collections.emptyList();
}
List<Target<INGREDIENT>> targets = new ArrayList<>();
List<Rectangle2d> coveredArea = new ArrayList<>();
// Note: we iterate the target info in reverse so that we are able to more easily build up a list of the area that is covered
// in front of the level of targets we are currently adding to
FastSortedEntrySet<List<TargetInfo<INGREDIENT>>> depthEntries = depthBasedTargets.int2ObjectEntrySet();
for (ObjectBidirectionalIterator<Entry<List<TargetInfo<INGREDIENT>>>> iter = depthEntries.fastIterator(depthEntries.last()); iter.hasPrevious(); ) {
Entry<List<TargetInfo<INGREDIENT>>> entry = iter.previous();
int targetDepth = entry.getIntKey();
for (; depth > targetDepth; depth--) {
// If we are at a lower depth than the max depth we have things for add all the ones of higher depth
coveredArea.addAll(layerIntersections.get(depth));
}
for (TargetInfo<INGREDIENT> ghostTarget : entry.getValue()) {
targets.addAll(ghostTarget.convertToTargets(coveredArea));
}
}
return targets;
}
Aggregations