liquid_feedback_frontend
view app/main/initiative/_suggestions.lua @ 1679:ac45e0fe1221
Automatically assume dropdown item id from name when id is empty
| author | bsw | 
|---|---|
| date | Mon Sep 20 09:02:57 2021 +0200 (2021-09-20) | 
| parents | c08690678b2d | 
| children | c33916811ca7 | 
 line source
     1 local initiative = param.get("initiative", "table")
     2 local direct_supporter
     3 if app.session.member_id then
     4   direct_supporter = initiative.issue.member_info.own_participation and initiative.member_info.supported
     5 end
     8 if direct_supporter then
     9   ui.tag{ tag = "dialog", attr = { id = "rating_dialog" }, content = function ()
    11     local opinion = {}
    12     ui.form { 
    13       attr = { onsubmit = "updateOpinion(); return false;" },
    14       module = "opinion", action = "update",
    15       routing = { default = {
    16         mode = "redirect", 
    17         module = "initiative", view = "show", id = initiative.id
    18       } },
    19       content = function ()
    20         ui.field.hidden{ attr = { id = "rating_suggestion_id" }, name = "suggestion_id" }        
    21         ui.container{ attr = { class = "opinon-question" }, content = _"Should the initiator implement this suggestion?" }
    22         ui.container { content = function ()
    24           local options = {
    25             { degree =  2, label = _"must" },
    26             { degree =  1, label = _"should" },
    27             { degree =  0, label = _"neutral" },
    28             { degree = -1, label = _"should not" },
    29             { degree = -2, label = _"must not" },
    30           }
    32           for i, option in ipairs(options) do
    33             ui.tag{
    34               tag = "label", 
    35               attr = { 
    36                 id = "rating_degree" .. option.degree,
    37                 class = "mdl-radio mdl-js-radio mdl-js-ripple-effect"
    38               }, 
    39               ["for"] = "rating_degree" .. option.degree, 
    40               content = function()
    41                 ui.tag{
    42                   tag = "input",
    43                   attr = {
    44                     class = "mdl-radio__button",
    45                     type = "radio",
    46                     name = "degree",
    47                     value = option.degree
    48                   }
    49                 }
    50                 ui.tag{
    51                   attr = { class = "mdl-radio__label" },
    52                   content = option.label
    53                 }
    54               end
    55             }
    56             slot.put("     ")
    57           end
    58         end }
    60         slot.put("<br />")
    62         ui.container{ attr = { class = "opinon-question" }, content = _"Did the initiator implement this suggestion?" }
    63         ui.container { content = function ()
    65           local options = {
    66             { degree = "false", id = "notfulfilled", label = _"No (not yet)" },
    67             { degree = "true", id = "fulfilled", label = _"Yes, it's implemented" },
    68           }
    70           for i, option in ipairs(options) do
    71             ui.tag{
    72               tag = "label", 
    73               attr = {
    74                 id = "rating_" .. option.id,
    75                 class = "mdl-radio mdl-js-radio mdl-js-ripple-effect"
    76               }, 
    77               ["for"] = "rating_" .. option.id, 
    78               content = function()
    79                 ui.tag{
    80                   tag = "input",
    81                   attr = {
    82                     class = "mdl-radio__button",
    83                     type = "radio",
    84                     name = "fulfilled",
    85                     value = option.degree,
    86                   }
    87                 }
    88                 ui.tag{
    89                   attr = { class = "mdl-radio__label" },
    90                   content = option.label
    91                 }
    92               end
    93             }
    94             slot.put("     ")
    95           end
    96         end }
    98         slot.put("<br />")
   100         ui.tag{
   101           tag = "input",
   102           attr = {
   103             type = "submit",
   104             class = "mdl-button mdl-js-button mdl-button--raised mdl-button--colored",
   105             value = _"publish my rating"
   106           },
   107           content = ""
   108         }
   110         slot.put("   ")
   112         ui.tag{
   113           tag = "input",
   114           attr = {
   115             onclick = "document.getElementById('rating_dialog').close(); return false;",
   116             type = "submit",
   117             class = "mdl-button mdl-js-button",
   118             value = _"cancel"
   119           },
   120           content = ""
   121         }
   123       end 
   124     }
   126   end }
   127 end
   130 ui.link { attr = { name = "suggestions" }, text = "" }
   132 ui.container {
   133   attr = { class = "section suggestions" },
   134   content = function ()
   136     if # ( initiative.suggestions ) > 0 then
   138       ui.heading { 
   139         level = 1, 
   140         content = _("Suggestions for improvement (#{count})", { count = # ( initiative.suggestions ) } ) 
   141       }
   142       ui.container { content = _"written and rated by the supportes of this initiative to improve the proposal and its reasons" }
   143       slot.put("<br />")
   145       for i, suggestion in ipairs(initiative.suggestions) do
   147         local opinion = Opinion:by_pk(app.session.member_id, suggestion.id)
   149         local class = "mdl-card mdl-card__fullwidth mdl-shadow--2dp not-folded"
   150         if suggestion.id == param.get("suggestion_id", atom.number) then
   151           class = class .. " highlighted"
   152         end
   153         if member and not initiative.issue.fully_frozen and not initiative.issue.closed and initiative.member_info.supported then
   154           class = class .. " rateable"
   155         end
   157         ui.link { attr = { name = "s" .. suggestion.id }, text = "" }
   158         ui.tag { tag = "div", attr = { class = class, id = "s" .. suggestion.id }, content = function ()
   159           ui.tag{ attr = { class = "mdl-card__title mdl-card--border" }, content = function()
   160             ui.heading { level = 2, 
   161               attr = { class = "mdl-card__title-text" },
   162               content = function()
   163                 ui.tag{ content = format.string(suggestion.name, {
   164                   truncate_at = 160, truncate_suffix = true })
   165                 }
   166               end
   167             }
   168           end }
   172           ui.container{ attr = { class = "suggestion-content" }, content = function()
   174             ui.container { 
   175               attr = { class = "mdl-card__content mdl-card--border suggestionInfo" },
   176               content = function ()
   178                 if app.session:has_access("authors_pseudonymous") then
   179                   ui.tag{ content = _"by" }
   180                   slot.put(" ")
   181                   ui.link{
   182                     module = "member", view = "show", id = suggestion.author_id,
   183                     content = suggestion.author.name
   184                   }
   185                 end
   187                 execute.view{
   188                   module = "suggestion", view = "_collective_rating", params = {
   189                     suggestion = suggestion
   190                   }
   191                 }
   193               end 
   194             }
   196             ui.container {
   197               attr = { class = "mdl-card__content suggestion-text draft" },
   198               content = function ()
   199                 slot.put ( suggestion:get_content( "html" ) )
   201                 ui.container { attr = { class = "floatx-right" }, content = function()
   203                   ui.link { 
   204                     attr = { 
   205                       class = "mdl-button mdl-js-button mdl-button--icon suggestion-more",
   206                       onclick = "document.querySelector('#s" .. suggestion.id .. "').classList.remove('folded');document.querySelector('#s" .. suggestion.id .. "').classList.add('unfolded'); return false;"
   207                     },
   208                     content = function()
   209                       ui.tag{ tag = "i", attr = { class = "material-icons" }, content = "expand_more" }
   210                     end
   211                   }
   213                   ui.link { 
   214                     attr = { 
   215                       class = "mdl-button mdl-js-button mdl-button--icon suggestion-less",
   216                       onclick = "document.querySelector('#s" .. suggestion.id .. "').classList.add('folded');document.querySelector('#s" .. suggestion.id .. "').classList.remove('unfolded'); return false;"
   217                     },
   218                     content = function()
   219                       ui.tag{ tag = "i", attr = { class = "material-icons" }, content = "expand_less" }
   220                     end
   221                   }
   222                   --[[
   223                   ui.link{
   224                     attr = { class = "mdl-button" },
   225                     content = _"Details",
   226                     module = "suggestion", view = "show", id = suggestion.id
   227                   }
   228                   --]]
   229                 end }
   231               end
   232             }
   234           end }
   236           ui.container { attr = { class = "mdl-card__actions mdl-card--border" }, content = function()
   238             if direct_supporter then
   239               ui.container{ attr = { class = "suggestion_rating_info" }, content = function()
   240                 ui.tag{ attr = { id = "s" .. suggestion.id .. "_rating_text" }, content = function()
   241                   local text = ""
   242                   if opinion then
   243                     if opinion.degree == 2 then
   244                       text = _"must"
   245                     elseif opinion.degree == 1 then
   246                       text = _"should"
   247                     elseif opinion.degree == 0 then
   248                       text = _"neutral"
   249                     elseif opinion.degree == -1 then
   250                       text = _"should not"
   251                     elseif opinion.degree == -2 then
   252                       text = _"must not"
   253                     end
   254                     ui.tag { content = text }
   255                     slot.put ( " " )
   256                     if 
   257                       (opinion.degree > 0 and not opinion.fulfilled)
   258                       or (opinion.degree < 0 and opinion.fulfilled)
   259                     then
   260                       ui.tag{ content = _"but" }
   261                     else
   262                       ui.tag{ content = _"and" }
   263                     end
   264                     slot.put ( " " )
   265                     local text = ""
   266                     if opinion.fulfilled then
   267                       text = _"is implemented"
   268                     else
   269                       text = _"is not implemented"
   270                     end
   271                     ui.tag { content = text }
   272                   end
   273                 end }
   274                 local id = "s" .. suggestion.id .. "_rating_icon"
   275                 if opinion and (
   276                     (opinion.degree > 0 and not opinion.fulfilled)
   277                     or (opinion.degree < 0 and opinion.fulfilled)
   278                   )
   279                 then
   280                   slot.put(" ")
   281                   if math.abs(opinion.degree) > 1 then
   282                     ui.icon("warning", "red", id)
   283                   else
   284                     ui.icon("warning", nil, id)
   285                   end
   286                 elseif opinion then
   287                   slot.put(" ")
   288                   ui.icon("done", nil, id)
   289                 else
   290                   slot.put(" ")
   291                   ui.icon("blank", nil, id)
   292                 end
   293               end }
   295               ui.link{
   296                 attr = {
   297                   id = "s" .. suggestion.id .. "_rate_button",
   298                   class = "mdl-button",
   299                   onclick = "rateSuggestion(" .. suggestion.id .. ", " .. (opinion and opinion.degree or 0) .. ", " .. (opinion and (opinion.fulfilled and "true" or "false") or "null") .. ");return false;"
   300                 },
   301                 content = function()
   302                   if opinion then
   303                     ui.tag { content = _"update rating" }
   304                   else
   305                     ui.tag { content = _"rate suggestion" }
   306                   end
   307                 end
   308               }
   309             end
   311             ui.link{
   312               attr = { class = "mdl-button" },
   313               content = _"Details",
   314               module = "suggestion", view = "show", id = suggestion.id
   315             }
   317           end }
   318           ui.script{ script = [[
   319             var rateSuggestionRateText = "]] .. _"rate suggestion" .. [[";
   320             var rateSuggestionUpdateRatingText = "]] .. _"update rating" .. [[";
   321             var rateSuggestionDegreeTexts = {
   322               "-2": "]] .. _"must not" .. [[",
   323               "-1": "]] .. _"should not" .. [[",
   324               "1": "]] .. _"should" .. [[",
   325               "2": "]] .. _"must" .. [["
   326             }
   327             var rateSuggestionAndText = "]] .. _"and" .. [[";
   328             var rateSuggestionButText = "]] .. _"but" .. [[";
   329             var rateSuggestionFulfilledText = "]] .. _"is implemented" .. [[";
   330             var rateSuggestionNotFulfilledText = "]] .. _"is not implemented" .. [[";
   331             window.addEventListener("load", function() {
   332               var textEl = document.querySelector('#s]] .. suggestion.id .. [[ .suggestion-content');
   333               var height = textEl.clientHeight;
   334               if (height > 250) {
   335                 document.querySelector('#s]] .. suggestion.id .. [[').classList.add('folded');
   336               }
   337             });
   338           ]] }
   340         end } 
   342       end -- for i, suggestion
   344     end -- if #initiative.suggestions > 0
   345   end
   346 }
