Sublime Forum

Launching an external process

#1

Hi,

I was just typing a LaTeX document inside Sublime and I wonder how to launch ie “pdflatex” on it.
I had a look at the docs, but “build”, “exec” etc. are not documented.

Thanks for any suggestion.

0 Likes

Zen Coding ( CSS Snippets )
#2

you can use python’s os.system() in a python plugin.

for example:

[code]
import sublime, sublimeplugin
import os
class MyPluginCommand(sublimeplugin.TextCommand):
def run(self, view, args):
f = view.fileName();
result = os.system("parser.exe " + f)

def isEnabled(self, view, args):
	return True[/code]
0 Likes

#3

Thanks for the suggestion vim, I’ve tried but got problems.

[code]#!/usr/bin/env python

-- coding: utf-8 --

import sublime, sublimeplugin
import os

class PdfLatexCommand(sublimeplugin.TextCommand):
def run(self, view, args):
f = view.fileName()
print “the file is %s”%f
result = os.system("pdflatex " + f)

def isEnabled(self, view, args):
    return True[/code]

(pdflatex is in my PATH so I don’t need to put the “.exe” behind it).
I’ve binded the command to a key, but nothing seems to happen.

So, I’ve tried to do a ‘LaTeX.sublime-build’ file with this (I took it from the Haskell one):

buildCommand exec "^(...*?):([0-9]*):?([0-9]*)" pdflatex.exe '"$File"'

It works, but in fact I really don’t know what I’m doing. What’s the regexp “^(…?):([0-9]):?([0-9]*)” for ?
And now that my file ie “myfile.tex” has been compiled to “myfile.pdf”, how to call my reader on it ? $File returns the file name, I need it without its extension + “pdf” ($File:-3]+“pdf” in Python). It must exist other variables like $File, but what are their names ?

I know it’s pain to write documentation, but Sublime really needs better docs (the wiki has become unreadable). We can all help jps on this point, I think it’s no problem.

0 Likes

#4

regarding the first method i suggested maybe you need to add:

[code]class MyPluginCommand(sublimeplugin.TextCommand):
def run(self, view, args):
f = view.fileName();
exe = sublime.packagesPath()
exe = os.path.join(exe, “User”)
exe = os.path.join(exe, “MyParser.exe”)

	# Spaces in path workaround:
	# add an extra quote (!) before the quoted command name:
	# result = os.system('""pythonbugtest.exe" "test"')
	# Explanation:
	# there was a time when the cmd prompt treated all spaces as delimiters, so
	# >cd My Documents
	# would fail. Nowadays you can do that successfully and even
	# >cd My Documents\My Pictures
	# works.
	# In the old days, if a directory had a space, you had to enclose it in quotes
	# >cd "My Documents"
	# But you didn't actually need to include the trailing quote, so you could get away with
	# >cd "My Documents
	cmd = '""%(exe)s" "%(args)s""' % {'exe' : exe, 'args' : f } # stderr > out.txt 2>&1
	result = os.system(cmd)[/code]

that what i have used once and it worked. regarding the other method, i must admit it seems cleaner, but i can join your feelings here, i also don’t have a clue how it works (i stumbled on it once, but couldn’t figure it out)

0 Likes

#5

I recommend using a Makefile for these sort of things, when I’m working with pdfs, I use a Makefile along the lines of:

foo.pdf: foo.tex
	pdfclose --all
	pdflatex -interaction=nonstopmode foo.tex
	pdfopen --file foo.pdf

The requires you to have make installed (e.g., from cygwin), and pdfopen/pdfclose (availble from a few places, magic.aladdin.cs.cmu.edu/2005/07 … -pdfclose/ is one).

The syntax of sublime-build files is:

buildCommand exec error-regex command [args].

The regex matches file names in the output of the command, typically compiler errors messages. Submatch 1 should be the filename, 2 the line number, and 3 the column (the latter two being optional). The regex must be quoted, and any escapes within it double-escaped.

I’m not happy with the syntax of *.sublime-build files, it’s on the todo list to make them more reasonable.

0 Likes

#6

Here’s some snippets from my pdflatex compile command. Should be almost everything you need.

#
# COMPILE LATEX AND LAUNCH ACROBAT
#
def compilePdf(latexFile):
  miktexExe = miktexCommandPath("pdflatex")
  commandLine = " --interaction=nonstopmode --aux-directory c:\\temp\\ \"" + latexFile + "\""
  # two compiles, to make sure contents etc are up-to-date
  for i in range(2):      
    print runSysCommand(miktexExe, commandLine) 
  pdf = os.path.splitext(latexFile)[0] + ".pdf"
  print "pdf created at '%s'" % pdf
  subprocess.Popen(pdf, shell=True)

#
# RUN EXE AND GET OUTPUT
#
def getOutputOfSysCommand(commandText, arguments=None):
  """Returns the output of a command, as a string"""
  print "getting output of %s %s" % (commandText, arguments)
  p = subprocess.Popen([commandText, arguments], shell=True, bufsize=1024, stdout=subprocess.PIPE)
  p.wait()
  stdout = p.stdout
  return stdout.read()

#
# WHERE DOES MIKTEX LIVE?
#
def miktexCommandPath(commandName):
  return os.path.join(programFiles(), "MiKTeX 2.7\\miktex\\bin", commandName + ".exe")

#
# WHERE ARE PROGRAM FILES?
#
def programFiles():
  prog32 = "c:\\program files"
  prog64 = "c:\\program files (x86)"
  if os.path.exists(prog64):
    return prog64
  elif os.path.exists(prog32):
    return prog32
  else:
    raise Exception("can't find a program files")
0 Likes

#7

Thanks for all your answers,

jps : thanks for clarifying these points, I know now what the regexps are for. I wasn’t aware of pdfopen/pdfclose : nice tool !

SteveCooperOrg : I’ll try to adapt it to my needs as I’m using TeXLive 2008 on Windows.

0 Likes