Wednesday, November 23, 2011

Eliminate Fast User Switching by Using an Applescript to Toggle Preferences

Alexia was a PC. I'm a Mac. However, when moving into our house after getting married, her PC bit the dust. So, eager to spread the gospel of Apple, I transferred her stuff over to my Macbook Pro.

However, as productive as Hot Corners can be when you are familiar with them (me), they can be equally frustrating to someone who is not familiar with them, nor has any intention of becoming so (Alexia). I like to tap to click sometimes, she doesn't. I have switched over to the natural scrolling of Lion, she is still using the unnatural(?) scrolling of Snow Leopard.

So, to make it work, I set up different profiles. While these allowed us to keep our individualized settings, it also had its drawbacks. Fast user switching is still not fast enough. You have to click on the name, select your name, type your password, and then wait for the cube to rotate to your profile. It was also a pain when restarting, because you were prompted for your password to confirm that the other user's programs would be terminated (also a problem if they had something open they didn't save). I also had a background program that would often crash while switching profiles. Finally, I have yet to figure the best way to share an iTunes library (and iPhoto is even worse). Permissions would always get wonky and the iTunes library file would be locked.

So today I made all that change. I had never Applescripted before, so I relied heavily on piecing code together from here and there. The Frankenstein that I ended up with was exactly what I wanted. I have a quick application called Switch that toggles back between my "preference profile" and my lovely wife's profile simply by switching the individual preferences back and forth. Run it once, and it turns off Hot Corners, tap to click, and natural scrolling, while displaying a Growl notification that Alexia's profile is now activated. Run it again, and you're back to mine.



The Hot Corners are toggled using some code that edits the plist files. I borrowed this code from a script called Lava Corners Switch. The Growl notification code is adapted from the Growl website (which I just noticed the other day is now in the Mac App Store. I declined to buy it because... how much more can Growl be improved? It gives me messages, that's great.). The toggling of the natural scrolling is implemented with UI scripting (so you have to enable access for assistive devices) and comes from commenter fireshadow52 on stackoverflow.com. I added the tap to click toggling. And finally, the method testing to see if an app is running came from CodeSnippets. Then I just grabbed a nice icon from the web and slapped it on there.

To get this running, copy the code into a new Applescript. Save it as an application and throw it on your dock. Set all your settings, and then run the application to toggle all of your Hot Corners off, and switch those other two trackpad settings. Obviously individuals will need to tweak the settings they want changed, and that will take some digging online. If you use it, let me know how it works. And if there is a better way to do any of this, feel free to enlighten me.

As a side note, it amazes me how much some people know out there. I'd like to think of myself as pretty computer savvy, especially compared to those I interact with daily, but my progress to this point can best be described as blindly stumbling for hours. The knowledge of some out there is very impressive. Anyway, I hope this helps. To me, this will be so much better than multiple logins.


-- List of properties for hot corners. Just set your hot corners and it will toggle back and forth between those settings and being disabled
property tl : 1
property tr : 1
property br : 1
property bl : 1
property runs : 0

if appIsRunning("GrowlHelperApp") then
tell application id "com.Growl.GrowlHelperApp"
-- Make a list of all the notification types
-- that this script will ever send:
set the allNotificationsList to ¬
{"Switch Notification"}

-- Make a list of the notifications
-- that will be enabled by default.
-- Those not enabled by default can be enabled later
-- in the 'Applications' tab of the Growl preferences.
set the enabledNotificationsList to ¬
{"Switch Notification"}

-- Register our script with growl.
-- You can optionally (as here) set a default icon
-- for this script's notifications.
register as application ¬
"Switch" all notifications allNotificationsList ¬
default notifications enabledNotificationsList ¬
icon of application "Switch.app"

-- Indicate which user or profile is now running
if runs = 1 then
notify with name ¬
"Switch Notification" title ¬
"Profile Activated:" description ¬
"User 1" application name "Switch"

else
notify with name ¬
"Switch Notification" title ¬
"Profile Activated:" description ¬
"User 2" application name "Switch"
end if

end tell
end if

-- Stores existing hot corners as properties for next toggle
if runs is 0 then
set tl to do shell script "defaults read com.apple.dock wvous-tl-corner"
set tr to do shell script "defaults read com.apple.dock wvous-tr-corner"
set bl to do shell script "defaults read com.apple.dock wvous-bl-corner"
set br to do shell script "defaults read com.apple.dock wvous-br-corner"

-- Disables hot corners
do shell script "defaults write com.apple.dock wvous-tl-corner -int 1; defaults write com.apple.dock wvous-br-corner -int 1; defaults write com.apple.dock wvous-bl-corner -int 1; defaults write com.apple.dock wvous-tr-corner -int 1; killall Dock"
set runs_A to 1
end if

-- Sets hot corners back to existing values
if runs is 1 then
do shell script ("defaults write com.apple.dock wvous-tl-corner -int " & tl & "; defaults write com.apple.dock wvous-br-corner -int " & br & "; defaults write com.apple.dock wvous-bl-corner -int " & bl & "; defaults write com.apple.dock wvous-tr-corner -int " & tr & "; killall Dock")
set runs_A to 0
end if

-- Initializes the trackpad preference pane
tell application "System Preferences"
set current pane to pane "com.apple.preference.trackpad"
end tell

tell application "System Events"
tell process "System Preferences"
-- Toggles between natural scrolling and unnatural(?) scrolling
click radio button "Scroll & Zoom" of tab group 1 of window "Trackpad"
click checkbox 1 of tab group 1 of window "Trackpad"
-- Toggles tap to click on
click radio button "Point & Click" of tab group 1 of window "Trackpad"
click checkbox 1 of tab group 1 of window "Trackpad"
end tell
end tell

quit application "System Preferences"

-- Keeps track of where you are at in the toggle
set runs to runs_A

-- Call to make sure growl is running
on appIsRunning(appName)
tell application "System Events" to (name of processes) contains appName
end appIsRunning