Skip to content

Commit

Permalink
Merge pull request #24 from fuziki/feature/livephoto
Browse files Browse the repository at this point in the history
support Live Photos
  • Loading branch information
fuziki authored Jul 23, 2021
2 parents 5d5d342 + 33b86a5 commit a7849d8
Show file tree
Hide file tree
Showing 21 changed files with 438 additions and 40 deletions.
35 changes: 24 additions & 11 deletions Examples/NativeExamples/MovExample/GameViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -54,9 +54,9 @@ class GameViewController: UIViewController {
link?.add(to: RunLoop.main, forMode: .common)
link?.isPaused = true

audioEngine.onBufferPublisher.sink { [weak self] (buffer: AVAudioPCMBuffer, timeSec: Double) in
self?.write(buffer: buffer, timeSec: timeSec)
}.store(in: &cancellables)
// audioEngine.onBufferPublisher.sink { [weak self] (buffer: AVAudioPCMBuffer, timeSec: Double) in
// self?.write(buffer: buffer, timeSec: timeSec)
// }.store(in: &cancellables)

let tmpDir = FileManager.default.temporaryDirectory.appendingPathComponent("tmpDri")
try! FileManager.default.createDirectory(at: tmpDir, withIntermediateDirectories: true, attributes: nil)
Expand All @@ -67,24 +67,37 @@ class GameViewController: UIViewController {
var recording: Bool = false
var tmpUrl: NSString?
var sentFirstFrame: Bool = false
let audioEngine = AudioEngineService()
// let audioEngine = AudioEngineService()

var uuid: NSString = ""

@IBAction func onTapButton(_ sender: Any) {
recording.toggle()
if recording {
print("start recording")
UnityMediaCreator_initAsMovWithAudio(tmpUrl?.utf8String,
"h264",
Int64(view.frame.width),
Int64(view.frame.height), 1, Float(AppConfig.fs))
uuid = UUID().uuidString as NSString
// UnityMediaCreator_initAsMovWithAudio(tmpUrl?.utf8String,
// "h264", Int64(view.frame.width), Int64(view.frame.height), 1, Float(AppConfig.fs),
// uuid.utf8String)
let tex = mtkView.currentDrawable!.texture
print("init \(tex.width) x \(tex.height)")
UnityMediaCreator_initAsMovWithNoAudio(tmpUrl?.utf8String, "h264",
Int64(tex.width), Int64(tex.height),
// "")
uuid.utf8String)
sentFirstFrame = false
link!.isPaused = false
audioEngine.start()
// audioEngine.start()
} else {
link!.isPaused = true
audioEngine.stop()
// audioEngine.stop()
UnityMediaCreator_finishSync()
UnityMediaSaver_saveVideo(tmpUrl?.utf8String)
// UnityMediaSaver_saveVideo(tmpUrl?.utf8String)

let tex = mtkView.currentDrawable!.texture
UnityMediaSaver_saveLivePhotos(Unmanaged.passUnretained(tex).toOpaque(),
uuid.utf8String,
tmpUrl?.utf8String)
print("finish recording")
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -207,13 +207,14 @@ typedef unsigned int swift_uint4 __attribute__((__ext_vector_type__(4)));
#endif

void UnityMediaCreator_finishSync(void);
void UnityMediaCreator_initAsMovWithAudio(char const * _Nullable url, char const * _Nullable codec, int64_t width, int64_t height, int64_t channel, float samplingRate);
void UnityMediaCreator_initAsMovWithNoAudio(char const * _Nullable url, char const * _Nullable codec, int64_t width, int64_t height);
void UnityMediaCreator_initAsMovWithAudio(char const * _Nullable url, char const * _Nullable codec, int64_t width, int64_t height, int64_t channel, float samplingRate, char const * _Nullable contentIdentifier);
void UnityMediaCreator_initAsMovWithNoAudio(char const * _Nullable url, char const * _Nullable codec, int64_t width, int64_t height, char const * _Nullable contentIdentifier);
void UnityMediaCreator_initAsWav(char const * _Nullable url, int64_t channel, float samplingRate, NSInteger bitDepth);
BOOL UnityMediaCreator_isRecording(void) SWIFT_WARN_UNUSED_RESULT;
void UnityMediaCreator_start(int64_t microSec);
void UnityMediaCreator_writeAudio(float const * _Nonnull pcm, int64_t frame, int64_t microSec);
void UnityMediaCreator_writeVideo(void const * _Nullable texturePtr, int64_t microSec);
void UnityMediaSaver_saveLivePhotos(void const * _Nullable texturePtr, char const * _Nullable contentIdentifier, char const * _Nullable url);
void UnityMediaSaver_saveVideo(char const * _Nullable url);

SWIFT_CLASS("_TtC17UnityVideoCreator17VideoCreatorUnity")
Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
Expand Up @@ -10,21 +10,29 @@ public class MediaSaver
[DllImport("__Internal")]
private static extern void UnityMediaSaver_saveVideo(string url);

[DllImport("__Internal")]
private static extern void UnityMediaSaver_saveLivePhotos(IntPtr texturePtr, string contentIdentifier, string url);

public static void SaveVideo(string url)
{
UnityMediaSaver_saveVideo(url);
}

public static void SaveLivePhotos(Texture texture, string contentIdentifier, string url)
{
UnityMediaSaver_saveLivePhotos(texture.GetNativeTexturePtr(), contentIdentifier, url);
}
#endif
}

public class MediaCreator
{
#if UNITY_IOS
[DllImport("__Internal")]
private static extern void UnityMediaCreator_initAsMovWithNoAudio(string url, string codec, long width, long height);
private static extern void UnityMediaCreator_initAsMovWithNoAudio(string url, string codec, long width, long height, string contentIdentifier);

[DllImport("__Internal")]
private static extern void UnityMediaCreator_initAsMovWithAudio(string url, string codec, long width, long height, long channel, float samplingRate);
private static extern void UnityMediaCreator_initAsMovWithAudio(string url, string codec, long width, long height, long channel, float samplingRate, string contentIdentifier);

[DllImport("__Internal")]
private static extern void UnityMediaCreator_initAsWav(string url, long channel, float samplingRate, long bitDepth);
Expand All @@ -45,17 +53,17 @@ public class MediaCreator
private static extern void UnityMediaCreator_writeAudio(float[] pcm, long frame, long microSec);
#endif

public static void InitAsMovWithNoAudio(string url, string codec, long width, long height)
public static void InitAsMovWithNoAudio(string url, string codec, long width, long height, string contentIdentifier = "")
{
#if UNITY_IOS
UnityMediaCreator_initAsMovWithNoAudio(url, codec, width, height);
UnityMediaCreator_initAsMovWithNoAudio(url, codec, width, height, contentIdentifier);
#endif
}

public static void InitAsMovWithAudio(string url, string codec, long width, long height, long channel, float samplingRate)
public static void InitAsMovWithAudio(string url, string codec, long width, long height, long channel, float samplingRate, string contentIdentifier = "")
{
#if UNITY_IOS
UnityMediaCreator_initAsMovWithAudio(url, codec, width, height, channel, samplingRate);
UnityMediaCreator_initAsMovWithAudio(url, codec, width, height, channel, samplingRate, contentIdentifier);
#endif
}

Expand Down
213 changes: 213 additions & 0 deletions Examples/UnityExample/Assets/Scenes/SampleScene.unity
Original file line number Diff line number Diff line change
Expand Up @@ -221,6 +221,7 @@ RectTransform:
- {fileID: 1091966527}
- {fileID: 1927427053}
- {fileID: 1563167747}
- {fileID: 1511568283}
m_Father: {fileID: 0}
m_RootOrder: 5
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
Expand Down Expand Up @@ -1747,6 +1748,218 @@ CanvasRenderer:
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1320822199}
m_CullTransparentMesh: 0
--- !u!1 &1347798594
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 1347798595}
- component: {fileID: 1347798597}
- component: {fileID: 1347798596}
m_Layer: 5
m_Name: Text
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!224 &1347798595
RectTransform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1347798594}
m_LocalRotation: {x: -0, y: -0, z: -0, w: 1}
m_LocalPosition: {x: 0, y: 0, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_Children: []
m_Father: {fileID: 1511568283}
m_RootOrder: 0
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
m_AnchorMin: {x: 0, y: 0}
m_AnchorMax: {x: 1, y: 1}
m_AnchoredPosition: {x: 0, y: 0}
m_SizeDelta: {x: 0, y: 0}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!114 &1347798596
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1347798594}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 5f7201a12d95ffc409449d95f23cf332, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Material: {fileID: 0}
m_Color: {r: 0.19607843, g: 0.19607843, b: 0.19607843, a: 1}
m_RaycastTarget: 1
m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []
m_FontData:
m_Font: {fileID: 10102, guid: 0000000000000000e000000000000000, type: 0}
m_FontSize: 32
m_FontStyle: 0
m_BestFit: 0
m_MinSize: 3
m_MaxSize: 40
m_Alignment: 4
m_AlignByGeometry: 0
m_RichText: 1
m_HorizontalOverflow: 0
m_VerticalOverflow: 0
m_LineSpacing: 1
m_Text: rec live photos
--- !u!222 &1347798597
CanvasRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1347798594}
m_CullTransparentMesh: 1
--- !u!1 &1511568282
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 1511568283}
- component: {fileID: 1511568286}
- component: {fileID: 1511568285}
- component: {fileID: 1511568284}
m_Layer: 5
m_Name: rec live phots
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!224 &1511568283
RectTransform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1511568282}
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 0, y: 0, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_Children:
- {fileID: 1347798595}
m_Father: {fileID: 14364497}
m_RootOrder: 6
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
m_AnchorMin: {x: 0.5, y: 0.5}
m_AnchorMax: {x: 0.5, y: 0.5}
m_AnchoredPosition: {x: -400, y: 0}
m_SizeDelta: {x: 480, y: 64}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!114 &1511568284
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1511568282}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 4e29b1a8efbd4b44bb3f3716e73f07ff, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Navigation:
m_Mode: 3
m_WrapAround: 0
m_SelectOnUp: {fileID: 0}
m_SelectOnDown: {fileID: 0}
m_SelectOnLeft: {fileID: 0}
m_SelectOnRight: {fileID: 0}
m_Transition: 1
m_Colors:
m_NormalColor: {r: 1, g: 1, b: 1, a: 1}
m_HighlightedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1}
m_PressedColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 1}
m_SelectedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1}
m_DisabledColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 0.5019608}
m_ColorMultiplier: 1
m_FadeDuration: 0.1
m_SpriteState:
m_HighlightedSprite: {fileID: 0}
m_PressedSprite: {fileID: 0}
m_SelectedSprite: {fileID: 0}
m_DisabledSprite: {fileID: 0}
m_AnimationTriggers:
m_NormalTrigger: Normal
m_HighlightedTrigger: Highlighted
m_PressedTrigger: Pressed
m_SelectedTrigger: Selected
m_DisabledTrigger: Disabled
m_Interactable: 1
m_TargetGraphic: {fileID: 1511568285}
m_OnClick:
m_PersistentCalls:
m_Calls:
- m_Target: {fileID: 668232124}
m_TargetAssemblyTypeName: RecordingController, Assembly-CSharp
m_MethodName: RecLivePhotos
m_Mode: 1
m_Arguments:
m_ObjectArgument: {fileID: 0}
m_ObjectArgumentAssemblyTypeName: UnityEngine.Object, UnityEngine
m_IntArgument: 0
m_FloatArgument: 0
m_StringArgument:
m_BoolArgument: 0
m_CallState: 2
--- !u!114 &1511568285
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1511568282}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Material: {fileID: 0}
m_Color: {r: 1, g: 1, b: 1, a: 1}
m_RaycastTarget: 1
m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []
m_Sprite: {fileID: 10905, guid: 0000000000000000f000000000000000, type: 0}
m_Type: 1
m_PreserveAspect: 0
m_FillCenter: 1
m_FillMethod: 4
m_FillAmount: 1
m_FillClockwise: 1
m_FillOrigin: 0
m_UseSpriteMesh: 0
m_PixelsPerUnitMultiplier: 1
--- !u!222 &1511568286
CanvasRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 1511568282}
m_CullTransparentMesh: 1
--- !u!1 &1563167746
GameObject:
m_ObjectHideFlags: 0
Expand Down
Loading

0 comments on commit a7849d8

Please sign in to comment.