Giter Club home page Giter Club logo

cfinst.github.io's Introduction

CFI WebTool

An interactive visualization of the Campaign Finance Institute database of campaign finance law, spanning all US States and every other year since 1996. Crafted and engineered by Seemant Kulleen and Curran Kelleher.

Try it out!

image

Table of Contents

Development Environment

This section describes how to get your development environment set up and run this site on your own computer.

This site is organized using Jekyll. Jekyll runs automatically on GitHub Pages, which is the main deployment strategy at the moment.

To run this site on your own machine, you'll need a working Ruby environment. (For windows, you can download and run RubyInstaller for Windows. For Linux or Mac you can use rvm). Then use the following commands:

# Install Jekyll on your machine (only required once).
gem install jekyll

# Use Jekyll to serve this site.
cd cfinst.github.io
jekyll serve --watch

Now the site should be available at http://localhost:4000/.

Configuration

This section is about how to configure various aspects of the visualization and user interface.

This project uses Jekyll to build the static site, which resides under _site. The content there is generated automatically by Jekyll based on source code files and configuration files in YAML and Markdown formats. These configuration files define many aspects of the visualization and user interface.

The following files are configuration files:

_config.yml
_data
├── buttons.yml
├── colors.yml
├── sections
│   ├── contribution-limits
│   │   ├── controls.yml
│   │   └── legends.yml
│   ├── disclosure
│   │   ├── controls.yml
│   │   └── legends.yml
│   ├── other-restrictions
│   │   ├── controls.yml
│   │   └── legends.yml
│   └── public-financing
│       ├── controls.yml
│       └── legends.yml
└── tabs.yml
index.md
_modals
├── intro.md
├── contribution-limits
│   ├── about.md
│   └── howto.md
├── disclosure
│   ├── about.md
│   └── howto.md
├── other-restrictions
│   ├── about.md
│   └── howto.md
└── public-financing
    ├── about.md
    └── howto.md
_sass
├── _tips.scss
└── _vis.scss

Configuration Parameters

_config.yml

This file configures the top-level Jekyll site. The following parameters are relevant to the visualization:

  • filterYear This defines the year beyond which data will be filtered out. For example, a configuration of filterYear: 2016 means that 2016 data (and data for all following years e.g. 2017, 2018) are filtered out and not included in the visualization.

  • backgroundRectFadeOpacity The opacity of the background rectangle overlay used with linked hover interactions. A value of 1 means the background will fade completely to white, and a value of 0 means that there will be no fade at all on hover.

  • yearSelectLabel The text shown as the label for the year select dropdown at the bottom of the map.

_data/buttons.yml

This file configures the text shown in the buttons along the right side. Each button has the following configuration options:

  • name A unique id for the button. Please do not change these values unless you also change the JavaScript code that references them.
  • text The text shown within the button.
  • icon The Font Awesome Icon Name for the icon to show withn the button (optional).
  • link The URL that this button links to.
_data/colors.yml

This file defines the color palette hex values. Each color entry has the following parameters:

  • name The name of the color within the palette, referenced from within legend configurations in _data/sections/.../legends.yml. Please do not change this unless you also update all references to it from all legend configurations.
  • hex The hex color value.
_data/tabs.yml

This file describes the visualization tabs. Each entry corresponds to a tab, and has the following parameters:

  • title The text shown in the tab on the page.
  • section The unique identifier for this tab. This value is used in the URLs, as folder names under _data/sections, and elsewhere. Please do not change this unless you also update all references to it from JavaScript and rename the corresponding folder under _data/sections.
  • fields This is unique to the Contribution Limits tab, and enumerates the fields to make available.
_data/sections
 ├── contribution-limits
 │   ├── controls.yml
 │   └── legends.yml
 ├── disclosure
 │   ├── controls.yml
 │   └── legends.yml
 ├── other-restrictions
 │   ├── controls.yml
 │   └── legends.yml
 └── public-financing
     ├── controls.yml
     └── legends.yml

This directory contains the configurations for controls and legend for each section.

_data/sections/:section/controls.yml

Within each section, the controls.yml file defines the content of the dropdown menu(s) available.

For sections other than Contribution Limits, each entry corresponds to an option in the dropdown menu of questions. Each entry has the following parameters:

  • name The field name in the database. This must match with the database.
  • legend The legend to use for this question, referencing the name of the legend entries defined in legends.yml for this section.
  • question The text description of the question, displayed in the "description" box below the dropdown.
  • label The short text description of the question, displayed as an option within the dropdown.
  • note (optional) Any additional notes for this question. This is displayed "below the fold" within the "description" box.
_data/sections/contribution-limits/controls.yml

For the contribution-limits section, dropdown configuration is structured differently from the others. Here, there are two groups of dropdowns, donor and recipient. Within those groups, dropdown entries are configured with the following parameters:

  • id The unique identifier for the dropdown. Please do not change this without also updating all references to it.
  • label The text shown as the label for the dropdown.
  • options The listing of options within the dropdown. Each option entry has the following parameters:
    • label The text shown as the dropdown option.
    • abbr The field name fragment corresponding to this option. This must match with the fields present in the database (please do not change without also updating the database field names).
    • disable (optional) The id of another dropdown that should be disabled when this option is selected.
_data/sections/:section/legends.yml

Within each section, the legends.yml file defines the set of color scales available. Each question maps onto one of these entries. Each entry defines a color scale that drives the color legend, with the following parameters:

  • name The unique identifier for this legend. This is referenced from within the controls.yml configuration to assign a legend to each question. Please do not change this without also updating all references to it.
  • type The scale type to use. The value must be either threshold, ordinal, or singular.
  • fallback The value to use when an empty cell is present in the data. For example, this can map empty cells to a meaningful value of -Infinity.
  • scale The scale entries.
    • If type is threshold, each scale entry defines an interval of values, and has the following parameters:
      • min The minimum value for this interval.
      • max The maximum value for this interval.
      • label The text to display in the legend and tooltips for this interval.
      • color The name of the color, referencing named colors defined in _data/colors.yml.
    • If type is ordinal, each scale entry has the following parameters:
      • label The text to display in the legend and tooltips for this interval. This must match with data values from the database.
      • color The name of the color, referencing named colors defined in _data/colors.yml.
index.md

This file contains two parameters:

  • title Allows you to configure the title of the Web page that appears in the browser tab.
  • layout Specifies which Jekyll layout to use at the top-level.
_modals
├── intro.md
├── contribution-limits
│   ├── about.md
│   └── howto.md
├── disclosure
│   ├── about.md
│   └── howto.md
├── other-restrictions
│   ├── about.md
│   └── howto.md
└── public-financing
    ├── about.md
    └── howto.md

The _modals directory contains configuration files that define what gets shown within the modal dialogs that pop up when the page loads, and when you click on the "About this topic" and "Using this page" buttons.

_modals/intro.md

This file specifies the content of the introduction popup that appears the first time a user loads the page.

_modals/:section/about.md

This file specifies the content of the "About this topic" modal dialog for each section. Its Markdown body text is used as the content of the dialog, passed through a Markdown parser. Its YAML frontmatter defines the following parameters:

  • layout The Jekyll layout to use for the modal HTML structure.
  • modal The unique identifier for this modal. Please do not change this without updating all references to it.
  • title The text displayed as the title of this modal.
_modals/:section/howto.md

This file specifies the content of the "Using this page" modal dialog for each section. Its Markdown body text is used as the content of the dialog, passed through a Markdown parser. Its YAML frontmatter defines the same parameters as in about.md.

_sass/_tips.scss

This CSS defines a custom appearance of the tooltips that appear when you hover over the map or the grid. Draws from examples of d3-tip.

_sass/_vis.scss

This CSS defines styles applied to the visualization. This is where details such as stroke color, cursors, font styles, margins, and transition durations are defined.

_includes/footer.html

This file contains the footer content.

Updating Data

This section is about how you can update the data shown in the visualization based on the original CFI Microsoft Access database file.

Updating from Access Database

The following instructions are for updating the data used by this software from a new database dump from the original Microsoft Access database. After following these steps, the software will use the updated data.

  1. Download database dump file, e.g. CFI State Laws Update_Merge.zip. This will likely end up in your ~/Downloads folder (on Linux / Mac).
  2. Move the file into the data directory of this repository: cd cfinst.github.io/data; mv ~/Downloads/CFI\ State\ Laws\ Update_Merge.zip .
  3. Unzip the file unzip CFI\ State\ Laws\ Update_Merge.zip
  4. Install mdbtools. In Ubuntu Linux, these can be installed with the command sudo apt-get install mdbtools.
  5. Run the shell script that generates the CSV files from the database dump: cd cfints.github.io; ./bin/parse-mdb.sh data/CFI\ State\ Laws\ Update_Merge.mdb

If successful, you should see the following output:

./bin/parse-mdb.sh data/CFI\ State\ Laws\ Update_Merge.mdb
Exporting Laws_00_IdentifierTable to CSV...
Exporting Laws_01_Defintions to CSV...
Exporting Laws_02_Contributions_1 to CSV...
Exporting Laws_02_Contributions_2 to CSV...
Exporting Laws_02_Contributions_3 to CSV...
Exporting Laws_03_Disclosure_1 to CSV...
Exporting Laws_03_Disclosure_2 to CSV...
Exporting Laws_03_Disclosure_3 to CSV...
Exporting Laws_04_PublicFinancing to CSV...
...

Updating Field Descriptions

Field descriptions live inside the Jekyll configurations, under _data/sections/<section>/controls.yml. These files are automatically converted to .CSV files when you run ./bin/package-downloads.sh.

Packaging Download Files

The database content as well as metadata (field descriptions and about button contents) is packaged into a .zip file for download. To create this .zip file, run the following script:

./bin/package-downloads.sh

You should see output similar to the following:

$ ./bin/package-downloads.sh
Configuration file: /home/curran/repos/cfi/_config.yml
            Source: /home/curran/repos/cfi
       Destination: /home/curran/repos/cfi/_site
 Incremental build: disabled. Enable with --incremental
      Generating... 
                    done in 0.133 seconds.
 Auto-regeneration: disabled. Use --watch to enable.

Creating cfi-laws-database.zip
updating: cfi-laws-database/ (stored 0%)
updating: cfi-laws-database/LICENSE (deflated 68%)
updating: cfi-laws-database/metadata/ (stored 0%)
updating: cfi-laws-database/metadata/other-restrictions-fields.csv (deflated 61%)
updating: cfi-laws-database/metadata/disclosure-fields.csv (deflated 70%)
updating: cfi-laws-database/metadata/public-financing-fields.csv (deflated 59%)
updating: cfi-laws-database/data/ (stored 0%)
updating: cfi-laws-database/data/Laws_03_Disclosure_3.csv (deflated 94%)
updating: cfi-laws-database/data/Laws_05_Other.csv (deflated 93%)
updating: cfi-laws-database/data/Laws_03_Disclosure_1.csv (deflated 96%)
updating: cfi-laws-database/data/Laws_02_Contributions_1.csv (deflated 95%)
updating: cfi-laws-database/data/Laws_00_IdentifierTable.csv (deflated 76%)
updating: cfi-laws-database/data/Laws_03_Disclosure_2.csv (deflated 92%)
updating: cfi-laws-database/data/Laws_02_Contributions_3.csv (deflated 93%)
updating: cfi-laws-database/data/Laws_04_PublicFinancing.csv (deflated 93%)
updating: cfi-laws-database/data/Laws_01_Defintions.csv (deflated 95%)
updating: cfi-laws-database/data/Laws_02_Contributions_2.csv (deflated 96%)

This will produce the cfi-laws-database.zip file inside the downloads directory, which will contain both the database tables and the metadata (field description) tables. The .zip archive will have the following layout:

├── cfi-laws-database
    ├── LICENSE
    ├── data
    │   ├── Laws_00_IdentifierTable.csv
    │   ├── Laws_01_Defintions.csv
    │   ├── Laws_02_Contributions_1.csv
    │   ├── Laws_02_Contributions_2.csv
    │   ├── Laws_02_Contributions_3.csv
    │   ├── Laws_03_Disclosure_1.csv
    │   ├── Laws_03_Disclosure_2.csv
    │   ├── Laws_03_Disclosure_3.csv
    │   ├── Laws_04_PublicFinancing.csv
    │   └── Laws_05_Other.csv
    └── metadata
        ├── disclosure-fields.csv
        ├── other-restrictions-fields.csv
        └── public-financing-fields.csv

Licensing

The source code is released under the GPL3 license (LICENSE).

The data driving the visualizations (found under data/CSVs) is released under the Creative Commons Attribution 4.0 International license (data/CSVs/LICENSE). This means that you are free to use the data for any purpose, as long as you add attribution citing Campaign Finance Institute as the source of the data.

cfinst.github.io's People

Contributors

bglavin avatar curran avatar seemantk avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

cfinst.github.io's Issues

Add CC License for data

Add a statement to the project saying that:
the code is released under the GPL3 license, and
the data is released under Creative Commons Attribution 4.0 International license

Party as a Donor

Add "Party" as a donor option in contribution limits section (using Brendan's instructions per email).

@seemantk I feel like you'd have a better idea of how to go about this, as it requires modification of the handling of fields for the contribution limits section.

Stylistic and aesthetic adjustments

Colors, fonts, layouts and finishing touches.

Note: This issue is directly from the Statement of Work, and may need to be broken up into smaller issues.

Restore data-driven values to legends

Now that the legends are no longer data-driven (instead are driven purely from the configuration), we need to go through each field of each section and make sure the legend items present match up with the values that are present in the data.

As one instance, in Public Financing, there are values "Mixed" and "none", which are not accounted for in the legend. This may be part of the issue with the mismatched colors - new data values are causing the colors in the legend to loop around. One thing we could do to help fix this is pad the color range with random colors, just so we will easily know when this is happening.

Maybe the best solution here would be to use the configurations as a starting point for the legends, then fill in the legends with more colors automatically if more values are discovered in the data.

Interface with the database of information

Transition from using a static database dump to a live database.

Note: This issue is directly from the Statement of Work, and may need to be broken up into smaller issues.

Use ranges for colors

The numeric fields can be represented using colors that reflect which range they fall into.

For this, we'll need to:

  • Detect whether or not the current field is numeric.
  • If it is, then use https://github.com/d3/d3-scale/blob/master/README.md#quantize-scales to produce colors based on a computed set of ranges. We can start by using equal-intervals and see if that works well. The ranges should be "nice", so I think we can use the scales in conjunction with scale.nice and scale.ticks to generate the ranges.

Tooltips on Map

This seems like low hanging fruit that would be a big win.

States alphabetized on resize

I just noticed that after sorting by a year, resizing the page causes the states to sort alphabetically. This looks to be an unintended consequence of the way the resize propagates to rendering.

Data Download Page

Create a new page dedicated to providing various data download links. To start, this could link to all of the raw CSV files. There should also be some way to navigate from the limits visualization page into the data download page, maybe a link that says "more download options".

Investigate Color Mismatches

In "Other Restrinctions", the colors for "Yes" and "Changed mid-cycle" seem to have gotten mixed up between the legend and the viz.

Restore "Download Currently Shown Data"

This button seems to be broken now, in all sections except "Other Restrictions". Odd.. It almost seems like an issue with the code that is adding the event listener to the button.

Explore and create visualization methods

  • Fulfill the visual goals (what users should be able to see).
  • Help users answer questions (such as given above).

Note: This issue is directly from the Statement of Work, and may need to be broken up into smaller issues.

Create/Explore navigational methods

Using the data hierarchy expressed in the initial spec from CFI, we will construct a navigational interface to allow exploration of the dataset in digestible chunks.

Note: This issue is directly from the Statement of Work, and may need to be broken up into smaller issues.

Grant CFI folks repository access

I would love to be able to send links to issues and pull requests to the CFI folks. In order for them to be able to access those links, they need to create GitHub accounts and be granted access to this repository.

Add prohibited and unlimited to current view download

Now there is a "Download Currently Shown Data" button that downloads CSV data for the currently selected field only. Here's a sample of the CSV output:

State,Year,IndividualToCandLimit_H_Max
"LA",1996,"5000"
"WV",1996,"2000"
"SD",1996,"500"
"NM",1996,""
"NV",1996,"2000"
"VT",1996,"2000"
"AK",1996,"2000"
"HI",1996,"2000"
"KS",1996,"1000"
"SC",1996,"3500"
"OK",1996,"5000"
"MN",1996,"600"
"AL",1996,""
"ID",1996,""
"PA",1996,""
"NE",1996,""

The information about unlimited vs. prohibited is missing.

This issue is about adding the missing information about prohibited and unlimited. The empty strings should be replaced by "No limit" or "Prohibited" (or something similar).

Make the download buttons work reliably in Firefox and Chrome

Currently the "Current View" download button only works in Chrome, not firefox.

The "Download Entire Limits Data" button no longer works at all in Chrome. This may have something to do with the introduction of encodeURIComponent() in #77 . Possibly the DataURL is too long?

Add year indicator to map

Add an indication of which year is being displayed on the map. This could be a simple text element on the top, or in some other location, just saying the year.

Final Stakeholder review and Go-Live

The website will be deployed and released

Note: This issue is directly from the Statement of Work, and may need to be broken up into smaller issues.

Download visible data button

Create a button that will download the currently visible data, for the current configuration of the visualization only, as CSV.

Add year selection interface below map

This issue is about implementing an interface idea we discussed recently, where there would be a user interface element below the map for selecting the year. This would obviate the need for the year label on top of the map.

Possible solutions we discussed included

  • Drop-down menu
  • Group of buttons, one for each year
    image
  • Slider with tick marks and tick labels

Linked Highlighting

I'd be curious to experiment with adding a linked hover interaction. This would make it easier to correlate between the two views. I envision we could try the following:

  • Hovering on a state in the map highlights the corresponding column in the grid.
  • Hovering over a cell in the grid would cause its current column and corresponding state in the map to highlight.

image

One way to do the highlighting would be using an outline around the state and column. Something similar is implemented in this example http://curran.github.io/model/examples/d3LinkedChoropleth/

Improve the contrast/color perception

During the call today, both Michael and Ronda observed that the lack of color contrast between the circular grid cells compromised the overall usability of the viz. Thus, #46 addresses changing the cells to rectangular, and this one is for the color pallette

Document dataset generation

Document in the README the command that can be used to generate the CSV files from the original MDB files. This will facilitate the workflow for updating the data whenever we receive a new database dump.

Black colors

I unfortunately introduced a bug in #88 where if you load the contributions tab, then change the recipient to "Party", we get some black colors. I have no idea why.

image

@seemantk Maybe you could find the source, I had trouble narrowing it down.

Revert back to textarea for descriptions

Undo commit c6ba380 "Swap textarea for Bootstrap well for .field-description"

This is to restore the thought-out behavior introduced by @seemantk and inadvertently clobbered by me.

The rationale is to have a fixed height box, so the interface is not jumping around when you switch fields. Also, the asterisk makes the "Additional notes" appear below the fold.

Download button(s)

complete tables as CSV for now
maybe later filtered based on "what's visible now"

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.