# | Copyright 2023-2024 John Ciolfi
# |
# | 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
# | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# | 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 <http://www.gnu.org/licenses/>.
# |
# | Commentary:
# |
# | Use this as a template for creating org-files with MATLAB and other language code blocks.
# | The '#+COMMENT' lines configure org-mode.

#+startup: showall
#+startup: inlineimages       //  C-c C-x C-v to toggle, C-c C-x C-M-v to redisplay
#+startup: latexpreview       //  C-c C-x C-l to toggle

#+html_head_extra: <link rel="stylesheet" type="text/css" href="css/styles-from-org.css"/>
#+html_head_extra: <link rel="stylesheet" type="text/css" href="css/styles.css"/>
#+options: ^:{}
#+options: toc:nil
#+latex_header: \usepackage[margin=0.5in]{geometry}
#+latex_header: \usepackage{parskip}
#+latex_header: \usepackage{tocloft}
#+latex_header: \advance\cftsecnumwidth 0.5em\relax
#+latex_header: \advance\cftsubsecindent 0.5em\relax
#+latex_header: \advance\cftsubsecnumwidth 0.5em\relax

# | Specifying "#+property: header-args+ :eval no-export" disables code block evaluation
# | prompting during export to HTML, PDF, etc.
#+property: header-args+ :eval no-export

* Overview

[[https://orgmode.org/][Org-mode]] and [[https://sourceforge.net/projects/matlab-emacs/][matlab-mode]] provide an efficient and effective system for creating scientific documents
which contain MATLAB code and/or Simulink models along with the results of these.  The results of
running MATLAB code or simulating Simulink models is placed into the org-mode file by org-mode using
org babel. [[https://orgmode.org/worg/org-contrib/babel/][Org babel]] is org-mode's ability to execute source code within org-mode files and
optionally insert the results back into the org-mode file. You define source code in code blocks,
e.g.

 : #+begin_src LANGUAGE <OPTIONS>
 :   <CODE>
 : #+end_src

See [[Setup and Export][Setup and Export]] below for instructions on how to setup org babel for matlab code blocks and how
to use this example as a template.

* matlab-code blocks

** matlab code blocks are semantically colored

With org-mode you can embed semantically colored code such as MATLAB within your document and
semantically edit it using "Org -> Editing -> Edit Source Example" menu or =C-c '=. For example,

#+begin_src matlab
  x = [12, 64, 24];
  plotType = 'pie3';

  switch plotType
    case 'bar'
      bar(x)
      title('Bar Graph')
    case {'pie', 'pie3'}
      pie3(x)
      title('Pie Chart')
    otherwise
      warning('Unexpected plot type. No plot created.')
  end
#+end_src

** matlab code block evaluation with ~ans~ results

You use org-mode babel to evaluate MATLAB code blocks. The evaluation is done by sending the MATLAB
code to the ~*MATLAB*~ buffer created by ~M-x matlab-shell~. To do the evaluation, the ~*MATLAB*~
shell must be waiting for input at the ">>" prompt. If you type =C-c C-c= in a matlab code block,
org-mode will evaluate the code in the ~*MATLAB*~ shell buffer and insert the value of =ans= just
below the code block. The ~*MATLAB*~ shell buffer is reused, thus one matlab code block evaluation
can leave variables for another code block evaluation.

When the matlab code block header contains ":results verbatim", the value of the MATLAB ~ans~
variable is saved using ~writematrix(ans, orgTmpFile, 'Delimiter', 'tab')~ and then the contents
of the /orgTmpFile/ is inserted under the "#+RESULTS:". In this example code block, the ":exports
both" header option says when exporting, keep the MATLAB code and also the results when exporting.
If you want to see only the results, leave off the ":exports both" option.

#+begin_src matlab :exports both :results verbatim
  a = 2 + 3;
  ans = magic(a);
#+end_src

#+RESULTS:
| 17 | 24 |  1 |  8 | 15 |
| 23 |  5 |  7 | 14 | 16 |
|  4 |  6 | 13 | 20 | 22 |
| 10 | 12 | 19 | 21 |  3 |
| 11 | 18 | 25 |  2 |  9 |

** matlab code block evaluation with ~output~ results

You can insert the results displayed by MATLAB by using the header option, ":results output":

#+begin_src matlab :exports both :results output
  disp('The results are:')
  a = [1, 2; 3, 4]
  b = a * 2
#+end_src

#+RESULTS:
#+begin_example
The results are:

a =

     1     2
     3     4

b =

     2     4
     6     8
#+end_example

** matlab code block evaluation with ~latex~ results

With the [[https://www.mathworks.com/help/symbolic/][Symbolic Math Toolbox]], you can produce LaTeX using the header option ":results output latex":

#+begin_src matlab :exports both :results output latex
  m = [4*pi, 3*pi; 2*pi, pi];
  result = latex(sym(m));
  disp(result)
#+end_src

#+RESULTS:
#+begin_export latex
\left(\begin{array}{cc} 4\,\pi  & 3\,\pi \\ 2\,\pi  & \pi  \end{array}\right)
#+end_export

You can use LaTeX directly, for example:

#+begin_export latex
  \begin{align}
  y(t)       = & f_o(t,x_c,x_d,u,P) && - \text{ outputs } \\
  \dot{x}_c(t) = & f_d(t,x_c,x_d,u,P) && - \text{ derivatives } \\
  x_d(t+h)   = & f_u(t,x_c,x_d,u,P) && - \text{ update }
  \end{align}
#+end_export

** matlab code block evaluation with ~figure~ results

You can use org-mode babel evaluate MATLAB code blocks to plot and insert figures back into this
file as well as the published (exported) html, LaTeX, pdf, odx (word), etc. file. To do this we use
a matlab code block with ":results file graphics" header option. After evaluating the code
block, org babel will print the current figure, [[https://www.mathworks.com/help/matlab/ref/gcf.html][gcf]], using "print -dpng FILE.png" where the name
of FILE.png comes from the ":file FILE.png" header option. In this example, we place the
":file FILE.png" header option on a separate line prior to the matlab code block to aid
in clarity.

#+header: :file sinewave.png
#+begin_src matlab :exports both :results file graphics
  t = [0 : 0.1 : 2*pi];
  y = sin(t);
  plot(t, y);
  set(gcf, 'PaperUnits', 'inches', 'PaperPosition', [0 0 4 3]) % Set the size to 4" x 3"
#+end_src

#+RESULTS:
[[file:sinewave.png]]

* Setup and Export

1. Enable MATLAB code block export.

   To enable exporting of org containing matlab code blocks, you need to

    : M-x customize-variable RET org-babel-load-languages RET

   and add matlab, then 'Save for future sessions' using the 'State' button.

   If matlab has not been added to org-babel-load-languages, when you try to evaluate a matlab code
   block, you will see

   : org-babel-execute-src-block: No org-babel-execute function for matlab!

2. Use these files as a template for your org files.

   #+begin_src bash
     cd your-working-directory
     cp /path/to/Emacs-MATLAB-Mode/examples/matlab-and-org-mode.org your-file.org
     cp -r /path/to/Emacs-MATLAB-Mode/examples/css .      # If exporting to html
   #+end_src

   Notice that within the *.org file there are several ~#+<comments>~. These setup for LaTeX/PDF and HTML export.

3. Configure HTML export.

   You need the htmlize package (1https://melpa.org/#/htmlize) to get coloring for HTML export.  For
   HTML export we set the "#+html_head_extra" properties in our org file to configure CSS.

   HTML export uses

   - [[file:css/styles-from-org.css]]. This is generated by running
     : M-x org-html-htmlize-generate-css
     and you'll want to update this for your version of Emacs.

   - [[file:css/styles.css]]. This contains customizations which you can edit as desired.

4. Configure PDF export.

   To get colored, better looking PDF, use the minted package. This
   setup can go in your =~/.emacs=:

    #+begin_src emacs-lisp
      (defun setup-org-pdf ()
	"Customize org PDF generation for color and more."
	(if (not (boundp 'org-latex-src-block-backend))
	    (message "Unable to configure org PDF export because it is too old.")
	  (setq org-latex-src-block-backend 'minted
		org-latex-packages-alist '(("cache=false" "minted"))
		org-latex-minted-options '(("xleftmargin" "1em")
					   ("breaklines" "true")
					   ("fontsize" "\\small"))
		org-latex-image-default-width ""
		;; Default value of org-latex-pdf-process does not include -shell-escape which is needed for minted
		;; Also improve latex log file error messages by adding -file-line-error
		org-latex-pdf-process '("%latex -file-line-error -shell-escape -interaction nonstopmode -output-directory %o %f"
					"%latex -file-line-error -shell-escape -interaction nonstopmode -output-directory %o %f"
					"%latex -file-line-error -shell-escape -interaction nonstopmode -output-directory %o %f")
		;; Keep *.log files to aid in debugging.
		org-latex-logfiles-extensions (remove "log" org-latex-logfiles-extensions))

	  ;; Color the hyper links, see
	  ;; https://tex.stackexchange.com/questions/823/remove-ugly-borders-around-clickable-cross-references-and-hyperlinks
	  (add-to-list 'org-latex-default-packages-alist
		       '("colorlinks=true,linkcolor={red!50!black},citecolor={blue!50!black},urlcolor={blue!80!black}"
			 "hyperref" nil))))

      (eval-after-load "ox-latex"
	'(setup-org-pdf))
    #+end_src

5. Export.

   After this setup, you can use the "Org -> Export/Publish" or ~C-c C-e~ to export to HTML, PDF,
   etc.

# LocalWords:  showall inlineimages latexpreview usepackage parskip tocloft cftsecnumwidth defun
# LocalWords:  cftsubsecindent cftsubsecnumwidth sinewave cp htmlize writematrix tmp odx boundp setq
# LocalWords:  alist xleftmargin breaklines fontsize nonstopmode logfiles colorlinks linkcolor dpng
# LocalWords:  citecolor urlcolor hyperref
