Invisible item frames for Paper 26.2. Shift + right-click a placed item frame with shears to hide the frame while keeping its item visible.
Download on Hangar · Changelog · MIT licensed
- Shift + right-click with shears in the main hand hides the frame. Repeat the gesture to turn it back into a regular frame. Works with regular and glow item frames and consumes shears durability.
- A hidden frame with an item is invisible; only the item shows. An empty hidden frame stays visible so it can be found and broken; it hides again as soon as an item is placed inside.
- Right-clicking a hidden frame does not rotate the item. Rotate with Shift + right-click.
- When a hidden frame hangs on a chest, barrel, shulker box, furnace or another container,
right-click opens the container. A
PlayerInteractEventis fired first, so region protection and lock plugins keep working. - Frames made invisible by another plugin or by commands are adopted on chunk load or first interaction and follow the same rules from then on.
- A broken frame drops as a regular item frame: the flag lives on the entity only.
- Folia-compatible, no global scheduler.
/unseenframes (alias /uf), permission unseenframes.admin:
| Command | Action |
|---|---|
/uf reload |
Re-read config.yml and resync loaded frames |
/uf scan [radius] |
Highlight hidden frames with particles for a few seconds |
/uf toggle |
Toggle the frame you are looking at, no shears or sneaking needed |
| Permission | Default | Description |
|---|---|---|
unseenframes.use |
everyone | Hide and reveal frames with shears |
unseenframes.admin |
operators | /unseenframes command |
Without unseenframes.use a click with shears behaves like vanilla.
| Key | Default | Meaning |
|---|---|---|
tool |
minecraft:shears |
Item used to toggle frames |
require-sneak |
true |
Require Shift |
tool-damage |
1 |
Durability per toggle, 0 = never damage the tool |
reveal-when-empty |
true |
Empty hidden frames become visible again |
lock-rotation |
true |
Rotate only with Shift + right-click |
container-passthrough.enabled |
true |
Right-click on a hidden frame opens the container behind it |
container-passthrough.check-protection |
true |
Check protection via PlayerInteractEvent |
adopt-invisible-frames |
true |
Adopt frames hidden by other means |
sound.key, sound.volume, sound.pitch |
minecraft:item.shears.snip |
Toggle sound, empty key = silent |
scan.* |
16 / 64 / 6 |
Default radius, maximum radius, highlight duration |
messages.* |
Messages in MiniMessage, empty string = do not show |
All player-facing messages live under messages and can be translated there.
The "hidden" flag is stored in the frame entity's PersistentDataContainer (unseenframes:hidden).
Vanilla invisibility (Invisible) is not stored separately; it is derived from the flag and the presence
of an item: after a toggle, one tick after PlayerItemFrameChangeEvent (PLACE, REMOVE) and on chunk load
(EntitiesLoadEvent). That keeps frames consistent even when another plugin changes the item through the API.
The toggle listens to PlayerInteractEntityEvent at HIGHEST priority with ignoreCancelled,
so a region denial cancels the event before the plugin acts.
Requires JDK 25.
./gradlew build
The resulting jar is build/libs/UnseenFrames-<version>.jar (bStats is relocated inside).
Dev server with Paper 26.2 in the run/ directory:
./gradlew runServer
Accept the EULA in run/eula.txt on the first start.
The release process is documented in RELEASING.md.
The plugin reports anonymous usage statistics to bStats
(service ID 33847): server and plugin versions plus four pie charts for container-passthrough,
reveal-when-empty, adopt-invisible-frames and the configured tool.
Server owners can turn this off for every plugin at once in plugins/bStats/config.yml.
MIT.
