no message

This commit is contained in:
Ilya Laktyushin 2018-09-07 00:35:43 +03:00
parent 1fc691a800
commit 43bbabfcbc
17 changed files with 288 additions and 128 deletions

View File

@ -90,6 +90,46 @@ public enum AvatarNodeColorOverride {
case blue
}
public final class AvatarEditOverlayNode: ASDisplayNode {
override public init() {
super.init()
self.isOpaque = false
self.displaysAsynchronously = true
}
@objc override public class func draw(_ bounds: CGRect, withParameters parameters: Any?, isCancelled: () -> Bool, isRasterizing: Bool) {
assertNotOnMainThread()
let context = UIGraphicsGetCurrentContext()!
if !isRasterizing {
context.setBlendMode(.copy)
context.setFillColor(UIColor.clear.cgColor)
context.fill(bounds)
}
context.beginPath()
context.addEllipse(in: CGRect(x: 0.0, y: 0.0, width: bounds.size.width, height:
bounds.size.height))
context.clip()
context.setFillColor(UIColor(rgb: 0x000000, alpha: 0.4).cgColor)
context.fill(bounds)
context.translateBy(x: bounds.size.width / 2.0, y: bounds.size.height / 2.0)
context.scaleBy(x: 1.0, y: -1.0)
context.translateBy(x: -bounds.size.width / 2.0, y: -bounds.size.height / 2.0)
context.setBlendMode(.normal)
if let editAvatarIcon = generateTintedImage(image: UIImage(bundleImageName: "Avatar/EditAvatarIcon"), color: .white) {
context.draw(editAvatarIcon.cgImage!, in: CGRect(origin: CGPoint(x: floor((bounds.size.width - editAvatarIcon.size.width) / 2.0), y: floor((bounds.size.height - editAvatarIcon.size.height) / 2.0)), size: editAvatarIcon.size))
}
}
}
public final class AvatarNode: ASDisplayNode {
var font: UIFont {
didSet {
@ -107,6 +147,7 @@ public final class AvatarNode: ASDisplayNode {
private var parameters: AvatarNodeParameters?
private var theme: PresentationTheme?
let imageNode: ImageNode
var editOverlayNode: AvatarEditOverlayNode?
private let imageReadyDisposable = MetaDisposable()
private var state: AvatarNodeState = .empty
@ -143,8 +184,10 @@ public final class AvatarNode: ASDisplayNode {
let updateImage = !value.size.equalTo(super.frame.size)
super.frame = value
self.imageNode.frame = CGRect(origin: CGPoint(), size: value.size)
self.editOverlayNode?.frame = self.imageNode.frame
if updateImage && !self.displaySuspended {
self.setNeedsDisplay()
self.editOverlayNode?.setNeedsDisplay()
}
}
}
@ -177,11 +220,24 @@ public final class AvatarNode: ASDisplayNode {
self.displaySuspended = true
self.contents = nil
let theme = account.telegramApplicationContext.currentPresentationData.with { $0 }.theme
if let signal = peerAvatarImage(account: account, peer: peer, authorOfMessage: authorOfMessage, representation: representation) {
self.imageReady.set(self.imageNode.ready)
self.imageNode.setSignal(signal)
parameters = AvatarNodeParameters(theme: account.telegramApplicationContext.currentPresentationData.with { $0 }.theme, accountPeerId: account.peerId, peerId: peer.id, letters: peer.displayLetters, font: self.font, icon: icon, explicitColorIndex: nil, hasImage: true)
if case .editAvatarIcon = icon {
if self.editOverlayNode == nil {
let editOverlayNode = AvatarEditOverlayNode()
editOverlayNode.frame = self.imageNode.frame
self.addSubnode(editOverlayNode)
self.editOverlayNode = editOverlayNode
}
self.editOverlayNode?.isHidden = false
}
parameters = AvatarNodeParameters(theme: theme, accountPeerId: account.peerId, peerId: peer.id, letters: peer.displayLetters, font: self.font, icon: icon, explicitColorIndex: nil, hasImage: true)
} else {
self.imageReady.set(.single(true))
self.displaySuspended = false
@ -189,7 +245,8 @@ public final class AvatarNode: ASDisplayNode {
self.imageNode.contents = nil
}
parameters = AvatarNodeParameters(theme: account.telegramApplicationContext.currentPresentationData.with { $0 }.theme, accountPeerId: account.peerId, peerId: peer.id, letters: peer.displayLetters, font: self.font, icon: icon, explicitColorIndex: nil, hasImage: false)
self.editOverlayNode?.isHidden = true
parameters = AvatarNodeParameters(theme: theme, accountPeerId: account.peerId, peerId: peer.id, letters: peer.displayLetters, font: self.font, icon: icon, explicitColorIndex: nil, hasImage: false)
}
if self.parameters == nil || self.parameters != parameters {
self.parameters = parameters

View File

@ -114,18 +114,17 @@ final class ChangePhoneNumberController: ViewController {
let text: String
switch error {
//TODO
case .limitExceeded:
text = "You have requested authorization code too many times. Please try again later."
text = presentationData.strings.Login_CodeFloodError
case .invalidPhoneNumber:
text = "The phone number you entered is not valid. Please enter the correct number along with your area code."
text = presentationData.strings.Login_InvalidPhoneError
case .phoneNumberOccupied:
text = "The number \(number) is already connected to a Telegram account. Please delete that account before migrating to the new number."
text = presentationData.strings.ChangePhone_ErrorOccupied(number).0
case .generic:
text = "An error occurred. Please try again later."
text = presentationData.strings.Login_UnknownError
}
strongSelf.present(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: "OK", action: {})]), in: .window(.root))
strongSelf.present(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), in: .window(.root))
}
}))
} else {

View File

@ -180,7 +180,7 @@ public final class ChatController: TelegramController, UIViewControllerPreviewin
self.messageId = messageId
self.botStart = botStart
let locationBroadcastPanelSource: LocationBroadcastPanelSource
var locationBroadcastPanelSource: LocationBroadcastPanelSource
switch chatLocation {
case let .peer(peerId):
@ -199,6 +199,8 @@ public final class ChatController: TelegramController, UIViewControllerPreviewin
var enableMediaAccessoryPanel = false
if case .standard = mode {
enableMediaAccessoryPanel = true
} else {
locationBroadcastPanelSource = .none
}
let navigationBarPresentationData: NavigationBarPresentationData?
switch mode {

View File

@ -49,7 +49,8 @@ func rightNavigationButtonForChatInterfaceState(_ presentationInterfaceState: Ch
}
}
if let peer = presentationInterfaceState.renderedPeer?.peer {
if case .standard(true) = presentationInterfaceState.mode {
} else if let peer = presentationInterfaceState.renderedPeer?.peer {
if presentationInterfaceState.accountPeerId == peer.id {
return ChatNavigationButton(action: .search, buttonItem: UIBarButtonItem(image: PresentationResourcesRootController.navigationCompactSearchIcon(presentationInterfaceState.theme), style: .plain, target: target, action: selector))
}

View File

@ -1506,7 +1506,7 @@ class ChatMessageBubbleItemNode: ChatMessageItemView {
if let sourceMessageId = forwardInfo.sourceMessageId {
item.controllerInteraction.navigateToMessage(item.message.id, sourceMessageId)
} else {
item.controllerInteraction.openPeer(forwardInfo.source?.id ?? forwardInfo.author.id, .chat(textInputState: nil, messageId: nil), nil)
item.controllerInteraction.openPeer(forwardInfo.source?.id ?? forwardInfo.author.id, .info, nil)
}
return
}

View File

@ -14,7 +14,7 @@ final class DateSelectionActionSheetController: ActionSheetController {
return self._ready
}
init(theme: PresentationTheme, strings: PresentationStrings, currentValue: Int32, emptyTitle: String? = nil, applyValue: @escaping (Int32?) -> Void) {
init(theme: PresentationTheme, strings: PresentationStrings, currentValue: Int32, minimumDate: Date? = nil, maximumDate: Date? = nil, emptyTitle: String? = nil, applyValue: @escaping (Int32?) -> Void) {
self.theme = theme
self.strings = strings
@ -24,7 +24,7 @@ final class DateSelectionActionSheetController: ActionSheetController {
var updatedValue = currentValue
var items: [ActionSheetItem] = []
items.append(DateSelectionActionSheetItem(strings: strings, currentValue: currentValue, valueChanged: { value in
items.append(DateSelectionActionSheetItem(strings: strings, currentValue: currentValue, minimumDate: minimumDate, maximumDate: maximumDate, valueChanged: { value in
updatedValue = value
}))
if let emptyTitle = emptyTitle {
@ -56,16 +56,20 @@ private final class DateSelectionActionSheetItem: ActionSheetItem {
let strings: PresentationStrings
let currentValue: Int32
let minimumDate: Date?
let maximumDate: Date?
let valueChanged: (Int32) -> Void
init(strings: PresentationStrings, currentValue: Int32, valueChanged: @escaping (Int32) -> Void) {
init(strings: PresentationStrings, currentValue: Int32, minimumDate: Date?, maximumDate: Date?, valueChanged: @escaping (Int32) -> Void) {
self.strings = strings
self.currentValue = roundDateToDays(currentValue)
self.minimumDate = minimumDate
self.maximumDate = maximumDate
self.valueChanged = valueChanged
}
func node(theme: ActionSheetControllerTheme) -> ActionSheetItemNode {
return DateSelectionActionSheetItemNode(theme: theme, strings: self.strings, currentValue: self.currentValue, valueChanged: self.valueChanged)
return DateSelectionActionSheetItemNode(theme: theme, strings: self.strings, currentValue: self.currentValue, minimumDate: self.minimumDate, maximumDate: self.maximumDate, valueChanged: self.valueChanged)
}
func updateNode(_ node: ActionSheetItemNode) {
@ -79,7 +83,7 @@ private final class DateSelectionActionSheetItemNode: ActionSheetItemNode {
private let valueChanged: (Int32) -> Void
private let pickerView: UIDatePicker
init(theme: ActionSheetControllerTheme, strings: PresentationStrings, currentValue: Int32, valueChanged: @escaping (Int32) -> Void) {
init(theme: ActionSheetControllerTheme, strings: PresentationStrings, currentValue: Int32, minimumDate: Date?, maximumDate: Date?, valueChanged: @escaping (Int32) -> Void) {
self.theme = theme
self.strings = strings
self.valueChanged = valueChanged
@ -88,7 +92,14 @@ private final class DateSelectionActionSheetItemNode: ActionSheetItemNode {
self.pickerView.datePickerMode = .date
self.pickerView.date = Date(timeIntervalSince1970: Double(roundDateToDays(currentValue)))
self.pickerView.locale = localeWithStrings(strings)
self.pickerView.maximumDate = Date(timeIntervalSince1970: Double(Int32.max - 1))
if let minimumDate = minimumDate {
self.pickerView.minimumDate = minimumDate
}
if let maximumDate = minimumDate {
self.pickerView.maximumDate = maximumDate
} else {
self.pickerView.maximumDate = Date(timeIntervalSince1970: Double(Int32.max - 1))
}
self.pickerView.setValue(theme.primaryTextColor, forKey: "textColor")

View File

@ -34,8 +34,8 @@ private enum SettingsEntry: ItemListNodeEntry {
case bioText(PresentationTheme, String, String)
case bioInfo(PresentationTheme, String)
case username(PresentationTheme, String, String)
case phoneNumber(PresentationTheme, String, String)
case username(PresentationTheme, String, String)
case logOut(PresentationTheme, String)
@ -45,7 +45,7 @@ private enum SettingsEntry: ItemListNodeEntry {
return SettingsSection.info.rawValue
case .bioText, .bioInfo:
return SettingsSection.bio.rawValue
case .username, .phoneNumber:
case .phoneNumber, .username:
return SettingsSection.personalData.rawValue
case .logOut:
return SettingsSection.logOut.rawValue
@ -62,9 +62,9 @@ private enum SettingsEntry: ItemListNodeEntry {
return 2
case .bioInfo:
return 3
case .username:
return 4
case .phoneNumber:
return 4
case .username:
return 5
case .logOut:
return 6
@ -123,14 +123,14 @@ private enum SettingsEntry: ItemListNodeEntry {
} else {
return false
}
case let .username(lhsTheme, lhsText, lhsAddress):
if case let .username(rhsTheme, rhsText, rhsAddress) = rhs, lhsTheme === rhsTheme, lhsText == rhsText, lhsAddress == rhsAddress {
case let .phoneNumber(lhsTheme, lhsText, lhsNumber):
if case let .phoneNumber(rhsTheme, rhsText, rhsNumber) = rhs, lhsTheme === rhsTheme, lhsText == rhsText, lhsNumber == rhsNumber {
return true
} else {
return false
}
case let .phoneNumber(lhsTheme, lhsText, lhsNumber):
if case let .phoneNumber(rhsTheme, rhsText, rhsNumber) = rhs, lhsTheme === rhsTheme, lhsText == rhsText, lhsNumber == rhsNumber {
case let .username(lhsTheme, lhsText, lhsAddress):
if case let .username(rhsTheme, rhsText, rhsAddress) = rhs, lhsTheme === rhsTheme, lhsText == rhsText, lhsAddress == rhsAddress {
return true
} else {
return false
@ -166,14 +166,14 @@ private enum SettingsEntry: ItemListNodeEntry {
})
case let .bioInfo(theme, text):
return ItemListTextItem(theme: theme, text: .plain(text), sectionId: self.section)
case let .username(theme, text, address):
return ItemListDisclosureItem(theme: theme, title: text, label: address, sectionId: ItemListSectionId(self.section), style: .blocks, action: {
arguments.presentController(usernameSetupController(account: arguments.account))
})
case let .phoneNumber(theme, text, number):
return ItemListDisclosureItem(theme: theme, title: text, label: number, sectionId: ItemListSectionId(self.section), style: .blocks, action: {
arguments.pushController(ChangePhoneNumberIntroController(account: arguments.account, phoneNumber: number))
})
case let .username(theme, text, address):
return ItemListDisclosureItem(theme: theme, title: text, label: address, sectionId: ItemListSectionId(self.section), style: .blocks, action: {
arguments.presentController(usernameSetupController(account: arguments.account))
})
case let .logOut(theme, text):
return ItemListActionItem(theme: theme, title: text, kind: .destructive, alignment: .center, sectionId: ItemListSectionId(self.section), style: .blocks, action: {
arguments.logout()
@ -248,11 +248,10 @@ private func editSettingsEntries(presentationData: PresentationData, state: Edit
entries.append(.bioText(presentationData.theme, state.editingBioText, presentationData.strings.UserInfo_About_Placeholder))
entries.append(.bioInfo(presentationData.theme, presentationData.strings.Settings_About_Help))
entries.append(.username(presentationData.theme, presentationData.strings.Settings_Username, peer.addressName == nil ? "" : ("@" + peer.addressName!)))
if let phone = peer.phone {
entries.append(.phoneNumber(presentationData.theme, presentationData.strings.Settings_PhoneNumber, formatPhoneNumber(phone)))
}
entries.append(.username(presentationData.theme, presentationData.strings.Settings_Username, peer.addressName == nil ? "" : ("@" + peer.addressName!)))
entries.append(.logOut(presentationData.theme, presentationData.strings.Settings_Logout))
}
@ -463,7 +462,7 @@ func editSettingsController(account: Account, currentName: ItemListAvatarAndName
}
let controller = ItemListController(account: account, state: signal, tabBarItem: (account.applicationContext as! TelegramApplicationContext).presentationData |> map { presentationData in
return ItemListControllerTabBarItem(title: presentationData.strings.Settings_Title, image: PresentationResourcesRootController.tabSettingsIcon(presentationData.theme), selectedImage: PresentationResourcesRootController.tabSettingsSelectedIcon(presentationData.theme))
return ItemListControllerTabBarItem(title: presentationData.strings.EditProfile_Title, image: PresentationResourcesRootController.tabSettingsIcon(presentationData.theme), selectedImage: PresentationResourcesRootController.tabSettingsSelectedIcon(presentationData.theme))
})
pushControllerImpl = { [weak controller] value in
(controller?.navigationController as? NavigationController)?.pushViewController(value)

View File

@ -5,17 +5,26 @@ import Display
private let textFont = Font.regular(17.0)
private let errorFont = Font.regular(13.0)
enum FormControllerTextInputItemType: Equatable {
case regular(capitalization: UITextAutocapitalizationType, autocorrection: Bool)
case latin
case email
case number
}
final class FormControllerTextInputItem: FormControllerItem {
let title: String
let text: String
let placeholder: String
let type: FormControllerTextInputItemType
let error: String?
let textUpdated: (String) -> Void
init(title: String, text: String, placeholder: String, error: String? = nil, textUpdated: @escaping (String) -> Void) {
init(title: String, text: String, placeholder: String, type: FormControllerTextInputItemType, error: String? = nil, textUpdated: @escaping (String) -> Void) {
self.title = title
self.text = text
self.placeholder = placeholder
self.type = type
self.error = error
self.textUpdated = textUpdated
}
@ -81,6 +90,39 @@ final class FormControllerTextInputItemNode: FormBlockItemNode<FormControllerTex
return (FormControllerItemPreLayout(aligningInset: aligningInset), { params in
transition.updateFrame(node: self.titleNode, frame: CGRect(origin: CGPoint(x: leftInset, y: 11.0), size: titleSize))
let capitalizationType: UITextAutocapitalizationType
let autocorrectionType: UITextAutocorrectionType
let keyboardType: UIKeyboardType
switch item.type {
case let .regular(capitalization, autocorrection):
capitalizationType = capitalization
autocorrectionType = autocorrection ? .default : .no
keyboardType = .default
case .latin:
capitalizationType = .words
autocorrectionType = .no
keyboardType = .asciiCapable
case .email:
capitalizationType = .none
autocorrectionType = .no
keyboardType = .emailAddress
case .number:
capitalizationType = .none
autocorrectionType = .no
keyboardType = .numberPad
}
if self.textField.textField.keyboardType != keyboardType {
self.textField.textField.keyboardType = keyboardType
}
if self.textField.textField.autocapitalizationType != capitalizationType {
self.textField.textField.autocapitalizationType = capitalizationType
}
if self.textField.textField.autocorrectionType != autocorrectionType {
self.textField.textField.autocorrectionType = autocorrectionType
}
let attributedPlaceholder = NSAttributedString(string: item.placeholder, font: textFont, textColor: theme.list.itemPlaceholderTextColor)
if !(self.textField.textField.attributedPlaceholder?.isEqual(to: attributedPlaceholder) ?? false) {
self.textField.textField.attributedPlaceholder = attributedPlaceholder

View File

@ -226,7 +226,10 @@ final class JoinLinkPreviewControllerNode: ViewControllerTracingNode, UIScrollVi
let cleanInsets = layout.insets(options: [.statusBar])
insets.top = max(10.0, insets.top)
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0
let titleAreaHeight: CGFloat = 64.0
@ -239,7 +242,7 @@ final class JoinLinkPreviewControllerNode: ViewControllerTracingNode, UIScrollVi
let contentContainerFrame = CGRect(origin: CGPoint(x: sideInset, y: insets.top), size: CGSize(width: width, height: maximumContentHeight))
let contentFrame = contentContainerFrame.insetBy(dx: 0.0, dy: 0.0)
var bottomGridInset = buttonHeight
let bottomGridInset = buttonHeight
self.containerLayout = (layout, navigationBarHeight, bottomGridInset)
self.scheduledLayoutTransitionRequest = nil
@ -272,7 +275,10 @@ final class JoinLinkPreviewControllerNode: ViewControllerTracingNode, UIScrollVi
insets.top = max(10.0, insets.top)
let cleanInsets = layout.insets(options: [.statusBar])
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0

View File

@ -126,7 +126,7 @@ func legacyLocationController(message: Message, mapMedia: TelegramMediaMap, acco
let presentationData = account.telegramApplicationContext.currentPresentationData.with { $0 }
let legacyController = LegacyController(presentation: .navigation, theme: presentationData.theme, presentationData: presentationData)
let legacyController = LegacyController(presentation: modal ? .modal(animateIn: true) : .navigation, theme: presentationData.theme, presentationData: presentationData)
let legacyMessage = makeLegacyMessage(message)

View File

@ -30,6 +30,7 @@ func legacyLocationPickerController(account: Account, selfPeer: Peer, peer: Peer
legacyController?.dismiss()
}, rootController: nil)
legacyController.bind(controller: navigationController)
legacyController.supportedOrientations = ViewControllerSupportedOrientations(regularSize: .all, compactSize: .portrait)
controller.locationPicked = { [weak legacyController] coordinate, venue in
sendLocation(coordinate, venue.flatMap { venue in
return MapVenue(title: venue.title, address: venue.address, provider: venue.provider, id: venue.venueId, type: venue.type)

View File

@ -1555,19 +1555,19 @@ enum SecureIdDocumentFormEntry: FormControllerEntry {
}
return FormControllerHeaderItem(text: text)
case let .identifier(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_DocumentNumber, text: value, placeholder: strings.Passport_Identity_DocumentNumberPlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_DocumentNumber, text: value, placeholder: strings.Passport_Identity_DocumentNumberPlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.identifier, text)
})
case let .firstName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_Name, text: value, placeholder: strings.Passport_Identity_NamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_Name, text: value, placeholder: strings.Passport_Identity_NamePlaceholder, type: .latin, error: error, textUpdated: { text in
params.updateText(.firstName, text)
})
case let .middleName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_MiddleName, text: value, placeholder: strings.Passport_Identity_MiddleNamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_MiddleName, text: value, placeholder: strings.Passport_Identity_MiddleNamePlaceholder, type: .latin, error: error, textUpdated: { text in
params.updateText(.middleName, text)
})
case let .lastName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_Surname, text: value, placeholder: strings.Passport_Identity_SurnamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_Surname, text: value, placeholder: strings.Passport_Identity_SurnamePlaceholder, type: .latin, error: error, textUpdated: { text in
params.updateText(.lastName, text)
})
case let .nativeInfoHeader(language):
@ -1579,23 +1579,23 @@ enum SecureIdDocumentFormEntry: FormControllerEntry {
}
return FormControllerHeaderItem(text: title)
case let .nativeFirstName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_Name, text: value, placeholder: strings.Passport_Identity_NamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_Name, text: value, placeholder: strings.Passport_Identity_NamePlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.nativeFirstName, text)
})
case let .nativeMiddleName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_MiddleName, text: value, placeholder: strings.Passport_Identity_MiddleNamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_MiddleName, text: value, placeholder: strings.Passport_Identity_MiddleNamePlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.nativeMiddleName, text)
})
case let .nativeLastName(value, error):
return FormControllerTextInputItem(title: strings.Passport_Identity_Surname, text: value, placeholder: strings.Passport_Identity_SurnamePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Identity_Surname, text: value, placeholder: strings.Passport_Identity_SurnamePlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.nativeLastName, text)
})
case let .nativeInfo(language):
let text: String
if !language.isEmpty, let value = strings.dict["Passport.Language.\(language)"] {
text = strings.Passport_Identity_NativeNameGenericHelp(value).0.uppercased()
} else {
if !language.isEmpty, let _ = strings.dict["Passport.Language.\(language)"] {
text = strings.Passport_Identity_NativeNameHelp
} else {
text = strings.Passport_Identity_NativeNameGenericHelp("").0
}
return FormControllerTextItem(text: text)
case let .gender(value, error):
@ -1632,23 +1632,23 @@ enum SecureIdDocumentFormEntry: FormControllerEntry {
params.deleteValue()
})
case let .street1(value, error):
return FormControllerTextInputItem(title: strings.Passport_Address_Street, text: value, placeholder: strings.Passport_Address_Street1Placeholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Address_Street, text: value, placeholder: strings.Passport_Address_Street1Placeholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.street1, text)
})
case let .street2(value, error):
return FormControllerTextInputItem(title: "", text: value, placeholder: strings.Passport_Address_Street2Placeholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: "", text: value, placeholder: strings.Passport_Address_Street2Placeholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.street2, text)
})
case let .city(value, error):
return FormControllerTextInputItem(title: strings.Passport_Address_City, text: value, placeholder: strings.Passport_Address_CityPlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Address_City, text: value, placeholder: strings.Passport_Address_CityPlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.city, text)
})
case let .state(value, error):
return FormControllerTextInputItem(title: strings.Passport_Address_Region, text: value, placeholder: strings.Passport_Address_RegionPlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Address_Region, text: value, placeholder: strings.Passport_Address_RegionPlaceholder, type: .regular(capitalization: .words, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.state, text)
})
case let .postcode(value, error):
return FormControllerTextInputItem(title: strings.Passport_Address_Postcode, text: value, placeholder: strings.Passport_Address_PostcodePlaceholder, error: error, textUpdated: { text in
return FormControllerTextInputItem(title: strings.Passport_Address_Postcode, text: value, placeholder: strings.Passport_Address_PostcodePlaceholder, type: .regular(capitalization: .allCharacters, autocorrection: false), error: error, textUpdated: { text in
params.updateText(.postcode, text)
})
case .requestedDocumentsHeader:
@ -1883,10 +1883,26 @@ final class SecureIdDocumentFormControllerNode: FormControllerNode<SecureIdDocum
strongSelf.present(controller, ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
case let .date(current, field):
var emptyTitle: String?
var minimumDate: Date? = nil
var maximumDate: Date? = nil
let calendar = Calendar(identifier: .gregorian)
let now = Date()
if case .expiry = field {
emptyTitle = strings.Passport_Identity_DoesNotExpire
var components = calendar.dateComponents([.year, .month, .day], from: now)
if let year = components.year {
components.year = year - 18
components.hour = 0
components.minute = 0
maximumDate = calendar.date(from: components)
}
} else if case .birthdate = field {
var deltaComponents = DateComponents()
deltaComponents.month = 6
minimumDate = calendar.date(byAdding: deltaComponents, to: now)
}
let controller = DateSelectionActionSheetController(theme: theme, strings: strings, currentValue: current ?? Int32(Date().timeIntervalSince1970), emptyTitle: emptyTitle, applyValue: { value in
let controller = DateSelectionActionSheetController(theme: theme, strings: strings, currentValue: current ?? Int32(Date().timeIntervalSince1970), minimumDate: minimumDate, maximumDate: maximumDate, emptyTitle: emptyTitle, applyValue: { value in
if let strongSelf = self, var innerState = strongSelf.innerState {
innerState.documentState.updateDateField(type: field, value: value.flatMap(SecureIdDate.init))
var valueKey: SecureIdValueKey?

View File

@ -509,17 +509,17 @@ enum SecureIdPlaintextFormEntry: FormControllerEntry {
case .numberInputInfo:
return FormControllerTextItem(text: strings.Passport_Phone_Help)
case let .numberCode(code):
return FormControllerTextInputItem(title: strings.ChangePhoneNumberCode_CodePlaceholder, text: code, placeholder: strings.ChangePhoneNumberCode_CodePlaceholder, textUpdated: { value in
return FormControllerTextInputItem(title: strings.ChangePhoneNumberCode_CodePlaceholder, text: code, placeholder: strings.ChangePhoneNumberCode_CodePlaceholder, type: .number, textUpdated: { value in
params.updateTextField(.code, value)
})
case .numberVerifyInfo:
return FormControllerTextItem(text: strings.ChangePhoneNumberCode_Help)
case let .emailAddress(address):
return FormControllerTextInputItem(title: strings.TwoStepAuth_Email, text: address, placeholder: strings.TwoStepAuth_Email, textUpdated: { value in
return FormControllerTextInputItem(title: strings.TwoStepAuth_Email, text: address, placeholder: strings.TwoStepAuth_Email, type: .email, textUpdated: { value in
params.updateTextField(.email, value)
})
case let .emailCode(code):
return FormControllerTextInputItem(title: strings.TwoStepAuth_RecoveryCode, text: code, placeholder: strings.TwoStepAuth_RecoveryCode, textUpdated: { value in
return FormControllerTextInputItem(title: strings.TwoStepAuth_RecoveryCode, text: code, placeholder: strings.TwoStepAuth_RecoveryCode, type: .number, textUpdated: { value in
params.updateTextField(.code, value)
})
case .emailVerifyInfo:
@ -563,10 +563,10 @@ final class SecureIdPlaintextFormControllerNode: FormControllerNode<SecureIdPlai
guard let strongSelf = self else {
return
}
let controller = AuthorizationSequenceCountrySelectionController(strings: strings, theme: AuthorizationSequenceCountrySelectionTheme(presentationTheme: strongSelf.theme), displayCodes: false)
controller.completeWithCountryCode = { _, id in
let controller = AuthorizationSequenceCountrySelectionController(strings: strings, theme: AuthorizationSequenceCountrySelectionTheme(presentationTheme: strongSelf.theme), displayCodes: true)
controller.completeWithCountryCode = { code, _ in
if let strongSelf = self, var innerState = strongSelf.innerState {
innerState.data.updateTextField(type: .countryCode, value: "+\(id)")
innerState.data.updateTextField(type: .countryCode, value: "+\(code)")
strongSelf.updateInnerState(transition: .immediate, with: innerState)
}
}

View File

@ -318,7 +318,11 @@ final class ShareControllerNode: ViewControllerTracingNode, UIScrollViewDelegate
let cleanInsets = layout.insets(options: [.statusBar])
insets.top = max(10.0, insets.top)
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0
let titleAreaHeight: CGFloat = 64.0
@ -378,7 +382,10 @@ final class ShareControllerNode: ViewControllerTracingNode, UIScrollViewDelegate
insets.top = max(10.0, insets.top)
let cleanInsets = layout.insets(options: [.statusBar])
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0

View File

@ -245,7 +245,11 @@ final class StickerPackPreviewControllerNode: ViewControllerTracingNode, UIScrol
transition.updateFrame(node: self.dimNode, frame: CGRect(origin: CGPoint(), size: layout.size))
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0
let titleAreaHeight: CGFloat = 51.0
@ -352,7 +356,11 @@ final class StickerPackPreviewControllerNode: ViewControllerTracingNode, UIScrol
insets.top = max(10.0, insets.top)
let cleanInsets = layout.insets(options: [.statusBar])
let bottomInset: CGFloat = 10.0 + cleanInsets.bottom
var bottomInset: CGFloat = 10.0 + cleanInsets.bottom
if insets.bottom > 0 {
bottomInset -= 12.0
}
let buttonHeight: CGFloat = 57.0
let sectionSpacing: CGFloat = 8.0
let titleAreaHeight: CGFloat = 51.0

View File

@ -44,7 +44,7 @@ private enum TwoStepVerificationPasswordEntryEntry: ItemListNodeEntry {
case hintTitle(PresentationTheme, String)
case hintEntry(PresentationTheme, String)
case emailEntry(PresentationTheme, String)
case emailEntry(PresentationTheme, PresentationStrings, String)
case emailInfo(PresentationTheme, String)
var section: ItemListSectionId {
@ -94,8 +94,8 @@ private enum TwoStepVerificationPasswordEntryEntry: ItemListNodeEntry {
} else {
return false
}
case let .emailEntry(lhsTheme, lhsText):
if case let .emailEntry(rhsTheme, rhsText) = rhs, lhsTheme === rhsTheme, lhsText == rhsText {
case let .emailEntry(lhsTheme, lhsStrings, lhsText):
if case let .emailEntry(rhsTheme, rhsStrings, rhsText) = rhs, lhsTheme === rhsTheme, lhsStrings === rhsStrings, lhsText == rhsText {
return true
} else {
return false
@ -131,8 +131,8 @@ private enum TwoStepVerificationPasswordEntryEntry: ItemListNodeEntry {
}, action: {
arguments.next()
})
case let .emailEntry(theme, text):
return ItemListSingleLineInputItem(theme: theme, title: NSAttributedString(string: "E-Mail", textColor: .black), text: text, placeholder: "", type: .email, spacing: 10.0, tag: TwoStepVerificationPasswordEntryTag.input, sectionId: self.section, textUpdated: { updatedText in
case let .emailEntry(theme, strings, text):
return ItemListSingleLineInputItem(theme: theme, title: NSAttributedString(string: strings.TwoStepAuth_Email, textColor: .black), text: text, placeholder: "", type: .email, spacing: 10.0, tag: TwoStepVerificationPasswordEntryTag.input, sectionId: self.section, textUpdated: { updatedText in
arguments.updateEntryText(updatedText)
}, action: {
arguments.next()
@ -235,7 +235,7 @@ private func twoStepVerificationPasswordEntryControllerEntries(presentationData:
entries.append(.hintTitle(presentationData.theme, presentationData.strings.TwoStepAuth_SetupHint))
entries.append(.hintEntry(presentationData.theme, text))
case let .email(_, _, text):
entries.append(.emailEntry(presentationData.theme, text))
entries.append(.emailEntry(presentationData.theme, presentationData.strings, text))
entries.append(.emailInfo(presentationData.theme, presentationData.strings.TwoStepAuth_EmailHelp))
}
@ -341,11 +341,11 @@ func twoStepVerificationPasswordEntryController(account: Account, mode: TwoStepV
let alertText: String
switch error {
case .generic:
alertText = "An error occurred."
alertText = presentationData.strings.Login_UnknownError
case .invalidEmail:
alertText = "Please enter valid e-mail address."
alertText = presentationData.strings.TwoStepAuth_EmailInvalid
}
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: alertText, actions: [TextAlertAction(type: .defaultAction, title: "OK", action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: alertText, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}))
case let .setupEmail(password):
updatePasswordDisposable.set((updateTwoStepVerificationEmail(account: account, currentPassword: password, updatedEmail: email) |> deliverOnMainQueue).start(next: { update in
@ -366,16 +366,16 @@ func twoStepVerificationPasswordEntryController(account: Account, mode: TwoStepV
let alertText: String
switch error {
case .generic:
alertText = "An error occurred."
alertText = presentationData.strings.Login_UnknownError
case .invalidEmail:
alertText = "Please enter valid e-mail address."
alertText = presentationData.strings.TwoStepAuth_EmailInvalid
}
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: alertText, actions: [TextAlertAction(type: .defaultAction, title: "OK", action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: alertText, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}))
}
} else if invalidReentry {
let presentationData = account.telegramApplicationContext.currentPresentationData.with { $0 }
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: "Passwords don't match.\nPlease try again.", actions: [TextAlertAction(type: .defaultAction, title: "OK", action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: presentationData.strings.TwoStepAuth_SetupPasswordConfirmFailed, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}
}

View File

@ -223,7 +223,7 @@ private struct TwoStepVerificationUnlockSettingsControllerState: Equatable {
}
}
private func twoStepVerificationUnlockSettingsControllerEntries(presentationData: PresentationData, state: TwoStepVerificationUnlockSettingsControllerState,data: TwoStepVerificationUnlockSettingsControllerData) -> [TwoStepVerificationUnlockSettingsEntry] {
private func twoStepVerificationUnlockSettingsControllerEntries(presentationData: PresentationData, state: TwoStepVerificationUnlockSettingsControllerState, data: TwoStepVerificationUnlockSettingsControllerData) -> [TwoStepVerificationUnlockSettingsEntry] {
var entries: [TwoStepVerificationUnlockSettingsEntry] = []
switch data {
@ -237,7 +237,7 @@ private func twoStepVerificationUnlockSettingsControllerEntries(presentationData
} else {
entries.append(.pendingEmailInfo(presentationData.theme, presentationData.strings.TwoStepAuth_ConfirmationText + "\n\n\(pendingEmailPattern)\n\n[" + presentationData.strings.TwoStepAuth_ConfirmationAbort + "]()"))
}
case let .set(hint, _, _):
case let .set(hint, _, _, _):
entries.append(.passwordEntry(presentationData.theme, presentationData.strings.TwoStepAuth_EnterPasswordPassword, state.passwordText))
if hint.isEmpty {
entries.append(.passwordEntryInfo(presentationData.theme, presentationData.strings.TwoStepAuth_EnterPasswordHelp + "\n\n[" + presentationData.strings.TwoStepAuth_EnterPasswordForgot + "](forgot)"))
@ -246,7 +246,7 @@ private func twoStepVerificationUnlockSettingsControllerEntries(presentationData
}
}
}
case let .manage(_, emailSet, pendingEmailPattern):
case let .manage(_, emailSet, pendingEmailPattern, _):
entries.append(.changePassword(presentationData.theme, presentationData.strings.TwoStepAuth_ChangePassword))
entries.append(.turnPasswordOff(presentationData.theme, presentationData.strings.TwoStepAuth_RemovePassword))
entries.append(.setupRecoveryEmail(presentationData.theme, emailSet ? presentationData.strings.TwoStepAuth_ChangeEmail : presentationData.strings.TwoStepAuth_SetupEmail))
@ -262,12 +262,12 @@ private func twoStepVerificationUnlockSettingsControllerEntries(presentationData
enum TwoStepVerificationUnlockSettingsControllerMode {
case access
case manage(password: String, email: String, pendingEmailPattern: String)
case manage(password: String, email: String, pendingEmailPattern: String, hasSecureValues: Bool)
}
private enum TwoStepVerificationUnlockSettingsControllerData {
case access(configuration: TwoStepVerificationConfiguration?)
case manage(password: String, emailSet: Bool, pendingEmailPattern: String)
case manage(password: String, emailSet: Bool, pendingEmailPattern: String, hasSecureValues: Bool)
}
func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStepVerificationUnlockSettingsControllerMode) -> ViewController {
@ -298,8 +298,8 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
switch mode {
case .access:
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.access(configuration: nil)) |> then(twoStepVerificationConfiguration(account: account) |> map { TwoStepVerificationUnlockSettingsControllerData.access(configuration: $0) }))
case let .manage(password, email, pendingEmailPattern):
dataPromise.set(.single(.manage(password: password, emailSet: !email.isEmpty, pendingEmailPattern: pendingEmailPattern)))
case let .manage(password, email, pendingEmailPattern, hasSecureValues):
dataPromise.set(.single(.manage(password: password, emailSet: !email.isEmpty, pendingEmailPattern: pendingEmailPattern, hasSecureValues: hasSecureValues)))
}
let arguments = TwoStepVerificationUnlockSettingsControllerArguments(updatePasswordText: { updatedText in
@ -313,7 +313,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
if let configuration = configuration {
let presentationData = account.telegramApplicationContext.currentPresentationData.with { $0 }
switch configuration {
case let .set(_, hasRecoveryEmail, _):
case let .set(_, hasRecoveryEmail, _, _):
if hasRecoveryEmail {
updateState {
$0.withUpdatedChecking(true)
@ -336,7 +336,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: presentationData.strings.Login_UnknownError, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}))
} else {
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: "Since you haven't provided a recovery e-mail when setting up your password, your remaining options are either to remember your password or to reset your account.", actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: presentationData.strings.TwoStepAuth_RecoveryUnavailable, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}
case .notSet:
break
@ -361,7 +361,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
if let pendingEmailPattern = updatedPassword.pendingEmailPattern {
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.access(configuration: TwoStepVerificationConfiguration.notSet(pendingEmailPattern: pendingEmailPattern))))
} else {
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: false, pendingEmailPattern: "")))
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: false, pendingEmailPattern: "", hasSecureValues: false)))
}
controller?.dismiss()
}
@ -370,69 +370,80 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
break
}
}
case let .manage(password, emailSet, pendingEmailPattern):
case let .manage(password, emailSet, pendingEmailPattern, hasSecureValues):
let result = Promise<TwoStepVerificationPasswordEntryResult?>()
let controller = twoStepVerificationPasswordEntryController(account: account, mode: .change(current: password), result: result)
presentControllerImpl?(controller, ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
setupResultDisposable.set((result.get() |> take(1) |> deliverOnMainQueue).start(next: { [weak controller] updatedPassword in
if let updatedPassword = updatedPassword {
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: emailSet, pendingEmailPattern: pendingEmailPattern)))
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: emailSet, pendingEmailPattern: pendingEmailPattern, hasSecureValues: hasSecureValues)))
controller?.dismiss()
}
}))
}
}))
}, openDisablePassword: {
let presentationData = account.telegramApplicationContext.currentPresentationData.with { $0 }
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: "Are you sure you want to disable your password?", actions: [TextAlertAction(type: .defaultAction, title: "Cancel", action: {}), TextAlertAction(type: .genericAction, title: "OK", action: {
var disablePassword = false
updateState { state in
if state.checking {
return state
} else {
disablePassword = true
return state.withUpdatedChecking(true)
}
}
if disablePassword {
setupDisposable.set((dataPromise.get()
|> take(1)
|> mapError { _ -> UpdateTwoStepVerificationPasswordError in return .generic }
|> mapToSignal { data -> Signal<Void, UpdateTwoStepVerificationPasswordError> in
switch data {
case .access:
return .complete()
case let .manage(password, _, _):
return updateTwoStepVerificationPassword(network: account.network, currentPassword: password, updatedPassword: .none)
|> mapToSignal { _ -> Signal<Void, UpdateTwoStepVerificationPasswordError> in
setupDisposable.set((dataPromise.get() |> take(1) |> deliverOnMainQueue).start(next: { data in
switch data {
case let .manage(_, _, _, hasSecureValues):
let presentationData = account.telegramApplicationContext.currentPresentationData.with { $0 }
var text = presentationData.strings.TwoStepAuth_PasswordRemoveConfirmation
if hasSecureValues {
text = presentationData.strings.TwoStepAuth_PasswordRemovePassportConfirmation
}
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_Cancel, action: {}), TextAlertAction(type: .genericAction, title: presentationData.strings.Common_OK, action: {
var disablePassword = false
updateState { state in
if state.checking {
return state
} else {
disablePassword = true
return state.withUpdatedChecking(true)
}
}
if disablePassword {
setupDisposable.set((dataPromise.get()
|> take(1)
|> mapError { _ -> UpdateTwoStepVerificationPasswordError in return .generic }
|> mapToSignal { data -> Signal<Void, UpdateTwoStepVerificationPasswordError> in
switch data {
case .access:
return .complete()
case let .manage(password, _, _, _):
return updateTwoStepVerificationPassword(network: account.network, currentPassword: password, updatedPassword: .none)
|> mapToSignal { _ -> Signal<Void, UpdateTwoStepVerificationPasswordError> in
return .complete()
}
}
}
|> deliverOnMainQueue).start(error: { _ in
updateState {
$0.withUpdatedChecking(false)
}
}, completed: {
updateState {
$0.withUpdatedChecking(false)
}
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.access(configuration: .notSet(pendingEmailPattern: ""))))
}))
}
}
|> deliverOnMainQueue).start(error: { _ in
updateState {
$0.withUpdatedChecking(false)
}
}, completed: {
updateState {
$0.withUpdatedChecking(false)
}
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.access(configuration: .notSet(pendingEmailPattern: ""))))
}))
})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
default:
break
}
})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}))
}, openSetupEmail: {
setupDisposable.set((dataPromise.get() |> take(1) |> deliverOnMainQueue).start(next: { data in
switch data {
case .access:
break
case let .manage(password, _, _):
case let .manage(password, _, _, hasSecureValues):
let result = Promise<TwoStepVerificationPasswordEntryResult?>()
let controller = twoStepVerificationPasswordEntryController(account: account, mode: .setupEmail(password: password), result: result)
presentControllerImpl?(controller, ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
setupResultDisposable.set((result.get() |> take(1) |> deliverOnMainQueue).start(next: { [weak controller] updatedPassword in
if let updatedPassword = updatedPassword {
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: true, pendingEmailPattern: updatedPassword.pendingEmailPattern ?? "")))
dataPromise.set(.single(TwoStepVerificationUnlockSettingsControllerData.manage(password: updatedPassword.password, emailSet: true, pendingEmailPattern: updatedPassword.pendingEmailPattern ?? "", hasSecureValues: hasSecureValues)))
controller?.dismiss()
}
}))
@ -472,7 +483,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
switch configuration {
case .notSet:
break
case .set:
case let .set(_, _, _, hasSecureValues):
rightNavigationButton = ItemListNavigationButton(content: .text(presentationData.strings.Common_Next), style: .bold, enabled: true, action: {
var wasChecking = false
var password: String?
@ -488,7 +499,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
$0.withUpdatedChecking(false)
}
replaceControllerImpl?(twoStepVerificationUnlockSettingsController(account: account, mode: .manage(password: password, email: settings.email, pendingEmailPattern: "")))
replaceControllerImpl?(twoStepVerificationUnlockSettingsController(account: account, mode: .manage(password: password, email: settings.email, pendingEmailPattern: "", hasSecureValues: hasSecureValues)))
}, error: { error in
updateState {
$0.withUpdatedChecking(false)
@ -506,7 +517,7 @@ func twoStepVerificationUnlockSettingsController(account: Account, mode: TwoStep
text = presentationData.strings.Login_UnknownError
}
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: "OK", action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
presentControllerImpl?(standardTextAlertController(theme: AlertControllerTheme(presentationTheme: presentationData.theme), title: nil, text: text, actions: [TextAlertAction(type: .defaultAction, title: presentationData.strings.Common_OK, action: {})]), ViewControllerPresentationArguments(presentationAnimation: .modalSheet))
}))
}
})