mirror of
https://github.com/divkit/divkit.git
synced 2026-06-06 20:07:59 +00:00
added divview implementation for tooltips
This commit is contained in:
@@ -8722,6 +8722,7 @@
|
||||
"client/ios/DivKit/Extensions/DivInputExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivInputExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivPagerExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivPagerExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivPivotExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivPivotExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivPointExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivPointExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivSelectExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivSelectExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivSeparatorExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivSeparatorExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivSizeExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivSizeExtensions.swift",
|
||||
@@ -8730,6 +8731,7 @@
|
||||
"client/ios/DivKit/Extensions/DivStateExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivStateExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivTabsExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivTabsExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivTextExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivTextExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivTooltipExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivTooltipExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivTransformExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivTransformExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivVideoExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivVideoExtensions.swift",
|
||||
"client/ios/DivKit/Extensions/DivVisibilityActionExtensions.swift":"divkit/public/client/ios/DivKit/Extensions/DivVisibilityActionExtensions.swift",
|
||||
|
||||
@@ -2,6 +2,7 @@ import CoreGraphics
|
||||
|
||||
import BasePublic
|
||||
import BaseUIPublic
|
||||
import CommonCorePublic
|
||||
import LayoutKit
|
||||
import NetworkingPublic
|
||||
import Serialization
|
||||
@@ -38,6 +39,7 @@ public struct DivBlockModelingContext {
|
||||
public let errorsStorage: DivErrorsStorage
|
||||
internal let variableTracker: DivVariableTracker?
|
||||
private let persistentValuesStorage: DivPersistentValuesStorage
|
||||
public let tooltipViewFactory: DivTooltipViewFactory?
|
||||
|
||||
var overridenWidth: DivOverridenSize?
|
||||
var overridenHeight: DivOverridenSize?
|
||||
@@ -80,7 +82,8 @@ public struct DivBlockModelingContext {
|
||||
errorsStorage: DivErrorsStorage = DivErrorsStorage(errors: []),
|
||||
layoutDirection: UserInterfaceLayoutDirection = .leftToRight,
|
||||
variableTracker: DivVariableTracker? = nil,
|
||||
persistentValuesStorage: DivPersistentValuesStorage = DivPersistentValuesStorage()
|
||||
persistentValuesStorage: DivPersistentValuesStorage = DivPersistentValuesStorage(),
|
||||
tooltipViewFactory: DivTooltipViewFactory? = nil
|
||||
) {
|
||||
self.cardId = cardId
|
||||
self.cardLogId = cardLogId
|
||||
@@ -105,6 +108,7 @@ public struct DivBlockModelingContext {
|
||||
self.layoutDirection = layoutDirection
|
||||
self.variableTracker = variableTracker
|
||||
self.persistentValuesStorage = persistentValuesStorage
|
||||
self.tooltipViewFactory = tooltipViewFactory
|
||||
|
||||
var extensionsHandlersDictionary = [String: DivExtensionHandler]()
|
||||
extensionHandlers.forEach {
|
||||
|
||||
@@ -278,7 +278,8 @@ public final class DivKitComponents {
|
||||
parentScrollView: parentScrollView,
|
||||
layoutDirection: layoutDirection,
|
||||
variableTracker: variableTracker,
|
||||
persistentValuesStorage: persistentValuesStorage
|
||||
persistentValuesStorage: persistentValuesStorage,
|
||||
tooltipViewFactory: makeTooltipViewFactory(divKitComponents: self, cardId: cardId)
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
@@ -84,7 +84,7 @@ extension DivBase {
|
||||
}
|
||||
),
|
||||
scheduler: context.scheduler,
|
||||
tooltips: try makeTooltips(context: context)
|
||||
tooltips: try tooltips.makeTooltips(context: context)
|
||||
)
|
||||
.addingTransform(
|
||||
transform: transform.resolveRotation(expressionResolver)
|
||||
@@ -178,15 +178,6 @@ extension DivBase {
|
||||
return nil
|
||||
}
|
||||
|
||||
private func makeTooltips(context: DivBlockModelingContext) throws -> [BlockTooltip] {
|
||||
try tooltips?.iterativeFlatMap { div, index in
|
||||
let tooltipContext = modified(context) {
|
||||
$0.parentPath = $0.parentPath + "tooltip" + index
|
||||
}
|
||||
return try div.makeTooltip(context: tooltipContext)
|
||||
} ?? []
|
||||
}
|
||||
|
||||
private func applyTransitioningAnimations(
|
||||
to block: Block,
|
||||
context: DivBlockModelingContext,
|
||||
@@ -368,46 +359,3 @@ extension DivBorder {
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
extension DivTooltip {
|
||||
fileprivate func makeTooltip(context: DivBlockModelingContext) throws
|
||||
-> BlockTooltip? {
|
||||
let expressionResolver = context.expressionResolver
|
||||
guard let position = resolvePosition(expressionResolver)?.cast() else {
|
||||
return nil
|
||||
}
|
||||
let block = try div.value.makeBlock(context: context)
|
||||
return BlockTooltip(
|
||||
id: id,
|
||||
block: block,
|
||||
duration: Duration(milliseconds: resolveDuration(expressionResolver)),
|
||||
offset: offset?.cast(with: expressionResolver) ?? .zero,
|
||||
position: position
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
extension DivTooltip.Position {
|
||||
fileprivate func cast() -> BlockTooltip.Position {
|
||||
switch self {
|
||||
case .left: return .left
|
||||
case .topLeft: return .topLeft
|
||||
case .top: return .top
|
||||
case .topRight: return .topRight
|
||||
case .right: return .right
|
||||
case .bottomRight: return .bottomRight
|
||||
case .bottom: return .bottom
|
||||
case .bottomLeft: return .bottomLeft
|
||||
case .center: return .center
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extension DivPoint {
|
||||
fileprivate func cast(with expressionResolver: ExpressionResolver) -> CGPoint {
|
||||
CGPoint(
|
||||
x: x.resolveUnit(expressionResolver).makeScaledValue(x.resolveValue(expressionResolver) ?? 0),
|
||||
y: y.resolveUnit(expressionResolver).makeScaledValue(y.resolveValue(expressionResolver) ?? 0)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
import Foundation
|
||||
|
||||
extension DivPoint {
|
||||
internal func cast(with expressionResolver: ExpressionResolver) -> CGPoint {
|
||||
CGPoint(
|
||||
x: x.resolveUnit(expressionResolver).makeScaledValue(x.resolveValue(expressionResolver) ?? 0),
|
||||
y: y.resolveUnit(expressionResolver).makeScaledValue(y.resolveValue(expressionResolver) ?? 0)
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
import BasePublic
|
||||
import CommonCorePublic
|
||||
import Foundation
|
||||
import LayoutKit
|
||||
|
||||
#if os(iOS)
|
||||
public typealias DivTooltipViewFactory = (Div) -> VisibleBoundsTrackingView
|
||||
#else
|
||||
public typealias DivTooltipViewFactory = (Div) -> ViewType
|
||||
#endif
|
||||
|
||||
extension DivTooltip {
|
||||
fileprivate func makeTooltip(context: DivBlockModelingContext) throws
|
||||
-> BlockTooltip? {
|
||||
let expressionResolver = context.expressionResolver
|
||||
guard let position = resolvePosition(expressionResolver)?.cast() else {
|
||||
return nil
|
||||
}
|
||||
|
||||
let block = try div.value.makeBlock(context: context)
|
||||
|
||||
let tooltipViewFactory: TooltipViewFactory =
|
||||
Variable { [tooltipViewFactory = context.tooltipViewFactory, div = self.div] in
|
||||
guard let tooltipViewFactory = tooltipViewFactory else { return nil }
|
||||
return tooltipViewFactory(div)
|
||||
}
|
||||
|
||||
return BlockTooltip(
|
||||
id: id,
|
||||
block: block,
|
||||
duration: Duration(milliseconds: resolveDuration(expressionResolver)),
|
||||
offset: offset?.cast(with: expressionResolver) ?? .zero,
|
||||
position: position,
|
||||
tooltipViewFactory: tooltipViewFactory
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
extension DivTooltip.Position {
|
||||
fileprivate func cast() -> BlockTooltip.Position {
|
||||
switch self {
|
||||
case .left: return .left
|
||||
case .topLeft: return .topLeft
|
||||
case .top: return .top
|
||||
case .topRight: return .topRight
|
||||
case .right: return .right
|
||||
case .bottomRight: return .bottomRight
|
||||
case .bottom: return .bottom
|
||||
case .bottomLeft: return .bottomLeft
|
||||
case .center: return .center
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extension Optional where Wrapped == [DivTooltip] {
|
||||
func makeTooltips(
|
||||
context: DivBlockModelingContext
|
||||
) throws -> [BlockTooltip] {
|
||||
try self?.iterativeFlatMap { div, index in
|
||||
let tooltipContext = modified(context) {
|
||||
$0.parentPath = $0.parentPath + "tooltip" + index
|
||||
}
|
||||
return try div.makeTooltip(context: tooltipContext)
|
||||
} ?? []
|
||||
}
|
||||
}
|
||||
|
||||
public func makeTooltipViewFactory(
|
||||
divKitComponents: DivKitComponents,
|
||||
cardId: DivCardID
|
||||
) -> DivTooltipViewFactory {
|
||||
{ (div: Div) in
|
||||
let view = DivView(divKitComponents: divKitComponents)
|
||||
let divData = DivData(
|
||||
logId: cardId.rawValue,
|
||||
states: [.init(div: div, stateId: 0)],
|
||||
timers: nil,
|
||||
transitionAnimationSelector: nil,
|
||||
variableTriggers: nil,
|
||||
variables: nil
|
||||
)
|
||||
view.setSource(.init(kind: .divData(divData), cardId: cardId))
|
||||
return view
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,11 @@
|
||||
import CommonCorePublic
|
||||
import CoreGraphics
|
||||
|
||||
import CommonCorePublic
|
||||
#if os(iOS)
|
||||
public typealias TooltipViewFactory = Variable<VisibleBoundsTrackingView?>
|
||||
#else
|
||||
public typealias TooltipViewFactory = Variable<ViewType?>
|
||||
#endif
|
||||
|
||||
public struct BlockTooltip: Equatable {
|
||||
public enum Position: String, CaseIterable {
|
||||
@@ -20,19 +25,22 @@ public struct BlockTooltip: Equatable {
|
||||
public let duration: Duration
|
||||
public let offset: CGPoint
|
||||
public let position: Position
|
||||
public let tooltipViewFactory: TooltipViewFactory?
|
||||
|
||||
public init(
|
||||
id: String,
|
||||
block: Block,
|
||||
duration: Duration,
|
||||
offset: CGPoint,
|
||||
position: BlockTooltip.Position
|
||||
position: BlockTooltip.Position,
|
||||
tooltipViewFactory: TooltipViewFactory? = nil
|
||||
) {
|
||||
self.id = id
|
||||
self.block = block
|
||||
self.duration = duration
|
||||
self.offset = offset
|
||||
self.position = position
|
||||
self.tooltipViewFactory = tooltipViewFactory
|
||||
}
|
||||
|
||||
public static func ==(lhs: BlockTooltip, rhs: BlockTooltip) -> Bool {
|
||||
|
||||
@@ -129,7 +129,11 @@ extension TooltipAnchorView {
|
||||
id: tooltip.id,
|
||||
duration: tooltip.duration,
|
||||
view: {
|
||||
let tooltipView = tooltip.block.makeBlockView()
|
||||
var tooltipView: VisibleBoundsTrackingView = tooltip.block.makeBlockView()
|
||||
if let tooltipViewFactory = tooltip.tooltipViewFactory,
|
||||
let view = tooltipViewFactory.value {
|
||||
tooltipView = view
|
||||
}
|
||||
let frame = tooltip.calculateFrame(targeting: bounds)
|
||||
tooltipView.frame = convert(frame, to: nil)
|
||||
return tooltipView
|
||||
|
||||
Reference in New Issue
Block a user