mirror of
https://github.com/LCE-Hub/LCE-Emerald-Launcher.git
synced 2026-08-20 04:27:29 +00:00
feat: builtin capes
This commit is contained in:
parent
58aff0db3a
commit
d49622495f
BIN
public/Capes/4J.png
Normal file
BIN
public/Capes/4J.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 3.5 KiB |
BIN
public/Capes/Unused_Cape_2.png
Normal file
BIN
public/Capes/Unused_Cape_2.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 730 B |
|
|
@ -76,10 +76,15 @@ const DEFAULT_SKINS: SavedSkin[] = [
|
|||
id: "tranqlmao",
|
||||
name: "Tranq",
|
||||
url: "/Skins/tranq.png",
|
||||
isSlim: false,
|
||||
isSlim: true,
|
||||
},
|
||||
];
|
||||
|
||||
const DEFAULT_CAPES: SavedCape[] = [
|
||||
{ id: "4j", name: "4J Studios", url: "/Capes/4J.png" },
|
||||
{ id: "unused2", name: "Unused Cape 2", url: "/Capes/Unused_Cape_2.png" },
|
||||
];
|
||||
|
||||
const HeadPreview = memo(function HeadPreview({ src }: { src: string }) {
|
||||
const canvasRef = useRef<HTMLCanvasElement>(null);
|
||||
|
||||
|
|
@ -135,13 +140,17 @@ const SkinsView = memo(function SkinsView() {
|
|||
"lce-custom-capes",
|
||||
[],
|
||||
);
|
||||
const savedCapes = [
|
||||
...DEFAULT_CAPES,
|
||||
...storedCapes.filter((c) => !DEFAULT_CAPES.some((d) => d.id === c.id)),
|
||||
];
|
||||
const [activeCapeId, setActiveCapeId] = useState<string | null>(null);
|
||||
|
||||
const TOP_BUTTONS_COUNT = viewMode === "skin" ? 3 : 3;
|
||||
const SKINS_START_INDEX = TOP_BUTTONS_COUNT;
|
||||
const BACK_BUTTON_INDEX =
|
||||
SKINS_START_INDEX +
|
||||
(viewMode === "skin" ? savedSkins.length : storedCapes.length);
|
||||
(viewMode === "skin" ? savedSkins.length : savedCapes.length);
|
||||
const ITEM_COUNT = BACK_BUTTON_INDEX + 1;
|
||||
|
||||
const setSavedSkins = (
|
||||
|
|
@ -243,10 +252,10 @@ const SkinsView = memo(function SkinsView() {
|
|||
|
||||
useEffect(() => {
|
||||
if (!activeCapeId) {
|
||||
const match = storedCapes.find((c) => c.url === capeUrl);
|
||||
const match = savedCapes.find((c) => c.url === capeUrl);
|
||||
if (match) setActiveCapeId(match.id);
|
||||
}
|
||||
}, [activeCapeId, storedCapes, capeUrl]);
|
||||
}, [activeCapeId, savedCapes, capeUrl]);
|
||||
|
||||
useEffect(() => {
|
||||
const handleKeyDown = (e: KeyboardEvent) => {
|
||||
|
|
@ -333,7 +342,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
setFocusIndex(0);
|
||||
} else if (focusIndex === BACK_BUTTON_INDEX) {
|
||||
const itemCount =
|
||||
viewMode === "cape" ? storedCapes.length + 1 : savedSkins.length;
|
||||
viewMode === "cape" ? savedCapes.length + 1 : savedSkins.length;
|
||||
setFocusIndex(SKINS_START_INDEX + itemCount - 1);
|
||||
} else if (focusIndex >= SKINS_START_INDEX) {
|
||||
const rowCount = 4;
|
||||
|
|
@ -351,7 +360,18 @@ const SkinsView = memo(function SkinsView() {
|
|||
playPressSound();
|
||||
setViewMode(viewMode === "skin" ? "cape" : "skin");
|
||||
} else if (focusIndex < BACK_BUTTON_INDEX) {
|
||||
handleSkinSelect(savedSkins[focusIndex - SKINS_START_INDEX]);
|
||||
if (viewMode === "cape") {
|
||||
const capeIdx = focusIndex - SKINS_START_INDEX;
|
||||
if (capeIdx === 0) {
|
||||
playPressSound();
|
||||
setCapeUrl(null);
|
||||
setActiveCapeId(null);
|
||||
} else {
|
||||
handleCapeSelect(savedCapes[capeIdx - 1]);
|
||||
}
|
||||
} else {
|
||||
handleSkinSelect(savedSkins[focusIndex - SKINS_START_INDEX]);
|
||||
}
|
||||
} else {
|
||||
playBackSound();
|
||||
setActiveView("main");
|
||||
|
|
@ -363,7 +383,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
}, [
|
||||
focusIndex,
|
||||
savedSkins.length,
|
||||
storedCapes.length,
|
||||
savedCapes.length,
|
||||
playBackSound,
|
||||
setActiveView,
|
||||
playPressSound,
|
||||
|
|
@ -414,6 +434,9 @@ const SkinsView = memo(function SkinsView() {
|
|||
const isDefaultSkin = (id: string | null) =>
|
||||
DEFAULT_SKINS.some((d) => d.id === id);
|
||||
|
||||
const isDefaultCape = (id: string | null) =>
|
||||
DEFAULT_CAPES.some((d) => d.id === id);
|
||||
|
||||
const handleDeleteActive = () => {
|
||||
if (!activeSkinId || isDefaultSkin(activeSkinId)) return;
|
||||
playPressSound();
|
||||
|
|
@ -457,7 +480,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
};
|
||||
|
||||
const handleDeleteActiveCape = () => {
|
||||
if (!activeCapeId) return;
|
||||
if (!activeCapeId || isDefaultCape(activeCapeId)) return;
|
||||
playPressSound();
|
||||
const updatedCapes = storedCapes.filter((c) => c.id !== activeCapeId);
|
||||
setStoredCapes(updatedCapes);
|
||||
|
|
@ -476,6 +499,8 @@ const SkinsView = memo(function SkinsView() {
|
|||
isDefaultSkin(activeSkinId) ||
|
||||
(!activeSkinId && skinUrl === "/images/Default.png");
|
||||
const isActiveCapeDefault = !activeCapeId && !capeUrl;
|
||||
const isCapeDeleteDisabled =
|
||||
isActiveCapeDefault || isDefaultCape(activeCapeId);
|
||||
|
||||
return (
|
||||
<motion.div
|
||||
|
|
@ -518,7 +543,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
data-index="1"
|
||||
onMouseEnter={() => {
|
||||
if (viewMode === "skin" && !isActiveDefault) setFocusIndex(1);
|
||||
else if (viewMode === "cape" && !isActiveCapeDefault)
|
||||
else if (viewMode === "cape" && !isCapeDeleteDisabled)
|
||||
setFocusIndex(1);
|
||||
}}
|
||||
onClick={() => {
|
||||
|
|
@ -528,7 +553,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
}}
|
||||
className={`w-40 h-10 flex items-center justify-center transition-colors text-2xl mc-text-shadow outline-none border-none ${
|
||||
(viewMode === "skin" && isActiveDefault) ||
|
||||
(viewMode === "cape" && isActiveCapeDefault)
|
||||
(viewMode === "cape" && isCapeDeleteDisabled)
|
||||
? "text-gray-400 opacity-80 cursor-not-allowed"
|
||||
: focusIndex === 1
|
||||
? "text-[#FFFF55]"
|
||||
|
|
@ -537,7 +562,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
style={{
|
||||
backgroundImage:
|
||||
(viewMode === "skin" && isActiveDefault) ||
|
||||
(viewMode === "cape" && isActiveCapeDefault)
|
||||
(viewMode === "cape" && isCapeDeleteDisabled)
|
||||
? "url('/images/Button_Background2.png')"
|
||||
: focusIndex === 1
|
||||
? "url('/images/button_highlighted.png')"
|
||||
|
|
@ -673,7 +698,7 @@ const SkinsView = memo(function SkinsView() {
|
|||
No Cape
|
||||
</span>
|
||||
</div>
|
||||
{storedCapes.map((cape, i) => {
|
||||
{savedCapes.map((cape, i) => {
|
||||
const idx = SKINS_START_INDEX + 1 + i;
|
||||
const isActive = activeCapeId
|
||||
? activeCapeId === cape.id
|
||||
|
|
@ -707,9 +732,10 @@ const SkinsView = memo(function SkinsView() {
|
|||
onChange={(e) =>
|
||||
handleCapeNameChange(cape.id, e.target.value)
|
||||
}
|
||||
className={`bg-transparent text-center outline-none border-none text-base mc-text-shadow w-full truncate transition-colors relative z-10 ${isActive || isFocused ? "text-[#FFFF55]" : "text-white"}`}
|
||||
className={`bg-transparent text-center outline-none border-none text-base mc-text-shadow w-full truncate transition-colors relative z-10 ${isActive || isFocused ? "text-[#FFFF55]" : "text-white"} ${isDefaultCape(cape.id) ? "pointer-events-none" : ""}`}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
spellCheck={false}
|
||||
readOnly={isDefaultCape(cape.id)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
|
|
|
|||
Loading…
Reference in a new issue