Newbie Guide: How to Patch Styles and Themes
Contents
How do I file a new bug?
- In Bugzilla, click on New. Select Dreamwidth Development. In Component, select Style System. Enter a Summary and a Description. Mention style and author(s) in the summary. If you're patching a color theme, add author names and submission URLs to the description. If you're patching a style, mention the style name, the number of themes it has, the name of the default theme, the author's name and the submission URL.
- Click on Show Advanced Fields. Set Initial State to IN_PROGRESS and enter your Bugzilla e-mail address in Assign To.
Where are style files?
- core1.s2 and core2.s2 are in
~/dw/styles/
- themes.s2 and layout.s2 files are in
~/dw/styles/STYLENAME/
and~/dw/ext/dw-nonfree/styles/STYLENAME/
- STYLENAME.pm style files are in
~/dw/cgi-bin/LJ/S2Theme/
and~/dw/ext/dw-nonfree/cgi-bin/LJ/S2Theme/
- S2Theme.pm is in
~/dw/cgi-bin/LJ/
and~/dw/ext/dw-nonfree/cgi-bin/LJ/
- N.B. this filed is called S2Theme_local.pm in nonfree.
- s2layers.dat is in
~/dw/styles/
and~/dw/ext/dw-nonfree/styles/
Checking usage rights
Before you patch any style or theme, make sure Dreamwidth is allowed to use it as well as the images it contains if there are any:
- We must have the submitter's Contributor Licensing Agreement before we can use their submission. If it's from someone who already has live styles or themes on the site, we already do. If the submission entry has the '-needs cla' tag, we don't. Otherwise, check the comments to see if they've already been asked about it.
- If design and images have been made entirely from scratch by the designer who submitted the style or theme, they need to explicitly state they made them themselves in their submission entry.
- If design or images haven't been made entirely from scratch by the designer who submitted the style or theme, they must mention where they came from and how they're licensed. We can only use designs and images if commercial use is allowed, use in website templates is allowed and storage on one own's server is allowed. You must also check if they may only be used as-is or if any kind of transformation (also called 'remix') is allowed, and how crediting must be done.
When in doubt, comment on the bug.
Dw-free or dw-nonfree?
Dreamwidth may be allowed to use designs and images on dreamwidth.org but may not be allowed to redistribute or sublicense them to other sites. If that's the case, elements need to go to dw-nonfree:
- Styles go to dw-nonfree if Dreamwidth can use them but can't redistribute/sublicense them.
- Themes go to dw-nonfree if they contain images Dreamwidth can use but can't redistribute/sublicense.
- Themes go to dw-nonfree if the base style is already in dw-nonfree. This the case for Transmogrified and Sunday Morning themes.
Adding a new style
Edit s2layers.dat
- If this is a new Core2 style, add:
stylename/layout layout core2 stylename/themes theme+ stylename/layout
- If this is a child of Tabula Rasa, add:
stylename/layout layout(core2base/layout) core2 stylename/themes theme+ stylename/layout
Edit S2Theme.pm
FIXME: still called _local in nonfree.
Scroll down to %default_themes
and add the style and default theme:
layoutname => 'stylename/defaulttheme',
Create STYLENAME.pm
- Create STYLENAME.pm in
~/dw/cgi-bin/LJ/S2Theme/
or~/dw/ext/dw-nonfree/cgi-bin/LJ/S2Theme/
.
- Add:
package LJ::S2Theme::layoutname; use base qw( LJ::S2Theme ); use strict; sub layouts { ( "1" => "one-column", "1s" => "one-column-split", "2l" => "two-columns-left", "2r" => "two-columns-right", "3" => "three-columns-sides", "3r" => "three-columns-right", "3l" => "three-columns-left" ) } sub layout_prop { "layout_type" } 1;
- Remove layout options which don't apply to the style.
- If the style has new Customize properties which can be sorted into existing categories (such as Page, Header, Module, Entry, etc.) you can add them to these categories using
sub xxx_props
:
sub module_props { my $self = shift; my @props = qw( new_property 1 new_property 2 new_property 3 new_property 4 new_property 5 ); return $self->_append_props( "module_props", @props ); }
- Existing categories can be found in
~/dw/cgi-bin/LJ/S2Theme.pm
- Note that, in Customize, they will be put after default properties, in the order you've listed them in in layout.s2.
Create the STYLENAME directory
Create a directory with the name of the style in ~/dw/styles/
or ~/dw/ext/dw-nonfree/styles/
.
Create layout.s2
- In the directory you've just created, create a file named
layout.s2
. Add:
layerinfo type = "layout"; layerinfo name = "stylename"; layerinfo redist_uniq = "stylename/layout"; layerinfo author_name = "someuser"; layerinfo lang = "en"; set layout_authors = [ { "name" => "someuser", "type" => "user" } ];
- Make sure to respect the designer's wishes concerning capitalization and that layerinfo author_name and layout_authors match.
- If the designer doesn't want their name to be displayed as a username or isn't a user, use this instead:
set layout_authors = [ { "name" => "someuser" } ];
- If there are resources to credit, add them with:
set layout_resources = [ { "name" => "Name", "url" => "http://URL" } ];
- Add the style code using headers for options (presentation, colors, fonts, images, modules, text, other) and for the stylesheet:
##=============================== ## Stylesheet ##===============================
Special case: custom properties
- If the style has custom properties, first try to see if you can find existing ones in Core2 which would fit just as well.
- If there aren't, make sure their names follow existing patterns: a) the property type (color, font, image, ...) b) the major area it applies to (header, entry, module,...) c) the precise element it applies to (text, link, background) and finally d) anything which might precise it further (alt, hover, active,...). The goal is to try to make it precise enough that anybody reading the code will know what it does without having to read the description.
Here are some examples:
color_header_navlinks_link_visited
color_module_link_background_hover
font_entry_datetime
- A few exceptions to this rule:
- image props mention whether they're background images or other sorts of images first ( e.g. image_background_entry_title, image_decoration_module_footer)
- some custom properties can apply to an element wherever it may be displayed. In this case try to name this element as precisely as possible (e.g. font_titles for any H1, H2, H3, H4 headings or calendar_entryday_background if it applies to both the archive page calendar and the module calendar).
- Sort them into existing groups (presentation, colors, fonts, images, modules, text, other) by appending
_child
to the group name. For example:
propgroup images_child { property string image_module_list { des = "Module list image"; } }
- Finally add a corresponding header (presentation, etc.).
Special case: custom module positions
- If a module has more or fewer available positions than other modules, you can customize the sections it can be set to by using
_override
. For example:
property string module_navlinks_section_override { values = "none|(none)|header|Header|one|Group One|two|Group Two"; grouped = 1; } set grouped_property_override = { "module_navlinks_section" => "module_navlinks_section_override" }; set module_navlinks_section = "header";
- Don't forget to make sure it's printed correctly when set to every position, possibly by editing
function Page::print() { }
.
Special case: custom functions
- If there is any function to be added, add a 'functions' header then briefly explain why each function had to be edited in a comment (e.g. to add an extra DIV, to add a new section for modules).
Create themes.s2
- Stille in the directory you made, create a file named
themes.s2
.
- Follow the steps outlined in the next section.
Adding a new color theme
Themes go into the themes.s2 file corresponding to the style your theme is for. Once you've found it follow these steps.
Add theme info
- First, make sure to add the theme code in the right place: themes should be alphabetically sorted.
- Then add the following lines with the correct information at the beginning of the theme. Note that blank spaces aren't allowed in #NEWLAYER and redist_uniq.
#NEWLAYER: stylename/themename layerinfo type = "theme"; layerinfo name = "Theme Name"; layerinfo redist_uniq = "stylename/themename"; layerinfo author_name = "someuser";
Add designer credit
- If the color theme author is not the style author, add this below the theme info, separated by a blank line:
set theme_authors = [ { "name" => "someuser", "type" => "user" } ];
- Make sure to respect the designer's wishes concerning capitalization and that layerinfo author_name and theme_authors match.
- If the designer doesn't want their name to be displayed as a username or isn't a user, use this instead:
set theme_authors = [ { "name" => "someuser" } ];
Add resource credit
- If there are resources to credit, add them with:
set layout_resources = [ { "name" => "Name", "url" => "http://URL" } ];
- If there were already resources credited in the style, you need to add them again or they'll be lost.
Add styling properties
- Add the theme properties (colors, fonts, etc.) by sorting them by category then alphabetically within each category. Possible categories are: Presentation, Page Colors, Entry Colors, Module Colors, Fonts and Images, in this order.
- Add headers to separate each category:
##=============================== ## Page Colors ##===============================
- In most cases, that's all there is to a theme and you can skip the next two sections.
Special case: images
- Images go into
~/dw/htdocs/img/styles/
or~/dw/ext/htdocs/img/styles/
.
- Check the /commons folder to see if they're already used in another style. Otherwise, create a folder named after the style and put them there. If necessary, edit their names to respect the following rules:
- If there's only one image per theme, just name if after the theme:
themename.xxx
- If there are several images per theme, name them like this:
themename_imagename.xxx
. However, if the image isn't specific to one theme, simply useimagename.xxx
.
- If there's only one image per theme, just name if after the theme:
- In the theme, use
folder_name/name.xxx
as the image URL.
Special case: theme-specific CSS
- If there's theme-specific CSS, add it in this function, after you've added all the properties:
##=============================== ## Stylesheet ##=============================== function Page::print_theme_stylesheet() { """ CSS HERE """; }
Check and format your files
General rules
- No tabs or trailing spaces.
- No empty properties.
- No hardcoded colors, fonts or text except shadows,
:before
/:after
characters, colors inprint_theme_stylesheet()
if the designer has used a non-safe combination (color_page_text on color_entry_background instead of color_entry_text on color_entry_background ) or colors which aren't used elsewhere.
- No redundant code.
- Use shorthand for color codes whenever possible: #555 instead of #555555 and #abc instead of #aabbcc.
- Fonts should be capitalized, and single-quoted if there are several words:
'News Gothic MT'
instead ofnews gothic mt
.
- Each theme must be separated by two blank lines. Leave one blank line after the last theme in the file.
Format CSS
If there's CSS in your files you want it to be easily readable and editable while still as compact as possible.
- Selectors should be listed in the order they're displayed in the source (as often as possible). Properties should be indented and alphabetized.
- Leading zeros should be removed from decimals: .5em instead of 0.5em.
- Selectors should be grouped whenever possible (although you sometimes need to favor what's comprehensible over what's economical).
- Use shorthand whenever possible:
border: 1px solid $*color_module_border; border-top: none; list-style: square inside url($*image_list_bullet); margin: 2em .5em 1em;
instead of:
border-bottom: 1px solid $*color_module_border; border-left: 1px solid $*color_module_border; border-right: 1px solid $*color_module_border; list-style-image: url($*image_list_bullet); list-style-position: inside; list-style-type: square; margin-bottom: 1em; margin-left: .5em; margin-right: .5em; margin-top: 2em;
- Remove gratuitous specificity such as
div.entry
instead of.entry
. Inserting .DIV and .SPAN when they're not needed makes it harder to override selectors and can cause conflicts or bugs down the line. Compare:
.entry-content { background: blue; } div.entry-content { background: red; } .entry .entry-content { background: green; } div.entry div.entry-content { background: yellow; }
- On the other hand,
!important
are to be avoided whenever possible. In this case, adding specificity to your selector is a good idea.
- In styles only, add style name and style author at the top of the stylesheet and use comment headers to separate sections:
/* Style Name /* by style author ******************************/ /* Modules ******************************/ .module { margin: 2em .5em; padding: 2em; }
Test, test and test
- On your test account, check colors on all pages. Don't forget hover and visited links, comment subjects, bottom links, reply boxes and drop-down menus on comment pages, pagination links, contextual pop-ups, the navigation strip, blockquotes in entries and comments if these have been customized. Also make sure make sure everything is correctly listed and named in Customize.
- Tip: it is generally a good idea to set up a test account for this purpose with entries with metadata, links, large images, long subjects, short content, non-square icons as well as entries with lots of comments, collapsed comments, etc.
- For styles, you need to do even more thorough checking and anticipate on what users and other designers could change: the style must not only work with the original set of themes but also with dark on light themes, backgrounds where the original designer didn't set one, etc. It must work with all types of supported page set-ups, on all pages, with all sorts of entries and comments, and do so in various screen resolutions and font sizes. It must also work on community journals.
- N.B. Also see the list of required features in dreamscapes.
Preview pictures
Preview pics go into ~/dw/htdocs/img/customize/previews/STYLENAME/
or ~/dw/ext/dw-nonfree/htdocs/img/customize/previews/STYLENAME/
. If you can't do them it's no big deal: simply mention it on the bug so that someone can do them for you or ask for help at dreamscapes.
Requirements
- Previews pics should be 150x114 pixels exactly, saved as color-indexed .PNGs without any color profile.
- Preview pictures are screenshots of the Recent Pages of your test account in a big enough font size (16px for example). They generally show one or two dummy entries with dummy titles and a generic Dreamwidth icon (or the no-userpic default graphic), few sidebar modules and no footer modules. The navigation strip shouldn't be visible.
- N.B. In Mozilla Firefox, you can use Dummy Lipsum to generate dummy text and CheckFox to uncheck several modules at once.
How to take a screenshot
- It is best if you take your screenshot when your browser window is set to 1280x973 pixels as this will resize to 150x114 nicely. If you have a smaller resolution you can of course set it to whatever fits your screen and will be easily resizable to 150x114.
- In Mozilla Firefox:
- In Google Chrome:
- Window Resizer will make your browser window a specified size. Especially useful, if you set "screen type" to "mobile device" then the content window is made to the specified size.
- Screen Capture will take screen shots of the contents of a browser window. A bit buggy but does the job.
How to use ImageMagick to resize and sharpen
- Once your screenshot is already the right aspect ratio, this command will resize it, sharpen it and convert it to the right format:
convert -resize '150x114' -sharpen 25 +dither -type Palette $inputfilename png8:$outputfilename
- You can also make this into a script:
#!/bin/bash for f in *.png; do convert -resize '150' -sharpen 25 +dither -type Palette "$f" png8:"$f" done
- This version also checks if any of the files have already been done (so doesn't do them again) and prints out the names of the files it resizes:
#!/bin/bash echo " Creating Dreamwidth previews..." for f in *.png; do w=$(identify -format "%w" "$f") h=$(identify -format "%h" "$f") t=$(identify -format "%r" "$f") c=$(identify -format "%k" "$f") if [ $w -ne 150 ] || [ $h -ne 114 ] || [ $t != "PseudoClassRGB" ] || [ $c -gt 256 ]; then echo " * $f" convert -resize '150' -sharpen 25 +dither -type Palette "$f" png8:"$f" fi done echo " ... done"
How to crop, resize, and optimize via the commandline
This script will take screengrabs of any aspect ratio, and resize and crop them to the appropriate dimensions for previews. It will also palettize them, and run optimizations to get smaller files. It will /not/ crop out menus and browser borders, so taking screengrabs with an extension such as ScreenCapture or FireShot is recommended to save time cropping out extra stuff. It's also better to have an image longer than it is wide, so any cropping comes from the bottom of the image, and not the sides (which would crop layout elements) It can be run locally if you have Linux, and requires the imagemagick package (frequently installed by default), as well as pngcrush and pngnq. The DreamHack server has all three packages already installed.
Installing the script
1) Navigate to the folder where bash scripts live.
a. On Linux, check your distribution's docs for where this is. If you use a shell other than bash, this script won't work for you.
b. On a Dreamhack account, navigate to the top-level /bin folder (note: this is NOT /dw/bin).
2) Make a new blank file with the name of what you want the script command to be.
3) Add the text of the script (below) to the new file and save.
#!/bin/bash for f in *.png; do convert -resize 150x114^ -gravity north -extent 150x114 -sharpen 25 +dither -type Palette "$f" png8:"out.png" && pngnq -n 256 -s 1 -f out.png && pngcrush -c 3 -bit_depth 8 -rem alla -brute out-nq8.png "$f" >/dev/null && rm out.png out-nq8.png done
4) Modify permissions to make the script executable.
a. In a GUI file manager, right-click -> properties should have a permissions tab. Either check 'Allow executing file as a program' (common on Ubuntu-derived distributions), or, if given a (R)ead/(W)rite/e(X)ecute grid, all users should have read and execute permissions.
b. On the commandline, make sure you're within the folder with the file, then run 'chmod 755 yourfilename'.
Using the script
1) On the commandline, navigate to the folder where your original image files are.
2) Call the script by simply typing its name on the commandline and hitting enter. It will act on all pngs in the given folder.
NOTE: this script modifies the original files. If for some reason you want to keep the full-sized versions, make copies before running the script.