Jump to content

lilyball

Member
  • Posts

    48
  • Joined

  • Last visited

Posts posted by lilyball

  1. If I write an Automator Apple Script action like

    on run {input, parameters}
    	tell application id "com.runningwithcrayons.Alfred" to action input
    	return input
    end run

    where the input is files (either Service inputs, or the results of "Get Specified Finder Items"), Alfred opens the browse panel but with the garbage input that looks like

    file:/slash/separate/path%20with%20percent%20encoding.txt

    I can instead pass `POSIX PATH of input` and that works, but only for one file. I'm not sure how to convert a list of files into a list of paths in AppleScript. Thankfully I can do this with JavaScript instead, but the Apple Script support really should handle Apple Script files.

  2. 9 hours ago, deanishe said:

     

    Have you considered changing the Hotkey to one that doesn't include ^ or ⇧? The default uses ⌥⌘, IIRC. If you only use the feature in Finder, why not delete that and re-assign it to your workflow?

     

    Now that I’m just limiting it to the Finder it’s more reasonable to do that. In general I avoid using ⌘ in global hotkeys because I don’t want to interfere with apps. Though I ended up limiting it to the Finder specifically because ⌃⇧\ was interfering with Xcode 😅 (though to be fair ⌘⌥\ would have interfered with Xcode too).

     

    Though now that I think about it, why is this a hotkey at all, instead of a Service? A Service would mean not having to muck about with Copy to figure out my selection. And IIRC service hotkeys are overridden by app hotkeys, so using ⌘⌥\ as a default hotkey for the service wouldn’t conflict with anything.

  3. I have a workflow that uses a Hotkey to trigger "Browse in Alfred". I've done this instead of using the built-in support so I can restrict the hotkey to only occur in the Finder, as that's the only app I ever use this feature with and the hotkey I use conflicts with Xcode.

     

    Anyway, I just discovered a problem today, which is that Alfred interprets the flag changed events for the modifiers used by the hotkey incorrectly. As near as I can tell, it's trying to detect a quick press-and-release of the shift or control modifiers to trigger the associated behavior (quicklook or showing the action panel; I have control enabled for this behavior, I don't remember if that's a default). The problem is my hotkey is ctrl-shift-\, and if the modifiers are still held down by the time Alfred shows the panel, and I release both modifiers at the same time, Alfred will trigger one of the two behaviors (quick look or showing action panel, whichever one corresponds to the modifier that got released second). I'm pretty sure what's going on is the flags changed event doesn't actually say which flags were added/removed, it just says what the current flags are, so when the first modifier is released Alfred interprets this as the addition of the second modifier, so when that gets released it triggers the action.

     

    This is rather irritating because it means I need to be really quick about releasing the modifiers when I trigger the hotkey or else I get this weird behavior. Alfred could fix this by keeping track of modifiers as global state, instead of what it's apparently doing which is keeping track of them only when the action panel is open. Or if it doesn't want to track modifiers globally, it could at least track the modifiers involved in a hotkey to see when they go away. Or poll the system when the action panel opens to see what flags are currently active.

  4. @Andrew Excellent. I'll check that out now. Incidentally, the first line of the change log for the pre-release has a typo ("exapnsion").

     

    As for reporting it, you could do that, but I'm honestly not sure how they're supposed to know that clipboard changes are complete. I can erase the clipboard now, then write one piece of data to it, then a bit later on add more data to the clipboard, and there's no way for me to say that I'm "done" mucking with it. 

  5. If I search for a place in Maps and hit ⌘C, it copies both an image of the map, as well as plain text that contains a URL like https://maps.apple.com/?address=826 Folsom St, San Francisco, CA 94107, United States&auid=7989913039222126743&ll=37.781586,-122.402010&lsp=9902&q=Zero Zero&t=m. I have Alfred configured to save plain text, so I would expect Alfred's Clipboard History to retain the URL there, but it doesn't. Alfred doesn't keep any history of URLs copied from Maps.app.

     

    I've tested this with "Keep Images" enabled and with it disabled, and in neither case does Alfred save the history. And I don't have Maps configured in the Ignore Apps section.

  6. On 3/18/2017 at 3:31 AM, Andrew said:

    The point is, when using NSTask, you literally have no choice, macOS automatically normalises. When this first cropped up, I added options to force normalisation to allow the user to pick the normalisation type, and NSTask re-normalised and undid any changes. Any arguments passed to the script are normalised in the same way by macOS, and this is how Alfred / macOS has always worked.

     

    Alfred works consciously within these constraints to give consistent behaviour across all the different modes of running scripts in Alfred.

     

    Your "consistent behavior" is my "broken behavior". You're telling me you're doing extra work to ensure there's no way for me to get un-normalized text, and that's extremely annoying.

     

    Quote

    Did you try using the normalise tool I provided? This should be able to set the normalisation to the type you need or require after being passed to your script.

     

    I feel like you don't actually understand my problem. I don't want normalized text. If I needed a particular normalization, I'd do it. But I want to pass the input exactly as provided to my script, because my script behaves differently when providing composed vs decomposed characters, and that behavior difference is very important. If I try to pass it a composed character, it should be given that composed character. And if I try to pass it decomposed characters, it should be given decomposed characters.

     

    I have a suggestion for an alternative workaround here. What if you added a third option for input, to pass it in via stdin (instead of argv or {query})? Then you could simply not normalize the stdin approach, because it's far less likely to be used for filenames than it is to be used for arbitrary text. And NSTask won't normalize for you here.

     

    As an aside, I just tested and it appears that current script actions are executed without closing off stdin. I made a script that ran `cat` as part of its processing, and the script never completed. I would have expected Alfred to run scripts with stdin either closed directly or connected to /dev/null, so that way anything that tries to read from stdin won't hang forever.

  7. 7 minutes ago, deanishe said:

    It's generally symptomatic of OS X's preference for NFD-normalised UTF-8 text.

     

    In most cases OS X does not normalize your text either way.

     

    7 minutes ago, deanishe said:

    Because OS X prefers NFD.

     

    HFS+ prefers NFD. NSTask here is the only other case I can think of where it's forcing your text to NFD, and even that was a complete surprise to me. The only justification I can think of for why is if it's using -[NSString fileSystemRepresentation] to create the C strings that it passes to the underlying POSIX APIs, and the only real reason to do that is to handle the weird edge cases with programs that accept input and then do byte-wise comparisons against the filesystem (as opposed to passing the string to the filesystem APIs and letting them do the comparison).

     

    But in general, OS X doesn't care if you're using composed or decomposed strings.

     

    7 minutes ago, deanishe said:

    How else would such a command be run? AFAIK, it all goes through NSTask.

     

    If you write a script to a file, and then invoke that script via NSTask, the NSTask APIs never actually see the input string and therefore won't have a chance to decompose it.

     

    7 minutes ago, deanishe said:

    Nah. Normalisation is a sensible default. I wish more platforms did it.

     

    Why? There's no need for normalization in most cases. There's certainly no benefit to normalizing the arguments passed to Alfred workflows.

     

    7 minutes ago, deanishe said:

    99% of the time, you're interested in the characters that make up a text, not the codepoints/bytes that represent them.

     

    And so whether it's composed or decomposed doesn't matter. That's not an argument for decomposing strings. That's jut an argument for using unicode canonical equivalence when comparing strings.

  8. 12 minutes ago, deanishe said:

     

    It probably isn't Alfred. In this case, it's likely NSTask, but OS X fundamentally prefers NFD (which all HFS+ filenames are normalised to).

     

    What does HFS+ filenames have to do with passing arguments to the command-line?

     

    It does appear, though, that NSTask does convert arguments to NFD, though I have no idea why that would be. I'm also not sure why that's particularly relevant here; I'm passing the input using {query}, not as arguments, so presumably Alfred is dynamically constructing a script that embeds my input and then running that script, which means NSTask doesn't ever see the input directly (and therefore cannot convert it to NFD).

     

    Edit: Or is Alfred evaluating the script by passing it to /bin/bash -c, and therefore the whole script is handled as an argument?

     

    Quote

    Why? I know naff-all about Asian alphabets, but I'm having trouble understanding why OSX should return the composed Unicode form, not the decomposed one.

     

    It should return whatever input I give it. It shouldn't be converting my input into either NFD or NFC form, just using it as-is. I'll grant you in most cases it won't really matter, but in some cases, like my workflow here, the difference is very important.

  9. It looks like Alfred is automatically converting workflow arguments into decomposed form. I swear it didn't used to do this, but I can't be certain.

     

    I've created a workflow you can use to test this. The workflow is invoked with the "char" keyword and shows the unicode codepoints for the workflow argument. If I paste in a precomposed character, the workflow shows me the info for the decomposed form. I've verified by running the workflow binary in the Terminal that the workflow does properly handle precomposed characters, so it must be Alfred decomposing it.

     

    To test, install the workflow and type "char 각". It should return U+AC01 HANGUL SYLLABLE GAG but instead it returns U+1100 HANGUL CHOSEONG KIYEOK, U+1161 HANGUL JUNGSEONG A, U+11A8 HANGUL JONGSEONG KIYEOK.

  10. 17 minutes ago, deanishe said:

     

    It's nothing to do with Alfred, it's the way OS X works. When you send keypresses to an application (i.e. paste), the system doesn't wait for the application to handle them. Your call returns immediately. So what's happening is that you're restoring the keyboard before the application can act on the paste instruction. You need to put a delay between pasting and restoring the clipboard to give the paste time to complete.

     

    That's one of the reasons why it's a terrible way to automate applications.

     

    I just tested, if I use Apple script to explicitly click the "Paste" menu item, then the application pastes before the Apple Script continues, which allows me to immediately set the clipboard again without delay. But of course this does require assistive access. I should probably just grant that to Alfred 3 and use this technique.

     

    But you are right, if I keystroke ⌘V with Apple Script, it does not wait, and therefore I would have to introduce a delay in order to set the clipboard.

     

    17 minutes ago, deanishe said:

    I'm 99.5% certain Alfred also simulates ⌘V. I'm also pretty sure Alfred doesn't have the same problem (it breaks if the user is holding other modifier keys) because it uses Carbon, not System Events, to simulate the keypress.

     

    Ah, that would make sense.

     

    17 minutes ago, deanishe said:

    This JavaScript function simulates ⌘V via Carbon and should also ignore whatever you've got your fingers on:

    
    ObjC.import('Carbon');
    
    // Simulate CMD+V keypress via Carbon. Unaffected by other modifiers the user may
    // be holding down.
    function paste() {
      var source = $.CGEventSourceCreate($.kCGEventSourceStateCombinedSessionState);
      
      var pasteCommandDown = $.CGEventCreateKeyboardEvent(source, $.kVK_ANSI_V, true);
      $.CGEventSetFlags(pasteCommandDown, $.kCGEventFlagMaskCommand);
      var pasteCommandUp = $.CGEventCreateKeyboardEvent(source, $.kVK_ANSI_V, false);
    
      $.CGEventPost($.kCGAnnotatedSessionEventTap, pasteCommandDown);
      $.CGEventPost($.kCGAnnotatedSessionEventTap, pasteCommandUp);
    }

     

     

    Very cool, thanks.

     

    I do wish Alfred had a built-in way to "paste to frontmost application" without modifying the clipboard, by using assistive access in order to click the Paste menu item, seeing as that does wait for the application to handle the paste before returning. But at least now I know how to work around this with Apple Script.

  11. In fact, it's not actually obvious to me how to reproduce Alfred's behavior for pasting the current clipboard. If I use `tell application "System Events" to keystroke "v" using command down` then it fails if I have any keys held down when I trigger the workflow (e.g. pressing shift-return). If I instead try to click the menu item "Paste" in the menu "Edit", I get told that Alfred 3 doesn't have assistive access (I don't use auto-expanding snippets so I guess I never hit this problem). So what is Alfred doing in order to paste in the current app?

×
×
  • Create New...