We have moved to https://dokuwiki.librecad.org/

Lots of content was already moved to the new wiki, but there is still work to do. If you want to contribute, please register a new account at https://dokuwiki.librecad.org/

This wiki will be kept for a while to keep search engine results valid. Moved sites may be deleted here in future.

Difference between revisions of "LibreCAD 3 - LibreCAD 3 - code style"

From LibreCAD wiki
Jump to: navigation, search
m (fix typo)
(8 intermediate revisions by 3 users not shown)
Line 1: Line 1:
 
== Code style guide ==
 
== Code style guide ==
 +
'''Line length'''<br/>
 +
Maximum line length is 120 columns
  
'''Accessor naming:'''
+
'''Spacing'''<br/>
 +
* Between if, for, while and (
 +
* Between comparison operators
 +
* After ,
  
<pre>use foo->layer()
+
 
 +
'''Indentation'''<br/>
 +
* Namespace blocks
 +
* public and private +1 and methods +2
 +
 
 +
'''Headers'''<br/>
 +
* use #pragma once instead of #ifndef
 +
* Include what you use
 +
* Do not use virtual and override in the same declaration
 +
 
 +
'''Accessor naming'''<br/>
 +
Use:
 +
<pre>foo->layer()
 
</pre>
 
</pre>
 
instead of
 
instead of
Line 11: Line 28:
  
  
'''Immutables:'''
+
'''Immutables'''<br/>
Are immutables must be created 'valid', throw an exception if a immutable is attempted to be created that is invalid.
+
All immutables must be created 'valid', throw an exception on an attempt to create an invalid immutable:
 
+
example:
+
 
<pre>
 
<pre>
 
Circle::Circle(Coordinate const& center, double radius) : _center(center), _radius(radius) {
 
Circle::Circle(Coordinate const& center, double radius) : _center(center), _radius(radius) {
Line 21: Line 36:
 
     }
 
     }
 
}
 
}
 
All variables in a immutable class must be declared as const
 
 
</pre>
 
</pre>
 +
All variables in an immutable class must be declared as const.
  
'''Exceptions:'''
 
  
Only throw exceptions in rare situations that are effectively unreasonable.
+
'''Exceptions'''
 
+
''For example:''
+
  
 +
Only throw where code is effectively unreasonable:
 
<pre>
 
<pre>
document->entityByID(...); // return null if a entry does not exists
+
document->entityByID(...); // return null if an entry does not exists
 
</pre>
 
</pre>
  
  
'''hide shared_ptr behind a typedef:'''
+
'''Variable naming'''
 +
 
 +
Use typedefs to shorten otherwise difficult to read names:
  
 
<pre>
 
<pre>
 +
    DECLARE_SHORT_SHARED_PTR(Circle)
 +
 +
    // OR
 +
 
     typedef std::shared_ptr<Circle> Circle_SPtr;
 
     typedef std::shared_ptr<Circle> Circle_SPtr;
 
     typedef std::shared_ptr<const Circle> Circle_CSPtr;
 
     typedef std::shared_ptr<const Circle> Circle_CSPtr;
 
</pre>
 
</pre>
 
+
This can also make further variable-use more legible:
This so we can 'shorten' our shred pointers, example:
+
  
 
<pre>
 
<pre>
   std::list<std::shared_ptr<const Circle>> myListLong; // Less readble
+
   std::list<std::shared_ptr<const Circle>> myListVeryLong; // very long
   std::list<Circle_CSPtr> myListReadable; // better readable
+
   std::list<Circle_CSPtr> myList; // better readable
 
</pre>
 
</pre>
  
  
'''Shared pointer passing:'''
+
'''Shared pointers'''
  
never pass shared_ptr by reference:
+
Shared pointers should be passed by const reference, they can be passed as value if they are going to be stored in the target (with std::move)
  
Good:
+
<br/>
<pre>
+
'''Namespace std'''
Line::Line(geo::Coordinate const& start, geo::Coordinate const& end, Layer_SPtr const  layer) : CADEntity(layer), Vector(start, end) {..}
+
</pre>
+
  
Bad:
+
Don't bring in the 'std' namespace into global; always use '''std::'''vector, '''std::'''map, '''std::'''string etc...
<pre>
+
Line::Line(geo::Coordinate const& start, geo::Coordinate const& end, Layer_SPtr const &layer) : CADEntity(layer), Vector(start, end) {..}
+
</pre>
+
  
'''using namespace std;'''
 
  
Don't bring in the std namespace into global. So  always use std::vector, std::map, std::string etc...
+
'''Variable declarations'''
  
'''Variable declarations on separate lines'''
+
Declare variables on separate lines to make them easier to read and to annotate.
  
For readability we prefer to have variables declared on separate lines.
+
Good:
This will make commenting on variables when needed easer and in general add to readability.
+
 
+
good style:
+
 
<pre>
 
<pre>
const Coordinate _extensionPoint1;
+
const Coordinate _extensionPoint1; // check dependencies...
const Coordinate _extensionPoint2;
+
const Coordinate _tangentPoint2;
 
</pre>
 
</pre>
  
bad style:
+
Bad:
 
<pre>
 
<pre>
const Coordinate _extension_point1, _extension_point2;
+
const Coordinate _extension_point1, _tangentPoint2; // which one did I want?
 
</pre>
 
</pre>
 
+
<br/>
 
'''Const variables '''
 
'''Const variables '''
Const modifier must be added after the variable type:
+
 
 +
You must add const modifiers ''after'' the variable type.
 +
 
 
Good:
 
Good:
 
<pre>
 
<pre>
Line::Line(geo::Coordinate const& start, geo::Coordinate const& end, Layer_SPtr const layer) : CADEntity(layer), Vector(start, end) {..}
+
Line::Line(geo::Coordinate const& start, geo::Coordinate const & end, Layer_SPtr const layer) : CADEntity(layer), Vector(start, end) {..}
 
</pre>
 
</pre>
  
 
Bad:
 
Bad:
 
<pre>
 
<pre>
Line::Line(geo::Coordinate const & start, geo::Coordinate const & end, Layer_SPtr const &layer) : CADEntity(layer), Vector(start, end) {..}
+
Line::Line(geo::Coordinate const & start, const geo::Coordinate& end, Layer_SPtr const layer) : CADEntity(layer), Vector(start, end) {..}
 
</pre>
 
</pre>
 +
<br/>
 +
'''Camel case'''
  
'''Use Camel case '''
+
Use it as much as possible, though some exceptions are allowed:
Try to use camel case as much as possible
+
* Variable names in a class may start with a underscore;
 
+
* An '_' (underscore) may be added if the variable name gets unreadable, e.g. in 'Dimension_CSptr';
Some exceptions:
+
* Underscores can help make function names autological, e.g. on_dimRadial_changed:
* Variable names in a class can start with a underscore
+
* add a _ (underscore) if the variable name get's unreadable, for example this is ok Dimension_CSptr  
+
* Function names to add clarification for example on_dimRadial_changed. where 'on' and 'changed' are not part of the variable name dimRadial but they are there to notify something.
+
  
 
Good:
 
Good:
Line 116: Line 125:
 
   void on_dim_radial_change() {...};
 
   void on_dim_radial_change() {...};
 
</pre>
 
</pre>
 +
<br/>
 +
'''Class names always start with an Upper-case letter.'''
  
'''Class name's always start with a upper case letter'''
+
'''Variable names always start with a lower-case letter.'''
 
+
<br/>
'''Variable name's always starts with a lower case letter'''
+
<br/>
 +
[[Category:Developers]]

Revision as of 20:50, 12 July 2018

Code style guide

Line length
Maximum line length is 120 columns

Spacing

  • Between if, for, while and (
  • Between comparison operators
  • After ,


Indentation

  • Namespace blocks
  • public and private +1 and methods +2

Headers

  • use #pragma once instead of #ifndef
  • Include what you use
  • Do not use virtual and override in the same declaration

Accessor naming
Use:

foo->layer()

instead of

 foo->getLayer();


Immutables
All immutables must be created 'valid', throw an exception on an attempt to create an invalid immutable:

Circle::Circle(Coordinate const& center, double radius) : _center(center), _radius(radius) {
    if (_radius < 0.0) {
        throw "Invalid radius";
    }
}

All variables in an immutable class must be declared as const.


Exceptions

Only throw where code is effectively unreasonable:

document->entityByID(...); // return null if an entry does not exists


Variable naming

Use typedefs to shorten otherwise difficult to read names:

    DECLARE_SHORT_SHARED_PTR(Circle) 

    // OR

    typedef std::shared_ptr<Circle> Circle_SPtr;
    typedef std::shared_ptr<const Circle> Circle_CSPtr;

This can also make further variable-use more legible:

  std::list<std::shared_ptr<const Circle>> myListVeryLong; // very long
  std::list<Circle_CSPtr> myList; // better readable


Shared pointers

Shared pointers should be passed by const reference, they can be passed as value if they are going to be stored in the target (with std::move)


Namespace std

Don't bring in the 'std' namespace into global; always use std::vector, std::map, std::string etc...


Variable declarations

Declare variables on separate lines to make them easier to read and to annotate.

Good:

const Coordinate _extensionPoint1; // check dependencies...
const Coordinate _tangentPoint2;

Bad:

const Coordinate _extension_point1, _tangentPoint2; // which one did I want?


Const variables

You must add const modifiers after the variable type.

Good:

Line::Line(geo::Coordinate const& start, geo::Coordinate  const  & end, Layer_SPtr const layer) : CADEntity(layer), Vector(start, end) {..}

Bad:

Line::Line(geo::Coordinate const & start, const geo::Coordinate& end, Layer_SPtr const layer) : CADEntity(layer), Vector(start, end) {..}


Camel case

Use it as much as possible, though some exceptions are allowed:

  • Variable names in a class may start with a underscore;
  • An '_' (underscore) may be added if the variable name gets unreadable, e.g. in 'Dimension_CSptr';
  • Underscores can help make function names autological, e.g. on_dimRadial_changed:

Good:

  const String _textValue;
  void on_dimRadial_change() {...};

Bad:

  const String _text_value;
  void on_dim_radial_change() {...};


Class names always start with an Upper-case letter.

Variable names always start with a lower-case letter.