Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added additional report info and extended UI customisation #1

Merged
3 changes: 1 addition & 2 deletions Package.swift
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,7 @@ let package = Package(
name: "FeedbacksKit",
defaultLocalization: "en",
platforms: [
.iOS(.v14),
.macOS(.v13),
.iOS(.v14)
],
products: [
// Products define the executables and libraries a package produces, and make them visible to other packages.
Expand Down
28 changes: 21 additions & 7 deletions Sources/FeedbacksKit/FeedbackForm/FeedbackForm.swift
Original file line number Diff line number Diff line change
Expand Up @@ -3,24 +3,29 @@ import SwiftUI
public struct FeedbackForm: View {

public struct Config {
let title: String?

public init(title: String?) {
self.title = title
let title: String
let textForegroundColor: Color

public init(
title: String? = nil,
textForegroundColor: Color? = nil
) {
self.title = title ?? "_send_a_feedback".localized
self.textForegroundColor = textForegroundColor ?? .blue
}
}

@Environment(\.presentationMode) private var presentationMode

@StateObject private var viewModel: FeedbackFormViewModel
private let config: Config?
private let config: Config

public init(
service: SubmitService,
config: Config? = nil
) {
self._viewModel = StateObject(wrappedValue: FeedbackFormViewModel(service: service))
self.config = config
self.config = config ?? Config()
}

public var body: some View {
Expand All @@ -29,18 +34,20 @@ public struct FeedbackForm: View {
formFields
submitButton
}
.navigationTitle(Text(config?.title ?? "_send_a_feedback".localized))
.navigationTitle(Text(config.title))
.toolbar {
ToolbarItem(placement: .navigationBarLeading) {
Button {
presentationMode.wrappedValue.dismiss()
} label: {
Text("_cancel".localized)
.foregroundColor(config.textForegroundColor)
}
}
}
}
.navigationViewStyle(.stack)
.accessibilityIdentifier("LeaveFeedbackScreen")
}

// MARK: Views
Expand All @@ -51,12 +58,15 @@ public struct FeedbackForm: View {
TextField("_email_placeholder".localized, text: $viewModel.email)
.keyboardType(.emailAddress)
.autocapitalization(.none)
.autocorrectionDisabled()
.accessibilityIdentifier("EmailTextField")
} header: {
Text("_email_title".localized)
}

Section {
TextEditor(text: $viewModel.message)
.accessibilityIdentifier("MessageTextEditor")
} header: {
Text("_message_title".localized)
}
Expand All @@ -75,9 +85,11 @@ public struct FeedbackForm: View {
.frame(maxWidth: .infinity)
} else {
Text("_send_feedback".localized)
.foregroundColor(viewModel.isSubmitDisabled ? .gray : config.textForegroundColor)
.frame(maxWidth: .infinity)
}
}
.accessibilityIdentifier("SendFeedbackButton")
.disabled(viewModel.isSubmitDisabled)
} footer: {
footer
Expand All @@ -104,6 +116,7 @@ public struct FeedbackForm: View {
.bold()
.frame(maxWidth: .infinity)
.foregroundColor(.green)
.accessibilityIdentifier("SendFeedbackSuccessText")
.onAppear {
Task {
try? await Task.sleep(nanoseconds: 2_000_000_000)
Expand All @@ -120,6 +133,7 @@ public struct FeedbackForm: View {
.bold()
.frame(maxWidth: .infinity)
.foregroundColor(.red)
.accessibilityIdentifier("SendFeedbackFailureText")
.onAppear {
Task {
try? await Task.sleep(nanoseconds: 3_000_000_000)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ class FeedbackFormViewModel: ObservableObject {
var message: String {
switch self {
case .success: return "_feedback_successfully_sent".localized
case .failure: return "_oups_error_occured".localized
case .failure: return "_oops_error_occurred".localized
}
}
}
Expand Down
12 changes: 12 additions & 0 deletions Sources/FeedbacksKit/Model/FeedbackFormData.swift
Original file line number Diff line number Diff line change
@@ -1,12 +1,24 @@
import UIKit
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❓ I can't check that now but I remember I added plateforme support for MacOS in the Package.swift. I'm wondering then if this won't break because UIKit can't be imported on MacOS.
Can you have a look ? It's not critical, you can remove MacOS support if needed 😄

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, it will. I hadn't noticed there was Mac support in the Package.swift there are however several existing compilation issues, including existing UIKit imports, use of iOS specific SwiftUI view modifiers which mean it would require a bit more work to get running on Mac. For that reason, I've removed support as per your suggestion.


public struct FeedbackFormData {
let email: String
let message: String

let deviceModelIdentifier: String
let systemNameAndVersion: String
let appVersion: String
let language: String

public init(
email: String,
message: String
) {
self.email = email
self.message = message

deviceModelIdentifier = UIDevice.modelIdentifier
systemNameAndVersion = "\(UIDevice.current.systemName) \(UIDevice.current.systemVersion)"
appVersion = "\(Bundle.main.appVersionLong) (\(Bundle.main.appBuild))"
language = Locale.current.localizedString(forIdentifier: Locale.current.identifier) ?? Locale.current.identifier
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,4 @@
"_send_feedback" = "Send feedback";

"_feedback_successfully_sent" = "Feedback successfully sent!";
"_oups_error_occured" = "Ooups! An error occurred.";
"_oops_error_occurred" = "Oops! An error occurred.";
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,4 @@
"_send_feedback" = "Envoyer";

"_feedback_successfully_sent" = "Message envoyé !";
"_oups_error_occured" = "Ooups! Il y a eu une erreur...";
"_oops_error_occurred" = "Ooups! Il y a eu une erreur...";
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,75 @@ public struct NotionSubmitService: SubmitService {
)
]
)
),
.init(type: "divider", divider: .init()),
.init(
object: "block",
type: "paragraph",
paragraph: .init(
richText: [
.init(
type: "text",
text: .init(content: "App version: "),
annotations: .init(bold: true)
),
.init(
type: "text",
text: .init(content: formData.appVersion)
)
]
)
),
.init(
object: "block",
type: "paragraph",
paragraph: .init(
richText: [
.init(
type: "text",
text: .init(content: "Device model identifier: "),
annotations: .init(bold: true)
),
.init(
type: "text",
text: .init(content: formData.deviceModelIdentifier)
)
]
)
),
.init(
object: "block",
type: "paragraph",
paragraph: .init(
richText: [
.init(
type: "text",
text: .init(content: "System: "),
annotations: .init(bold: true)
),
.init(
type: "text",
text: .init(content: formData.systemNameAndVersion)
)
]
)
),
.init(
object: "block",
type: "paragraph",
paragraph: .init(
richText: [
.init(
type: "text",
text: .init(content: "System Locale: "),
annotations: .init(bold: true)
),
.init(
type: "text",
text: .init(content: formData.language)
)
]
)
)
]
)
Expand Down Expand Up @@ -113,16 +182,28 @@ private struct NotionBody: Codable {
}

struct Child: Codable {
let object: String
var object: String?
let type: String
let paragraph: Paragraph
var paragraph: Paragraph?
var divider: Divider?

struct Divider: Codable {}

struct Paragraph: Codable {
let richText: [RichText]

struct RichText: Codable {
let type: String
let text: Text
struct Annotations: Codable {
var bold = false
var italic = false
var strikethrough = false
var underline = false
var code = false
var color = "default"
}
var annotations: Annotations?

struct Text: Codable {
let content: String
Expand Down
11 changes: 11 additions & 0 deletions Sources/FeedbacksKit/Utils/Bundle+VersionInfo.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import Foundation

extension Bundle {
var appBuild: String { getInfo("CFBundleVersion") }
var appVersionLong: String { getInfo("CFBundleShortVersionString") }
var appVersionShort: String { getInfo("CFBundleShortVersion") }

private func getInfo(_ string: String) -> String {
infoDictionary?[string] as? String ?? "⚠️"
}
}
22 changes: 22 additions & 0 deletions Sources/FeedbacksKit/Utils/UIDevice+ModelInfo.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import UIKit

extension UIDevice {

/// The device model identifier e.g. "iPhone14,5" (iPhone 13) or "Simulator"
static var modelIdentifier: String {
var systemInfo = utsname()
uname(&systemInfo)
let machineMirror = Mirror(reflecting: systemInfo.machine)
let identifier = machineMirror.children.reduce("") { identifier, element in
guard let value = element.value as? Int8, value != 0 else { return identifier }
return identifier + String(UnicodeScalar(UInt8(value)))
}

switch identifier {
case "i386", "x86_64":
return "Simulator"
default:
return identifier
}
}
}
4 changes: 4 additions & 0 deletions Sources/FeedbacksKit/Utils/View+hideKeyboard.swift
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,7 @@ extension View {
}
}
#endif