Find file
Fetching contributors…
Cannot retrieve contributors at this time
121 lines (107 sloc) 4.19 KB
;; emacs-xcode.el --- an interface to the XCode IDE.
;; Copyright (C) 2009 Yves Senn <>
;; This program is free software: you can redistribute it and/or modify
;; it under the terms of the GNU General Public License as published by
;; the Free Software Foundation, either version 3 of the License, or
;; (at your option) any later version.
;; This program is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; GNU General Public License for more details.
;; You should have received a copy of the GNU General Public License
;; along with this program. If not, see <>.
;;; Contributors
;; - Yves Senn <yves senn * gmx ch>
;; - Peter Jones <>
;;; Conventions
;; Conventions used in this file: Name internal variables and functions
;; "xcode--<descriptive-name>", and name xcode command invocations
;; "xcode/command-name", like xcode/build.
;;* emacs-xcode
(defvar *xcode-project-root* nil)
(defun xcode--project-root ()
(or *xcode-project-root*
(setq *xcode-project-root* (xcode--project-lookup))))
(defun xcode--project-lookup (&optional current-directory)
(when (null current-directory) (setq current-directory default-directory))
(cond ((xcode--project-for-directory (directory-files current-directory)) (expand-file-name current-directory))
((equal (expand-file-name current-directory) "/") nil)
(t (xcode--project-lookup (concat (file-name-as-directory current-directory) "..")))))
(defun xcode--project-for-directory (files)
(let ((project-file nil))
(dolist (file files project-file)
(if (> (length file) 10)
(when (string-equal (substring file -10) ".xcodeproj") (setq project-file file))))))
(defun xcode--project-command (options)
(concat "cd " (xcode--project-root) "; " options))
(defun xcode/build-compile ()
(compile (xcode--project-command (xcode--build-command))))
(defun xcode/build-list-sdks ()
(message (shell-command-to-string (xcode--project-command "xcodebuild -showsdks"))))
(defun xcode--build-command (&optional target configuration sdk)
(let ((build-command "xcodebuild"))
(if (not target)
(setq build-command (concat build-command " -activetarget"))
(setq build-command (concat build-command " -target " target)))
(if (not configuration)
(setq build-command (concat build-command " -activeconfiguration"))
(setq build-command (concat build-command " -configuration " configuration)))
(when sdk (setq build-command (concat build-command " -sdk " sdk)))
(defun xcode/toggle-header-and-source nil
"Toggle between source and header files"
(let ((fname buffer-file-name) oname)
(setq oname
((string-match "\\.h$" fname) (replace-match ".m" nil nil fname))
((string-match "\\.m$" fname) (replace-match ".h" nil nil fname))
(t fname)))
(find-file oname)))
(defun bh-compile ()
(let ((df (directory-files "."))
(has-proj-file nil)
(while (and df (not has-proj-file))
(let ((fn (car df)))
(if (> (length fn) 10)
(if (string-equal (substring fn -10) ".xcodeproj")
(setq has-proj-file t)
(setq df (cdr df))
(if has-proj-file
(compile "xcodebuild -configuration Debug")
(compile "make")
(defun bh-choose-header-mode ()
(if (string-equal (substring (buffer-file-name) -2) ".h")
;; OK, we got a .h file, if a .m file exists we'll assume it's
;; an objective c file. Otherwise, we'll look for a .cpp file.
(let ((dot-m-file (concat (substring (buffer-file-name) 0 -1) "m"))
(dot-cpp-file (concat (substring (buffer-file-name) 0 -1) "cpp")))
(if (file-exists-p dot-m-file)
(if (file-exists-p dot-cpp-file)
(add-hook 'find-file-hook 'bh-choose-header-mode)
(provide 'xcode)