https://github.com/atreyagaurav/units-mode
Unit conversion in emacs using gnu units
https://github.com/atreyagaurav/units-mode
emacs unit-conversion unit-converter
Last synced: 3 months ago
JSON representation
Unit conversion in emacs using gnu units
- Host: GitHub
- URL: https://github.com/atreyagaurav/units-mode
- Owner: Atreyagaurav
- License: gpl-3.0
- Created: 2022-08-27T18:28:59.000Z (about 3 years ago)
- Default Branch: main
- Last Pushed: 2022-10-27T03:03:32.000Z (almost 3 years ago)
- Last Synced: 2023-03-05T09:52:51.264Z (over 2 years ago)
- Topics: emacs, unit-conversion, unit-converter
- Language: Emacs Lisp
- Homepage:
- Size: 74.2 KB
- Stars: 7
- Watchers: 1
- Forks: 1
- Open Issues: 0
-
Metadata Files:
- Readme: README.org
- License: LICENSE
Awesome Lists containing this project
README
[[https://melpa.org/#/units-mode][file:https://melpa.org/packages/units-mode-badge.svg]]
[[https://stable.melpa.org/#/units-mode][file:https://stable.melpa.org/packages/units-mode-badge.svg]]* Introduction
This mode uses [[https://www.gnu.org/software/units/units.html][gnu units]] (which you need to install) to facilitate unit related conversions/calculations inside emacs.
I wrote =units-mode= so that I can do quick conversion and see the values, as well as get possible units as completion to choose from so I know which units are similar. And =gnu units= being lot more powerful for units, you'll get the full power of =gnu units= inside emacs.
Emacs supports unit conversion in [[https://www.gnu.org/software/emacs/manual/html_node/calc/Units.html][=calc= by default]], so if you use calc then you can do conversions there too however =units-mode= will make the conversion available anywhere, and easily callable functions to convert for your packages too.
*This package is a work in progress* it may not handle all the errors or perform all the checks yet.
* Contents :TOC:
- [[#introduction][Introduction]]
- [[#features][Features]]
- [[#installation][Installation]]
- [[#customizations][Customizations]]
- [[#customize-variables][customize variables]]
- [[#keybindings][Keybindings]]
- [[#interactive-functions][Interactive Functions]]
- [[#examples][Examples]]
- [[#simple-conversion][Simple conversion]]
- [[#derived-units][Derived units]]
- [[#multiple-units][Multiple units]]
- [[#reduce-to-standard-units][Reduce to standard units]]
- [[#package-functions-to-use-in-your-code][Package Functions to use in your code]]
- [[#elisp][Elisp]]
- [[#slime-integration-example-is-for-sbcl-adapt-to-whatever-clisp-you-use][Slime Integration (example is for sbcl; adapt to whatever clisp you use)]]* Features
- convert region to other units (e.g 1 mile ⇒ 5280 ft)
- check =--conformable= units for completion
- Early error out for non-existent units
- Errors out when target unit isn't the same dimension
- reduce expressions to standard unit form (e.g 1ft + 12 inch ⇒ 0.6096 m)
- Calculate molecular weight from chemical formula (e.g. CH3 ⇒ 15.03482)* Installation
First clone this repo into your local machine or install it from melpa, then you can load it.An example config using =use-package= is like this:
#+begin_src emacs-lisp
(use-package units-mode
;; :load-path "/path/to/units-mode"
:hook text-mode
:config
(local-set-key (kbd "C-c u") 'units-convert-region-and-insert))
#+end_src* Customizations
** customize variables
Available variables to customize are:
- =units-binary-path= [default: "units"]
"Path to the units binary."Change this if units isn't in your path, it should point to the units binary
- =units-user-args= [default: ""]
"Extra args for user to add to units command."If there is any args necessary for user. Default arg used by system is "-t" to get terse results so it depends on that to parse the results. Look at =man units= for possible args.
- =units-insert-separator= [default: " = "]
"Separator to insert before inserting the `units' outputs."When using the convert and insert variety of functions the converted value is separated with this separator before being inserted. for eg =1 m = 3.2808399 ft=.
** Keybindings
feel free to set your own keybindings, example is shown in [[Installation]]. The functions you can bind are in [[Interactive Functions]].* Interactive Functions
- =units-convert-region=
Convert the marked region to a unit by asking units interactively. The interactive prompt has completions for defined units with same dimension but complex ones can be entered too.- =units-convert-region-and-insert=
Convert region to unit and insert the results. Same as =units-convert-region= but insert the results.- =units-reduce-region=
Reduce the region to standard units.- =units-reduce-region-and-insert=
Reduce the region to standard units and insert the results.- =units-quick-convert=
Quickly convert an expression into a unit interactively.* Examples
** Simple conversion
If you have#+begin_src
L = 23 ft
#+end_srcAnd you ran =units-convert-region-and-insert= while selecting =23 ft= you'll be asked for target unit and with =mm= you get:
#+begin_src
L = 23 ft = 7010.4 mm
#+end_srcThere is completion for the target unit, that is non-exhaustive. So feel free to type whatever unit you want to. But pressing tab will help you see some of them.
** Derived units
Similar to previous, you can use derived units that are product of other units, or expression with numbers with units.
#+begin_src
g = 9.81 m/s^2
g = 9.81 m/s^2 = 32.185039 ft/s^2
#+end_srcand,
#+begin_src
g = 9.81 m/s^2 + 12 N / 4kg
g = 9.81 m/s^2 + 12 N / 4kg = 42.027559 ft/s^2
#+end_srcdo note that the expression needs to be valid, if you try =1m + 2 gram= You'll get error.
Completion only includes defined units and not derived ones like =ft/s^2=, so you need to type it fully.
Running =units-convert-region= will just show the converted results in the minibuffer.
If there is errors, like units aren't matched then it'll end with the error from =units=
** Multiple units
Since units can allow you to convert to multiple units, this package also can.For example using =ft;in= in =1m= here returns this:
#+begin_src
L = 1m
L = 1m = 3 ft + 3.3700787 in
L = 1m = 3 ft + 3.3700787 in = 100 cm
#+end_srcAs you can see in the third line, you can use that value again to convert to something else as =units= supports simple calculations on units.
Also note that it'll remove the unit with 0 coefficient, for example converting =1mile= to =ft;in= will result in this:
#+begin_src
L = 1mile
L = 1mile = 5280 ft
#+end_src** Reduce to standard units
You can reduce a expression to standard units, for example running =units-reduce-region-and-insert= on region after ~=~ in these examples we get:
#+begin_src
L = 1 miles
L = 1 miles = 1609.344 m
g' = 1.9 force
g' = 1.9 force = 18.632635 m / s^2
area = 5 acre
area = 5 acre = 20234.282 m^2
#+end_src* Package Functions to use in your code
** Elisp
You can load and then directly use the functions in your code. Most useful ones are:
#+begin_src emacs-lisp :exports both
(list (units-convert-simple (/ 1.0 2) "m" "ft")
(units-convert "2 m" "ft")
(units-reduce "1 m + 24 in")
(units-ignore 5 "ft"))
#+end_src#+RESULTS:
| 1.6404199 | 6.5616798 | 1.6096 m | 5 |** Slime Integration (example is for sbcl; adapt to whatever clisp you use)
Although not part of emacs package there is a file =clisp/units.lisp= with functions that do similar things in sbcl. You can load/evaluate the functions there in slime process to use those same functions in slime.You can also put the contents in =clisp/units.lisp= to =~/.sbclrc= so it's evaluated in sbcl startup, similarly for any other dialect you use.
The slime integration means you'll have advantages of clisp rational numbers and other things while using the same syntax as that of elisp.
Same example using sbcl. (Note that here you don't have to use 1.0/2 coz 1/2 ≠ 0 in sbcl)
#+begin_src lisp :exports both :cache no
(list (units-convert-simple (/ 1 2) "m" "ft")
(units-convert "2 m" "ft")
(units-reduce "1 m + 24 in")
(units-ignore 5 "ft"))
#+end_src#+RESULTS:
| 1.6404198 | 6.56168 | 1.6096 | 5 |