From 8bcd6fa796a5069bf21dc9ce142293d09cca5dad Mon Sep 17 00:00:00 2001 From: Violet Caulfield Date: Fri, 5 Dec 2025 13:33:19 -0600 Subject: [PATCH] add native tab bar --- bun.lock | 61 ++++++++++++- ios/Podfile.lock | 98 +++++++++++++++++++++ package.json | 3 + src/screens/Tabs/index.tsx | 165 ++++++++++++++++------------------- src/screens/Tabs/tab-bar.tsx | 5 +- 5 files changed, 236 insertions(+), 96 deletions(-) diff --git a/bun.lock b/bun.lock index 40899b94..aa39933d 100644 --- a/bun.lock +++ b/bun.lock @@ -5,11 +5,13 @@ "": { "name": "jellify", "dependencies": { + "@bottom-tabs/react-navigation": "^1.1.0", "@jellyfin/sdk": "0.13.0", "@react-native-async-storage/async-storage": "^2.2.0", "@react-native-community/cli": "20.0.0", "@react-native-community/netinfo": "^11.4.1", "@react-native-masked-view/masked-view": "^0.3.2", + "@react-native-vector-icons/get-image": "^12.3.0", "@react-native-vector-icons/material-design-icons": "12.4.0", "@react-navigation/bottom-tabs": "7.8.10", "@react-navigation/material-top-tabs": "7.4.7", @@ -34,6 +36,7 @@ "react-native-background-actions": "^4.0.1", "react-native-blob-util": "^0.22.2", "react-native-blurhash": "2.1.1", + "react-native-bottom-tabs": "^1.1.0", "react-native-carplay": "^2.4.1-beta.0", "react-native-config": "1.5.6", "react-native-device-info": "15.0.1", @@ -356,6 +359,8 @@ "@bcoe/v8-coverage": ["@bcoe/v8-coverage@0.2.3", "", {}, "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw=="], + "@bottom-tabs/react-navigation": ["@bottom-tabs/react-navigation@1.1.0", "", { "dependencies": { "color": "^5.0.0" }, "peerDependencies": { "@react-navigation/native": ">=7", "react": "*", "react-native": "*", "react-native-bottom-tabs": "*" } }, "sha512-+4YppCodABcSNIgJiq95QUQ+3ClVBG+rLG3WmYI0+/nbxqKbCz6luFBep4KFOj98Iplj1JY2Ki6ix8CcOZVQ/Q=="], + "@egjs/hammerjs": ["@egjs/hammerjs@2.0.17", "", { "dependencies": { "@types/hammerjs": "^2.0.36" } }, "sha512-XQsZgjm2EcVUiZQf11UBJQfmZeEmOW8DpI1gsFeln6w0ae0ii4dMQEQ0kjl6DspdWX1aGY1/loyXnP0JS06e/A=="], "@emnapi/core": ["@emnapi/core@1.7.1", "", { "dependencies": { "@emnapi/wasi-threads": "1.1.0", "tslib": "^2.4.0" } }, "sha512-o1uhUASyo921r2XtHYOHy7gdkGLge8ghBEQHMWmyJFoXlpU58kIrhhN3w26lpQb6dspetweapMn2CSNwQ8I4wg=="], @@ -528,6 +533,8 @@ "@react-native-vector-icons/common": ["@react-native-vector-icons/common@12.4.0", "", { "dependencies": { "find-up": "^7.0.0", "picocolors": "^1.1.1", "plist": "^3.1.0" }, "peerDependencies": { "@react-native-vector-icons/get-image": "^12.3.0", "react": "*", "react-native": "*" }, "optionalPeers": ["@react-native-vector-icons/get-image"], "bin": { "rnvi-update-plist": "lib/commonjs/scripts/updatePlist.js" } }, "sha512-t9W0q+AW7WH1Oj5aEg7wGNXDLZJb5sIVkAWo5qtad3PcbBADqoCdikRK/ToLK+xlB0TxjcuL0T74ogudMkYGeA=="], + "@react-native-vector-icons/get-image": ["@react-native-vector-icons/get-image@12.3.0", "", { "peerDependencies": { "react": "*", "react-native": "*" } }, "sha512-ch9mwFWePde7AR0DfhcuNDeMH7N/vLPvoiJbqm28oeJPnCS6XA98F5GPwpMO9IE/omTv2RYwBTmhMA+8Wlwv/A=="], + "@react-native-vector-icons/material-design-icons": ["@react-native-vector-icons/material-design-icons@12.4.0", "", { "dependencies": { "@react-native-vector-icons/common": "^12.4.0" }, "peerDependencies": { "react": "*", "react-native": "*" } }, "sha512-4ewAiHdOCujqprUJYFnBcUJduNddAc+w3Plnl1NhJksAyOaHzCNBg01JgVtkysxPho6++OOMge3FhwyBT8Wtcg=="], "@react-native/assets-registry": ["@react-native/assets-registry@0.82.1", "", {}, "sha512-B1SRwpntaAcckiatxbjzylvNK562Ayza05gdJCjDQHTiDafa1OABmyB5LHt7qWDOpNkaluD+w11vHF7pBmTpzQ=="], @@ -1112,13 +1119,13 @@ "collect-v8-coverage": ["collect-v8-coverage@1.0.3", "", {}, "sha512-1L5aqIkwPfiodaMgQunkF1zRhNqifHBmtbbbxcr6yVxxBnliw4TDOW6NxpO8DJLgJ16OT+Y4ztZqP6p/FtXnAw=="], - "color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="], + "color": ["color@5.0.3", "", { "dependencies": { "color-convert": "^3.1.3", "color-string": "^2.1.3" } }, "sha512-ezmVcLR3xAVp8kYOm4GS45ZLLgIE6SPAFoduLr6hTDajwb3KZ2F46gulK3XpcwRFb5KKGCSezCBAY4Dw4HsyXA=="], - "color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + "color-convert": ["color-convert@3.1.3", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-fasDH2ont2GqF5HpyO4w0+BcewlhHEZOFn9c1ckZdHpJ56Qb7MHhH/IcJZbBGgvdtwdwNbLvxiBEdg336iA9Sg=="], - "color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + "color-name": ["color-name@2.1.0", "", {}, "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg=="], - "color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="], + "color-string": ["color-string@2.1.4", "", { "dependencies": { "color-name": "^2.0.0" } }, "sha512-Bb6Cq8oq0IjDOe8wJmi4JeNn763Xs9cfrBcaylK1tPypWzyoy2G3l90v9k64kjphl/ZJjPIShFztenRomi8WTg=="], "color2k": ["color2k@2.0.3", "", {}, "sha512-zW190nQTIoXcGCaU08DvVNFTmQhUpnJfVuAKfWqUQkflXKpaDdpaYoM0iluLS9lgJNHyBF58KKA2FBEwkD7wog=="], @@ -1904,6 +1911,8 @@ "react-native-blurhash": ["react-native-blurhash@2.1.1", "", { "peerDependencies": { "react": ">=16.8.1", "react-native": ">=0.60.0-rc.0 <1.0.x" } }, "sha512-b1aA5Tn31pPbqmaWnhJv7zSuN6o9M1t4yHciPunfP89LDkH2dvDIynvkE00Hen4Vmt6SnyXViSYH34MyvTvRiA=="], + "react-native-bottom-tabs": ["react-native-bottom-tabs@1.1.0", "", { "dependencies": { "react-freeze": "^1.0.0", "sf-symbols-typescript": "^2.0.0", "use-latest-callback": "^0.2.1" }, "peerDependencies": { "react": "*", "react-native": "*" } }, "sha512-Uu1gvM3i1Hb4DjVvR/38J1QVQEs0RkPc7K6yon99HgvRWWOyLs7kjPDhUswtb8ije4pKW712skIXWJ0lgKzbyQ=="], + "react-native-carplay": ["react-native-carplay@2.4.1-beta.0", "", { "peerDependencies": { "react": "^17.0.2 || ^18.0.0", "react-native": "^0.60.0" }, "optionalPeers": ["react", "react-native"] }, "sha512-tYJymLgJi+0516niv4ApGVC+VgENX/uCYqCX81tewSILWnS6KR7M0A9+bHyNk8xoheFyYGruX7onYxU2U8ykPA=="], "react-native-cli-bump-version": ["react-native-cli-bump-version@1.5.1", "", {}, "sha512-C7Vss+BBD4iNMnn2YR00cU+GDDPZ+LDmIqWoh3FPwI/LBsJ/Vp5qanwtyVYRPcIe7Cg1PPB8WdeZ8XcnqF5Klw=="], @@ -2358,6 +2367,14 @@ "@react-native/eslint-config/eslint-plugin-react-native": ["eslint-plugin-react-native@4.1.0", "", { "dependencies": { "eslint-plugin-react-native-globals": "^0.1.1" }, "peerDependencies": { "eslint": "^3.17.0 || ^4 || ^5 || ^6 || ^7 || ^8" } }, "sha512-QLo7rzTBOl43FvVqDdq5Ql9IoElIuTdjrz9SKAXCvULvBoRZ44JGSkx9z4999ZusCsb4rK3gjS8gOGyeYqZv2Q=="], + "@react-navigation/bottom-tabs/color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="], + + "@react-navigation/elements/color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="], + + "@react-navigation/material-top-tabs/color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="], + + "@react-navigation/native-stack/color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="], + "@typescript-eslint/eslint-plugin/ignore": ["ignore@7.0.5", "", {}, "sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg=="], "@typescript-eslint/typescript-estree/minimatch": ["minimatch@9.0.5", "", { "dependencies": { "brace-expansion": "^2.0.1" } }, "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow=="], @@ -2372,6 +2389,8 @@ "ansi-fragments/strip-ansi": ["strip-ansi@5.2.0", "", { "dependencies": { "ansi-regex": "^4.1.0" } }, "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA=="], + "ansi-styles/color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + "babel-jest/@jest/transform": ["@jest/transform@29.7.0", "", { "dependencies": { "@babel/core": "^7.11.6", "@jest/types": "^29.6.3", "@jridgewell/trace-mapping": "^0.3.18", "babel-plugin-istanbul": "^6.1.1", "chalk": "^4.0.0", "convert-source-map": "^2.0.0", "fast-json-stable-stringify": "^2.1.0", "graceful-fs": "^4.2.9", "jest-haste-map": "^29.7.0", "jest-regex-util": "^29.6.3", "jest-util": "^29.7.0", "micromatch": "^4.0.4", "pirates": "^4.0.4", "slash": "^3.0.0", "write-file-atomic": "^4.0.2" } }, "sha512-ok/BTPFzFKVMwO5eOHRrvnBVHdRy9IrsrW1GpMaQ9MCnilNLXQKmAX8s1YXDFaai9xJpac2ySzV0YeRRECr2Vw=="], "babel-jest/slash": ["slash@3.0.0", "", {}, "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q=="], @@ -2636,10 +2655,28 @@ "@react-native-vector-icons/common/find-up/path-exists": ["path-exists@5.0.0", "", {}, "sha512-RjhtfwJOxzcFmNOi6ltcbcu4Iu+FL3zEj83dk4kAS+fVpTxXLO1b38RvJgT/0QwvV/L3aY9TAnyv0EOqW4GoMQ=="], + "@react-navigation/bottom-tabs/color/color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + + "@react-navigation/bottom-tabs/color/color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="], + + "@react-navigation/elements/color/color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + + "@react-navigation/elements/color/color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="], + + "@react-navigation/material-top-tabs/color/color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + + "@react-navigation/material-top-tabs/color/color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="], + + "@react-navigation/native-stack/color/color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="], + + "@react-navigation/native-stack/color/color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="], + "@typescript-eslint/typescript-estree/minimatch/brace-expansion": ["brace-expansion@2.0.2", "", { "dependencies": { "balanced-match": "^1.0.0" } }, "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ=="], "ansi-fragments/strip-ansi/ansi-regex": ["ansi-regex@4.1.1", "", {}, "sha512-ILlv4k/3f6vfQ4OoP2AGvirOktlQ98ZEL1k9FaQjxa3L1abBgbuTDAdPOpvbGncC0BTVQrl+OM8xZGK6tWXt7g=="], + "ansi-styles/color-convert/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + "babel-jest/@jest/transform/@jest/types": ["@jest/types@29.6.3", "", { "dependencies": { "@jest/schemas": "^29.6.3", "@types/istanbul-lib-coverage": "^2.0.0", "@types/istanbul-reports": "^3.0.0", "@types/node": "*", "@types/yargs": "^17.0.8", "chalk": "^4.0.0" } }, "sha512-u3UPsIilWKOM3F9CXtrG8LEJmNxwoCQC/XVj4IKYXvvpx7QIi/Kg1LI5uDmDpKlac62NUtX7eLjRh+jVZcLOzw=="], "babel-jest/@jest/transform/jest-haste-map": ["jest-haste-map@29.7.0", "", { "dependencies": { "@jest/types": "^29.6.3", "@types/graceful-fs": "^4.1.3", "@types/node": "*", "anymatch": "^3.0.3", "fb-watchman": "^2.0.0", "graceful-fs": "^4.2.9", "jest-regex-util": "^29.6.3", "jest-util": "^29.7.0", "jest-worker": "^29.7.0", "micromatch": "^4.0.4", "walker": "^1.0.8" }, "optionalDependencies": { "fsevents": "^2.3.2" } }, "sha512-fP8u2pyfqx0K1rGn1R9pyE0/KTn+G7PxktWidOBTqFPLYX0b9ksaMFkhK5vrS3DVun09pckLdlx90QthlW7AmA=="], @@ -2778,6 +2815,22 @@ "@react-native-vector-icons/common/find-up/locate-path/p-locate": ["p-locate@6.0.0", "", { "dependencies": { "p-limit": "^4.0.0" } }, "sha512-wPrq66Llhl7/4AGC6I+cqxT07LhXvWL08LNXz1fENOw0Ap4sRZZ/gZpTTJ5jpurzzzfS2W/Ge9BY3LgLjCShcw=="], + "@react-navigation/bottom-tabs/color/color-convert/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/bottom-tabs/color/color-string/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/elements/color/color-convert/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/elements/color/color-string/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/material-top-tabs/color/color-convert/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/material-top-tabs/color/color-string/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/native-stack/color/color-convert/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + + "@react-navigation/native-stack/color/color-string/color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="], + "babel-jest/@jest/transform/@jest/types/@jest/schemas": ["@jest/schemas@29.6.3", "", { "dependencies": { "@sinclair/typebox": "^0.27.8" } }, "sha512-mo5j5X+jIZmJQveBKeS/clAueipV7KgiX1vMgCxam1RNYiqE1w62n0/tJJnHtjW8ZHcQco5gY85jA3mi0L+nSA=="], "cli-truncate/string-width/strip-ansi/ansi-regex": ["ansi-regex@6.2.2", "", {}, "sha512-Bq3SmSpyFHaWjPk8If9yc6svM8c56dB5BAtW4Qbw5jHTwwXXcTLoRMkpDJp6VL0XzlWaCHTXrkFURMYmD0sLqg=="], diff --git a/ios/Podfile.lock b/ios/Podfile.lock index 7a809916..6f3c941e 100644 --- a/ios/Podfile.lock +++ b/ios/Podfile.lock @@ -1964,6 +1964,65 @@ PODS: - ReactCommon/turbomodule/core - SocketRocket - Yoga + - react-native-bottom-tabs (1.1.0): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-ImageManager + - React-jsi + - react-native-bottom-tabs/common (= 1.1.0) + - React-NativeModulesApple + - React-RCTFabric + - React-renderercss + - React-rendererdebug + - React-utils + - ReactCodegen + - ReactCommon/turbomodule/bridging + - ReactCommon/turbomodule/core + - SocketRocket + - SwiftUIIntrospect (~> 1.0) + - Yoga + - react-native-bottom-tabs/common (1.1.0): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-ImageManager + - React-jsi + - React-NativeModulesApple + - React-RCTFabric + - React-renderercss + - React-rendererdebug + - React-utils + - ReactCodegen + - ReactCommon/turbomodule/bridging + - ReactCommon/turbomodule/core + - SocketRocket + - SwiftUIIntrospect (~> 1.0) + - Yoga - react-native-carplay (2.4.1-beta.0): - React - react-native-config (1.5.6): @@ -2148,6 +2207,34 @@ PODS: - SocketRocket - SwiftAudioEx (= 1.1.0) - Yoga + - react-native-vector-icons (12.3.0): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-ImageManager + - React-jsi + - React-NativeModulesApple + - React-RCTFabric + - React-renderercss + - React-rendererdebug + - React-utils + - ReactCodegen + - ReactCommon/turbomodule/bridging + - ReactCommon/turbomodule/core + - SocketRocket + - Yoga - react-native-vector-icons-material-design-icons (12.4.0) - react-native-worklets-core (1.6.2): - boost @@ -3111,6 +3198,7 @@ PODS: - SocketRocket (0.7.1) - SSZipArchive (2.4.3) - SwiftAudioEx (1.1.0) + - SwiftUIIntrospect (1.3.0) - Yoga (0.0.0) DEPENDENCIES: @@ -3163,6 +3251,7 @@ DEPENDENCIES: - react-native-background-actions (from `../node_modules/react-native-background-actions`) - react-native-blob-util (from `../node_modules/react-native-blob-util`) - react-native-blurhash (from `../node_modules/react-native-blurhash`) + - react-native-bottom-tabs (from `../node_modules/react-native-bottom-tabs`) - react-native-carplay (from `../node_modules/react-native-carplay`) - react-native-config (from `../node_modules/react-native-config`) - react-native-google-cast (from `../node_modules/react-native-google-cast`) @@ -3171,6 +3260,7 @@ DEPENDENCIES: - react-native-pager-view (from `../node_modules/react-native-pager-view`) - react-native-safe-area-context (from `../node_modules/react-native-safe-area-context`) - react-native-track-player (from `../node_modules/react-native-track-player`) + - "react-native-vector-icons (from `../node_modules/@react-native-vector-icons/get-image`)" - "react-native-vector-icons-material-design-icons (from `../node_modules/@react-native-vector-icons/material-design-icons`)" - react-native-worklets-core (from `../node_modules/react-native-worklets-core`) - React-NativeModulesApple (from `../node_modules/react-native/ReactCommon/react/nativemodule/core/platform/ios`) @@ -3230,6 +3320,7 @@ SPEC REPOS: - SocketRocket - SSZipArchive - SwiftAudioEx + - SwiftUIIntrospect EXTERNAL SOURCES: boost: @@ -3329,6 +3420,8 @@ EXTERNAL SOURCES: :path: "../node_modules/react-native-blob-util" react-native-blurhash: :path: "../node_modules/react-native-blurhash" + react-native-bottom-tabs: + :path: "../node_modules/react-native-bottom-tabs" react-native-carplay: :path: "../node_modules/react-native-carplay" react-native-config: @@ -3345,6 +3438,8 @@ EXTERNAL SOURCES: :path: "../node_modules/react-native-safe-area-context" react-native-track-player: :path: "../node_modules/react-native-track-player" + react-native-vector-icons: + :path: "../node_modules/@react-native-vector-icons/get-image" react-native-vector-icons-material-design-icons: :path: "../node_modules/@react-native-vector-icons/material-design-icons" react-native-worklets-core: @@ -3490,6 +3585,7 @@ SPEC CHECKSUMS: react-native-background-actions: 48e6bad9e2a47e3b04858634c5a05ea11062f680 react-native-blob-util: e2162ce4757849682559754bca954b65dc7eeb2f react-native-blurhash: c1721deafe7a685088ea14ab4712a1c460be9fe4 + react-native-bottom-tabs: e33312fc663d163f0be73d3474dfb448ba38dad8 react-native-carplay: 8f388f6f73e5e0f73ed154ad8794371343ee20c0 react-native-config: f1dde39f8468ad922fc7e8bd4308c8e6223d5ee8 react-native-google-cast: 7be68a5d0b7eeb95a5924c3ecef8d319ef6c0a44 @@ -3498,6 +3594,7 @@ SPEC CHECKSUMS: react-native-pager-view: a0516effb17ca5120ac2113bfd21b91130ad5748 react-native-safe-area-context: c00143b4823773bba23f2f19f85663ae89ceb460 react-native-track-player: 89d8e641c83a89bea5dee43c381be743282553e9 + react-native-vector-icons: 6ba2060e1b82ce0663f14375579fe1d48e9b668a react-native-vector-icons-material-design-icons: 76cd460b3540b80527b4a80fb7f867f7deedb498 react-native-worklets-core: 28a6e2121dcf62543b703e81bc4860e9a0150cee React-NativeModulesApple: 46690a0fe94ec28fc6fc686ec797b911d251ded0 @@ -3548,6 +3645,7 @@ SPEC CHECKSUMS: SocketRocket: d4aabe649be1e368d1318fdf28a022d714d65748 SSZipArchive: fe6a26b2a54d5a0890f2567b5cc6de5caa600aef SwiftAudioEx: f6aa653770f3a0d3851edaf8d834a30aee4a7646 + SwiftUIIntrospect: fee9aa07293ee280373a591e1824e8ddc869ba5d Yoga: 689c8e04277f3ad631e60fe2a08e41d411daf8eb PODFILE CHECKSUM: 05d07b9cff134e4c27345bc2b588e090e4d3431c diff --git a/package.json b/package.json index 817addb1..495e7342 100644 --- a/package.json +++ b/package.json @@ -37,11 +37,13 @@ "postinstall": "patch-package" }, "dependencies": { + "@bottom-tabs/react-navigation": "^1.1.0", "@jellyfin/sdk": "0.13.0", "@react-native-async-storage/async-storage": "^2.2.0", "@react-native-community/cli": "20.0.0", "@react-native-community/netinfo": "^11.4.1", "@react-native-masked-view/masked-view": "^0.3.2", + "@react-native-vector-icons/get-image": "^12.3.0", "@react-native-vector-icons/material-design-icons": "12.4.0", "@react-navigation/bottom-tabs": "7.8.10", "@react-navigation/material-top-tabs": "7.4.7", @@ -66,6 +68,7 @@ "react-native-background-actions": "^4.0.1", "react-native-blob-util": "^0.22.2", "react-native-blurhash": "2.1.1", + "react-native-bottom-tabs": "^1.1.0", "react-native-carplay": "^2.4.1-beta.0", "react-native-config": "1.5.6", "react-native-device-info": "15.0.1", diff --git a/src/screens/Tabs/index.tsx b/src/screens/Tabs/index.tsx index 1e3bf08a..a352a704 100644 --- a/src/screens/Tabs/index.tsx +++ b/src/screens/Tabs/index.tsx @@ -4,110 +4,99 @@ import Home from '../Home' import MaterialDesignIcons from '@react-native-vector-icons/material-design-icons' import SettingsScreen from '../Settings' import { Discover } from '../Discover' -import { useTheme } from 'tamagui' +import { useTheme, YStack } from 'tamagui' import SearchStack from '../Search' import LibraryScreen from '../Library' import TabParamList from './types' import { TabProps } from '../types' import TabBar from './tab-bar' import { Platform } from 'react-native' +import { createNativeBottomTabNavigator } from '@bottom-tabs/react-navigation' -const Tab = createBottomTabNavigator() +const Tab = createNativeBottomTabNavigator() export default function Tabs({ route, navigation }: TabProps): React.JSX.Element { const theme = useTheme() + const activeJellyfishIcon = MaterialDesignIcons.getImageSourceSync('jellyfish')! + const inactiveJellyfishIcon = MaterialDesignIcons.getImageSourceSync('jellyfish-outline')! + + const activeLibraryIcon = MaterialDesignIcons.getImageSourceSync('music-box-multiple')! + const inactiveLibraryIcon = MaterialDesignIcons.getImageSourceSync( + 'music-box-multiple-outline', + )! + + const searchIcon = MaterialDesignIcons.getImageSourceSync('magnify', 24, theme.primary.val)! + + const activeDiscoverIcon = MaterialDesignIcons.getImageSourceSync('compass')! + const inactiveDiscoverIcon = MaterialDesignIcons.getImageSourceSync('compass-outline')! + + const settingsIcon = MaterialDesignIcons.getImageSourceSync('cogs')! + return ( - } - > - ( - - ), - tabBarButtonTestID: 'home-tab-button', - }} - /> + <> + - ( - - ), - tabBarButtonTestID: 'library-tab-button', + + > + + focused ? activeJellyfishIcon : inactiveJellyfishIcon, + tabBarButtonTestID: 'home-tab-button', + }} + /> - ( - - ), - tabBarButtonTestID: 'search-tab-button', - }} - /> + + focused ? activeLibraryIcon : inactiveLibraryIcon, + tabBarButtonTestID: 'library-tab-button', + }} + /> - ( - - ), - tabBarButtonTestID: 'discover-tab-button', - }} - /> + searchIcon, + tabBarButtonTestID: 'search-tab-button', + }} + /> - ( - - ), - tabBarButtonTestID: 'settings-tab-button', - }} - /> - + + focused ? activeDiscoverIcon : inactiveDiscoverIcon, + tabBarButtonTestID: 'discover-tab-button', + }} + /> + + settingsIcon, + tabBarButtonTestID: 'settings-tab-button', + }} + /> + + ) } diff --git a/src/screens/Tabs/tab-bar.tsx b/src/screens/Tabs/tab-bar.tsx index 57a529fd..66d139ec 100644 --- a/src/screens/Tabs/tab-bar.tsx +++ b/src/screens/Tabs/tab-bar.tsx @@ -1,10 +1,9 @@ import { Miniplayer } from '../../components/Player/mini-player' import InternetConnectionWatcher from '../../components/Network/internetConnectionWatcher' -import { BottomTabBar, BottomTabBarProps } from '@react-navigation/bottom-tabs' import useIsMiniPlayerActive from '../../hooks/use-mini-player' import { useIsFocused } from '@react-navigation/native' -export default function TabBar({ ...props }: BottomTabBarProps): React.JSX.Element { +export default function TabBar(): React.JSX.Element { const isFocused = useIsFocused() const isMiniPlayerActive = useIsMiniPlayerActive() @@ -13,8 +12,6 @@ export default function TabBar({ ...props }: BottomTabBarProps): React.JSX.Eleme <> {isMiniPlayerActive && isFocused && } - - ) }