Skip to content

r-lib/styler

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

<!DOCTYPE html>
<!-- Generated by pkgdown: do not edit by hand --><html lang="en"><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Contributing to {styler} • styler</title><!-- favicons --><link rel="icon" type="image/png" sizes="16x16" href="favicon-16x16.png"><link rel="icon" type="image/png" sizes="32x32" href="favicon-32x32.png"><link rel="apple-touch-icon" type="image/png" sizes="180x180" href="apple-touch-icon.png"><link rel="apple-touch-icon" type="image/png" sizes="120x120" href="apple-touch-icon-120x120.png"><link rel="apple-touch-icon" type="image/png" sizes="76x76" href="apple-touch-icon-76x76.png"><link rel="apple-touch-icon" type="image/png" sizes="60x60" href="apple-touch-icon-60x60.png"><!-- jquery --><script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js" integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo=" crossorigin="anonymous"></script><!-- Bootstrap --><link href="https://cdnjs.cloudflare.com/ajax/libs/bootswatch/3.4.0/flatly/bootstrap.min.css" rel="stylesheet" crossorigin="anonymous"><script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js" integrity="sha256-nuL8/2cJ5NDSSwnKD8VqreErSWHtnEP9E7AySL+1ev4=" crossorigin="anonymous"></script><!-- bootstrap-toc --><link rel="stylesheet" href="bootstrap-toc.css"><script src="bootstrap-toc.js"></script><!-- Font Awesome icons --><link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.12.1/css/all.min.css" integrity="sha256-mmgLkCYLUQbXn0B1SRqzHar6dCnv9oZFPEC1g1cwlkk=" crossorigin="anonymous"><link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.12.1/css/v4-shims.min.css" integrity="sha256-wZjR52fzng1pJHwx4aV2AO3yyTOXrcDW7jBpJtTwVxw=" crossorigin="anonymous"><!-- clipboard.js --><script src="https://cdnjs.cloudflare.com/ajax/libs/clipboard.js/2.0.6/clipboard.min.js" integrity="sha256-inc5kl9MA1hkeYUt+EC3BhlIgyp/2jDIyBLS6k3UxPI=" crossorigin="anonymous"></script><!-- headroom.js --><script src="https://cdnjs.cloudflare.com/ajax/libs/headroom/0.11.0/headroom.min.js" integrity="sha256-AsUX4SJE1+yuDu5+mAVzJbuYNPHj/WroHuZ8Ir/CkE0=" crossorigin="anonymous"></script><script src="https://cdnjs.cloudflare.com/ajax/libs/headroom/0.11.0/jQuery.headroom.min.js" integrity="sha256-ZX/yNShbjqsohH1k95liqY9Gd8uOiE1S4vZc+9KQ1K4=" crossorigin="anonymous"></script><!-- pkgdown --><link href="pkgdown.css" rel="stylesheet"><script src="pkgdown.js"></script><!-- docsearch --><script src="docsearch.js"></script><link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/docsearch.js/2.6.3/docsearch.min.css" integrity="sha256-QOSRU/ra9ActyXkIBbiIB144aDBdtvXBcNc3OTNuX/Q=" crossorigin="anonymous"><link href="docsearch.css" rel="stylesheet"><script src="https://cdnjs.cloudflare.com/ajax/libs/mark.js/8.11.1/jquery.mark.min.js" integrity="sha256-4HLtjeVgH0eIB3aZ9mLYF6E8oU5chNdjU6p6rrXpl9U=" crossorigin="anonymous"></script><meta property="og:title" content="Contributing to {styler}"><meta property="og:image" content="https://styler.r-lib.org/logo.png"><!-- mathjax --><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/MathJax.js" integrity="sha256-nvJJv9wWKEm88qvoQl9ekL2J+k/RWIsaSScxxlsrv8k=" crossorigin="anonymous"></script><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/config/TeX-AMS-MML_HTMLorMML.js" integrity="sha256-84DKXVJXs0/F8OTMzX4UR909+jtl4G7SPypPavF+GfA=" crossorigin="anonymous"></script><!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/html5shiv/3.7.3/html5shiv.min.js"></script>
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
<![endif]--></head><body data-spy="scroll" data-target="#toc">
    

    <div class="container template-title-body">
      <header><div class="navbar navbar-default navbar-fixed-top" role="navigation">
  <div class="container">
    <div class="navbar-header">
      <button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#navbar" aria-expanded="false">
        <span class="sr-only">Toggle navigation</span>
        <span class="icon-bar"></span>
        <span class="icon-bar"></span>
        <span class="icon-bar"></span>
      </button>
      <span class="navbar-brand">
        <a class="navbar-link" href="index.html">styler</a>
        <span class="version label label-default" data-toggle="tooltip" data-placement="bottom" title="Released version">1.10.3</span>
      </span>
    </div>

    <div id="navbar" class="navbar-collapse collapse">
      <ul class="nav navbar-nav"><li>
  <a href="articles/styler.html">Get started</a>
</li>
<li>
  <a href="reference/index.html">Reference</a>
</li>
<li class="dropdown">
  <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" data-bs-toggle="dropdown" aria-expanded="false">
    Articles
     
    <span class="caret"></span>
  </a>
  <ul class="dropdown-menu" role="menu"><li>
      <a href="articles/detect-alignment.html">Alignment detection</a>
    </li>
    <li>
      <a href="articles/strict.html">The effect of `strict = FALSE`</a>
    </li>
    <li>
      <a href="articles/third-party-integrations.html">Third-party integrations</a>
    </li>
    <li class="divider">
    <li class="dropdown-header">Developers</li>
    <li>
      <a href="articles/remove_rules.html">Remove rules</a>
    </li>
    <li>
      <a href="articles/customizing_styler.html">Customizing styler</a>
    </li>
    <li>
      <a href="articles/distribute_custom_style_guides.html">Distribute custom style guides</a>
    </li>
    <li>
      <a href="articles/caching.html">Caching</a>
    </li>
  </ul></li>
<li class="dropdown">
  <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" data-bs-toggle="dropdown" aria-expanded="false">
    News
     
    <span class="caret"></span>
  </a>
  <ul class="dropdown-menu" role="menu"><li class="dropdown-header">Releases</li>
    <li>
      <a href="https://www.tidyverse.org/blog/2017/12/styler-1.0.0/" class="external-link">Version 1.0.0</a>
    </li>
    <li>
      <a href="https://www.tidyverse.org/blog/2019/11/styler-1-2-0/" class="external-link">Version 1.2.0</a>
    </li>
    <li>
      <a href="https://lorenzwalthert.netlify.com/post/styler-1-3-0/" class="external-link">Version 1.3.0</a>
    </li>
    <li>
      <a href="https://lorenzwalthert.netlify.app/post/styler-1-4-0/" class="external-link">Version 1.4.0</a>
    </li>
    <li class="divider">
    <li>
      <a href="news/index.html">Changelog</a>
    </li>
  </ul></li>
      </ul><ul class="nav navbar-nav navbar-right"><li>
  <a href="https://github.com/r-lib/styler/" class="external-link">
    <span class="fab fa-github fa-lg"></span>
     
  </a>
</li>
      </ul><form class="navbar-form navbar-right hidden-xs hidden-sm" role="search">
        <div class="form-group">
          <input type="search" class="form-control" name="search-input" id="search-input" placeholder="Search..." aria-label="Search for..." autocomplete="off"></div>
      </form>
      
    </div><!--/.nav-collapse -->
  </div><!--/.container -->
</div><!--/.navbar -->

      

      </header><div class="row">
  <div class="contents col-md-9">
    <div class="page-header">
      <h1>Contributing to {styler}</h1>
    </div>

<div id="contributing-to-styler" class="section level1">

<div class="section level2">
<h2 id="introduction">Introduction<a class="anchor" aria-label="anchor" href="#introduction"></a></h2>
<p>This project follows the contributing recommendations outlined by <a href="https://lorenzwalthert.github.io/saamwerk/" class="external-link">saamwerk</a>. In particular, issues labelled with <code>Status: Postponed</code> are closed even if they are not resolved.</p>
</div>
<div class="section level2">
<h2 id="contributing-code">Contributing code<a class="anchor" aria-label="anchor" href="#contributing-code"></a></h2>
<ul><li>Open a PR only when your idea was approved of by a contributor in an issue.</li>
<li>Follow guidelines in <a href="http://style.tidyverse.org" class="external-link">tidyverse style guide</a> for your code contributions.</li>
<li>Make sure your commit pass the pre-commit hooks in this repo. See the <a href="https://lorenzwalthert.github.io/precommit/" class="external-link">precommit</a> <a href="https://github.com/lorenzwalthert/precommit" class="external-link">README.md</a> on how to install the pre-commit framework and the R package on your system and then run <code>precommit::use_precommit()</code> to make sure the hooks are activated in your local styler clone. If you skip a hook, describe why in the PR.</li>
</ul></div>
<div class="section level2">
<h2 id="how-to-dive-in-and-understanding-the-source-code">How to dive in and understanding the source code<a class="anchor" aria-label="anchor" href="#how-to-dive-in-and-understanding-the-source-code"></a></h2>
<p>Read the vignettes. If you are done, come back here.</p>
<div class="sourceCode" id="cb1"><pre class="downlit sourceCode r">
<code class="sourceCode R"><span><span class="fu">devtools</span><span class="fu">::</span><span class="fu"><a href="https://devtools.r-lib.org/reference/load_all.html" class="external-link">load_all</a></span><span class="op">(</span><span class="op">)</span></span>
<span></span>
<span><span class="fu"><a href="https://rdrr.io/r/base/debug.html" class="external-link">debug</a></span><span class="op">(</span><span class="va">style_text</span><span class="op">)</span></span>
<span></span>
<span><span class="fu"><a href="reference/style_text.html">style_text</a></span><span class="op">(</span><span class="st">"call(1, 2 + 1)"</span><span class="op">)</span></span></code></pre></div>
<p>Go broad before you go deep. Before going into the very deep layers of function calls of <code><a href="reference/style_text.html">style_text()</a></code>, try to understand that <code><a href="reference/style_text.html">style_text()</a></code> consists of a few function calls only. Go into each of them and try to understand one layer deep. That is, try to understand what <code><a href="reference/make_transformer.html">make_transformer()</a></code> does by reading the names of the functions that get called, the name of the objects that are created by assigning the output of these function calls. Before looking into a functions source code, look at the documentation for that function. All internal important functions are documented and documentation is available also for unexported objects via <code>?</code> (if you did <code><a href="https://devtools.r-lib.org/reference/load_all.html" class="external-link">devtools::load_all()</a></code>). Then, go into <code>parse_transform_serialize()</code>, and so on.</p>
<p>To understand the most fundamental operation in styler, the manipulation of the columns related to spacing and line break information, pick a rule from <code>R/rules-*.R</code> (e.g. <code>R/rules-spacing</code>), add a break point to a rule, and style a string where you think this rule will be active. Then, see what happens and how this rule is applied on each level of nesting.</p>
</div>
<div class="section level2">
<h2 id="static-code-analysis">Static code analysis<a class="anchor" aria-label="anchor" href="#static-code-analysis"></a></h2>
<p>There are multiple packages that can be used to analyze a code base:</p>
<ul><li>
<a href="https://github.com/lorenzwalthert/gitsum" class="external-link">gitsum</a>: Parses and summarises git repository history.</li>
<li>
<a href="https://github.com/lorenzwalthert/parsesum" class="external-link">parsesum</a>: Analyses source code through parsing.</li>
</ul><p>Check out the links above to see how the tools listed could help you understanding styler.</p>
</div>
<div class="section level2">
<h2 id="project-setup">Project setup<a class="anchor" aria-label="anchor" href="#project-setup"></a></h2>
<ul><li>The package is developed with {devtools} suite, which includes {roxgen2} for documentation, {testthat} for unit testing, {pkgdown} for HTML documentation.</li>
<li>Continuous integration uses github-actions.</li>
<li>A key development principle of styler is to separate infrastructure from style guide. Hence, whenever possible, transformer functions should be adapted, instead of changing the infrastructure for a specific style guide.</li>
<li>{styler} was created in 2017 by Kirill Müller. It was then turned from a proof-of-concept into a ready-for-production tool as part of GSOC 2017 with Kirill Müller and Yihui Xie as mentors and Lorenz Walthert as student.</li>
</ul></div>
<div class="section level2">
<h2 id="file-structure">File Structure<a class="anchor" aria-label="anchor" href="#file-structure"></a></h2>
<p>The source code is organized as follows:</p>
<table class="table"><colgroup><col width="18%"><col width="81%"></colgroup><thead><tr class="header"><th align="right">File</th>
<th align="left">Description</th>
</tr></thead><tbody><tr class="odd"><td align="right">addins.R</td>
<td align="left">ui and helpers for the Addins of styler.</td>
</tr><tr class="even"><td align="right">communicate.R</td>
<td align="left">function to communicate to the user via the console.</td>
</tr><tr class="odd"><td align="right">compat-dplyr.R</td>
<td align="left">compatibility functions. Since styler does not depend on dplyr, we define the dplyr functions ourself.</td>
</tr><tr class="even"><td align="right">compat-tidyr.R</td>
<td align="left">compatibility functions. Since styler does not depend on tidy, we define the tidyr functions ourself.</td>
</tr><tr class="odd"><td align="right">expr-is.R</td>
<td align="left">Functions to check whether an expression matches a predicate (e.g. whether it <em>is</em> a function call, a curly brace expression etc.).</td>
</tr><tr class="even"><td align="right">indent.R</td>
<td align="left">Computation of whether indention is needed (<code><a href="reference/needs_indention.html">needs_indention()</a></code>), if so which indices are indented and how indention is it is triggered.</td>
</tr><tr class="odd"><td align="right">initialize.R</td>
<td align="left">initializer called with the visitor at each nest.</td>
</tr><tr class="even"><td align="right">nest.R</td>
<td align="left">converting from a text representation into a flat and then into a nested parse table representation.</td>
</tr><tr class="odd"><td align="right">nested-to-tree.R</td>
<td align="left">utilities to create a tree representation from text (after text was converted into a nested parse table).</td>
</tr><tr class="even"><td align="right">parse.R</td>
<td align="left">parse text into parse table, minor token manipulation, verification of parsed objects.</td>
</tr><tr class="odd"><td align="right">reindent.R</td>
<td align="left">Deals with token-dependent indention and re-indention, opposed to indent.R where all indention is token independent (i.e. a brace just adds one level of indention, whereas in function declaration headers (if mutli-line), indention depends on token position of “function”).</td>
</tr><tr class="even"><td align="right">relevel.R</td>
<td align="left">Reorganizing the nested parse table, namely relocates expressions on both sides of “%&gt;%” to the same nest.</td>
</tr><tr class="odd"><td align="right">rules-line-break.R, rules-other.R, rules-replacement.R, rules-spacing.R</td>
<td align="left">transformer rules</td>
</tr><tr class="even"><td align="right">serialize.R</td>
<td align="left">converts flattened parse table into text representation. Complement operation to the functions in nest.R</td>
</tr><tr class="odd"><td align="right">set-assert-args.R</td>
<td align="left">Assertion and setting of arguments.</td>
</tr><tr class="even"><td align="right">style-guides.R</td>
<td align="left">How to create style guide objects from transformers.</td>
</tr><tr class="odd"><td align="right">styler.R</td>
<td align="left">General package information.</td>
</tr><tr class="even"><td align="right">testing.R</td>
<td align="left">function used for testing.</td>
</tr><tr class="odd"><td align="right">token-create.R</td>
<td align="left">Utilities for creating tokens, mostly to insert braces around mutli-line if statements.</td>
</tr><tr class="even"><td align="right">token-define.R</td>
<td align="left">Defines which tokens belong to which group.</td>
</tr><tr class="odd"><td align="right">transform-code.R, transform-files.R</td>
<td align="left">Transformation of code for APIs that manipulate files (e.g. <code><a href="reference/style_file.html">style_file()</a></code>).</td>
</tr><tr class="even"><td align="right">ui.R</td>
<td align="left">User interaces. Top-level functions for styling.</td>
</tr><tr class="odd"><td align="right">unindent.R</td>
<td align="left">Certain tokens cause unindention, e.g. closing braces.</td>
</tr><tr class="even"><td align="right">utils.R</td>
<td align="left">low-level general purpose utilities.</td>
</tr><tr class="odd"><td align="right">vertical.R</td>
<td align="left">S3 class for pretty printing of styled code.</td>
</tr><tr class="even"><td align="right">visit.R</td>
<td align="left">Functions that apply functions to each level of nesting, either inside out or outside in.</td>
</tr><tr class="odd"><td align="right">zzz.R</td>
<td align="left">backport imports.</td>
</tr></tbody></table></div>
<div class="section level2">
<h2 id="obtaining-contextual-information">Obtaining contextual information<a class="anchor" aria-label="anchor" href="#obtaining-contextual-information"></a></h2>
<p>You may have problems understanding some code because documentation is minimal, some code / functions seem to solve problems you don’t understand or handle cases that seem unreasonable or otherwise incomprehensible. You can resort to the following strategies:</p>
<ul><li>Use full-text search to see where functions are defined or called and how different parts of {styler} depend on it.</li>
<li>Use <code>$ git blame</code> to see where changes were introduced. Look at the commit message, check changes that were made to the code in the same commit. If you are using the GUI of GitHub, you can easily obtain more contextual information such as the pull request with which a change was introduced. Often, functionality was introduced with testing. So, you can easily see which new tests are related to the new functionality. You can remove the changes in the source code and re-run the tests and see what fails and why.</li>
<li>Search Issues and Pull Requests on GitHub with the full text search. Make sure you also search for closed Issues and PRs.</li>
</ul></div>
<div class="section level2">
<h2 id="high-level-conventions">High-level conventions<a class="anchor" aria-label="anchor" href="#high-level-conventions"></a></h2>
<ul><li>The project follows a highly functional approach. This means that functionality should be capsuled into functions, even if they are only called once. This makes abstraction from the code easier, reduces the number of lines for each function declaration considerably, and makes it easier for people not familiar with the codebase to dive into it.</li>
<li>All internal functions (except if they are 100% self-explanatory) are to be documented.</li>
<li>New functionality (e.g. in terms of styling rules) needs to be unit tested. If the new functionality changes how code is to be styled, the infrastructure with <code><a href="reference/test_collection.html">test_collection()</a></code> should be used.</li>
<li>Cases that are not yet formatted correctly can be labelled with a <code>FIXME</code>.</li>
<li>GitHub is the platform where communication about source code happens. We refrain from adding extensive in-line code comments. One can use <code>$ git blame</code> to track when changes were introduced and find the corresponding pull request and associated issues to understand the thought process that lead to a change in the source code. This also implies that issues and / or pull request contain verbose explanation of problems and solutions provided.</li>
</ul></div>
<div class="section level2">
<h2 id="low-level-coventions">Low-level coventions<a class="anchor" aria-label="anchor" href="#low-level-coventions"></a></h2>
<p>This project follows the <a href="http://style.tidyverse.org" class="external-link">tidyverse style guide</a>. If we refer to specific variables / values etc. in the following sections, you can use RStudio’s full text search to find where <code>remove_line_break_before_round_closing_after_curly()</code> is declared or called.</p>
<div class="section level3">
<h3 id="files">Files<a class="anchor" aria-label="anchor" href="#files"></a></h3>
<ul><li>File names only contain alphanumeric characters and dashes.</li>
<li>Files are named according to topics / contexts, not according to functions that live in these files.</li>
</ul></div>
<div class="section level3">
<h3 id="functions">Functions<a class="anchor" aria-label="anchor" href="#functions"></a></h3>
<ul><li>Function names should be verbs. No abbreviations should be used, we don’t care if function names are particularly long. For example, there is a function with the name <code>remove_line_break_before_round_closing_after_curly()</code>.</li>
<li>Only very low-level functions or functions that don’t fit in any other file go to <code>utils.R</code>.</li>
</ul></div>
<div class="section level3">
<h3 id="control-flow">Control Flow<a class="anchor" aria-label="anchor" href="#control-flow"></a></h3>
<ul><li>Conditional statements should always evaluate to <code>TRUE</code> or <code>FALSE</code>, i.e. we don’t encourage <code>if (length(x))</code>, but rather <code>if (length(x) &gt; 0L)</code>.</li>
<li>We avoid loops whenever possible and use functions like <code><a href="https://purrr.tidyverse.org/reference/map.html" class="external-link">purrr::map()</a></code> and friends when possible and prefer them over R base counterparts like <code><a href="https://rdrr.io/r/base/lapply.html" class="external-link">base::lapply()</a></code>.</li>
</ul></div>
<div class="section level3">
<h3 id="boolean-values">Boolean Values<a class="anchor" aria-label="anchor" href="#boolean-values"></a></h3>
<p>Functions that return Boolean values or variables that hold Boolean values are to be prefixed with <code>is</code> or <code>has</code>. For example, <code>is_rmd_file(path)</code> is a function that returns <code>TRUE</code> if <code>path</code> is the path to a <code>.Rmd</code> file and <code>FALSE</code> otherwise.</p>
</div>
<div class="section level3">
<h3 id="vectors-with-indices">Vectors with indices<a class="anchor" aria-label="anchor" href="#vectors-with-indices"></a></h3>
<p>Vectors that hold indices are often suffixed with <code>idx</code>. For example, <code>else_idx</code> indicates for every row in a parse table whether it contains an <code>else</code> token.</p>
</div>
<div class="section level3">
<h3 id="closures">Closures<a class="anchor" aria-label="anchor" href="#closures"></a></h3>
<p>The use of closures is discouraged. We prefer to prefill a template function with <code><a href="https://purrr.tidyverse.org/reference/partial.html" class="external-link">purrr::partial()</a></code>.</p>
</div>
</div>
<div class="section level2">
<h2 id="testing">Testing<a class="anchor" aria-label="anchor" href="#testing"></a></h2>
<p>We have a testing framework powered by <code><a href="reference/test_collection.html">test_collection()</a></code>. Essentially, there is an *-in.R file and a *-out.R file. The *-in.R file is the input that is transformed and - if it matches the *-out.R file, the test will pass. You can create an *-in.R file, run <code>devtools::test(f = "[your file]")</code> and an *-out.R file is generated. If the file matches your expectation, you can commit it. <strong>Note that files are overwritten and version control should be used to track failed tests.</strong> The files are placed in <code>tests/testthat</code> under the category they fit. Please have a look at the documentation for <code><a href="reference/test_collection.html">test_collection()</a></code> and see other unit tests.</p>
</div>
<div class="section level2">
<h2 id="feedback">Feedback<a class="anchor" aria-label="anchor" href="#feedback"></a></h2>
<p>Please open an issue if something is unclear so that we can improve the contributing guidelines.</p>
</div>
</div>

  </div>

  <div class="col-md-3 hidden-xs hidden-sm" id="pkgdown-sidebar">
    <nav id="toc" data-toggle="toc" class="sticky-top"><h2 data-toc-skip>Contents</h2>
    </nav></div>

</div>



      <footer><div class="copyright">
  <p></p><p>Developed by <a href="https://krlmlr.info" class="external-link">Kirill Müller</a>, <a href="https://lorenzwalthert.com" class="external-link">Lorenz Walthert</a>.</p>
</div>

<div class="pkgdown">
  <p></p><p>Site built with <a href="https://pkgdown.r-lib.org/" class="external-link">pkgdown</a> 2.0.7.</p>
</div>

      </footer></div>

  
<script src="https://cdnjs.cloudflare.com/ajax/libs/docsearch.js/2.6.1/docsearch.min.js" integrity="sha256-GKvGqXDznoRYHCwKXGnuchvKSwmx9SRMrZOTh2g4Sb0=" crossorigin="anonymous"></script><script>
  docsearch({
    
    
    apiKey: '13580d327d8a7159f83a7cff178d2141',
    indexName: 'r-lib_styler',
    inputSelector: 'input#search-input.form-control',
    transformData: function(hits) {
      return hits.map(function (hit) {
        hit.url = updateHitURL(hit);
        return hit;
      });
    }
  });
</script></body></html>

About

Non-invasive pretty printing of R code

Topics

License

Unknown, Unknown licenses found

Licenses found

Unknown
LICENSE
Unknown
LICENSE.md

Contributing

Stars

Watchers

Forks

Packages

No packages published

Contributors 32

Languages