]> git.donarmstrong.com Git - lilypond.git/blobdiff - Documentation/CodingStyle.pod
partial: 1.0.1.jcn
[lilypond.git] / Documentation / CodingStyle.pod
index 995188dec2fe1b6d4ebbb3275a14e1d75a52e78a..0f57d3e1b31bd48a60b019cf6bd519bad4a50105 100644 (file)
 =head1 NAME
 
-CodingStyle - standards while programming for LilyPond
+CodingStyle - standards while programming for GNU LilyPond
 
 =head1 DESCRIPTION
 
-Please use these standards while doing programming for LilyPond
+We use these standards while doing programming for GNU LilyPond.  If
+you do some hacking, we appreciate it if you would follow this rules,
+but if you don't, we still like you.
 
 Functions and methods do not return errorcodes, but use assert for
 checking status. 
 
-=head2 INDENTATION
+=head2 Quote:
+
+A program should be light and agile, its subroutines
+connected like a string of pearls.  The spirit and intent of
+the program should be retained throughout.  There should be
+neither too little nor too much, neither needless loops nor
+useless variables, neither lack of structure nor overwhelming
+rigidity.
+
+A program should follow the 'Law of Least
+Astonishment'.  What is this law?  It is simply that the
+program should always respond to the user in the way that
+astonishes him least.
+
+A program, no matter how complex, should act as a
+single unit.  The program should be directed by the logic
+within rather than by outward appearances.
+
+If the program fails in these requirements, it will be
+in a state of disorder and confusion.  The only way to correct
+this is to rewrite the program.
+
+-- Geoffrey James, "The Tao of Programming"
+
+
+=head2 LANGUAGES
+
+C++, /bin/sh and python are preferred.  Perl is not.
+
+=head2 FILES
+
+Definitions of classes that are only accessed via pointers
+(*) or references (&) shall not be included as include files.
+
+filenames
+
+       ".hh"   Include files
+       ".cc"   Implementation files
+       ".icc"  Inline definition files
+       ".tcc"  non inline Template defs
 
 in emacs:
 
+       (setq auto-mode-alist
+             (append '(("\\.make$" . makefile-mode)
+                       ("\\.cc$" . c++-mode)
+                       ("\\.icc$" . c++-mode)
+                       ("\\.tcc$" . c++-mode)
+                       ("\\.hh$" . c++-mode)
+                       ("\\.pod$" . text-mode)         
+                       )
+                     auto-mode-alist))
+
+
+The class Class_name_abbreviation is coded in F<class-name-abbr.*>
 
-       (add-hook 'c-mode-hook
-                 '(lambda ()(setq c-basic-offset 4)))
+
+=head2 INDENTATION
+
+in emacs:
 
 
        (add-hook 'c++-mode-hook
-                 '(lambda() (c-set-style "Stroustrup")
+                 '(lambda() (c-set-style "gnu")
                     )
                  )
 
+If you like using font-lock, you can also add this to your F<.emacs>:
+
+       (setq font-lock-maximum-decoration t)
+       (setq c++-font-lock-keywords-3 
+             (append
+              c++-font-lock-keywords-3
+              '(("\\b\\([a-zA-Z_]+_\\)\\b" 1 font-lock-variable-name-face)
+              ("\\b\\([A-Z]+[a-z_]+\\)\\b" 1 font-lock-type-face))
+              ))
 
 =head2 CLASSES and TYPES:
 
        This_is_a_class
        AClass_name     (for Abbreviation_class_name)
 
-=head2 DATA MEMBERS
+=head2 MEMBERS
 
        Class::member()
-       Class::member_type_()
+       Type Class::member_type_
+       Type Class::member_type()
+
+the C<type> is a Hungarian notation postfix for C<Type>. See below
+
+=head2 MACROS
+
+Macros should be written completely in uppercase
 
-the C<type> is a Hungarian notation postfix
+The code should not be compilable if proper macro declarations are not
+included. 
+
+Don't laugh. It took us a whole evening/night to figure out one of
+these bugs.
+
+=head2 BROKEN CODE
+
+Broken code (hardwired dependencies, hardwired constants, slow
+algorithms and obvious limitations) should be marked as such:
+either with a verbose TODO, or with a short "ugh" comment.
 
 =head2 COMMENTS
 
 The source is commented in the DOC++ style.  Check out doc++ at
-F<http://www.ZIB-Berlin.DE/VisPar/doc++/doc++.html>
+http://www.zib.de/Visual/software/doc++/index.html
+
+       /*
+               C style comments for multiline comments.
+               They come before the thing to document.
+               [...]
+       */
+
 
-       /// short description
+       /**
+               short description.
+               Long class documentation.
+               (Hungarian postfix)
+
+               TODO Fix boring_member()
+       */
        class Class {
-               ///
-               Data data_member_;
                /**
-                       ..
+                 short description.
+                 long description
                */
 
-               /****************/
+               Data data_member_;
+
 
-               /// short memo
-               member();
                /**
-                       long doco of member()
+                       short memo. long doco of member()
+                       @param description of arguments
+                       @return Rettype
                */
-       };
-       /**
-               Class documentation.
-       */
-
-Unfortunately most of the code isn't really documented that good.
+               Rettype member(Argtype);
 
-=head2 CLASSNAMES (2)
-
-A lot of classes in LilyPond start with 'P', this is to distinguish
-certain parts of LilyPond: the P stands for Printer, and the P-classes
-are supposed to be more lowlevel than the others. Example:
+               /// memo only
+               boring_member() {
+                       data_member_ = 121; // ugh
+               }
+       };
 
-Staff uses PStaff, PScore and PCol to do the typesetting of
-symbols. Staff is  the "brains" for PStaff
 
-NB: in PCursor (which is part of the library) P stands for PointerCursor
+       
+Unfortunately most of the code isn't really documented that good.
 
 
-=head2 MEMBERS(2)
+=head2 MEMBERS (2)
 
 Standard methods:
 
@@ -85,13 +173,312 @@ Standard methods:
        /// print *this (and substructures) to debugging log
        void print() const
 
-       /// add some data to *this; 
-       add( .. )
        /**
+       protected member. Usually invoked by non-virtual XXXX()
+       */
+       virtual do_XXXX()
+
+       /**add some data to *this.
        Presence of these methods usually imply that it is not feasible to this
        via  a constructor
        */
+       add (..)
 
        /// replace some data of *this
-       set( .. )
+       set (..)
+
+=head2 Constructor
+
+Every class should have a default constructor.  
+
+Don't use non-default constructors if this can be avoided:
+
+       Foo f(1)
+
+is less readable than
+
+       Foo f;
+       f.x = 1
+
+or 
+       Foo f(Foo_convert::int_to_foo (1))
+
+
+
+=head1 HUNGARIAN NOTATION NAMING CONVENTION
+
+Proposed is a naming convention derived from the so-called I<Hungarian
+Notation>.
+
+=head2 Hungarian
+
+The Hungarian Notation was conceived by or at least got its name from,
+the hungarian programmer Charles Simonyi.  It is a naming convention 
+with the aim to make code more readable (for fellow programmers), and 
+more accessible for programmers that are new to a project.
+
+The essence of the Hungarian Notation is that every identifier has a
+part which identifies its type (for functions this is the result
+type).  This is particularly useful in object oriented programming,
+where a particular object implies a specific interface (a set of
+member functions, perhaps some redefined operators), and for
+accounting heap allocated memory pointers and links.
+
+=head2 Advantages
+
+Another fun quote from Microsoft Secrets:
+
+
+       The Hungarian naming convention gives developers the ability
+       to read other people's code relatively easily, with a minmum
+       number of comments in the source code.  Jon De Vann estimated
+       that only about 1 percent of all lines in the Excel product
+       code consist of comments, but the code is still very
+       understandable due to the use of Hungarian: "if you look at
+       our source code, you also notice very few comments.  Hungarian
+       gives us the ability to go in and read code..."
+
+Wow! If you use Hungarian you don't have to document your software!
+Just think of the hours I have wasted documenting while this "silver bullet"
+existed. I feel so stupid and ashamed!  [Didn't MMM-Brooks say `There is
+no silver bullet?' --HWN]
+
+
+=head2 Disadvantages
+
+=over 5
+
+=item *
+
+more keystrokes (disk space!)
+
+=item *
+
+it looks silly C<get_slu_p()>
+
+=item *
+
+it looks like code from micro suckers
+
+=item *
+
+(which) might scare away some (otherwise good?)
+progammers, or make you a paria in the free
+software community
+
+=item *
+
+it has ambiguities
+
+=item *
+
+not very useful if not used consistently
+
+=item *
+
+usefullness in I<very large> (but how many classes is very large?)
+remains an issue.
+
+=back
+
+
+
+=head2 Proposal
+
+=over 5
+
+=item *
+
+learn about cut and paste / use emacs or vi
+or lean to type using ten fingers
+
+=item *
+
+Use emacs dabbrev-expand, with dabbrev-case-fold-search set to nil.
+
+=item *
+
+use no, or pick less silly, abbrvs.
+
+=item *
+
+use non-ambiguous postfixes C<identifier_name_type_modifier[_modifier]>
+
+=item *
+
+There is no need for Hungarian if the scope of the variable is small,
+ie. local variables, arguments in function definitions (not
+declarations).
+
+=back
+
+Macros, C<enum>s and C<const>s are all uppercase,
+with the parts of the names separated by underscores.
+
+=head2 Types
+
+=over 5
+
+=item C<byte>
+
+
+unsigned char. (The postfix _by is ambiguous)
+
+=item C<b>
+
+
+bool
+
+=item C<bi>
+
+bit
+
+=item C<ch>
+
+char
+
+=item C<f>
+
+float
+
+=item C<i>
+
+signed integer
+
+=item C<str>
+
+string class
+
+=item C<sz>
+
+Zero terminated c string
+
+=item C<u>
+
+unsigned integer
+
+=back
+
+=head2 User defined types
+
+
+       /** Slur blah. blah.
+       (slur)
+       */
+       class Slur {};
+       Slur* slur_p = new Slur;
+
+=head2 Modifiers
+
+The following types modify the meaning of the prefix. 
+These are preceded by the prefixes:
+
+=over 5
+
+=item C<a>
+
+array
+
+=item C<array>
+
+user built array.
+
+=item C<c>
+
+const. Note that the proper order is C<Type const> i.s.o. C<const Type>
+
+=item C<C>
+
+A const pointer. This would be equivalent to C<_c_l>, but since any
+"const" pointer has to be a link (you can't delete a const pointer),
+it is superfluous.
+
+=item C<l>
+
+temporary pointer to object (link)
+
+=item C<p>
+
+pointer to newed object
+
+=item C<r>
+
+reference
+
+=back
+
+=over 5
+
+=head2 Adjective
+
+Adjectives such as global and static should be spelled out in full.
+They come before the noun that they refer to, just as in normal english.
+
+foo_global_i: a global variable of type int commonly called "foo".
+
+static class members do not need the static_ prefix in the name (the
+Class::var notation usually makes it clear that it is static)
+
+=item C<loop_i>
+
+Variable loop: an integer
+
+=item C<u>
+
+Temporary variable: an unsigned integer
+
+=item C<test_ch>
+
+Variable test: a character
+
+=item C<first_name_str>
+
+Variable first_name: a String class object
+
+=item C<last_name_ch_a>
+
+Variable last_name: a C<char> array
+
+=item C<foo_i_p>
+
+Variable foo: an C<Int*> that you must delete
+
+=item C<bar_i_l>
+
+Variable bar: an C<Int*> that you must not delete
+
+=back
+
+Generally default arguments are taboo, except for nil pointers.
+
+The naming convention can be quite conveniently memorised, by
+expressing the type in english, and abbreviating it
+
+       static Array<int*> foo
+
+C<foo> can be described as "the static int-pointer user-array", so you get
+
+       foo_static_l_arr
+       
+
+
+
+=head1 MISCELLANEOUS
+
+For some tasks, some scripts are supplied, notably creating patches, a
+mirror of the website, generating the header to put over cc and hh
+files, doing a release.
+
+Use them.
+
+The following generic identifications are used:
+
+       up == 1
+       left == -1
+       right == 1
+       down == -1
+
+Intervals are pictured lying on a horizontal numberline (Interval[-1]
+is the minimum). The 2D plane has +x on the right, +y pointing up.
+