Skip to content

Commit

Permalink
Add UI app boilerplate, including dynamic updates
Browse files Browse the repository at this point in the history
  • Loading branch information
Lants committed Feb 16, 2022
1 parent cc25c38 commit 70dcc2c
Show file tree
Hide file tree
Showing 11 changed files with 502 additions and 0 deletions.
152 changes: 152 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,152 @@
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
*$py.class

# C extensions
*.so

# Distribution / packaging
.Python
build/
develop-eggs/
dist/
downloads/
eggs/
.eggs/
lib/
lib64/
parts/
sdist/
var/
wheels/
share/python-wheels/
*.egg-info/
.installed.cfg
*.egg
MANIFEST

# PyInstaller
# Usually these files are written by a python script from a template
# before PyInstaller builds the exe, so as to inject date/other infos into it.
*.manifest
*.spec

# Installer logs
pip-log.txt
pip-delete-this-directory.txt

# Unit test / coverage reports
htmlcov/
.tox/
.nox/
.coverage
.coverage.*
.cache
nosetests.xml
coverage.xml
*.cover
*.py,cover
.hypothesis/
.pytest_cache/
cover/

# Translations
*.mo
*.pot

# Django stuff:
*.log
local_settings.py
db.sqlite3
db.sqlite3-journal

# Flask stuff:
instance/
.webassets-cache

# Scrapy stuff:
.scrapy

# Sphinx documentation
docs/_build/

# PyBuilder
.pybuilder/
target/

# Jupyter Notebook
.ipynb_checkpoints

# IPython
profile_default/
ipython_config.py

# pyenv
# For a library or package, you might want to ignore these files since the code is
# intended to run in multiple environments; otherwise, check them in:
# .python-version

# pipenv
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
# However, in case of collaboration, if having platform-specific dependencies or dependencies
# having no cross-platform support, pipenv may install dependencies that don't work, or not
# install all needed dependencies.
#Pipfile.lock

# poetry
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
# This is especially recommended for binary packages to ensure reproducibility, and is more
# commonly ignored for libraries.
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
#poetry.lock

# PEP 582; used by e.g. github.com/David-OConnor/pyflow
__pypackages__/

# Celery stuff
celerybeat-schedule
celerybeat.pid

# SageMath parsed files
*.sage.py

# Environments
.env
.venv
env/
venv/
ENV/
env.bak/
venv.bak/

# Spyder project settings
.spyderproject
.spyproject

# Rope project settings
.ropeproject

# mkdocs documentation
/site

# mypy
.mypy_cache/
.dmypy.json
dmypy.json

# Pyre type checker
.pyre/

# pytype static type analyzer
.pytype/

# Cython debug symbols
cython_debug/

# PyCharm
# JetBrains specific template is maintained in a separate JetBrains.gitignore that can
# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
# and can be added to the global gitignore or merged into this file. For a more nuclear
# option (not recommended) you can uncomment the following to ignore the entire idea folder.
#.idea/
93 changes: 93 additions & 0 deletions src/UI_Integrations/UI.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
# Before running, set env variables:
# export FLASK_APP=UI.py
# export FLASK_DEBUG=1 for true, 0 for false
# flask run

# Now you can pull up localhost:5000 in your browser to view the webpage. Refresh to see changes.

# Note: DO NOT SET DEBUG MODE IF DEPLOYING PUBLICLY!!! ---------------------------------------------------
# Debug mode allows for arbitrary code executions from the deployed site. log4j flashbacks...

# Disclaimer: A majority of this boilerplate was written alongside the YouTube tutorials by Corey Schafer

from flask import Flask, render_template, url_for
from turbo_flask import Turbo
from datetime import datetime, timedelta
from time import sleep
import threading

app = Flask(__name__)
turbo = Turbo(app)

def test_url(self):
with app.app_context(), app.test_request_context():
self.assertEqual('/', url_for('root.home'))

test_data = [
{
'id': 0,
'content': 'data 0'
},
{
'id': 1,
'content': 'data 1'
}
]

# For Spotify, retrieve data and format it something like this:
# spotify_API_retrieve = Spotify.retrieve() ... blablabla
spotify_data = [
{
'title': 'Never Gonna Give You Up',
'artist': 'Rick Astley',
'album': 'Whenever You Need Somebody',
'time_elapsed': str(timedelta(seconds=72)), # Replace 72 with spotify_API_retrieve.song_length or whatever
'length': str(timedelta(seconds=212)), # Replace 212 with however many seconds long the song is
# NOTE: You must move time_elapsed to the inject_load function below for dynamic updates
}
]


@app.route("/")
@app.route("/home")
@app.route("/index.html")
def home():
return render_template("home.html")


@app.route("/smol")
def smol():
return render_template("smol.html", test_data=test_data)

@app.route("/chungus")
def chungus():

return render_template("chungus.html")


@app.context_processor
def inject_load():
dynamic_vars = {}

# Add dictionaries for dynamic data here


dynamic_vars['chungus_current_time'] = datetime.now().strftime("%H:%M:%S")
dynamic_vars['spotify_data'] = spotify_data

return dynamic_vars

def update_load():
with app.app_context():
while True:
sleep(1)
turbo.push(turbo.replace(render_template('chungus_display_1.html'), 'display-1')) # look into the "to" argument for client-specific updates

@app.before_first_request
def before_first_request():
threading.Thread(target=update_load).start()



# if __name__ == '__main__':
# app.run(debug=True)
Binary file added src/UI_Integrations/images/favicon.ico
Binary file not shown.
22 changes: 22 additions & 0 deletions src/UI_Integrations/snippets/main.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<!-- Snippets from https://github.com/CoreyMSchafer/code_snippets/blob/master/Python/Flask_Blog/snippets/navigation.html -->

<main role="main" class="container">
<div class="row">
<div class="col-md-8">
{% block content %}{% endblock %}
</div>
<div class="col-md-4">
<div class="content-section">
<h3>Our Sidebar</h3>
<p class='text-muted'>You can put any information here you'd like.
<ul class="list-group">
<li class="list-group-item list-group-item-light">Latest Posts</li>
<li class="list-group-item list-group-item-light">Announcements</li>
<li class="list-group-item list-group-item-light">Calendars</li>
<li class="list-group-item list-group-item-light">etc</li>
</ul>
</p>
</div>
</div>
</div>
</main>
23 changes: 23 additions & 0 deletions src/UI_Integrations/snippets/navigation.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
<!-- Snippets from https://github.com/CoreyMSchafer/code_snippets/blob/master/Python/Flask_Blog/snippets/navigation.html -->

<header class="site-header">
<nav class="navbar navbar-expand-md navbar-dark bg-steel fixed-top">
<div class="container">
<a class="navbar-brand mr-4" href="/">Flask Blog</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarToggle" aria-controls="navbarToggle" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarToggle">
<div class="navbar-nav mr-auto">
<a class="nav-item nav-link" href="/">Home</a>
<a class="nav-item nav-link" href="/about">About</a>
</div>
<!-- Navbar Right Side -->
<div class="navbar-nav">
<a class="nav-item nav-link" href="/login">Login</a>
<a class="nav-item nav-link" href="/register">Register</a>
</div>
</div>
</div>
</nav>
</header>
80 changes: 80 additions & 0 deletions src/UI_Integrations/static/main.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
body {
background: #fafafa;
color: #333333;
margin-top: 5rem;
}

h1, h2, h3, h4, h5, h6 {
color: #444444;
}

.bg-steel {
background-color: #5f788a;
}

.site-header .navbar-nav .nav-link {
color: #cbd5db;
}

.site-header .navbar-nav .nav-link:hover {
color: #ffffff;
}

.site-header .navbar-nav .nav-link.active {
font-weight: 500;
}

.content-section {
background: #ffffff;
padding: 10px 20px;
border: 1px solid #dddddd;
border-radius: 3px;
margin-bottom: 20px;
}

.article-title {
color: #444444;
}

a.article-title:hover {
color: #428bca;
text-decoration: none;
}

.article-content {
white-space: pre-line;
}

.article-img {
height: 65px;
width: 65px;
margin-right: 16px;
}

.article-metadata {
padding-bottom: 1px;
margin-bottom: 4px;
border-bottom: 1px solid #e3e3e3
}

.article-metadata a:hover {
color: #333;
text-decoration: none;
}

.article-svg {
width: 25px;
height: 25px;
vertical-align: middle;
}

.account-img {
height: 125px;
width: 125px;
margin-right: 20px;
margin-bottom: 16px;
}

.account-heading {
font-size: 2.5rem;
}
Loading

0 comments on commit 70dcc2c

Please sign in to comment.