diff --git a/submodules/Components/PagerComponent/Sources/PagerComponent.swift b/submodules/Components/PagerComponent/Sources/PagerComponent.swift index de0f925063..b4c8c28192 100644 --- a/submodules/Components/PagerComponent/Sources/PagerComponent.swift +++ b/submodules/Components/PagerComponent/Sources/PagerComponent.swift @@ -14,7 +14,7 @@ open class PagerExternalTopPanelContainer: SparseContainerView { } public protocol PagerContentViewWithBackground: UIView { - func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, transition: ComponentTransition) + func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, externalTintMaskContainer: UIView?, transition: ComponentTransition) } public final class PagerComponentChildEnvironment: Equatable { @@ -206,6 +206,7 @@ public final class PagerComponent>? public let externalBottomPanelContainer: PagerExternalTopPanelContainer? + public let externalTintMaskContainer: UIView? public let panelStateUpdated: ((PagerComponentPanelState, ComponentTransition) -> Void)? public let isTopPanelExpandedUpdated: (Bool, ComponentTransition) -> Void public let isTopPanelHiddenUpdated: (Bool, ComponentTransition) -> Void @@ -228,6 +229,7 @@ public final class PagerComponent>?, externalBottomPanelContainer: PagerExternalTopPanelContainer?, + externalTintMaskContainer: UIView?, panelStateUpdated: ((PagerComponentPanelState, ComponentTransition) -> Void)?, isTopPanelExpandedUpdated: @escaping (Bool, ComponentTransition) -> Void, isTopPanelHiddenUpdated: @escaping (Bool, ComponentTransition) -> Void, @@ -249,6 +251,7 @@ public final class PagerComponent + let tintMaskContainer: UIView var scrollingPanelOffsetToTopEdge: CGFloat = 0.0 var scrollingPanelOffsetToBottomEdge: CGFloat = .greatestFiniteMagnitude var scrollingPanelOffsetFraction: CGFloat = 0.0 @@ -315,6 +322,7 @@ public final class PagerComponent) { self.view = view + self.tintMaskContainer = UIView() } } @@ -847,6 +855,9 @@ public final class PagerComponent CGFloat? { switch self { case .iPhoneX, .iPhoneXSMax, .iPhoneXr, .iPhone12Mini, .iPhone12, .iPhone12ProMax, .iPhone13Mini, .iPhone13, .iPhone13Pro, .iPhone13ProMax, .iPhone14Pro, .iPhone14ProMax, .iPhone16Pro, .iPhone16ProMax: - return inLandscape ? 21.0 : 34.0 + if #available(iOS 26.0, *) { + return 20.0 + } else { + return inLandscape ? 21.0 : 34.0 + } case .iPhone14ProZoomed: return inLandscape ? 21.0 : 28.0 case .iPhone14ProMaxZoomed: diff --git a/submodules/Display/Source/NavigationBar.swift b/submodules/Display/Source/NavigationBar.swift index 3cb91fded3..45b6568209 100644 --- a/submodules/Display/Source/NavigationBar.swift +++ b/submodules/Display/Source/NavigationBar.swift @@ -312,6 +312,7 @@ open class BlurredBackgroundView: UIView { private var _color: UIColor? private var enableBlur: Bool + private var customBlurRadius: CGFloat? public private(set) var effectView: UIVisualEffectView? private let backgroundView: UIView @@ -326,9 +327,10 @@ open class BlurredBackgroundView: UIView { } } - public init(color: UIColor?, enableBlur: Bool = true) { + public init(color: UIColor?, enableBlur: Bool = true, customBlurRadius: CGFloat? = nil) { self._color = nil self.enableBlur = enableBlur + self.customBlurRadius = customBlurRadius self.backgroundView = UIView() @@ -349,7 +351,6 @@ open class BlurredBackgroundView: UIView { if let color = self._color, self.enableBlur && !sharedIsReduceTransparencyEnabled && ((color.alpha > .ulpOfOne && color.alpha < 0.95) || forceKeepBlur) { if self.effectView == nil { let effectView = UIVisualEffectView(effect: UIBlurEffect(style: .light)) - //effectView.isHidden = true for subview in effectView.subviews { if subview.description.contains("VisualEffectSubview") { @@ -373,6 +374,9 @@ open class BlurredBackgroundView: UIView { if !allowedKeys.contains(filterName) { return false } + if let customBlurRadius = self.customBlurRadius, filterName == "gaussianBlur" { + filter.setValue(customBlurRadius as NSNumber, forKey: "inputRadius") + } return true } } diff --git a/submodules/TabBarUI/Sources/TabBarContollerNode.swift b/submodules/TabBarUI/Sources/TabBarContollerNode.swift index 6b6921fd92..064f74ffd3 100644 --- a/submodules/TabBarUI/Sources/TabBarContollerNode.swift +++ b/submodules/TabBarUI/Sources/TabBarContollerNode.swift @@ -179,9 +179,9 @@ final class TabBarControllerNode: ASDisplayNode { if bottomInset == 0.0 { bottomInset = 8.0 } else { - bottomInset = max(bottomInset - 13.0, 8.0) + bottomInset = max(bottomInset, 8.0) } - let sideInset: CGFloat = 21.0 + let sideInset: CGFloat = 20.0 var selectedId: AnyHashable? if self.selectedIndex < self.tabBarItems.count { diff --git a/submodules/TelegramPresentationData/Sources/DefaultDayPresentationTheme.swift b/submodules/TelegramPresentationData/Sources/DefaultDayPresentationTheme.swift index c7af0c0ed6..35dff9586b 100644 --- a/submodules/TelegramPresentationData/Sources/DefaultDayPresentationTheme.swift +++ b/submodules/TelegramPresentationData/Sources/DefaultDayPresentationTheme.swift @@ -941,7 +941,7 @@ public func makeDefaultDayPresentationTheme(extendingThemeReference: Presentatio let inputPanel = PresentationThemeChatInputPanel( panelBackgroundColor: rootNavigationBar.blurredBackgroundColor, panelBackgroundColorNoWallpaper: UIColor(rgb: 0xffffff), - panelSeparatorColor: UIColor(rgb: 0xb2b2b2), + panelSeparatorColor: UIColor(white: 1.0, alpha: 0.5), panelControlAccentColor: defaultDayAccentColor, panelControlColor: UIColor(rgb: 0x858e99), panelControlDisabledColor: UIColor(rgb: 0x727b87, alpha: 0.5), diff --git a/submodules/TelegramUI/Components/AvatarEditorScreen/Sources/AvatarEditorScreen.swift b/submodules/TelegramUI/Components/AvatarEditorScreen/Sources/AvatarEditorScreen.swift index bcce0831af..5e6b6f25fd 100644 --- a/submodules/TelegramUI/Components/AvatarEditorScreen/Sources/AvatarEditorScreen.swift +++ b/submodules/TelegramUI/Components/AvatarEditorScreen/Sources/AvatarEditorScreen.swift @@ -1219,6 +1219,7 @@ final class AvatarEditorScreenComponent: Component { defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/Chat/ChatRecordingViewOnceButtonNode/Sources/ChatRecordingViewOnceButtonNode.swift b/submodules/TelegramUI/Components/Chat/ChatRecordingViewOnceButtonNode/Sources/ChatRecordingViewOnceButtonNode.swift index d62b84c0c2..e61edcd038 100644 --- a/submodules/TelegramUI/Components/Chat/ChatRecordingViewOnceButtonNode/Sources/ChatRecordingViewOnceButtonNode.swift +++ b/submodules/TelegramUI/Components/Chat/ChatRecordingViewOnceButtonNode/Sources/ChatRecordingViewOnceButtonNode.swift @@ -99,7 +99,7 @@ public final class ChatRecordingViewOnceButtonNode: HighlightTrackingButtonNode let backgroundFrame = CGRect(origin: CGPoint(x: floorToScreenPixels(size.width / 2.0 - innerSize.width / 2.0), y: floorToScreenPixels(size.height / 2.0 - innerSize.height / 2.0)), size: innerSize) self.backgroundView.frame = backgroundFrame - self.backgroundView.update(size: backgroundFrame.size, cornerRadius: backgroundFrame.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: .immediate) + self.backgroundView.update(size: backgroundFrame.size, cornerRadius: backgroundFrame.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: .immediate) if let iconImage = self.iconNode.image { let iconFrame = CGRect(origin: CGPoint(x: floorToScreenPixels(size.width / 2.0 - iconImage.size.width / 2.0), y: floorToScreenPixels(size.height / 2.0 - iconImage.size.height / 2.0)), size: iconImage.size) diff --git a/submodules/TelegramUI/Components/Chat/ChatTextInputActionButtonsNode/Sources/ChatTextInputActionButtonsNode.swift b/submodules/TelegramUI/Components/Chat/ChatTextInputActionButtonsNode/Sources/ChatTextInputActionButtonsNode.swift index 75380ef626..8f94a44ff8 100644 --- a/submodules/TelegramUI/Components/Chat/ChatTextInputActionButtonsNode/Sources/ChatTextInputActionButtonsNode.swift +++ b/submodules/TelegramUI/Components/Chat/ChatTextInputActionButtonsNode/Sources/ChatTextInputActionButtonsNode.swift @@ -334,7 +334,7 @@ public final class ChatTextInputActionButtonsNode: ASDisplayNode, ChatSendMessag } transition.updateFrame(view: self.micButtonBackgroundView, frame: CGRect(origin: CGPoint(), size: size)) - self.micButtonBackgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: ComponentTransition(transition)) + self.micButtonBackgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: ComponentTransition(transition)) transition.updateFrame(layer: self.micButton.layer, frame: CGRect(origin: CGPoint(), size: size)) self.micButton.layoutItems() @@ -349,7 +349,7 @@ public final class ChatTextInputActionButtonsNode: ASDisplayNode, ChatSendMessag transition.updateFrame(view: self.expandMediaInputButton, frame: CGRect(origin: CGPoint(), size: size)) transition.updateFrame(view: self.expandMediaInputButtonBackgroundView, frame: CGRect(origin: CGPoint(), size: size)) - self.expandMediaInputButtonBackgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: ComponentTransition(transition)) + self.expandMediaInputButtonBackgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: ComponentTransition(transition)) if let image = self.expandMediaInputButtonIcon.image { let expandIconFrame = CGRect(origin: CGPoint(x: floor((size.width - image.size.width) * 0.5), y: floor((size.height - image.size.height) * 0.5)), size: image.size) transition.updatePosition(layer: self.expandMediaInputButtonIcon.layer, position: expandIconFrame.center) diff --git a/submodules/TelegramUI/Components/Chat/ChatTextInputPanelNode/Sources/ChatTextInputPanelNode.swift b/submodules/TelegramUI/Components/Chat/ChatTextInputPanelNode/Sources/ChatTextInputPanelNode.swift index 42145a2428..204e7a6c10 100644 --- a/submodules/TelegramUI/Components/Chat/ChatTextInputPanelNode/Sources/ChatTextInputPanelNode.swift +++ b/submodules/TelegramUI/Components/Chat/ChatTextInputPanelNode/Sources/ChatTextInputPanelNode.swift @@ -2213,7 +2213,7 @@ public class ChatTextInputPanelNode: ChatInputPanelNode, ASEditableTextNodeDeleg let alphaTransitionIn: ContainedViewLayoutTransition = transition.isAnimated ? ContainedViewLayoutTransition.animated(duration: 0.15, curve: .easeInOut) : .immediate let alphaTransitionOut: ContainedViewLayoutTransition = transition.isAnimated ? ContainedViewLayoutTransition.animated(duration: 0.2, curve: .easeInOut) : .immediate - let accessoryPanelAnimationBlurRadius: CGFloat = 10.0 + let accessoryPanelAnimationBlurRadius: CGFloat = 20.0 var removedAccessoryPanelView: UIView? if let currentAccessoryPanel = self.accessoryPanel, currentAccessoryPanel.component.id != accessoryPanel?.id { @@ -2334,7 +2334,7 @@ public class ChatTextInputPanelNode: ChatInputPanelNode, ASEditableTextNodeDeleg transition.updateFrame(node: self.textInputContainer, frame: textInputContainerBackgroundFrame) transition.updateFrame(view: self.textInputContainerBackgroundView, frame: CGRect(origin: CGPoint(), size: textInputContainerBackgroundFrame.size)) - self.textInputContainerBackgroundView.update(size: textInputContainerBackgroundFrame.size, cornerRadius: floor(minimalInputHeight * 0.5), isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: ComponentTransition(transition)) + self.textInputContainerBackgroundView.update(size: textInputContainerBackgroundFrame.size, cornerRadius: floor(minimalInputHeight * 0.5), isDark: interfaceState.theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: ComponentTransition(transition)) if let removedAccessoryPanelView { if let removedAccessoryPanelView = removedAccessoryPanelView as? ChatInputAccessoryPanelView { @@ -2625,7 +2625,7 @@ public class ChatTextInputPanelNode: ChatInputPanelNode, ASEditableTextNodeDeleg let attachmentButtonFrame = CGRect(origin: CGPoint(x: attachmentButtonX, y: textInputFrame.maxY - 40.0), size: CGSize(width: 40.0, height: 40.0)) self.attachmentButtonBackground.frame = CGRect(origin: CGPoint(), size: attachmentButtonFrame.size) - self.attachmentButtonBackground.update(size: attachmentButtonFrame.size, cornerRadius: attachmentButtonFrame.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: isEditingMedia ? .init(kind: .custom, color: interfaceState.theme.chat.inputPanel.actionControlFillColor) : .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: ComponentTransition(transition)) + self.attachmentButtonBackground.update(size: attachmentButtonFrame.size, cornerRadius: attachmentButtonFrame.height * 0.5, isDark: interfaceState.theme.overallDarkAppearance, tintColor: isEditingMedia ? .init(kind: .custom, color: interfaceState.theme.chat.inputPanel.actionControlFillColor) : .init(kind: .panel, color: interfaceState.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: ComponentTransition(transition)) transition.updateFrame(layer: self.attachmentButton.layer, frame: attachmentButtonFrame) transition.updateFrame(node: self.attachmentButtonDisabledNode, frame: self.attachmentButton.frame) diff --git a/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/BUILD b/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/BUILD index b5b70dc871..6c8e0d451e 100644 --- a/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/BUILD +++ b/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/BUILD @@ -41,6 +41,7 @@ swift_library( "//submodules/TelegramUI/Components/LegacyMessageInputPanelInputView:LegacyMessageInputPanelInputView", "//submodules/AttachmentTextInputPanelNode", "//submodules/TelegramUI/Components/BatchVideoRendering", + "//submodules/TelegramUI/Components/GlassBackgroundComponent", ], visibility = [ "//visibility:public", diff --git a/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/Sources/ChatEntityKeyboardInputNode.swift b/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/Sources/ChatEntityKeyboardInputNode.swift index 72a31c25c4..0a98d73031 100644 --- a/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/Sources/ChatEntityKeyboardInputNode.swift +++ b/submodules/TelegramUI/Components/ChatEntityKeyboardInputNode/Sources/ChatEntityKeyboardInputNode.swift @@ -31,6 +31,7 @@ import Pasteboard import EntityKeyboardGifContent import LegacyMessageInputPanelInputView import AttachmentTextInputPanelNode +import GlassBackgroundComponent public final class EmptyInputView: UIView, UIInputViewAudioFeedback { public var enableInputClicksWhenVisible: Bool { @@ -168,6 +169,7 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { hasStickers: Bool = true, hasGifs: Bool = true, hideBackground: Bool = false, + maskEdge: Bool = false, forceHasPremium: Bool = false, sendGif: ((FileMediaReference, UIView, CGRect, Bool, Bool) -> Bool)? ) -> Signal { @@ -187,7 +189,8 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { chatPeerId: chatPeerId, hasSearch: hasSearch, forceHasPremium: forceHasPremium, - hideBackground: hideBackground + hideBackground: hideBackground, + maskEdge: maskEdge ) let stickerNamespaces: [ItemCollectionId.Namespace] = [Namespaces.ItemCollection.CloudStickerPacks] @@ -414,6 +417,14 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { return self.externalTopPanelContainerImpl } + private let clippingView: UIView + private var backgroundView: BlurredBackgroundView? + private var backgroundTintView: UIImageView? + private var backgroundChromeView: UIImageView? + private var backgroundTintMaskView: UIView? + private var backgroundTintMaskContentView: UIView? + private var externalBackground: EmojiPagerContentComponent.ExternalBackground? + public var switchToTextInput: (() -> Void)? private var currentState: (width: CGFloat, leftInset: CGFloat, rightInset: CGFloat, bottomInset: CGFloat, standardInputHeight: CGFloat, inputHeight: CGFloat, maximumHeight: CGFloat, inputPanelHeight: CGFloat, interfaceState: ChatPresentationInterfaceState, layoutMetrics: LayoutMetrics, deviceMetrics: DeviceMetrics, isVisible: Bool, isExpanded: Bool)? @@ -476,6 +487,10 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { self.interaction = interaction + self.clippingView = UIView() + self.clippingView.clipsToBounds = true + self.clippingView.layer.cornerRadius = 20.0 + self.entityKeyboardView = ComponentHostView() super.init() @@ -485,7 +500,41 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { self.topBackgroundExtension = 34.0 self.followsDefaultHeight = true - self.view.addSubview(self.entityKeyboardView) + if "".isEmpty { + let backgroundView = BlurredBackgroundView(color: .black, enableBlur: true) + self.backgroundView = backgroundView + self.view.addSubview(backgroundView) + + let backgroundTintView = UIImageView() + self.backgroundTintView = backgroundTintView + self.view.addSubview(backgroundTintView) + + let backgroundTintMaskView = UIView() + backgroundTintMaskView.backgroundColor = .white + self.backgroundTintMaskView = backgroundTintMaskView + if let filter = CALayer.luminanceToAlpha() { + backgroundTintMaskView.layer.filters = [filter] + } + backgroundTintView.mask = backgroundTintMaskView + + let backgroundTintMaskContentView = UIView() + backgroundTintMaskView.addSubview(backgroundTintMaskContentView) + self.backgroundTintMaskContentView = backgroundTintMaskContentView + + let backgroundChromeView = UIImageView() + self.backgroundChromeView = backgroundChromeView + + self.externalBackground = EmojiPagerContentComponent.ExternalBackground( + effectContainerView: backgroundTintMaskContentView + ) + } + + self.clippingView.addSubview(self.entityKeyboardView) + self.view.addSubview(self.clippingView) + + if let backgroundChromeView = self.backgroundChromeView { + self.view.addSubview(backgroundChromeView) + } self.externalTopPanelContainerImpl = PagerExternalTopPanelContainer() @@ -1162,7 +1211,7 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { chatPeerId: chatPeerId, peekBehavior: stickerPeekBehavior, customLayout: nil, - externalBackground: nil, + externalBackground: self.externalBackground, externalExpansionView: nil, customContentView: nil, useOpaqueTheme: self.useOpaqueTheme, @@ -1509,7 +1558,7 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { chatPeerId: chatPeerId, peekBehavior: stickerPeekBehavior, customLayout: nil, - externalBackground: nil, + externalBackground: self.externalBackground, externalExpansionView: nil, customContentView: nil, useOpaqueTheme: self.useOpaqueTheme, @@ -1739,6 +1788,22 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { let _ = self.updateLayout(width: width, leftInset: leftInset, rightInset: rightInset, bottomInset: bottomInset, standardInputHeight: standardInputHeight, inputHeight: inputHeight, maximumHeight: maximumHeight, inputPanelHeight: inputPanelHeight, transition: .immediate, interfaceState: interfaceState, layoutMetrics: layoutMetrics, deviceMetrics: deviceMetrics, isVisible: isVisible, isExpanded: isExpanded) } + override public func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? { + if let result = super.hitTest(point, with: event) { + return result + } + + if let backgroundView = self.backgroundView, backgroundView.frame.contains(point) { + for subview in self.view.subviews.reversed() { + if let result = subview.hitTest(self.view.convert(point, to: subview), with: event) { + return result + } + } + } + + return nil + } + public override func updateLayout(width: CGFloat, leftInset: CGFloat, rightInset: CGFloat, bottomInset: CGFloat, standardInputHeight: CGFloat, inputHeight: CGFloat, maximumHeight: CGFloat, inputPanelHeight: CGFloat, transition: ContainedViewLayoutTransition, interfaceState: ChatPresentationInterfaceState, layoutMetrics: LayoutMetrics, deviceMetrics: DeviceMetrics, isVisible: Bool, isExpanded: Bool) -> (CGFloat, CGFloat) { self.currentState = (width, leftInset, rightInset, bottomInset, standardInputHeight, inputHeight, maximumHeight, inputPanelHeight, interfaceState, layoutMetrics, deviceMetrics, isVisible, isExpanded) @@ -1849,7 +1914,8 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { defaultToEmojiTab: self.defaultToEmojiTab, externalTopPanelContainer: self.externalTopPanelContainerImpl, externalBottomPanelContainer: nil, - displayTopPanelBackground: self.opaqueTopPanelBackground ? .opaque : .none, + externalTintMaskContainer: self.backgroundTintMaskContentView, + displayTopPanelBackground: self.opaqueTopPanelBackground ? .opaque : .blur, topPanelExtensionUpdated: { [weak self] topPanelExtension, transition in guard let strongSelf = self else { return @@ -1939,7 +2005,52 @@ public final class ChatEntityKeyboardInputNode: ChatInputNode { environment: {}, containerSize: CGSize(width: width, height: expandedHeight) ) - transition.updateFrame(view: self.entityKeyboardView, frame: CGRect(origin: CGPoint(x: 0.0, y: 0.0), size: entityKeyboardSize)) + + var clippingFrame = CGRect(origin: CGPoint(), size: entityKeyboardSize) + clippingFrame.size.height += 32.0 + + var entityKeyboardSizeFrame = CGRect(origin: CGPoint(), size: entityKeyboardSize) + if self.hideInput { + clippingFrame.size.height += self.topBackgroundExtension + clippingFrame.origin.y -= self.topBackgroundExtension + entityKeyboardSizeFrame.origin.y += self.topBackgroundExtension + } + + transition.updateFrame(view: self.entityKeyboardView, frame: entityKeyboardSizeFrame) + + transition.updateFrame(view: self.clippingView, frame: clippingFrame) + + if let backgroundView = self.backgroundView, let backgroundTintView = self.backgroundTintView, let backgroundTintMaskView = self.backgroundTintMaskView, let backgroundTintMaskContentView = self.backgroundTintMaskContentView, let backgroundChromeView = self.backgroundChromeView { + var backgroundFrame = CGRect(origin: CGPoint(x: 0.0, y: 0.0), size: entityKeyboardSize) + if self.hideInput { + backgroundFrame.size.height += self.topBackgroundExtension + backgroundFrame.origin.y -= self.topBackgroundExtension + } + backgroundFrame.size.height += 32.0 + + if backgroundChromeView.image == nil { + backgroundChromeView.image = GlassBackgroundView.generateForegroundImage(size: CGSize(width: 20.0 * 2.0, height: 20.0 * 2.0), isDark: interfaceState.theme.overallDarkAppearance, fillColor: .clear) + } + if backgroundTintView.image == nil { + backgroundTintView.image = generateStretchableFilledCircleImage(diameter: 20.0 * 2.0, color: .white)?.withRenderingMode(.alwaysTemplate) + } + backgroundTintView.tintColor = interfaceState.theme.chat.inputMediaPanel.backgroundColor + + transition.updateFrame(view: backgroundView, frame: backgroundFrame) + backgroundView.updateColor(color: .clear, forceKeepBlur: true, transition: .immediate) + backgroundView.update(size: backgroundFrame.size, cornerRadius: 20.0, maskedCorners: [.layerMinXMinYCorner, .layerMaxXMinYCorner], transition: transition) + + transition.updateFrame(view: backgroundChromeView, frame: backgroundFrame.insetBy(dx: -1.0, dy: 0.0)) + + var backgroundTintMaskContentFrame = CGRect(origin: CGPoint(), size: backgroundFrame.size) + if self.hideInput { + backgroundTintMaskContentFrame.origin.y += self.topBackgroundExtension + } + transition.updateFrame(view: backgroundTintView, frame: backgroundFrame) + + transition.updateFrame(view: backgroundTintMaskView, frame: CGRect(origin: CGPoint(), size: backgroundFrame.size)) + transition.updateFrame(view: backgroundTintMaskContentView, frame: backgroundTintMaskContentFrame) + } let layoutTime = CFAbsoluteTimeGetCurrent() - startTime if layoutTime > 0.1 { diff --git a/submodules/TelegramUI/Components/ChatTextInputMediaRecordingButton/Sources/ChatTextInputMediaRecordingButton.swift b/submodules/TelegramUI/Components/ChatTextInputMediaRecordingButton/Sources/ChatTextInputMediaRecordingButton.swift index e2d2c0b811..7f1ab9ea04 100644 --- a/submodules/TelegramUI/Components/ChatTextInputMediaRecordingButton/Sources/ChatTextInputMediaRecordingButton.swift +++ b/submodules/TelegramUI/Components/ChatTextInputMediaRecordingButton/Sources/ChatTextInputMediaRecordingButton.swift @@ -467,7 +467,7 @@ public final class ChatTextInputMediaRecordingButton: TGModernConversationInputM tintColor = UIColor(white: 0.0, alpha: 0.5) } else { isDark = self.theme.overallDarkAppearance - tintColor = self.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65) + tintColor = self.theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7) } let view = WrapperBlurrredBackgroundView(size: CGSize(width: 40.0, height: 72.0), isDark: isDark, tintColor: tintColor) diff --git a/submodules/TelegramUI/Components/EmojiStatusSelectionComponent/Sources/EmojiStatusSelectionComponent.swift b/submodules/TelegramUI/Components/EmojiStatusSelectionComponent/Sources/EmojiStatusSelectionComponent.swift index 9728c603d0..01d0a629d1 100644 --- a/submodules/TelegramUI/Components/EmojiStatusSelectionComponent/Sources/EmojiStatusSelectionComponent.swift +++ b/submodules/TelegramUI/Components/EmojiStatusSelectionComponent/Sources/EmojiStatusSelectionComponent.swift @@ -187,6 +187,7 @@ public final class EmojiStatusSelectionComponent: Component { defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentComponent.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentComponent.swift index d861a02f6a..73f5c6ea89 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentComponent.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentComponent.swift @@ -623,6 +623,7 @@ public final class EmojiPagerContentComponent: Component { public let searchState: SearchState public let warpContentsOnEdges: Bool public let hideBackground: Bool + public let maskEdge: Bool public let displaySearchWithPlaceholder: String? public let searchCategories: EmojiSearchCategories? public let searchInitiallyHidden: Bool @@ -648,6 +649,7 @@ public final class EmojiPagerContentComponent: Component { searchState: SearchState, warpContentsOnEdges: Bool, hideBackground: Bool, + maskEdge: Bool, displaySearchWithPlaceholder: String?, searchCategories: EmojiSearchCategories?, searchInitiallyHidden: Bool, @@ -672,6 +674,7 @@ public final class EmojiPagerContentComponent: Component { self.searchState = searchState self.warpContentsOnEdges = warpContentsOnEdges self.hideBackground = hideBackground + self.maskEdge = maskEdge self.displaySearchWithPlaceholder = displaySearchWithPlaceholder self.searchCategories = searchCategories self.searchInitiallyHidden = searchInitiallyHidden @@ -699,6 +702,7 @@ public final class EmojiPagerContentComponent: Component { searchState: searchState, warpContentsOnEdges: self.warpContentsOnEdges, hideBackground: self.hideBackground, + maskEdge: self.maskEdge, displaySearchWithPlaceholder: self.displaySearchWithPlaceholder, searchCategories: self.searchCategories, searchInitiallyHidden: self.searchInitiallyHidden, @@ -727,6 +731,7 @@ public final class EmojiPagerContentComponent: Component { searchState: searchState, warpContentsOnEdges: self.warpContentsOnEdges, hideBackground: self.hideBackground, + maskEdge: self.maskEdge, displaySearchWithPlaceholder: self.displaySearchWithPlaceholder, searchCategories: self.searchCategories, searchInitiallyHidden: self.searchInitiallyHidden, @@ -755,6 +760,7 @@ public final class EmojiPagerContentComponent: Component { searchState: searchState, warpContentsOnEdges: self.warpContentsOnEdges, hideBackground: self.hideBackground, + maskEdge: self.maskEdge, displaySearchWithPlaceholder: self.displaySearchWithPlaceholder, searchCategories: self.searchCategories, searchInitiallyHidden: self.searchInitiallyHidden, @@ -811,6 +817,9 @@ public final class EmojiPagerContentComponent: Component { if lhs.hideBackground != rhs.hideBackground { return false } + if lhs.maskEdge != rhs.maskEdge { + return false + } if lhs.displaySearchWithPlaceholder != rhs.displaySearchWithPlaceholder { return false } @@ -4016,12 +4025,12 @@ public final class EmojiPagerContentComponent: Component { self.state?.updated(transition: ComponentTransition(animation: .curve(duration: 0.4, curve: .spring)).withUserData(ContentAnimation(type: .groupExpanded(id: groupId)))) } - public func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, transition: ComponentTransition) { + public func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, externalTintMaskContainer: UIView?, transition: ComponentTransition) { guard let component = self.component, let keyboardChildEnvironment = self.keyboardChildEnvironment, let pagerEnvironment = self.pagerEnvironment else { return } - if let externalBackground = component.inputInteractionHolder.inputInteraction?.externalBackground, let effectContainerView = externalBackground.effectContainerView { + if let effectContainerView = externalTintMaskContainer { let mirrorContentClippingView: UIView if let current = self.mirrorContentClippingView { mirrorContentClippingView = current @@ -4066,17 +4075,19 @@ public final class EmojiPagerContentComponent: Component { if component.hideBackground { self.backgroundView.isHidden = true - let maskLayer: FadingMaskLayer - if let current = self.fadingMaskLayer { - maskLayer = current - } else { - maskLayer = FadingMaskLayer() - self.fadingMaskLayer = maskLayer + if component.maskEdge { + let maskLayer: FadingMaskLayer + if let current = self.fadingMaskLayer { + maskLayer = current + } else { + maskLayer = FadingMaskLayer() + self.fadingMaskLayer = maskLayer + } + if self.layer.mask == nil { + self.layer.mask = maskLayer + } + maskLayer.frame = CGRect(origin: CGPoint(x: 0.0, y: floorToScreenPixels((topPanelHeight - 34.0) * 0.75)), size: backgroundFrame.size) } - if self.layer.mask == nil { - self.layer.mask = maskLayer - } - maskLayer.frame = CGRect(origin: CGPoint(x: 0.0, y: floorToScreenPixels((topPanelHeight - 34.0) * 0.75)), size: backgroundFrame.size) } else if component.warpContentsOnEdges { self.backgroundView.isHidden = true } else { diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentSignals.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentSignals.swift index 65d4422d7a..c16e3501b5 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentSignals.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiPagerContentSignals.swift @@ -65,7 +65,8 @@ public extension EmojiPagerContentComponent { hasRecent: Bool = true, forceHasPremium: Bool = false, premiumIfSavedMessages: Bool = true, - hideBackground: Bool = false + hideBackground: Bool = false, + maskEdge: Bool = false ) -> Signal { let premiumConfiguration = PremiumConfiguration.with(appConfiguration: context.currentAppConfiguration.with { $0 }) let isPremiumDisabled = premiumConfiguration.isPremiumDisabled @@ -1596,6 +1597,7 @@ public extension EmojiPagerContentComponent { searchState: .empty(hasResults: false), warpContentsOnEdges: warpContentsOnEdges, hideBackground: hideBackground, + maskEdge: maskEdge, displaySearchWithPlaceholder: displaySearchWithPlaceholder, searchCategories: searchCategories, searchInitiallyHidden: searchInitiallyHidden, @@ -1632,7 +1634,8 @@ public extension EmojiPagerContentComponent { hasAdd: Bool = false, searchIsPlaceholderOnly: Bool = true, subject: StickersSubject = .chatStickers, - hideBackground: Bool = false + hideBackground: Bool = false, + maskEdge: Bool = false ) -> Signal { let premiumConfiguration = PremiumConfiguration.with(appConfiguration: context.currentAppConfiguration.with { $0 }) let isPremiumDisabled = premiumConfiguration.isPremiumDisabled @@ -2178,6 +2181,7 @@ public extension EmojiPagerContentComponent { searchState: .empty(hasResults: false), warpContentsOnEdges: warpContentsOnEdges, hideBackground: hideBackground, + maskEdge: maskEdge, displaySearchWithPlaceholder: hasSearch ? strings.StickersSearch_SearchStickersPlaceholder : nil, searchCategories: searchCategories, searchInitiallyHidden: true, @@ -2197,7 +2201,8 @@ public extension EmojiPagerContentComponent { animationCache: AnimationCache, animationRenderer: MultiAnimationRenderer, hasSearch: Bool, - hideBackground: Bool = false + hideBackground: Bool = false, + maskEdge: Bool = false ) -> Signal { let premiumConfiguration = PremiumConfiguration.with(appConfiguration: context.currentAppConfiguration.with { $0 }) let isPremiumDisabled = premiumConfiguration.isPremiumDisabled @@ -2330,6 +2335,7 @@ public extension EmojiPagerContentComponent { searchState: .empty(hasResults: false), warpContentsOnEdges: warpContentsOnEdges, hideBackground: hideBackground, + maskEdge: maskEdge, displaySearchWithPlaceholder: hasSearch ? strings.StickersSearch_SearchStickersPlaceholder : nil, searchCategories: searchCategories, searchInitiallyHidden: true, diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiSearchContent.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiSearchContent.swift index 7e04ed8f6e..1366bfafd4 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiSearchContent.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EmojiSearchContent.swift @@ -469,6 +469,7 @@ public final class EmojiSearchContent: ASDisplayNode, EntitySearchContainerNode searchState: .empty(hasResults: false), warpContentsOnEdges: false, hideBackground: false, + maskEdge: false, displaySearchWithPlaceholder: self.presentationData.strings.EmojiSearch_SearchEmojiPlaceholder, searchCategories: nil, searchInitiallyHidden: false, @@ -509,6 +510,7 @@ public final class EmojiSearchContent: ASDisplayNode, EntitySearchContainerNode defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboard.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboard.swift index 1935765c7e..5916d871fa 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboard.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboard.swift @@ -106,6 +106,7 @@ public final class EntityKeyboardComponent: Component { public let defaultToEmojiTab: Bool public let externalTopPanelContainer: PagerExternalTopPanelContainer? public let externalBottomPanelContainer: PagerExternalTopPanelContainer? + public let externalTintMaskContainer: UIView? public let displayTopPanelBackground: DisplayTopPanelBackground public let topPanelExtensionUpdated: (CGFloat, ComponentTransition) -> Void public let topPanelScrollingOffset: (CGFloat, ComponentTransition) -> Void @@ -141,6 +142,7 @@ public final class EntityKeyboardComponent: Component { defaultToEmojiTab: Bool, externalTopPanelContainer: PagerExternalTopPanelContainer?, externalBottomPanelContainer: PagerExternalTopPanelContainer?, + externalTintMaskContainer: UIView?, displayTopPanelBackground: DisplayTopPanelBackground, topPanelExtensionUpdated: @escaping (CGFloat, ComponentTransition) -> Void, topPanelScrollingOffset: @escaping (CGFloat, ComponentTransition) -> Void, @@ -175,6 +177,7 @@ public final class EntityKeyboardComponent: Component { self.defaultToEmojiTab = defaultToEmojiTab self.externalTopPanelContainer = externalTopPanelContainer self.externalBottomPanelContainer = externalBottomPanelContainer + self.externalTintMaskContainer = externalTintMaskContainer self.displayTopPanelBackground = displayTopPanelBackground self.topPanelExtensionUpdated = topPanelExtensionUpdated self.topPanelScrollingOffset = topPanelScrollingOffset @@ -716,6 +719,12 @@ public final class EntityKeyboardComponent: Component { forceUpdate = true } + var bottomPanelContainerInsets = component.containerInsets + if bottomPanelContainerInsets.left == 0.0 && bottomPanelContainerInsets.bottom != 0.0 { + bottomPanelContainerInsets.left += 16.0 + bottomPanelContainerInsets.right += 16.0 + } + let isContentInFocus = component.isContentInFocus && self.searchComponent == nil let pagerSize = self.pagerView.update( transition: transition, @@ -732,19 +741,20 @@ public final class EntityKeyboardComponent: Component { topPanel: AnyComponent(EntityKeyboardTopContainerPanelComponent( theme: component.theme, overflowHeight: component.hiddenInputHeight, - topInset: 12.0, + topInset: 6.0, displayBackground: component.externalTopPanelContainer != nil ? .none : component.displayTopPanelBackground )), externalTopPanelContainer: component.externalTopPanelContainer, bottomPanel: component.displayBottomPanel ? AnyComponent(EntityKeyboardBottomPanelComponent( theme: component.theme, - containerInsets: component.containerInsets, + containerInsets: bottomPanelContainerInsets, deleteBackwards: { [weak self] in self?.component?.emojiContent?.inputInteractionHolder.inputInteraction?.deleteBackwards?() AudioServicesPlaySystemSound(0x451) } )) : nil, externalBottomPanelContainer: component.externalBottomPanelContainer, + externalTintMaskContainer: component.externalTintMaskContainer, panelStateUpdated: { [weak self] panelState, transition in guard let strongSelf = self else { return diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardBottomPanelComponent.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardBottomPanelComponent.swift index 73390b8127..d81a344101 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardBottomPanelComponent.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardBottomPanelComponent.swift @@ -163,7 +163,7 @@ final class EntityKeyboardBottomPanelComponent: Component { private var component: EntityKeyboardBottomPanelComponent? override init(frame: CGRect) { - self.backgroundView = BlurredBackgroundView(color: .clear, enableBlur: true) + self.backgroundView = BlurredBackgroundView(color: .clear, enableBlur: true, customBlurRadius: 5.0) self.separatorView = UIView() self.separatorView.isUserInteractionEnabled = false @@ -186,8 +186,8 @@ final class EntityKeyboardBottomPanelComponent: Component { func update(component: EntityKeyboardBottomPanelComponent, availableSize: CGSize, state: EmptyComponentState, environment: Environment, transition: ComponentTransition) -> CGSize { if self.component?.theme !== component.theme { - self.separatorView.backgroundColor = component.theme.chat.inputMediaPanel.panelSeparatorColor - self.backgroundView.updateColor(color: component.theme.chat.inputPanel.panelBackgroundColor.withMultipliedAlpha(1.0), transition: .immediate) + self.separatorView.backgroundColor = component.theme.chat.inputPanel.panelSeparatorColor + self.backgroundView.updateColor(color: component.theme.chat.inputPanel.panelBackgroundColor.withMultipliedAlpha(0.65), transition: .immediate) self.highlightedIconBackgroundView.backgroundColor = component.theme.chat.inputMediaPanel.panelHighlightedIconBackgroundColor } diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardTopContainerPanelComponent.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardTopContainerPanelComponent.swift index c0f3538db9..85a1fc65ee 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardTopContainerPanelComponent.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/EntityKeyboardTopContainerPanelComponent.swift @@ -206,7 +206,8 @@ final class EntityKeyboardTopContainerPanelComponent: Component { if let current = self.backgroundView { backgroundView = current } else { - backgroundView = BlurredBackgroundView(color: .clear, enableBlur: true) + backgroundView = BlurredBackgroundView(color: .clear, enableBlur: true, customBlurRadius: 5.0) + self.backgroundView = backgroundView self.insertSubview(backgroundView, at: 0) } @@ -218,12 +219,12 @@ final class EntityKeyboardTopContainerPanelComponent: Component { self.insertSubview(backgroundSeparatorView, aboveSubview: backgroundView) } - backgroundView.updateColor(color: component.theme.chat.inputPanel.panelBackgroundColor.withMultipliedAlpha(1.0), transition: .immediate) - backgroundView.update(size: CGSize(width: availableSize.width, height: height), transition: transition.containedViewLayoutTransition) - transition.setFrame(view: backgroundView, frame: CGRect(origin: CGPoint(), size: CGSize(width: availableSize.width, height: height))) + backgroundView.updateColor(color: component.theme.chat.inputPanel.panelBackgroundColor.withMultipliedAlpha(0.65), transition: .immediate) + backgroundView.update(size: CGSize(width: availableSize.width, height: height + component.overflowHeight), transition: transition.containedViewLayoutTransition) + transition.setFrame(view: backgroundView, frame: CGRect(origin: CGPoint(x: 0.0, y: -component.overflowHeight), size: CGSize(width: availableSize.width, height: height + component.overflowHeight))) backgroundSeparatorView.backgroundColor = component.theme.chat.inputPanel.panelSeparatorColor - transition.setFrame(view: backgroundSeparatorView, frame: CGRect(origin: CGPoint(x: 0.0, y: height), size: CGSize(width: availableSize.width, height: UIScreenPixel))) + transition.setFrame(view: backgroundSeparatorView, frame: CGRect(origin: CGPoint(x: 0.0, y: height - UIScreenPixel), size: CGSize(width: availableSize.width, height: UIScreenPixel))) } else if case .none = component.displayBackground { self.backgroundColor = nil diff --git a/submodules/TelegramUI/Components/EntityKeyboard/Sources/GifPagerContentComponent.swift b/submodules/TelegramUI/Components/EntityKeyboard/Sources/GifPagerContentComponent.swift index b60b78d694..9fa0ec62b8 100644 --- a/submodules/TelegramUI/Components/EntityKeyboard/Sources/GifPagerContentComponent.swift +++ b/submodules/TelegramUI/Components/EntityKeyboard/Sources/GifPagerContentComponent.swift @@ -876,7 +876,7 @@ public final class GifPagerContentComponent: Component { } } - public func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, transition: ComponentTransition) { + public func pagerUpdateBackground(backgroundFrame: CGRect, topPanelHeight: CGFloat, externalTintMaskContainer: UIView?, transition: ComponentTransition) { guard let theme = self.theme else { return } @@ -912,6 +912,8 @@ public final class GifPagerContentComponent: Component { transition.setFrame(view: self.backgroundView, frame: backgroundFrame) self.backgroundView.update(size: backgroundFrame.size, transition: transition.containedViewLayoutTransition) + self.backgroundView.isHidden = hideBackground + if let vibrancyEffectView = self.vibrancyEffectView { transition.setFrame(view: vibrancyEffectView, frame: CGRect(origin: CGPoint(x: 0.0, y: -backgroundFrame.minY), size: CGSize(width: backgroundFrame.width, height: backgroundFrame.height + backgroundFrame.minY))) } diff --git a/submodules/TelegramUI/Components/ForumCreateTopicScreen/Sources/ForumCreateTopicScreen.swift b/submodules/TelegramUI/Components/ForumCreateTopicScreen/Sources/ForumCreateTopicScreen.swift index 182c9ed0f9..08000283b8 100644 --- a/submodules/TelegramUI/Components/ForumCreateTopicScreen/Sources/ForumCreateTopicScreen.swift +++ b/submodules/TelegramUI/Components/ForumCreateTopicScreen/Sources/ForumCreateTopicScreen.swift @@ -350,6 +350,7 @@ private final class TopicIconSelectionComponent: Component { defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/GlassBackgroundComponent/Sources/GlassBackgroundComponent.swift b/submodules/TelegramUI/Components/GlassBackgroundComponent/Sources/GlassBackgroundComponent.swift index 7ac15dbe9b..e0121387fc 100644 --- a/submodules/TelegramUI/Components/GlassBackgroundComponent/Sources/GlassBackgroundComponent.swift +++ b/submodules/TelegramUI/Components/GlassBackgroundComponent/Sources/GlassBackgroundComponent.swift @@ -4,86 +4,6 @@ import Display import ComponentFlow import ComponentDisplayAdapters -private func generateForegroundImage(size: CGSize, isDark: Bool, fillColor: UIColor) -> UIImage { - var size = size - if size == .zero { - size = CGSize(width: 1.0, height: 1.0) - } - - return generateImage(size, rotatedContext: { size, context in - context.clear(CGRect(origin: CGPoint(), size: size)) - - let maxColor = UIColor(white: 1.0, alpha: isDark ? 0.67 : 0.9) - let minColor = UIColor(white: 1.0, alpha: 0.0) - - context.setFillColor(fillColor.cgColor) - context.fillEllipse(in: CGRect(origin: CGPoint(), size: size)) - - let lineWidth: CGFloat = isDark ? 0.66 : 0.66 - - context.saveGState() - - let darkShadeColor = UIColor(white: isDark ? 1.0 : 0.0, alpha: 0.035) - let lightShadeColor = UIColor(white: isDark ? 0.0 : 1.0, alpha: 0.035) - let innerShadowBlur: CGFloat = 24.0 - - context.resetClip() - context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) - context.clip() - context.addRect(CGRect(origin: CGPoint(), size: size).insetBy(dx: -100.0, dy: -100.0)) - context.addEllipse(in: CGRect(origin: CGPoint(), size: size)) - context.setFillColor(UIColor.black.cgColor) - context.setShadow(offset: CGSize(width: 10.0, height: -10.0), blur: innerShadowBlur, color: darkShadeColor.cgColor) - context.fillPath(using: .evenOdd) - - context.resetClip() - context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) - context.clip() - context.addRect(CGRect(origin: CGPoint(), size: size).insetBy(dx: -100.0, dy: -100.0)) - context.addEllipse(in: CGRect(origin: CGPoint(), size: size)) - context.setFillColor(UIColor.black.cgColor) - context.setShadow(offset: CGSize(width: -10.0, height: 10.0), blur: innerShadowBlur, color: lightShadeColor.cgColor) - context.fillPath(using: .evenOdd) - - context.restoreGState() - - context.setLineWidth(lineWidth) - - context.addRect(CGRect(origin: CGPoint(x: 0.0, y: 0.0), size: CGSize(width: size.width * 0.5, height: size.height))) - context.clip() - context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) - context.replacePathWithStrokedPath() - context.clip() - - do { - var locations: [CGFloat] = [0.0, 0.5, 0.5 + 0.2, 1.0 - 0.1, 1.0] - let colors: [CGColor] = [maxColor.cgColor, maxColor.cgColor, minColor.cgColor, minColor.cgColor, maxColor.cgColor] - - let colorSpace = CGColorSpaceCreateDeviceRGB() - let gradient = CGGradient(colorsSpace: colorSpace, colors: colors as CFArray, locations: &locations)! - - context.drawLinearGradient(gradient, start: CGPoint(x: 0.0, y: 0.0), end: CGPoint(x: 0.0, y: size.height), options: CGGradientDrawingOptions()) - } - - context.resetClip() - context.addRect(CGRect(origin: CGPoint(x: size.width - size.width * 0.5, y: 0.0), size: CGSize(width: size.width * 0.5, height: size.height))) - context.clip() - context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) - context.replacePathWithStrokedPath() - context.clip() - - do { - var locations: [CGFloat] = [0.0, 0.1, 0.5 - 0.2, 0.5, 1.0] - let colors: [CGColor] = [maxColor.cgColor, minColor.cgColor, minColor.cgColor, maxColor.cgColor, maxColor.cgColor] - - let colorSpace = CGColorSpaceCreateDeviceRGB() - let gradient = CGGradient(colorsSpace: colorSpace, colors: colors as CFArray, locations: &locations)! - - context.drawLinearGradient(gradient, start: CGPoint(x: 0.0, y: 0.0), end: CGPoint(x: 0.0, y: size.height), options: CGGradientDrawingOptions()) - } - })!.stretchableImage(withLeftCapWidth: Int(size.width * 0.5), topCapHeight: Int(size.height * 0.5)) -} - private final class ContentContainer: UIView { private let maskContentView: UIView @@ -345,7 +265,6 @@ public final class GlassBackgroundView: UIView { private let foregroundView: UIImageView? private let shadowView: UIImageView? - private let shadowMaskView: UIImageView? public let maskContentView: UIView private let contentContainer: ContentContainer @@ -371,14 +290,12 @@ public final class GlassBackgroundView: UIView { nativeView.traitOverrides.userInterfaceStyle = .light //self.foregroundView = UIImageView() self.foregroundView = nil - self.shadowView = nil - self.shadowMaskView = nil + self.shadowView = UIImageView() } else { self.backgroundNode = NavigationBackgroundNode(color: .black, enableBlur: true, customBlurRadius: 5.0) self.nativeView = nil self.foregroundView = UIImageView() self.shadowView = UIImageView() - self.shadowMaskView = UIImageView() } self.maskContentView = UIView() @@ -393,9 +310,6 @@ public final class GlassBackgroundView: UIView { if let shadowView = self.shadowView { self.addSubview(shadowView) - if let shadowMaskView = self.shadowMaskView { - shadowView.mask = shadowMaskView - } } if let nativeView = self.nativeView { self.addSubview(nativeView) @@ -435,39 +349,36 @@ public final class GlassBackgroundView: UIView { transition.setFrame(view: backgroundNode.view, frame: CGRect(origin: CGPoint(), size: size)) } + let shadowInset: CGFloat = 32.0 + let params = Params(cornerRadius: cornerRadius, isDark: isDark, tintColor: tintColor) if self.params != params { self.params = params if let shadowView = self.shadowView { - shadowView.layer.shadowRadius = 10.0 - shadowView.layer.shadowColor = UIColor(white: 0.0, alpha: 1.0).cgColor - shadowView.layer.shadowOpacity = 0.08 - shadowView.layer.shadowOffset = CGSize(width: 0.0, height: 1.0) - - if let shadowMaskView = self.shadowMaskView { - let shadowInset: CGFloat = 32.0 - let shadowInnerInset: CGFloat = 0.5 - shadowMaskView.image = generateImage(CGSize(width: shadowInset * 2.0 + cornerRadius * 2.0, height: shadowInset * 2.0 + cornerRadius * 2.0), rotatedContext: { size, context in - context.setFillColor(UIColor.white.cgColor) - context.fill(CGRect(origin: CGPoint(), size: size)) - - context.setFillColor(UIColor.clear.cgColor) - context.setBlendMode(.copy) - context.fillEllipse(in: CGRect(origin: CGPoint(x: shadowInset + shadowInnerInset, y: shadowInset + shadowInnerInset), size: CGSize(width: size.width - shadowInset * 2.0 - shadowInnerInset * 2.0, height: size.height - shadowInset * 2.0 - shadowInnerInset * 2.0))) - })?.stretchableImage(withLeftCapWidth: Int(shadowInset + cornerRadius), topCapHeight: Int(shadowInset + cornerRadius)) - } + let shadowInnerInset: CGFloat = 0.5 + shadowView.image = generateImage(CGSize(width: shadowInset * 2.0 + cornerRadius * 2.0, height: shadowInset * 2.0 + cornerRadius * 2.0), rotatedContext: { size, context in + context.clear(CGRect(origin: CGPoint(), size: size)) + + context.setFillColor(UIColor.black.cgColor) + context.setShadow(offset: CGSize(width: 0.0, height: 1.0), blur: 30.0, color: UIColor(white: 0.0, alpha: 0.08).cgColor) + context.fillEllipse(in: CGRect(origin: CGPoint(x: shadowInset + shadowInnerInset, y: shadowInset + shadowInnerInset), size: CGSize(width: size.width - shadowInset * 2.0 - shadowInnerInset * 2.0, height: size.height - shadowInset * 2.0 - shadowInnerInset * 2.0))) + + context.setFillColor(UIColor.clear.cgColor) + context.setBlendMode(.copy) + context.fillEllipse(in: CGRect(origin: CGPoint(x: shadowInset + shadowInnerInset, y: shadowInset + shadowInnerInset), size: CGSize(width: size.width - shadowInset * 2.0 - shadowInnerInset * 2.0, height: size.height - shadowInset * 2.0 - shadowInnerInset * 2.0))) + })?.stretchableImage(withLeftCapWidth: Int(shadowInset + cornerRadius), topCapHeight: Int(shadowInset + cornerRadius)) } if let foregroundView = self.foregroundView { - foregroundView.image = generateForegroundImage(size: CGSize(width: cornerRadius * 2.0, height: cornerRadius * 2.0), isDark: isDark, fillColor: tintColor.color) + foregroundView.image = GlassBackgroundView.generateForegroundImage(size: CGSize(width: cornerRadius * 2.0, height: cornerRadius * 2.0), isDark: isDark, fillColor: tintColor.color) } else { if let nativeView { if #available(iOS 26.0, *) { - let glassEffect = UIGlassEffect(style: .regular) + let glassEffect = UIGlassEffect(style: .clear) switch tintColor.kind { case .panel: - glassEffect.tintColor = nil + glassEffect.tintColor = tintColor.color case .custom: glassEffect.tintColor = tintColor.color } @@ -484,14 +395,7 @@ public final class GlassBackgroundView: UIView { transition.setFrame(view: foregroundView, frame: CGRect(origin: CGPoint(), size: size)) } if let shadowView = self.shadowView { - if shadowView.bounds.size != size { - shadowView.layer.shadowPath = UIBezierPath(roundedRect: CGRect(origin: CGPoint(), size: size), cornerRadius: size.height * 0.5).cgPath - } - transition.setFrame(view: shadowView, frame: CGRect(origin: CGPoint(), size: size)) - - if let shadowMaskView = self.shadowMaskView { - transition.setFrame(view: shadowMaskView, frame: CGRect(origin: CGPoint(), size: size).insetBy(dx: -32.0, dy: -32.0)) - } + transition.setFrame(view: shadowView, frame: CGRect(origin: CGPoint(), size: size).insetBy(dx: -shadowInset, dy: -shadowInset)) } transition.setFrame(view: self.contentContainer, frame: CGRect(origin: CGPoint(), size: size)) } @@ -585,3 +489,85 @@ public final class VariableBlurView: UIVisualEffectView { backdropLayer?.filters = [variableBlur] } } + +public extension GlassBackgroundView { + static func generateForegroundImage(size: CGSize, isDark: Bool, fillColor: UIColor) -> UIImage { + var size = size + if size == .zero { + size = CGSize(width: 1.0, height: 1.0) + } + + return generateImage(size, rotatedContext: { size, context in + context.clear(CGRect(origin: CGPoint(), size: size)) + + let maxColor = UIColor(white: 1.0, alpha: isDark ? 0.25 : 0.9) + let minColor = UIColor(white: 1.0, alpha: 0.0) + + context.setFillColor(fillColor.cgColor) + context.fillEllipse(in: CGRect(origin: CGPoint(), size: size)) + + let lineWidth: CGFloat = isDark ? 0.66 : 0.66 + + context.saveGState() + + let darkShadeColor = UIColor(white: isDark ? 1.0 : 0.0, alpha: 0.035) + let lightShadeColor = UIColor(white: isDark ? 0.0 : 1.0, alpha: 0.035) + let innerShadowBlur: CGFloat = 24.0 + + context.resetClip() + context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) + context.clip() + context.addRect(CGRect(origin: CGPoint(), size: size).insetBy(dx: -100.0, dy: -100.0)) + context.addEllipse(in: CGRect(origin: CGPoint(), size: size)) + context.setFillColor(UIColor.black.cgColor) + context.setShadow(offset: CGSize(width: 10.0, height: -10.0), blur: innerShadowBlur, color: darkShadeColor.cgColor) + context.fillPath(using: .evenOdd) + + context.resetClip() + context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) + context.clip() + context.addRect(CGRect(origin: CGPoint(), size: size).insetBy(dx: -100.0, dy: -100.0)) + context.addEllipse(in: CGRect(origin: CGPoint(), size: size)) + context.setFillColor(UIColor.black.cgColor) + context.setShadow(offset: CGSize(width: -10.0, height: 10.0), blur: innerShadowBlur, color: lightShadeColor.cgColor) + context.fillPath(using: .evenOdd) + + context.restoreGState() + + context.setLineWidth(lineWidth) + + context.addRect(CGRect(origin: CGPoint(x: 0.0, y: 0.0), size: CGSize(width: size.width * 0.5, height: size.height))) + context.clip() + context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) + context.replacePathWithStrokedPath() + context.clip() + + do { + var locations: [CGFloat] = [0.0, 0.5, 0.5 + 0.2, 1.0 - 0.1, 1.0] + let colors: [CGColor] = [maxColor.cgColor, maxColor.cgColor, minColor.cgColor, minColor.cgColor, maxColor.cgColor] + + let colorSpace = CGColorSpaceCreateDeviceRGB() + let gradient = CGGradient(colorsSpace: colorSpace, colors: colors as CFArray, locations: &locations)! + + context.drawLinearGradient(gradient, start: CGPoint(x: 0.0, y: 0.0), end: CGPoint(x: 0.0, y: size.height), options: CGGradientDrawingOptions()) + } + + context.resetClip() + context.addRect(CGRect(origin: CGPoint(x: size.width - size.width * 0.5, y: 0.0), size: CGSize(width: size.width * 0.5, height: size.height))) + context.clip() + context.addEllipse(in: CGRect(origin: CGPoint(), size: size).insetBy(dx: lineWidth * 0.5, dy: lineWidth * 0.5)) + context.replacePathWithStrokedPath() + context.clip() + + do { + var locations: [CGFloat] = [0.0, 0.1, 0.5 - 0.2, 0.5, 1.0] + let colors: [CGColor] = [maxColor.cgColor, minColor.cgColor, minColor.cgColor, maxColor.cgColor, maxColor.cgColor] + + let colorSpace = CGColorSpaceCreateDeviceRGB() + let gradient = CGGradient(colorsSpace: colorSpace, colors: colors as CFArray, locations: &locations)! + + context.drawLinearGradient(gradient, start: CGPoint(x: 0.0, y: 0.0), end: CGPoint(x: 0.0, y: size.height), options: CGGradientDrawingOptions()) + } + })!.stretchableImage(withLeftCapWidth: Int(size.width * 0.5), topCapHeight: Int(size.height * 0.5)) + } +} diff --git a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift index 608ae85e60..7412d9bc9c 100644 --- a/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift +++ b/submodules/TelegramUI/Components/MediaEditorScreen/Sources/MediaEditorScreen.swift @@ -407,6 +407,7 @@ final class MediaEditorScreenComponent: Component { areCustomEmojiEnabled: true, hasSearch: true, hideBackground: true, + maskEdge: true, sendGif: nil ) |> map { inputData -> ChatEntityKeyboardInputNode.InputData in return ChatEntityKeyboardInputNode.InputData( diff --git a/submodules/TelegramUI/Components/PeerAllowedReactionsScreen/Sources/EmojiSelectionComponent.swift b/submodules/TelegramUI/Components/PeerAllowedReactionsScreen/Sources/EmojiSelectionComponent.swift index 31c385a7fc..8f94c92974 100644 --- a/submodules/TelegramUI/Components/PeerAllowedReactionsScreen/Sources/EmojiSelectionComponent.swift +++ b/submodules/TelegramUI/Components/PeerAllowedReactionsScreen/Sources/EmojiSelectionComponent.swift @@ -257,6 +257,7 @@ public final class EmojiSelectionComponent: Component { defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/EmojiPickerItem.swift b/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/EmojiPickerItem.swift index ed4f8b15d0..e4f962bbcb 100644 --- a/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/EmojiPickerItem.swift +++ b/submodules/TelegramUI/Components/Settings/PeerNameColorScreen/Sources/EmojiPickerItem.swift @@ -335,6 +335,7 @@ private final class EmojiSelectionComponent: Component { defaultToEmojiTab: true, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, topPanelScrollingOffset: { _, _ in }, diff --git a/submodules/TelegramUI/Components/StickerPickerScreen/Sources/StickerPickerScreen.swift b/submodules/TelegramUI/Components/StickerPickerScreen/Sources/StickerPickerScreen.swift index 6968c89459..c5631fee10 100644 --- a/submodules/TelegramUI/Components/StickerPickerScreen/Sources/StickerPickerScreen.swift +++ b/submodules/TelegramUI/Components/StickerPickerScreen/Sources/StickerPickerScreen.swift @@ -283,6 +283,7 @@ private final class StickerSelectionComponent: Component { defaultToEmojiTab: defaultToEmoji, externalTopPanelContainer: self.panelHostView, externalBottomPanelContainer: nil, + externalTintMaskContainer: nil, displayTopPanelBackground: .blur, topPanelExtensionUpdated: { _, _ in }, diff --git a/submodules/TelegramUI/Sources/ChatControllerNode.swift b/submodules/TelegramUI/Sources/ChatControllerNode.swift index 19b57b0205..b1ab2da1b9 100644 --- a/submodules/TelegramUI/Sources/ChatControllerNode.swift +++ b/submodules/TelegramUI/Sources/ChatControllerNode.swift @@ -1768,9 +1768,6 @@ class ChatControllerNode: ASDisplayNode, ASScrollViewDelegate { if let inputNode = inputNode as? ChatEntityKeyboardInputNode { inputNode.externalTopPanelContainerImpl = nil } - inputNode.clipsToBounds = true - inputNode.layer.maskedCorners = [.layerMinXMinYCorner, .layerMaxXMinYCorner] - inputNode.layer.cornerRadius = 30.0 dismissedInputNode = self.inputNode dismissedInputNodeExternalTopPanelContainer = self.inputNode?.externalTopPanelContainer @@ -2158,11 +2155,7 @@ class ChatControllerNode: ASDisplayNode, ASScrollViewDelegate { if self.dismissedAsOverlay { inputPanelFrame!.origin.y = layout.size.height } - if let inputNode = self.inputNode, inputNode.hideInput, !inputNode.adjustLayoutForHiddenInput { - inputPanelsHeight += inputPanelNodeBaseHeight - } else { - inputPanelsHeight += inputPanelSize!.height - } + inputPanelsHeight += inputPanelSize!.height } if self.secondaryInputPanelNode != nil { @@ -3942,6 +3935,7 @@ class ChatControllerNode: ASDisplayNode, ASScrollViewDelegate { chatPeerId: self.chatLocation.peerId, areCustomEmojiEnabled: self.chatPresentationInterfaceState.customEmojiAvailable, hasEdit: true, + hideBackground: true, sendGif: { [weak self] fileReference, sourceView, sourceRect, silentPosting, schedule in if let self { return self.controllerInteraction.sendGif(fileReference, sourceView, sourceRect, silentPosting, schedule) @@ -4235,15 +4229,20 @@ class ChatControllerNode: ASDisplayNode, ASScrollViewDelegate { } var maybeDismissOverlayContent = true - if let inputNode = self.inputNode, inputNode.bounds.contains(self.view.convert(point, to: inputNode.view)) { - if let externalTopPanelContainer = inputNode.externalTopPanelContainer { - if externalTopPanelContainer.hitTest(self.view.convert(point, to: externalTopPanelContainer), with: nil) != nil { - maybeDismissOverlayContent = true + if let inputNode = self.inputNode { + if let result = inputNode.view.hitTest(self.view.convert(point, to: inputNode.view), with: event) { + return result + } + if inputNode.bounds.contains(self.view.convert(point, to: inputNode.view)) { + if let externalTopPanelContainer = inputNode.externalTopPanelContainer { + if externalTopPanelContainer.hitTest(self.view.convert(point, to: externalTopPanelContainer), with: nil) != nil { + maybeDismissOverlayContent = true + } else { + maybeDismissOverlayContent = false + } } else { maybeDismissOverlayContent = false } - } else { - maybeDismissOverlayContent = false } } diff --git a/submodules/TelegramUI/Sources/ChatHistoryNavigationButtonNode.swift b/submodules/TelegramUI/Sources/ChatHistoryNavigationButtonNode.swift index a4b577d383..e997379ea8 100644 --- a/submodules/TelegramUI/Sources/ChatHistoryNavigationButtonNode.swift +++ b/submodules/TelegramUI/Sources/ChatHistoryNavigationButtonNode.swift @@ -94,7 +94,7 @@ class ChatHistoryNavigationButtonNode: ContextControllerSourceNode { self.buttonNode.view.addSubview(self.backgroundView) self.backgroundView.frame = CGRect(origin: CGPoint(), size: size) - self.backgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: .immediate) + self.backgroundView.update(size: size, cornerRadius: size.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: .immediate) self.imageView.tintColor = theme.chat.inputPanel.inputControlColor self.backgroundView.contentView.addSubview(self.imageView) @@ -110,7 +110,7 @@ class ChatHistoryNavigationButtonNode: ContextControllerSourceNode { if self.theme !== theme { self.theme = theme - self.backgroundView.update(size: self.backgroundView.bounds.size, cornerRadius: self.backgroundView.bounds.size.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.65)), transition: .immediate) + self.backgroundView.update(size: self.backgroundView.bounds.size, cornerRadius: self.backgroundView.bounds.size.height * 0.5, isDark: theme.overallDarkAppearance, tintColor: .init(kind: .panel, color: theme.chat.inputPanel.inputBackgroundColor.withMultipliedAlpha(0.7)), transition: .immediate) self.imageView.tintColor = theme.chat.inputPanel.inputControlColor switch self.type {