parent
03661eef9e
commit
f326ca5ae5
1
NEWS
1
NEWS
|
@ -14,6 +14,7 @@ Bug fixes
|
||||||
- [web] improved detection of changes in CKEditor (#3839)
|
- [web] improved detection of changes in CKEditor (#3839)
|
||||||
- [web] fixed vCard generation for tags with no type (#3826)
|
- [web] fixed vCard generation for tags with no type (#3826)
|
||||||
- [web] only show the organizer field of an IMIP REPLY if one is defined
|
- [web] only show the organizer field of an IMIP REPLY if one is defined
|
||||||
|
- [web] fixed saving the note of a card (#3849)
|
||||||
- [eas] improve handling of email folders without a parent
|
- [eas] improve handling of email folders without a parent
|
||||||
- [eas] never send IMIP reply when the "initiator" is Outlook 2013/2016
|
- [eas] never send IMIP reply when the "initiator" is Outlook 2013/2016
|
||||||
- [core] only consider SMTP addresses for AD's proxyAddresses (#3842)
|
- [core] only consider SMTP addresses for AD's proxyAddresses (#3842)
|
||||||
|
|
|
@ -861,8 +861,11 @@ convention:
|
||||||
|
|
||||||
- (void) setNotes: (NSArray *) newNotes
|
- (void) setNotes: (NSArray *) newNotes
|
||||||
{
|
{
|
||||||
|
NSArray *elements;
|
||||||
NSUInteger count, max;
|
NSUInteger count, max;
|
||||||
|
|
||||||
|
elements = [self childrenWithTag: @"note"];
|
||||||
|
[self removeChildren: elements];
|
||||||
max = [newNotes count];
|
max = [newNotes count];
|
||||||
for (count = 0; count < max; count++)
|
for (count = 0; count < max; count++)
|
||||||
{
|
{
|
||||||
|
|
|
@ -476,7 +476,7 @@ static Class SOGoContactGCSEntryK = Nil;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[card setNote: [attributes objectForKey: @"note"]];
|
[card setNotes: [attributes objectForKey: @"notes"]];
|
||||||
|
|
||||||
if ([[attributes objectForKey: @"categories"] isKindOfClass: [NSArray class]])
|
if ([[attributes objectForKey: @"categories"] isKindOfClass: [NSArray class]])
|
||||||
{
|
{
|
||||||
|
|
|
@ -705,28 +705,28 @@
|
||||||
// return [self _cardStringWithLabel: @"Timezone:" value: [card tz]];
|
// return [self _cardStringWithLabel: @"Timezone:" value: [card tz]];
|
||||||
// }
|
// }
|
||||||
|
|
||||||
- (NSArray *) notes
|
// - (NSArray *) notes
|
||||||
{
|
// {
|
||||||
NSMutableArray *notes;
|
// NSMutableArray *notes;
|
||||||
NSString *note;
|
// NSString *note;
|
||||||
NSUInteger count, max;
|
// NSUInteger count, max;
|
||||||
|
|
||||||
notes = [NSMutableArray arrayWithArray: [card notes]];
|
// notes = [NSMutableArray arrayWithArray: [card notes]];
|
||||||
max = [notes count];
|
// max = [notes count];
|
||||||
for (count = 0; count < max; count++)
|
// for (count = 0; count < max; count++)
|
||||||
{
|
// {
|
||||||
note = [notes objectAtIndex: count];
|
// note = [notes objectAtIndex: count];
|
||||||
note = [note stringByEscapingHTMLString];
|
// note = [note stringByEscapingHTMLString];
|
||||||
note = [note stringByReplacingString: @"\r\n"
|
// note = [note stringByReplacingString: @"\r\n"
|
||||||
withString: @"<br />"];
|
// withString: @"<br />"];
|
||||||
note = [note stringByReplacingString: @"\n"
|
// note = [note stringByReplacingString: @"\n"
|
||||||
withString: @"<br />"];
|
// withString: @"<br />"];
|
||||||
|
|
||||||
[notes replaceObjectAtIndex: count withObject: note];
|
// [notes replaceObjectAtIndex: count withObject: note];
|
||||||
}
|
// }
|
||||||
|
|
||||||
return notes;
|
// return notes;
|
||||||
}
|
// }
|
||||||
|
|
||||||
/* hrefs */
|
/* hrefs */
|
||||||
|
|
||||||
|
@ -888,7 +888,7 @@
|
||||||
o = [self urls];
|
o = [self urls];
|
||||||
if ([o count]) [data setObject: o forKey: @"urls"];
|
if ([o count]) [data setObject: o forKey: @"urls"];
|
||||||
|
|
||||||
o = [self notes];
|
o = [card notes];
|
||||||
if (o) [data setObject: o forKey: @"notes"];
|
if (o) [data setObject: o forKey: @"notes"];
|
||||||
o = [self _fetchAndCombineCategoriesList];
|
o = [self _fetchAndCombineCategoriesList];
|
||||||
if (o) [data setObject: o forKey: @"allCategories"];
|
if (o) [data setObject: o forKey: @"allCategories"];
|
||||||
|
|
|
@ -337,9 +337,10 @@
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- note -->
|
<!-- note -->
|
||||||
<md-input-container class="md-block md-flex">
|
<md-input-container class="md-block md-flex"
|
||||||
|
ng-repeat="note in editor.card.notes">
|
||||||
<label><var:string label:value="Note"/></label>
|
<label><var:string label:value="Note"/></label>
|
||||||
<textarea ng-model="editor.card.note"><!-- note --></textarea>
|
<textarea ng-model="note.value"><!-- note --></textarea>
|
||||||
</md-input-container>
|
</md-input-container>
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
|
|
|
@ -147,11 +147,11 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="section" ng-show="editor.card.notes">
|
<div class="section" ng-show="editor.card.notes[0].value.length">
|
||||||
<div class="pseudo-input-container" ng-repeat="note in editor.card.notes">
|
<div class="pseudo-input-container" ng-repeat="note in editor.card.notes">
|
||||||
<label class="pseudo-input-label"><var:string label:value="Note"/></label>
|
<label class="pseudo-input-label"><var:string label:value="Note"/></label>
|
||||||
<div class="pseudo-input-field">
|
<div class="pseudo-input-field">
|
||||||
<div ng-bind-html="note"><!-- note --></div>
|
<div ng-bind-html="note.value | ln2br"><!-- note --></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
21
UI/WebServerResources/js/Common/ln2br.filter.js
Normal file
21
UI/WebServerResources/js/Common/ln2br.filter.js
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
/* -*- Mode: javascript; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ln2br - A filter to convert line feeds and carriage returns to html line breaks
|
||||||
|
* @memberof SOGo.Common
|
||||||
|
*/
|
||||||
|
(function () {
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @ngInject
|
||||||
|
*/
|
||||||
|
function ln2br() {
|
||||||
|
return function(text) {
|
||||||
|
return text ? String(text).replace(/\r?\n/gm, '<br>') : undefined;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
angular.module('SOGo.Common')
|
||||||
|
.filter('ln2br', ln2br);
|
||||||
|
})();
|
|
@ -140,7 +140,6 @@
|
||||||
|
|
||||||
this.refs = [];
|
this.refs = [];
|
||||||
this.categories = [];
|
this.categories = [];
|
||||||
this.notes = [this.note];
|
|
||||||
this.c_screenname = null;
|
this.c_screenname = null;
|
||||||
angular.extend(this, data);
|
angular.extend(this, data);
|
||||||
if (!this.$$fullname)
|
if (!this.$$fullname)
|
||||||
|
@ -155,6 +154,25 @@
|
||||||
});
|
});
|
||||||
if (this.isgroup)
|
if (this.isgroup)
|
||||||
this.c_component = 'vlist';
|
this.c_component = 'vlist';
|
||||||
|
if (this.notes && this.notes.length)
|
||||||
|
this.notes = _.map(this.notes, function(note) { return { 'value': note }; });
|
||||||
|
else
|
||||||
|
this.notes = [ { value: '' } ];
|
||||||
|
// Instanciate Card objects for list members
|
||||||
|
angular.forEach(this.refs, function(o, i) {
|
||||||
|
if (o.email) o.emails = [{value: o.email}];
|
||||||
|
o.id = o.reference;
|
||||||
|
_this.refs[i] = new Card(o);
|
||||||
|
});
|
||||||
|
// Instanciate date object of birthday
|
||||||
|
if (this.birthday) {
|
||||||
|
Card.$Preferences.ready().then(function() {
|
||||||
|
var dlp = Card.$Preferences.$mdDateLocaleProvider;
|
||||||
|
_this.birthday = _this.birthday.parseDate(dlp, '%Y-%m-%d');
|
||||||
|
_this.$birthday = dlp.formatDate(_this.birthday);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
this.$loaded = angular.isDefined(this.c_name)? Card.STATUS.LOADED : Card.STATUS.NOT_LOADED;
|
this.$loaded = angular.isDefined(this.c_name)? Card.STATUS.LOADED : Card.STATUS.NOT_LOADED;
|
||||||
|
|
||||||
// An empty attribute to trick md-autocomplete when adding attendees from the appointment editor
|
// An empty attribute to trick md-autocomplete when adding attendees from the appointment editor
|
||||||
|
@ -497,12 +515,7 @@
|
||||||
delete _this[key];
|
delete _this[key];
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
angular.extend(this, this.$shadowData);
|
this.init(this.$shadowData);
|
||||||
// Reinstanciate Card objects for list members
|
|
||||||
angular.forEach(this.refs, function(o, i) {
|
|
||||||
if (o.email) o.emails = [{value: o.email}];
|
|
||||||
_this.refs[i] = new Card(o);
|
|
||||||
});
|
|
||||||
this.$shadowData = this.$omit(true);
|
this.$shadowData = this.$omit(true);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -547,19 +560,6 @@
|
||||||
// Expose the promise
|
// Expose the promise
|
||||||
this.$futureCardData = futureCardData.then(function(data) {
|
this.$futureCardData = futureCardData.then(function(data) {
|
||||||
_this.init(data);
|
_this.init(data);
|
||||||
// Instanciate Card objects for list members
|
|
||||||
angular.forEach(_this.refs, function(o, i) {
|
|
||||||
if (o.email) o.emails = [{value: o.email}];
|
|
||||||
o.id = o.reference;
|
|
||||||
_this.refs[i] = new Card(o);
|
|
||||||
});
|
|
||||||
if (_this.birthday) {
|
|
||||||
Card.$Preferences.ready().then(function() {
|
|
||||||
var dlp = Card.$Preferences.$mdDateLocaleProvider;
|
|
||||||
_this.birthday = _this.birthday.parseDate(dlp, '%Y-%m-%d');
|
|
||||||
_this.$birthday = dlp.formatDate(_this.birthday);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
// Mark card as loaded
|
// Mark card as loaded
|
||||||
_this.$loaded = Card.STATUS.LOADED;
|
_this.$loaded = Card.STATUS.LOADED;
|
||||||
// Make a copy of the data for an eventual reset
|
// Make a copy of the data for an eventual reset
|
||||||
|
@ -602,6 +602,10 @@
|
||||||
card.birthday = '';
|
card.birthday = '';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// We flatten the notes to an array of strings
|
||||||
|
if (this.notes)
|
||||||
|
card.notes = _.map(this.notes, 'value');
|
||||||
|
|
||||||
return card;
|
return card;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue