second version from author
[ob-spice.git] / ob-spice.el
blob55d8cba2b5e0cc04d2b3b609a8d1aab42fe112c0
1 ;;; ob-spice.el --- org-babel functions for spice evaluation
3 ;; Author: Tiago Oliveira Weber
4 ;; Version: 0.4
5 ;; 2016
6 ;; Homepage: http://tiagoweber.github.io
8 ;; Org-Babel support for evaluating spice script.
9 ;; Inspired by Ian Yang's org-export-blocks-format-plantuml (http://www.emacswiki.org/emacs/org-export-blocks-format-plantuml.el)
11 ;;; Requirements:
12 ;; ngspice
14 ;;; Code:
15 (require 'ob)
17 (add-to-list 'org-babel-tangle-lang-exts '("spice" . "cir"))
19 (defun ob-spice-concat (wordlist)
20 "Concat elements of a list of string into a string separated by spaces"
21 ;; example of usage
22 ;; (ob-spice-concat '("This" "is" "a" "long" "journey"))
23 (setq newtext (car wordlist)) ; first word is without space before
24 (setq wordlist (rest wordlist)) ; exclude the first word from the list
25 (dolist (word wordlist newtext) (setq newtext (concat newtext " " word)) ) ;loop through the list and concatenate the values
30 (defun org-babel-expand-body:spice (body params)
31 "Expand BODY according to PARAMS, return the expanded body."
32 (let* (
33 (vars (mapcar #'cdr (org-babel-get-header params :var)))
36 (setq newbody "");
37 (setq bodylinelist (split-string body "\n"))
38 (dolist (line bodylinelist newbody) (progn ;loop through list of lines
39 (setq wordlist (split-string line " "))
40 (setq firstword 1)
41 (dolist (word wordlist) (progn ;loop through the words
42 (if (string-match "\\$\\(.*\\)\\[\\(.*\\)\\]" word)
43 (progn
44 ;; if matchs a vector variable format
45 (setq varname (match-string 1 word))
46 (setq varindex (match-string 2 word))
47 ;; search varname in vars and use the value of varindex to word
48 (setq newword (nth (string-to-number varindex)
49 (car
50 (assoc-default varname vars
51 (lambda (key candidate)
52 (string= key candidate))))))
54 (if (not (eq newword nil))
55 (if (not (stringp newword))
56 (setq word (number-to-string newword))
57 (setq word newword)
60 ) ;; end of (if (string-match "\\$\\(.*\\)\\[\\(.*\\)\\]" word))
61 (if (string-match "\\$\\(.*\\)\\." word) ;; if variable has a dot in the end
62 (progn
63 ;; if matchs a non-vector variable format
64 (setq varname (match-string 1 word))
65 (setq newword
66 (assoc-default varname vars
67 (lambda (key candidate)
68 (string= key candidate))))
69 (if (not (eq newword nil))
70 (progn
71 (if (not (stringp newword))
72 (setq newword (number-to-string newword)))
73 (setq word (replace-match (concat newword ".") nil nil word))
74 ;(setq word word)
77 );; end of (if (string-match "\\$\\(.*\\)\\." word)
78 (if (string-match "\\$\\(.*\\)" word)
79 (progn
80 ;; if matchs a non-vector variable format
81 (setq varname (match-string 1 word))
82 (setq newword
83 (assoc-default varname vars
84 (lambda (key candidate)
85 (string= key candidate))))
86 (if (not (eq newword nil))
87 (if (not (stringp newword))
88 (setq word (number-to-string newword))
89 (setq word newword)
92 );; end of (if (string-match "\\$\\(.*\\)" word)
95 (setq newbody (concat newbody
96 (if (not (eq firstword 1)) " ")
97 word))
98 (setq firstword 0)
99 ) ;; end of (progn
100 ) ;; end of (dolist (word wordlist))
102 (setq newbody (concat newbody "\n"))
103 ) ;; end of (progn ;; loop through list of lines ... )
104 ) ;; end of (dolist (line bodylinelist) ...function ...)
108 (defun org-babel-execute:spice (body params)
109 "Execute a block of Spice code with org-babel."
110 (let ((body (org-babel-expand-body:spice body params))
111 (vars (mapcar #'cdr (org-babel-get-header params :var)))
114 ;;******************************
115 ;; clean temporary files
116 (mapc (lambda (pair)
117 (when (string= (car pair) "file")
118 (setq textfile (concat (cdr pair) ".txt"))
119 (setq imagefile (concat (cdr pair) ".png"))
122 vars)
123 ;; (if (file-readable-p textfile) (delete-file textfile))
124 ;; (if (file-readable-p imagefile) (delete-file imagefile))
125 ;;*******************************
127 (org-babel-eval "ngspice -b " body)
129 ;; loop through all pairs (elements) of the list vars and set text and image file if finds "file" var
130 (mapc (lambda (pair)
131 (when (string= (car pair) "file")
132 (setq textfile (concat (cdr pair) ".txt"))
133 (setq imagefile (concat (cdr pair) ".png"))
136 vars)
137 ;; produce results
138 ;; THE FOLLOWING WAS COMMENTED TEMPORARILY
139 ;; (concat
140 ;; (if (file-readable-p textfile)
141 ;; (get-string-from-file textfile))
142 ;; (if (file-readable-p imagefile)
143 ;; (concat '"#+ATTR_HTML: :width 600px \n [[file:./" imagefile "]]")
144 ;; )
145 ;; )
147 ;; ;; Get measurement values from text-file by splitting comma separated values
148 (if (file-readable-p textfile)
149 (progn
150 (setq rawtext (get-string-from-file textfile))
151 ;;(setq rawtext (replace-regexp-in-string "\n" "" rawtext))
152 (setq rawtext (replace-regexp-in-string "\n" "" rawtext))
153 (setq result (split-string rawtext ","))
156 (if (file-readable-p imagefile)
157 (progn
158 ;; test if result exist already
159 ;;(if (boundp 'result)
160 (add-to-list 'result (concat '"[[file:./" imagefile "]]") t) ;; add imagefile to last entry
161 ;;(concat '"[[file:./" imagefile "]]")
162 ;;)
165 result
166 ;; Produce output like '(test test2)
167 ;;'(test test2)
172 (provide 'ob-spice)
173 ;;; ob-spice.el ends here