Eksperymentalny pakiet Unity Pokoju gier YouTube

Ten wrapper umożliwia dostęp do pakietu SDK Pokoju gier na YouTube w Unity C#. Zawiera on wtyczkę .jslib i plik C#, które przyspieszają proces tworzenia. Dostępny jest też przykładowy projekt, który pokazuje, jak używać tych funkcji w swoim projekcie.

Pakiety Unity można pobrać z naszego repozytorium przykładowych gier typu playable.

Wykorzystanie

  1. Sprawdź, czy platforma projektu Unity jest ustawiona na WebGL. To ustawienie znajdziesz w Build Settings.
  2. Użyj WebGLTemplate, aby skompilować grę na potrzeby internetu, lub postępuj zgodnie z instrukcjami w sekcji Używanie własnego pliku index.html i sprawdź, czy w pliku index.htmlskonfigurowano i zainicjowano pakiet SDK na potrzeby internetu.
    • WebGLTemplate znajdziesz w pakiecieGoogle-WebGLTemplate-only.unitypackage lubGoogleYTGameWrapper-with-sample.unitypackage. Aby skonfigurować i używać tego szablonu, wykonaj czynności opisane w sekcji Szablon WebGL.
    • Aby użyć własnego pliku internetowego i index.html, musisz dodać 2 wiersze do skryptu tworzenia index.html Unity. Informacje o integracji znajdziesz w sekcji Używanie własnego pliku index.html.
  3. Otwórz projekt w Unity, a następnie otwórz i zaimportuj do niego jeden z pakietów.
    • GoogleYTGameWrapper.unitypackage: zawiera wtyczkę JS do łączenia pakietu SDK Pokoju gier na YouTube i otoczkę C# ułatwiającą połączenie z Twoim produktem.
    • GoogleYTGameWrapper-with-sample.unitypackage: zawiera te same pliki i treści co pakiet GoogleYTGameWrapper oraz przykład pokazujący, jak używać pakietu SDK Pokoju gier na YouTube w języku C#.
  4. WAŻNE: w scenie głównej utwórz nowy obiekt gry i nadaj mu nazwę YTGameWrapper. Ten obiekt gry służy do komunikacji z mostem JS.
  5. WAŻNE: dodaj zaimportowany kod YTGameWrapper.cs jako komponent skryptu do obiektu YTGameWrapper GameObject.
  6. Jeśli Twój projekt ma wiele scen, dodaj DontDestroyOnLoad do skryptu YTGameWrapper.cs (uwaga: nowe wersje skryptu mają przełącznik DontDestroyOnSceneChange, który jest domyślnie włączony). Dzięki temu skrypt i obiekt GameObject będą dostępne w całej grze.

    GameObject.DontDestroyOnLoad(this.gameObject);
    
  7. Komponent YTGameWrapper.cs i obiekt YTGameWrapper GameObject służą do łączenia się z pakietem SDK Pokoju gier na YouTube. Użyj ich, aby połączyć się z YouTube. Możesz użyć skryptu, aby znaleźć obiekt i komponent, lub dodać je ręcznie do kodu gry w edytorze Unity.

  8. Sprawdź, czy spełniasz wymagania techniczne dotyczące projektu.

Używanie własnego pliku index.html

Jeśli nie używasz podanego index.html przykładu, musisz dodać 2 wiersze kodu do index.html skryptu tworzenia w Unity.

Najpierw dodaj ten wiersz w tym samym miejscu, w którym projekt konfiguruje zmienne dla kontenera Unity, obszaru roboczego itp.

    var container = document.querySelector("#unity-container");
    var canvas = document.querySelector("#unity-canvas");

    var unityGameInstance = null; // <-- Add this line >

    ...

Po drugie, w funkcji createUnityInstance dodaj ten wiersz.

    createUnityInstance(canvas, config, (progress) => {
        progressBarFull.style.width = 100 * progress + "%";
    }).then((unityInstance) => {

        unityGameInstance = unityInstance; // <-- Add this line >

    ...

Przykłady

W tej sekcji znajdziesz kilka przykładów użycia otoki C#. Nie jest to pełna lista dostępnych interfejsów API. Pełną listę dostępnych interfejsów API znajdziesz w pakiecie YouTube Playables SDK.

sendScore

Ten przykład pokazuje implementację sendScore(int points) w C#:

...
using YTGameSDK;
...

public YTGameWrapper ytGameWrapper;
public int battleScore = 0;

...

// Update the total score and send this to the YouTube Game Wrapper.
public void UpdateScores(int scoreAmt)
{
    battleScore += scoreAmt;
    // ytGameWrapper should be a reference to your YTGameWrapper component.
    ytGameWrapper.SendGameScore(battleScore);
}

onPause

Oto przykład, jak gra może nasłuchiwać zdarzeń Pause pochodzących z YT Playables, aby w razie potrzeby wstrzymać działanie silnika:

...
using YTGameSDK;
...

public YTGameWrapper ytGameWrapper;
public bool gameIsPaused = false;

...
void Start()
{
    // Sets the OnPause callback with the YT Playables SDK
    ytGameWrapper.SetOnPauseCallback(PauseTheGameCallback);
}

// Pause game callback, will pause the game when called.
public void PauseTheGameCallback()
{
    gameIsPaused = true;
}

saveData

Oto przykład użycia parametru saveData i przesłania go do pakietu YT Playables SDK:

...
using YTGameSDK;
...

public YTGameWrapper ytGameWrapper;

...

// Saves the current score of the game and converts it to a JSON format.
public void SaveScore(int scoreAmt)
{
    SaveGameData("{\"BestScore\": \"" + scoreAmt.ToString() + "\"}");
}

public void SaveGameData(string saveString)
{
    if (string.IsNullOrEmpty(saveString)) return;

    // Sends save data to the YT Playables SDK
    ytGameWrapper.SendGameSaveData(saveString);
}

loadData

Oto przykład użycia parametru loadData i przesłania go do pakietu YT Playables SDK:

...
using UnityEngine;
using YTGameSDK;
...

[Serializable]
public class LoadedScores
{
    public int BestScore;
    public float BestTime;
}

public YTGameWrapper ytGameWrapper;

...

void Start()
{
    ytGameWrapper.LoadGameSaveData(LoadSaveGameDataReturned);
}

public void LoadSaveGameDataReturned(string data)
{
    if (!string.IsNullOrEmpty(data))
    {
        LoadedScores loadedScores = JsonUtility.FromJson<LoadedScores>(data);
        Debug.Log("LoadSaveGameDataReturned > Score <" + loadedScores.BestScore.ToString()
                  +   "> Time <" + loadedScores.BestTime.ToString("0.00"));
    }
}

requestInterstitialAd

To przykład użycia funkcji requestInterstitialAd, która wskazuje, że jest to dobry moment na wyświetlenie reklamy pełnoekranowej, jeśli jest dostępna. Aby uzyskać najlepsze wyniki, zadzwoń w trakcie przerwy w grze, np. po zakończeniu poziomu.

...
using YTGameSDK;
...

public YTGameWrapper ytGameWrapper;

...

// At the end of a round send a request to show an interstitial Ad, if one is
//  available an Ad will be shown and Pause Game Callback should be called.

// EXAMPLE: send and forget
public void RequestInterstitialAd()
{
    ytGameWrapper.RequestInterstitialAd();
}

// EXAMPLE: send and react to if an Ad was shown
public void RequestInterstitialAd()
{
    int status = ytGameWrapper.RequestInterstitialAd();
    if (status == 0)
    {
        // Ad request was successful, do some action.
    }
}

requestRewardedAd

To przykład użycia requestRewardedAd. Używa się go, gdy użytkownik zdecyduje się obejrzeć reklamę z nagrodą w zamian za nagrodę w grze. Jeśli reklama jest dostępna, zostanie wyświetlona użytkownikowi.

...
using YTGameSDK;
...

public YTGameWrapper ytGameWrapper;

...

public void RequestRewardedAd()
{
    // Register callback for Rewarded Ads. If an Ad is available one will be
    //  shown. Pause Game Callback should be called. Any ID is fine as long as
    //  its identifyable for your game.
    ytGameWrapper.RequestRewardedAd("my-reward-ad-id-123", (rewardEarned) => {
        if (rewardEarned) {
            // Rewarded Ad is earned, reward the user.
        } else {
            // Rewarded Ad not earned, take the appropriate action
        }
    });
}

Jak korzystać z przykładowego szablonu WebGL w YouTube

Jeśli nie masz bardzo dużego projektu Unity, zbudowane pliki .wasm.data powinny mieścić się w limicie rozmiaru pliku. W takim przypadku nie musisz dodatkowo kompresować tych plików, ponieważ zostaną one automatycznie skompresowane podczas przesyłania plików gry natychmiastowej. Automatyczna kompresja sprawdzi też, czy plik .wasm spełnia wymaganie dotyczące początkowego rozmiaru pakietu. Na przykład plik .wasm o rozmiarze około 25 MiB zostanie skompresowany do około 7 MiB.

Jeśli z jakiegoś powodu Twoje pliki przekraczają maksymalny rozmiar pojedynczego pliku, najlepiej użyć kompresji ZIP, aby sprawdzić, czy mieszczą się w tym limicie. Kompresja z możliwością odtwarzania nie spowoduje ponownej kompresji tych plików.

Jeśli kompresja jest potrzebna, należy ją zastosować po początkowym utworzeniu projektu.

Szablon WebGL

  1. Aby przeprowadzić wstępną konfigurację, postępuj zgodnie z instrukcjami dotyczącymi pakietu Unity. Użyj symbolu Google-WebGLTemplate-only.unitypackage lub GoogleYTGameWrapper-with-sample.unitypackage i zaimportuj wszystkie pliki z folderu WebGLTemplates/YTGameWrapperTemplate/.
    • Uwaga: jeśli nie masz jeszcze zaimportowanych YTGameWrapper.cs iUnityYTGameSDKLib.jslib, zaimportuj je również.
  2. Ustaw szablon WebGL na YTGameWrapperTemplate. To ustawienie znajduje się na karcie Edit –> Project settings –> Player –> WebGL w sekcji Resolution and Presentation.
    • Uwaga: domyślna szerokość i wysokość obszaru roboczego są ustawione w szablonie na 100%, więc te ustawienia Unity niczego nie zmienią.
  3. Upewnij się, że opcja Compression Format jest wyłączona. To ustawienie znajduje się na karcie Project settings –> Player –> WebGL –> Publishing Settings.
  4. W oknie WebGL utwórz Build Settings, a potem przejdź do kroku 7 lub 5 w zależności od potrzeb projektu.
  5. Kroki 5 i 6 wykonaj tylko wtedy, gdy używasz kompresji: po utworzeniu projektu przejdź do folderu kompilacji i otwórz folder Build. Znajdź pliki .wasm lub .data projektów, które wymagają skompresowania, aby zmieścić się w ramach limitów rozmiaru pliku, i skompresuj je. Pamiętaj, aby usunąć oryginalne pliki .wasm/.data, które zostały skompresowane, ponieważ zamiast nich prześlesz pliki *.wasm.zip*.data.zip.
    • Uwaga: jeśli używasz komputera Mac, możesz kliknąć plik prawym przyciskiem myszy i wybrać „Kompresuj *”. Na komputerze PC możesz kliknąć plik prawym przyciskiem myszy i wybrać „Kompresuj do pliku ZIP”.
  6. Wykonaj tylko wtedy, gdy wykonano krok 5: zaktualizuj plik index.html utworzony na podstawie pliku YTGameWrapperTemplate, aby wczytywać spakowane pliki i je dekompresować.
    • Pod koniec plików index.html znajdziesz Path 1 i zakomentuj ten wiersz InitUnitySection();.
    • Pod koniec plików index.html znajdziesz Path 2 i zakomentuj ten wiersz loadResources(InitUnitySection);.
  7. Podczas przesyłania projektu do certyfikacji musisz wysłać wszystkie pliki utworzone w Unity do lokalizacji kompilacji z kroku 4. Jeśli wykonano kroki 5 i 6, dołącz również te pliki.

Uaktualnij podane przykłady, aby korzystać z uniwersalnego potoku renderowania (URP)

Jednym z najnowszych ulepszeń w nowszych wersjach Unity jest to, że korzystają one z uniwersalnego potoku renderowania (URP). Aby uaktualnić przykład, tak aby wszystko było renderowane prawidłowo.

  1. Zacznij od zaimportowania pakietu GoogleYTGameWrapper-with-sample.unitypackage do nowego lub istniejącego projektu.
  2. Otwórz okno Render Pipeline Converter: Window -> Rendering -> Render Pipeline Converter.
  3. Wybierz Rendering Settings, Material UpgradeReadonly Material Converter.
  4. Następnie wybierz Initialize and Convert, poczekaj na zakończenie tego procesu i sprawdź, czy próbka jest gotowa do użycia w URP.

Dzielenie komponentów w projekcie Unity (leniwe wczytywanie)

Jednym z głównych problemów, na które zwracają uwagę deweloperzy korzystający z Unity, jest utrzymanie rozmiaru pliku poniżej limitu i spełnienie wymagań dotyczących całkowitego rozmiaru pakietu.

Leniwe ładowanie zasobów to świetna optymalizacja, którą możesz wprowadzić w swoim projekcie, ponieważ możesz ładować zasoby, poziomy i dane w miarę potrzeb. Nasz zespół certyfikacyjny może odstąpić od ogólnych ograniczeń rozmiaru pliku, jeśli zostanie to prawidłowo wykonane, ponieważ pełna wersja gry nie będzie ładowana z góry, ale w miarę poruszania się użytkownika po produkcie.

Aby zapewnić prawidłowe wczytywanie, Unity oferuje kilka sposobów dzielenia zasobów. Sprawdź, czy poszczególne grupy zasobów nie przekraczają limitów rozmiaru i czy wczytujesz treści z upływem czasu. Sugerujemy użycie Addressables lub Asset Bundles.

Adresowalne

Adresy umożliwiają identyfikowanie różnych plików, które powinny być ładowane razem, a Unity zajmie się większością pakowania. Unity udostępnia też narzędzia do zarządzania rozmiarami plików i zapobiegania duplikowaniu zasobów.

Aby korzystać z Addressables, musisz zaimportować pakiet Addressables za pomocą Menedżera pakietów w Unity, a następnie otagować zasoby w grupach Addressable. Więcej informacji znajdziesz w dokumentacji Unity.

Pakiety zasobów

Pakiety zasobów są przydatne, ponieważ możesz podzielić projekt i ładować elementy w trakcie działania aplikacji. Przydadzą się one w przypadku DLC, pakietów poziomów, nowych postaci i innych elementów. Pakiety zasobów świetnie nadają się do samodzielnego zarządzania wczytywaniem i grupowaniem treści. Możesz je wykorzystać, tagując komponenty w określonych pakietach, a następnie wczytując pakiety w miarę potrzeb. Więcej informacji znajdziesz w dokumentacji pakietu zasobów Unity.

Zapoznaj się z pełną dokumentacją interfejsu YT Playables API.