Coding Style: Difference between revisions

From Dolphin Emulator Wiki
Jump to navigation Jump to search
(Added Development category)
(Added syntax highlighting)
Line 49: Line 49:
=== UsefulClass.h ===
=== UsefulClass.h ===


<pre>#pragma once
<syntaxhighlight lang="cpp">#pragma once


class UsefulClass : public SomeParent, public AnotherParent
class UsefulClass : public SomeParent, public AnotherParent
Line 86: Line 86:
         return m_x;
         return m_x;
}
}
// Every file should end in a newline</pre>
// Every file should end in a newline</syntaxhighlight>




Line 93: Line 93:
Follow the indentation/whitespace style shown below.
Follow the indentation/whitespace style shown below.


<pre>namespace Example
<syntaxhighlight lang="cpp">namespace Example
{
{
// Namespace contents are not indented
// Namespace contents are not indented
Line 180: Line 180:
}
}


}</pre>
}</syntaxhighlight>




Line 187: Line 187:
Do not do any of this.
Do not do any of this.


<pre>// Try to avoid macros, use a constant variable instead
<syntaxhighlight lang="cpp">// Try to avoid macros, use a constant variable instead
#define FOO_BAR 5
#define FOO_BAR 5


Line 241: Line 241:
          
          
         /* Don't use multiline comments */
         /* Don't use multiline comments */
}</pre>
}</syntaxhighlight>


[[Category:Development]]
[[Category:Development]]

Revision as of 23:23, 13 March 2014

This is how we write code in Dolphin. Because of multiple developers spread out over many many years, Dolphin is a mess of different coding standards. We stray from this ideal in many places in the code, but the mess is slowly but surely being cleaned up. Do try follow these guidelines for any new code.

The following astyle command will format very closely to our style:

astyle -A1TfpHUxdk1W1wYm0M2j filename.cpp


General Rules

  • Try to keep lines to 80 characters.
  • Prefer namespaces to classes with all members static.
  • Classes/OO is allowed, but keep it simple please. No crazy double visitor patterns etc.
  • Should you use iterators, always use pre-increment (++iter) over post-increment (iter++) where possible.
  • Use single tabs as indentation (tabs, not spaces).
  • Try to eliminate all warnings.
  • Define global variables at the top of the file/namespace they belong to.


Naming Rules

  • All class, struct and function names:
    • CamelCase
  • Compile-time constants:
    • ALL_CAPS
  • Template parameters:
    • T (capital letter)
  • All other variables:
    • lower_case_underscored
  • Variable prefixes:
    • globals
      • "g_"
    • class members
      • "m_"
    • statics
      • "s_"


Class Names

  • Use struct for POD types, class everywhere else.
  • Put class contents in public, protected, private order.
  • For each access level, put contents in constructors, destructor, operators, functions, variables order.
  • Omit unneeded sections.
  • Define static member variables first.
  • Define member functions in the order they were declared.
  • Follow the indentation/whitespace style shown in the example.


UsefulClass.h

<syntaxhighlight lang="cpp">#pragma once

class UsefulClass : public SomeParent, public AnotherParent { public:

       UsefulClass(int x, int y);
       
       int GetX() const;
       
       int GetY() const;
       

protected:

       virtual void SomeProtectedFunction() = 0;
       static float s_some_variable;
       

private:

       int m_x;
       int m_y;

};

float UsefulClass::s_some_variable; UsefulClass::UsefulClass(int x, int y)  : m_x(x) , m_y(y) {} int UsefulClass::GetX() const { return m_x; } int UsefulClass::GetY() const { return m_x; } // Every file should end in a newline</syntaxhighlight>

Indentation/Whitespace Style

Follow the indentation/whitespace style shown below.

<syntaxhighlight lang="cpp">namespace Example { // Namespace contents are not indented

// Declare globals at the top int g_foo = 0;

enum SomeEnum {

       COLOR_RED,
       COLOR_GREEN,
       COLOR_BLUE

};

struct Position {

       int x, y;

};

// Use "typename" rather than "class" here, just to be consistent template <typename T, typename N> void FooBar() {

       int some_array[] =
       {
               5,
               25,
               7,
               42
       };
       if (note == the_space_after_the_if)
       {
               CallAfunction();
       }
       else
       {
               // Use a space after the // when commenting
       }
       // Comment directly above code when possible
       if (some_condition)
               single_statement();
       // Place a single space after the for loop semicolons
       for (int i = 0; i != 25; ++i)
       {
               // This is how we write loops
       }
       
       DoStuff(this, function, call, takes, up, multiple,
               lines, like, this);
               
       if (this || condition_takes_up_multiple &&
               lines && like && this || everything ||
               alright || then)
       {
       
       }
       switch (var)
       {
       // No indentation for case label
       case 1:
       {
               int case_var = var + 3;
               DoSomething(case_var);
               break;
       }
       case 3:
               DoSomething(var);
               return;
               // Always break, even after a return
               break;
               
       default:
               // Yes, even break for the last case
               break;
       }
       std::vector<int>
               you_can_declare,
               a_few,
               variables,
               like_this;

}

}</syntaxhighlight>


DON'T DO

Do not do any of this.

<syntaxhighlight lang="cpp">// Try to avoid macros, use a constant variable instead

  1. define FOO_BAR 5

// Don't include wxWidgets (directly or indirectly) from Core

  1. include <wx/wx.h>

// No, put the curly-bracket on the next line void FooBar(){

       // Don't declare a bunch of variables at the top of a function
       // Declare variables when they are first needed
       int foo;
       float bar;
       std::string str;
       
       // No, put the curly-bracket on the next line
       if (condition) {
       }
       // Don't use a semicolon for an empty body, use {}
       while (true);
       
       // Put a space between "while/if/switch" and the condition parenthesis
       while(true)
       {}
       
       // Use "while (true)" if needed
       for (;;)
       {}
       
       // Declare iterators within the for loop
       int i;
       for (i = 0; i != 10; ++i)
       {}
       
       // This makes it harder to read, put the statement on the next line
       if (condition) DoStuff();
       
       if (condition)
               CallFoo(),      // This is legitimate code, but don't do it
               CallBar();      // Try not to comment to the right of code
       
       // Save CamelCase for function and class names
       int LocalVariable = 5;
       
       // Avoid implicit conversion and even explicit cast to bool, this produces a warning in msvc
       // Use bool b = (some_int != 0);
       int some_int = 5;
       bool b = some_int;
       // Avoid implicit conversions to smaller types and between float/int, it causes warnings
       u32 u = some_u64;
       float f = u;
       
       /* Don't use multiline comments */

}</syntaxhighlight>