You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift Game Center无网络时排行榜加载异常问题求助

Fixing Game Center Leaderboard Display Issues Offline

Hey there! Let's work through this problem you're having with Game Center leaderboards not showing properly when users are offline. The default GKGameCenterViewController doesn't handle offline states gracefully out of the box, so here are a few practical solutions to improve the user experience:

1. Check Network Connection Before Showing the Leaderboard

First, you can add a quick network check before presenting the leaderboard. This lets you alert users upfront instead of showing them a broken interface.

Use NWPathMonitor (available on iOS 12+) to check connectivity:

import Network

private func isNetworkAvailable() -> Bool {
    let monitor = NWPathMonitor()
    let queue = DispatchQueue(label: "GameCenterNetworkCheck")
    var connected = false
    
    monitor.pathUpdateHandler = { path in
        connected = path.status == .satisfied
    }
    
    monitor.start(queue: queue)
    // Wait a tiny bit to ensure we get the latest status
    Thread.sleep(forTimeInterval: 0.1)
    monitor.cancel()
    
    return connected
}

Then update your button tap handler to use this check:

@IBAction func showLeaderboardButtonTapped(_ sender: UIButton) {
    guard isNetworkAvailable() else {
        let alert = UIAlertController(
            title: "No Internet Connection",
            message: "Please check your network settings and try again.",
            preferredStyle: .alert
        )
        alert.addAction(UIAlertAction(title: "OK", style: .default))
        present(alert, animated: true)
        return
    }
    
    // Your original Game Center code
    let gcViewController = GKGameCenterViewController()
    gcViewController.gameCenterDelegate = self
    gcViewController.viewState = .leaderboards
    present(gcViewController, animated: true)
}

2. Handle Game Center Loading Errors via Delegate

The GKGameCenterControllerDelegate has a method specifically for handling errors that occur when loading the leaderboard. Implement this to clean up and notify users if something goes wrong (like no network):

extension YourViewController: GKGameCenterControllerDelegate {
    func gameCenterViewControllerDidFinish(_ gameCenterViewController: GKGameCenterViewController) {
        gameCenterViewController.dismiss(animated: true)
    }
    
    func gameCenterViewController(_ gameCenterViewController: GKGameCenterViewController, didFailWithError error: Error) {
        gameCenterViewController.dismiss(animated: true) {
            let alert = UIAlertController(
                title: "Leaderboard Load Failed",
                message: "Could not connect to Game Center. Please check your network and try again.",
                preferredStyle: .alert
            )
            alert.addAction(UIAlertAction(title: "OK", style: .default))
            self.present(alert, animated: true)
        }
    }
}

This way, if the leaderboard fails to load (e.g., offline), the broken view gets dismissed immediately, and users get a clear error message.

3. Cache Leaderboard Data for Offline Viewing (Advanced)

If you want users to see leaderboard data even when offline, you can manually fetch and cache scores using GKLeaderboard, then display a custom offline-friendly interface when there's no network.

Here's a quick example of fetching and caching scores:

private func fetchAndCacheLeaderboardData() {
    let leaderboard = GKLeaderboard(identifier: "your_leaderboard_id") // Replace with your actual ID
    leaderboard.loadScores { [weak self] scores, error in
        guard let self = self else { return }
        
        if let error = error {
            // If offline, show cached data instead
            if !self.isNetworkAvailable() {
                self.showCachedLeaderboard()
            } else {
                // Handle other errors
                self.showErrorAlert(message: error.localizedDescription)
            }
            return
        }
        
        if let scores = scores {
            // Cache scores to UserDefaults (or use Core Data for more complex data)
            let encoder = JSONEncoder()
            if let data = try? encoder.encode(scores) {
                UserDefaults.standard.set(data, forKey: "CachedLeaderboardScores")
            }
            // Show the system leaderboard or your custom interface
            self.showLeaderboard()
        }
    }
}

private func showCachedLeaderboard() {
    // Load cached data from UserDefaults and display in a custom table view/UI
    guard let data = UserDefaults.standard.data(forKey: "CachedLeaderboardScores"),
          let cachedScores = try? JSONDecoder().decode([GKScore].self, from: data) else {
        showErrorAlert(message: "No cached leaderboard data available.")
        return
    }
    
    // Present your custom offline leaderboard view controller with cachedScores
}

This requires building a custom leaderboard UI, but it gives users a seamless experience whether they're online or offline.


Start with the first two solutions—they're quick to implement and will fix the immediate issue of users seeing a broken leaderboard when offline. The third option is great if you want to go the extra mile for user experience.

内容的提问来源于stack exchange,提问作者kmell96

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.25 07:45:42