Css Editor made with very minimal js. Distribusi Workflow currently very buggy
This commit is contained in:
parent
fbd1887753
commit
dab3b1ebdf
@ -11,9 +11,12 @@ This particular work in progress project is an attempt to make distribusi into a
|
|||||||
This project is made for Autonomous Practices at the WDKA in Rotterdam.
|
This project is made for Autonomous Practices at the WDKA in Rotterdam.
|
||||||
## Work in progress
|
## Work in progress
|
||||||
|
|
||||||
~~Nothing is working yet but I need to do this project in smaller steps then everything in one go.~~
|
1. ~~Nothing is working yet but I need to do this project in smaller steps then everything in one go.~~
|
||||||
So far, in this project you can make a user, upload a zip, make a website name and have distribusi
|
2. So far, in this project you can make a user, upload a zip, make a website name and have distribusi
|
||||||
run it for you.
|
run it for you.
|
||||||
|
3. There is a css editor and a theme selector, but very buggy.
|
||||||
|
I am still developing a lot of features and I want to finish them first before
|
||||||
|
I do a first pass, fixing issues and refactoring code.
|
||||||
|
|
||||||
## Start your engines!
|
## Start your engines!
|
||||||
|
|
||||||
|
21
verse/forms/editorform.py
Normal file
21
verse/forms/editorform.py
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
"""Form to save your CSS editor work."""
|
||||||
|
from wtforms import (
|
||||||
|
StringField,
|
||||||
|
TextAreaField,
|
||||||
|
SubmitField,
|
||||||
|
)
|
||||||
|
|
||||||
|
from wtforms import validators
|
||||||
|
from wtforms.validators import Length
|
||||||
|
from flask_wtf import FlaskForm
|
||||||
|
|
||||||
|
|
||||||
|
class EditorForm(FlaskForm):
|
||||||
|
"""Css editor form class."""
|
||||||
|
|
||||||
|
cssname = StringField(
|
||||||
|
"fill in a name for your css style:",
|
||||||
|
validators=[validators.InputRequired(), Length(5, 200)],
|
||||||
|
)
|
||||||
|
css = TextAreaField()
|
||||||
|
submit = SubmitField("Save")
|
@ -42,6 +42,7 @@ from forms.registerform import RegisterForm
|
|||||||
from forms.uploadform import UploadForm
|
from forms.uploadform import UploadForm
|
||||||
from forms.distribusiform import DistribusiForm
|
from forms.distribusiform import DistribusiForm
|
||||||
from forms.themeform import ThemeForm
|
from forms.themeform import ThemeForm
|
||||||
|
from forms.editorform import EditorForm
|
||||||
|
|
||||||
# Tada!
|
# Tada!
|
||||||
from distribusi.cli import build_argparser
|
from distribusi.cli import build_argparser
|
||||||
@ -138,20 +139,21 @@ def distribusi():
|
|||||||
zipfilename = "{}.zip".format(user.distribusiname)
|
zipfilename = "{}.zip".format(user.distribusiname)
|
||||||
userfolder = os.path.join("stash", user.distribusiname)
|
userfolder = os.path.join("stash", user.distribusiname)
|
||||||
unzipfile = os.path.join(userfolder, zipfilename)
|
unzipfile = os.path.join(userfolder, zipfilename)
|
||||||
|
if os.path.exists(unzipfile):
|
||||||
with zipfile.ZipFile(unzipfile, "r") as zip_ref:
|
with zipfile.ZipFile(unzipfile, "r") as zip_ref:
|
||||||
# To do, replace extractall with inspection and extract
|
# To do, replace extractall with inspection and extract
|
||||||
zip_ref.extractall(userfolder)
|
zip_ref.extractall(userfolder)
|
||||||
|
if os.path.exists(unzipfile):
|
||||||
os.remove(os.path.join(userfolder, zipfilename))
|
os.remove(os.path.join(userfolder, zipfilename))
|
||||||
# To Do: Make sure nothing can be executed from the upload folder
|
# To Do: Make sure nothing can be executed from the upload folder
|
||||||
# add the css file
|
# add the css file
|
||||||
cssfile = ""
|
cssfile = ""
|
||||||
for filename in os.listdir(userfolder):
|
for filename in os.listdir(userfolder):
|
||||||
if filename.endswith('.css'):
|
if filename.endswith(".css"):
|
||||||
cssfile = os.path.join(userfolder, filename)
|
cssfile = os.path.join(userfolder, filename)
|
||||||
|
|
||||||
parser = build_argparser()
|
parser = build_argparser()
|
||||||
args = parser.parse_args(['-s', cssfile])
|
args = parser.parse_args(["-s", cssfile])
|
||||||
distribusify(args, userfolder)
|
distribusify(args, userfolder)
|
||||||
return redirect(url_for("index"))
|
return redirect(url_for("index"))
|
||||||
template = render_template(
|
template = render_template(
|
||||||
@ -196,7 +198,7 @@ def upload():
|
|||||||
return template
|
return template
|
||||||
|
|
||||||
|
|
||||||
@APP.route("/theme", methods=["POST"])
|
@APP.route("/theme", methods=["GET", "POST"])
|
||||||
@login_required
|
@login_required
|
||||||
def theme():
|
def theme():
|
||||||
uploadform = UploadForm()
|
uploadform = UploadForm()
|
||||||
@ -220,6 +222,30 @@ def theme():
|
|||||||
return template
|
return template
|
||||||
|
|
||||||
|
|
||||||
|
@APP.route("/editor", methods=["GET", "POST"])
|
||||||
|
@login_required
|
||||||
|
def editor():
|
||||||
|
editorform = EditorForm()
|
||||||
|
user = User.query.filter_by(email=current_user.email).first()
|
||||||
|
files_uploaded = True
|
||||||
|
if user.distribusiname is None:
|
||||||
|
files_uploaded = False
|
||||||
|
print("no folder to add css to!")
|
||||||
|
if editorform.validate_on_submit():
|
||||||
|
userfolder = os.path.join("stash", user.distribusiname)
|
||||||
|
cssfilename = "{}.css".format(editorform.cssname.data)
|
||||||
|
with open(os.path.join(userfolder, cssfilename), 'w') as cssfile:
|
||||||
|
cssfile.write(editorform.css.data)
|
||||||
|
cssfile.close
|
||||||
|
|
||||||
|
template = render_template(
|
||||||
|
"editor.html",
|
||||||
|
files_uploaded=files_uploaded,
|
||||||
|
editorform=editorform,
|
||||||
|
)
|
||||||
|
return template
|
||||||
|
|
||||||
|
|
||||||
@APP.route("/stash/<path:path>")
|
@APP.route("/stash/<path:path>")
|
||||||
def distribusistash(path):
|
def distribusistash(path):
|
||||||
return send_from_directory("stash", path)
|
return send_from_directory("stash", path)
|
||||||
|
34
verse/static/css/editor.css
Normal file
34
verse/static/css/editor.css
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
.editareas {
|
||||||
|
width: 100%;
|
||||||
|
margin: auto;
|
||||||
|
display: flex;
|
||||||
|
justify-content: flex-start;
|
||||||
|
}
|
||||||
|
.editarea {
|
||||||
|
border: 1px solid #E0B0FF;
|
||||||
|
margin-right: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.editor {
|
||||||
|
min-width: 40%;
|
||||||
|
}
|
||||||
|
|
||||||
|
textarea {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
box-sizing: border-box;
|
||||||
|
min-height: 250px;
|
||||||
|
overflow: scroll;
|
||||||
|
background: #E0B0FF;
|
||||||
|
outline: none;
|
||||||
|
font-family: Courier, sans-serif;
|
||||||
|
font-size: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
iframe {
|
||||||
|
bottom: 0;
|
||||||
|
position: relative;
|
||||||
|
margin-top: 1em;
|
||||||
|
width: 100%;
|
||||||
|
height: 30em;
|
||||||
|
}
|
@ -20,7 +20,7 @@ div#login form {
|
|||||||
padding-right: 15%;
|
padding-right: 15%;
|
||||||
}
|
}
|
||||||
|
|
||||||
div#login input[type=text], input[type=password]{
|
input[type=text], input[type=password], input[type=file]{
|
||||||
background-color: #383C4A;
|
background-color: #383C4A;
|
||||||
color: white;
|
color: white;
|
||||||
border: 1px solid #E0B0FF;
|
border: 1px solid #E0B0FF;
|
||||||
@ -72,17 +72,24 @@ fieldset.required {
|
|||||||
border: none;
|
border: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.button input {
|
input {
|
||||||
border: none;
|
border: none;
|
||||||
background: #E0B0FF;
|
background: #E0B0FF;
|
||||||
text-decoration: none;
|
text-decoration: none;
|
||||||
margin: 1px;
|
margin: 1px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.button input:hover {
|
input:hover {
|
||||||
background: #60337F;
|
background: #60337F;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
input[type="submit"]:disabled:hover,
|
||||||
|
input[type="submit"]:disabled,
|
||||||
|
input[type="submit"]:disabled:focus {
|
||||||
|
background: #777777;
|
||||||
|
color: #d28cff;
|
||||||
|
}
|
||||||
|
|
||||||
/* unvisited link */
|
/* unvisited link */
|
||||||
a:link {
|
a:link {
|
||||||
color: red;
|
color: red;
|
||||||
|
14
verse/static/js/editorupdate.js
Normal file
14
verse/static/js/editorupdate.js
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
function update() {
|
||||||
|
|
||||||
|
var html = document.getElementById("html");
|
||||||
|
var css = document.getElementById("css");
|
||||||
|
var code = document.getElementById("code").contentWindow.document;
|
||||||
|
|
||||||
|
document.body.onkeyup = function(){
|
||||||
|
code.open();
|
||||||
|
code.writeln(html.value+"<style>"+css.value+"</style>");
|
||||||
|
code.close();
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
update();
|
@ -5,7 +5,7 @@
|
|||||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||||
<title>Autonomous Practices X Distribusi-Verse</title>
|
<title>Autonomous Practices X Distribusi-Verse</title>
|
||||||
<link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='css/style.css')}}">
|
<link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='css/style.css')}}">
|
||||||
<link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='css/arrows.css')}}">
|
|
||||||
<link rel="shortcut icon" href="{{ url_for('static', filename='icons/favicon.ico') }}">
|
<link rel="shortcut icon" href="{{ url_for('static', filename='icons/favicon.ico') }}">
|
||||||
<link rel="apple-touch-icon" sizes="180x180" href="{{ url_for('static', filename='icons/apple-touch-icon.png')}}">
|
<link rel="apple-touch-icon" sizes="180x180" href="{{ url_for('static', filename='icons/apple-touch-icon.png')}}">
|
||||||
<link rel="icon" type="image/png" sizes="32x32" href="{{ url_for('static', filename='icons/favicon-32x32.png')}}">
|
<link rel="icon" type="image/png" sizes="32x32" href="{{ url_for('static', filename='icons/favicon-32x32.png')}}">
|
||||||
|
@ -48,7 +48,7 @@
|
|||||||
<img src="{{ url_for('static', filename='svg/arrow_2.svg')}}" />
|
<img src="{{ url_for('static', filename='svg/arrow_2.svg')}}" />
|
||||||
<div id="edit" class="workflow">
|
<div id="edit" class="workflow">
|
||||||
<h3>(Optional) Step 3: Edit</h3>
|
<h3>(Optional) Step 3: Edit</h3>
|
||||||
<p>go to CSS editor</p>
|
<a href="/editor"><p>Go to CSS editor</p></a>
|
||||||
</div>
|
</div>
|
||||||
<img src="{{ url_for('static', filename='svg/arrow_3.svg')}}" />
|
<img src="{{ url_for('static', filename='svg/arrow_3.svg')}}" />
|
||||||
<div id="distribusi" class="workflow">
|
<div id="distribusi" class="workflow">
|
||||||
|
43
verse/templates/editor.html
Normal file
43
verse/templates/editor.html
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
{% extends "base.html" %}
|
||||||
|
{% block main %}
|
||||||
|
<form method="POST" enctype="multipart/form-data" action="{{ url_for('editor') }}">
|
||||||
|
<div class="editareas">
|
||||||
|
<div class="editarea editor">
|
||||||
|
<fieldset class="required">
|
||||||
|
<textarea id="html" placeholder="Write some test HTML here"></textarea>
|
||||||
|
</fieldset>
|
||||||
|
</div>
|
||||||
|
{{ editorform.csrf_token }}
|
||||||
|
<div class="editarea editor">
|
||||||
|
<fieldset class="required">
|
||||||
|
{{ editorform.css(placeholder="Try out your CSS here") }}
|
||||||
|
{% for message in editorform.css.errors %}
|
||||||
|
<div class="error">{{ message }}</div>
|
||||||
|
{% endfor %}
|
||||||
|
</fieldset>
|
||||||
|
</div>
|
||||||
|
<div class="editarea">
|
||||||
|
{% if files_uploaded %}
|
||||||
|
<fieldset class="required">
|
||||||
|
{{ editorform.cssname.label }}
|
||||||
|
{{ editorform.cssname }}
|
||||||
|
{% for message in editorform.cssname.errors %}
|
||||||
|
<div class="error">{{ message }}</div>
|
||||||
|
{% endfor %}
|
||||||
|
</fieldset>
|
||||||
|
<fieldset class="button required">
|
||||||
|
{{ editorform.submit }}
|
||||||
|
</fieldset>
|
||||||
|
{% else %}
|
||||||
|
<p>
|
||||||
|
You need to upload your files first before you can save a css file.
|
||||||
|
</p>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
<iframe id="code"></iframe>
|
||||||
|
|
||||||
|
<link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='css/editor.css')}}">
|
||||||
|
<script src="{{ url_for('static', filename='js/editorupdate.js')}}"></script>
|
||||||
|
{% endblock main %}
|
Loading…
Reference in New Issue
Block a user