I am trying to make Menu using swiftUI in MacOS application.
Based on this:
I am using this specific code
struct SelectionRow: View {
var title: String
var isSelected: Bool
var action: () -> Void
var body: some View {
Button(action: self.action) {
HStack {
if self.isSelected {
Image("checkmark")
.resizable()
.renderingMode(.template)
.scaledToFit()
} else {
//FIXME: What to add here ???!!! <-- Need to add solution here I believe
}
Text(self.title)
//.frame(alignment: .trailing). <-- Not effective
}
}.foregroundColor(Color.black)
}
}
Menu-item entries:
Menu("Example Menu"){
SelectionRow(title: "One", isSelected: true, action: { print("hello world")})
SelectionRow(title: "Two", isSelected: false, action: { print("hello world")})
SelectionRow(title: "Three", isSelected: true, action: { print("hello world")})
}
If you look at the image "Two" menu item is not aligned with "One" and "Three" menu options, as there is an image of checkmark is there for options "One" & "Thrree".
I tried Spacer with Minimum width (and some other options) but doesn’t seem to work and align "Two" with "One" & "Three"
Can you recommend anything which can resolve this issue and make alignment of "Two" inline with "One" & "Three" ?
2
Answers
Here is possible approach – just make it invisible instead of removing:
This doesn’t quite answer the question you asked, but instead goes to what I think is your goal. Instead of buttons, try toggles, like this:
Here’s how it looks on macOS:
And here’s iOS:
The item titles all line up, whether toggle or button, and the checkmarks extend the menu out in the leading direction. This doesn’t let you use arbitrary images in your menu items, but it works well for the specific case of checkmarks indicating toggled menu items.
Creating the bindings just-in-time like that isn’t great coding style, but it’s functional for a snippet like this, and makes it clear what is going on. For these, I have hard-coded the conditions, but you can get arbitrarily fancy in the binding get and set methods.
I have some code like this to let me toggle a few bools in a Core Data object representing data pulled from a remote server. In my bindings’ get methods, I return the value of a property of the object which has been passed to my view. In the bindings’ set methods, I do a little NSManagedObjectContext jig to create a private copy of the object where I set the property I’m working with to not itself, then I pass the private object to a method in another object which writes the data to the remote server and refreshes the real copy in the persistent store.