Esta guía te muestra cómo usar el SDK de Cardboard para iOS para crear tu propio plan Experiencias de realidad (RV).
Puedes usar el SDK de Cardboard para convertir un smartphone en una plataforma de RV. Un smartphone puede mostrar escenas en 3D con renderización estereoscópica, seguir y reaccionar a los movimientos de la cabeza, y interactuar con las apps detectando cuando el usuario presiona el botón del visor.
Para empezar, usarás HelloCardboard, un juego de demostración que demuestra las funciones principales. del SDK de Cardboard. En el juego, los usuarios miran alrededor de un mundo virtual para encontrar y recolectar objetos. Allí se indica cómo hacer lo siguiente:
- Configura tu entorno de desarrollo
- Descarga y compila la app de demostración
- Escanea el código QR de un visor Cardboard para guardar sus parámetros
- Realizar un seguimiento de los movimientos de la cabeza del usuario
- Renderiza imágenes estereoscópicas configurando la distorsión correcta para cada ojo
Configura tu entorno de desarrollo
Requisitos de hardware:
- iPhone con iOS 12.0 o versiones posteriores
- Visor de Cardboard
Requisitos de software:
- Xcode 12.5 o una versión posterior
- CocoaPods 1.9 o una versión más reciente
Descarga y compila la app de demostración
El SDK de Cardboard se creó con búferes de protocolo compilados previamente. Archivos de origen C++. Puedes encontrar los pasos para compilar los archivos fuente desde cero aquí.
Clona el SDK de Cardboard y la aplicación de demostración Hello Cardboard desde GitHub ejecutando este comando:
git clone https://github.com/googlevr/cardboard.git
Instala la dependencia de búferes de protocolo en el proyecto Xcode. Para ello, ejecuta el siguiente comando en la raíz del repositorio:
pod install
Abre el espacio de trabajo de Cardboard (
Cardboard.xcworkspace
) en Xcode.Cambia el ID del paquete de la app para que puedas firmarla con tu equipo.
Navega a SDK > Fases de compilación > Vincula objetos binarios con bibliotecas
- Elimina
libPods-sdk.a
de la lista; para ello, selecciónalo y haz clic en el signo '-'. . - Para agregar
libProtobuf-C++.a
a la lista, haz clic en el signo '+' botón y selecciónalo. Si aparece un mensaje que sugiere usar un XCFramework, haz clic en "Add Anyway".
- Elimina
Haz clic en Ejecutar.
Escanea el código QR
Para guardar los parámetros del dispositivo, escanea el código QR del visor Cardboard:
Probar la demostración
En HelloCardboard, buscarás y recopilarás esferas geodésicas en un espacio 3D.
Para buscar y recopilar una esfera, sigue estos pasos:
Mueve la cabeza en cualquier dirección hasta que veas una esfera flotante.
Mira directamente la esfera. Esto hace que cambie de color.
Presiona el botón del visor Cardboard para "recopilar" la esfera.
Configura el dispositivo
Cuando el usuario presiona el ícono de ajustes para cambiar los visores de Cardboard, el elemento didTapSwitchButton
se llama a este método en HelloCardboardOverlayView
.
- (void)didTapSwitchButton:(id)sender {
if ([self.delegate respondsToSelector:@selector(didTapBackButton)]) {
[self.delegate didChangeViewerProfile];
}
self.settingsBackgroundView.hidden = YES;
}
De esta manera, se llama a CardboardQrCode_scanQrCodeAndSaveDeviceParams
, que abre la ventana
para escanear el código QR del usuario. Cuando el usuario escanea el código QR,
se actualizan los parámetros de distorsión.
- (void)switchViewer {
CardboardQrCode_scanQrCodeAndSaveDeviceParams();
}
- (void)didChangeViewerProfile {
[self pauseCardboard];
[self switchViewer];
[self resumeCardboard];
}
Seguimiento de cabeza
Crea un monitor de cabeza
El seguimiento de cabeza se crea una vez en el método viewDidLoad
de HelloCardboardViewController
:
_cardboardHeadTracker = CardboardHeadTracker_create();
Pausar y reanudar el seguimiento de la cabeza
Los métodos pauseCardboard
y resumeCardboard
de la
La clase HelloCardboardViewController
pausa y reanuda el seguimiento de la cabeza.
respectivamente. resumeCardboard
también establece la marca _updateParams
, lo que provoca
los parámetros del dispositivo que se actualizarán en la próxima llamada de dibujo
- (void)pauseCardboard {
self.paused = true;
CardboardHeadTracker_pause(_cardboardHeadTracker);
}
- (void)resumeCardboard {
// Parameters may have changed.
_updateParams = YES;
// Check for device parameters existence in app storage. If they're missing,
// we must scan a Cardboard QR code and save the obtained parameters.
uint8_t *buffer;
int size;
CardboardQrCode_getSavedDeviceParams(&buffer, &size);
if (size == 0) {
[self switchViewer];
}
CardboardQrCode_destroy(buffer);
CardboardHeadTracker_resume(_cardboardHeadTracker);
self.paused = false;
}
Distorsión del lente
Cada vez que Cardboard escanea un nuevo código QR, el siguiente código lee los parámetros guardados y los usa para crear el objeto de distorsión de la lente, que aplica la distorsión de lente adecuada al contenido procesado:
CardboardQrCode_getSavedDeviceParams(&encodedDeviceParams, &size);
// Create CardboardLensDistortion.
CardboardLensDistortion_destroy(_cardboardLensDistortion);
_cardboardLensDistortion =
CardboardLensDistortion_create(encodedDeviceParams, size, width, height);
// Initialize HelloCardboardRenderer.
_renderer.reset(new cardboard::hello_cardboard::HelloCardboardRenderer(
_cardboardLensDistortion, _cardboardHeadTracker, width, height));
Renderización
La renderización de contenido en Cardboard implica lo siguiente:
- Cómo crear texturas
- Obtén matrices de vistas y proyección para el ojo izquierdo y derecho
- Cómo crear el procesador y configurar la malla de distorsión
- Cómo renderizar cada fotograma
Crea texturas
El contenido se dibuja en una textura, que se divide en secciones para el ojo izquierdo y el derecho.
Estas secciones se inicializan en _leftEyeTexture
y _rightEyeTexture
, respectivamente.
La app de ejemplo usa una sola textura para ambos ojos, pero también es posible crear una imagen
textura para cada ojo.
// Generate texture to render left and right eyes.
glGenTextures(1, &_eyeTexture);
glBindTexture(GL_TEXTURE_2D, _eyeTexture);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, _width, _height, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
_leftEyeTexture.texture = _eyeTexture;
_leftEyeTexture.left_u = 0;
_leftEyeTexture.right_u = 0.5;
_leftEyeTexture.top_v = 1;
_leftEyeTexture.bottom_v = 0;
_rightEyeTexture.texture = _eyeTexture;
_rightEyeTexture.left_u = 0.5;
_rightEyeTexture.right_u = 1;
_rightEyeTexture.top_v = 1;
_rightEyeTexture.bottom_v = 0;
CheckGLError("Create Eye textures");
Esas texturas se pasan como parámetros a CardboardDistortionRenderer_renderEyeToDisplay
.
Obtén matrices de vistas y proyección para el ojo izquierdo y derecho
Primero, recupera las matrices oculares para el ojo izquierdo y derecho:
CardboardLensDistortion_getEyeFromHeadMatrix(_lensDistortion, kLeft, _eyeMatrices[kLeft]);
CardboardLensDistortion_getEyeFromHeadMatrix(_lensDistortion, kRight, _eyeMatrices[kRight]);
CardboardLensDistortion_getProjectionMatrix(_lensDistortion, kLeft, kZNear, kZFar,
_projMatrices[kLeft]);
CardboardLensDistortion_getProjectionMatrix(_lensDistortion, kRight, kZNear, kZFar,
_projMatrices[kRight]);
A continuación, obtén las mallas de distorsión para cada uno de los ojos y pásalas al renderizador de distorsión:
CardboardLensDistortion_getDistortionMesh(_lensDistortion, kLeft, &leftMesh);
CardboardLensDistortion_getDistortionMesh(_lensDistortion, kRight, &rightMesh);
Crea el procesador y establece la malla de distorsión correcta
El renderizador solo se debe inicializar una vez. Cuando se haya creado el renderizador, configura el nuevo
malla de distorsión para el ojo izquierdo y derecho de acuerdo con los valores de malla que devuelve el
función CardboardLensDistortion_getDistortionMesh
.
_distortionRenderer = CardboardOpenGlEs2DistortionRenderer_create();
CardboardDistortionRenderer_setMesh(_distortionRenderer, &leftMesh, kLeft);
CardboardDistortionRenderer_setMesh(_distortionRenderer, &rightMesh, kRight);
Cómo renderizar el contenido
Recupera la orientación actual de la cabeza de CardboardHeadTracker_getPose
:
CardboardHeadTracker_getPose(_headTracker, targetTime, position, orientation);
_headView =
GLKMatrix4Multiply(GLKMatrix4MakeTranslation(position[0], position[1], position[2]),
GLKMatrix4MakeWithQuaternion(GLKQuaternionMakeWithArray(orientation)));
Usa la orientación actual de la cabeza con las matrices de vista y proyección para crear una vista y usarlas para renderizar el contenido del mundo para cada uno de los ojos:
// Draw left eye.
glViewport(0, 0, _width / 2.0, _height);
glScissor(0, 0, _width / 2.0, _height);
DrawWorld(_leftEyeViewPose, GLKMatrix4MakeWithArray(_projMatrices[kLeft]));
// Draw right eye.
glViewport(_width / 2.0, 0, _width / 2.0, _height);
glScissor(_width / 2.0, 0, _width / 2.0, _height);
DrawWorld(_rightEyeViewPose, GLKMatrix4MakeWithArray(_projMatrices[kRight]));
Usa CardboardDistortionRenderer_renderEyeToDisplay
para aplicar la distorsión.
corrección del contenido y renderizarlo en la pantalla.
CardboardDistortionRenderer_renderEyeToDisplay(_distortionRenderer, renderTarget, /*x=*/0,
/*y=*/0, _width, _height, &_leftEyeTexture,
&_rightEyeTexture);