Django admin - creating image admin models - django

I have looked through the posts but didn't find what I'm looking for, this is why I'm asking.
The goal is to be able to create image galleries in the admin, then to upload images and to choose in which (already created) gallery to be uploaded and after that, when creating a post (for example) to have a field which to access the gallery model and to choose images to be used in a carousel gallery in the said post.
For example, I'm creating a post in a travel blog and would like to add few images from the trip I had to use in a carousel.
I hope I have explained the goal understandable and someone to be able to show me a way or to point in the right direction
If there are any first party solutions, I'd be very happy
Please, since I'm new in django link a more detailed answer or tutorial or explain for a newbie

Heres answer for your idea..
change your models.py like this
class Carousel(models.Model):
carousel_name = models.CharField(max_length=50)
def __str__(self):
return self.carousel_name
class Photo(models.Model):
carousel = models.ForeignKey(Carousel, on_delete=models.CASCADE)
image =models.ImageField(upload_to="carousel_image", height_field=None, width_field=None, max_length=None)
Then in your Views.py:
from django.views.generic import DetailView
from .models import Carousel, Photo
class CarouselView(DetailView):
model = Carousel
template_name = 'carousel.html'
Now in your admin.py:
from .models import Carousel, Photo
class PhotoInline(admin.TabularInline):
model= Photo
extra= 3
class CarouselAdmin(admin.ModelAdmin):
inlines=[PhotoInline]
admin.site.register(Carousel, CarouselAdmin)
Now make your urlpattern to fetch pk as kwargs for image to be loaded like this:
urlpatterns = [
path('<int:pk>/', CarouselView.as_view())
]
Finally in your template:
render as:
<!-- The slideshow -->
<div class="carousel-inner">
{% for photo in carousel.photo_set.all %}
<div class="carousel-item active">
<img src="{{ photo.image.url }}" alt="Image {{forloop.counter}}" width="1100" height="500">
</div>
{% endfor %}
</div>
Now the gallery should work as you have expected it to.
Hope You get what you are searching for.😊

Related

HOW TO OUTPUT DATA GOT FROM combined queryset IN DJANGO TEMPLATE (html file)?

Am having a problem. And l request for your Help.
Am having 3 apps in Django project
action
adventure
others
`#action/ models.py
....
class Action(models.Model):
name=models.Charfield()
os= models.Charfield( choices=OS)....
#adventure/models.py
....
class Adventure(models.Model):
name=models.Charfield()
os= models.Charfield( choices=OS)....
#Others/views.py
from itertools import chain
from action.models import Action
from adventure.models import Adventure
def windows_games(request):
win_action = Action.objects.filter(os='windows')
win_adventure = Adventure.objects.filter(os='windows')
combined_list = list(chain(win_action,win_adventure))
context = ['combined_list':combined_list,]
return render(request, 'others/os/windows_game.html' , context)
#others/os/windows_game.html
.....
<div class="container">
<img src="{{combined_list.game_pic}}">
<p>{{combined_list.name}}</p>
1). I need to correct me in #others/ views.py if there is any mistake done.
2). I would like to know how to know how to write the tag that outputs the results in #others/os/windows_game.html because I tried that but outputs nothing.
And l would like to be in form of, #{{combined_list.game_pic}}, etc
It needed to display all items created in those models to display in windows_game page, after filtering those that only follow in category of windows.
I tried creating the context but there was no output results.
One of my friend here helped me like that bellow and it worked for me
#Windows_game.html
{% for game in combined_list %}
<p> {{game.game_name}}</p>
......
{% endfor %}

Django & AJAX to show DB objects upon user's input submission

I'm pretty new in the Web development world, have been using Django so far.
I've been trying to figure out how to render data back to page after clicking on a submit button, so I see I'll need to use AJAX for that purpose.
I've created a very simple app just to understand the basics of AJAX.
However, googling, I couldn't really find a basic straight-forward implementation so I kinda got lost...
What I'm trying to achieve:
I have a model called Country:
class Country(models.Model):
name = models.CharField(primary_key=True, max_length=35)
continent = models.CharField(max_length=10)
capital = models.CharField(max_length=35)
currency = models.CharField(max_length=10)
And a super simple main page that asks the user to insert some country name.
The idea is to bring to the page all the info from the DB.
So it would look like this:
Main page HTML body:
<body>
<h2><em>Please type a country name:</em></h2><br><br>
<div class="container">
<form id="get_info" method="post">
{{ form }}
{% csrf_token %}
<input id="submit_button" type="submit" name="submit" value="Get info">
</form>
</div>
</body>
views.py:
from django.shortcuts import render
from country_trivia import forms
def main_page(request):
get_info_form = forms.GetInfo()
return render(request, 'country_trivia/index.html', {'form': get_info_form})
forms.py:
from django import forms
class GetInfo(forms.Form):
country_name = forms.CharField(label="")
I've seen some examples using forms, but I'm not even sure if it's needed, as I've seen some other examples that count on 'onclick' even listeners, then "grab" the text in the search field and pass it via AJAX...
How should I build my AJAX object for that simple purpose, and how should I integrate it?
Do I need to use forms at all?
I don't post anything to DB, just query it and print out data...
Thanks!!

trying to show the full blog on a new html page after clicking on read more button in the blog card in django

I am working on a blogging website in Django.
I have a few blogs and I am loading them in the card from my database.My card has a read more button(To go to new HTML page and dynamically fetch the contents of the particular blog).
Instead of creating a new html page for every blog I am using a single html page to show the contents of the blog from the read more button clicked on card.
But I am getting the following error:
Reverse for 'post_detail' with arguments '('',)' not found. 1 pattern(s) tried: ['(?P[-a-zA-Z0-9_]+)\/$']
Request Method: GET
Request URL: http://127.0.0.1:8000/blogs/
Django Version: 2.2.6
Exception Type: NoReverseMatch
Exception Value:
Exception Location: C:\django\lib\site-packages\django\urls\resolvers.py in_reverse_with_prefix, line 673**
Thanks alot in advance
models.py
class blog(models.Model):
STATUS_CHOICES=(
("scholarship","Scholarship"),
("examination","Examination"),
("career","Career"),
("fellowship","Fellowship")
)
blog_image=models.ImageField(upload_to='blog_media',default="")
blog_title=models.CharField(max_length=300)
slug = models.SlugField( max_length=200, unique=True)
blog_type = models.CharField( max_length=50, choices=STATUS_CHOICES, default="scholarship" )
blog_author_name=models.CharField(max_length=200)
blog_content=models.CharField(max_length=5000)
publish_date=models.DateField()
urls.py:
urlpatterns = [
path('',views.index,name='home'),
path('blogs/',views.blogs,name='blogs'),
path('about/',views.about,name='about'),
path('admissions/',views.admissions,name='admissions'),
path( '<slug:slug>/', views.PostDetail.as_view(), name='post_detail' ),]
views.py
class PostDetail(DetailView):
#my model name is blog
model = blog
#this is the html page on which I want to show the single blog data
template_name = 'buddyscholarship_html/post_detail.html'
code for loading the dynamic data from Django in html in a CardView:
{% for i in data %}
</div>
<div class="card-body">
<h5 class="card-title">{{i.blog_title}}</h5>
<p class="card-text">{{i.blog_type}}</p>
<p class="card-text">By:{{i.blog_author_name}}</p>
<p class="card-text">{{i.blog_content|truncatechars:100}}</p>
<h5 class="card-title">{{i.publish_date}}</h5>
<!-----read more button for each and every blog coming from the database---------->
Read More →</div>
</div>
</div>
{% endfor %}
It should be i.slug not blog.slug
Read More →</div>
Apart from the above answer one another method is define a get absoulute method in your models as follows and call it in your templates as <a href="{{i.get_absolute_url}}".....
def get_absolute_url(self):
return reverse("post_detail", kwargs={"slug": self.slug})
Read More →</div>
Your problem should be solved after using i.slug instead of blog.slug but this is not the good approach here,you should use get_absolute_url method in this case.
Read More →</div>
To implement this:
In your models.py inside your Model class add this method something like this:
from django.urls import reverse
class Blog(models.Model):
title = models.CharField(max_length=255, unique=True)
slug = models.SlugField(max_length=255)
def get_absolute_url(self):
return reverse('post_detail',kwargs={'slug':self.slug})

Understanding Django and Django FormView

I am trying to create a Django web app that accepts text in a form/textbox, processes it and redirects to a webpage showing the processed text . I have written a half-functioning app and find de-bugging quite challenging because I don't understand most of what I've done. I'm hoping you will help me understand a few concepts, Linking to resources, also appreciated.
Consider this simple model:
class ThanksModel(models.Model):
thanks_text = models.CharField(max_length=200)
Is the only way to set the text of thanks_text through the manage.py shell? This feels like a pain if I just have one piece of text that I want to display. If I want to display a webpage that just says 'hi', do I still need to create a model?
Consider the view and template below:
views.py
class TestView(generic.FormView):
template_name = 'vader/test.html'
form_class = TestForm
success_url = '/thanks/'
test.html
<form action = "{% url 'vader:thanks'%}" method="post">
{% csrf_token %}
{{ form }}
<input type = "submit" value = "Submit">
</form>
I need to create another model, view and html template and update urls.py for '/thanks/' in order for the success_url to redirect correctly? (That's what I've done.) Do I need to use reverse() or reverse_lazy() the success_url in this situation?
Models are used when you are dealing with Objects and Data and DataBases that can contain a lot of information.
For Example A Person would be a model. their attributes would be age, name, nationality etc.
models.py
class Person(models.Model):
Name = models.CharField(max_length=50)
age = models.IntegerField()
nationality = models.CharField(max_length=50)
Thi deals with multiple bits of information for one object. (the object being the person)
A Thank you message would not need this? so scrap the model for the thank you message. just have views where you create the view using a templates and setting the view to a url.
views.py
class TestView(generic.FormView):
template_name = 'vader/test.html' # self explantory
form_class = TestForm # grabs the test form object
success_url = reverse_lazy('vader:thanks') # this makes sure you can use the name of the url instead of the path
def ThanksView(request): # its simple so you don't even need a class base view. a function view will do just fine.
return render(request,"thanks.html")
test.html
<form action = "{% url 'vader:thanks'%}" method="post">
{% csrf_token %}
{{ form }}
<input type = "submit" value = "Submit">
</form>
thanks.html
<h1>Thank you for Submitting</h1>
<h2> Come Again </h2>
url.py
from django.urls import path
from djangoapp5 import views
urlpatterns = [
path('', TestView.as_view(), name='test_form'),
path('thanks/', views.ThanksView, name='vader:thanks'),
]
I haven't tested this but hopefully it helps and guide you in the right direction

Django: I can't succeed displaying multiple checkboxes in my template

I read the following thread: Django Multiple Choice Field / Checkbox Select Multiple
But I somehow miss something important as I can't succeed in displaying the checkboxes in my template. However, the name of the field does appear in the template but that's all, after the field name, it's all white and blank.
Curiously, in the thread I read, the author didn't wrote a list of tuple. That's why I think the problem could lie in the models.py
Here is my models.py
from django.db import models
from user.models import User
class RegionChoices(models.Model):
REGION_CHOICES = (
('London', 'Londres'),
('Paris', 'Paris'),
('Berlin', 'Berlin'),
)
region = models.CharField(max_length=30, choices=REGION_CHOICES)
def __str__(self):
return self.region
class Offer(models.Model):
publisher = models.ForeignKey(User)
content = models.TextField()
region_choices = models.ManyToManyField(RegionChoices)
def __str__(self):
return self.publisher.username
forms.py
from django import forms
from django.contrib import admin
from django.conf import settings
from offers.models import Offer, RegionChoices
class SendOfferForm(forms.ModelForm):
region_choices = forms.ModelMultipleChoiceField(queryset=RegionChoices.objects.all(), widget=forms.CheckboxSelectMultiple)
class Meta:
model = Offer
exclude = ['publisher']
offer.html
<form action="{% url "send_offer" %}" method='POST' class='sendofferform'>
{{ form.errors }}
{{ form.non_field_errors }}
{% csrf_token %}
{{ offerform.as_p }}
</form>
views.py
if offerform.is_valid():
sent = True
offer = offerform.save(commit=False)
offer.publisher = User.objects.get(id=logged_user.id)
offer.save()
offerform.save_m2m()
else:
print(offerform.errors)
From your code sounds like you want to limit the choices of region your project can have. I think you should create an admin for RegionChoices first. In there you could create entrances of RegionChoices you like. Follow the django docs if you are not sure how to create an admin interface for a model https://docs.djangoproject.com/en/1.8/ref/contrib/admin/
ps: You might want to do unique=True on region field in RegionChoices. Otherwise you might create duplicate entries of the same region by accident.
Okay, I realize I had to load data in the model RegionChoices.
I loaded the data in the admin part of my website and now, it works perfectly.