Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Death of a Themer - Frontend United - 14 April 2013

2,357 views

Published on

"Death of a themer" was presented by James Panton and myself at Frontend United on 14th April 2013. This was a revised and extended talk of the same name presented by James at DrupalCamp London on 2nd March 2013.
http://www.slideshare.net/therealmcjim/death-of-a-themer-drupal-camplondon2013

Themers are the magicians who transform what Drupal wants to do into what the designer wants it to do. They work alongside developers and site builders and are usually hammering out CSS files, overriding templates, writing theme functions and scratching their heads.

The thing is — and whisper this if possible redundancy concerns you — we can bypass the themer entirely.

With some simple configuration, a site builder can get Drupal to output exactly the semantic, lightweight markup that any modern front-end designer would be proud of. The designer can be left alone to write the most appropriate HTML, CSS and JS, while the site builder need only choose a couple of options when putting together content types, views and panels to make Drupal behave.

A friendly developer may have to lend a hand every now and then, but that’s it. You can get rid of the themer altogether.

This is an extended version of a session James did recently but will take a closer look at the tools and workflow we created and the design principles that initially drove us to this approach.

Published in: Technology, Design
  • Be the first to comment

Death of a Themer - Frontend United - 14 April 2013

  1. 1. Hello, we’re James and Matt@mcjim and @MattFieldingfrom Code Enigma
  2. 2. developersite builderthemerdesigner
  3. 3. developersite builderthemerdesigner
  4. 4. developersite builderthemer (deceased)designer
  5. 5. the life of a themer
  6. 6. overworkedthe life of a themer
  7. 7. overworkedangrythe life of a themer
  8. 8. overworkedangryfrustratedthe life of a themer
  9. 9. overriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuffoverriding stuff overriding stuff overridingstuff overriding stuff overriding stuff
  10. 10. happinesstimethe theming curve
  11. 11. Murder Investigation
  12. 12. developersite builderdesignerwhodunnit?
  13. 13. the developer?whodunnit?
  14. 14. “...to be honest, I never really saw the themer.We worked on different floors.”official statement
  15. 15. the designer?whodunnit?
  16. 16. excluded
  17. 17. 15 columns, why? arrgghh $£@^£$%
  18. 18. “...there was a clash between my personal designprinciples and practices and his methods”official statement
  19. 19. what did he mean bydesign principlesand practices?
  20. 20. Textthey are guides for the way we approachproblems and craft our methodsdesign principles
  21. 21. here are 3 to start us off
  22. 22. minimise wastewaste is any activity whereno value is produced
  23. 23. use the best toolspick the tools that fit your workflow
  24. 24. PreprocessorsSass - CSS preprocessingLess - similar to SassStylus - a good but less popularpreprocessorSusy/Singularity/ZenGrids/GridSet - gridsystem generatorsCompass - add-on functionality for Sass likevertical rhythm, sprites, css3 etcBourbon - Similar to Compass much to theirdismayToolkit - A few nice extras to have -https://github.com/Snugug/toolkitCSS FrameworksSMACSS - styleguide/framework fordeveloping css that is both modular andscalableOOCSS - object oriented CSS - more strictthan smacssStyleguide generationKSS - uses comments in files to generate astyleguide - http://warpspire.com/posts/kss/Typecast - quick way to generate styles fortypeClarify - http://www.clarify.ioStyle-Sites -https://github.com/snugug/style-sitesBrowsersChrome - Supports Sass in the webinspector - needs sass debugging turned onCanary - Same as above but also supportssource mapsSafari - can use the desktop web inspectoron the remote iphone/ipad siteStatic page generatorsHammer for Machttp://hammerformac.com/Middleman - a bit more complex - requirescommand line http://middlemanapp.com/CodeKit -http://incident57.com/codekit/index.phpMixture.io http://mixture.io/Serve - Riby gemhttps://github.com/gummesson/serveTestingLive ReloadGuard - command line tool, faster thanlive-reloadAdobe Edge Inspect -http://html.adobe.com/edge/inspect/Mixture.io - http://mixture.io/Virtual Box with Windows XP andsnapshots with IE6, IE7, IE8Lots of devicesTypographytypecast - http://typecast.com/ - canpreview fastColourKuler - https://kuler.adobe.com/Colour Lovers -http://www.colourlovers.com/Color Scheme Designer -http://colorschemedesigner.com/http://color.hailpixel.com/Static image prototypingInvisionApp - very slick -http://invisionapp.com/Shipment - nice dropbox integration -http://blog.shipmentapp.com/Browser ExtentionsWeb Inspector - needs sass debuggingturned on and experimental modeSpeed TracerYSlowAdobe edge InspectLive ReloadVisual design and layoutFireworks - for working outPhotoshop - mainly for image manipulationInDesign - some very useful tools forwireframesIllustrator - creating SVG files andillustrationsUXPin - http://uxpin.com/Useful websites and guidesHTML5 Please - http://html5please.com/Javascript Compression Tool -http://jscompress.comCompass - http://compass-style.org/examples/compass/HTML 5 Outliner -http://gsnedders.html5.org/outliner/Fontello - Icon Font generator -http://fontello.com/http://responsivepx.com/http://css3gen.com/button-generator/Sharing and experimenting with codeDabblet - http://dabblet.com/JS Fiddle - http://jsfiddle.net/CodePen - http://codepen.io/Practical tipsStart with pens and paper
  25. 25. add – don’t removeonly include what we want and need
  26. 26. Textdesign principles are used as guides to informthe decisions we make as designers – primarilythe practices we use to designdesign practices
  27. 27. work with real contentcontent strategy and modeling shouldcome before design
  28. 28. get to code quicklydoing so also minimises a lot of waste
  29. 29. design a process for each jobeach project is different, so designa unique process for each
  30. 30. what happens if we followthese design principles andpractices
  31. 31. static html
  32. 32. pure and honest
  33. 33. these principles andpractices can be appliedby any designer/frontenddeveloper
  34. 34. what problems doesthis cause us?
  35. 35. traditional Drupal workflow
  36. 36. traditional Drupal workflow
  37. 37. traditional Drupal workflowangry viking god themerdrowning in a sea of divs
  38. 38. “...there was a clash between my personal designprinciples and practices and his methods”official statement
  39. 39. Murder Investigation
  40. 40. the site builder?whodunnit?
  41. 41. “...I always got on really well with the themer.Hadn’t seen him much since he went on holiday,though.”official statement
  42. 42. so, what happened whenthe themer went onholiday?
  43. 43. designer, site-builder anddeveloper were left to copewithout a themer
  44. 44. developer and site-buildercame up with a plan…
  45. 45. they knew the designerwas frustrated and wantedto try new methods ofworking
  46. 46. so, they let the designerdo what he wanted…
  47. 47. …and figured out a way ofgetting Drupal to outputthat without the help of athemer
  48. 48. theming without a themerSTEP ONE
  49. 49. the designer builtprototypes in HTML
  50. 50. designer handedHTML, CSS and JSover to the site builder
  51. 51. CSS and JS wasplaced in the theme**can be created there in the first placeHTML was used asa markup guide
  52. 52. theming without a themerSTEP TWO
  53. 53. the developer setone or two things upfor the site builder
  54. 54. required code
  55. 55. a basic theme
  56. 56. base theme?
  57. 57. <div id="page-wrapper"><div id="page"><div id="header"><div class="section clearfix"><?php if ($logo): ?><a href="<?php print $front_page; ?>" title="<?php print t(Home); ?>" rel="home" id="logo"><img src="<?php print $logo; ?>" alt="<?php print t(Home); ?>" /></a><?php endif; ?><?php if ($site_name || $site_slogan): ?><div id="name-and-slogan"><?php if ($site_name): ?><?php if ($title): ?><div id="site-name"><strong><a href="<?php print $front_page; ?>" title="<?php print t(Home); ?>" rel="home"><span><?php print $site_name; ?></span></a></strong></div><?php else: /* Use h1 when the content title is empty */ ?><h1 id="site-name"><a href="<?php print $front_page; ?>" title="<?php print t(Home); ?>" rel="home"><span><?php print $site_name; ?></span></a></h1><?php endif; ?><?php endif; ?><?php if ($site_slogan): ?><div id="site-slogan"><?php print $site_slogan; ?></div><?php endif; ?></div> <!-- /#name-and-slogan --><?php endif; ?><?php print render($page[header]); ?></div></div> <!-- /.section, /#header --><?php if ($main_menu || $secondary_menu): ?><div id="navigation"><div class="section"><?php print theme(links__system_main_menu, array(links => $main_menu, attributes => array(id => main-menu, class => array(links, inline, clearfix)), heading => t(Main menu))); ?><?php print theme(links__system_secondary_menu, array(links => $secondary_menu, attributes => array(id => secondary-menu, class => array(links, inline, clearfix)), heading => t(Secondary menu))); ?></div></div> <!-- /.section, /#navigation --><?php endif; ?><?php if ($breadcrumb): ?><div id="breadcrumb"><?php print $breadcrumb; ?></div><?php endif; ?><?php print $messages; ?><div id="main-wrapper"><div id="main" class="clearfix"><div id="content" class="column"><div class="section"><?php if ($page[highlighted]): ?><div id="highlighted"><?php print render($page[highlighted]); ?></div><?php endif; ?><a id="main-content"></a><?php print render($title_prefix); ?><?php if ($title): ?><h1 class="title" id="page-title"><?php print $title; ?></h1><?php endif; ?><?php print render($title_suffix); ?><?php if ($tabs): ?><div class="tabs"><?php print render($tabs); ?></div><?php endif; ?><?php print render($page[help]); ?><?php if ($action_links): ?><ul class="action-links"><?php print render($action_links); ?></ul><?php endif; ?><?php print render($page[content]); ?><?php print $feed_icons; ?></div></div> <!-- /.section, /#content --><?php if ($page[sidebar_first]): ?><div id="sidebar-first" class="column sidebar"><div class="section"><?php print render($page[sidebar_first]); ?></div></div> <!-- /.section, /#sidebar-first --><?php endif; ?><?php if ($page[sidebar_second]): ?><div id="sidebar-second" class="column sidebar"><div class="section"><?php print render($page[sidebar_second]); ?></div></div> <!-- /.section, /#sidebar-second --><?php endif; ?></div></div> <!-- /#main, /#main-wrapper --><div id="footer"><div class="section"><?php print render($page[footer]); ?></div></div> <!-- /.section, /#footer --></div></div> <!-- /#page, /#page-wrapper -->
  58. 58. <div id="page-wrapper"><div id="page"><div id="header"><div class="section clearfix"><?php if ($logo): ?><a href="<?php print $front_page;?>" title="<?php print t(Home); ?>" rel="home" id="logo"><img src="<?php print $logo; ?>" alt="<?php print t(Home); ?>" /></a><?phpendif; ?><?php if ($site_name || $site_slogan): ?><div id="name-and-slogan"><?php if ($site_name): ?><?php if ($title): ?><div id="site-name"><strong><a href="<?php print $front_page; ?>" title="<?php print t(Home); ?>" rel="home"><span><?php print $site_name; ?></span></a></strong></div><?php else: /* Use h1 when the content title is empty */ ?><h1 id="site-name"><a href="<?php print $front_page;?>" title="<?php print t(Home); ?>" rel="home"><span><?php print $site_name; ?></span></a></h1><?php endif; ?><?php endif; ?><?php if($site_slogan): ?><div id="site-slogan"><?php print $site_slogan; ?></div><?php endif; ?></div> <!-- /#name-and-slogan --><?php endif; ?><?php print render($page[header]); ?></div></div> <!-- /.section, /#header --><?php if ($main_menu || $secondary_menu): ?><divid="navigation"><div class="section"><?php print theme(links__system_main_menu, array(links => $main_menu, attributes => array(id=> main-menu, class => array(links, inline, clearfix)), heading => t(Main menu))); ?><?php printtheme(links__system_secondary_menu, array(links => $secondary_menu, attributes => array(id => secondary-menu, class =>array(links, inline, clearfix)), heading => t(Secondary menu))); ?></div></div> <!-- /.section, /#navigation --><?php endif; ?><?php if ($breadcrumb): ?><div id="breadcrumb"><?php print $breadcrumb; ?></div><?php endif; ?><?php print $messages; ?><div id="main-wrapper"><div id="main" class="clearfix"><div id="content" class="column"><div class="section"><?php if ($page[highlighted]): ?><divid="highlighted"><?php print render($page[highlighted]); ?></div><?php endif; ?><a id="main-content"></a><?php printrender($title_prefix); ?><?php if ($title): ?><h1 class="title" id="page-title"><?php print $title; ?></h1><?php endif; ?><?php printrender($title_suffix); ?><?php if ($tabs): ?><div class="tabs"><?php print render($tabs); ?></div><?php endif; ?><?php printrender($page[help]); ?><?php if ($action_links): ?><ul class="action-links"><?php print render($action_links); ?></ul><?php endif; ?><?php print render($page[content]); ?><?php print $feed_icons; ?></div></div> <!-- /.section, /#content --><?php if($page[sidebar_first]): ?><div id="sidebar-first" class="column sidebar"><div class="section"><?php printrender($page[sidebar_first]); ?></div></div> <!-- /.section, /#sidebar-first --><?php endif; ?><?php if ($page[sidebar_second]): ?><div id="sidebar-second" class="column sidebar"><div class="section"><?php print render($page[sidebar_second]); ?></div></div> <!--/.section, /#sidebar-second --><?php endif; ?></div></div> <!-- /#main, /#main-wrapper --><div id="footer"><div class="section"><?phpprint render($page[footer]); ?></div></div> <!-- /.section, /#footer --></div></div> <!-- /#page, /#page-wrapper -->
  59. 59. <?phpprint $content;
  60. 60. <?phpprint $content;
  61. 61. <div id="<?php print $block_html_id; ?>" class="<?php print $classes; ?>"<?php print $attributes; ?>> <?php printrender($title_prefix); ?><?php if ($block->subject): ?> <h2<?php print $title_attributes; ?>><?php print $block->subject ?></h2><?phpendif;?> <?php print render($title_suffix); ?> <div class="content"<?php print $content_attributes; ?>> <?php print $content ?></div></div><?phpprint $content;
  62. 62. <?phpprint $content;
  63. 63. <?phpprint $content;
  64. 64. a panels layout or two
  65. 65. /*** Implements hook_ctools_plugin_api().*/function ce_panels_ctools_plugin_api($module, $api) {if ($module == panels && $api == styles) {return array(version => 2.0);}if ($module == page_manager && $api == pages_default) {return array(version => 1);}if ($module == "panels_mini" && $api == "panels_default") {return array("version" => "1");}}/*** Implements hook_ctools_plugin_directory()*/function ce_panels_ctools_plugin_directory($module, $plugin) {if ($module == page_manager || $module == panels || $module == ctools) {return $plugin;}}
  66. 66. <?php/*** @file* Layout definition for Code Enigma one column layout.*//*** Panel layout definition.*/$plugin = array(title => t(Code Enigma One Column),category => t(Code Enigma),icon => ce_one_column.png,theme => ce_one_column,regions => array(content => t(Content),),);
  67. 67. <?php/*** @file* Layout template for Code Enigma one column layout.** Regions:* - content*/if (isset($content[content])) {print $content[content];}
  68. 68. a method for turning off allsupplied CSS and JS
  69. 69. /*** Implements hook_js_alter().*/function mytheme_js_alter(&$js) {if (user_is_anonymous()) {$path_to_theme = path_to_theme();$allowed_js = array(settings,misc/jquery.js,sites/all/modules/contrib/google_analytics/googleanalytics.js,);foreach ($js as $key => $script) {if (!is_numeric($key) && !in_array($key, $allowed_js) &&strpos($key, $path_to_theme) === FALSE) {unset($js[$key]);}}}}
  70. 70. theming without a themerSTEP THREE
  71. 71. add a few modules
  72. 72. display suitesemantic viewspanelspanels everywheresemantic panels**using a forked version atmhttp://drupal.org/sandbox/mcjim/1899120
  73. 73. display suite
  74. 74. control over fieldand node markup
  75. 75. <img width="120" height="289" alt="useful alt text, ta"src="/files/my_image.jpg" />
  76. 76. <div class="field field-name-field-image field-type-imagefield-label-hidden"><div class="field-items"><div class="field-item even"><img width="120" height="289" alt="useful alt text, ta"src="/files/my_image.jpg"></div></div></div>
  77. 77. view modes
  78. 78. semantic views
  79. 79. panelspanels everywheresemantic panels
  80. 80. an interface for wrappingcontent with markup
  81. 81. CONTENT<MARKUP> </MARKUP>
  82. 82. CONTENT<MARKUP> </MARKUP>
  83. 83. doesnt panels addloads* of divs?*seriously, loads
  84. 84. <?php/*** @file* Layout template for Code Enigma one column layout.** Regions:* - content*/if (isset($content[content])) {print $content[content];}
  85. 85. what do we end up with?
  86. 86. a real example
  87. 87. some rules
  88. 88. never write a .tpl.php
  89. 89. never write a .tpl.phpunless you really have to
  90. 90. start by outputting nomarkup at all
  91. 91. add markup via the UI
  92. 92. think carefully about whereyou add your layoutclasses
  93. 93. use Features andzero-touch deployment
  94. 94. Murder Investigation
  95. 95. was it a team effort?whodunnit?
  96. 96. whodunnit?
  97. 97. was it a team effort?whodunnit?
  98. 98. project managerthe PM did it
  99. 99. what have we learnedfrom this sorry tale?
  100. 100. design driven
  101. 101. give higher priority to the frontendlet designers take advantage ofthe best tools to improve speedand reduce wastegroup design & frontend dev
  102. 102. team structure
  103. 103. traditional Drupal workflow
  104. 104. new Drupal workflow
  105. 105. new Drupal workflow
  106. 106. split team effort evenly insprints – creates a closerworking relationship acrossteam disciplinesopen up opportunities forcontractors from outsideof Drupal
  107. 107. consistency
  108. 108. remove a layer ofcomplexity forsite buildersmarkup is managedin UI only
  109. 109. dictate
  110. 110. reverse traditionaldrupal working methodstake an uncompromisingapproach to your markupdon’t let Drupal tell youwhat it should be – you show itwho’s boss
  111. 111. thank you!
  112. 112. epiloguewhat happened to the team?
  113. 113. the designer was happy
  114. 114. site builder had an easy life
  115. 115. sprints were productive
  116. 116. the themer SURVIVED and adopted anew identity as a frontend developer
  117. 117. which was a greatfit for the team
  118. 118. there were trust issues withthe PM so he moved on
  119. 119. the end
  120. 120. questions?
  121. 121. exit@MattFielding@mcjim

×