mirror of
https://github.com/divkit/divkit.git
synced 2026-06-06 20:07:59 +00:00
107 lines
3.1 KiB
Swift
107 lines
3.1 KiB
Swift
import Foundation
|
|
import LayoutKit
|
|
import VGSL
|
|
|
|
extension DivTooltip {
|
|
fileprivate func makeTooltip(
|
|
context: DivBlockModelingContext
|
|
) throws -> BlockTooltip? {
|
|
let expressionResolver = context.expressionResolver
|
|
guard let position = resolvePosition(expressionResolver)?.cast() else {
|
|
return nil
|
|
}
|
|
|
|
let tooltipViewFactory: TooltipViewFactory = { [weak self] in
|
|
guard let self, let tooltipViewFactory = context.tooltipViewFactory else {
|
|
return nil
|
|
}
|
|
return await tooltipViewFactory.makeView(div: self.div, tooltipId: self.id)
|
|
}
|
|
|
|
let substrateViewFactory: TooltipViewFactory? = if let substrateDiv = self.substrateDiv {
|
|
{ [weak self] in
|
|
guard let self, let tooltipViewFactory = context.tooltipViewFactory else {
|
|
return nil
|
|
}
|
|
return await tooltipViewFactory.makeSubstrateView(div: substrateDiv, tooltipId: self.id)
|
|
}
|
|
} else {
|
|
nil
|
|
}
|
|
|
|
let mode: BlockTooltip.Mode = switch mode {
|
|
case .divTooltipModeModal:
|
|
.modal
|
|
case .divTooltipModeNonModal:
|
|
.nonModal
|
|
}
|
|
|
|
return try BlockTooltip(
|
|
// Legacy behavior. Views should be created with tooltipViewFactory.
|
|
block: div.value.makeBlock(context: context),
|
|
params: BlockTooltipParams(
|
|
id: id,
|
|
mode: mode,
|
|
duration: TimeInterval(milliseconds: resolveDuration(expressionResolver)),
|
|
closeByTapOutside: resolveCloseByTapOutside(expressionResolver),
|
|
tapOutsideActions: tapOutsideActions?.uiActions(context: context) ?? [],
|
|
backgroundAccessibilityDescription: resolveBackgroundAccessibilityDescription(
|
|
expressionResolver
|
|
),
|
|
animationIn: animationIn?.makeTransitioningAnimations(
|
|
for: .appearing,
|
|
with: expressionResolver
|
|
),
|
|
animationOut: animationOut?.makeTransitioningAnimations(
|
|
for: .disappearing,
|
|
with: expressionResolver
|
|
)
|
|
),
|
|
offset: offset?.resolve(expressionResolver) ?? .zero,
|
|
position: position,
|
|
useLegacyWidth: context.flagsInfo.useTooltipLegacyWidth,
|
|
bringToTopId: bringToTopId,
|
|
tooltipViewFactory: tooltipViewFactory,
|
|
substrateViewFactory: substrateViewFactory
|
|
)
|
|
}
|
|
}
|
|
|
|
extension DivTooltip.Position {
|
|
fileprivate func cast() -> BlockTooltip.Position {
|
|
switch self {
|
|
case .left: .left
|
|
case .topLeft: .topLeft
|
|
case .top: .top
|
|
case .topRight: .topRight
|
|
case .right: .right
|
|
case .bottomRight: .bottomRight
|
|
case .bottom: .bottom
|
|
case .bottomLeft: .bottomLeft
|
|
case .center: .center
|
|
}
|
|
}
|
|
}
|
|
|
|
extension [DivTooltip]? {
|
|
func makeTooltips(
|
|
context: DivBlockModelingContext
|
|
) throws -> [BlockTooltip] {
|
|
let items = self ?? []
|
|
if !items.isEmpty, context.viewId.isTooltip {
|
|
context.errorsStorage.add(
|
|
DivBlockModelingError(
|
|
"Tooltip can not host another tooltips",
|
|
path: context.path
|
|
)
|
|
)
|
|
return []
|
|
}
|
|
|
|
return try items.compactMap {
|
|
let tooltipContext = context.cloneForTooltip(tooltipId: $0.id)
|
|
return try $0.makeTooltip(context: tooltipContext)
|
|
}
|
|
}
|
|
}
|