Various improvements

This commit is contained in:
Ilya Laktyushin 2024-04-06 16:38:31 +04:00
parent 59982fe019
commit 698a74b6b6
3 changed files with 88 additions and 48 deletions

View File

@ -13,7 +13,7 @@ import FastBlur
import AccountContext
import ImageTransparency
public struct MediaEditorPlayerState {
public struct MediaEditorPlayerState: Equatable {
public struct Track: Equatable {
public enum Content: Equatable {
case video(frames: [UIImage], framesUpdateTimestamp: Double)

View File

@ -159,14 +159,30 @@ private final class MediaCutoutScreenComponent: Component {
return
}
controller.drawingView.isUserInteractionEnabled = true
if case .restore = controller.mode {
let overlayView = controller.overlayView
let backgroundView = controller.backgroundView
overlayView.alpha = 1.0
overlayView.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
backgroundView.alpha = 0.0
backgroundView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2)
self.updateBackgroundViews()
}
func updateBackgroundViews() {
guard let controller = self.environment?.controller() as? MediaCutoutScreen else {
return
}
let overlayView = controller.overlayView
let backgroundView = controller.backgroundView
let overlayAlpha: CGFloat
let backgroundAlpha: CGFloat
switch controller.mode {
case .restore:
overlayAlpha = 1.0
backgroundAlpha = 0.0
default:
overlayAlpha = 0.0
backgroundAlpha = 1.0
}
let transition = Transition(animation: .curve(duration: 0.2, curve: .easeInOut))
transition.setAlpha(view: overlayView, alpha: overlayAlpha)
transition.setAlpha(view: backgroundView, alpha: backgroundAlpha)
}
private var animatingOut = false
@ -211,14 +227,12 @@ private final class MediaCutoutScreenComponent: Component {
return
}
controller.drawingView.isUserInteractionEnabled = false
if case .restore = controller.mode {
let overlayView = controller.overlayView
let backgroundView = controller.backgroundView
overlayView.alpha = 0.0
overlayView.layer.animateAlpha(from: 1.0, to: 0.0, duration: 0.2)
backgroundView.alpha = 1.0
backgroundView.layer.animateAlpha(from: 0.0, to: 1.0, duration: 0.2)
}
let overlayView = controller.overlayView
let backgroundView = controller.backgroundView
let transition = Transition(animation: .curve(duration: 0.2, curve: .easeInOut))
transition.setAlpha(view: overlayView, alpha: 0.0)
transition.setAlpha(view: backgroundView, alpha: 1.0)
}
public func playDissolveAnimation() {
@ -489,6 +503,16 @@ final class MediaCutoutScreen: ViewController {
return result
}
func requestLayout(transition: Transition) {
if let layout = self.validLayout {
self.containerLayoutUpdated(layout: layout, forceUpdate: true, transition: transition)
if let view = self.componentHost.view as? MediaCutoutScreenComponent.View {
view.updateBackgroundViews()
}
}
}
func containerLayoutUpdated(layout: ContainerViewLayout, forceUpdate: Bool = false, animateOut: Bool = false, transition: Transition) {
guard let controller = self.controller else {
return
@ -565,7 +589,12 @@ final class MediaCutoutScreen: ViewController {
}
fileprivate let context: AccountContext
fileprivate let mode: Mode
public var mode: Mode {
didSet {
self.updateDrawingState()
self.node.requestLayout(transition: .easeInOut(duration: 0.2))
}
}
fileprivate let mediaEditor: MediaEditor
fileprivate let maskWrapperView: UIView
fileprivate let previewView: MediaEditorPreviewView
@ -610,13 +639,7 @@ final class MediaCutoutScreen: ViewController {
self.statusBar.statusBarStyle = .White
if let toolState = drawingView.appliedToolState {
if case .erase = mode {
drawingView.updateToolState(toolState.withUpdatedColor(DrawingColor(color: .black)))
} else if case .restore = mode {
drawingView.updateToolState(toolState.withUpdatedColor(DrawingColor(color: .white)))
}
}
self.updateDrawingState()
}
required init(coder aDecoder: NSCoder) {
@ -628,6 +651,16 @@ final class MediaCutoutScreen: ViewController {
super.displayNodeDidLoad()
}
private func updateDrawingState() {
if let toolState = self.drawingView.appliedToolState {
if case .erase = mode {
self.drawingView.updateToolState(toolState.withUpdatedColor(DrawingColor(color: .black)))
} else if case .restore = mode {
self.drawingView.updateToolState(toolState.withUpdatedColor(DrawingColor(color: .white)))
}
}
}
func requestDismiss(animated: Bool) {
self.dismissed()

View File

@ -245,8 +245,10 @@ final class MediaEditorScreenComponent: Component {
}
|> deliverOnMainQueue).start(next: { [weak self] playerState in
if let self {
self.playerState = playerState
self.updated()
if self.playerState != playerState {
self.playerState = playerState
self.updated()
}
}
})
@ -4421,6 +4423,7 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
fileprivate var drawingScreen: DrawingScreen?
fileprivate var stickerScreen: StickerPickerScreen?
fileprivate weak var cutoutScreen: MediaCutoutScreen?
private var defaultToEmoji = false
private var previousDrawingData: Data?
@ -4685,28 +4688,6 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
self.controller?.present(controller, in: .current)
self.animateOutToTool(tool: mode)
case .cutout, .cutoutErase, .cutoutRestore:
if self.isDisplayingTool != nil {
guard self.isDisplayingTool != mode else {
return
}
self.isDisplayingTool = mode
if let state = self.stickerMaskDrawingView?.appliedToolState {
switch mode {
case .cutoutErase:
self.stickerMaskDrawingView?.updateToolState(state.withUpdatedColor(DrawingColor(color: .black)))
case .cutoutRestore:
self.stickerMaskDrawingView?.updateToolState(state.withUpdatedColor(DrawingColor(color: .white)))
default:
break
}
}
self.requestUpdate(transition: .easeInOut(duration: 0.2))
return
}
guard let mediaEditor = self.mediaEditor, let stickerMaskDrawingView = self.stickerMaskDrawingView, let stickerBackgroundView = self.stickerBackgroundView else {
return
}
let cutoutMode: MediaCutoutScreen.Mode
switch mode {
case .cutout:
@ -4718,6 +4699,19 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
default:
cutoutMode = .cutout
}
if self.isDisplayingTool != nil {
guard self.isDisplayingTool != mode else {
return
}
self.isDisplayingTool = mode
self.cutoutScreen?.mode = cutoutMode
self.requestUpdate(transition: .easeInOut(duration: 0.2))
return
}
guard let mediaEditor = self.mediaEditor, let stickerMaskDrawingView = self.stickerMaskDrawingView, let stickerBackgroundView = self.stickerBackgroundView else {
return
}
let cutoutController = MediaCutoutScreen(
context: self.context,
mode: cutoutMode,
@ -4734,6 +4728,7 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
}
}
controller.present(cutoutController, in: .window(.root))
self.cutoutScreen = cutoutController
self.animateOutToTool(tool: mode, inPlace: true)
controller.hapticFeedback.impact(.medium)
@ -4776,6 +4771,12 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
if let drawingImage = stickerMaskDrawingView.drawingImage {
mediaEditor.setSegmentationMask(drawingImage)
}
if self.isDisplayingTool == .cutoutRestore && !stickerMaskDrawingView.internalState.canUndo && !controller.node.isCutout {
self.cutoutScreen?.mode = .erase
self.isDisplayingTool = .cutoutErase
self.requestLayout(forceUpdate: true, transition: .easeInOut(duration: 0.25))
}
} else if controller.node.isCutout {
let action = {
let snapshotView = self.previewView.snapshotView(afterScreenUpdates: false)
@ -4797,6 +4798,12 @@ public final class MediaEditorScreen: ViewController, UIDropInteractionDelegate
} else {
action()
}
if self.isDisplayingTool == .cutoutRestore {
self.cutoutScreen?.mode = .erase
self.isDisplayingTool = .cutoutErase
self.requestLayout(forceUpdate: true, transition: .easeInOut(duration: 0.25))
}
}
}
}