1

I want to make a .desktop file that opens a folder in my default file manager in a new tab. To test if it opened the right location, I tried nautilus ~/*folder*. That opens my file manager, but it says that something went wrong. The same happens when I use nautilus /home/*username*/*folder*. What command can I use to open a specific folder in home in a new tab from a .desktop file?

My goal is to have an icon on my dock (plank) that opens the map ~/Downloads in a new tab in Nautilus.

Jacob Vlijm
  • 83,767
Maud Kon
  • 561
  • 1
  • 4
  • 18
  • Do you want a new tab or a new window? – Pilot6 May 25 '15 at 16:56
  • 1
    nautilus does not support opening a directory in a new tab from command line, only in a new window. It can be faked however, but what is the error it gives? (could you @ping me if you addres a comment to me, or anyone else? Otherwise I'd have to keep all posts opened :) ) – Jacob Vlijm May 25 '15 at 17:25
  • @n0noob and other voters (@muru?): There is a subtle difference: the supposed dupe asks for opening new directories anyway, not about opening a specific directory in a new tab. The answer there offers to do that, (although dupes are about questions), but moreover, I couldn't get it working there. – Jacob Vlijm May 26 '15 at 07:09
  • @JacobVlijm Yes, and I voted to close as that is a more general question, with a possible merging of questions to get your answer there. – muru May 26 '15 at 08:14
  • @muru I agree the answer there could possibly cover this one, but it doesn't as far as I can see (tried). The question however does not, and opening a specific directory requires a more extensive number of steps. I think the supposed dupe is fit for a more limited number of situations; while leaving out a number of lines here will cover the supposed dupe question (will post here if I get home). – Jacob Vlijm May 26 '15 at 08:19
  • @JacobVlijm Then we are reading the questions very differently. OP wants to create a launcher that when clicked opens a new tab. The dupe: "if I click a launcher/shortcut icon etc i will get a new nautilus window. If there is already a nautilus window open, I would rather it open up in a new tab" - the only difference is that they already have a launcher. What the answer there says right now, I don't know and don't care. – muru May 26 '15 at 08:28
  • @muru Differently indeed: My goal is to have an icon on my dock (plank) that opens the map ~/Downloads in a new tab in Nautilus. That is: opening a tab in a specific directory – Jacob Vlijm May 26 '15 at 08:35
  • @JacobVlijm What do you imagine the shortcut icon in the other question does? Open in random directories? – muru May 26 '15 at 08:36
  • @muru, well, not in a controlled directory anyway (and not in ~/Downloads) – Jacob Vlijm May 26 '15 at 08:37
  • @JacobVlijm Come to [chat]. – muru May 26 '15 at 08:39

2 Answers2

4

EDIT:

As a result of ongoing insight, below an improved version of the script.

Due to the fact that the script now pastes the path instead of typing it (using xdotool), the script is more reliable. Although the script is not actually faster (consider it is a work around, due to nautilus' lack of cli options) the script "feels" more "crispy". Fact remains however that the script simply needs to wait for the GUI to be ready for each next step, since it simulates user actions. Timing inside the script is on the save side; on faster systems, one might be able to do some optimization.

Use the script exactly as explained in the original answer; it (still) needs both wmctrl and xdotool to be installed. This version furthermore rquires xclip:

sudo apt-get install xclip

The new version of the script:

#!/usr/bin/env python3
import subprocess
import sys
import time

arg = sys.argv[1:]
arg = arg[0] if arg else ""

def get(cmd):
    return subprocess.check_output(cmd).decode("utf-8").strip()

try:
    pid = get(["pidof", "nautilus"])
except subprocess.CalledProcessError:
    wlist = []    
else:
    wlist = [l for l in get(["wmctrl", "-lp"]).splitlines() if pid in l\
             and "_NET_WM_WINDOW_TYPE_NORMAL" in get(["xprop", "-id", l.split()[0]])]

if wlist:
    w = wlist[-1].split()[0]
    subprocess.call(["wmctrl", "-ia", w])
    subprocess.call(["/bin/bash", "-c", "printf '"+arg+"' | xclip -selection clipboard"])
    subprocess.Popen(["xdotool", "key", "Control_L+t"])
    time.sleep(0.4)
    subprocess.Popen(["xdotool", "key", "Control_L+l"])
    time.sleep(0.2)
    subprocess.call(["xdotool", "key", "Control_L+v"])
    subprocess.Popen(["xdotool", "key", "Return"])

else:
    subprocess.Popen(["nautilus", arg])



Old answer:

Nautilus does not have a command line option to open a new tab, however, you can "fake" it with the help of a script, using xdotool and wmctrl.

How to use

  1. Install (if necessary) both wmctrl and xdotool:

    sudo apt-get install xdotool wmctrl
    
  2. Copy the script below into an empty file, save it as nautilus_tab (no extension) in ~/bin, and make it executable.
    If the directory ~/bin didn't exist yet, create it, and run source ~/.profile to make the directory "show up" in $PATH. (or alternatively, log out/in)

  3. Test-run it by running the command:

    nautilus_tab <directory>
    

    It should:

    • if no nautilus window is open, open a new nautilus window in the directory
    • if a window is open, open a new tab in the directory

The script

#!/usr/bin/env python3
import subprocess
import time
import sys

get = lambda cmd: subprocess.check_output(cmd).decode("utf-8")
def run(cmd):
    subprocess.call(cmd)

try:
    arg = sys.argv[1]
except:
    arg = ""

try:
    pid = get(["pidof", "nautilus"]).strip()
except subprocess.CalledProcessError:
    run(["nautilus ", arg])
else:
    w = [l.split() for l in get(["wmctrl", "-lp"]).splitlines() if pid in l][-1]
    print(w)
    w_id = w[0]   
    if len([l for l in get(["xprop", "-id", w_id]).splitlines() if all(
        ["_NET_WM_WINDOW_TYPE(ATOM)" in l, "_TYPE_NORMAL" in l])]) != 0:
        run(["wmctrl", "-ia", w[0]]); time.sleep(0.1)
        run(["xdotool", "key", "Control_L+t"])
        if arg != "":
            run(["xdotool", "key", "Control_L+l"])
            time.sleep(0.2)
            run(["xdotool", "type", arg])
            time.sleep(0.02*len(arg))
            run(["xdotool", "key", "Return"])
    else:
        run(["nautilus", arg])

Notes

  • The script is a workaround, to simulate user actions. As a result, the timing "inside" the script is important. I set timing to "safe" values on my system, and made it "smart" if possible. If it might not work correctly on your system, leave a comment.
  • The script will possibly brake if the targeted window (to add the tab to) is on another workspace
  • In case of directories with spaces, use quotes:

    nautilus_tab '</directory/with spaces>'
    

If no argument (-directory) is used, the script will open a new tab in the same directory as the currently opened nautilus window. If no `nautilus window was opened, a new window will open in your home directory.

Jacob Vlijm
  • 83,767
  • @MaudKon Just curious, but did you try it? – Jacob Vlijm Jun 02 '15 at 08:18
  • Perhaps you should go back to using proper lists for call instead of [bash, -c, "big huge command"] – muru Feb 17 '16 at 02:43
  • @mure done, hardly remember writing it. Works fine though. – Jacob Vlijm Feb 17 '16 at 07:26
  • Interesting, I could get the bash script working simply with Exec in desktop file written without /bin/bash -c and with full path instead of ~. On the other hand, I can see your script working very slowly with commands Ctrl+L and Ctrl+V (and also see that we need Ctrl+T before those to open a New Tab). How can we make it run faster please? – Sadi Mar 26 '16 at 13:37
  • @Sadi Not sure where you find /bin/bash in my code? Thanks for mentioning the speed issue. This post is from quite a while ago, relatively, ongoing insight makes me use pasting text instead of typing these days. The fact remains however that the cleanest (and fastest) option is not available, since nautilus' cli options are quite limited. I will edit if I get home. – Jacob Vlijm Mar 26 '16 at 15:23
  • Thanks, the bash command is in the other (bash) script mentioned above, sorry for the confusion – Sadi Mar 26 '16 at 15:27
  • 1
    Hi @Sadi updated. See the remark in the updated section. – Jacob Vlijm Mar 27 '16 at 15:25
  • Thanks a lot! It works much better now. BTW have you looked at the bash script here (http://askubuntu.com/a/123801/47343)? I've also tried it before I saw this, and it seems to work a little faster, but a little buggy, (e.g. sometimes not catching the path right) I guess this might be related with what you call "a safe speed" ;-) – Sadi Mar 27 '16 at 15:37
  • 1
    @Sadi exactly. The timing needs to be surprisingly slow on this system, but I need to try on my other systems once I can (tomorrow). This is my 12 years old laptop :) Wow, never noticed the link! – Jacob Vlijm Mar 27 '16 at 15:42
  • It looks fine on my system; only very sharp eyes can see the action now ; -) Also love your QLE here (https://launchpad.net/~vlijm/+archive/ubuntu/qle) by the way -- Ubuntu should incorporate it into Unity ; -) – Sadi Mar 27 '16 at 15:46
  • 1
    @Sadi great that you found qle! It was my very first project ever. I am working on a new version, but the old version still works fine over the Ubuntu versions since 11.04 :) – Jacob Vlijm Mar 27 '16 at 15:49
0

(These sites drive me crazy with their weird requirements - this should be a comment, but I don’t have enough reputation and this kind of nonsense doesn’t encourage me to get it!)

Jacob’s answer does not work for paths with spaces in them. It requires two changes...

run("nautilus "+arg)
run('nautilus "'+arg+'"')

run("xdotool type "+arg)
run('xdotool type "'+arg+'"')

I run it with Thunar though and it doesn’t interpret ~ well. E.g. thunar-tab.py "~/Documents" will produce an error that /home/user/~/Documents cannot be found. You have to call it with an explicit path.