diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml new file mode 100644 index 0000000..66e85b0 --- /dev/null +++ b/.github/workflows/build.yml @@ -0,0 +1,123 @@ +name: Build + +on: + push: + branches: + - main + tags: + - "v*" + pull_request: + +permissions: + contents: read + +jobs: + check: + strategy: + fail-fast: false + matrix: + check: [lint, typecheck] + + runs-on: ubuntu-latest + + steps: + - name: Checkout + uses: actions/checkout@v5 + + - name: Setup pnpm + uses: pnpm/action-setup@v5 + + - name: Setup Node.js + uses: actions/setup-node@v5 + with: + node-version: 22 + cache: pnpm + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Run ${{ matrix.check }} + run: pnpm ${{ matrix.check }} + + build: + needs: check + strategy: + fail-fast: false + matrix: + include: + - os: windows-latest + platform: windows + build-script: build:win + - os: macos-latest + platform: macos + build-script: build:mac + - os: ubuntu-latest + platform: linux + build-script: build:linux + + runs-on: ${{ matrix.os }} + + steps: + - name: Checkout + uses: actions/checkout@v5 + + - name: Setup pnpm + uses: pnpm/action-setup@v5 + + - name: Setup Node.js + uses: actions/setup-node@v5 + with: + node-version: 22 + cache: pnpm + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Set artifact version + id: version + shell: bash + run: | + if [[ "${GITHUB_REF}" == refs/tags/* ]]; then + echo "value=${GITHUB_REF_NAME}" >> "$GITHUB_OUTPUT" + else + echo "value=${GITHUB_SHA::7}" >> "$GITHUB_OUTPUT" + fi + + - name: Build + env: + BUILD_VERSION: ${{ steps.version.outputs.value }} + CSC_IDENTITY_AUTO_DISCOVERY: false + run: pnpm ${{ matrix.build-script }} + + - name: Upload artifacts + uses: actions/upload-artifact@v6 + with: + name: ${{ matrix.platform }}-${{ steps.version.outputs.value }} + path: | + dist/*.exe + dist/*.dmg + dist/*.AppImage + if-no-files-found: error + + release: + needs: build + if: startsWith(github.ref, 'refs/tags/v') + runs-on: ubuntu-latest + permissions: + contents: write + + steps: + - name: Download artifacts + uses: actions/download-artifact@v6 + with: + path: dist + merge-multiple: true + + - name: Create release + uses: softprops/action-gh-release@v2 + with: + files: | + dist/*.exe + dist/*.dmg + dist/*.AppImage + generate_release_notes: true diff --git a/package.json b/package.json index 6dcdf23..7627044 100644 --- a/package.json +++ b/package.json @@ -19,7 +19,10 @@ "format:fix": "prettier --write .", "package": "pnpm run build && electron-builder --dir", "package:run": "pnpm run package && open dist/mac*/'VRC Circle.app'", - "dist": "pnpm run build && electron-builder" + "dist": "pnpm run build && electron-builder", + "build:win": "pnpm run build && electron-builder --win", + "build:mac": "pnpm run build && electron-builder --mac", + "build:linux": "pnpm run build && electron-builder --linux" }, "dependencies": { "electron-updater": "^6.3.9", diff --git a/src/renderer/src/features/avatar/AvatarsView.tsx b/src/renderer/src/features/avatar/AvatarsView.tsx index 9d18a83..446fb54 100644 --- a/src/renderer/src/features/avatar/AvatarsView.tsx +++ b/src/renderer/src/features/avatar/AvatarsView.tsx @@ -395,7 +395,8 @@ function FavoritesTab({ filter, searching }: { filter: AvatarFilter; searching: const toggle = (id: string) => setSelected((s) => { const next = new Set(s); - next.has(id) ? next.delete(id) : next.add(id); + if (next.has(id)) next.delete(id); + else next.add(id); return next; }); @@ -429,7 +430,10 @@ function FavoritesTab({ filter, searching }: { filter: AvatarFilter; searching: setSelected((s) => { const next = new Set(s); const all = ids.every((id) => next.has(id)); - for (const id of ids) all ? next.delete(id) : next.add(id); + for (const id of ids) { + if (all) next.delete(id); + else next.add(id); + } return next; }); diff --git a/src/renderer/src/features/friends/FriendsSidebar.tsx b/src/renderer/src/features/friends/FriendsSidebar.tsx index d7d8860..af7164f 100644 --- a/src/renderer/src/features/friends/FriendsSidebar.tsx +++ b/src/renderer/src/features/friends/FriendsSidebar.tsx @@ -30,7 +30,8 @@ export function FriendsSidebar({ onOpen }: { onOpen: (id: string) => void }) { const toggle = (id: string) => setCollapsed((prev) => { const next = new Set(prev); - next.has(id) ? next.delete(id) : next.add(id); + if (next.has(id)) next.delete(id); + else next.add(id); return next; }); diff --git a/src/renderer/src/features/world/MyFavoriteWorldsSection.tsx b/src/renderer/src/features/world/MyFavoriteWorldsSection.tsx index fd8f284..19776f9 100644 --- a/src/renderer/src/features/world/MyFavoriteWorldsSection.tsx +++ b/src/renderer/src/features/world/MyFavoriteWorldsSection.tsx @@ -102,7 +102,10 @@ export function MyFavoriteWorldsSection({ filter }: { filter?: WorldFilter }) { setSelected((s) => { const next = new Set(s); const all = ids.every((id) => next.has(id)); - for (const id of ids) all ? next.delete(id) : next.add(id); + for (const id of ids) { + if (all) next.delete(id); + else next.add(id); + } return next; });