Skip to content
This repository was archived by the owner on Dec 15, 2022. It is now read-only.

Commit 0716bd3

Browse files
authored
Add naming convention doc
1 parent ece5f33 commit 0716bd3

File tree

1 file changed

+195
-0
lines changed

1 file changed

+195
-0
lines changed

docs/naming-convention.md

Lines changed: 195 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,195 @@
1+
# CSS Naming Convention
2+
3+
4+
This is Atom's naming convention for creating UI in Atom and Atom packages. It's close to [BEM/SUIT](https://github.com/suitcss/suit/blob/master/doc/naming-conventions.md), but slightly customized for Atom's use case.
5+
6+
7+
## Example
8+
9+
Below the commit box as a possible example:
10+
11+
```html
12+
<div class='gitub-CommitBox'>
13+
<div class='gitub-CommitBox-editor'></div>
14+
<footer class='gitub-CommitBox-footer'>
15+
<button class='gitub-CommitBox-button'>Commit to sm-branch</button>
16+
<div class='gitub-CommitBox-counter is-warning'>50</div>
17+
</footer>
18+
</div>
19+
```
20+
21+
And when styled in Less:
22+
23+
```less
24+
.github {
25+
&-CommitBox {
26+
27+
&-editor {}
28+
29+
&-footer {}
30+
31+
&-button {}
32+
33+
&-counter {
34+
background: red;
35+
36+
&.is-warning {
37+
color: black;
38+
}
39+
}
40+
}
41+
}
42+
```
43+
44+
## Breakdown
45+
46+
Here another example:
47+
48+
```html
49+
<button class='
50+
github-CommitBox-commitButton
51+
github-CommitBox-commitButton--primary
52+
is-disabled
53+
'>
54+
```
55+
56+
And now let's break it down into all the different parts.
57+
58+
```html
59+
<button class='
60+
namespace-ComponentName-childElement
61+
namespace-ComponentName-childElement--modifier
62+
is-state
63+
'>
64+
```
65+
66+
67+
### Namespace
68+
69+
`github`-CommitBox
70+
71+
Every class starts with a namespace, in Atom's case it's the __package name__. Since packages are unique (well, at least for all the packages published on atom.io), it avoids style conflicts. Using a namespace like this makes sure that no styles __leak out__. And even more importantly that no styles __leak in__.
72+
73+
The namespace for Atom core ([atom/atom](https://github.com/atom/atom-ui)) is `core`-ComponentName.
74+
75+
Atom's [UI library](https://github.com/atom/atom-ui) is the only exception that doesn't use a namespace. All components start with the `ComponentName`. For example `Button`, `Checkbox`.
76+
77+
> Note: If multiple words are needed, camelCase is used: `myPackage`-Component.
78+
79+
80+
### Component
81+
82+
github-`CommitBox`
83+
84+
Components are building blocks of a package. They can be small or large. Components can also contain other components. It's more about seeing what belongs together.
85+
86+
Components can also share the same elements. A pattern often found is that a new Component starts where a childElement ends.
87+
88+
```html
89+
<ul class="github-List">
90+
<li class="github-List-item github-Commit">
91+
<label class="github-Commit-message"></label>
92+
<span class="github-Commit-time"></span>
93+
</li>
94+
</ul>
95+
```
96+
97+
In this example, `github-List-item` is responsible for the "container" and layout styles. `github-Commit` is responsible for the "content" inside.
98+
99+
> Note: Components use PascalCase. This makes it easy to spot them in the markup. For example in `settings-List-item`, it's easy to see that the component is `List` and not `settings` or `item`.
100+
101+
102+
### Child element
103+
104+
github-CommitBox-`commitButton`
105+
106+
Elements that are part of a component are appended to the component's class name with a single dash (`-`).
107+
108+
> Note: If multiple words are needed, camelCase is used: github-CommitBox`-commitButton`.
109+
110+
111+
### Modifier
112+
113+
github-CommitBox-commitButton`--primary`
114+
115+
Modifiers are used if a component is very similar to the default component but varies slightly. Like has a different color. Modifiers use a double dash `--` to distinguish them from components and child elements.
116+
117+
> Note: If multiple words are needed, camelCase is used: github-CommitBox-commitButton`--primaryColor`.
118+
119+
120+
### States
121+
122+
github-CommitBox-commitButton `is-disabled`
123+
124+
States are prefixed with a short verb, like `is-` or `has-`. Since these class names probably get used in many different places, it should never be styled stand-alone and always be a chained selector.
125+
126+
```less
127+
.is-disabled {
128+
// nope
129+
}
130+
.github-CommitBox-commitButton.is-disabled {
131+
// yep
132+
}
133+
```
134+
135+
> Note: If multiple words are needed, camelCase is used: `has-collapsedItems`.
136+
137+
138+
139+
## More guidelines
140+
141+
- Styling elements (like `div`) should be avoided. This makes it easier to switch elements, like from a `<button>` to `<a>`.
142+
- No utility classes. Themes and user styles can only override CSS but not change the markup. Therefore having utility classes doesn't make as much sense once you override them.
143+
- Avoid using existing CSS classes to reference elements in the DOM. That way when the markup changes, functionality and specs will less likely break. Instead use `ref` attributes (`ref="commitButton"`).
144+
- Avoid changing modifiers at runtime. If you're in need, consider turning the modifier class into a state. For example if you often want to switch a default button to a primary button, change the `github-CommitBox-commitButton--primary` modifier class into a `is-primary` state instead. Since state classes are decoupled from components, it's easier to reuse that state class even if the component changes later.
145+
146+
147+
## Benefits
148+
149+
- Just by looking at a class in the DevTools you already get a lot of information about where the source can be found (what package, what component). What relationship each element has (parent/child). What class names are states and might be changed/removed. There should be less "what does this class do" moments.
150+
- Reduces specificity. Mostly there is just a single class. Two when using states. This reduces the specificity war when trying to override styles in packages and `styles.less`.
151+
- Using a single class makes it easier to change the markup later. Once a selector like `.class > div > .class` is in the wild, removing the `div` later would break the styling.
152+
- Easier to refactor/move code around because you can see what class belongs to what component.
153+
154+
155+
## Concerns
156+
157+
### Class names get quite long
158+
159+
Only in the DOM. During authoring in Less class names can be split into different parts and glued together with `&`.
160+
161+
```less
162+
.github {
163+
&-CommitBox {
164+
// styles
165+
&-editor {
166+
// styles
167+
}
168+
}
169+
}
170+
```
171+
172+
will output as
173+
174+
```less
175+
.github-CommitBox {
176+
// styles
177+
}
178+
.github-CommitBox-editor {
179+
// styles
180+
}
181+
```
182+
183+
Child elements might also be styled as components. Especially in smaller packages or when components should be shared inside a package. For example `github-CommitBox-commitButton` could just be `github-Button` if that button doesn't need any special styles even tough it's part of the the `CommitBox` component.
184+
185+
### I don't like nesting selectors
186+
187+
The whole selector can of course also be written without nesting. One benefit for not nesting selectors is that they can be easier searched for.
188+
189+
```less
190+
.github-CommitBox { /* styles */ }
191+
192+
.github-CommitBox-editor { /* styles */ }
193+
194+
.github-CommitBox-footer { /* styles */ }
195+
```

0 commit comments

Comments
 (0)