9/18/2013

Launch App From Its Name

Long time ago, I want to launch app when AutoVoice recongnized the app name I said. Unfortunately, the "Launch App" will not support app name as variable at present. After some digging, I found a way out. Here it is.

A launcher is something similar with desktop shell in Windows, I think. You should know most app will leave its package information in the database of launcher when installed. So we can dive into the database of launcher and pull the specific information out. The figures below shows the database of MIUI launcher in my MIUI ROM. You can find the database in path /data/data/com.miui.home/databases/launcher.db.


Figure 1. tables in launcher.db


Figure 2. records in the table "favourites"


Figure 3. record of app named "SwipePad"

In "Figure 3", the field "intent" is very important for us. We can launch app with "am start" command in Android shell. You can type "am start" command in shell to get detailed help of this command.


Figure 5. "am start" command help

We can launch specific app with "am start" command when we extract useful intent information from corresponding "intent" field.

Here is one of my AutoVoice task which aimed to launch app from speech:

Task: LaunchApp
A1: Run Shell [ Command:sqlite3 /data/data/com.miui.home/databases/launcher.db "SELECT intent FROM favorites WHERE intent IS NOT NULL AND title LIKE '%%avcommnofilter%' LIMIT 1;" Timeout (Seconds):0 Use Root:On Store Output In:%intent Store Errors In: Store Result In: ] 
A2: If [ %intent Is Set ]
A3: Variable Search Replace [ Variable:%intent Search:#Intent;action= Ignore Case:On Multi-Line:Off One Match Only:Off Store Matches In: Replace Matches:On Replace With:am start -a  ] 
A4: Variable Search Replace [ Variable:%intent Search:;category= Ignore Case:On Multi-Line:Off One Match Only:Off Store Matches In: Replace Matches:On Replace With: -c  ] 
A5: Variable Search Replace [ Variable:%intent Search:;launchFlags= Ignore Case:On Multi-Line:Off One Match Only:Off Store Matches In: Replace Matches:On Replace With: -f  ] 
A6: Variable Search Replace [ Variable:%intent Search:;component= Ignore Case:On Multi-Line:Off One Match Only:Off Store Matches In: Replace Matches:On Replace With: -n  ] 
A7: Variable Search Replace [ Variable:%intent Search:;end Ignore Case:On Multi-Line:Off One Match Only:Off Store Matches In: Replace Matches:On Replace With: ] 
A8: Run Shell [ Command:%intent Timeout (Seconds):0 Use Root:On Store Output In: Store Errors In: Store Result In: ] 
A9: Else 
A10: Music Play [ File:Tasker/Notify/Dialog/sorry.wav Start:0 Loop:Off Stream:3 ] 
A11: End If 

Note: 
1. Records are case-sensitive in SQLite database. My former task can not process this situation.
2. Few apps can't show on desktopof launcher, and even can't be found in launcher.db. You can't launch it in this way.
3. Although I talked here with taking the MIUI launcher as example, I think the principle will be same with other launcher. Maybe databases differ!
4. If you want do it with a separate app, you can try AutoLaunch(paid).
5. Some useful files for all packages installed:  /data/system/packages.list  /data/system/packages.xml
6. A useful command to list packages: "pm list packages -f"

2 comments:

  1. I found a simpler way, but still haven't figured it out if that makes sense.
    Using a javascriptlet action:
    var ok = loadApp(appname, false);
    will launch whatever %appname is set to. The problem is that it is case sensitive. Most apps just have the first letter of every word uppercase which is easy enough to loop through and fix, but quite a few throw an uppercase in the middle of a word (all of the AutoApps for example). This would soon get littered with if statements and end up becoming quite lengthy/might as well just use an if statement for each app.

    This would be easy if I could find a list of installed apps as they appear to the user with correct capitalization and all, but I haven't found anything.

    Very cool what you have set up, thanks for sharing

    ReplyDelete
  2. I figured it out, got it down to a 2 liner (err, "actioner"?) I was checking my stock launcher the way you were (Trebuchet) but it only had a handfull of apps in there. Nova Launcher's database had everything though.

    Profile: Launch App (290)
    State: AutoVoice Recognized [ Configuration:Command: "(?open|launch) (?.+) (regex)" ]
    Enter: Anon (291)
    A1: Destroy Scene [ Name:HAL 9000 ]
    A2: Run Shell [ Command:sqlite3 /data/data/com.teslacoilsw.launcher/databases/launcher.db "SELECT title FROM allapps WHERE title LIKE '%%app%' OR title LIKE '%%app' OR title LIKE '%app%';" Timeout (Seconds):0 Use Root:On Store Output In:%launch Store Errors In: Store Result In: ]
    A3: JavaScriptlet [ Code:var ok = loadApp(launch, false); Libraries: Auto Exit:On Timeout (Seconds):45 ]


    I gave up trying to do this a while ago, thank you for posting this.

    ReplyDelete