- (let ((patchsym (stgit-patch-at-point)))
- (if (not patchsym)
- (let ((patched-file (stgit-patched-file-at-point t)))
- (unless patched-file
- (error "No patch or file at point"))
- (let ((id (stgit-id (car patched-file))))
- (if (consp (cdr patched-file))
- ;; two files (copy or rename)
- (stgit-run-git "diff" "-C" "-C" (concat id "^") id "--"
- (cadr patched-file) (cddr patched-file))
- ;; just one file
- (stgit-run-git "diff" (concat id "^") id "--"
- (cdr patched-file)))))
- (stgit-run "show" "-O" "--patch-with-stat" "-O" "-M" patchsym))
- (with-current-buffer standard-output
- (goto-char (point-min))
- (diff-mode)))))
+ (case (get-text-property (point) 'entry-type)
+ ('file
+ (let* ((patched-file (stgit-patched-file-at-point))
+ (patch-name (stgit-patch-name-at-point))
+ (patch-id (stgit-id patch-name))
+ (args (append (and (stgit-file-cr-from patched-file)
+ (list (stgit-find-copies-harder-diff-arg)))
+ (cond ((eq patch-id :index)
+ '("--cached"))
+ ((eq patch-id :work)
+ nil)
+ (t
+ (list (concat patch-id "^") patch-id)))
+ '("--")
+ (if (stgit-file-copy-or-rename patched-file)
+ (list (stgit-file-cr-from patched-file)
+ (stgit-file-cr-to patched-file))
+ (list (stgit-file-file patched-file))))))
+ (apply 'stgit-run-git "diff" args)))
+ ('patch
+ (let* ((patch-name (stgit-patch-name-at-point))
+ (patch-id (stgit-id patch-name)))
+ (if (or (eq patch-id :index) (eq patch-id :work))
+ (apply 'stgit-run-git "diff"
+ (stgit-find-copies-harder-diff-arg)
+ (and (eq patch-id :index)
+ '("--cached")))
+ (stgit-run "show" "-O" "--patch-with-stat" "-O" "-M"
+ (stgit-patch-name-at-point)))))
+ (t
+ (error "No patch or file at point")))
+ (with-current-buffer standard-output
+ (goto-char (point-min))
+ (diff-mode))))
+
+(defun stgit-move-change-to-index (file)
+ "Copies the workspace state of FILE to index, using git add or git rm"
+ (let ((op (if (or (file-exists-p file) (file-symlink-p file))
+ '("add") '("rm" "-q"))))
+ (stgit-capture-output "*git output*"
+ (apply 'stgit-run-git (append op '("--") (list file))))))
+
+(defun stgit-remove-change-from-index (file)
+ "Unstages the change in FILE from the index"
+ (stgit-capture-output "*git output*"
+ (stgit-run-git "reset" "-q" "--" file)))
+
+(defun stgit-file-toggle-index ()
+ "Move modified file in or out of the index."
+ (interactive)
+ (let ((patched-file (stgit-patched-file-at-point)))
+ (unless patched-file
+ (error "No file on the current line"))
+ (when (eq (stgit-file-status patched-file) 'unmerged)
+ (error (substitute-command-keys "Use \\[stgit-resolve-file] to move an unmerged file to the index")))
+ (let ((patch-name (stgit-patch-name-at-point)))
+ (cond ((eq patch-name :work)
+ (stgit-move-change-to-index (stgit-file-file patched-file)))
+ ((eq patch-name :index)
+ (stgit-remove-change-from-index (stgit-file-file patched-file)))
+ (t
+ (error "Can only move files in the working tree to index")))))
+ (stgit-refresh-worktree)
+ (stgit-refresh-index))