\input texinfo @c -*-texinfo-*-@c %**start of header@setfilename ../../info/ses@settitle SES: Simple Emacs Spreadsheet@setchapternewpage off@syncodeindex fn cp@syncodeindex vr cp@syncodeindex ky cp@c %**end of header@copyingThis file documents SES: the Simple Emacs Spreadsheet.Copyright @copyright{} 2002, 2003, 2004, 2005, 2006, 2007Free Software Foundation, Inc.@quotationPermission is granted to copy, distribute and/or modify this documentunder the terms of the GNU Free Documentation License, Version 1.2 orany later version published by the Free Software Foundation; with noInvariant Sections, with the Front-Cover texts being ``A GNUManual,'' and with the Back-Cover Texts as in (a) below. A copy of thelicense is included in the section entitled ``GNU Free DocumentationLicense'' in the Emacs manual.(a) The FSF's Back-Cover Text is: ``You have freedom to copy and modifythis GNU Manual, like GNU software. Copies published by the FreeSoftware Foundation raise funds for GNU development.''This document is part of a collection distributed under the GNU FreeDocumentation License. If you want to distribute this documentseparately from the collection, you can do so by adding a copy of thelicense to the document, as described in section 6 of the license.@end quotation@end copying@dircategory Emacs@direntry* SES: (ses). Simple Emacs Spreadsheet@end direntry@finalout@titlepage@title SES@subtitle Simple Emacs Spreadsheet@author Jonathan A. Yavner@author @email{jyavner@@member.fsf.org}@page@vskip 0pt plus 1filll@insertcopying@end titlepage@contents@c ===================================================================@ifnottex@node Top, Sales Pitch, (dir), (dir)@comment node-name, next, previous, up@top SES: Simple Emacs Spreadsheet@displaySES is a major mode for GNU Emacs to edit spreadsheet files, whichcontain a rectangular grid of cells. The cells' values are specifiedby formulas that can refer to the values of other cells.@end display@end ifnottexTo report bugs, send email to @email{jyavner@@member.fsf.org}.@menu* Sales Pitch:: Why use SES?* The Basics:: Basic spreadsheet commands* Advanced Features:: Want to know more?* For Gurus:: Want to know @emph{even more}?* Index:: Concept, Function and Variable Index* Acknowledgements:: Acknowledgements* GNU Free Documentation License:: The license for this documentation.@end menu@c ===================================================================@node Sales Pitch, The Basics, Top, Top@comment node-name, next, previous, up@chapter Sales Pitch@cindex features@itemize @bullet@item Create and edit simple spreadsheets with a minimum of fuss.@item Full undo/redo/autosave.@item Immune to viruses in spreadsheet files.@item Cell formulas are straight Emacs Lisp.@item Printer functions for control of cell appearance.@item Intuitive keystroke commands: C-o = insert row, M-o = insert column, etc.@item ``Spillover'' of lengthy cell values into following blank cells.@item Header line shows column letters or a selected row.@item Completing-read for entering symbols as cell values.@item Cut, copy, and paste can transfer formulas and printer functions.@item Import and export of tab-separated values or tab-separated formulas.@item Plaintext, easily-hacked file format.@end itemize@c ===================================================================@node The Basics, Advanced Features, Sales Pitch, Top@comment node-name, next, previous, up@chapter The Basics@cindex basic commands@findex ses-jump@findex ses-mark-row@findex ses-mark-column@findex ses-mark-whole-buffer@findex set-mark-command@findex keyboard-quitTo create a new spreadsheet, visit a nonexistent file whose name ends with ".ses". For example, @kbd{C-x C-f test.ses RET}.A @dfn{cell identifier} is a symbol with a column letter and a rownumber. Cell B7 is the 2nd column of the 7th row. For very widespreadsheets, there are two column letters: cell AB7 is the 28thcolumn of the 7th row. Super wide spreadsheets get AAA1, etc.@table @kbd@item jMoves point to cell, specified by identifier (@code{ses-jump}).@end tablePoint is always at the left edge of a cell, or at the empty endline.When mark is inactive, the current cell is underlined. When mark isactive, the range is the highlighted rectangle of cells (SES alwaysuses transient mark mode). Drag the mouse from A1 to A3 to create therange A1-A2. Many SES commands operate only on single cells, notranges.@table @kbd@item C-SPC@itemx C-@@Set mark at point (@code{set-mark-command}).@item C-gTurn off the mark (@code{keyboard-quit}).@item M-hHighlight current row (@code{ses-mark-row}).@item S-M-hHighlight current column (@code{ses-mark-column}).@item C-x hHighlight all cells (@code{mark-whole-buffer}).@end table@menu* Formulas::* Resizing::* Printer functions::* Clearing cells::* Copy/cut/paste::* Customizing SES::@end menu@node Formulas, Resizing, The Basics, The Basics@section Cell formulas@cindex formulas@cindex formulas, entering@findex ses-read-cell@findex ses-read-symbol@findex ses-edit-cell@findex ses-recalculate-cell@findex ses-recalculate-allTo enter a number into the current cell, just start typing:@table @kbd@item 0..9Self-insert a digit (@code{ses-read-cell}).@item -Self-insert a negative number (@code{ses-read-cell}).@item .Self-insert a fractional number (@code{ses-read-cell}).@item "Self-insert a quoted string. The ending double-quoteis inserted for you (@code{ses-read-cell}).@item (Self-insert an expression. The right-parenthesis is inserted for you(@code{ses-read-cell}). To access another cell's value, just use itsidentifier in your expression. Whenever the other cell is changed,this cell's formula will be reevaluated. While typing in theexpression, you can use @kbd{M-@key{TAB}} to complete symbol names.@item ' @r{(apostrophe)}Enter a symbol (ses-read-symbol). SES remembers all symbols that havebeen used as formulas, so you can type just the beginning of a symboland use @kbd{@key{SPC}}, @kbd{@key{TAB}}, and @kbd{?} to complete it.@end tableTo enter something else (e.g., a vector), begin with a digit, thenerase the digit and type whatever you want.@table @kbd@item RETEdit the existing formula in the current cell (@code{ses-edit-cell}).@item C-c C-cForce recalculation of the current cell or range (@code{ses-recalculate-cell}).@item C-c C-lRecalculate the entire spreadsheet (@code{ses-recalculate-all}).@end table@node Resizing, Printer functions, Formulas, The Basics@section Resizing the spreadsheet@cindex resizing spreadsheets@findex ses-insert-row@findex ses-insert-column@findex ses-delete-row@findex ses-delete-column@findex ses-set-column-width@findex ses-forward-or-insert@findex ses-append-row-jump-first-columnBasic commands:@table @kbd@item C-o(@code{ses-insert-row})@item M-o(@code{ses-insert-column})@item C-k(@code{ses-delete-row})@item M-k(@code{ses-delete-column})@item w(@code{ses-set-column-width})@item TABMoves point to the next rightward cell, or inserts a new column ifalready at last cell on line, or inserts a new row if at endline(@code{ses-forward-or-insert}).@item C-jLinefeed inserts below the current row and moves to column A(@code{ses-append-row-jump-first-column}).@end tableResizing the spreadsheet (unless you're just changing a column width)relocates all the cell-references in formulas so they still refer tothe same cells. If a formula mentioned B1 and you insert a new firstrow, the formula will now mention B2.If you delete a cell that a formula refers to, the cell-symbol isdeleted from the formula, so @code{(+ A1 B1 C1)} after deleting the thirdcolumn becomes @code{(+ A1 B1)}. In case this is not what you wanted:@table @kbd@item C-_@itemx C-x uUndo previous action (@code{(undo)}).@end table@node Printer functions, Clearing cells, Resizing, The Basics@section Printer functions@cindex printer functions@findex ses-read-cell-printer@findex ses-read-column-printer@findex ses-read-default-printer@findex ses-center@findex ses-center-span@findex ses-dashfill@findex ses-dashfill-span@findex ses-tildefill-spanPrinter functions convert binary cell values into the print forms thatEmacs will display on the screen.A printer can be a format string, like @samp{"$%.2f"}. The resultstring is right-aligned within the print cell. To get left-alignment,use parentheses: @samp{("$%.2f")}. A printer can also be aone-argument function (a symbol or a lambda), whose result is a string(right-aligned) or list of one string (left-aligned). While typing ina lambda, you can use @kbd{M-@key{TAB}} to complete the names of symbols.Each cell has a printer. If @code{nil}, the column-printer for the cell'scolumn is used. If that is also @code{nil}, the default-printer for thespreadsheet is used.@table @kbd@item pEnter a printer for current cell or range (@code{ses-read-cell-printer}).@item M-pEnter a printer for the current column (@code{ses-read-column-printer}).@item C-c C-pEnter the default printer for the spreadsheet(@code{ses-read-default-printer}).@end tableThe @code{ses-read-@r{XXX}-printer} commands have their own minibufferhistory, which is preloaded with the set of all printers used in thisspreadsheet, plus the standard printers.The standard printers are suitable only for cells, not columns ordefault, because they format the value using the column-printer (ordefault-printer if @code{nil}) and then center the result:@table @code@item ses-centerJust centering.@item ses-center-spanCentering with spill-over to following blank cells.@item ses-dashfillCentering using dashes (-) instead of spaces.@item ses-dashfill-spanCentering with dashes and spill-over.@item ses-tildefill-spanCentering with tildes (~) and spill-over.@end table@node Clearing cells, Copy/cut/paste, Printer functions, The Basics@section Clearing cells@cindex clearing commands@findex ses-clear-cell-backward@findex ses-clear-cell-forwardThese commands set both formula and printer to @code{nil}:@table @kbd@item DELClear cell and move left (@code{ses-clear-cell-backward}).@item C-dClear cell and move right (@code{ses-clear-cell-forward}).@end table@node Copy/cut/paste, Customizing SES, Clearing cells, The Basics@section Copy, cut, and paste@cindex copy@cindex cut@cindex paste@findex kill-ring-save@findex mouse-set-region@findex mouse-set-secondary@findex ses-kill-override@findex yank@findex clipboard-yank@findex mouse-yank-at-click@findex mouse-yank-at-secondary@findex ses-yank-popThe copy functions work on rectangular regions of cells. You can paste thecopies into non-SES buffers to export the print text.@table @kbd@item M-w@itemx [copy]@itemx [C-insert]Copy the highlighted cells to kill ring and primary clipboard(@code{kill-ring-save}).@item [drag-mouse-1]Mark a region and copy it to kill ring and primary clipboard(@code{mouse-set-region}).@item [M-drag-mouse-1]Mark a region and copy it to kill ring and secondary clipboard(@code{mouse-set-secondary}).@item C-w@itemx [cut]@itemx [S-delete]The cut functions do not actually delete rows or columns---they copyand then clear (@code{ses-kill-override}).@item C-y@itemx [S-insert]Paste from kill ring (@code{yank}). The paste functions behavedifferently depending on the format of the text being inserted:@itemize @bullet@itemWhen pasting cells that were cut from a SES buffer, the print text isignored and only the attached formula and printer are inserted; cellreferences in the formula are relocated unless you use @kbd{C-u}.@itemThe pasted text overwrites a rectangle of cells whose top left corneris the current cell. If part of the rectangle is beyond the edges ofthe spreadsheet, you must confirm the increase in spreadsheet size.@itemNon-SES text is usually inserted as a replacement formula for thecurrent cell. If the formula would be a symbol, it's treated as astring unless you use @kbd{C-u}. Pasted formulas with syntax errorsare always treated as strings.@end itemize@item [paste]Paste from primary clipboard or kill ring (@code{clipboard-yank}).@item [mouse-2]Set point and paste from primary clipboard (@code{mouse-yank-at-click}).@item [M-mouse-2]Set point and paste from secondary clipboard (@code{mouse-yank-secondary}).@item M-yImmediately after a paste, you can replace the text with a precedingelement from the kill ring (@code{ses-yank-pop}). Unlike the standardEmacs yank-pop, the SES version uses @code{undo} to delete the oldyank. This doesn't make any difference?@end table@node Customizing SES, , Copy/cut/paste, The Basics@section Customizing SES@cindex customizing@vindex enable-local-eval@vindex ses-mode-hook@vindex safe-functions@vindex enable-local-evalBy default, a newly-created spreadsheet has 1 row and 1 column. Thecolumn width is 7 and the default printer is @samp{"%.7g"}. Each of thesecan be customized. Look in group ``ses''.After entering a cell value, point normally moves right to the nextcell. You can customize @code{ses-after-entry-functions} to move left orup or down. For diagonal movement, select two functions from thelist.@code{ses-mode-hook} is a normal mode hook (list of functions toexecute when starting SES mode for a buffer).The variable @code{safe-functions} is a list of possibly-unsafefunctions to be treated as safe when analysing formulas and printers.@xref{Virus protection}. Before customizing @code{safe-functions},think about how much you trust the person who's suggesting thischange. The value @code{t} turns off all anti-virus protection. Alist-of-functions value might enable a ``gee whiz'' spreadsheet, but italso creates trapdoors in your anti-virus armor. In order for virusprotection to work, you must always press @kbd{n} when presented witha virus warning, unless you understand what the questionable code istrying to do. Do not listen to those who tell you to customize@code{enable-local-eval}---this variable is for people who don't wearsafety belts!@c ===================================================================@node Advanced Features, For Gurus, The Basics, Top@chapter Advanced Features@cindex advanced features@findex ses-read-header-row@table @kbd@item C-c M-C-h(@code{ses-set-header-row}). The header line at the top of the SESwindow normally shows the column letter for each column. You can setit to show a copy of some row, such as a row of column titles, so thatrow will always be visible. Default is to set the current row as theheader; use C-u to prompt for header row. Set the header to row 0 toshow column letters again.@item [header-line mouse-3]Pops up a menu to set the current row as the header, or revert tocolumn letters.@end table@menu* The print area::* Ranges in formulas::* Sorting by column::* Standard formula functions::* More on cell printing::* Import and export::* Virus protection::* Spreadsheets with details and summary::@end menu@node The print area, Ranges in formulas, Advanced Features, Advanced Features@section The print area@cindex print area@findex widen@findex ses-renarrow-buffer@findex ses-reprint-allA SES file consists of a print area and a data area. Normally thebuffer is narrowed to show only the print area. The print area isread-only except for special SES commands; it contains cell valuesformatted by printer functions. The data area records the formula andprinter functions, etc.@table @kbd@item C-x n wShow print and data areas (@code{widen}).@item C-c C-nShow only print area (@code{ses-renarrow-buffer}).@item S-C-l@itemx M-C-lRecreate print area by reevaluating printer functions for all cells(@code{ses-reprint-all}).@end table@node Ranges in formulas, Sorting by column, The print area, Advanced Features@section Ranges in formulas@cindex ranges@findex ses-insert-range-click@findex ses-insert-range@findex ses-insert-ses-range-click@findex ses-insert-ses-range@vindex from@vindex toA formula like@lisp(+ A1 A2 A3)@end lispis the sum of three specific cells. If you insert a new second row,the formula becomes@lisp(+ A1 A3 A4)@end lispand the new row is not included in the sum.The macro @code{(ses-range @var{from} @var{to})} evaluates to a list ofthe values in a rectangle of cells. If your formula is@lisp(apply '+ (ses-range A1 A3))@end lispand you insert a new second row, it becomes@lisp(apply '+ (ses-range A1 A4))@end lispand the new row is included in the sum.While entering or editing a formula in the minibuffer, you can selecta range in the spreadsheet (using mouse or keyboard), then paste arepresentation of that range into your formula. Suppose you selectA1-C1:@table @kbd@item [S-mouse-3]Inserts "A1 B1 C1" @code{(ses-insert-range-click})@item C-c C-rKeyboard version (@code{ses-insert-range}).@item [C-S-mouse-3]Inserts "(ses-range A1 C1)" (@code{ses-insert-ses-range-click}).@item C-c C-sKeyboard version (@code{ses-insert-ses-range}).@end tableIf you delete the @var{from} or @var{to} cell for a range, the neareststill-existing cell is used instead. If you delete the entire range,the formula relocator will delete the ses-range from the formula.If you insert a new row just beyond the end of a one-column range, ora new column just beyond a one-row range, the new cell is included inthe range. New cells inserted just before a range are not included.@node Sorting by column, Standard formula functions, Ranges in formulas, Advanced Features@section Sorting by column@cindex sorting@findex ses-sort-column@findex ses-sort-column-click@table @kbd@item C-c M-C-sSort the cells of a range using one of the columns(@code{ses-sort-column}). The rows (or partial rows if the rangedoesn't include all columns) are rearranged so the chosen column willbe in order.@item [header-line mouse-2]The easiest way to sort is to click mouse-2 on the chosen column's header row(@code{ses-sort-column-click}).@end tableThe sort comparison uses @code{string<}, which works well forright-justified numbers and left-justified strings.With prefix arg, sort is in descending order.Rows are moved one at a time, with relocation of formulas. This workswell if formulas refer to other cells in their row, not so well forformulas that refer to other rows in the range or to cells outside therange.@node Standard formula functions, More on cell printing, Sorting by column, Advanced Features@section Standard formula functions@cindex standard formula functions@cindex *skip*@cindex *error*@findex ses-delete-blanks@findex ses-average@findex ses+Oftentimes you want a calculation to exclude the blank cells. Hereare some useful functions to call from your formulas:@table @code@item (ses-delete-blanks &rest @var{args})Returns a list from which all blank cells (value is either @code{nil} or'*skip*) have been deleted.@item (ses+ &rest @var{args})Sum of non-blank arguments.@item (ses-average @var{list})Average of non-blank elements in @var{list}. Here the list is passedas a single argument, since you'll probably use it with @code{ses-range}.@end table@node More on cell printing, Import and export, Standard formula functions, Advanced Features@section More on cell printing@cindex cell printing, more@findex ses-truncate-cell@findex ses-recalculate-cellSpecial cell values:@itemize@item nil prints the same as "", but allows previous cell to spill over.@item '*skip* replaces nil when the previous cell actually does spill over;nothing is printed for it.@item '*error* indicates that the formula signaled an error instead ofproducing a value: the print cell is filled with hash marks (#).@end itemizeIf the result from the printer function is too wide for the cell andthe following cell is @code{nil}, the result will spill over into thefollowing cell. Very wide results can spill over several cells. Ifthe result is too wide for the available space (up to the end of therow or the next non-@code{nil} cell), the result is truncated if the cell'svalue is a string, or replaced with hash marks otherwise.SES could get confused by printer results that contain newlines ortabs, so these are replaced with question marks.@table @kbd@item tConfine a cell to its own column (@code{ses-truncate-cell}). Thisallows you to move point to a rightward cell that would otherwise becovered by a spill-over. If you don't change the rightward cell, theconfined cell will spill over again the next time it is reprinted.@item cWhen applied to a single cell, this command displays in the echo areaany formula error or printer error that occurred duringrecalculation/reprinting (@code{ses-recalculate-cell}). You can usethis to undo the effect of @kbd{t}.@end tableWhen a printer function signals an error, the fallback printer@samp{"%s"} is substituted. This is useful when your column printeris numeric-only and you use a string as a cell value. Note that thestandard default printer is ``%.7g'' which is numeric-only, so cellsthat are empty of contain strings will use the fallback printer.@kbd{c} on such cells will display ``Format specifier doesn't matchargument type''.@node Import and export, Virus protection, More on cell printing, Advanced Features@section Import and export@cindex import and export@cindex export, and import@findex ses-export-tsv@findex ses-export-tsf@table @kbd@item x tExport a range of cells as tab-separated values (@code{ses-export-tsv}).@item x TExport a range of cells as tab-separated formulas (@code{ses-export-tsf}).@end tableThe exported text goes to the kill ring --- you can paste it intoanother buffer. Columns are separated by tabs, rows by newlines.To import text, use any of the yank commands where the text to pastecontains tabs and/or newlines. Imported formulas are not relocated.@node Virus protection, Spreadsheets with details and summary, Import and export, Advanced Features@section Virus protection@cindex virus protectionWhenever a formula or printer is read from a file or is pasted intothe spreadsheet, it receives a ``needs safety check'' marking. Later,when the formula or printer is evaluated for the first time, it ischecked for safety using the @code{unsafep} predicate; if found to be``possibly unsafe'', the questionable formula or printer is displayedand you must press Y to approve it or N to use a substitute. Thesubstitute always signals an error.Formulas or printers that you type in are checked immediately forsafety. If found to be possibly unsafe and you press N to disapprove,the action is canceled and the old formula or printer will remain.Besides viruses (which try to copy themselves to other files),@code{unsafep} can also detect all other kinds of Trojan horses, such asspreadsheets that delete files, send email, flood Web sites, alteryour Emacs settings, etc.Generally, spreadsheet formulas and printers are simple things thatdon't need to do any fancy computing, so all potentially-dangerousparts of the Emacs Lisp environment can be excluded without crampingyour style as a formula-writer. See the documentation in @file{unsafep.el}for more info on how Lisp forms are classified as safe or unsafe.@node Spreadsheets with details and summary, , Virus protection, Advanced Features@section Spreadsheets with details and summary@cindex details and summary@cindex summary, and detailsA common organization for spreadsheets is to have a bunch of ``detail''rows, each perhaps describing a transaction, and then a set of``summary'' rows that each show reduced data for some subset of thedetails. SES supports this organization via the @code{ses-select}function.@table @code@item (ses-select @var{fromrange} @var{test} @var{torange})Returns a subset of @var{torange}. For each member in @var{fromrange}that is equal to @var{test}, the corresponding member of @var{torange}is included in the result.@end tableExample of use:@lisp(ses-average (ses-select (ses-range A1 A5) 'Smith (ses-range B1 B5)))@end lispThis computes the average of the B column values for those rows whoseA column value is the symbol 'Smith.Arguably one could specify only @var{fromrange} plus@var{to-row-offset} and @var{to-column-offset}. The @var{torange} isstated explicitly to ensure that the formula will be recalculated ifany cell in either range is changed.File @file{etc/ses-example.el} in the Emacs distribution is an example of adetails-and-summary spreadsheet.@c ===================================================================@node For Gurus, Index, Advanced Features, Top@chapter For Gurus@cindex advanced features@menu* Deferred updates::* Nonrelocatable references::* The data area::* Buffer-local variables in spreadsheets::* Uses of defadvice in SES::@end menu@node Deferred updates, Nonrelocatable references, For Gurus, For Gurus@section Deferred updates@cindex deferred updates@cindex updates, deferred@vindex run-with-idle-timerTo save time by avoiding redundant computations, cells that needrecalculation due to changes in other cells are added to a set. Atthe end of the command, each cell in the set is recalculated once.This can create a new set of cells that need recalculation. Theprocess is repeated until either the set is empty or it stops changing(due to circular references among the cells). In extreme cases, youmight see progress messages of the form ``Recalculating... (@var{nnn}cells left)''. If you interrupt the calculation using @kbd{C-g}, thespreadsheet will be left in an inconsistent state, so use @kbd{C-_} or@kbd{C-c C-l} to fix it.To save even more time by avoiding redundant writes, cells that havechanges are added to a set instead of being written immediately to thedata area. Each cell in the set is written once, at the end of thecommand. If you change vast quantities of cells, you might see aprogress message of the form ``Writing... (@var{nnn} cells left)''.These deferred cell-writes cannot be interrupted by @kbd{C-g}, soyou'll just have to wait.SES uses @code{run-with-idle-timer} to move the cell underline whenEmacs will be scrolling the buffer after the end of a command, andalso to narrow and underline after @kbd{C-x C-v}. This is visible asa momentary glitch after C-x C-v and certain scrolling commands. Youcan type ahead without worrying about the glitch.@node Nonrelocatable references, The data area, Deferred updates, For Gurus@section Nonrelocatable references@cindex nonrelocatable references@cindex references, nonrelocatable@kbd{C-y} relocates all cell-references in a pasted formula, while@kbd{C-u C-y} relocates none of the cell-references. What about mixedcases?You can use@lisp(symbol-value 'B3)@end lispto make an @dfn{absolute reference}. The formula relocator skips overquoted things, so this will not be relocated when pasted or whenrows/columns are inserted/deleted. However, B3 will not be recordedas a dependency of this cell, so this cell will not be updatedautomatically when B3 is changed.The variables @code{row} and @code{col} are dynamically bound while acell formula is being evaluated. You can use@lisp(ses-cell-value row 0)@end lispto get the value from the leftmost column in the current row. Thiskind of dependency is also not recorded.@node The data area, Buffer-local variables in spreadsheets, Nonrelocatable references, For Gurus@section The data area@cindex data area@findex ses-reconstruct-allBegins with an 014 character, followed by sets of cell-definitionmacros for each row, followed by column-widths, column-printers,default-printer, and header-row. Then there's the global parameters(file-format ID, numrows, numcols) and the local variables (specifyingSES mode for the buffer, etc.)When a SES file is loaded, first the numrows and numcols values areloaded, then the entire data area is @code{eval}ed, and finally the localvariables are processed.You can edit the data area, but don't insert or delete any newlinesexcept in the local-variables part, since SES locates things bycounting newlines. Use @kbd{C-x C-e} at the end of a line to installyour edits into the spreadsheet data structures (this does not updatethe print area, use e.g. @kbd{C-c C-l} for that).The data area is maintained as an image of spreadsheet datastructures that area stored in buffer-local variables. If the dataarea gets messed up, you can try reconstructing the data area from thedata structures:@table @kbd@item C-c M-C-l(@code{ses-reconstruct-all}).@end table@node Buffer-local variables in spreadsheets, Uses of defadvice in SES, The data area, For Gurus@section Buffer-local variables in spreadsheets@cindex buffer-local variables@cindex variables, buffer-localYou can add additional local variables to the list at the bottom ofthe data area, such as hidden constants you want to refer to in yourformulas.You can override the variable @code{ses--symbolic-formulas} to be a list ofsymbols (as parenthesized strings) to show as completions for the 'command. This initial completions list is used instead of the actualset of symbols-as-formulas in the spreadsheet.For an example of this, see file @file{etc/ses-example.ses}.If (for some reason) you want your formulas or printers to save datainto variables, you must declare these variables as buffer-locals inorder to avoid a virus warning.You can define functions by making them values for the fake localvariable @code{eval}. Such functions can then be used in yourformulas and printers, but usually each @code{eval} is presented tothe user during file loading as a potential virus --- this can getannoying.You can define functions in your @file{.emacs} file. Other people canstill read the print area of your spreadsheet, but they won't be ableto recalculate or reprint anything that depends on your functions. Toavoid virus warnings, each function used in a formula needs@lisp(put 'your-function-name 'safe-function t)@end lisp@node Uses of defadvice in SES, , Buffer-local variables in spreadsheets, For Gurus@section Uses of defadvice in SES@cindex defadvice@cindex undo-more@cindex copy-region-as-kill@cindex yank@table @code@item undo-moreDefines a new undo element format (@var{fun} . @var{args}), whichmeans ``undo by applying @var{fun} to @var{args}''. For spreadsheetbuffers, it allows undos in the data area even though that's outsidethe narrowing.@item copy-region-as-killWhen copying from the print area of a spreadsheet, treat the region asa rectangle and attach each cell's formula and printer as 'sesproperties.@item yankWhen yanking into the print area of a spreadsheet, first try to yankas cells (if the yank text has 'ses properties), then as tab-separatedformulas, then (if all else fails) as a single formula for the currentcell.@end table@c ===================================================================@node Index, Acknowledgements, For Gurus, Top@unnumbered Index@printindex cp@c ===================================================================@node Acknowledgements, GNU Free Documentation License, Index, Top@chapter AcknowledgementsCoding by:@quotationJonathan Yavner @email{jyavner@@member.fsf.org}@*Stefan Monnier @email{monnier@@gnu.org}@end quotation@noindentTexinfo manual by:@quotationJonathan Yavner @email{jyavner@@member.fsf.org}@*Brad Collins <brad@@chenla.org>@end quotation@noindentIdeas from:@quotationChristoph Conrad @email{christoph.conrad@@gmx.de}@*CyberBob @email{cyberbob@@redneck.gacracker.org}@*Syver Enstad @email{syver-en@@online.no}@*Ami Fischman @email{fischman@@zion.bpnetworks.com}@*Thomas Gehrlein @email{Thomas.Gehrlein@@t-online.de}@*Chris F.A. Johnson @email{c.f.a.johnson@@rogers.com}@*Yusong Li @email{lyusong@@hotmail.com}@*Juri Linkov @email{juri@@jurta.org}@*Harald Maier @email{maierh@@myself.com}@*Alan Nash @email{anash@@san.rr.com}@*Fran�ois Pinard @email{pinard@@iro.umontreal.ca}@*Pedro Pinto @email{ppinto@@cs.cmu.edu}@*Stefan Reich�r @email{xsteve@@riic.at}@*Oliver Scholz @email{epameinondas@@gmx.de}@*Richard M. Stallman @email{rms@@gnu.org}@*Luc Teirlinck @email{teirllm@@dms.auburn.edu}@*J. Otto Tennant @email{jotto@@pobox.com}@*Jean-Philippe Theberge @email{jphil@@acs.pagesjaunes.fr}@end quotation@c ===================================================================@node GNU Free Documentation License, , Acknowledgements, Top@appendix GNU Free Documentation License@include doclicense.texi@bye@ignore arch-tag: 10a4ee1c-7ef4-4c06-8b7a-f975e39f0dec@end ignore