Skip to content

Commit

Permalink
Merge commit 'c8c08d5e338adde8f2e435982325cd8678d6f9b9' into beta
Browse files Browse the repository at this point in the history
  • Loading branch information
Ali committed Nov 6, 2023
2 parents c77e800 + c8c08d5 commit 037ebcf
Show file tree
Hide file tree
Showing 29 changed files with 491 additions and 1,039 deletions.
32 changes: 30 additions & 2 deletions Telegram/Telegram-iOS/en.lproj/Localizable.strings
Original file line number Diff line number Diff line change
Expand Up @@ -10297,8 +10297,8 @@ Sorry for the inconvenience.";
"Stats.Boosts.Gift" = "Gift";
"Stats.Boosts.TabBoosts_1" = "%@ Boost";
"Stats.Boosts.TabBoosts_any" = "%@ Boosts";
"Stats.Boosts.TabGifts_1" = "%@ Boost";
"Stats.Boosts.TabGifts_any" = "%@ Boosts";
"Stats.Boosts.TabGifts_1" = "%@ Gift";
"Stats.Boosts.TabGifts_any" = "%@ Gifts";
"Stats.Boosts.ToBeDistributed" = "To Be Distributed";
"Stats.Boosts.Unclaimed" = "Unclaimed";
"Stats.Boosts.GetBoosts" = "Get Boosts via Gifts";
Expand Down Expand Up @@ -10364,6 +10364,8 @@ Sorry for the inconvenience.";
"Chat.Giveaway.Info.DidntWin" = "You didn't win a prize in this giveaway.";
"Chat.Giveaway.Info.ViewPrize" = "View My Prize";

"Chat.Giveaway.Info.FullDate" = "**%1$@** on **%2$@**";

"Chat.Giveaway.Toast.NotAllowed" = "You can't participate in this giveaway.";
"Chat.Giveaway.Toast.Participating" = "You are participating in this giveaway.";
"Chat.Giveaway.Toast.NotQualified" = "You are not qualified for this giveaway yet.";
Expand Down Expand Up @@ -10414,6 +10416,7 @@ Sorry for the inconvenience.";

"ChannelBoost.EnableColors" = "Enable Colors";
"ChannelBoost.EnableColorsText" = "Your channel needs %1$@ to change channel color.\n\nAsk your **Premium** subscribers to boost your channel with this link:";
"ChannelBoost.EnableColorsLevelText" = "Your channel needs **Level %1$@** to change channel color.\n\nAsk your **Premium** subscribers to boost your channel with this link:";
"ChannelBoost.BoostAgain" = "Boost Again";

"Settings.New" = "NEW";
Expand All @@ -10423,3 +10426,28 @@ Sorry for the inconvenience.";
"Channel.ChannelColor" = "Channel Color";

"TextFormat.Code" = "Code";

"Notification.ChannelJoinedByYou" = "You joined the channel";

"CountriesList.SelectCountries" = "Select Countries";
"CountriesList.SaveCountries" = "Save Countries";
"CountriesList.SelectUpTo_1" = "select up to %@ country";
"CountriesList.SelectUpTo_any" = "select up to %@ countries";

"Message.GiveawayOngoing" = "Giveaway: %1$@ on %2$@";
"Message.GiveawayOngoing.Winners_1" = "%@ winner to be selected";
"Message.GiveawayOngoing.Winners_any" = "%@ winners to be selected";

"Message.GiveawayFinished" = "Giveaway: %1$@ on %2$@";
"Message.GiveawayFinished.Winners_1" = "%@ winner was selected";
"Message.GiveawayFinished.Winners_any" = "%@ winners were selected";

"Conversation.PinnedGiveaway" = "Giveaway";

"Conversation.PinnedGiveaway.Ongoing" = "%1$@ on %2$@";
"Conversation.PinnedGiveaway.Ongoing.Winners_1" = "%@ winner to be selected";
"Conversation.PinnedGiveaway.Ongoing.Winners_any" = "%@ winners to be selected";

"Conversation.PinnedGiveaway.Finished" = "%1$@ on %2$@";
"Conversation.PinnedGiveaway.Finished.Winners_1" = "%@ winner was selected";
"Conversation.PinnedGiveaway.Finished.Winners_any" = "%@ winners were selected";
9 changes: 6 additions & 3 deletions submodules/AccountContext/Sources/AccountContext.swift
Original file line number Diff line number Diff line change
Expand Up @@ -1064,21 +1064,23 @@ public protocol AccountContext: AnyObject {

public struct PremiumConfiguration {
public static var defaultValue: PremiumConfiguration {
return PremiumConfiguration(isPremiumDisabled: false, showPremiumGiftInAttachMenu: false, showPremiumGiftInTextField: false, giveawayGiftsPurchaseAvailable: false, boostsPerGiftCount: 3)
return PremiumConfiguration(isPremiumDisabled: false, showPremiumGiftInAttachMenu: false, showPremiumGiftInTextField: false, giveawayGiftsPurchaseAvailable: false, boostsPerGiftCount: 3, minChannelNameColorLevel: 5)
}

public let isPremiumDisabled: Bool
public let showPremiumGiftInAttachMenu: Bool
public let showPremiumGiftInTextField: Bool
public let giveawayGiftsPurchaseAvailable: Bool
public let boostsPerGiftCount: Int32
public let minChannelNameColorLevel: Int32

fileprivate init(isPremiumDisabled: Bool, showPremiumGiftInAttachMenu: Bool, showPremiumGiftInTextField: Bool, giveawayGiftsPurchaseAvailable: Bool, boostsPerGiftCount: Int32) {
fileprivate init(isPremiumDisabled: Bool, showPremiumGiftInAttachMenu: Bool, showPremiumGiftInTextField: Bool, giveawayGiftsPurchaseAvailable: Bool, boostsPerGiftCount: Int32, minChannelNameColorLevel: Int32) {
self.isPremiumDisabled = isPremiumDisabled
self.showPremiumGiftInAttachMenu = showPremiumGiftInAttachMenu
self.showPremiumGiftInTextField = showPremiumGiftInTextField
self.giveawayGiftsPurchaseAvailable = giveawayGiftsPurchaseAvailable
self.boostsPerGiftCount = boostsPerGiftCount
self.minChannelNameColorLevel = minChannelNameColorLevel
}

public static func with(appConfiguration: AppConfiguration) -> PremiumConfiguration {
Expand All @@ -1088,7 +1090,8 @@ public struct PremiumConfiguration {
showPremiumGiftInAttachMenu: data["premium_gift_attach_menu_icon"] as? Bool ?? false,
showPremiumGiftInTextField: data["premium_gift_text_field_icon"] as? Bool ?? false,
giveawayGiftsPurchaseAvailable: data["giveaway_gifts_purchase_available"] as? Bool ?? false,
boostsPerGiftCount: Int32(data["boosts_per_sent_gift"] as? Double ?? 3)
boostsPerGiftCount: Int32(data["boosts_per_sent_gift"] as? Double ?? 3),
minChannelNameColorLevel: Int32(data["channel_color_level_min"] as? Double ?? 5)
)
} else {
return .defaultValue
Expand Down
15 changes: 12 additions & 3 deletions submodules/ChatListUI/Sources/Node/ChatListItemStrings.swift
Original file line number Diff line number Diff line change
Expand Up @@ -305,9 +305,18 @@ public func chatListItemStrings(strings: PresentationStrings, nameDisplayOrder:
} else {
messageText = strings.Notification_Story
}
case _ as TelegramMediaGiveaway:
messageText = strings.Message_Giveaway
case let webpage as TelegramMediaWebpage:
case let giveaway as TelegramMediaGiveaway:
let dateString = stringForDateWithoutYear(date: Date(timeIntervalSince1970: TimeInterval(giveaway.untilDate)), timeZone: .current, strings: strings)
let currentTime = Int32(CFAbsoluteTimeGetCurrent() + kCFAbsoluteTimeIntervalSince1970)
let isFinished = currentTime >= giveaway.untilDate
if isFinished {
let winnersString = strings.Message_GiveawayFinished_Winners(giveaway.quantity)
messageText = strings.Message_GiveawayFinished(winnersString, dateString).string
} else {
let winnersString = strings.Message_GiveawayOngoing_Winners(giveaway.quantity)
messageText = strings.Message_GiveawayOngoing(winnersString, dateString).string
}
case let webpage as TelegramMediaWebpage:
if messageText.isEmpty, case let .Loaded(content) = webpage.content {
messageText = content.displayUrl
}
Expand Down
7 changes: 7 additions & 0 deletions submodules/DatePickerNode/Sources/DatePickerNode.swift
Original file line number Diff line number Diff line change
Expand Up @@ -666,6 +666,13 @@ public final class DatePickerNode: ASDisplayNode {
}
}

if let date = calendar.date(from: dateComponents), date > self.maximumDate {
let maximumDateComponents = calendar.dateComponents([.hour, .minute, .day, .month, .year], from: self.maximumDate)
if let hour = maximumDateComponents.hour {
dateComponents.hour = hour - 1
}
}

if let date = calendar.date(from: dateComponents), date >= self.minimumDate && date < self.maximumDate {
let updatedState = State(minDate: self.state.minDate, maxDate: self.state.maxDate, date: date, displayingMonthSelection: self.state.displayingMonthSelection, displayingDateSelection: self.state.displayingDateSelection, displayingTimeSelection: self.state.displayingTimeSelection, selectedMonth: monthNode.month)
self.updateState(updatedState, animated: false)
Expand Down
104 changes: 55 additions & 49 deletions submodules/PremiumUI/Sources/CreateGiveawayController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -896,58 +896,58 @@ public func createGiveawayController(context: AccountContext, updatedPresentatio

buyActionImpl = { [weak controller] in
let state = stateValue.with { $0 }
guard let products = productsValue.with({ $0 }), !products.isEmpty else {
return
}


let presentationData = context.sharedContext.currentPresentationData.with { $0 }

var selectedProduct: PremiumGiftProduct?
let selectedMonths = state.selectedMonths ?? 12
switch state.mode {
case .giveaway:
if let product = products.first(where: { $0.months == selectedMonths && $0.giftOption.users == state.subscriptions }) {
selectedProduct = product
}
case .gift:
if let product = products.first(where: { $0.months == selectedMonths && $0.giftOption.users == 1 }) {
selectedProduct = product
}
}

guard let selectedProduct else {
let alertController = textAlertController(context: context, title: presentationData.strings.BoostGift_ReduceQuantity_Title, text: presentationData.strings.BoostGift_ReduceQuantity_Text("\(state.subscriptions)", "\(selectedMonths)", "\(25)").string, actions: [TextAlertAction(type: .genericAction, title: presentationData.strings.Common_Cancel, action: {}), TextAlertAction(type: .defaultAction, title: presentationData.strings.BoostGift_ReduceQuantity_Reduce, action: {
updateState { state in
var updatedState = state
updatedState.subscriptions = 25
return updatedState
}
})], parseMarkdown: true)
presentControllerImpl?(alertController)
return
}

let (currency, amount) = selectedProduct.storeProduct.priceCurrencyAndAmount

let purpose: AppStoreTransactionPurpose
let quantity: Int32
switch state.mode {
case .giveaway:
purpose = .giveaway(boostPeer: peerId, additionalPeerIds: state.channels.filter { $0 != peerId }, countries: state.countries, onlyNewSubscribers: state.onlyNewEligible, randomId: Int64.random(in: .min ..< .max), untilDate: state.time, currency: currency, amount: amount)
quantity = selectedProduct.giftOption.storeQuantity
case .gift:
purpose = .giftCode(peerIds: state.peers, boostPeer: peerId, currency: currency, amount: amount)
quantity = Int32(state.peers.count)
}

updateState { state in
var updatedState = state
updatedState.updating = true
return updatedState
}


switch subject {
case .generic:
guard let products = productsValue.with({ $0 }), !products.isEmpty else {
return
}
var selectedProduct: PremiumGiftProduct?
let selectedMonths = state.selectedMonths ?? 12
switch state.mode {
case .giveaway:
if let product = products.first(where: { $0.months == selectedMonths && $0.giftOption.users == state.subscriptions }) {
selectedProduct = product
}
case .gift:
if let product = products.first(where: { $0.months == selectedMonths && $0.giftOption.users == 1 }) {
selectedProduct = product
}
}

guard let selectedProduct else {
let alertController = textAlertController(context: context, title: presentationData.strings.BoostGift_ReduceQuantity_Title, text: presentationData.strings.BoostGift_ReduceQuantity_Text("\(state.subscriptions)", "\(selectedMonths)", "\(25)").string, actions: [TextAlertAction(type: .genericAction, title: presentationData.strings.Common_Cancel, action: {}), TextAlertAction(type: .defaultAction, title: presentationData.strings.BoostGift_ReduceQuantity_Reduce, action: {
updateState { state in
var updatedState = state
updatedState.subscriptions = 25
return updatedState
}
})], parseMarkdown: true)
presentControllerImpl?(alertController)
return
}

updateState { state in
var updatedState = state
updatedState.updating = true
return updatedState
}

let (currency, amount) = selectedProduct.storeProduct.priceCurrencyAndAmount

let purpose: AppStoreTransactionPurpose
let quantity: Int32
switch state.mode {
case .giveaway:
purpose = .giveaway(boostPeer: peerId, additionalPeerIds: state.channels.filter { $0 != peerId }, countries: state.countries, onlyNewSubscribers: state.onlyNewEligible, randomId: Int64.random(in: .min ..< .max), untilDate: state.time, currency: currency, amount: amount)
quantity = selectedProduct.giftOption.storeQuantity
case .gift:
purpose = .giftCode(peerIds: state.peers, boostPeer: peerId, currency: currency, amount: amount)
quantity = Int32(state.peers.count)
}

let _ = (context.engine.payments.canPurchasePremium(purpose: purpose)
|> deliverOnMainQueue).startStandalone(next: { [weak controller] available in
if available, let inAppPurchaseManager = context.inAppPurchaseManager {
Expand Down Expand Up @@ -1033,6 +1033,12 @@ public func createGiveawayController(context: AccountContext, updatedPresentatio
}
})
case let .prepaid(prepaidGiveaway):
updateState { state in
var updatedState = state
updatedState.updating = true
return updatedState
}

let _ = (context.engine.payments.launchPrepaidGiveaway(peerId: peerId, id: prepaidGiveaway.id, additionalPeerIds: state.channels.filter { $0 != peerId }, countries: state.countries, onlyNewSubscribers: state.onlyNewEligible, randomId: Int64.random(in: .min ..< .max), untilDate: state.time)
|> deliverOnMainQueue).startStandalone(completed: {
if let controller, let navigationController = controller.navigationController as? NavigationController {
Expand Down
11 changes: 9 additions & 2 deletions submodules/PremiumUI/Sources/GiveawayInfoController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,10 @@ public func presentGiveawayInfoController(

switch giveawayInfo {
case let .ongoing(start, status):
let startDate = stringForDate(timestamp: start, timeZone: timeZone, strings: presentationData.strings)
let startDate = presentationData.strings.Chat_Giveaway_Info_FullDate(
stringForMessageTimestamp(timestamp: start, dateTimeFormat: presentationData.dateTimeFormat),
stringForDate(timestamp: start, timeZone: timeZone, strings: presentationData.strings)
).string.trimmingCharacters(in: CharacterSet(charactersIn: "*"))

title = presentationData.strings.Chat_Giveaway_Info_Title

Expand Down Expand Up @@ -123,7 +126,11 @@ public func presentGiveawayInfoController(

text = "\(intro)\n\n\(ending)\(participation)"
case let .finished(status, start, finish, _, activatedCount):
let startDate = stringForDate(timestamp: start, timeZone: timeZone, strings: presentationData.strings)
let startDate = presentationData.strings.Chat_Giveaway_Info_FullDate(
stringForMessageTimestamp(timestamp: start, dateTimeFormat: presentationData.dateTimeFormat),
stringForDate(timestamp: start, timeZone: timeZone, strings: presentationData.strings)
).string.trimmingCharacters(in: CharacterSet(charactersIn: "*"))

let finishDate = stringForDate(timestamp: finish, timeZone: timeZone, strings: presentationData.strings)
title = presentationData.strings.Chat_Giveaway_Info_EndedTitle

Expand Down
4 changes: 4 additions & 0 deletions submodules/PremiumUI/Sources/PremiumLimitScreen.swift
Original file line number Diff line number Diff line change
Expand Up @@ -517,6 +517,10 @@ public class PremiumLimitDisplayComponent: Component {
countWidth = 51.0
case 4:
countWidth = 60.0
case 5:
countWidth = 74.0
case 6:
countWidth = 88.0
default:
countWidth = 51.0
}
Expand Down
Loading

0 comments on commit 037ebcf

Please sign in to comment.