mirror of
https://github.com/Start9Labs/start-os.git
synced 2026-03-31 04:23:40 +00:00
login page and fix autoscrolling on nav
This commit is contained in:
committed by
Aiden McClelland
parent
8d01ebe8b2
commit
21dd8fa618
@@ -47,7 +47,7 @@ export class AppActionsPage {
|
||||
})
|
||||
await alert.present()
|
||||
} else {
|
||||
const statuses = [...action.allowedStatuses]
|
||||
const statuses = [...action.value['allowedStatuses']]
|
||||
const last = statuses.pop()
|
||||
let statusesStr = statuses.join(', ')
|
||||
let error = null
|
||||
@@ -63,7 +63,7 @@ export class AppActionsPage {
|
||||
}
|
||||
const alert = await this.alertCtrl.create({
|
||||
header: 'Forbidden',
|
||||
message: error || `Action "${action.name}" can only be executed when service is ${statusesStr}`,
|
||||
message: error || `Action "${action.value.name}" can only be executed when service is ${statusesStr}`,
|
||||
buttons: ['OK'],
|
||||
cssClass: 'alert-error-message',
|
||||
})
|
||||
|
||||
@@ -41,7 +41,7 @@
|
||||
</ion-card-content>
|
||||
</ion-card>
|
||||
|
||||
<ion-spinner *ngIf="pkgsLoading; else pkgsLoaded" class="center" name="lines" color="warning"></ion-spinner>
|
||||
<ion-spinner *ngIf="pkgsLoading; else pkgsLoaded" style="padding-top: 200px;" name="lines" color="warning"></ion-spinner>
|
||||
|
||||
<ng-template #pkgsLoaded>
|
||||
<ion-card *ngFor="let pkg of pkgs" style="margin: 10px 10px;" [routerLink]="[pkg.id]">
|
||||
|
||||
@@ -145,11 +145,6 @@
|
||||
|
||||
<!-- versions -->
|
||||
<ion-item-divider></ion-item-divider>
|
||||
<ion-item *ngIf="vars.licenseLink" lines="none" button [href]="vars.licenseLink" target="_blank">
|
||||
<ion-icon slot="start" name="newspaper-outline"></ion-icon>
|
||||
<ion-label>License</ion-label>
|
||||
<ion-note slot="end">{{ vars.licenseName }}</ion-note>
|
||||
</ion-item>
|
||||
<ion-item lines="none" button (click)="presentAlertVersions()">
|
||||
<ion-icon color="dark" slot="start" name="file-tray-stacked-outline"></ion-icon>
|
||||
<ion-label color="dark">Other versions</ion-label>
|
||||
|
||||
@@ -104,7 +104,7 @@
|
||||
<ion-label><ion-text color="primary">Restore from Backup</ion-text></ion-label>
|
||||
</ion-item>
|
||||
<!-- donate -->
|
||||
<ion-item button [href]="manifest['donation-url']" target="_blank">
|
||||
<ion-item button (click)="donate(manifest)">
|
||||
<ion-icon slot="start" name="shapes-outline" color="primary"></ion-icon>
|
||||
<ion-label><ion-text color="primary">Donate</ion-text></ion-label>
|
||||
</ion-item>
|
||||
|
||||
@@ -2,7 +2,7 @@ import { Component, ViewChild } from '@angular/core'
|
||||
import { AlertController, NavController, ModalController, IonContent, PopoverController } from '@ionic/angular'
|
||||
import { ApiService } from 'src/app/services/api/api.service'
|
||||
import { ActivatedRoute, NavigationExtras } from '@angular/router'
|
||||
import { chill } from 'src/app/util/misc.util'
|
||||
import { chill, pauseFor } from 'src/app/util/misc.util'
|
||||
import { LoaderService } from 'src/app/services/loader.service'
|
||||
import { Observable, of, Subscription } from 'rxjs'
|
||||
import { wizardModal } from 'src/app/components/install-wizard/install-wizard.component'
|
||||
@@ -10,7 +10,7 @@ import { WizardBaker } from 'src/app/components/install-wizard/prebaked-wizards'
|
||||
import { InformationPopoverComponent } from 'src/app/components/information-popover/information-popover.component'
|
||||
import { ConfigService } from 'src/app/services/config.service'
|
||||
import { PatchDbModel } from 'src/app/models/patch-db/patch-db-model'
|
||||
import { DependencyErrorConfigUnsatisfied, DependencyErrorNotInstalled, DependencyErrorType, PackageDataEntry, PackageState } from 'src/app/models/patch-db/data-model'
|
||||
import { DependencyErrorConfigUnsatisfied, DependencyErrorNotInstalled, DependencyErrorType, Manifest, PackageDataEntry, PackageState } from 'src/app/models/patch-db/data-model'
|
||||
import { FEStatus } from 'src/app/services/pkg-status-rendering.service'
|
||||
import { ConnectionService } from 'src/app/services/connection.service'
|
||||
import { Recommendation } from 'src/app/components/recommendation-button/recommendation-button.component'
|
||||
@@ -54,6 +54,10 @@ export class AppInstalledShowPage {
|
||||
this.pkgSub = this.patch.watch$('package-data', this.pkgId).subscribe(pkg => this.pkg = pkg)
|
||||
}
|
||||
|
||||
async ngAfterViewInit () {
|
||||
this.content.scrollToPoint(undefined, 1)
|
||||
}
|
||||
|
||||
async ngOnDestroy () {
|
||||
this.pkgSub.unsubscribe()
|
||||
}
|
||||
@@ -114,6 +118,20 @@ export class AppInstalledShowPage {
|
||||
return this.navCtrl.navigateRoot('/services/installed')
|
||||
}
|
||||
|
||||
async donate (manifest: Manifest): Promise<void> {
|
||||
const url = manifest['donation-url']
|
||||
if (url) {
|
||||
window.open(url, '_blank')
|
||||
} else {
|
||||
const alert = await this.alertCtrl.create({
|
||||
header: 'Not Accepting Donations',
|
||||
message: `The developers of ${manifest.title} have not provided a donation URL. Please contact them directly if you insist on giving them money.`,
|
||||
buttons: ['OK'],
|
||||
})
|
||||
await alert.present()
|
||||
}
|
||||
}
|
||||
|
||||
async presentPopover (information: string, ev: any) {
|
||||
const popover = await this.popoverController.create({
|
||||
component: InformationPopoverComponent,
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { Component } from '@angular/core'
|
||||
import { Component, ViewChild } from '@angular/core'
|
||||
import { ActivatedRoute } from '@angular/router'
|
||||
import { ToastController } from '@ionic/angular'
|
||||
import { IonContent, ToastController } from '@ionic/angular'
|
||||
import { InstalledPackageDataEntry } from 'src/app/models/patch-db/data-model'
|
||||
import { PatchDbModel } from 'src/app/models/patch-db/patch-db-model'
|
||||
import { ConfigService } from 'src/app/services/config.service'
|
||||
@@ -14,6 +14,8 @@ import { copyToClipboard } from 'src/app/util/web.util'
|
||||
export class AppInterfacesPage {
|
||||
pkgId: string
|
||||
|
||||
@ViewChild(IonContent) content: IonContent
|
||||
|
||||
constructor (
|
||||
private readonly route: ActivatedRoute,
|
||||
private readonly toastCtrl: ToastController,
|
||||
@@ -25,6 +27,10 @@ export class AppInterfacesPage {
|
||||
this.pkgId = this.route.snapshot.paramMap.get('pkgId')
|
||||
}
|
||||
|
||||
async ngAfterViewInit () {
|
||||
this.content.scrollToPoint(undefined, 1)
|
||||
}
|
||||
|
||||
async copy (address: string): Promise<void> {
|
||||
let message = ''
|
||||
await copyToClipboard(address || '')
|
||||
|
||||
@@ -14,51 +14,62 @@
|
||||
|
||||
<ion-content class="ion-padding-top" *ngIf="patch.watch$('package-data', pkgId) | ngrxPush as pkg">
|
||||
|
||||
<ion-item *ngIf="error" style="margin-bottom: 16px;">
|
||||
<ion-text class="ion-text-wrap" color="danger">{{ error }}</ion-text>
|
||||
</ion-item>
|
||||
|
||||
<ion-item class="ion-margin-bottom">
|
||||
<ion-label class="ion-text-wrap">
|
||||
<p><ion-text color="dark">About</ion-text></p>
|
||||
<p>
|
||||
Select a location from which to restore {{ pkg.installed.manifest.title }}. This will overwrite all current data.
|
||||
</p>
|
||||
</ion-label>
|
||||
</ion-item>
|
||||
|
||||
<ion-spinner *ngIf="loading; else loaded" name="lines" color="warning" class="center"></ion-spinner>
|
||||
<ion-grid *ngIf="loading; else loaded" style="height: 100%;">
|
||||
<ion-row class="ion-align-items-center ion-text-center" style="height: 100%;">
|
||||
<ion-col>
|
||||
<ion-spinner name="lines" color="warning"></ion-spinner>
|
||||
<p>Loading Drives</p>
|
||||
</ion-col>
|
||||
</ion-row>
|
||||
</ion-grid>
|
||||
|
||||
<ng-template #loaded>
|
||||
|
||||
<ion-item *ngIf="allPartitionsMounted">
|
||||
<ion-text *ngIf="type === 'restore'" class="ion-text-wrap" color="warning">No partitions available. Insert the storage device containing the backup you intend to restore.</ion-text>
|
||||
<ion-item *ngIf="error" style="margin-bottom: 16px;">
|
||||
<ion-text class="ion-text-wrap" color="danger">{{ error }}</ion-text>
|
||||
</ion-item>
|
||||
|
||||
<ion-card *ngFor="let disk of disks | keyvalue">
|
||||
<ion-card-header>
|
||||
<ion-card-title>
|
||||
{{ disk.value.size }}
|
||||
</ion-card-title>
|
||||
<ion-card-subtitle>
|
||||
{{ disk.key }}
|
||||
</ion-card-subtitle>
|
||||
</ion-card-header>
|
||||
<ion-card-content>
|
||||
<ion-item-group>
|
||||
<ion-item button *ngFor="let partition of disk.value.partitions | keyvalue" [disabled]="partition.value['is-mounted']" (click)="presentModal(partition.key, partition.value)">
|
||||
<ion-icon slot="start" name="save-outline"></ion-icon>
|
||||
<ion-label>
|
||||
<h2>{{ partition.value.label || partition.key }} ({{ partition.value.size || 'unknown size' }})</h2>
|
||||
<p *ngIf="!partition.value['is-mounted']; else unavailable"><ion-text color="success">Available</ion-text></p>
|
||||
<ng-template #unavailable>
|
||||
<p><ion-text color="danger">Unavailable</ion-text></p>
|
||||
</ng-template>
|
||||
</ion-label>
|
||||
</ion-item>
|
||||
</ion-item-group>
|
||||
</ion-card-content>
|
||||
</ion-card>
|
||||
|
||||
<ion-item class="ion-margin-bottom">
|
||||
<ion-label class="ion-text-wrap">
|
||||
<p><ion-text color="dark">About</ion-text></p>
|
||||
<p>
|
||||
Select a location from which to restore {{ pkg.installed.manifest.title }}. This will overwrite all current data.
|
||||
</p>
|
||||
</ion-label>
|
||||
</ion-item>
|
||||
|
||||
<ion-spinner *ngIf="loading; else loaded" name="lines" color="warning" class="center"></ion-spinner>
|
||||
|
||||
<ng-template #loaded>
|
||||
|
||||
<ion-item *ngIf="allPartitionsMounted">
|
||||
<ion-text *ngIf="type === 'restore'" class="ion-text-wrap" color="warning">No partitions available. Insert the storage device containing the backup you intend to restore.</ion-text>
|
||||
</ion-item>
|
||||
|
||||
<ion-card *ngFor="let disk of disks | keyvalue">
|
||||
<ion-card-header>
|
||||
<ion-card-title>
|
||||
{{ disk.value.size }}
|
||||
</ion-card-title>
|
||||
<ion-card-subtitle>
|
||||
{{ disk.key }}
|
||||
</ion-card-subtitle>
|
||||
</ion-card-header>
|
||||
<ion-card-content>
|
||||
<ion-item-group>
|
||||
<ion-item button *ngFor="let partition of disk.value.partitions | keyvalue" [disabled]="partition.value['is-mounted']" (click)="presentModal(partition.key, partition.value)">
|
||||
<ion-icon slot="start" name="save-outline"></ion-icon>
|
||||
<ion-label>
|
||||
<h2>{{ partition.value.label || partition.key }} ({{ partition.value.size || 'unknown size' }})</h2>
|
||||
<p *ngIf="!partition.value['is-mounted']; else unavailable"><ion-text color="success">Available</ion-text></p>
|
||||
<ng-template #unavailable>
|
||||
<p><ion-text color="danger">Unavailable</ion-text></p>
|
||||
</ng-template>
|
||||
</ion-label>
|
||||
</ion-item>
|
||||
</ion-item-group>
|
||||
</ion-card-content>
|
||||
</ion-card>
|
||||
</ng-template>
|
||||
</ng-template>
|
||||
|
||||
</ion-content>
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { Component } from '@angular/core'
|
||||
import { LoadingController, ModalController } from '@ionic/angular'
|
||||
import { Component, ViewChild } from '@angular/core'
|
||||
import { IonContent, LoadingController, ModalController } from '@ionic/angular'
|
||||
import { ApiService } from 'src/app/services/api/api.service'
|
||||
import { BackupConfirmationComponent } from 'src/app/modals/backup-confirmation/backup-confirmation.component'
|
||||
import { DiskInfo, PartitionInfoEntry } from 'src/app/services/api/api-types'
|
||||
@@ -18,6 +18,8 @@ export class AppRestorePage {
|
||||
error: string
|
||||
allPartitionsMounted: boolean
|
||||
|
||||
@ViewChild(IonContent) content: IonContent
|
||||
|
||||
constructor (
|
||||
private readonly route: ActivatedRoute,
|
||||
private readonly modalCtrl: ModalController,
|
||||
@@ -31,6 +33,10 @@ export class AppRestorePage {
|
||||
this.getExternalDisks()
|
||||
}
|
||||
|
||||
async ngAfterViewInit () {
|
||||
this.content.scrollToPoint(undefined, 1)
|
||||
}
|
||||
|
||||
async doRefresh () {
|
||||
this.loading = true
|
||||
await this.getExternalDisks()
|
||||
|
||||
Reference in New Issue
Block a user