Merge pull request #285 from NicolasConstant/develop

0.28.1 PR
This commit is contained in:
Nicolas Constant 2020-05-17 18:21:02 -04:00 committed by GitHub
commit 18f6caf24a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 89 additions and 15 deletions

View File

@ -1,6 +1,6 @@
{
"name": "sengi",
"version": "0.28.0",
"version": "0.28.1",
"license": "AGPL-3.0-or-later",
"main": "main-electron.js",
"description": "A multi-account desktop client for Mastodon and Pleroma",

View File

@ -17,7 +17,7 @@ import { NotificationService } from '../../services/notification.service';
import { StatusWrapper } from '../../models/common.model';
import { AccountInfo } from '../../states/accounts.state';
import { InstancesInfoService } from '../../services/instances-info.service';
import { MediaService } from '../../services/media.service';
import { MediaService, MediaWrapper } from '../../services/media.service';
import { AutosuggestSelection, AutosuggestUserActionEnum } from './autosuggest/autosuggest.component';
import { EmojiPickerComponent } from './emoji-picker/emoji-picker.component';
import { PollEditorComponent } from './poll-editor/poll-editor.component';
@ -79,8 +79,14 @@ export class CreateStatusComponent implements OnInit, OnDestroy {
@Input('redraftedStatus')
set redraftedStatus(value: StatusWrapper) {
if (value) {
if (value) {
this.statusLoaded = false;
if(value.status && value.status.media_attachments){
for (const m of value.status.media_attachments) {
this.mediaService.addExistingMedia(new MediaWrapper(m.id, null, m));
}
}
const newLine = String.fromCharCode(13, 10);
let content = value.status.content;

View File

@ -88,11 +88,11 @@ export class SearchComponent implements OnInit {
})
.then((results: Results) => {
if (results) {
this.accounts = results.accounts.slice(0, 5);
this.accounts = results.accounts.slice(0, 7);
this.hashtags = results.hashtags;
if(!this.hashtags.map(x => x.toLowerCase()).includes(data.toLowerCase())){
this.hashtags.unshift(data);
if(data && data[0] === '#' && !this.hashtags.map(x => x.toLowerCase()).includes(data.replace('#', '').toLowerCase())){
this.hashtags.unshift(data.replace('#', ''));
}
for (let status of results.statuses) {
@ -107,6 +107,4 @@ export class SearchComponent implements OnInit {
})
.then(() => { this.isLoading = false; });
}
private
}

View File

@ -5,9 +5,10 @@
<img class="notification-hub__notification--avatar" *ngIf="notification.avatar"
src="{{ notification.avatar }}" />
<div class="notification-hub__notification--message">
<div class="notification-hub__notification--message" [class.notification-hub__notification--message--no-avatar]="!notification.avatar">
<span *ngIf="!notification.message">Error {{ notification.errorCode }}</span>
<span *ngIf="notification.message">{{ notification.message }}</span>
<span class="notification-hub__notification--count" *ngIf="notification.count > 1"> ({{ notification.count}})</span>
</div>
</div>
</div>

View File

@ -27,7 +27,17 @@
}
&--message {
padding-top: 4px;
margin-left: 37px;
&--no-avatar {
margin-left: 0px;
margin-left: 5px;
}
}
&--count {
color: rgba(255, 255, 255, .6);
}
}
}

View File

@ -7,17 +7,26 @@ import { NotificationService, NotificatioData } from '../../services/notificatio
styleUrls: ['./notification-hub.component.scss']
})
export class NotificationHubComponent implements OnInit {
notifications: NotificatioData[] = [];
notifications: NotificationWrapper[] = [];
constructor(private notificationService: NotificationService) { }
ngOnInit() {
this.notificationService.notifactionStream.subscribe((notification: NotificatioData) => {
this.notifications.push(notification);
let alreadyExistingNotification = this.notifications.find(x => x.avatar === notification.avatar && x.message === notification.message);
setTimeout(() => {
this.notifications = this.notifications.filter(x => x.id !== notification.id);
}, 5000);
if(alreadyExistingNotification){
alreadyExistingNotification.count++;
} else{
this.notifications.push(new NotificationWrapper(notification));
if(this.notifications.length > 3){
this.notifications.length = 3;
}
setTimeout(() => {
this.notifications = this.notifications.filter(x => x.id !== notification.id);
}, 5000);
}
});
//this.autoSubmit();
@ -35,3 +44,11 @@ export class NotificationHubComponent implements OnInit {
this.notifications = this.notifications.filter(x => x.id !== notification.id);
}
}
class NotificationWrapper extends NotificatioData {
constructor(data: NotificatioData) {
super(data.avatar, data.errorCode, data.message, data.isError);
}
count = 1;
}

View File

@ -11,6 +11,9 @@
<ng-template contextMenuItem (execute)="copyStatusLink()" *ngIf="statusWrapper">
Copy link to status
</ng-template>
<ng-template contextMenuItem (execute)="copyAllData()" *ngIf="statusWrapper">
Copy all data
</ng-template>
<ng-template contextMenuItem divider="true" *ngIf="statusWrapper"></ng-template>
<ng-template contextMenuItem (execute)="mentionAccount()" *ngIf="!isOwnerSelected">
Mention @{{ this.username }}

View File

@ -75,7 +75,7 @@ export class StatusUserContextMenuComponent implements OnInit, OnDestroy {
private checkStatus(accounts: AccountInfo[]): void {
const selectedAccount = accounts.find(x => x.isSelected);
this.isOwnerSelected = selectedAccount.username.toLowerCase() === this.displayedStatus.account.username.toLowerCase()
&& selectedAccount.instance.toLowerCase() === this.displayedStatus.account.url.replace('https://', '').split('/')[0].toLowerCase();
}
@ -118,6 +118,33 @@ export class StatusUserContextMenuComponent implements OnInit, OnDestroy {
return false;
}
copyAllData(): boolean {
const newLine = String.fromCharCode(13, 10);
let selBox = document.createElement('textarea');
selBox.style.position = 'fixed';
selBox.style.left = '0';
selBox.style.top = '0';
selBox.style.opacity = '0';
selBox.value = `${this.displayedStatus.url}${newLine}${newLine}${this.displayedStatus.content}${newLine}${newLine}`;
let parser = new DOMParser();
var dom = parser.parseFromString(this.displayedStatus.content, 'text/html')
selBox.value += `${dom.body.textContent}${newLine}${newLine}`;
for (const att of this.displayedStatus.media_attachments) {
selBox.value += `${att.url}${newLine}${newLine}`;
}
document.body.appendChild(selBox);
selBox.focus();
selBox.select();
document.execCommand('copy');
document.body.removeChild(selBox);
return false;
}
mentionAccount(): boolean {
this.navigationService.replyToUser(this.fullHandle, false);
return false;

View File

@ -12,6 +12,7 @@ import { NotificationService } from './notification.service';
})
export class MediaService {
mediaSubject: BehaviorSubject<MediaWrapper[]> = new BehaviorSubject<MediaWrapper[]>([]);
fileCache: { [url: string]: File } = {};
constructor(
private readonly notificationService: NotificationService,
@ -36,6 +37,7 @@ export class MediaService {
this.mastodonService.uploadMediaAttachment(account, file, null)
.then((attachment: Attachment) => {
this.fileCache[attachment.url] = file;
let currentMedias = this.mediaSubject.value;
let currentMedia = currentMedias.filter(x => x.id === uniqueId)[0];
if (currentMedia) {
@ -64,6 +66,15 @@ export class MediaService {
});
}
addExistingMedia(media: MediaWrapper){
if(!this.fileCache[media.attachment.url]) return;
media.file = this.fileCache[media.attachment.url];
let medias = this.mediaSubject.value;
medias.push(media);
this.mediaSubject.next(medias);
}
remove(media: MediaWrapper) {
let medias = this.mediaSubject.value;
let filteredMedias = medias.filter(x => x.id !== media.id);
@ -84,6 +95,7 @@ export class MediaService {
for (let media of medias) {
this.mastodonService.uploadMediaAttachment(account, media.file, media.description)
.then((attachment: Attachment) => {
this.fileCache[attachment.url] = media.file;
let currentMedias = this.mediaSubject.value;
let currentMedia = currentMedias.filter(x => x.id === media.id)[0];
if (currentMedia) {