User Tools

Site Tools


coding_guidelines

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revision Previous revision
Next revision
Previous revision
Next revision Both sides next revision
coding_guidelines [2019/06/17 19:58]
haslersn [Code Formatting]
coding_guidelines [2020/02/05 16:46]
tapir [Line Widths] Broken lines indent
Line 86: Line 86:
 ===== Line Widths ===== ===== Line Widths =====
  
-Please configure your editor to have a max column-width of 80-columns. While it is not a strict requirement,​ 80-column cleanliness makes it easy to tile multiple buffers of code across a laptop screen, which provides significant efficiency gains to developers. Use double indent (8-spaces) for broken lines or align with the opening "​("​ in the line above for hanging indents.+Please configure your editor to have a max column-width of 80-columns. While it is not a strict requirement,​ 80-column cleanliness makes it easy to tile multiple buffers of code across a laptop screen, which provides significant efficiency gains to developers. 
 + 
 +For Mixxx'​s clang-format compatibility (ColumnLimit:​ 0):  
 +  * Use double indent (8-spaces) for broken lines 
 +  * Break line after binary operators.  
 +  * If you break a list of function parameters, put each parameter on a single ​line.  
  
  
Line 472: Line 477:
     * ''​parented_ptr''​ for ownership by the QT object tree: e.g. ''​auto p = make_parented<​T>​(...)''​     * ''​parented_ptr''​ for ownership by the QT object tree: e.g. ''​auto p = make_parented<​T>​(...)''​
  
-  * Pass raw pointer ''​T*''​ if no ownership is transfered. A function which receives a raw pointer should not hold onto the pointer ​outside the scope of the function (e.g. by storing it in a member variable). An exception is the parent pointer passed into the constructor of a ''​QObject''​ and internally stored as a non owning ​reference. Do not pass smart pointers by reference. ​+  * Pass reference ''​const T&''​ or ''​T&''​ if no ownership is transfered. ​Pass raw pointer ​''​const T*''​ or ''​T*''​ if no ownership is transfered ​and ''​nullptr''​ is a valid argument value. A function which receives a reference or raw pointer should not hold onto it outside the scope of the function (e.g. by storing it in a member variable). An exception is the parent pointer passed into the constructor of a ''​QObject''​ and internally stored as a non owning reference.
  
-  * ''​parented_ptr''​ requires the parent to be passed into the constructor at the time of creation. If a pointer that will eventually be managed ​by the QT object tree needs to be temporarily created without a parent, first create the object ​''​p'' ​with ''​std::​make_unique''​, and then later create a new variable using ''​parented_ptr(p.release())''​ once the underlying object gets a parent.+  * Pass smart pointers ​by value if ownership is transfered (''​std::​unique_ptr''​) or shared (''​std::​shared_ptr''​)Do not pass smart pointers by reference.
  
-  * Never store a ''​parented_ptr'' ​in an object ​that outlives the parent. If the lifetime of the child relative to the parent ​is not clear then store the output of ''​parented_ptr::​toWeakRef()'' ​instead.+  * Use ''​make_parented''​ to create objects derived from ''​QObject''​ that will be assigned to a parent ​(and will therefore be managed by the Qt object tree). The created object must get a parent ​before ​the ''​parented_ptr'' ​is destructedExample:
  
-  ​Any exceptions ​to these guidelines must be clearly documented inline in the code+    auto pBrowseButton = make_parented<​QPushButton>​(tr("​Browse"​));​ 
 +    // *pBrowseButton is not assigned ​to a parent yet 
 +    pLayout->​addWidget(pBrowseButton);​ 
 +    // Now *pLayout is the parent
  
 +  * The destructor of ''​parented_ptr''​ asserts that the pointed-to object actually has a parent. This ensures that the pointed-to object isn't leaked. A consequence is that **a ''​parented_ptr''​ must never dangle**. Never store a ''​parented_ptr''​ in an object that outlives the parent. This is most easily done by storing the ''​parented_ptr''​ inside exact the parent. If the lifetime of the pointer relative to the parent is not clear then store the output of ''​parented_ptr::​toWeakRef()''​ instead of a ''​parented_ptr''​.
 +
 +  * Any exceptions to these guidelines must be clearly documented inline in the code.
  
 ===== Assertions ===== ===== Assertions =====
Line 504: Line 515:
 </​code>​ </​code>​
  
-               +===== QString ===== 
 + 
 +Use [[http://​doc.qt.io/​qt-5/​qstring.html#​QStringLiteral|QStringLiteral]]. This has a variety of [[https://​woboq.com/​blog/​qstringliteral.html|benefits]].  
 + 
 +Escape non ASCII characters:  
 + 
 +<code cpp-qt>​ 
 +QStringLiteral("​Hello I\u2019ve to go"​);​ 
 +</​code>​ 
 + 
 +QChars can be initialized with ASCII characters 16 bit Unicode L’\u00fc'​ if required. Both are constexpr.  
 + 
 +<code cpp-qt>​ 
 +constexpr QChar kc = '​c'​ 
 +constexpr QChar kue = L'​\u00fc'​ // for "​ü"​ 
 +</​code>​ 
 + 
 +From Mixxx 2.3 we set QT_USE_QSTRINGBUILDER to use QStringBuilder for operator+. Use + in favour of % for better readability. ​         ​
  
  
Line 516: Line 544:
  
  
-===== C++14 =====+===== C++17 =====
  
-As of the Mixxx 2.3 release, Mixxx is switching to C++14. We are taking a conservative approach to adopting C++11/14 features and whitelisting them one by one. If a C++11/14 feature you would like to use is not listed here, please email mixxx-devel to make a case for it and we will consider whitelisting it.+As of the Mixxx 2.3 release, Mixxx is switching to C++17. We are taking a conservative approach to adopting C++11/14/17 features and whitelisting them one by one. If a C++11/14/17 feature you would like to use is not listed here, please email mixxx-devel to make a case for it and we will consider whitelisting it.
  
 We are limited to what is supported across our 3 supported compilers: We are limited to what is supported across our 3 supported compilers:
Line 575: Line 603:
 Use. Use.
  
-==== unicode string literals ==== 
  
-**Do Not Use**. Once we switch to Qt5, you should use [[http://​doc.qt.io/​qt-5/​qstring.html#​QStringLiteral|QStringLiteral]]. This has a variety of [[https://​woboq.com/​blog/​qstringliteral.html|benefits]]. ​ 
  
 ==== right angle brackets ==== ==== right angle brackets ====
Line 591: Line 617:
 In contrast to the pre-C++11 rules (see above) when using //​override//​ on a function in a derived class it is recommended to omit the redundant //virtual// keyword, because //​override//​ implies //​virtual//​. In contrast to the pre-C++11 rules (see above) when using //​override//​ on a function in a derived class it is recommended to omit the redundant //virtual// keyword, because //​override//​ implies //​virtual//​.
  
-Destructors in derived classes should also be marked with //​override//​ instead of //​virtual//​. This ensures at compile time that the base class has declared a //virtual// destructor. If the base class has not declared a //virtual// destructor the destructor of a derived class might not be invoked.+Destructors in derived classes should also be marked with //​override//​ instead of //​virtual//​. This ensures at compile time that the base class has declared a //virtual// destructor. If the base class has not declared a //virtual// destructor the destructor of a derived class might not be invoked. This applies also for default destructors even if it looks noisy
  
 +<code cpp-qt>
 +~ClassName() override = default;
 +</​code>​
 ==== alignment ==== ==== alignment ====
  
coding_guidelines.txt · Last modified: 2020/05/22 06:30 by xerus