David Janes' Code Weblog

November 20, 2009

How to use XCode for Android Projects

android, code fragments, ideas, macintosh · David Janes · 6:07 pm ·

Let’s assume you already have an Android project on your Mac.

Create the XCode Project

  • start XCode
  • select File > New Project…
  • select External Build System
  • go to the parent directory of your Android Project
  • in the Save As: field, enter the directory name of your Android Project
  • select the scarily-misnamed Replace option

Add Files

In your new XCode project:

  • select first item in the left hand column, which is the name of your project
  • right-click, select Add > Existing Files…
  • select add files (don’t select the Copy option)
  • organize as desired (I like to do a lot of grouping). You should be probably adding at least your Java files and your Layout resources.

Configure your Build Target

In your new XCode project:

  • look for Targets
  • inside will be a target for your project’s name
  • double click on it
    • change Build Tool to ant
    • change Arguments to install

Clicking ⌘B should now compile your project.

Note: if you figure out how to have a Build vs. Build & Install (e.g. ⌘ENTER) please let me know!.

Getting XCode to Recognize Java errors

  • Reconfigure the Build Target, changing ant to ./xant
  • Make a file xant in the project’s home directory, using the code below
  • do (from a Terminal) chmod a+x xant
#!/usr/bin/env python

import sys
import re
import subprocess

av = list(sys.argv)
av[0] = "ant"

p = subprocess.Popen(av, stdout = subprocess.PIPE)

javac_rex = re.compile(" +[[]javac[]] +")
line_rex = re.compile("[.]java:[\d]+:")

pending = ""
while True:
    d = p.stdout.read(128)
    if not d:
        break

    d = pending + d

    nx = d.rfind('\n')
    if nx == -1:
        pending = d
        continue
    else:
        d, pending = d[:nx + 1], d[nx + 1:]

        d = javac_rex.sub("", d)
        d = line_rex.sub(r"\g<0> error: ", d)
        sys.stdout.write(d)
        sys.stdout.flush()

sys.stdout.write(pending)
p.wait()
sys.exit(p.returncode)

Note: this code has been updated from the original post. It now reads little chunks and outputs them immediately rather than post-processing the ant output.

6 comments »

  1. David Oster · 2009-12-07 15:01

    RE: if you figure out how to have a Build vs. Build & Install (e.g. ⌘ENTER) please let me know!.

    If you edit your python script add these lines after:
    av = list(sys.argv)
    av[0] = “/usr/bin/ant”

    if len(av) == 1 :
    av.append(“compile”)

    then and leave Xcode’s build argument set to $ACTION, then you’ll find that get Xcode’s builds, installs, and clean connected through to ant.

  2. David Janes · 2009-12-08 18:48

    Oh god, awesome, thanks.

  3. David Oster · 2009-12-16 20:20

    After a further look, I’ve been using:
    #!/bin/bash
    if [ "x${ACTION}" == "xclean" ] ; then
    echo CLEAN
    # remove the generated files in bin (Assumes all files in bin are discardable.)
    cp /dev/null bin/a
    rm -rf bin/*
    else
    echo /usr/bin/ant -emacs ${ACTION} $(echo ${BUILD_STYLE} | tr ‘[A-Z]‘ ‘[a-z]‘)
    /usr/bin/ant -emacs ${ACTION} $(echo ${BUILD_STYLE} | tr ‘[A-Z]‘ ‘[a-z]‘)
    fi

    which handles Build, and Clean, for both the Debug and Release targets, but doesn’t do the install, and doesn’t have your Python error editing so Xcode will see it. You script does the install, which is more useful.

    Rather than following Apple’s directions and using an “External Build System” style target, an empty target with a series of custom build phases might work better. You could have a phase like this;

    #!/bin/bash
    if [ "false" == $(osascript -e 'tell application "Finder" to exists process "emulator"') ] ; then
    echo starting Emulator
    ../../android-sdk-mac/tools/emulator -avd ${MYAVD}
    else
    /usr/bin/ant install bin/${TARGET}
    fi

    to start the emulator, or if it was started, install the .apk on it. But that still doesn’t solve the problem of connecting Xcode’s Java debugger via TCP/IP to the environment in the emulator. Sorry I don’t have all the answers.

  4. David Oster · 2009-12-16 20:22

    But it does look like the -emacs command line option to ant makes the errors from ant immediately compatible with Xcode without any need to post process the error messages with Python.

  5. I’ve never worked with Android, but it might also be worth looking at Xcode’s Organizer feature. The Organizer lets you work with Ant/Java projects without cluttering them with Xcode project files. Apple’s doco on using the Organizer with Java is sparse, but these links are a start:
    http://developer.apple.com/mac/library/documentation/Java/Conceptual/Java14Development/02-JavaDevTools/JavaDevTools.html
    http://developer.apple.com/mac/library/documentation/DeveloperTools/Conceptual/XcodeProjectManagement/140-Using_the_Organizer/using_the_organizer.html

  6. David Janes · 2010-04-07 06:13

    Thank you Robert – I’ll check this out, as I’m just in the process of picking up this project again. Timely!

RSS feed for comments on this post. TrackBack URL

Leave a comment

Powered by WordPress