diff --git a/android/src/main/kotlin/com/usercentrics/sdk/flutter/serializer/CMPDataSerializer.kt b/android/src/main/kotlin/com/usercentrics/sdk/flutter/serializer/CMPDataSerializer.kt index e33ee98..4266e25 100644 --- a/android/src/main/kotlin/com/usercentrics/sdk/flutter/serializer/CMPDataSerializer.kt +++ b/android/src/main/kotlin/com/usercentrics/sdk/flutter/serializer/CMPDataSerializer.kt @@ -8,6 +8,7 @@ import com.usercentrics.sdk.v2.settings.data.CustomizationFont import com.usercentrics.sdk.v2.settings.data.FirstLayer import com.usercentrics.sdk.v2.settings.data.PublishedApp import com.usercentrics.sdk.v2.settings.data.SecondLayer +import com.usercentrics.sdk.v2.settings.data.ConsentOrPaySettings import com.usercentrics.sdk.v2.settings.data.TCF2ChangedPurposes import com.usercentrics.sdk.v2.settings.data.TCF2Settings import com.usercentrics.sdk.v2.settings.data.UsercentricsCategory @@ -225,10 +226,18 @@ private fun TCF2Settings.serialize(): Any { "scope" to scope.name, "changedPurposes" to changedPurposes?.serialize(), "acmV2Enabled" to acmV2Enabled, - "selectedATPIds" to selectedATPIds + "selectedATPIds" to selectedATPIds, + "consentOrPay" to consentOrPay?.serialize() ) } +private fun ConsentOrPaySettings.serialize(): Map = mapOf( + "enableConsentOrPay" to enableConsentOrPay, + "showTogglesForVendors" to showTogglesForVendors, + "publisherRestrictions" to publisherRestrictions, + "specialFeatures" to specialFeatures +) + private fun UsercentricsCustomization.serialize(): Any { return mapOf( "color" to color?.serialize(), diff --git a/ios/Classes/Serializer/CMPDataSerializer.swift b/ios/Classes/Serializer/CMPDataSerializer.swift index 1ddc1dc..7219691 100644 --- a/ios/Classes/Serializer/CMPDataSerializer.swift +++ b/ios/Classes/Serializer/CMPDataSerializer.swift @@ -216,11 +216,22 @@ extension TCF2Settings { "scope": self.scope.name, "changedPurposes": self.changedPurposes?.serialize() as Any, "acmV2Enabled" : self.acmV2Enabled, - "selectedATPIds" : self.selectedATPIds + "selectedATPIds" : self.selectedATPIds, + "consentOrPay": self.consentOrPay?.serialize() as Any ] } } +extension ConsentOrPaySettings { + func serialize() -> [String: Any] { + return [ + "enableConsentOrPay": self.enableConsentOrPay, + "showTogglesForVendors": self.showTogglesForVendors, + "publisherRestrictions": self.publisherRestrictions, + "specialFeatures": self.specialFeatures + ] + } +} extension UsercentricsCustomization { func serialize() -> Any { diff --git a/lib/src/internal/serializer/tcf2_settings_serializer.dart b/lib/src/internal/serializer/tcf2_settings_serializer.dart index 1bde696..f43b048 100644 --- a/lib/src/internal/serializer/tcf2_settings_serializer.dart +++ b/lib/src/internal/serializer/tcf2_settings_serializer.dart @@ -68,7 +68,9 @@ class TCF2SettingsSerializer { changedPurposes: TCF2ChangedPurposesSerializer.deserialize(value['changedPurposes']), acmV2Enabled: value['acmV2Enabled'] ?? false, - selectedATPIds: value['selectedATPIds']?.cast() ?? []); + selectedATPIds: value['selectedATPIds']?.cast() ?? [], + consentOrPay: TCF2ConsentOrPaySettingsSerializer.deserialize( + value['consentOrPay'])); } } @@ -107,3 +109,17 @@ class TCF2ChangedPurposesSerializer { legIntPurposes: value['legIntPurposes']?.cast() ?? []); } } + +class TCF2ConsentOrPaySettingsSerializer { + static TCF2ConsentOrPaySettings? deserialize(value) { + if (value == null) return null; + return TCF2ConsentOrPaySettings( + enableConsentOrPay: value['enableConsentOrPay'] ?? false, + showTogglesForVendors: value['showTogglesForVendors'] ?? true, + publisherRestrictions: + (value['publisherRestrictions'] as Map?)?.cast() ?? + {}, + specialFeatures: + (value['specialFeatures'] as Map?)?.cast() ?? {}); + } +} diff --git a/lib/src/model/tcf2_settings.dart b/lib/src/model/tcf2_settings.dart index 4d8b11e..0c84616 100644 --- a/lib/src/model/tcf2_settings.dart +++ b/lib/src/model/tcf2_settings.dart @@ -60,7 +60,8 @@ class TCF2Settings { required this.scope, required this.changedPurposes, required this.acmV2Enabled, - required this.selectedATPIds}); + required this.selectedATPIds, + this.consentOrPay}); final String firstLayerTitle; final String secondLayerTitle; @@ -121,6 +122,7 @@ class TCF2Settings { final TCF2ChangedPurposes changedPurposes; final bool acmV2Enabled; final List selectedATPIds; + final TCF2ConsentOrPaySettings? consentOrPay; @override bool operator ==(Object other) => @@ -189,7 +191,8 @@ class TCF2Settings { scope == other.scope && changedPurposes == other.changedPurposes && acmV2Enabled == other.acmV2Enabled && - listEquals(selectedATPIds, other.selectedATPIds); + listEquals(selectedATPIds, other.selectedATPIds) && + consentOrPay == other.consentOrPay; @override int get hashCode => @@ -251,7 +254,8 @@ class TCF2Settings { scope.hashCode + changedPurposes.hashCode + acmV2Enabled.hashCode + - selectedATPIds.hashCode; + selectedATPIds.hashCode + + consentOrPay.hashCode; @override String toString() => "$TCF2Settings($hashCode)"; @@ -279,3 +283,37 @@ class TCF2ChangedPurposes { @override int get hashCode => purposes.hashCode ^ legIntPurposes.hashCode; } + +class TCF2ConsentOrPaySettings { + const TCF2ConsentOrPaySettings( + {required this.enableConsentOrPay, + required this.showTogglesForVendors, + required this.publisherRestrictions, + required this.specialFeatures}); + + final bool enableConsentOrPay; + final bool showTogglesForVendors; + + /// Maps TCF Purpose ID (as string) to "flexible". Absent entries are mandatory. + final Map publisherRestrictions; + + /// Maps Special Feature ID (as string) to "flexible". Absent entries are mandatory. + final Map specialFeatures; + + @override + bool operator ==(Object other) => + identical(this, other) || + other is TCF2ConsentOrPaySettings && + runtimeType == other.runtimeType && + enableConsentOrPay == other.enableConsentOrPay && + showTogglesForVendors == other.showTogglesForVendors && + mapEquals(publisherRestrictions, other.publisherRestrictions) && + mapEquals(specialFeatures, other.specialFeatures); + + @override + int get hashCode => + enableConsentOrPay.hashCode ^ + showTogglesForVendors.hashCode ^ + publisherRestrictions.hashCode ^ + specialFeatures.hashCode; +}