diff --git a/openslides/assignments/access_permissions.py b/openslides/assignments/access_permissions.py
index 65a38bcf7..c3dac3029 100644
--- a/openslides/assignments/access_permissions.py
+++ b/openslides/assignments/access_permissions.py
@@ -40,11 +40,16 @@ class AssignmentAccessPermissions(BaseAccessPermissions):
if has_perm(user, 'assignments.can_see') and has_perm(user, 'assignments.can_manage'):
data = full_data
elif has_perm(user, 'assignments.can_see'):
- # Exclude unpublished polls.
+ # Exclude unpublished poll votes.
data = []
for full in full_data:
full_copy = full.copy()
- full_copy['polls'] = [poll for poll in full['polls'] if poll['published']]
+ polls = full_copy['polls']
+ for poll in polls:
+ if not poll['published']:
+ for option in poll['options']:
+ option['votes'] = [] # clear votes for not published polls
+ poll['has_votes'] = False # A user should see, if there are votes.
data.append(full_copy)
else:
data = []
diff --git a/openslides/assignments/static/js/assignments/base.js b/openslides/assignments/static/js/assignments/base.js
index f7b46826a..59ce54898 100644
--- a/openslides/assignments/static/js/assignments/base.js
+++ b/openslides/assignments/static/js/assignments/base.js
@@ -337,9 +337,12 @@ angular.module('OpenSlidesApp.assignments', [])
getResourceName: function () {
return name;
},
- getAgendaTitle: function () {
+ getTitle: function () {
return this.title;
},
+ getAgendaTitle: function () {
+ return this.getTitle();
+ },
// link name which is shown in search result
getSearchResultName: function () {
return this.getAgendaTitle();
diff --git a/openslides/assignments/static/js/assignments/site.js b/openslides/assignments/static/js/assignments/site.js
index 31320853d..84cd2f6d5 100644
--- a/openslides/assignments/static/js/assignments/site.js
+++ b/openslides/assignments/static/js/assignments/site.js
@@ -716,14 +716,12 @@ angular.module('OpenSlidesApp.assignments.site', [
defaultValue[vote.value.toLowerCase()] = vote.weight;
});
- $scope.formFields.push(
- {
- noFormControl: true,
- template: '' + option.candidate.get_full_name() + ''
- },
+ var columnClass = (assignmentpoll.pollmethod === 'yna') ? 'col-xs-4' : 'col-xs-6';
+ var columns = [
{
key: 'yes_' + option.candidate_id,
type: 'input',
+ className: columnClass + ' no-padding-left',
templateOptions: {
label: gettextCatalog.getString('Yes'),
type: 'number',
@@ -735,6 +733,8 @@ angular.module('OpenSlidesApp.assignments.site', [
{
key: 'no_' + option.candidate_id,
type: 'input',
+ className: columnClass + ' no-padding-left' +
+ (assignmentpoll.pollmethod === 'yn' ? ' no-padding-right' : ''),
templateOptions: {
label: gettextCatalog.getString('No'),
type: 'number',
@@ -743,12 +743,12 @@ angular.module('OpenSlidesApp.assignments.site', [
},
defaultValue: defaultValue.no
}
- );
+ ];
if (assignmentpoll.pollmethod == 'yna'){
- $scope.formFields.push(
- {
+ columns.push({
key:'abstain_' + option.candidate_id,
type: 'input',
+ className: columnClass + ' no-padding-left no-padding-right',
templateOptions: {
label: gettextCatalog.getString('Abstain'),
type: 'number',
@@ -758,6 +758,14 @@ angular.module('OpenSlidesApp.assignments.site', [
defaultValue: defaultValue.abstain
});
}
+ $scope.formFields.push({
+ noFormControl: true,
+ template: '' + option.candidate.get_full_name() + ''
+ },
+ {
+ className: 'row',
+ fieldGroup: columns,
+ });
} else { // votes method
if (option.votes.length) {
defaultValue = option.votes[0].weight;
diff --git a/openslides/assignments/views.py b/openslides/assignments/views.py
index 3ebf251ea..ef6750960 100644
--- a/openslides/assignments/views.py
+++ b/openslides/assignments/views.py
@@ -191,8 +191,10 @@ class AssignmentViewSet(ModelViewSet):
if not assignment.candidates.exists():
raise ValidationError({'detail': _('Can not create ballot because there are no candidates.')})
with transaction.atomic():
- assignment.create_poll()
- return Response({'detail': _('Ballot created successfully.')})
+ poll = assignment.create_poll()
+ return Response({
+ 'detail': _('Ballot created successfully.'),
+ 'createdPollId': poll.pk})
@detail_route(methods=['post'])
def sort_related_users(self, request, pk=None):
diff --git a/openslides/core/static/js/core/base.js b/openslides/core/static/js/core/base.js
index 8daead7d8..06fc85d68 100644
--- a/openslides/core/static/js/core/base.js
+++ b/openslides/core/static/js/core/base.js
@@ -155,6 +155,7 @@ angular.module('OpenSlidesApp.core', [
'User',
'Group',
function (User, Group) {
+ var setUserCallbacks = [];
var operator = {
user: null,
perms: [],
@@ -167,6 +168,10 @@ angular.module('OpenSlidesApp.core', [
} else {
operator.user = null;
}
+ operator.reloadPerms();
+ _.forEach(setUserCallbacks, function (cb) {
+ cb(operator.user);
+ });
},
// Returns true if the operator has at least one perm of the perms-list.
hasPerms: function(perms) {
@@ -191,6 +196,9 @@ angular.module('OpenSlidesApp.core', [
}
return _.indexOf(groups, group.id) > -1;
},
+ registerSetUserCallback: function (cb) {
+ setUserCallbacks.push(cb);
+ },
};
return operator;
}
@@ -715,6 +723,7 @@ angular.module('OpenSlidesApp.core', [
});
}
+ scope.content = '';
if (attributes.content) {
attributes.$observe('content', function (content) {
scope.content = content;
@@ -816,8 +825,9 @@ angular.module('OpenSlidesApp.core', [
* provide also html markup for the messages. There are 4 types: 'info',
* 'success', 'warning', 'error'. The timeout is for autodeleting the message.
* Args that could be provided:
- * - timeout: Milliseconds until autoclose the message
- * - noClose: Whether to show the close button*/
+ * - timeout: Milliseconds until autoclose the message (default: not set, no auto close)
+ * - noClose: Whether to show the close button (default: false)
+ */
.factory('Messaging', [
'$timeout',
function($timeout) {
diff --git a/openslides/core/static/templates/projector-button.html b/openslides/core/static/templates/projector-button.html
index 1628dbf12..ab236c6c2 100644
--- a/openslides/core/static/templates/projector-button.html
+++ b/openslides/core/static/templates/projector-button.html
@@ -6,7 +6,7 @@
ng-click="model.project(defaultProjectorId, arg)"
ng-class="{ 'btn-primary': inArray(model.isProjected(arg), defaultProjectorId) }">
- {{ content }}
+ {{ content | translate }}