Skip to content

Commit

Permalink
Update documentation
Browse files Browse the repository at this point in the history
  • Loading branch information
jgallegocalderon committed Apr 4, 2024
0 parents commit 1cf9100
Show file tree
Hide file tree
Showing 172 changed files with 26,767 additions and 0 deletions.
4 changes: 4 additions & 0 deletions .buildinfo
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# Sphinx build info version 1
# This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done.
config: b65771a0dcac5147282ac3c676b35310
tags: 645f666f9bcd5a90fca523b33c5a78b7
Empty file added .nojekyll
Empty file.
9 changes: 9 additions & 0 deletions _sources/architecture.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
# Architecture

HydroGenerate is currently implemented as three separate Python scripts: turbine_calculation.py, hydropower_potential.py, and hydraulic_processing.py. turbine_calculation.py handles turbine efficiency calculations for different turbine types and the calculation of design flow by percent exceedance. hydraulic_processing.py handles head losses calculation in the penstock by Darcy-Weisbach or Hazen Williams. The scripts use classes and functions for different implementation.

The code is modular, and several steps were followed to facilitate the process of integrating functionality. Classes are single-function, small, and simple to facilitate overview of the code. Abstract Base Classes (ABC) are used to group methods that belong to the same category, e.g., calculation of efficiency of different turbine types. All turbine efficiency calculations belong to the same abstract class and use a method that is inherited from the ABC class. ABC classes facilitate the addition of new methods, e.g., the efficiency of a new turbine. The efficiency of a new turbine can be included in the code without modifying any of the existing turbines, minimizing the opportunity for errors while keeping all turbine efficiency methods under the same class. This facilitates code reuse and modularity by enforcing consistency. All turbine types in HydroGenerate must implement the method turbine_calculator. The same principle is followed by all other abstract classes. In some instances, an ABC is defined, and a single class is implemented. This reflects the intention to add additional methods. For example, the class Cost contains a single model (described in the documentation) but the addition of others models as they become available is anticipated.

New features, functionalities, or additional work should not affect an existing feature. While it is likely that new features utilizing additional variables will require modifying the variable definitions for existing classes, this should not impact the already implemented methods or functions. The existing code in HydroGenerate contains extensive comments along all code files that document what the variables being used are, what chunk of codes are doing, and why (when needed) certain implementations were used. New code added to HydroGenerate should follow a similar approach.

Currently, users can access all functionalities by using a single function (hydropower_potential). Future development could maintain interactions via a single function, however, adding more user executable functions is not discouraged.
3 changes: 3 additions & 0 deletions _sources/hydro_kinetics.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Hydrokinetics

For hydrokinetic assessments the only required input is the average velocity in the river section. Additionally, the users can select among different hydrokinetic turbine types and vary the dimensions to evaluate energy potential.
1 change: 1 addition & 0 deletions _sources/hydrogenerate_api_call.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
# Using the Water Services API
31 changes: 31 additions & 0 deletions _sources/hydrogenerate_intro.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# Getting started

HG can currently compute hydropower under three hydropower types: Basic, Diversion, and Hydrokinetic. The file HydroGenerate_Workflow.ipynb included in the HG’s GitHub repository (https://github.com/IdahoLabResearch/HydroGenerate/blob/main/examples/HydroGenerate_Workflow.ipynb) walks used through these three calculations.

Basic hydropower calculation:

Required inputs: Hydraulic head, flow, rated power. In the basic calculation mode, users can input two of these three variables and HG will calculate the third.

Diversion

Required inputs: Hydraulic head, flow.

Optional inputs: all the inputs listed in Table 1, except those used only for hydrokinetic estimations.

Computation Steps:

Compute head losses: the procedure and available options for head loss calculation in HG for each type of hydropower estimation is described in Appendix A Head Loss Calculations.

Select the turbine type: Based on the net hydraulic head, HG will suggest a recommended turbine type by following 3.

Define the design flow (Qd). The procedure for this step is explained in Appendix B Design Flow Selection.

Compute the efficiency of the turbine at flows above and below the design flow and estimate power for the value (s) of flow provided the user. Turbine efficiency is calculated following the methodology presented in the Clean Energy Project Analysis electronic textbook ​(CANMET Energy Technology Center, 2004)​ (included in Appendix C Turbine Efficiency Calculation)

Compute the overall efficiency of the system. The overall efficiency of the system is computed as the turbine efficiency (calculated in step 4) times the Generator efficiency.

Compute estimated power potential using Equation 1.

Compute all economic parameters (O&M, initial capital cost, revenue).

Output: the list of outputs will depend on the inputs used. In the most complete case, the output list includes all the variables listed in Table 2, except for those resulting from hydrokinetic calculations.
3 changes: 3 additions & 0 deletions _sources/hydropower_potential.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Hydropower potential

The hydropower potential ...
62 changes: 62 additions & 0 deletions _sources/index.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
# HydroGenerate: Hydropower Potential Estimation

**HydroGenerate** is an open-source python library that has the estimates hydropower generation based on head height and flow rate either provided by the user or received from United States Geological Survey (USGS) water data services. The tool calculates the efficiency as a function of flow based on the turbine type either selected by the user or estimated based on the “head” provided by the user.

## Quick Start

**HydroGenerate** can be installed in your local environment using `pip install HydroGenerate`. In its most basic usage, the user needs to provide one value of flow in cubic-ft-sec (cfs) and head (ft). The function `calculate_hp_potential` is the main interface for the hydropower potential calculation using different types of inputs (float, numpy array, and pandas dataframe), and several attributes. More advance usage can be found in the user guide.

```
# Local imports
from HydroGenerate.hydropower_potential import *
# 1.1) Calculate power from a given head and flow
flow = 8000 # given flow, in cfs
head = 20 # head, in ft
power = None
hp = calculate_hp_potential(flow= flow,
head= head,
rated_power= power)
print("Hydropower potential is {} kW".format(round(hp.rated_power, 0)))
```

The results are returned in an object with multiple attributes. In the example above, `hp.power` gives the estimated potential for the given flow and head. If a time-series is provided, then a time-series of power will be available.

## Giving credit

HydroGenerate was built with support from the USDOE Office of Energy Efficiency and Renewable Energy (EERE). For more information please refer to the [OSTI webpage](https://www.osti.gov/biblio/1829986).

**Authors**
```
Bhaskar Mitra
Juan Gallego-Calderon
Shiloh Elliott
Thomas M. Mosier
Camilo J. Bastidas Pacheco
```

**Citation**

If you are using our repository kindly use the following citation format.

_Bibtex_
```
@misc{osti_1829986,
title = {Hydrogenerate: Open Source Python Tool To Estimate Hydropower Generation Time-series, Version 3.6 or newer},
author = {Mitra, Bhaskar and Gallego-Calderon, Juan F. and Elliott, Shiloh N and Mosier, Thomas M and Bastidas Pacheco, Camilo Jose and USDOE Office of Energy Efficiency and Renewable Energy},
abstractNote = {Hydropower is one of the most mature forms of renewable energy generation. The United States (US) has almost 103 GW of installed, with 80 GW of conventional generation and 23 GW of pumped hydropower [1]. Moreover, the potential for future development on Non-Powered Dams is up to 10 GW. With the US setting its goals to become carbon neutral [2], more renewable energy in the form of hydropower needs to be integrated with the grid. Currently, there are no publicly available tool that can estimate the hydropower potential for existing hydropower dams or other non-powered dams. The HydroGenerate is an open-source python library that has the capability of estimating hydropower generation based on flow rate either provided by the user or received from United States Geological Survey (USGS) water data services. The tool calculates the efficiency as a function of flow based on the turbine type either selected by the user or estimated based on the “head” provided by the user.},
url = {https://www.osti.gov//servlets/purl/1829986},
doi = {10.11578/dc.20211112.1},
url = {https://www.osti.gov/biblio/1829986}, year = {2021},
month = {10},
note =
}
```
47 changes: 47 additions & 0 deletions _sources/installation.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# Installation

**HydroGenerate** is offered as a python package. This means that the classes and utilities can be used anywhere in your system, without risks of making unwanted changes to the core code in the repo, issues with finsing the module in path, etc.

**HydroGenerate** can be installed by downloading the source code from GitHub or via the PyPI package manager using pip.

For those interested only in using the code, the simplest way to obtain it is with pip by using this command:

```
pip install HydroGenerate
```

## For developers


1. Clone the repo:

```
git clone git@github.com:IdahoLabResearch/HydroGenerate.git
cd HydroGenerate
```

2. It is recommended that a dedicated conda environment be created for developing/using this repo and prior to the installation below.

```
conda create --name hat-env python=3.6
```

To activate the environment, execute the following command:

```
conda activate hat-env
```

3. Install the package in your environment:

```
pip install -e .
```

**Optional**

4. Install jupyter lab in your new environment
```
conda install -c conda-forge jupyterlab
```

Large diffs are not rendered by default.

27 changes: 27 additions & 0 deletions _sphinx_design_static/design-tabs.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
var sd_labels_by_text = {};

function ready() {
const li = document.getElementsByClassName("sd-tab-label");
for (const label of li) {
syncId = label.getAttribute("data-sync-id");
if (syncId) {
label.onclick = onLabelClick;
if (!sd_labels_by_text[syncId]) {
sd_labels_by_text[syncId] = [];
}
sd_labels_by_text[syncId].push(label);
}
}
}

function onLabelClick() {
// Activate other inputs with the same sync id.
syncId = this.getAttribute("data-sync-id");
for (label of sd_labels_by_text[syncId]) {
if (label === this) continue;
label.previousElementSibling.checked = true;
}
window.localStorage.setItem("sphinx-design-last-tab", syncId);
}

document.addEventListener("DOMContentLoaded", ready, false);
Binary file added _static/HG_horizontal.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added _static/HG_icon.ico
Binary file not shown.
134 changes: 134 additions & 0 deletions _static/_sphinx_javascript_frameworks_compat.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
/*
* _sphinx_javascript_frameworks_compat.js
* ~~~~~~~~~~
*
* Compatability shim for jQuery and underscores.js.
*
* WILL BE REMOVED IN Sphinx 6.0
* xref RemovedInSphinx60Warning
*
*/

/**
* select a different prefix for underscore
*/
$u = _.noConflict();


/**
* small helper function to urldecode strings
*
* See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/decodeURIComponent#Decoding_query_parameters_from_a_URL
*/
jQuery.urldecode = function(x) {
if (!x) {
return x
}
return decodeURIComponent(x.replace(/\+/g, ' '));
};

/**
* small helper function to urlencode strings
*/
jQuery.urlencode = encodeURIComponent;

/**
* This function returns the parsed url parameters of the
* current request. Multiple values per key are supported,
* it will always return arrays of strings for the value parts.
*/
jQuery.getQueryParameters = function(s) {
if (typeof s === 'undefined')
s = document.location.search;
var parts = s.substr(s.indexOf('?') + 1).split('&');
var result = {};
for (var i = 0; i < parts.length; i++) {
var tmp = parts[i].split('=', 2);
var key = jQuery.urldecode(tmp[0]);
var value = jQuery.urldecode(tmp[1]);
if (key in result)
result[key].push(value);
else
result[key] = [value];
}
return result;
};

/**
* highlight a given string on a jquery object by wrapping it in
* span elements with the given class name.
*/
jQuery.fn.highlightText = function(text, className) {
function highlight(node, addItems) {
if (node.nodeType === 3) {
var val = node.nodeValue;
var pos = val.toLowerCase().indexOf(text);
if (pos >= 0 &&
!jQuery(node.parentNode).hasClass(className) &&
!jQuery(node.parentNode).hasClass("nohighlight")) {
var span;
var isInSVG = jQuery(node).closest("body, svg, foreignObject").is("svg");
if (isInSVG) {
span = document.createElementNS("http://www.w3.org/2000/svg", "tspan");
} else {
span = document.createElement("span");
span.className = className;
}
span.appendChild(document.createTextNode(val.substr(pos, text.length)));
node.parentNode.insertBefore(span, node.parentNode.insertBefore(
document.createTextNode(val.substr(pos + text.length)),
node.nextSibling));
node.nodeValue = val.substr(0, pos);
if (isInSVG) {
var rect = document.createElementNS("http://www.w3.org/2000/svg", "rect");
var bbox = node.parentElement.getBBox();
rect.x.baseVal.value = bbox.x;
rect.y.baseVal.value = bbox.y;
rect.width.baseVal.value = bbox.width;
rect.height.baseVal.value = bbox.height;
rect.setAttribute('class', className);
addItems.push({
"parent": node.parentNode,
"target": rect});
}
}
}
else if (!jQuery(node).is("button, select, textarea")) {
jQuery.each(node.childNodes, function() {
highlight(this, addItems);
});
}
}
var addItems = [];
var result = this.each(function() {
highlight(this, addItems);
});
for (var i = 0; i < addItems.length; ++i) {
jQuery(addItems[i].parent).before(addItems[i].target);
}
return result;
};

/*
* backward compatibility for jQuery.browser
* This will be supported until firefox bug is fixed.
*/
if (!jQuery.browser) {
jQuery.uaMatch = function(ua) {
ua = ua.toLowerCase();

var match = /(chrome)[ \/]([\w.]+)/.exec(ua) ||
/(webkit)[ \/]([\w.]+)/.exec(ua) ||
/(opera)(?:.*version|)[ \/]([\w.]+)/.exec(ua) ||
/(msie) ([\w.]+)/.exec(ua) ||
ua.indexOf("compatible") < 0 && /(mozilla)(?:.*? rv:([\w.]+)|)/.exec(ua) ||
[];

return {
browser: match[ 1 ] || "",
version: match[ 2 ] || "0"
};
};
jQuery.browser = {};
jQuery.browser[jQuery.uaMatch(navigator.userAgent).browser] = true;
}
Loading

0 comments on commit 1cf9100

Please sign in to comment.