tutorial plugin javafx javafxports gluon gluon-mobile

javafx - plugin - Gluon Mobile iOS Reproductor de audio



gluon plugin (1)

Mientras que en Android podemos agregar fácilmente API nativa a las carpetas de Android de un proyecto Gluon (verifique esta solución para usar Media nativo en Android), el uso de código nativo (Objetive-C) con Media API en las carpetas de iOS no es suficiente, ya que tiene que compilarse, y los archivos compilados deben incluirse en el ipa.

Actualmente, Charm Down está haciendo esto para muchos servicios. Si echa un vistazo al script build.gradle para iOS , incluye la tarea xcodebuild para compilar y compilar la biblioteca nativa libCharm.a , que luego debería incluirse en cualquier proyecto iOS que utilice cualquiera de esos servicios.

Mi sugerencia será clonar Charm Down y proporcionar un nuevo servicio: AudioService , con algunos métodos básicos como:

public interface AudioService { void play(String audioName); void pause(); void resume(); void stop(); }

Este servicio se agregará a la clase Platform :

public abstract class Platform { ... public abstract AudioService getAudioService(); }

y debe proporcionar implementaciones para escritorio (vacío), Android (como el que está aquí ) e iOS.

Implementación de IOS - Java

Deberá agregar esto a la clase IOSPlatform :

public class IOSPlatform extends Platform { ... @Override public AudioService getAudioService() { if (audioService == null) { audioService = new IOSAudioService(); } return audioService; } }

y crea la clase IOSAudioService :

public class IOSAudioService implements AudioService { @Override public void play(String audioName) { CharmApplication.play(audioName); } @Override public void pause() { CharmApplication.pause(); } @Override public void resume() { CharmApplication.resume(); } @Override public void stop() { CharmApplication.stop(); } }

Finalmente, deberás agregar las llamadas nativas en CharmApplication :

public class CharmApplication { static { System.loadLibrary("Charm"); _initIDs(); } ... public static native void play(String audioName); public static native void pause(); public static native void resume(); public static native void stop(); }

Implementación de IOS - Objective-C

Ahora, en la carpeta nativa, en CharmApplication.m , agregue la implementación de esas llamadas:

#include "CharmApplication.h" ... #include "Audio.h" // Audio Audio *_audio; JNIEXPORT void JNICALL Java_com_gluonhq_charm_down_ios_CharmApplication_play (JNIEnv *env, jclass jClass, jstring jTitle) { NSLog(@"Play audio"); const jchar *charsTitle = (*env)->GetStringChars(env, jTitle, NULL); NSString *name = [NSString stringWithCharacters:(UniChar *)charsTitle length:(*env)->GetStringLength(env, jTitle)]; (*env)->ReleaseStringChars(env, jTitle, charsTitle); _audio = [[Audio alloc] init]; [_audio playAudio:name]; return; } JNIEXPORT void JNICALL Java_com_gluonhq_charm_down_ios_CharmApplication_pause (JNIEnv *env, jclass jClass) { if (_audio) { [_audio pauseAudio]; } return; } JNIEXPORT void JNICALL Java_com_gluonhq_charm_down_ios_CharmApplication_resume (JNIEnv *env, jclass jClass) { if (_audio) { [_audio resumeAudio]; } return; } JNIEXPORT void JNICALL Java_com_gluonhq_charm_down_ios_CharmApplication_stop (JNIEnv *env, jclass jClass) { if (_audio) { [_audio stopAudio]; } return; }

y crea el archivo de cabecera Audio.h :

#import <AVFoundation/AVFoundation.h> #import <UIKit/UIKit.h> @interface Audio :UIViewController <AVAudioPlayerDelegate> { } - (void) playAudio: (NSString *) audioName; - (void) pauseAudio; - (void) resumeAudio; - (void) stopAudio; @end

y la implementación Audio.m . Este se basa en este tutorial :

#include "Audio.h" #include "CharmApplication.h" @implementation Audio AVAudioPlayer* player; - (void)playAudio:(NSString *) audioName { NSString* fileName = [audioName stringByDeletingPathExtension]; NSString* extension = [audioName pathExtension]; NSURL* url = [[NSBundle mainBundle] URLForResource:[NSString stringWithFormat:@"%@",fileName] withExtension:[NSString stringWithFormat:@"%@",extension]]; NSError* error = nil; if(player) { [player stop]; player = nil; } player = [[AVAudioPlayer alloc] initWithContentsOfURL:url error:&error]; if(!player) { NSLog(@"Error creating player: %@", error); return; } player.delegate = self; [player prepareToPlay]; [player play]; } - (void)pauseAudio { if(!player) { return; } [player pause]; } - (void)resumeAudio { if(!player) { return; } [player play]; } - (void)stopAudio { if(!player) { return; } [player stop]; player = nil; } - (void)audioPlayerDidFinishPlaying:(AVAudioPlayer *)player successfully:(BOOL)flag { NSLog(@"%s successfully=%@", __PRETTY_FUNCTION__, flag ? @"YES" : @"NO"); } - (void)audioPlayerDecodeErrorDidOccur:(AVAudioPlayer *)player error:(NSError *)error { NSLog(@"%s error=%@", __PRETTY_FUNCTION__, error); } @end

Construye la biblioteca nativa

Edite build.gradle para el módulo iOS y agregue el servicio de audio a la tarea xcodebuild :

def nativeSources = ["$project.projectDir/src/main/native/CharmApplication.m", ..., "$project.projectDir/src/main/native/Audio.m"] ... def compileOutputs = [ "$project.buildDir/native/$arch/CharmApplication.o", "$project.buildDir/native/$arch/Charm.o", ..., "$project.buildDir/native/$arch/Audio.o"]

Construye el proyecto

Guarde el proyecto, y desde la raíz del proyecto Charm Down, ejecute la línea de comando:

./gradlew clean build

Si todo está bien, debes tener:

  • Common / build / libs / charm-down-common-2.1.0-SNAPSHOT.jar
  • Desktop / build / libs / charm-down-desktop-2.1.0-SNAPSHOT.jar
  • Android / build / libs / charm-down-android-2.1.0-SNAPSHOT.jar
  • IOS / build / libs / charm-down-ios-2.1.0-SNAPSHOT.jar
  • IOS / build / native / libCharm.a

Proyecto Gluon

Con esas dependencias y la biblioteca nativa, podrá crear un nuevo Proyecto Gluon y agregar los archivos jar como dependencias locales (a la carpeta libs ).

En cuanto a la biblioteca nativa, se debe agregar a esta ruta: src/ios/jniLibs/libCharm.a .

Actualice el script build.gradle :

repositories { flatDir { dirs ''libs'' } jcenter() ... } dependencies { compile ''com.gluonhq:charm-glisten:3.0.0'' compile ''com.gluonhq:charm-down-common:2.1.0-SNAPSHOT'' compile ''com.gluonhq:charm-glisten-connect-view:3.0.0'' iosRuntime ''com.gluonhq:charm-glisten-ios:3.0.0'' iosRuntime ''com.gluonhq:charm-down-ios:2.1.0-SNAPSHOT'' }

En su vista, recupere el servicio y proporcione una interfaz de usuario básica para llamar a los play("audio.mp3") , pause() , resume() y stop() :

private boolean pause; public BasicView(String name) { super(name); AudioService audioService = PlatformFactory.getPlatform().getAudioService(); final HBox hBox = new HBox(10, MaterialDesignIcon.PLAY_ARROW.button(e -> audioService.play("audio.mp3")), MaterialDesignIcon.PAUSE.button(e -> { if (!pause) { audioService.pause(); pause = true; } else { audioService.resume(); pause = false; } }), MaterialDesignIcon.STOP.button(e -> audioService.stop())); hBox.setAlignment(Pos.CENTER); setCenter(new StackPane(hBox)); }

Finalmente, coloque un archivo de audio como audio.mp3 , en src/ios/assets/audio.mp3 , compile e implemente en iOS.

Afortunadamente, esta API será proporcionada por Charm Down en el corto plazo. Además, si se le ocurre una buena implementación, no dude en compartirla y crear una solicitud de extracción .

Dado que JavaFx Media aún no se ha portado a las plataformas móviles, ¿alguien puede ayudarme con el uso de los APi nativos de iOS para reproducir un archivo de sonido mp3 que se almacenaría en mi carpeta principal / recursos en mi proyecto de gluones?