Low bandwidth mode

This commit is contained in:
rimu 2024-01-08 19:41:32 +13:00
parent 2e3cf467ba
commit 90d5d525ae
13 changed files with 64 additions and 26 deletions

View file

@ -1,5 +1,5 @@
from flask_wtf import FlaskForm, RecaptchaField from flask_wtf import FlaskForm, RecaptchaField
from wtforms import StringField, PasswordField, SubmitField, HiddenField from wtforms import StringField, PasswordField, SubmitField, HiddenField, BooleanField
from wtforms.validators import ValidationError, DataRequired, Email, EqualTo, Length from wtforms.validators import ValidationError, DataRequired, Email, EqualTo, Length
from flask_babel import _, lazy_gettext as _l from flask_babel import _, lazy_gettext as _l
from app.models import User, Community from app.models import User, Community
@ -8,6 +8,7 @@ from app.models import User, Community
class LoginForm(FlaskForm): class LoginForm(FlaskForm):
user_name = StringField(_l('User name'), validators=[DataRequired()]) user_name = StringField(_l('User name'), validators=[DataRequired()])
password = PasswordField(_l('Password'), validators=[DataRequired()]) password = PasswordField(_l('Password'), validators=[DataRequired()])
low_bandwidth_mode = BooleanField(_l('Low bandwidth mode'))
submit = SubmitField(_l('Log In')) submit = SubmitField(_l('Log In'))

View file

@ -62,14 +62,21 @@ def login():
next_page = request.args.get('next') next_page = request.args.get('next')
if not next_page or url_parse(next_page).netloc != '': if not next_page or url_parse(next_page).netloc != '':
next_page = url_for('main.index') next_page = url_for('main.index')
return redirect(next_page) response = make_response(redirect(next_page))
if form.low_bandwidth_mode.data:
response.set_cookie('low_bandwidth', '1', expires=datetime(year=2099, month=12, day=30))
else:
response.set_cookie('low_bandwidth', '0', expires=datetime(year=2099, month=12, day=30))
return response
return render_template('auth/login.html', title=_('Login'), form=form) return render_template('auth/login.html', title=_('Login'), form=form)
@bp.route('/logout') @bp.route('/logout')
def logout(): def logout():
logout_user() logout_user()
return redirect(url_for('main.index')) response = make_response(redirect(url_for('main.index')))
response.set_cookie('low_bandwidth', '0', expires=datetime(year=2099, month=12, day=30))
return response
@bp.route('/register', methods=['GET', 'POST']) @bp.route('/register', methods=['GET', 'POST'])

View file

@ -139,7 +139,7 @@ def show_community(community: Community):
is_moderator=is_moderator, is_owner=is_owner, is_admin=is_admin, mods=mod_list, posts=posts, description=description, is_moderator=is_moderator, is_owner=is_owner, is_admin=is_admin, mods=mod_list, posts=posts, description=description,
og_image=og_image, POST_TYPE_IMAGE=POST_TYPE_IMAGE, POST_TYPE_LINK=POST_TYPE_LINK, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, og_image=og_image, POST_TYPE_IMAGE=POST_TYPE_IMAGE, POST_TYPE_LINK=POST_TYPE_LINK, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING,
SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, etag=f"{community.id}_{hash(community.last_active)}", SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, etag=f"{community.id}_{hash(community.last_active)}",
next_url=next_url, prev_url=prev_url, next_url=next_url, prev_url=prev_url, low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1',
rss_feed=f"https://{current_app.config['SERVER_NAME']}/community/{community.link()}/feed", rss_feed_name=f"{community.title} posts on PieFed") rss_feed=f"https://{current_app.config['SERVER_NAME']}/community/{community.link()}/feed", rss_feed_name=f"{community.title} posts on PieFed")
@ -423,7 +423,7 @@ def add_post(actor):
form.notify_author.data = True form.notify_author.data = True
return render_template('community/add_post.html', title=_('Add post to community'), form=form, community=community, return render_template('community/add_post.html', title=_('Add post to community'), form=form, community=community,
images_disabled=images_disabled, markdown_editor=True) images_disabled=images_disabled, markdown_editor=True, low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/community/<int:community_id>/report', methods=['GET', 'POST']) @bp.route('/community/<int:community_id>/report', methods=['GET', 'POST'])

View file

@ -53,7 +53,7 @@ def index():
active_communities = Community.query.filter_by(banned=False).order_by(desc(Community.last_active)).limit(5).all() active_communities = Community.query.filter_by(banned=False).order_by(desc(Community.last_active)).limit(5).all()
return render_template('index.html', posts=posts, active_communities=active_communities, show_post_community=True, return render_template('index.html', posts=posts, active_communities=active_communities, show_post_community=True,
POST_TYPE_IMAGE=POST_TYPE_IMAGE, POST_TYPE_LINK=POST_TYPE_LINK, POST_TYPE_IMAGE=POST_TYPE_IMAGE, POST_TYPE_LINK=POST_TYPE_LINK, low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1',
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER,
etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url, etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url,
rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed", rss_feed_name=f"Posts on " + g.site.name, rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed", rss_feed_name=f"Posts on " + g.site.name,
@ -93,7 +93,7 @@ def new_posts():
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER,
etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url, etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url,
rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed", rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed",
rss_feed_name=f"Posts on " + g.site.name) rss_feed_name=f"Posts on " + g.site.name, low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/top', methods=['HEAD', 'GET', 'POST']) @bp.route('/top', methods=['HEAD', 'GET', 'POST'])
@ -129,7 +129,7 @@ def top_posts():
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER,
etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url, etag=f"home_{hash(str(g.site.last_active))}", next_url=next_url, prev_url=prev_url,
rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed", rss_feed=f"https://{current_app.config['SERVER_NAME']}/feed",
rss_feed_name=f"Posts on " + g.site.name) rss_feed_name=f"Posts on " + g.site.name, low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/communities', methods=['GET']) @bp.route('/communities', methods=['GET'])
@ -153,7 +153,8 @@ def list_communities():
return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), search=search_param, title=_('Communities'), return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), search=search_param, title=_('Communities'),
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER,
SUBSCRIPTION_OWNER=SUBSCRIPTION_OWNER, topics=topics, topic_id=topic_id, sort_by=sort_by) SUBSCRIPTION_OWNER=SUBSCRIPTION_OWNER, topics=topics, topic_id=topic_id, sort_by=sort_by,
low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/communities/local', methods=['GET']) @bp.route('/communities/local', methods=['GET'])
@ -162,7 +163,8 @@ def list_local_communities():
sort_by = text('community.' + request.args.get('sort_by') if request.args.get('sort_by') else 'community.post_reply_count desc') sort_by = text('community.' + request.args.get('sort_by') if request.args.get('sort_by') else 'community.post_reply_count desc')
communities = Community.query.filter_by(ap_id=None, banned=False) communities = Community.query.filter_by(ap_id=None, banned=False)
return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), title=_('Local communities'), sort_by=sort_by, return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), title=_('Local communities'), sort_by=sort_by,
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER) SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER,
low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/communities/subscribed', methods=['GET']) @bp.route('/communities/subscribed', methods=['GET'])
@ -174,7 +176,8 @@ def list_subscribed_communities():
else: else:
communities = [] communities = []
return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), title=_('Joined communities'), return render_template('list_communities.html', communities=communities.order_by(sort_by).all(), title=_('Joined communities'),
SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, sort_by=sort_by) SUBSCRIPTION_PENDING=SUBSCRIPTION_PENDING, SUBSCRIPTION_MEMBER=SUBSCRIPTION_MEMBER, sort_by=sort_by,
low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/donate') @bp.route('/donate')

View file

@ -177,7 +177,8 @@ def show_post(post_id: int):
canonical=post.ap_id, form=form, replies=replies, THREAD_CUTOFF_DEPTH=constants.THREAD_CUTOFF_DEPTH, canonical=post.ap_id, form=form, replies=replies, THREAD_CUTOFF_DEPTH=constants.THREAD_CUTOFF_DEPTH,
description=description, og_image=og_image, POST_TYPE_IMAGE=constants.POST_TYPE_IMAGE, description=description, og_image=og_image, POST_TYPE_IMAGE=constants.POST_TYPE_IMAGE,
POST_TYPE_LINK=constants.POST_TYPE_LINK, POST_TYPE_ARTICLE=constants.POST_TYPE_ARTICLE, POST_TYPE_LINK=constants.POST_TYPE_LINK, POST_TYPE_ARTICLE=constants.POST_TYPE_ARTICLE,
etag=f"{post.id}_{hash(post.last_active)}", markdown_editor=True) etag=f"{post.id}_{hash(post.last_active)}", markdown_editor=True,
low_bandwidth=request.cookies.get('low_bandwidth', '0') == '1')
@bp.route('/post/<int:post_id>/<vote_direction>', methods=['GET', 'POST']) @bp.route('/post/<int:post_id>/<vote_direction>', methods=['GET', 'POST'])

View file

@ -496,6 +496,11 @@ fieldset legend {
height: auto; height: auto;
} }
.form-check .form-check-input {
position: relative;
top: 4px;
}
.post_reply_form label { .post_reply_form label {
display: none; display: none;
} }

View file

@ -127,6 +127,11 @@ nav, etc which are used site-wide */
} }
} }
.form-check .form-check-input {
position: relative;
top: 4px;
}
.post_reply_form { .post_reply_form {
label { label {
display: none; display: none;

View file

@ -3,7 +3,7 @@
{% if user.deleted %} {% if user.deleted %}
[deleted] [deleted]
{% else %} {% else %}
{% if user.avatar_id %} {% if user.avatar_id and not low_bandwidth %}
<a href="/u/{{ user.link() }}" title="{{ user.ap_id if user.ap_id != none else user.user_name }}"> <a href="/u/{{ user.link() }}" title="{{ user.ap_id if user.ap_id != none else user.user_name }}">
<img src="{{ user.avatar_thumbnail() }}" alt="Avatar" /></a> <img src="{{ user.avatar_thumbnail() }}" alt="Avatar" /></a>
{% endif %} {% endif %}
@ -73,8 +73,7 @@
{% block navbar %} {% block navbar %}
<nav class="navbar navbar-expand-lg navbar-light bg-light fixed-top"> <nav class="navbar navbar-expand-lg navbar-light bg-light fixed-top">
<div class="container-lg"> <div class="container-lg">
<a class="navbar-brand" href="/"><img src="/static/images/logo2.png" alt="Logo" width="50" height="50" />{{ g.site.name }}</a> <a class="navbar-brand" href="/">{% if not low_bandwidth %}<img src="/static/images/logo2.png" alt="Logo" width="50" height="50" />{% endif %}{{ g.site.name }}</a>
{% if current_user.is_authenticated %} {% if current_user.is_authenticated %}
<a class="nav-link d-lg-none" href="/notifications"> <a class="nav-link d-lg-none" href="/notifications">
{% if current_user.unread_notifications %} {% if current_user.unread_notifications %}
@ -138,7 +137,11 @@
</div> </div>
<footer class="footer mt-auto"> <footer class="footer mt-auto">
<p id="timeSpent" class="text-center mt-4" title="This is how long you have spent using PieFed during this month. We hope this use of your time aligns with your priorities and values."></p> <p id="timeSpent" class="text-center mt-4" title="This is how long you have spent using PieFed during this month. We hope this use of your time aligns with your priorities and values."></p>
{% if not low_bandwidth %}
<p class="text-center mt-4"><a href="https://liberapay.com/PieFed/donate"><img alt="Donate using Liberapay" src="https://liberapay.com/assets/widgets/donate.svg"></a></p> <p class="text-center mt-4"><a href="https://liberapay.com/PieFed/donate"><img alt="Donate using Liberapay" src="https://liberapay.com/assets/widgets/donate.svg"></a></p>
{% else %}
<p class="text-center mt-4"><a href="https://liberapay.com/PieFed/donate">Donate with Liberapay</a></p>
{% endif %}
<p class="text-center"><a href="https://patreon.com/PieFed">Donate with Patreon</a></p> <p class="text-center"><a href="https://patreon.com/PieFed">Donate with Patreon</a></p>
<p class="text-center"><a href="https://codeberg.org/rimu/pyfedi">PieFed is free and open source</a></p> <p class="text-center"><a href="https://codeberg.org/rimu/pyfedi">PieFed is free and open source</a></p>
<p class="text-center"><a href="/privacy">Privacy policy</a></p> <p class="text-center"><a href="/privacy">Privacy policy</a></p>
@ -146,13 +149,17 @@
{% endblock %} {% endblock %}
{% block scripts %} {% block scripts %}
{% if not low_bandwidth %}
{{ str(moment.include_moment()).replace('<script>', '<script nonce="' + session['nonce'] + '">')|safe }} {{ str(moment.include_moment()).replace('<script>', '<script nonce="' + session['nonce'] + '">')|safe }}
{{ str(moment.lang(g.locale)).replace('<script>', '<script nonce="' + session['nonce'] + '">')|safe }} {{ str(moment.lang(g.locale)).replace('<script>', '<script nonce="' + session['nonce'] + '">')|safe }}
{% endif %}
{% endblock %} {% endblock %}
{% if not low_bandwidth %}
{{ bootstrap.load_js() }} {{ bootstrap.load_js() }}
{% endif %}
<script type="text/javascript" src="{{ url_for('static', filename='js/htmx.min.js') }}"></script> <script type="text/javascript" src="{{ url_for('static', filename='js/htmx.min.js') }}"></script>
<script type="text/javascript" src="{{ url_for('static', filename='js/scripts.js', changed=getmtime('js/scripts.js')) }}"></script> <script type="text/javascript" src="{{ url_for('static', filename='js/scripts.js', changed=getmtime('js/scripts.js')) }}"></script>
{% if markdown_editor %} {% if markdown_editor and not low_bandwidth %}
<script type="text/javascript" src="{{ url_for('static', filename='js/markdown/downarea.js') }}"></script> <script type="text/javascript" src="{{ url_for('static', filename='js/markdown/downarea.js') }}"></script>
{% endif %} {% endif %}
{% block end_scripts %} {% block end_scripts %}

View file

@ -4,7 +4,7 @@
{% block app_content %} {% block app_content %}
<div class="row"> <div class="row">
<div class="col-12 col-md-8 position-relative main_pane"> <div class="col-12 col-md-8 position-relative main_pane">
{% if community.header_image() != '' %} {% if community.header_image() != '' and not low_bandwidth %}
<div class="community_header" style="background-image: url({{ community.header_image() }});"> <div class="community_header" style="background-image: url({{ community.header_image() }});">
<nav aria-label="breadcrumb" id="breadcrumb_nav" title="Navigation"> <nav aria-label="breadcrumb" id="breadcrumb_nav" title="Navigation">
<ol class="breadcrumb"> <ol class="breadcrumb">
@ -20,7 +20,7 @@
{% include 'community/_notification_toggle.html' %} {% include 'community/_notification_toggle.html' %}
{% endif %} {% endif %}
</h1> </h1>
{% elif community.icon_id %} {% elif community.icon_id and not low_bandwidth %}
<div class="row"> <div class="row">
<nav aria-label="breadcrumb" id="breadcrumb_nav" title="Navigation"> <nav aria-label="breadcrumb" id="breadcrumb_nav" title="Navigation">
<ol class="breadcrumb"> <ol class="breadcrumb">

View file

@ -45,7 +45,7 @@
<thead> <thead>
<tr> <tr>
<th scope="col"> </th> <th scope="col"> </th>
<th scope="col" colspan="2"> <th scope="col" {% if not low_bandwidth %}colspan="2"{% endif %}>
<a href="?sort_by=title{{ ' desc' if sort_by.text == 'community.title' }}" title="{{ _('Sort by name') }}" class="no-underline" rel="nofollow">{{ _('Community') }} <a href="?sort_by=title{{ ' desc' if sort_by.text == 'community.title' }}" title="{{ _('Sort by name') }}" class="no-underline" rel="nofollow">{{ _('Community') }}
<span class="{{ 'fe fe-chevron-up' if sort_by.text == 'community.title' }}{{ 'fe fe-chevron-down' if sort_by.text == 'community.title desc' }}"></span> <span class="{{ 'fe fe-chevron-up' if sort_by.text == 'community.title' }}{{ 'fe fe-chevron-down' if sort_by.text == 'community.title desc' }}"></span>
</a> </a>
@ -81,7 +81,11 @@
{% else %} {% else %}
<a class="btn btn-primary btn-sm" href="/community/{{ community.link() }}/subscribe">{{ _('Join') }}</a> <a class="btn btn-primary btn-sm" href="/community/{{ community.link() }}/subscribe">{{ _('Join') }}</a>
{% endif %}</td> {% endif %}</td>
<td width="46"><a href="/c/{{ community.link() }}"><img src="{{ community.icon_image('tiny') }}" class="community_icon rounded-circle" loading="lazy" /></a></td> {% if not low_bandwidth %}
<td width="46">
<a href="/c/{{ community.link() }}"><img src="{{ community.icon_image('tiny') }}" class="community_icon rounded-circle" loading="lazy" /></a>
</td>
{% endif %}
<td scope="row" class="pl-0"><a href="/c/{{ community.link() }}">{{ community.display_name() }}</a></td> <td scope="row" class="pl-0"><a href="/c/{{ community.link() }}">{{ community.display_name() }}</a></td>
<td>{{ community.post_count }}</td> <td>{{ community.post_count }}</td>
<td>{{ community.post_reply_count }}</td> <td>{{ community.post_reply_count }}</td>

View file

@ -25,8 +25,13 @@
</small></p> </small></p>
<div class="post_image"> <div class="post_image">
{% if post.image_id %} {% if post.image_id %}
{% if low_bandwidth %}
<a href="{{ post.image.view_url() }}" rel="nofollow ugc"><img src="{{ post.image.thumbnail_url() }}" alt="{{ post.image.alt_text }}"
width="{{ post.image.width }}" height="{{ post.image.height }}" /></a>
{% else %}
<a href="{{ post.image.view_url() }}" rel="nofollow ugc"><img src="{{ post.image.view_url() }}" alt="{{ post.image.alt_text }}" <a href="{{ post.image.view_url() }}" rel="nofollow ugc"><img src="{{ post.image.view_url() }}" alt="{{ post.image.alt_text }}"
width="{{ post.image.width }}" height="{{ post.image.height }}" /></a> width="{{ post.image.width }}" height="{{ post.image.height }}" /></a>
{% endif %}
{% else %} {% else %}
<a href="{{ post.url }}" rel="nofollow ugc" target="_blank"><img src="{{ post.url }}" style="max-width: 100%; height: auto;" /></a> <a href="{{ post.url }}" rel="nofollow ugc" target="_blank"><img src="{{ post.url }}" style="max-width: 100%; height: auto;" /></a>
{% endif %} {% endif %}

View file

@ -7,7 +7,7 @@
<div class="voting_buttons"> <div class="voting_buttons">
{% include "post/_post_voting_buttons.html" %} {% include "post/_post_voting_buttons.html" %}
</div> </div>
{% if post.image_id %} {% if post.image_id and not low_bandwidth %}
<div class="thumbnail"> <div class="thumbnail">
{% if post.type == POST_TYPE_LINK %} {% if post.type == POST_TYPE_LINK %}
<a href="{{ post.url }}" rel="nofollow ugc" target="_blank"><img src="{{ post.image.thumbnail_url() }}" <a href="{{ post.url }}" rel="nofollow ugc" target="_blank"><img src="{{ post.image.thumbnail_url() }}"

View file

@ -77,7 +77,7 @@
{% if comment['comment'].author.deleted %} {% if comment['comment'].author.deleted %}
<strong>[deleted]</strong> <strong>[deleted]</strong>
{% else %} {% else %}
{% if comment['comment'].author.avatar_id and comment['comment'].score > -10 %} {% if comment['comment'].author.avatar_id and comment['comment'].score > -10 and not low_bandwidth %}
<a href="/u/{{ comment['comment'].author.link() }}" title="{{ comment['comment'].author.ap_id }}"> <a href="/u/{{ comment['comment'].author.link() }}" title="{{ comment['comment'].author.ap_id }}">
<img src="{{ comment['comment'].author.avatar_image() }}" alt="Avatar" /></a> <img src="{{ comment['comment'].author.avatar_image() }}" alt="Avatar" /></a>
{% endif %} {% endif %}