|
| 1 | +--- |
| 2 | +icon: play |
| 3 | +--- |
| 4 | + |
| 5 | +# Unity |
| 6 | + |
| 7 | +## Integration of Unity WebGL with the tconnect.io sdk |
| 8 | + |
| 9 | +This section of the documentation describes the integration of Unity WebGL applications with the tconnect.io SDK. The goal is to enable communication between a Unity WebGL application and a React application utilizing the tconnect.io sdk. |
| 10 | + |
| 11 | +### Overview |
| 12 | + |
| 13 | +Unity is a powerful platform for developing 2D and 3D games and applications, including WebGL applications. Unity WebGL builds can be seamlessly embedded in React applications. Using the tconnect.io SDK, Web3 features such as wallet integration can be added to these applications. |
| 14 | + |
| 15 | +### Use Case |
| 16 | + |
| 17 | +We consider a simple WebGL application with two buttons: |
| 18 | + |
| 19 | +1. **Open Modal:** A button that opens the React modal, part of the tconnect.io sdk, to connect to a wallet. |
| 20 | +2. **Display Address:** A button that displays the wallet address connected through the modal in the Unity application. |
| 21 | + |
| 22 | +### Implementation Steps |
| 23 | + |
| 24 | +#### Unity Script: `ReactCommunicator` |
| 25 | + |
| 26 | +The following Unity script manages communication between the Unity application and React: |
| 27 | + |
| 28 | +```csharp |
| 29 | +using UnityEngine; |
| 30 | +using UnityEngine.UI; |
| 31 | +using TMPro; |
| 32 | + |
| 33 | +public class ReactCommunicator : MonoBehaviour |
| 34 | +{ |
| 35 | + // Text field to display received data |
| 36 | + public TMP_Text displayText; |
| 37 | + |
| 38 | + // Function called by the button |
| 39 | + public void RequestDataFromReact() |
| 40 | + { |
| 41 | + Debug.Log("Unity: Request sent to React!"); |
| 42 | + // Calls the JavaScript function in the WebGL build |
| 43 | + Application.ExternalCall("sendDataToUnity"); |
| 44 | + } |
| 45 | + |
| 46 | + public void openModalUnity() |
| 47 | + { |
| 48 | + Debug.Log("Unity: Open modal"); |
| 49 | + Application.ExternalCall("openModalUnity"); |
| 50 | + } |
| 51 | + |
| 52 | + // This function is called by React |
| 53 | + public void ReceiveDataFromReact(string data) |
| 54 | + { |
| 55 | + Debug.Log($"Unity: Data received from React - {data}"); |
| 56 | + displayText.text = data; |
| 57 | + } |
| 58 | +} |
| 59 | +``` |
| 60 | + |
| 61 | +#### React Communication Class: `useUnityCommunicator` |
| 62 | + |
| 63 | +The following React hook manages communication between React and Unity: |
| 64 | + |
| 65 | +```typescript |
| 66 | +import { useTConnectModal } from '@tconnect.io/modal'; |
| 67 | +import { useCallback, useState } from 'react'; |
| 68 | +import Web3 from 'web3'; |
| 69 | + |
| 70 | +export const useUnityCommunicator = ( |
| 71 | +sendMessage: (gameObject: string, methodName: string, data: string) => void) => { |
| 72 | + const [address, setAddress] = useState<string | undefined>(); |
| 73 | + const { openModal, evmProvider, tezosBeaconProvider, tezosWcProvider } = useTConnectModal(); |
| 74 | + |
| 75 | + const getAddressEvm = useCallback(async () => { |
| 76 | + if (!evmProvider) return; |
| 77 | + const web3 = new Web3(evmProvider); |
| 78 | + const accounts = await web3.eth.getAccounts(); |
| 79 | + const walletAddress = accounts.length > 0 ? accounts[0] : undefined; |
| 80 | + setAddress(walletAddress); |
| 81 | + return walletAddress; |
| 82 | + }, [evmProvider]); |
| 83 | + |
| 84 | + const getAddressBeacon = useCallback(async () => { |
| 85 | + if (!tezosBeaconProvider) return; |
| 86 | + const address = await tezosBeaconProvider.getPKH(); |
| 87 | + setAddress(address); |
| 88 | + return address; |
| 89 | + }, [tezosBeaconProvider]); |
| 90 | + |
| 91 | + const getAddressWc = useCallback(async () => { |
| 92 | + if (!tezosWcProvider) return; |
| 93 | + const address = await tezosWcProvider.getPKH(); |
| 94 | + setAddress(address); |
| 95 | + return address; |
| 96 | + }, [tezosWcProvider]); |
| 97 | + |
| 98 | + const setupUnityCommunication = useCallback(() => { |
| 99 | + (window as any).openModalUnity = () => { |
| 100 | + openModal(); |
| 101 | + }; |
| 102 | + |
| 103 | + (window as any).sendDataToUnity = async () => { |
| 104 | + try { |
| 105 | + const data = evmProvider |
| 106 | + ? await getAddressEvm() |
| 107 | + : tezosBeaconProvider |
| 108 | + ? await getAddressBeacon() |
| 109 | + : tezosWcProvider |
| 110 | + ? await getAddressWc() |
| 111 | + : 'not connected'; |
| 112 | + |
| 113 | + if (data) { |
| 114 | + sendMessage('Canvas', 'ReceiveDataFromReact', data); |
| 115 | + } |
| 116 | + } catch (error) { |
| 117 | + console.error('React: Error calling from:', error); |
| 118 | + } |
| 119 | + }; |
| 120 | + }, [openModal, getAddressEvm, getAddressBeacon, getAddressWc, sendMessage]); |
| 121 | + |
| 122 | + return { |
| 123 | + setupUnityCommunication, |
| 124 | + address, |
| 125 | + }; |
| 126 | +}; |
| 127 | +``` |
| 128 | + |
| 129 | +### Embedding Unity in React |
| 130 | + |
| 131 | +1. **Embedding the Unity WebGL Build:** The WebGL build can be embedded in React using the [`react-unity-webgl`](https://www.npmjs.com/package/react-unity-webgl)package or as iFrame. |
| 132 | +2. **Initializing Communication:** The `useUnityCommunicator` hook is used to set up communication between Unity and React. |
| 133 | + |
| 134 | +```typescript |
| 135 | +import React, { useEffect } from 'react'; |
| 136 | +import { useUnityCommunicator } from './useUnityCommunicator'; |
| 137 | +import Unity, { UnityContext } from 'react-unity-webgl'; |
| 138 | + |
| 139 | +const UnityGame = () => { |
| 140 | + const unityContext = new UnityContext({ |
| 141 | + loaderUrl: '/path-to-unity-build/Build/loader.js', |
| 142 | + dataUrl: '/path-to-unity-build/Build/data.data', |
| 143 | + frameworkUrl: '/path-to-unity-build/Build/framework.js', |
| 144 | + codeUrl: '/path-to-unity-build/Build/code.wasm', |
| 145 | + }); |
| 146 | + onst { setupUnityCommunication } = useUnityCommunicator(sendMessage); |
| 147 | + |
| 148 | + useEffect(() => { |
| 149 | + setupUnityCommunication(); |
| 150 | + }, [setupUnityCommunication]); |
| 151 | + |
| 152 | + return ( |
| 153 | + <div className="text-center"> |
| 154 | + <h1 className="text-4xl font-bold mb-4">Unity React Integration</h1> |
| 155 | + <div className="mx-auto" style={{ width: 350, height: 600 }}> |
| 156 | + <Unity unityProvider={unityProvider} |
| 157 | + style={{ width: '100%', height: '100%' }} /> |
| 158 | + </div> |
| 159 | + </div> |
| 160 | + ); |
| 161 | +}; |
| 162 | + |
| 163 | +export default UnityGame; |
| 164 | +``` |
| 165 | + |
| 166 | +### Conclusion |
| 167 | + |
| 168 | +By following these steps, Unity WebGL applications can be seamlessly embedded in React and integrated with the tconnect.io SDK. This enables smooth integration of Web3 features such as wallet connectivity into your Unity applications. Further customizations can be made based on the specific requirements of your application. |
| 169 | + |
| 170 | +{% hint style="info" %} |
| 171 | +you can find a demo bot here: @tconnect\_unity\_bot |
| 172 | +{% endhint %} |
0 commit comments