liquid_feedback_frontend

diff app/main/initiative/show_tab.lua @ 19:00d1004545f1

Dynamic interface using XMLHttpRequests, and many other changes

Bugfixes:
- Only allow voting on admitted initiatives
- Repaired issue search
- Don't display delegations for closed issues on member page
- Don't show revoke link in initiative, when issue is already half_frozen
- Localization for voting JavaScript
- Display author of suggestions

Disclosure of voting data after voting is finished:
- Possibility to inspect every ballot including preferences
- Show number of voters preferring one initiative to another initiative

Interface behaviour changes:
- Reversed default order of drafts
- Default order of suggestions changed
- Show new drafts of initiatives only once per day in timeline

Accessibility:
- Barrier-free voting implemented
- POST links are now accessible without JavaScript
- Changed gray for unsatisfied supporters in bar graph to a lighter gray

Other interface improvements:
- Optical enhancements
- Dynamic interface using XMLHttpRequests
- Show usage terms in about section
- Show own membership in area listing
- Show uninformed supporters greyed out and marked with yellow question mark
- Warning box in non-admitted initiatives
- When voted, don't display voting notice and change label of voting link
- Show object counts in more tabulator heads
- Enlarged member statement input field

Miscellaneous:
- Code cleanup
- Added README file containing installation instructions
- Use new WebMCP function ui.filters{...} instead of own ui.filter and ui.order functions
author bsw/jbe
date Sat Feb 20 22:10:31 2010 +0100 (2010-02-20)
parents
children 0849be391140
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/app/main/initiative/show_tab.lua	Sat Feb 20 22:10:31 2010 +0100
     1.3 @@ -0,0 +1,175 @@
     1.4 +local initiative = param.get("initiative", "table")
     1.5 +local initiator = param.get("initiator", "table")
     1.6 +
     1.7 +if not initiative then
     1.8 +  initiative = Initiative:by_id(param.get("initiative_id", atom.number))
     1.9 +end
    1.10 +
    1.11 +if not initiator then
    1.12 +  initiator = Initiator:by_pk(initiative.id, app.session.member.id)
    1.13 +end
    1.14 +
    1.15 +local current_draft_name = _"Current draft"
    1.16 +if initiative.issue.half_frozen then
    1.17 +  current_draft_name = _"Voting proposal"
    1.18 +end
    1.19 +
    1.20 +if initiative.issue.state == "finished" then
    1.21 +  current_draft_name = _"Voted proposal"
    1.22 +end
    1.23 +
    1.24 +local tabs = {
    1.25 +  {
    1.26 +    name = "current_draft",
    1.27 +    label = current_draft_name,
    1.28 +    icon = { static = "icons/16/script.png" },
    1.29 +    module = "initiative",
    1.30 +    view = "_current_draft",
    1.31 +    params = {
    1.32 +      initiative = initiative,
    1.33 +      initiator = initiator
    1.34 +    }
    1.35 +  }
    1.36 +}
    1.37 +
    1.38 +if initiative.issue.ranks_available then
    1.39 +  tabs[#tabs+1] = {
    1.40 +    name = "voting",
    1.41 +    label = _"Voting details",
    1.42 +    icon = { static = "icons/16/email_open.png" },
    1.43 +    module = "initiative",
    1.44 +    view = "_show_voting",
    1.45 +    params = {
    1.46 +      initiative = initiative
    1.47 +    }
    1.48 +  }
    1.49 +end
    1.50 +
    1.51 +local suggestion_count = initiative:get_reference_selector("suggestions"):count()
    1.52 +
    1.53 +tabs[#tabs+1] = {
    1.54 +  name = "suggestions",
    1.55 +  label = _"Suggestions" .. " (" .. tostring(suggestion_count) .. ")",
    1.56 +  icon = { static = "icons/16/comments.png" },
    1.57 +  module = "initiative",
    1.58 +  view = "_suggestions",
    1.59 +  params = {
    1.60 +    initiative = initiative
    1.61 +  }
    1.62 +}
    1.63 +
    1.64 +local members_selector = initiative:get_reference_selector("supporting_members_snapshot")
    1.65 +          :join("issue", nil, "issue.id = direct_supporter_snapshot.issue_id")
    1.66 +          :join("direct_interest_snapshot", nil, "direct_interest_snapshot.event = issue.latest_snapshot_event AND direct_interest_snapshot.issue_id = issue.id AND direct_interest_snapshot.member_id = member.id")
    1.67 +          :add_field("direct_interest_snapshot.weight")
    1.68 +          :add_where("direct_supporter_snapshot.event = issue.latest_snapshot_event")
    1.69 +          :add_where("direct_supporter_snapshot.satisfied")
    1.70 +          :add_field("direct_supporter_snapshot.informed", "is_informed")
    1.71 +
    1.72 +local tmp = db:query("SELECT count(1) AS count, sum(weight) AS weight FROM (" .. tostring(members_selector) .. ") as subquery", "object")
    1.73 +local direct_satisfied_supporter_count = tmp.count
    1.74 +local indirect_satisfied_supporter_count = (tmp.weight or 0) - tmp.count
    1.75 +
    1.76 +local count_string
    1.77 +if indirect_satisfied_supporter_count > 0 then
    1.78 +  count_string = "(" .. tostring(direct_satisfied_supporter_count) .. "+" .. tostring(indirect_satisfied_supporter_count) .. ")"
    1.79 +else
    1.80 +  count_string = "(" .. tostring(direct_satisfied_supporter_count) .. ")"
    1.81 +end
    1.82 +
    1.83 +tabs[#tabs+1] = {
    1.84 +  name = "satisfied_supporter",
    1.85 +  label = _"Supporter" .. " " .. count_string,
    1.86 +  icon = { static = "icons/16/thumb_up_green.png" },
    1.87 +  module = "member",
    1.88 +  view = "_list",
    1.89 +  params = {
    1.90 +    initiative = initiative,
    1.91 +    members_selector = members_selector
    1.92 +  }
    1.93 +}
    1.94 +
    1.95 +local members_selector = initiative:get_reference_selector("supporting_members_snapshot")
    1.96 +          :join("issue", nil, "issue.id = direct_supporter_snapshot.issue_id")
    1.97 +          :join("direct_interest_snapshot", nil, "direct_interest_snapshot.event = issue.latest_snapshot_event AND direct_interest_snapshot.issue_id = issue.id AND direct_interest_snapshot.member_id = member.id")
    1.98 +          :add_field("direct_interest_snapshot.weight")
    1.99 +          :add_where("direct_supporter_snapshot.event = issue.latest_snapshot_event")
   1.100 +          :add_where("NOT direct_supporter_snapshot.satisfied")
   1.101 +          :add_field("direct_supporter_snapshot.informed", "is_informed")
   1.102 +
   1.103 +local tmp = db:query("SELECT count(1) AS count, sum(weight) AS weight FROM (" .. tostring(members_selector) .. ") as subquery", "object")
   1.104 +local direct_potential_supporter_count = tmp.count
   1.105 +local indirect_potential_supporter_count = (tmp.weight or 0) - tmp.count
   1.106 +
   1.107 +local count_string
   1.108 +if indirect_potential_supporter_count > 0 then
   1.109 +  count_string = "(" .. tostring(direct_potential_supporter_count) .. "+" .. tostring(indirect_potential_supporter_count) .. ")"
   1.110 +else
   1.111 +  count_string = "(" .. tostring(direct_potential_supporter_count) .. ")"
   1.112 +end
   1.113 +
   1.114 +tabs[#tabs+1] = {
   1.115 +  name = "supporter",
   1.116 +  label = _"Potential supporter" .. " " .. count_string,
   1.117 +  icon = { static = "icons/16/thumb_up.png" },
   1.118 +  module = "member",
   1.119 +  view = "_list",
   1.120 +  params = {
   1.121 +    initiative = initiative,
   1.122 +    members_selector = members_selector
   1.123 +  }
   1.124 +}
   1.125 +
   1.126 +local initiators_members_selector = initiative:get_reference_selector("initiating_members")
   1.127 +  :add_field("initiator.accepted", "accepted")
   1.128 +
   1.129 +if not (initiator and initiator.accepted) then
   1.130 +  initiators_members_selector:add_where("initiator.accepted")
   1.131 +end
   1.132 +
   1.133 +local initiator_count = initiators_members_selector:count()
   1.134 +
   1.135 +tabs[#tabs+1] = {
   1.136 +  name = "initiators",
   1.137 +  label = _"Initiators" .. " (" .. tostring(initiator_count) .. ")",
   1.138 +  icon = { static = "icons/16/user_edit.png" },
   1.139 +  module = "initiative",
   1.140 +  view = "_initiators",
   1.141 +  params = {
   1.142 +    initiative = initiative,
   1.143 +    initiator = initiator,
   1.144 +    initiators_members_selector = initiators_members_selector
   1.145 +  }
   1.146 +}
   1.147 +
   1.148 +local drafts_count = initiative:get_reference_selector("drafts"):count()
   1.149 +
   1.150 +tabs[#tabs+1] = {
   1.151 +  name = "drafts",
   1.152 +  label = _"Draft history" .. " (" .. tostring(drafts_count) .. ")",
   1.153 +  icon = { static = "icons/16/script.png" },
   1.154 +  module = "draft",
   1.155 +  view = "_list",
   1.156 +  params = { drafts = initiative.drafts }
   1.157 +}
   1.158 +
   1.159 +tabs[#tabs+1] = {
   1.160 +  name = "details",
   1.161 +  label = _"Details",
   1.162 +  icon = { static = "icons/16/magnifier.png" },
   1.163 +  module = "initiative",
   1.164 +  view = "_details",
   1.165 +  params = {
   1.166 +    initiative = initiative,
   1.167 +    members_selector = members_selector
   1.168 +  }
   1.169 +}
   1.170 +
   1.171 +tabs.module = "initiative"
   1.172 +tabs.view = "show_tab"
   1.173 +tabs.static_params = {
   1.174 +  initiative_id = initiative.id
   1.175 +}
   1.176 +
   1.177 +ui.tabs(tabs)
   1.178 +

Impressum / About Us