Browse Source

basic webxdc draft support

cyberta 3 năm trước cách đây
mục cha
commit
baf5d93c39

+ 14 - 9
deltachat-ios/Chat/ChatViewController.swift

@@ -1478,7 +1478,7 @@ class ChatViewController: UITableViewController {
 
     private func stageDocument(url: NSURL) {
         keepKeyboard = true
-        self.draft.setAttachment(viewType: DC_MSG_FILE, path: url.relativePath)
+        self.draft.setAttachment(viewType: url.pathExtension == "xdc" ? DC_MSG_WEBXDC : DC_MSG_FILE, path: url.relativePath)
         self.configureDraftArea(draft: self.draft)
         self.messageInputBar.inputTextView.becomeFirstResponder()
     }
@@ -1850,6 +1850,7 @@ extension ChatViewController: InputBarAccessoryViewDelegate {
         }
         inputBar.inputTextView.text = String()
         inputBar.inputTextView.attributedText = nil
+        draft.clear()
         draftArea.cancel()
     }
 
@@ -1869,7 +1870,7 @@ extension ChatViewController: DraftPreviewDelegate {
 
     func onCancelAttachment() {
         keepKeyboard = true
-        draft.setAttachment(viewType: nil, path: nil, mimetype: nil)
+        draft.clearAttachment()
         configureDraftArea(draft: draft)
         evaluateInputBar(draft: draft)
     }
@@ -1881,14 +1882,18 @@ extension ChatViewController: DraftPreviewDelegate {
     func onAttachmentTapped() {
         if let attachmentPath = draft.attachment {
             let attachmentURL = URL(fileURLWithPath: attachmentPath, isDirectory: false)
-            let previewController = PreviewController(dcContext: dcContext, type: .single(attachmentURL))
-            if #available(iOS 13.0, *), draft.viewType == DC_MSG_IMAGE || draft.viewType == DC_MSG_VIDEO {
-                previewController.setEditing(true, animated: true)
-                previewController.delegate = self
+            if draft.viewType == DC_MSG_WEBXDC, let draftMessage = draft.draftMsg {
+                showWebxdcViewFor(message: draftMessage)
+            } else {
+                let previewController = PreviewController(dcContext: dcContext, type: .single(attachmentURL))
+                if #available(iOS 13.0, *), draft.viewType == DC_MSG_IMAGE || draft.viewType == DC_MSG_VIDEO {
+                    previewController.setEditing(true, animated: true)
+                    previewController.delegate = self
+                }
+                let nav = UINavigationController(rootViewController: previewController)
+                nav.modalPresentationStyle = .fullScreen
+                navigationController?.present(nav, animated: true)
             }
-            let nav = UINavigationController(rootViewController: previewController)
-            nav.modalPresentationStyle = .fullScreen
-            navigationController?.present(nav, animated: true)
         }
     }
 }

+ 55 - 34
deltachat-ios/Chat/DraftModel.swift

@@ -3,15 +3,29 @@ import UIKit
 import DcCore
 
 public class DraftModel {
-    var quoteMessage: DcMsg?
+    var draftMsg: DcMsg?
     var dcContext: DcContext
-    var quoteText: String?
     var text: String?
-    var attachment: String?
-    var attachmentMimeType: String?
-    var viewType: Int32?
     let chatId: Int
     var isEditing: Bool = false
+    var quoteMessage: DcMsg? {
+        return draftMsg?.quoteMessage
+    }
+    var quoteText: String? {
+        return draftMsg?.quoteText
+    }
+    var attachment: String? {
+        return draftMsg?.fileURL?.relativePath
+    }
+    var attachmentMimeType: String? {
+        return draftMsg?.filemime
+    }
+    var viewType: Int32? {
+        if let viewType = draftMsg?.type {
+            return Int32(viewType)
+        }
+        return nil
+    }
 
     public init(dcContext: DcContext, chatId: Int) {
         self.chatId = chatId
@@ -19,53 +33,60 @@ public class DraftModel {
     }
 
     public func parse(draftMsg: DcMsg?) {
+        self.draftMsg = draftMsg
         text = draftMsg?.text
-        quoteText = draftMsg?.quoteText
-        quoteMessage = draftMsg?.quoteMessage
-        attachment = draftMsg?.fileURL?.relativePath
-        if let viewType = draftMsg?.type {
-            self.viewType = Int32(viewType)
-        }
-        attachmentMimeType = draftMsg?.filemime
     }
 
     public func setQuote(quotedMsg: DcMsg?) {
-        if let quotedMsg = quotedMsg {
-            // create a temporary draft to get the correct quoteText
-            let draftMessage = dcContext.newMessage(viewType: DC_MSG_TEXT)
-            draftMessage.quoteMessage = quotedMsg
-            self.quoteText = draftMessage.quoteText
-            self.quoteMessage = quotedMsg
-        } else {
-            self.quoteText = nil
-            self.quoteMessage = nil
+        if draftMsg == nil {
+            draftMsg = dcContext.newMessage(viewType: DC_MSG_TEXT)
         }
+        draftMsg?.quoteMessage = quotedMsg
     }
 
     public func setAttachment(viewType: Int32?, path: String?, mimetype: String? = nil) {
-        attachment = path
-        self.viewType = viewType
-        attachmentMimeType = mimetype
+        if draftMsg == nil {
+            draftMsg = dcContext.newMessage(viewType: viewType ?? DC_MSG_TEXT)
+        }
+        draftMsg?.setFile(filepath: path, mimeType: mimetype)
+        save(context: dcContext)
+    }
+
+    public func clearAttachment() {
+        let text = draftMsg?.text
+        let quoteMsg = draftMsg?.quoteMessage
+        if text != nil || quoteMsg != nil {
+            draftMsg = dcContext.newMessage(viewType: DC_MSG_TEXT)
+            draftMsg?.text = text
+            draftMsg?.quoteMessage = quoteMsg
+            save(context: dcContext)
+        } else {
+            draftMsg = nil
+            dcContext.setDraft(chatId: chatId, message: nil)
+        }
     }
 
     public func save(context: DcContext) {
-        if (text?.isEmpty ?? true) && quoteMessage == nil {
-            context.setDraft(chatId: chatId, message: nil)
+        if (text?.isEmpty ?? true) &&
+            (draftMsg == nil || quoteMessage == nil && attachment == nil) {
+            self.clear()
             return
         }
 
-        let draftMessage = dcContext.newMessage(viewType: viewType ?? DC_MSG_TEXT)
-        draftMessage.text = text
-        if quoteMessage != nil {
-            draftMessage.quoteMessage = quoteMessage
-        }
-        if attachment != nil {
-            draftMessage.setFile(filepath: attachment, mimeType: attachmentMimeType)
+        if draftMsg == nil {
+            draftMsg = dcContext.newMessage(viewType: DC_MSG_TEXT)
         }
-        context.setDraft(chatId: chatId, message: draftMessage)
+        draftMsg?.text = text
+        context.setDraft(chatId: chatId, message: draftMsg)
     }
 
     public func canSend() -> Bool {
         return !(text?.isEmpty ?? true) || attachment != nil
     }
+
+    public func clear() {
+        text = nil
+        draftMsg = nil
+        dcContext.setDraft(chatId: chatId, message: nil)
+    }
 }

+ 2 - 1
deltachat-ios/Helper/MediaPicker.swift

@@ -72,7 +72,8 @@ class MediaPicker: NSObject, UINavigationControllerDelegate, AudioRecorderContro
     }
 
     func showDocumentLibrary() {
-        let types = [kUTTypePDF, kUTTypeText, kUTTypeRTF, kUTTypeSpreadsheet, kUTTypeVCard, kUTTypeZipArchive, kUTTypeImage]
+        // TODO: instead of adding kUTTypeData, we probably should implement a Document provider for webxdc's https://developer.apple.com/library/archive/documentation/General/Conceptual/ExtensibilityPG/FileProvider.html#//apple_ref/doc/uid/TP40014214-CH18
+        let types = [kUTTypePDF, kUTTypeText, kUTTypeRTF, kUTTypeSpreadsheet, kUTTypeVCard, kUTTypeZipArchive, kUTTypeImage, kUTTypeData]
         let documentPicker = UIDocumentPickerViewController(documentTypes: types as [String], in: .import)
         documentPicker.delegate = self
         documentPicker.allowsMultipleSelection = false