visionOS: Further Compose screen tweaks
This commit is contained in:
parent
14f32f24fa
commit
c0301ce7e7
|
@ -136,7 +136,7 @@ class AttachmentRowController: ViewController {
|
||||||
.overlay {
|
.overlay {
|
||||||
thumbnailFocusedOverlay
|
thumbnailFocusedOverlay
|
||||||
}
|
}
|
||||||
.frame(width: 80, height: 80)
|
.frame(width: thumbnailSize, height: thumbnailSize)
|
||||||
.onTapGesture {
|
.onTapGesture {
|
||||||
textEditorFocused = false
|
textEditorFocused = false
|
||||||
// if we just focus the attachment immediately, the text editor doesn't actually unfocus
|
// if we just focus the attachment immediately, the text editor doesn't actually unfocus
|
||||||
|
@ -162,7 +162,7 @@ class AttachmentRowController: ViewController {
|
||||||
|
|
||||||
switch controller.descriptionMode {
|
switch controller.descriptionMode {
|
||||||
case .allowEntry:
|
case .allowEntry:
|
||||||
InlineAttachmentDescriptionView(attachment: attachment, minHeight: 80)
|
InlineAttachmentDescriptionView(attachment: attachment, minHeight: thumbnailSize)
|
||||||
.matchedGeometrySource(id: AttachmentDescriptionTextViewID(attachment), presentationID: attachment.id)
|
.matchedGeometrySource(id: AttachmentDescriptionTextViewID(attachment), presentationID: attachment.id)
|
||||||
.focused($textEditorFocused)
|
.focused($textEditorFocused)
|
||||||
|
|
||||||
|
@ -192,6 +192,14 @@ class AttachmentRowController: ViewController {
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private var thumbnailSize: CGFloat {
|
||||||
|
#if os(visionOS)
|
||||||
|
120
|
||||||
|
#else
|
||||||
|
80
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
@ViewBuilder
|
@ViewBuilder
|
||||||
private var thumbnailFocusedOverlay: some View {
|
private var thumbnailFocusedOverlay: some View {
|
||||||
Image(systemName: "arrow.up.backward.and.arrow.down.forward")
|
Image(systemName: "arrow.up.backward.and.arrow.down.forward")
|
||||||
|
|
|
@ -334,6 +334,11 @@ public final class ComposeController: ViewController {
|
||||||
.toolbar {
|
.toolbar {
|
||||||
ToolbarItem(placement: .cancellationAction) { cancelButton }
|
ToolbarItem(placement: .cancellationAction) { cancelButton }
|
||||||
ToolbarItem(placement: .confirmationAction) { postButton }
|
ToolbarItem(placement: .confirmationAction) { postButton }
|
||||||
|
#if os(visionOS)
|
||||||
|
ToolbarItem(placement: .bottomOrnament) {
|
||||||
|
ControllerView(controller: { controller.toolbarController })
|
||||||
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
.background(GeometryReader { proxy in
|
.background(GeometryReader { proxy in
|
||||||
Color.clear
|
Color.clear
|
||||||
|
@ -342,11 +347,6 @@ public final class ComposeController: ViewController {
|
||||||
globalFrameOutsideList = newValue
|
globalFrameOutsideList = newValue
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
#if os(visionOS)
|
|
||||||
.ornament(attachmentAnchor: .scene(.bottom)) {
|
|
||||||
ControllerView(controller: { controller.toolbarController })
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
.sheet(isPresented: $controller.isShowingDraftsList) {
|
.sheet(isPresented: $controller.isShowingDraftsList) {
|
||||||
ControllerView(controller: { DraftsController(parent: controller, isPresented: $controller.isShowingDraftsList) })
|
ControllerView(controller: { DraftsController(parent: controller, isPresented: $controller.isShowingDraftsList) })
|
||||||
}
|
}
|
||||||
|
|
|
@ -53,7 +53,6 @@ class ToolbarController: ViewController {
|
||||||
var body: some View {
|
var body: some View {
|
||||||
#if os(visionOS)
|
#if os(visionOS)
|
||||||
buttons
|
buttons
|
||||||
.glassBackgroundEffect(in: .rect(cornerRadius: 50))
|
|
||||||
#else
|
#else
|
||||||
ScrollView(.horizontal, showsIndicators: false) {
|
ScrollView(.horizontal, showsIndicators: false) {
|
||||||
buttons
|
buttons
|
||||||
|
|
|
@ -22,13 +22,21 @@ struct InlineAttachmentDescriptionView: View {
|
||||||
self.minHeight = minHeight
|
self.minHeight = minHeight
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private var placeholderOffset: CGSize {
|
||||||
|
#if os(visionOS)
|
||||||
|
CGSize(width: 8, height: 8)
|
||||||
|
#else
|
||||||
|
CGSize(width: 4, height: 8)
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
var body: some View {
|
var body: some View {
|
||||||
ZStack(alignment: .topLeading) {
|
ZStack(alignment: .topLeading) {
|
||||||
if attachment.attachmentDescription.isEmpty {
|
if attachment.attachmentDescription.isEmpty {
|
||||||
placeholder
|
placeholder
|
||||||
.font(.body)
|
.font(.body)
|
||||||
.foregroundColor(.secondary)
|
.foregroundColor(.secondary)
|
||||||
.offset(x: 4, y: 8)
|
.offset(placeholderOffset)
|
||||||
}
|
}
|
||||||
|
|
||||||
WrappedTextView(
|
WrappedTextView(
|
||||||
|
@ -84,6 +92,10 @@ private struct WrappedTextView: UIViewRepresentable {
|
||||||
view.font = .preferredFont(forTextStyle: .body)
|
view.font = .preferredFont(forTextStyle: .body)
|
||||||
view.adjustsFontForContentSizeCategory = true
|
view.adjustsFontForContentSizeCategory = true
|
||||||
view.textContainer.lineBreakMode = .byWordWrapping
|
view.textContainer.lineBreakMode = .byWordWrapping
|
||||||
|
#if os(visionOS)
|
||||||
|
view.borderStyle = .roundedRect
|
||||||
|
view.textContainerInset = UIEdgeInsets(top: 8, left: 4, bottom: 8, right: 4)
|
||||||
|
#endif
|
||||||
return view
|
return view
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -57,7 +57,9 @@ struct EmojiTextField: UIViewRepresentable {
|
||||||
context.coordinator.maxLength = maxLength
|
context.coordinator.maxLength = maxLength
|
||||||
context.coordinator.focusNextView = focusNextView
|
context.coordinator.focusNextView = focusNextView
|
||||||
|
|
||||||
|
#if !os(visionOS)
|
||||||
uiView.backgroundColor = colorScheme == .dark ? UIColor(controller.config.fillColor) : .secondarySystemBackground
|
uiView.backgroundColor = colorScheme == .dark ? UIColor(controller.config.fillColor) : .secondarySystemBackground
|
||||||
|
#endif
|
||||||
|
|
||||||
if becomeFirstResponder?.wrappedValue == true {
|
if becomeFirstResponder?.wrappedValue == true {
|
||||||
DispatchQueue.main.async {
|
DispatchQueue.main.async {
|
||||||
|
|
|
@ -31,11 +31,19 @@ struct MainTextView: View {
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private var textViewBackgroundColor: UIColor? {
|
||||||
|
#if os(visionOS)
|
||||||
|
nil
|
||||||
|
#else
|
||||||
|
colorScheme == .dark ? UIColor(config.fillColor) : .secondarySystemBackground
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
var body: some View {
|
var body: some View {
|
||||||
ZStack(alignment: .topLeading) {
|
ZStack(alignment: .topLeading) {
|
||||||
MainWrappedTextViewRepresentable(
|
MainWrappedTextViewRepresentable(
|
||||||
text: $draft.text,
|
text: $draft.text,
|
||||||
backgroundColor: colorScheme == .dark ? UIColor(config.fillColor) : .secondarySystemBackground,
|
backgroundColor: textViewBackgroundColor,
|
||||||
becomeFirstResponder: $controller.mainComposeTextViewBecomeFirstResponder,
|
becomeFirstResponder: $controller.mainComposeTextViewBecomeFirstResponder,
|
||||||
updateSelection: $updateSelection,
|
updateSelection: $updateSelection,
|
||||||
textDidChange: textDidChange
|
textDidChange: textDidChange
|
||||||
|
@ -76,7 +84,7 @@ fileprivate struct MainWrappedTextViewRepresentable: UIViewRepresentable {
|
||||||
typealias UIViewType = UITextView
|
typealias UIViewType = UITextView
|
||||||
|
|
||||||
@Binding var text: String
|
@Binding var text: String
|
||||||
let backgroundColor: UIColor
|
let backgroundColor: UIColor?
|
||||||
@Binding var becomeFirstResponder: Bool
|
@Binding var becomeFirstResponder: Bool
|
||||||
@Binding var updateSelection: ((UITextView) -> Void)?
|
@Binding var updateSelection: ((UITextView) -> Void)?
|
||||||
let textDidChange: (UITextView) -> Void
|
let textDidChange: (UITextView) -> Void
|
||||||
|
|
Loading…
Reference in New Issue