mirror of
				https://github.com/HS-Flensburg-Klein/hausarbeit-hikmat_galan_neumann_stark_becker
				synced 2025-04-04 21:43:31 +00:00 
			
		
		
		
	update
This commit is contained in:
		
							parent
							
								
									7893cbcb6f
								
							
						
					
					
						commit
						3387056120
					
				@ -18,6 +18,6 @@ class LocationAdmin(admin.ModelAdmin):
 | 
			
		||||
    pass
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@admin.register(Day)
 | 
			
		||||
class DayAdmin(admin.ModelAdmin):
 | 
			
		||||
@admin.register(NewsArticle)
 | 
			
		||||
class NewsArticleAdmin(admin.ModelAdmin):
 | 
			
		||||
    pass
 | 
			
		||||
 | 
			
		||||
@ -9,9 +9,7 @@ from datetime import date
 | 
			
		||||
class MenuForm(forms.ModelForm):
 | 
			
		||||
    class Meta:
 | 
			
		||||
        model = Menu
 | 
			
		||||
        fields = ['art', 'name', 'price', 'allergens', 'types', 'day']
 | 
			
		||||
        fields = ['location', 'art', 'name', 'price', 'allergens', 'types', 'day']
 | 
			
		||||
        widgets = {
 | 
			
		||||
            'types': forms.CheckboxSelectMultiple(choices=TYPES_CHOICES),
 | 
			
		||||
            'allergens': forms.CheckboxSelectMultiple(choices=ALLERGENS_CHOICES),
 | 
			
		||||
            'day': forms.DateInput(attrs={'type': 'date'}, format="%d.%m.%Y"),
 | 
			
		||||
            'day': forms.DateInput(attrs={'type': 'date'}),
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -20,46 +20,39 @@ example_json = [
 | 
			
		||||
 | 
			
		||||
def load_data(locations, checked_types, status):
 | 
			
		||||
    current_week = datetime.date.today().isocalendar().week
 | 
			
		||||
    days = Day.objects.filter(date__week=current_week)
 | 
			
		||||
 | 
			
		||||
    for location in locations:
 | 
			
		||||
        menus = Menu.objects.filter(days__in=days, locations=location)
 | 
			
		||||
        menus = Menu.objects.filter(day__week=current_week, location=location)
 | 
			
		||||
        if not menus.exists():
 | 
			
		||||
            fetched_data = fetch(location.mensa_id)
 | 
			
		||||
            store(fetched_data, location)
 | 
			
		||||
 | 
			
		||||
    data = formatted_menu_data(locations, checked_types, status)
 | 
			
		||||
    return data
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def formatted_menu_data(locations, checked_types, status):
 | 
			
		||||
    current_week = datetime.date.today().isocalendar().week
 | 
			
		||||
    days = Day.objects.filter(date__week=current_week)
 | 
			
		||||
    today = datetime.date.today()
 | 
			
		||||
    days = [today + datetime.timedelta(days=i)
 | 
			
		||||
            for i in range(0 - today.weekday(), 5 - today.weekday())]
 | 
			
		||||
 | 
			
		||||
    formatted_data = {}
 | 
			
		||||
 | 
			
		||||
    for day in days:
 | 
			
		||||
        formatted_data[str(day.date)] = []
 | 
			
		||||
 | 
			
		||||
    for day in days:
 | 
			
		||||
        if day not in formatted_data:
 | 
			
		||||
            formatted_data[day] = []
 | 
			
		||||
        for location in locations:
 | 
			
		||||
            menus = Menu.objects.filter(days=day, locations=location)
 | 
			
		||||
            menus = Menu.objects.filter(location=location, day=day)
 | 
			
		||||
            for menu in menus:
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
                # AND or OR filter ???
 | 
			
		||||
                if set(checked_types).issubset(set(menu.types)): # <-- AND
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
                    formatted_data[str(day.date)].append({
 | 
			
		||||
                    formatted_data[day].append({
 | 
			
		||||
                        'art': menu.art,
 | 
			
		||||
                        'name': menu.name,
 | 
			
		||||
                        'price': menu.price if status is None else menu.get_price[status],
 | 
			
		||||
                        'price': menu.price if status is None
 | 
			
		||||
                                            else menu.get_price[status],
 | 
			
		||||
                        'allergens': menu.get_allergens,
 | 
			
		||||
                        'types': menu.get_types,
 | 
			
		||||
                        'likes': menu.likes,
 | 
			
		||||
                        'location': location.name,
 | 
			
		||||
                        'location': location,
 | 
			
		||||
                        'pk': menu.pk,
 | 
			
		||||
                    })
 | 
			
		||||
    return formatted_data
 | 
			
		||||
@ -67,32 +60,21 @@ def formatted_menu_data(locations, checked_types, status):
 | 
			
		||||
 | 
			
		||||
def store(data, location):
 | 
			
		||||
    for day_json in data:
 | 
			
		||||
        date_string= day_json['day']
 | 
			
		||||
        date_string = day_json['day']
 | 
			
		||||
        menus_json = day_json['menus']
 | 
			
		||||
 | 
			
		||||
        date = parse_date(date_string)
 | 
			
		||||
 | 
			
		||||
        if not Day.objects.filter(date=date).exists():
 | 
			
		||||
            Day(date=date).save()
 | 
			
		||||
 | 
			
		||||
        day = Day.objects.get(date=date)
 | 
			
		||||
 | 
			
		||||
        day = parse_date(date_string)
 | 
			
		||||
        for menu_json in menus_json:
 | 
			
		||||
            art = menu_json['art']
 | 
			
		||||
            name = menu_json['name']
 | 
			
		||||
            price = menu_json['price'] or "0,00€ / 0,00€ / 0,00€"
 | 
			
		||||
            price = menu_json['price'] or "0,00 € / 0,00 € / 0,00 €"
 | 
			
		||||
            allergens = menu_json['allergens']
 | 
			
		||||
            types = menu_json['types']
 | 
			
		||||
 | 
			
		||||
            menu_exists = Menu.objects.filter(art=art, name=name, price=price, allergens=allergens, types=types).exists()
 | 
			
		||||
 | 
			
		||||
            menu_exists = Menu.objects.filter(art=art, name=name, price=price,
 | 
			
		||||
                                              allergens=allergens, types=types,
 | 
			
		||||
                                              day=day).exists()
 | 
			
		||||
            if not menu_exists:
 | 
			
		||||
                Menu(art=art, name=name, price=price, allergens=allergens, types=types).save()
 | 
			
		||||
 | 
			
		||||
            menu = Menu.objects.get(art=art, name=name, price=price, allergens=allergens, types=types)
 | 
			
		||||
            menu.locations.add(location)
 | 
			
		||||
            menu.days.add(day)
 | 
			
		||||
            menu.save()
 | 
			
		||||
                Menu(art=art, name=name, price=price, allergens=allergens,
 | 
			
		||||
                            types=types, day=day, location=location).save()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def fetch(mensa_id: int):
 | 
			
		||||
@ -100,43 +82,3 @@ def fetch(mensa_id: int):
 | 
			
		||||
    if res.status_code != 200:
 | 
			
		||||
        raise Exception('request failed')
 | 
			
		||||
    return res.json()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def models_from_json(mensa_id: int):
 | 
			
		||||
    for day_json in fetch_menus(mensa_id):
 | 
			
		||||
        day_date = datetime.datetime.strptime(day_json['day'], '%Y-%m-%d').date()
 | 
			
		||||
 | 
			
		||||
        if not Day.objects.filter(mensa_id=mensa_id, date__contains=day_date):
 | 
			
		||||
            # create new day model ONLY if it does not yet exist for the given
 | 
			
		||||
            # day_date(s) and mensa_id.
 | 
			
		||||
 | 
			
		||||
            Day(mensa_id=mensa_id, date=day_date).save()
 | 
			
		||||
        day = Day.objects.get(mensa_id=mensa_id, date=day_date)
 | 
			
		||||
 | 
			
		||||
        for menu_json in day_json['menus']:
 | 
			
		||||
            # if meal already exists, simply add day to related menus.
 | 
			
		||||
            # otherwise, build new meal model from json with the specified menu
 | 
			
		||||
            # as the first related menu.
 | 
			
		||||
 | 
			
		||||
            if not Menu.objects.filter(name=menu_json['name']):
 | 
			
		||||
                Menu.from_json(menu_json, day).save()
 | 
			
		||||
 | 
			
		||||
            day.menus.add(Menu.objects.get(name=menu_json['name']))
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def days_as_json(mensa_ids: list, types_filter: list, price_filter: str):
 | 
			
		||||
    cw = datetime.date.today().isocalendar().week
 | 
			
		||||
    dates = list(dict.fromkeys([day.date for day in Day.objects.filter(date__week=cw)]))
 | 
			
		||||
 | 
			
		||||
    days_list = []
 | 
			
		||||
    for date in dates:
 | 
			
		||||
        day_json = { 'day': date, 'menus': [] }
 | 
			
		||||
        for mensa_id in mensa_ids:
 | 
			
		||||
            try:
 | 
			
		||||
                day = Day.objects.get(mensa_id=mensa_id, date=date)
 | 
			
		||||
                for menu in Menu.objects.filter(day=day, related_types__in=Type.objects.filter(type__in=types_filter) if types_filter else Type.objects.all()).distinct():
 | 
			
		||||
                    day_json['menus'].append({ 'menu': menu, 'mensa_id': mensa_id })
 | 
			
		||||
            except ObjectDoesNotExist:
 | 
			
		||||
                pass
 | 
			
		||||
        days_list.append(day_json)
 | 
			
		||||
    return days_list
 | 
			
		||||
 | 
			
		||||
@ -0,0 +1,25 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-06 00:06
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0015_comment_timestamp'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='days',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='Day',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='days',
 | 
			
		||||
            field=models.JSONField(blank=True, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -0,0 +1,37 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-06 22:11
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0016_remove_menu_days_delete_day_menu_days'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='days',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='locations',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='location',
 | 
			
		||||
            name='city',
 | 
			
		||||
            field=models.CharField(blank=True, max_length=144, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='day',
 | 
			
		||||
            field=models.DateField(blank=True, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='location',
 | 
			
		||||
            field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, to='mensaviewer.location'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -0,0 +1,42 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-06 22:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0017_remove_menu_days_remove_menu_locations_location_city_and_more'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='comment',
 | 
			
		||||
            old_name='username',
 | 
			
		||||
            new_name='author',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='comment',
 | 
			
		||||
            old_name='related_menu',
 | 
			
		||||
            new_name='menu',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='comment',
 | 
			
		||||
            name='comment',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='comment',
 | 
			
		||||
            name='text',
 | 
			
		||||
            field=models.CharField(blank=True, max_length=512, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='NewsArticle',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('author', models.CharField(default='anon', max_length=144)),
 | 
			
		||||
                ('text', models.CharField(blank=True, max_length=8192, null=True)),
 | 
			
		||||
                ('location', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='mensaviewer.location')),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -0,0 +1,23 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-06 22:39
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0018_rename_username_comment_author_and_more'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='comment',
 | 
			
		||||
            name='text',
 | 
			
		||||
            field=models.TextField(blank=True, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='newsarticle',
 | 
			
		||||
            name='text',
 | 
			
		||||
            field=models.TextField(blank=True, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
							
								
								
									
										19
									
								
								mensaviewer/migrations/0020_newsarticle_timestamp.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								mensaviewer/migrations/0020_newsarticle_timestamp.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,19 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-08 01:01
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.utils.timezone
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0019_alter_comment_text_alter_newsarticle_text'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='newsarticle',
 | 
			
		||||
            name='timestamp',
 | 
			
		||||
            field=models.DateTimeField(blank=True, default=django.utils.timezone.now),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
							
								
								
									
										18
									
								
								mensaviewer/migrations/0021_newsarticle_title.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										18
									
								
								mensaviewer/migrations/0021_newsarticle_title.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,18 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-08 02:10
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0020_newsarticle_timestamp'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='newsarticle',
 | 
			
		||||
            name='title',
 | 
			
		||||
            field=models.CharField(blank=True, max_length=144),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -0,0 +1,38 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-08 03:00
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0021_newsarticle_title'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='allergens',
 | 
			
		||||
            field=models.JSONField(blank=True, default=[]),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='art',
 | 
			
		||||
            field=models.CharField(choices=[('M', 'Mensa'), ('C', 'Cafeteria')], default='M', max_length=1),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='name',
 | 
			
		||||
            field=models.CharField(blank=True, default='', max_length=144),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='price',
 | 
			
		||||
            field=models.CharField(blank=True, default='', max_length=144),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='types',
 | 
			
		||||
            field=models.JSONField(blank=True, default=[]),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -0,0 +1,38 @@
 | 
			
		||||
# Generated by Django 4.1.4 on 2023-01-08 18:03
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('mensaviewer', '0022_alter_menu_allergens_alter_menu_art_alter_menu_name_and_more'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='allergens',
 | 
			
		||||
            field=models.JSONField(blank=True, default=list),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='art',
 | 
			
		||||
            field=models.CharField(choices=[('Mensa', 'Mensa'), ('Cafeteria', 'Cafeteria')], default='M', max_length=24),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='name',
 | 
			
		||||
            field=models.CharField(blank=True, default='---', max_length=144),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='price',
 | 
			
		||||
            field=models.CharField(blank=True, default='---', max_length=144),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='menu',
 | 
			
		||||
            name='types',
 | 
			
		||||
            field=models.JSONField(blank=True, default=list),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
@ -10,7 +10,7 @@ class Location(models.Model):
 | 
			
		||||
    mensa_id = models.CharField(max_length=2, null=True, blank=True)
 | 
			
		||||
 | 
			
		||||
    def __str__(self):
 | 
			
		||||
        return f"{self.city} - {self.name} [{self.mensa_id}]"
 | 
			
		||||
        return f"{self.city} - {self.name}"
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def menus(self):
 | 
			
		||||
@ -33,7 +33,7 @@ class Menu(models.Model):
 | 
			
		||||
                                 blank=True)
 | 
			
		||||
 | 
			
		||||
    def __str__(self):
 | 
			
		||||
        return f"{self.name}"
 | 
			
		||||
        return f"{self.name} - {self.location} | {self.day}"
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def get_price(self):
 | 
			
		||||
@ -69,6 +69,9 @@ class Comment(models.Model):
 | 
			
		||||
    author = models.CharField(max_length=144, default='anon')
 | 
			
		||||
    text = models.TextField(null=True, blank=True)
 | 
			
		||||
 | 
			
		||||
    def __str__(self):
 | 
			
		||||
        return f"{self.menu} - {self.author} | {self.timestamp}"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticle(models.Model):
 | 
			
		||||
    location = models.ForeignKey(Location, on_delete=models.CASCADE)
 | 
			
		||||
@ -76,3 +79,6 @@ class NewsArticle(models.Model):
 | 
			
		||||
    author = models.CharField(max_length=144, default='anon')
 | 
			
		||||
    title = models.CharField(max_length=144, blank=True)
 | 
			
		||||
    text = models.TextField(null=True, blank=True)
 | 
			
		||||
 | 
			
		||||
    def __str__(self):
 | 
			
		||||
        return f"{self.title} | {self.title} - {self.author} | {self.timestamp}"
 | 
			
		||||
 | 
			
		||||
@ -5,19 +5,28 @@
 | 
			
		||||
  <head>
 | 
			
		||||
    <meta charset="utf-8">
 | 
			
		||||
    <link rel="stylesheet" href="{% static 'base.css' %}">
 | 
			
		||||
    <title>Mensaviewer | {% block title %}Home{%endblock%}</title>
 | 
			
		||||
    <title>Mensaviewer | {% block title %}Home{% endblock %}</title>
 | 
			
		||||
  </head>
 | 
			
		||||
  <body>
 | 
			
		||||
    <header>
 | 
			
		||||
      <h1>Header Title</h1>
 | 
			
		||||
      {% block header %}<h1>Header Title</h1>{% endblock %}
 | 
			
		||||
    </header>
 | 
			
		||||
    <nav>
 | 
			
		||||
      <a href="{% url 'mensaviewer:home' %}">Home</a>
 | 
			
		||||
      <a href="/admin">Admin</a>
 | 
			
		||||
    </nav>
 | 
			
		||||
    <main>
 | 
			
		||||
      {% block content %}
 | 
			
		||||
      {% endblock %}
 | 
			
		||||
      <nav>
 | 
			
		||||
        <a href="{% url 'mensaviewer:flensburg' %}">Flensburg</a>
 | 
			
		||||
        <a href="{% url 'mensaviewer:custom' %}">Custom</a>
 | 
			
		||||
        <hr>
 | 
			
		||||
        <a href="{% url 'mensaviewer:location_list' %}">Locations</a>
 | 
			
		||||
        <a href="{% url 'mensaviewer:news_list' %}">News Articles</a>
 | 
			
		||||
        <a href="{% url 'mensaviewer:menu_list' %}">Menus</a>
 | 
			
		||||
        <a href="{% url 'mensaviewer:comment_list' %}">Comments</a>
 | 
			
		||||
        <hr>
 | 
			
		||||
        <a href="/admin">Admin</a>
 | 
			
		||||
      </nav>
 | 
			
		||||
      <div class="content">
 | 
			
		||||
        {% block content %}
 | 
			
		||||
        {% endblock %}
 | 
			
		||||
      </div>
 | 
			
		||||
    </main>
 | 
			
		||||
  </body>
 | 
			
		||||
</html>
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/comment/delete.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/comment/delete.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  <p>Are you sure you want to delete "{{ object }}"?</p>
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Confirm">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/comment/detail.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/comment/detail.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<div class="detail-container">
 | 
			
		||||
  <h1>By {{ comment.author }}</h1>
 | 
			
		||||
  <h3>Timestamp: {{ comment.timestamp }}</h3>
 | 
			
		||||
  <h3>Menu: <a href="{% url 'mensaviewer:menu_detail' comment.menu.pk %}">{{ comment.menu.name }}</a></h3>
 | 
			
		||||
  <h3>Text: {{ comment.text }}</h3>
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										11
									
								
								mensaviewer/templates/comment/edit.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								mensaviewer/templates/comment/edit.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Save">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										31
									
								
								mensaviewer/templates/comment/list.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										31
									
								
								mensaviewer/templates/comment/list.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,31 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<h1>Comments</h1>
 | 
			
		||||
 | 
			
		||||
<table class="comment-list">
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td colspan="99" class="centered-td">
 | 
			
		||||
      <a class="btn" href="{% url 'mensaviewer:comment_create' %}">Add Comment</a>
 | 
			
		||||
    </td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  <tr>
 | 
			
		||||
    <th>Author</th>
 | 
			
		||||
    <th>Timestamp</th>
 | 
			
		||||
    <th>Menu</th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% for comment in object_list %}
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td>{{ comment.author }}</td>
 | 
			
		||||
    <td>{{ comment.timestamp }}</td>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:menu_detail' comment.menu.pk %}">{{ comment.menu }}</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:comment_update' comment.pk %}">Edit</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:comment_delete' comment.pk %}">Delete</a></td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</table>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										60
									
								
								mensaviewer/templates/custom.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										60
									
								
								mensaviewer/templates/custom.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,60 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block title %}Custom Locations{% endblock %}
 | 
			
		||||
 | 
			
		||||
{% block header %}<h1>Show menus for custom location selection</h1>{% endblock %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="filter-form" action="{% url 'mensaviewer:custom' %}" method="get">
 | 
			
		||||
  <input type="hidden" name="filterform" value="filter">
 | 
			
		||||
  <div class="type-filter">
 | 
			
		||||
    {% for name, id in types %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ name }}
 | 
			
		||||
      <input type="checkbox" name="type" value={{ id }} {% if id in checked_types %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="status-filter">
 | 
			
		||||
    {% for status_value in status_values %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ status_value }}
 | 
			
		||||
      <input type="radio" name="status" value="{{ status_value }}" {% if status == status_value %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="location-filter">
 | 
			
		||||
    {% for location in locations %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ location.name }}
 | 
			
		||||
      <input type="checkbox" name="location" value="{{ location.mensa_id }}" {% if location.mensa_id in selected_locations %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <button type="submit">Filter</button>
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
<div class="container">
 | 
			
		||||
  {% for day, menus in menu_data.items %}
 | 
			
		||||
  <div class="column">
 | 
			
		||||
    <h2>{{ day }}</h2>
 | 
			
		||||
 | 
			
		||||
    {% for menu in menus %}
 | 
			
		||||
    <div class="menu {% if menu.mensa_id == 1 %}a-mensa{% elif menu.mensa_id == 6 %}b-mensa{% endif %}">
 | 
			
		||||
      <a href="{% url 'mensaviewer:menu_detail' menu.pk %}">{{ menu.name }}</a>
 | 
			
		||||
      <p>{{ menu.art }}</p>
 | 
			
		||||
      <p>{{ menu.price }}</p>
 | 
			
		||||
      <p>{{ menu.types }}</p>
 | 
			
		||||
      <p>{{ menu.allergens }}</p>
 | 
			
		||||
      <p>{{ menu.likes }}</p>
 | 
			
		||||
      <a href="{% url 'mensaviewer:like' menu.pk %}?next={{ request.path }}">Like</a>
 | 
			
		||||
      <a href="{% url 'mensaviewer:dislike' menu.pk %}?next={{ request.path }}">Dislike</a>
 | 
			
		||||
    </div>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
 | 
			
		||||
  </div>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
@ -1,17 +1,18 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block title %}Flensburg{% endblock %}
 | 
			
		||||
 | 
			
		||||
{% block header %}<h1>Mensen in Flensburg</h1>{% endblock %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form action="{% url 'mensaviewer:home' %}" method="get">
 | 
			
		||||
<form class="filter-form" action="{% url 'mensaviewer:flensburg' %}" method="get">
 | 
			
		||||
  <input type="hidden" name="filterform" value="filter">
 | 
			
		||||
  <div class="type-filters">
 | 
			
		||||
  <div class="type-filter">
 | 
			
		||||
    {% for name, id in types %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ name }}
 | 
			
		||||
      <input type="checkbox"
 | 
			
		||||
             name="type"
 | 
			
		||||
             value={{ id }}
 | 
			
		||||
             {% if id in checked_types %} checked{% endif %}>
 | 
			
		||||
      <input type="checkbox" name="type" value={{ id }} {% if id in checked_types %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
@ -19,25 +20,10 @@
 | 
			
		||||
    {% for status_value in status_values %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ status_value }}
 | 
			
		||||
      <input type="radio"
 | 
			
		||||
             name="status"
 | 
			
		||||
             value="{{ status_value }}"
 | 
			
		||||
             {% if status == status_value %} checked{% endif %}>
 | 
			
		||||
      <input type="radio" name="status" value="{{ status_value }}" {% if status == status_value %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="location-filter">
 | 
			
		||||
    {% for location in locations %}
 | 
			
		||||
    <label>
 | 
			
		||||
      {{ location.name }}
 | 
			
		||||
      <input type="checkbox"
 | 
			
		||||
             name="location"
 | 
			
		||||
             value="{{ location.mensa_id }}"
 | 
			
		||||
             {% if location.mensa_id in selected_locations %} checked{% endif %}>
 | 
			
		||||
    </label>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <a href="{% url 'mensaviewer:location_create' %}">New Location</a>
 | 
			
		||||
  <button type="submit">Filter</button>
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
@ -47,23 +33,21 @@
 | 
			
		||||
    <h2>{{ day }}</h2>
 | 
			
		||||
 | 
			
		||||
    {% for menu in menus %}
 | 
			
		||||
    <div class="menu {% if menu.mensa_id == 1 %}a-mensa{% elif menu.mensa_id == 6 %}b-mensa{% endif %}">
 | 
			
		||||
      <a href="{% url 'mensaviewer:menu_detail' menu.pk %}">{{ menu.name }}</a>
 | 
			
		||||
      <p>{{ menu.art }}</p>
 | 
			
		||||
    <div class="menu {% if menu.location.mensa_id == '1' %}a-mensa{% elif menu.location.mensa_id == '6' %}b-mensa{% endif %}">
 | 
			
		||||
      <p>{{ menu.art }} - {{ menu.location.name }}</p>
 | 
			
		||||
      <hr>
 | 
			
		||||
      <h4><a href="{% url 'mensaviewer:menu_detail' menu.pk %}">{{ menu.name }}</a></h4>
 | 
			
		||||
      <p>{{ menu.price }}</p>
 | 
			
		||||
      <p>{{ menu.types }}</p>
 | 
			
		||||
      <p>{{ menu.allergens }}</p>
 | 
			
		||||
      <p>{{ menu.likes }}</p>
 | 
			
		||||
      <a href="{% url 'mensaviewer:like' menu.pk %}?next={{ request.path }}">Like</a>
 | 
			
		||||
      <span>{{ menu.likes }}</span>
 | 
			
		||||
      <a href="{% url 'mensaviewer:dislike' menu.pk %}?next={{ request.path }}">Dislike</a>
 | 
			
		||||
    </div>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  </div>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/location/delete.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/location/delete.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  <p>Are you sure you want to delete "{{ object }}"?</p>
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Confirm">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										29
									
								
								mensaviewer/templates/location/detail.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										29
									
								
								mensaviewer/templates/location/detail.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,29 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<div class="detail-container">
 | 
			
		||||
  <h1>{{ location.name }}</h1>
 | 
			
		||||
  <h3>City: {{ location.city }}</h3>
 | 
			
		||||
  <h3>ID: {{ location.mensa_id }}</h3>
 | 
			
		||||
  <a href="{% url 'mensaviewer:news_add' location.pk %}">Add News</a>
 | 
			
		||||
  <a href="{% url 'mensaviewer:menu_add' location.pk %}">Add Menu</a>
 | 
			
		||||
  <div class="related-items">
 | 
			
		||||
    <h2>News</h2>
 | 
			
		||||
    {% for news_article in location.news_articles %}
 | 
			
		||||
    <div class="news-article">
 | 
			
		||||
      <h3><a href="{% url 'mensaviewer:news_detail' news_article.pk %}">{{ news_article.title }}</a></h3>
 | 
			
		||||
    </div>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="related-items">
 | 
			
		||||
    <h2>Menus</h2>
 | 
			
		||||
    {% for menu in location.menus %}
 | 
			
		||||
    <div class="menu">
 | 
			
		||||
      <h3><a href="{% url 'mensaviewer:menu_detail' menu.pk %}">{{ menu.name }}</a></h3>
 | 
			
		||||
    </div>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										11
									
								
								mensaviewer/templates/location/edit.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								mensaviewer/templates/location/edit.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Save">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										31
									
								
								mensaviewer/templates/location/list.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										31
									
								
								mensaviewer/templates/location/list.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,31 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<h1>Locations</h1>
 | 
			
		||||
 | 
			
		||||
<table class="location-list">
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td colspan="99" class="centered-td">
 | 
			
		||||
      <a class="btn" href="{% url 'mensaviewer:location_create' %}">New Location</a>
 | 
			
		||||
    </td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  <tr>
 | 
			
		||||
    <th>Name</th>
 | 
			
		||||
    <th>City</th>
 | 
			
		||||
    <th>ID</th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% for location in object_list %}
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:location_detail' location.pk %}">{{ location.name }}</a></td>
 | 
			
		||||
    <td>{{ location.city }}</td>
 | 
			
		||||
    <td class="fit-width">{{ location.mensa_id }}</td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:location_update' location.pk %}">Edit</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:location_delete' location.pk %}">Delete</a></td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</table>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/menu/delete.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/menu/delete.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  <p>Are you sure you want to delete "{{ object }}"?</p>
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Confirm">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										28
									
								
								mensaviewer/templates/menu/detail.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										28
									
								
								mensaviewer/templates/menu/detail.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,28 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<div class="detail-container">
 | 
			
		||||
  <h1>{{ menu.name }}</h1>
 | 
			
		||||
  <p>Art: {{ menu.art }}</p>
 | 
			
		||||
  <p>Price for Students: {{ menu.get_price.Student }}</p>
 | 
			
		||||
  <p>Price for Employees: {{ menu.get_price.Employee }}</p>
 | 
			
		||||
  <p>Price for Guests: {{ menu.get_price.Guest }}</p>
 | 
			
		||||
  <p>Allergens: {{ menu.get_allergens }}</p>
 | 
			
		||||
  <p>Types: {{ menu.get_types }}</p>
 | 
			
		||||
  <p>Rating: {{ menu.likes }}</p>
 | 
			
		||||
  <p>Location and Date: {{ menu.location.city }} {{ menu.location.name }} | {{ menu.day }}</p>
 | 
			
		||||
  <a href="{% url 'mensaviewer:like' menu.id %}?next={{ request.path }}">Like</a>
 | 
			
		||||
  <a href="{% url 'mensaviewer:dislike' menu.id %}?next={{ request.path }}">Dislike</a>
 | 
			
		||||
  <a href="{% url 'mensaviewer:comment_add' menu.id %}">Comment</a>
 | 
			
		||||
  <div class="related-items">
 | 
			
		||||
    {% for comment in menu.comments %}
 | 
			
		||||
    <div class="comment">
 | 
			
		||||
      <h3>{{ comment.author }}</h3>
 | 
			
		||||
      <p>{{ comment.text }}</p>
 | 
			
		||||
    </div>
 | 
			
		||||
    {% endfor %}
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										11
									
								
								mensaviewer/templates/menu/edit.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								mensaviewer/templates/menu/edit.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Save">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										31
									
								
								mensaviewer/templates/menu/list.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										31
									
								
								mensaviewer/templates/menu/list.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,31 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<h1>Menus</h1>
 | 
			
		||||
 | 
			
		||||
<table class="menu-list">
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td colspan="99" class="centered-td">
 | 
			
		||||
      <a class="btn" href="{% url 'mensaviewer:menu_create' %}">Add Menu</a>
 | 
			
		||||
    </td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  <tr>
 | 
			
		||||
    <th>Name</th>
 | 
			
		||||
    <th>Location</th>
 | 
			
		||||
    <th>Day</th>
 | 
			
		||||
    <th>Edit</th>
 | 
			
		||||
    <th>Delete</th>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% for menu in object_list %}
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:menu_detail' menu.pk %}">{{ menu.name }}</a></td>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:location_detail' menu.location.pk %}">{{ menu.location.name }}</a></td>
 | 
			
		||||
    <td>{{ menu.day }}</td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:menu_update' menu.pk %}">Edit</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:menu_delete' menu.pk %}">Delete</a></td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</table>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/news/delete.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/news/delete.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  <p>Are you sure you want to delete "{{ object }}"?</p>
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Confirm">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										12
									
								
								mensaviewer/templates/news/detail.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								mensaviewer/templates/news/detail.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<div class="detail-container">
 | 
			
		||||
  <h1>By {{ newsarticle.author }}</h1>
 | 
			
		||||
  <h3>Timestamp: {{ newsarticle.timestamp }}</h3>
 | 
			
		||||
  <h3>Location: <a href="{% url 'mensaviewer:location_detail' newsarticle.location.pk %}">{{ newsarticle.location.name }}</a></h3>
 | 
			
		||||
  <h3>Text: {{ newsarticle.text }}</h3>
 | 
			
		||||
</div>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										11
									
								
								mensaviewer/templates/news/edit.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								mensaviewer/templates/news/edit.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,11 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<form class="model-form" method="post">
 | 
			
		||||
  {% csrf_token %}
 | 
			
		||||
  {{ form }}
 | 
			
		||||
  <input type="submit" value="Save">
 | 
			
		||||
</form>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
							
								
								
									
										33
									
								
								mensaviewer/templates/news/list.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										33
									
								
								mensaviewer/templates/news/list.html
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,33 @@
 | 
			
		||||
{% extends 'base.html' %}
 | 
			
		||||
 | 
			
		||||
{% block content %}
 | 
			
		||||
 | 
			
		||||
<h1>News Articles</h1>
 | 
			
		||||
 | 
			
		||||
<table class="news-list">
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td colspan="99" class="centered-td">
 | 
			
		||||
      <a class="btn" href="{% url 'mensaviewer:news_create' %}">Add News Article</a>
 | 
			
		||||
    </td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  <tr>
 | 
			
		||||
    <th>Title</th>
 | 
			
		||||
    <th>Author</th>
 | 
			
		||||
    <th>Timestamp</th>
 | 
			
		||||
    <th>Menu</th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
    <th></th>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% for newsarticle in object_list %}
 | 
			
		||||
  <tr>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:news_detail' newsarticle.pk %}">{{ newsarticle.title }}</a></td>
 | 
			
		||||
    <td>{{ newsarticle.author }}</td>
 | 
			
		||||
    <td>{{ newsarticle.timestamp }}</td>
 | 
			
		||||
    <td><a href="{% url 'mensaviewer:location_detail' newsarticle.location.pk %}">{{ newsarticle.location.city }} - {{ newsarticle.location.name }}</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:news_update' newsarticle.pk %}">Edit</a></td>
 | 
			
		||||
    <td class="fit-width"><a href="{% url 'mensaviewer:news_delete' newsarticle.pk %}">Delete</a></td>
 | 
			
		||||
  </tr>
 | 
			
		||||
  {% endfor %}
 | 
			
		||||
</table>
 | 
			
		||||
 | 
			
		||||
{% endblock %}
 | 
			
		||||
@ -3,10 +3,46 @@ from . import views
 | 
			
		||||
 | 
			
		||||
app_name = 'mensaviewer'
 | 
			
		||||
urlpatterns = [
 | 
			
		||||
    path('', views.home, name='home'),
 | 
			
		||||
    # routes for overview
 | 
			
		||||
    path('', views.flensburg, name='flensburg'),
 | 
			
		||||
    path('custom-location', views.custom, name='custom'),
 | 
			
		||||
 | 
			
		||||
    # raw create routes
 | 
			
		||||
    path('add-location/', views.LocationCreateView.as_view(), name='location_create'),
 | 
			
		||||
    path('add-news-article/', views.NewsArticleCreateView.as_view(), name='news_create'),
 | 
			
		||||
    path('add-menu/', views.MenuCreateView.as_view(), name='menu_create'),
 | 
			
		||||
    path('add-comment/', views.CommentCreateView.as_view(), name='comment_create'),
 | 
			
		||||
 | 
			
		||||
    # relation-dependent create routes
 | 
			
		||||
    path('location/<int:pk>/add-news-article/', views.NewsArticleCreateView.as_view(), name='news_add'),
 | 
			
		||||
    path('location/<int:pk>/add-menu/', views.MenuCreateView.as_view(), name='menu_add'),
 | 
			
		||||
    path('menu/<int:pk>/add-comment/', views.CommentCreateView.as_view(), name='comment_add'),
 | 
			
		||||
 | 
			
		||||
    # list-view routes
 | 
			
		||||
    path('locations/', views.LocationListView.as_view(), name='location_list'),
 | 
			
		||||
    path('news-articles/', views.NewsArticleListView.as_view(), name='news_list'),
 | 
			
		||||
    path('menus/', views.MenuListView.as_view(), name='menu_list'),
 | 
			
		||||
    path('comments/', views.CommentListView.as_view(), name='comment_list'),
 | 
			
		||||
 | 
			
		||||
    # detail-view routes
 | 
			
		||||
    path('location/<int:pk>/', views.LocationDetailView.as_view(), name='location_detail'),
 | 
			
		||||
    path('news-article/<int:pk>/', views.NewsArticleDetailView.as_view(), name='news_detail'),
 | 
			
		||||
    path('menu/<int:pk>/', views.MenuDetailView.as_view(), name='menu_detail'),
 | 
			
		||||
    path('comment/<int:pk>/', views.CommentDetailView.as_view(), name='comment_detail'),
 | 
			
		||||
 | 
			
		||||
    # update-view routes
 | 
			
		||||
    path('location/<int:pk>/edit/', views.LocationUpdateView.as_view(), name='location_update'),
 | 
			
		||||
    path('news-artice/<int:pk>/edit/', views.NewsArticleUpdateView.as_view(), name='news_update'),
 | 
			
		||||
    path('menu/<int:pk>/edit/', views.MenuUpdateView.as_view(), name='menu_update'),
 | 
			
		||||
    path('comment/<int:pk>/edit/', views.CommentUpdateView.as_view(), name='comment_update'),
 | 
			
		||||
 | 
			
		||||
    # delete-view routes
 | 
			
		||||
    path('location/<int:pk>/delete/', views.LocationDeleteView.as_view(), name='location_delete'),
 | 
			
		||||
    path('news-artice/<int:pk>/delete/', views.NewsArticleDeleteView.as_view(), name='news_delete'),
 | 
			
		||||
    path('menu/<int:pk>/delete/', views.MenuDeleteView.as_view(), name='menu_delete'),
 | 
			
		||||
    path('comment/<int:pk>/delete/', views.CommentDeleteView.as_view(), name='comment_delete'),
 | 
			
		||||
 | 
			
		||||
    # like / dislike routes
 | 
			
		||||
    path('menu/<int:pk>/like/', views.like, name='like'),
 | 
			
		||||
    path('menu/<int:pk>/dislike/', views.dislike, name='dislike'),
 | 
			
		||||
    path('menu/<int:pk>/comment/', views.CommentCreateView.as_view(), name='comment'),
 | 
			
		||||
    path('location/create/', views.LocationCreateView.as_view(), name='location_create')
 | 
			
		||||
]
 | 
			
		||||
 | 
			
		||||
@ -1,6 +1,7 @@
 | 
			
		||||
from django.views.generic import DetailView
 | 
			
		||||
from django.views.generic.edit import CreateView
 | 
			
		||||
from django.views.generic import DetailView, ListView
 | 
			
		||||
from django.views.generic.edit import CreateView, UpdateView, DeleteView
 | 
			
		||||
from django.shortcuts import render, redirect, reverse
 | 
			
		||||
from django.urls import reverse_lazy
 | 
			
		||||
 | 
			
		||||
from .models import *
 | 
			
		||||
from .helpers import *
 | 
			
		||||
@ -8,16 +9,36 @@ from .forms import *
 | 
			
		||||
from .data import *
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def home(request):
 | 
			
		||||
def flensburg(request):
 | 
			
		||||
    filter_query = request.COOKIES.get('filter_query', '')
 | 
			
		||||
    if len(request.GET.getlist('filterform')) == 0 and filter_query != '':
 | 
			
		||||
        return redirect(reverse('mensaviewer:home') + '?' + filter_query)
 | 
			
		||||
        return redirect(reverse('mensaviewer:flensburg') + '?' + filter_query)
 | 
			
		||||
 | 
			
		||||
    checked_types = request.GET.getlist('type')
 | 
			
		||||
    status = request.GET.get('status')
 | 
			
		||||
    selected_locations = Location.objects.filter(mensa_id__in=[1, 6])
 | 
			
		||||
    context = {
 | 
			
		||||
        'types': [(TYPES[type], type) for type in TYPES],
 | 
			
		||||
        'checked_types': checked_types,
 | 
			
		||||
        'status_values': STATUS_VALUES,
 | 
			
		||||
        'status': status,
 | 
			
		||||
        'locations': Location.objects.all(),
 | 
			
		||||
        'menu_data': load_data(selected_locations, checked_types, status),
 | 
			
		||||
    }
 | 
			
		||||
    response = render(request, "flensburg.html", context)
 | 
			
		||||
    response.set_cookie('filter_query', request.GET.urlencode())
 | 
			
		||||
    return response
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def custom(request):
 | 
			
		||||
    filter_query = request.COOKIES.get('filter_query', '')
 | 
			
		||||
    if len(request.GET.getlist('filterform')) == 0 and filter_query != '':
 | 
			
		||||
        return redirect(reverse('mensaviewer:custom') + '?' + filter_query)
 | 
			
		||||
 | 
			
		||||
    selected_location_ids = request.GET.getlist('location')
 | 
			
		||||
    checked_types = request.GET.getlist('type')
 | 
			
		||||
    status = request.GET.get('status')
 | 
			
		||||
    selected_locations = Location.objects.filter(mensa_id__in=selected_location_ids)
 | 
			
		||||
 | 
			
		||||
    context = {
 | 
			
		||||
        'types': [(TYPES[type], type) for type in TYPES],
 | 
			
		||||
        'checked_types': checked_types,
 | 
			
		||||
@ -27,8 +48,7 @@ def home(request):
 | 
			
		||||
        'selected_locations': selected_location_ids,
 | 
			
		||||
        'menu_data': load_data(selected_locations, checked_types, status),
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    response = render(request, "flensburg.html", context)
 | 
			
		||||
    response = render(request, "custom.html", context)
 | 
			
		||||
    response.set_cookie('filter_query', request.GET.urlencode())
 | 
			
		||||
    return response
 | 
			
		||||
 | 
			
		||||
@ -38,7 +58,7 @@ def like(request, pk):
 | 
			
		||||
        menu = Menu.objects.get(pk=pk)
 | 
			
		||||
        menu.likes += 1
 | 
			
		||||
        menu.save()
 | 
			
		||||
        return redirect(reverse('mensaviewer:home') + '?' + request.GET.get('next'))
 | 
			
		||||
        return redirect(request.GET.get('next'))
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def dislike(request, pk):
 | 
			
		||||
@ -46,30 +66,155 @@ def dislike(request, pk):
 | 
			
		||||
        menu = Menu.objects.get(pk=pk)
 | 
			
		||||
        menu.likes -= 1
 | 
			
		||||
        menu.save()
 | 
			
		||||
        return redirect(reverse('mensaviewer:home') + '?' + request.GET.get('next'))
 | 
			
		||||
        return redirect(request.GET.get('next'))
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuDetailView(DetailView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    template_name = "menu_detail.html"
 | 
			
		||||
    queryset = Menu.objects.all()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class LocationCreateView(CreateView):
 | 
			
		||||
    model = Location
 | 
			
		||||
    template_name = "location/edit.html"
 | 
			
		||||
    fields = '__all__'
 | 
			
		||||
    template_name = "create_location.html"
 | 
			
		||||
    success_url = "/"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:location_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class LocationUpdateView(UpdateView):
 | 
			
		||||
    model = Location
 | 
			
		||||
    template_name = "location/edit.html"
 | 
			
		||||
    fields = '__all__'
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:location_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class LocationDeleteView(DeleteView):
 | 
			
		||||
    model = Location
 | 
			
		||||
    template_name = "location/delete.html"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:location_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class LocationDetailView(DetailView):
 | 
			
		||||
    model = Location
 | 
			
		||||
    template_name = "location/detail.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class LocationListView(ListView):
 | 
			
		||||
    model = Location
 | 
			
		||||
    template_name = "location/list.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticleCreateView(CreateView):
 | 
			
		||||
    model = NewsArticle
 | 
			
		||||
    template_name = "news/edit.html"
 | 
			
		||||
    fields = ['location', 'title', 'author', 'text']
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:news_list")
 | 
			
		||||
 | 
			
		||||
    def get_initial(self):
 | 
			
		||||
        if 'pk' in self.kwargs:
 | 
			
		||||
            return { 'location': get_object_or_404(Location, pk=self.kwargs['pk']) }
 | 
			
		||||
        else:
 | 
			
		||||
            return { 'location': None }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticleUpdateView(UpdateView):
 | 
			
		||||
    model = NewsArticle
 | 
			
		||||
    template_name = "news/edit.html"
 | 
			
		||||
    fields = ['location', 'title', 'author', 'text']
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:news_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticleDeleteView(DeleteView):
 | 
			
		||||
    model = NewsArticle
 | 
			
		||||
    template_name = "news/delete.html"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:news_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticleDetailView(DetailView):
 | 
			
		||||
    model = NewsArticle
 | 
			
		||||
    template_name = "news/detail.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class NewsArticleListView(ListView):
 | 
			
		||||
    model = NewsArticle
 | 
			
		||||
    template_name = "news/list.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuCreateView(CreateView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    form_class = MenuForm
 | 
			
		||||
    template_name = "menu/edit.html"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:menu_list")
 | 
			
		||||
 | 
			
		||||
    def get_initial(self):
 | 
			
		||||
        if 'pk' in self.kwargs:
 | 
			
		||||
            return { 'location': get_object_or_404(Location, pk=self.kwargs['pk']) }
 | 
			
		||||
        else:
 | 
			
		||||
            return { 'location': None }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuUpdateView(UpdateView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    form_class = MenuForm
 | 
			
		||||
    template_name = "menu/edit.html"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:menu_list")
 | 
			
		||||
 | 
			
		||||
    def get_initial(self):
 | 
			
		||||
        menu = get_object_or_404(Menu, pk=self.kwargs['pk'])
 | 
			
		||||
        print(menu.types)
 | 
			
		||||
        return { 'types': menu.types }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuDeleteView(DeleteView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    template_name = "menu/delete.html"
 | 
			
		||||
    success_url = reverse_lazy("mensaviewer:menu_list")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuDetailView(DetailView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    template_name = "menu/detail.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class MenuListView(ListView):
 | 
			
		||||
    model = Menu
 | 
			
		||||
    template_name = "menu/list.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class CommentCreateView(CreateView):
 | 
			
		||||
    model = Comment
 | 
			
		||||
    fields = ['username', 'comment']
 | 
			
		||||
    template_name = "comment.html"
 | 
			
		||||
    success_url = '/menu/{pk}/'
 | 
			
		||||
    fields = ['menu', 'author', 'text']
 | 
			
		||||
    template_name = "comment/edit.html"
 | 
			
		||||
    success_url = '/menu/{menu_id}/'
 | 
			
		||||
 | 
			
		||||
    def form_valid(self, form):
 | 
			
		||||
        self.menu = get_object_or_404(Menu, pk=self.kwargs['pk'])
 | 
			
		||||
        form.instance.menu = self.menu
 | 
			
		||||
        print(self.menu)
 | 
			
		||||
        return super().form_valid(form)
 | 
			
		||||
    def get_initial(self):
 | 
			
		||||
        if 'pk' in self.kwargs:
 | 
			
		||||
            return { 'menu': get_object_or_404(Menu, pk=self.kwargs['pk']) }
 | 
			
		||||
        else:
 | 
			
		||||
            return { 'menu': None }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class CommentUpdateView(UpdateView):
 | 
			
		||||
    model = Comment
 | 
			
		||||
    fields = ['author', 'text']
 | 
			
		||||
    template_name = "comment/edit.html"
 | 
			
		||||
    success_url = '/menu/{menu_id}/'
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class CommentDeleteView(DeleteView):
 | 
			
		||||
    model = Comment
 | 
			
		||||
    template_name = "comment/delete.html"
 | 
			
		||||
    success_url = '/menu/{menu_id}/'
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class CommentDetailView(DetailView):
 | 
			
		||||
    model = Comment
 | 
			
		||||
    template_name = "comment/detail.html"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class CommentListView(ListView):
 | 
			
		||||
    model = Comment
 | 
			
		||||
    template_name = "comment/list.html"
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										182
									
								
								static/base.css
									
									
									
									
									
								
							
							
						
						
									
										182
									
								
								static/base.css
									
									
									
									
									
								
							@ -1,15 +1,170 @@
 | 
			
		||||
* {
 | 
			
		||||
  font-family: monospace;
 | 
			
		||||
  font-family: Tahoma;
 | 
			
		||||
  box-sizing: border-box;
 | 
			
		||||
  outline: 1px solid green;
 | 
			
		||||
  background-color: rgba(16, 16, 16, 0.1)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
body {
 | 
			
		||||
  margin: 0;
 | 
			
		||||
  background-color: #1D1D28;
 | 
			
		||||
  color: #EEEDFF;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
h1, h2, h3 {
 | 
			
		||||
  margin: 0;
 | 
			
		||||
  padding: 1em;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
header {
 | 
			
		||||
  padding-left: 12vw;
 | 
			
		||||
  box-shadow: 0px 0px 32px rgba(0, 0, 0, 0.5);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
main {
 | 
			
		||||
  display: flex;
 | 
			
		||||
  background-color: #3E3949;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
nav {
 | 
			
		||||
  border-right: 1px solid rgba(0, 0, 0, 0.2);
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-direction: column;
 | 
			
		||||
  width: 16vw;
 | 
			
		||||
  min-width: 16em;
 | 
			
		||||
  padding-top: 4em;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
nav a {
 | 
			
		||||
  text-align: center;
 | 
			
		||||
  font-size: 18px;
 | 
			
		||||
  padding: 0.6em;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
nav a:hover {
 | 
			
		||||
  transition: 250ms;
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
nav hr {
 | 
			
		||||
  width: 16em;
 | 
			
		||||
  opacity: 0.1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
a {
 | 
			
		||||
  text-decoration: none;
 | 
			
		||||
  color: #EEEDFF;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
a:hover {
 | 
			
		||||
  transition: 250ms;
 | 
			
		||||
  color: #FFEFCA;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
a:active {
 | 
			
		||||
  color: #CEA716;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
form {
 | 
			
		||||
  padding: 1em;
 | 
			
		||||
  margin: 0.5em;
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 0.3);
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
  box-shadow: inset 0px 0px 1em rgba(0, 0, 0, 0.2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
table {
 | 
			
		||||
  width: 100%;
 | 
			
		||||
  padding: 1em;
 | 
			
		||||
  margin: 0.5em;
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 0.3);
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
  box-shadow: inset 0px 0px 1em rgba(0, 0, 0, 0.2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
th {
 | 
			
		||||
  padding: 0.5em;
 | 
			
		||||
  color: #CEA716;
 | 
			
		||||
  text-align: left;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
td {
 | 
			
		||||
  padding: 0.5em;
 | 
			
		||||
  border: 1px solid rgba(255, 255, 255, 0.1);
 | 
			
		||||
  border-radius: 0.2em;
 | 
			
		||||
  max-width: 30vw;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.fit-width {
 | 
			
		||||
  width: 1%;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.content {
 | 
			
		||||
  margin-left: 4vw;
 | 
			
		||||
  margin-right: 4vw;
 | 
			
		||||
  flex: 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.centered-td {
 | 
			
		||||
  text-align: center;
 | 
			
		||||
  padding: 1em;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.btn {
 | 
			
		||||
  padding: 0.4em;
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.2);
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 0.3);
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.model-form {
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-direction: column;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.model-form input, .model-form textarea, .model-form select, button {
 | 
			
		||||
  margin-top: 0.5em;
 | 
			
		||||
  margin-bottom: 1em;
 | 
			
		||||
  padding: 0.5em;
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.5);
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 1);
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
  color: #EEEDFF;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.filter-form {
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-direction: column;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.filter-form .type-filter, .filter-form .status-filter, .filter-form .location-filter {
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-direction: row;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.filter-form label {
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.2);
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 0.3);
 | 
			
		||||
  border-radius: 0.3em;
 | 
			
		||||
  padding: 0.3em;
 | 
			
		||||
  margin: 0.5em;
 | 
			
		||||
  text-align: right;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
input[type="submit"], button {
 | 
			
		||||
  cursor: pointer;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
input[type="submit"]:active, button:active {
 | 
			
		||||
  transition: 200ms;
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.7);
 | 
			
		||||
  cursor: pointer;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.container {
 | 
			
		||||
  padding: 0.3em;
 | 
			
		||||
  margin: 0.3em;
 | 
			
		||||
  border: 1px solid rgba(0, 0, 0, 0.3);
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
  box-shadow: inset 0px 0px 1em rgba(0, 0, 0, 0.2);
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-flow: row wrap;
 | 
			
		||||
}
 | 
			
		||||
@ -20,10 +175,31 @@ body {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.menu {
 | 
			
		||||
  padding: 1em;
 | 
			
		||||
  margin: 0.2em;
 | 
			
		||||
  border-radius: 0.5em;
 | 
			
		||||
  box-shadow: inset 0px 0px 1em rgba(0, 0, 0, 0.2);
 | 
			
		||||
  background-color: rgba(0, 0, 0, 0.2);
 | 
			
		||||
  display: flex;
 | 
			
		||||
  flex-direction: column;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.menu * {
 | 
			
		||||
  margin: 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.menu hr {
 | 
			
		||||
  opacity: 0.2;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.menu p {
 | 
			
		||||
  font-size: 12px;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.menu a {
 | 
			
		||||
  display: inline-block;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
.a-mensa {
 | 
			
		||||
  background-color: rgba(16, 64, 16, 0.2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user