minecraft-inventory 0.1.36 → 0.1.38
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/package.json +1 -1
- package/src/components/InventoryOverlay/InventoryOverlay.tsx +1 -1
- package/src/components/JEI/JEI.module.css +16 -0
- package/src/components/JEI/JEI.tsx +39 -2
- package/src/components/RecipeGuide/RecipeInventoryView.tsx +23 -0
- package/src/globals.d.ts +8 -0
package/README.md
CHANGED
|
@@ -4,7 +4,7 @@ A flexible, scalable React library for rendering Minecraft inventory GUIs. Desig
|
|
|
4
4
|
|
|
5
5
|
## Features
|
|
6
6
|
|
|
7
|
-
-
|
|
7
|
+
- ALL standard inventory types (chest, furnace, crafting table, enchanting table, brewing stand, anvil, smithing table, horse, **beacon**, and more)
|
|
8
8
|
- CSS variable–based scaling — no layout jank, no `transform: scale`
|
|
9
9
|
- `<img>`-rendered item textures with automatic `items/` → `blocks/` fallback (via PrismarineJS asset mirror by default)
|
|
10
10
|
- Tooltips that follow the cursor, matching the original Minecraft style
|
package/package.json
CHANGED
|
@@ -41,3 +41,19 @@
|
|
|
41
41
|
.pageBtnActive:hover:not(:disabled) {
|
|
42
42
|
background: #a07820;
|
|
43
43
|
}
|
|
44
|
+
|
|
45
|
+
.displayAllBtn {
|
|
46
|
+
background: #505050;
|
|
47
|
+
color: #ffffff;
|
|
48
|
+
border: 2px solid #8b8b8b;
|
|
49
|
+
cursor: pointer;
|
|
50
|
+
font-family: inherit;
|
|
51
|
+
font-weight: normal;
|
|
52
|
+
transition: background 0.1s;
|
|
53
|
+
text-align: center;
|
|
54
|
+
white-space: nowrap;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
.displayAllBtn:hover {
|
|
58
|
+
background: #606060;
|
|
59
|
+
}
|
|
@@ -81,6 +81,7 @@ export function JEI({
|
|
|
81
81
|
const { hoveredSlot } = useInventoryContext()
|
|
82
82
|
const [search, setSearch] = useState('')
|
|
83
83
|
const [page, setPage] = useState(0)
|
|
84
|
+
const [showAllItems, setShowAllItems] = useState(false)
|
|
84
85
|
const [showFavorites, setShowFavorites] = useState(false)
|
|
85
86
|
const [favorites, setFavorites] = useState<Set<string>>(loadFavorites)
|
|
86
87
|
// Map from negative slot index → JEI item (to enable F-key and R/U on hover)
|
|
@@ -187,7 +188,7 @@ export function JEI({
|
|
|
187
188
|
}, [items, showFavorites, favorites])
|
|
188
189
|
|
|
189
190
|
const filteredItems = useMemo(() => {
|
|
190
|
-
if (!search.trim()) return baseList
|
|
191
|
+
if (!search.trim()) return showAllItems ? baseList : []
|
|
191
192
|
const q = search.toLowerCase()
|
|
192
193
|
return baseList.filter(
|
|
193
194
|
(item) =>
|
|
@@ -195,7 +196,7 @@ export function JEI({
|
|
|
195
196
|
item.name.toLowerCase().includes(q) ||
|
|
196
197
|
String(item.type).includes(q),
|
|
197
198
|
)
|
|
198
|
-
}, [baseList, search])
|
|
199
|
+
}, [baseList, search, showAllItems])
|
|
199
200
|
|
|
200
201
|
const totalPages = Math.ceil(filteredItems.length / itemsPerPage)
|
|
201
202
|
const visibleItems = filteredItems.slice(page * itemsPerPage, (page + 1) * itemsPerPage)
|
|
@@ -231,6 +232,26 @@ export function JEI({
|
|
|
231
232
|
slotToItemRef.current.set(slotIndex, jeiItem)
|
|
232
233
|
})
|
|
233
234
|
|
|
235
|
+
const displayAllButton = !showAllItems ? (
|
|
236
|
+
<button
|
|
237
|
+
type="button"
|
|
238
|
+
className={styles.displayAllBtn}
|
|
239
|
+
onClick={() => {
|
|
240
|
+
setShowAllItems(true)
|
|
241
|
+
setPage(0)
|
|
242
|
+
}}
|
|
243
|
+
style={{
|
|
244
|
+
fontSize: 8 * scale,
|
|
245
|
+
padding: `${2 * scale}px ${5 * scale}px`,
|
|
246
|
+
fontFamily: "'Minecraftia', 'Minecraft', monospace",
|
|
247
|
+
}}
|
|
248
|
+
>
|
|
249
|
+
Display All {baseList.length} {baseList.length === 1 ? 'item' : 'items'}
|
|
250
|
+
</button>
|
|
251
|
+
) : null
|
|
252
|
+
|
|
253
|
+
const showDisplayAllInGrid = !showAllItems && visibleItems.length === 0
|
|
254
|
+
|
|
234
255
|
return (
|
|
235
256
|
<div
|
|
236
257
|
ref={rootRef}
|
|
@@ -324,10 +345,26 @@ export function JEI({
|
|
|
324
345
|
padding: `${padding}px`,
|
|
325
346
|
gap: 0,
|
|
326
347
|
flex: 1,
|
|
348
|
+
minHeight: 0,
|
|
327
349
|
alignContent: 'flex-start',
|
|
328
350
|
overflowY: 'hidden',
|
|
329
351
|
}}
|
|
330
352
|
>
|
|
353
|
+
{showDisplayAllInGrid && displayAllButton && (
|
|
354
|
+
<div
|
|
355
|
+
style={{
|
|
356
|
+
position: 'absolute',
|
|
357
|
+
inset: 0,
|
|
358
|
+
display: 'flex',
|
|
359
|
+
alignItems: 'center',
|
|
360
|
+
justifyContent: 'center',
|
|
361
|
+
pointerEvents: 'none',
|
|
362
|
+
padding: `${padding}px`,
|
|
363
|
+
}}
|
|
364
|
+
>
|
|
365
|
+
<span style={{ pointerEvents: 'auto' }}>{displayAllButton}</span>
|
|
366
|
+
</div>
|
|
367
|
+
)}
|
|
331
368
|
{visibleItems.map((jeiItem, i) => {
|
|
332
369
|
const itemStack: ItemStack = {
|
|
333
370
|
type: jeiItem.type,
|
|
@@ -79,6 +79,7 @@ export function RecipeInventoryView({
|
|
|
79
79
|
const frame = navStack[navStack.length - 1]
|
|
80
80
|
const guide = frame.guides[frame.guideIndex]
|
|
81
81
|
const hoveredItemRef = useRef<RecipeNavFrame['item'] | null>(null)
|
|
82
|
+
const recipeViewRootRef = useRef<HTMLDivElement>(null)
|
|
82
83
|
|
|
83
84
|
const handleHoverItem = useCallback((item: ItemStack | null) => {
|
|
84
85
|
if (!item) { hoveredItemRef.current = null; return }
|
|
@@ -143,8 +144,30 @@ export function RecipeInventoryView({
|
|
|
143
144
|
const navFontSize = Math.max(6, Math.round(6 * scale))
|
|
144
145
|
const navPx = Math.max(1, Math.round(scale))
|
|
145
146
|
|
|
147
|
+
const handleWheel = useCallback(
|
|
148
|
+
(e: WheelEvent) => {
|
|
149
|
+
if (totalGuides <= 1) return
|
|
150
|
+
e.preventDefault()
|
|
151
|
+
const idx = frame.guideIndex
|
|
152
|
+
if (e.deltaY > 0) {
|
|
153
|
+
onGuideIndexChange(Math.min(idx + 1, totalGuides - 1))
|
|
154
|
+
} else {
|
|
155
|
+
onGuideIndexChange(Math.max(idx - 1, 0))
|
|
156
|
+
}
|
|
157
|
+
},
|
|
158
|
+
[totalGuides, frame.guideIndex, onGuideIndexChange],
|
|
159
|
+
)
|
|
160
|
+
|
|
161
|
+
useEffect(() => {
|
|
162
|
+
const el = recipeViewRootRef.current
|
|
163
|
+
if (!el || totalGuides <= 1) return
|
|
164
|
+
el.addEventListener('wheel', handleWheel, { passive: false })
|
|
165
|
+
return () => el.removeEventListener('wheel', handleWheel)
|
|
166
|
+
}, [handleWheel, totalGuides])
|
|
167
|
+
|
|
146
168
|
return (
|
|
147
169
|
<div
|
|
170
|
+
ref={recipeViewRootRef}
|
|
148
171
|
className="mc-inv-recipe-view"
|
|
149
172
|
style={{ display: 'inline-flex', flexDirection: 'column', alignItems: 'stretch' }}
|
|
150
173
|
>
|
package/src/globals.d.ts
CHANGED