Django 将数字渲染为 5 星评级

Jul*_*rtz 5 django django-templates django-forms

我正在为我的网站建立一个评级系统。它目前运行良好,但我想改进系统的美观方面。我希望能够从数据库中获取评级并将其显示为 5 星级评级。另外,如果不是太复杂,我希望能够点击星星来将评级记录在数据库中,而不是写一个数字。

\n\n

我对网络开发还很陌生。特别是,我没有使用 javascript 的经验(我只做过在互联网上找到的教程),我认为这是实现我正在搜索的功能所必需的,所以请给我一个小例子和你的回复,以便让我能够理解。

\n\n

为了将评级渲染为星级,我不知道该怎么做。为了将评级记录为星级,我想到了两种解决方案:

\n\n

1)使用django 星级评级,但我不认为我有能力理解它是如何工作的。我已经发帖寻求有关此应用程序的帮助和示例,但我没有收到任何帮助,所以我想我应该忘记这一点。

\n\n

2) 使用带有适当小部件的表单将 IntegerInput 呈现为 5 星评级。

\n\n

对于第二个解决方案,我已经有了代码,我现在需要一个小部件来替换\'Stars\'下面的代码,但我不知道该怎么做。有人能帮我吗 ?

\n\n

模型.py

\n\n
class Avis(models.Model):\n    note = models.IntegerField()\n
Run Code Online (Sandbox Code Playgroud)\n\n

表格.py

\n\n
class AvisForm(forms.ModelForm):\n    class Meta:\n        model = Avis\n        fields = [\'note\']\n        widgets = {\'note\': forms.NumberInput(attrs={\'class\': \'Stars\'})}\n        labels = {\'note\': \'Note /5\'}\n
Run Code Online (Sandbox Code Playgroud)\n\n

用于记录的 hmtl

\n\n
<form method="post" action="">\n  {% csrf_token %}\n  {% for field in form %}\n  <div class="fieldWrapper form-group">\n    {{ field.label_tag }}\n    {{ field }}\n  </div>\n  {% endfor %}\n  <input type="submit" class="btn btn-lg btn-outline-primary btn-block btn-login text-uppercase font- \n  weight-bold mb-2" value="Envoyer mon avis" />\n</form>\n
Run Code Online (Sandbox Code Playgroud)\n\n

hmtl 用于显示

\n\n
{{ avis.note }}\n
Run Code Online (Sandbox Code Playgroud)\n\n

提前致谢 !

\n\n

编辑(到目前为止我的评级存储代码):\nviews.py

\n\n
def avis(request, id): # view for displaying and storing the form\n    commande = get_object_or_404(Commande, id=id)\n\n    if request.method == "POST":\n        form = AvisForm(request.POST)\n        if form.is_valid():\n            avis = form.save(commit = False)\n            avis.commande = commande\n            avis.save()\n            commande.has_avis = True\n            commande.save()\n            if commande.plat.chef.nb_avis==0:\n                commande.plat.chef.rating = avis.note\n            else:\n                commande.plat.chef.rating = (commande.plat.chef.rating*commande.plat.chef.nb_avis + avis.note)/(commande.plat.chef.nb_avis + 1)\n            commande.plat.chef.nb_avis += 1\n            commande.plat.chef.save()\n            messages.success(request, \'Votre avis a \xc3\xa9t\xc3\xa9 correctement envoy\xc3\xa9 !\')\n            return redirect(mes_commandes)\n    else:\n        form = AvisForm()\n\n    return render(request, \'actualites/avis.html\', locals())\n\ndef avis2(request, id): # view for recording the rating\n    avis = get_object_or_404(Avis, id=id)\n    rating = request.POST.get(\'rating\')\n    avis.note = rating\n    avis.save()\n    messages.success(request, \'Votre avis a \xc3\xa9t\xc3\xa9 correctement envoy\xc3\xa9 !\')\n    return redirect(mes_commandes)\n
Run Code Online (Sandbox Code Playgroud)\n\n

html

\n\n
 <form method="post" action="">\n   {% csrf_token %}\n   {% for field in form %}\n   <div class="fieldWrapper form-group">\n      {{ field.label_tag }}\n      {{ field }}\n   </div>\n   {% endfor %}\n   <input type="submit" class="btn btn-lg btn-outline-primary btn-block btn-login text-uppercase font-weight-bold mb-2" value="Envoyer mon avis" />\n</form>\n<div class="rating rating2">\n  <a href="#5" title="Give 5 stars" data-value="5">\xe2\x98\x85</a>\n  <a href="#4" title="Give 4 stars" data-value="4">\xe2\x98\x85</a>\n  <a href="#3" title="Give 3 stars" data-value="3">\xe2\x98\x85</a>\n  <a href="#2" title="Give 2 stars" data-value="2">\xe2\x98\x85</a>\n  <a href="#1" title="Give 1 star" data-value="1">\xe2\x98\x85</a>\n</div>\n\n<script>\n  $(".rating a").on(\'click\', function(e){\n    let value = $(this).data(\'value\');\n     $.ajax({\n        url: "{% url \'avis2\' %}",\n        type: \'POST\',\n        data: {\'rating\': value},\n        success: function (d){\n         // some processing\n        }\n     })\n  });\n</script>\n
Run Code Online (Sandbox Code Playgroud)\n\n

表格.py

\n\n
class AvisForm(forms.ModelForm):\n    class Meta:\n        model = Avis\n        fields = [\'commentaire\']\n        widgets = {\'commentaire\': forms.Textarea(attrs={\'class\': \'form-control\'})}\n
Run Code Online (Sandbox Code Playgroud)\n

小智 4

我将尽力回答您的两个问题。为了获得评级,您可以渲染星星并为其添加 JS 点击事件。\n代码(HTML、CSS)来源:https://codepen.io/GeoffreyCrofte/pen/jEkBL

\n\n

\r\n
\r\n
$(".rating a").on(\'click\', function(e){\r\n\tlet value = $(this).data(\'value\');\r\n   $.ajax({\r\n      url: "some_url",\r\n      type: \'POST\',\r\n      data: {\'rating\': value},\r\n      success: function (d){\r\n       // some processing\r\n      }\r\n   })\r\n});
Run Code Online (Sandbox Code Playgroud)\r\n
.rating {\r\n  width: 300px;\r\n  margin: 0 auto 1em;\r\n  font-size: 45px;\r\n  overflow:hidden;\r\n}\r\n.rating input {\r\n  float: right;\r\n  opacity: 0;\r\n  position: absolute;\r\n}\r\n.rating a, \r\n.rating label {\r\n\t\t\tfloat:right;\r\n\t\t\tcolor: #aaa;\r\n\t\t\ttext-decoration: none;\r\n\t\t\t-webkit-transition: color .4s;\r\n\t\t\t-moz-transition: color .4s;\r\n\t\t\t-o-transition: color .4s;\r\n\t\t\ttransition: color .4s;\r\n\t\t}\r\n.rating label:hover ~ label,\r\n.rating input:focus ~ label,\r\n.rating label:hover,\r\n\t\t.rating a:hover,\r\n\t\t.rating a:hover ~ a,\r\n\t\t.rating a:focus,\r\n\t\t.rating a:focus ~ a\t\t{\r\n\t\t\tcolor: orange;\r\n\t\t\tcursor: pointer;\r\n\t\t}\r\n\t\t.rating2 {\r\n\t\t\tdirection: rtl;\r\n\t\t}\r\n\t\t.rating2 a {\r\n\t\t\tfloat:none\r\n\t\t}
Run Code Online (Sandbox Code Playgroud)\r\n
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>\r\n<div class="rating rating2">\r\n\t<a href="#5" title="Give 5 stars" data-value="5">\xe2\x98\x85</a>\r\n\t<a href="#4" title="Give 4 stars" data-value="4">\xe2\x98\x85</a>\r\n\t<a href="#3" title="Give 3 stars" data-value="3">\xe2\x98\x85</a>\r\n\t<a href="#2" title="Give 2 stars" data-value="2">\xe2\x98\x85</a>\r\n\t<a href="#1" title="Give 1 star" data-value="1">\xe2\x98\x85</a>\r\n</div>
Run Code Online (Sandbox Code Playgroud)\r\n
\r\n
\r\n

\n\n

为了渲染评级,您需要首先计算该值。您需要确定评价 5 星、3 星、... 1 星的人数。假设有 100 个 5 星级、70 * 4 星级、50 * 3 星级、30 * 2 和 20 * 1 星级。因此,您可以通过以下方式确定评级:

\n\n
\n

评分总和/总评分

\n
\n\n

所以它将是 (100 * 5 + 70 * 4 + 50 * 3 + 30 * 2 + 20 * 1) / 100 + 70 + 50 + 30 + 20

\n\n

所以最终评分为:3.74

\n\n

获取宽度百分比:(3.74 * 100) / 5 = 74.8

\n\n

这里5指的是星星总数,这里我假设评级将基于5的等级。

\n\n

为了渲染,您将需要不同的 HTML 和 CSS。

\n\n

代码来源: https: //codepen.io/Bluetidepro/pen/GkpEa

\n\n

\r\n
\r\n
      .star-ratings-css {\r\n            unicode-bidi: bidi-override;\r\n            color: #c5c5c5;\r\n            font-size: 25px;\r\n            height: 25px;\r\n            width: 100px;\r\n            margin: 0 auto;\r\n            position: relative;\r\n            padding: 0;\r\n            text-shadow: 0px 1px 0 #a2a2a2;\r\n        }\r\n\r\n        .star-ratings-css-top {\r\n            color: #e7711b;\r\n            padding: 0;\r\n            position: absolute;\r\n            z-index: 1;\r\n            display: block;\r\n            top: 0;\r\n            left: 0;\r\n            overflow: hidden;\r\n        }\r\n\r\n        .star-ratings-css-bottom {\r\n            padding: 0;\r\n            display: block;\r\n            z-index: 0;\r\n        }\r\n\r\n        .star-ratings-sprite {\r\n            background: url("https://s3-us-west-2.amazonaws.com/s.cdpn.io/2605/star-rating-sprite.png") repeat-x;\r\n            font-size: 0;\r\n            height: 21px;\r\n            line-height: 0;\r\n            overflow: hidden;\r\n            text-indent: -999em;\r\n            width: 110px;\r\n            margin: 0 auto;\r\n        }\r\n\r\n        .star-ratings-sprite-rating {\r\n            background: url("https://s3-us-west-2.amazonaws.com/s.cdpn.io/2605/star-rating-sprite.png") repeat-x;\r\n            background-position: 0 100%;\r\n            float: left;\r\n            height: 21px;\r\n            display: block;\r\n        }
Run Code Online (Sandbox Code Playgroud)\r\n
<div class="star-ratings-css">\r\n    <div class="star-ratings-css-top" style="width: 74.8%">\r\n        <span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span></div>\r\n    <div class="star-ratings-css-bottom"><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span><span>\xe2\x98\x85</span></div>\r\n</div>
Run Code Online (Sandbox Code Playgroud)\r\n
\r\n
\r\n

\n\n

您需要从视图传递宽度,并在 HTML 中访问它。\n <div class="star-ratings-css-top" style="width: {{ width }}%">。我尝试了这些代码片段,对我有用,也应该对你有用:)

\n