Browse Source

Panel and modal refactored

pull/271/head
Sebastian Stehle 8 years ago
parent
commit
3c0626e554
  1. 2
      src/Squidex/app/features/administration/pages/event-consumers/event-consumers-page.component.html
  2. 6
      src/Squidex/app/features/administration/pages/event-consumers/event-consumers-page.component.ts
  3. 4
      src/Squidex/app/features/administration/pages/users/user-page.component.html
  4. 4
      src/Squidex/app/features/administration/pages/users/users-page.component.html
  5. 6
      src/Squidex/app/features/apps/pages/apps-page.component.html
  6. 6
      src/Squidex/app/features/apps/pages/apps-page.component.ts
  7. 13
      src/Squidex/app/features/apps/pages/onboarding-dialog.component.html
  8. 108
      src/Squidex/app/features/assets/pages/assets-page.component.html
  9. 4
      src/Squidex/app/features/content/pages/content/content-field.component.html
  10. 40
      src/Squidex/app/features/content/pages/content/content-history.component.html
  11. 103
      src/Squidex/app/features/content/pages/content/content-page.component.html
  12. 177
      src/Squidex/app/features/content/pages/contents/contents-page.component.html
  13. 42
      src/Squidex/app/features/content/pages/schemas/schemas-page.component.html
  14. 8
      src/Squidex/app/features/content/shared/content-item.component.html
  15. 190
      src/Squidex/app/features/rules/pages/events/rule-events-page.component.html
  16. 237
      src/Squidex/app/features/rules/pages/rules/rule-wizard.component.html
  17. 4
      src/Squidex/app/features/rules/pages/rules/rule-wizard.component.ts
  18. 164
      src/Squidex/app/features/rules/pages/rules/rules-page.component.html
  19. 4
      src/Squidex/app/features/rules/pages/rules/rules-page.component.ts
  20. 8
      src/Squidex/app/features/schemas/pages/schema/field-wizard.component.html
  21. 20
      src/Squidex/app/features/schemas/pages/schema/schema-page.component.html
  22. 2
      src/Squidex/app/features/schemas/pages/schema/schema-page.component.ts
  23. 6
      src/Squidex/app/features/schemas/pages/schema/schema-scripts-form.component.html
  24. 4
      src/Squidex/app/features/schemas/pages/schema/types/date-time-validation.component.html
  25. 4
      src/Squidex/app/features/schemas/pages/schemas/schema-form.component.html
  26. 2
      src/Squidex/app/features/schemas/pages/schemas/schemas-page.component.html
  27. 9
      src/Squidex/app/features/schemas/pages/schemas/schemas-page.component.ts
  28. 20
      src/Squidex/app/features/schemas/state/schemas.state.ts
  29. 29
      src/Squidex/app/features/settings/pages/clients/client.component.html
  30. 6
      src/Squidex/app/features/settings/pages/clients/client.component.ts
  31. 10
      src/Squidex/app/features/settings/pages/patterns/pattern.component.ts
  32. 4
      src/Squidex/app/features/settings/pages/plans/plans-page.component.html
  33. 10
      src/Squidex/app/features/settings/settings-area.component.html
  34. 2
      src/Squidex/app/framework/angular/forms/autocomplete.component.html
  35. 4
      src/Squidex/app/framework/angular/forms/dropdown.component.html
  36. 3
      src/Squidex/app/framework/angular/forms/form-error.component.html
  37. 2
      src/Squidex/app/framework/angular/forms/form-error.component.scss
  38. 24
      src/Squidex/app/framework/angular/forms/form-error.component.ts
  39. 5
      src/Squidex/app/framework/angular/forms/stars.component.html
  40. 31
      src/Squidex/app/framework/angular/modals/dialog-renderer.component.html
  41. 2
      src/Squidex/app/framework/angular/modals/modal-dialog.component.html
  42. 5
      src/Squidex/app/framework/angular/modals/modal-dialog.component.ts
  43. 1
      src/Squidex/app/framework/declarations.ts
  44. 3
      src/Squidex/app/framework/module.ts
  45. 4
      src/Squidex/app/shared/components/app-form.component.html
  46. 51
      src/Squidex/app/shared/components/asset.component.html
  47. 4
      src/Squidex/app/shared/components/asset.component.ts
  48. 22
      src/Squidex/app/shared/components/help.component.html
  49. 38
      src/Squidex/app/shared/components/history.component.html
  50. 6
      src/Squidex/app/shared/state/apps.state.ts
  51. 14
      src/Squidex/app/shell/pages/internal/apps-menu.component.html

2
src/Squidex/app/features/administration/pages/event-consumers/event-consumers-page.component.html

@ -61,7 +61,7 @@
</ng-container>
</sqx-panel>
<sqx-modal-dialog *sqxModalView="eventConsumerErrorDialog;onRoot:true" @fade (close)="eventConsumerErrorDialog.hide()">
<sqx-modal-dialog *sqxModalView="eventConsumerErrorDialog;onRoot:true" (close)="eventConsumerErrorDialog.hide()">
<ng-container #title>
Error
</ng-container>

6
src/Squidex/app/features/administration/pages/event-consumers/event-consumers-page.component.ts

@ -9,7 +9,6 @@ import { Component, OnDestroy, OnInit } from '@angular/core';
import { Observable, Subscription } from 'rxjs';
import {
fadeAnimation,
DialogService,
ImmutableArray,
ModalView
@ -20,10 +19,7 @@ import { EventConsumerDto, EventConsumersService } from './../../services/event-
@Component({
selector: 'sqx-event-consumers-page',
styleUrls: ['./event-consumers-page.component.scss'],
templateUrl: './event-consumers-page.component.html',
animations: [
fadeAnimation
]
templateUrl: './event-consumers-page.component.html'
})
export class EventConsumersPageComponent implements OnDestroy, OnInit {
private subscription: Subscription;

4
src/Squidex/app/features/administration/pages/users/user-page.component.html

@ -23,9 +23,7 @@
</ng-container>
<ng-container content>
<ng-container *ngIf="userForm.error | async; let error">
<div class="form-alert form-alert-error" [innerHTML]="error"></div>
</ng-container>
<sqx-form-error [error]="userForm.error | async"></sqx-form-error>
<div class="form-group">
<label for="email">Email</label>

4
src/Squidex/app/features/administration/pages/users/users-page.component.html

@ -61,14 +61,14 @@
<span class="user-email table-cell">{{user.email}}</span>
</td>
<td class="cell-actions">
<span *ngIf="user.id !== authState.user?.id">
<ng-container *ngIf="user.id !== authState.user?.id">
<button class="btn btn-link" (click)="lock(user); $event.stopPropagation();" *ngIf="!user.isLocked" title="Lock User">
<i class="icon icon-unlocked"></i>
</button>
<button class="btn btn-link" (click)="unlock(user); $event.stopPropagation();" *ngIf="user.isLocked" title="Unlock User">
<i class="icon icon-lock"></i>
</button>
</span>
</ng-container>
<button *ngIf="user.id === authState.user?.id" class="btn btn-link invisible">
&nbsp;
</button>

6
src/Squidex/app/features/apps/pages/apps-page.component.html

@ -74,12 +74,10 @@
</div>
</div>
<div class="modal" *sqxModalView="addAppDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
<ng-container *sqxModalView="addAppDialog;onRoot:true">
<sqx-app-form [template]="appTemplate"
(completed)="addAppDialog.hide()">
</sqx-app-form>
</div>
</ng-container>
<sqx-onboarding-dialog [modalView]="onboardingModal"></sqx-onboarding-dialog>

6
src/Squidex/app/features/apps/pages/apps-page.component.ts

@ -12,7 +12,6 @@ import {
AppDto,
AppsState,
AuthService,
fadeAnimation,
ImmutableArray,
ModalView,
OnboardingService
@ -21,10 +20,7 @@ import {
@Component({
selector: 'sqx-apps-page',
styleUrls: ['./apps-page.component.scss'],
templateUrl: './apps-page.component.html',
animations: [
fadeAnimation
]
templateUrl: './apps-page.component.html'
})
export class AppsPageComponent implements OnDestroy, OnInit {
private appsSubscription: Subscription;

13
src/Squidex/app/features/apps/pages/onboarding-dialog.component.html

@ -1,7 +1,6 @@
<div class="modal" *sqxModalView="modalView;onRoot:true;closeAuto:false" @fade>
<div class="modal-backdrop"></div>
<div class="modal-dialog">
<div class="modal-content">
<ng-container *sqxModalView="modalView;onRoot:true;closeAuto:false">
<sqx-modal-dialog showHeader="false">
<ng-container content>
<a class="header-right modal-close" (click)="modalView.hide()">Skip Tour</a>
<div class="onboarding-step" *ngIf="step === 0">
@ -145,6 +144,6 @@
</div>
</div>
</div>
</div>
</div>
</div>
</ng-container>
</sqx-modal-dialog>
</ng-container>

108
src/Squidex/app/features/assets/pages/assets-page.component.html

@ -1,70 +1,62 @@
<sqx-title message="{app} | Assets" parameter1="app" [value1]="ctx.appName"></sqx-title>
<sqx-panel desiredWidth="60rem">
<div class="panel-header">
<div class="panel-title-row">
<div class="float-right">
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Assets (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<form class="form-inline" (ngSubmit)="search()">
<input class="form-control" #inputFind [formControl]="assetsFilter" placeholder="Search for assets" />
</form>
<ng-container title>
Assets
</ng-container>
<ng-container header>
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Assets (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<form class="form-inline" (ngSubmit)="search()">
<input class="form-control" #inputFind [formControl]="assetsFilter" placeholder="Search for assets" />
</form>
</ng-container>
<ng-container content>
<div class="file-drop" (sqxFileDrop)="addFiles($event)">
<h3 class="file-drop-header">Drop files here to upload</h3>
<div class="file-drop-or">or</div>
<div class="file-drop-button">
<span class="btn btn-success" (click)="fileInput.click()">
<span>Select File(s)</span>
<input class="file-drop-button-input" type="file" (change)="addFiles($event.target.files)" #fileInput multiple />
</span>
</div>
<h3 class="panel-title">Assets</h3>
<div class="file-drop-info">Drop file on existing item to replace the asset with a newer version.</div>
</div>
<a class="panel-close" sqxParentLink isLazyLoaded="true">
<i class="icon-close"></i>
</a>
</div>
<div class="panel-main">
<div class="panel-content panel-content-scroll">
<div class="file-drop" (sqxFileDrop)="addFiles($event)">
<h3 class="file-drop-header">Drop files here to upload</h3>
<div class="file-drop-or">or</div>
<div class="file-drop-button">
<span class="btn btn-success" (click)="fileInput.click()">
<span>Select File(s)</span>
<input class="file-drop-button-input" type="file" (change)="addFiles($event.target.files)" #fileInput multiple />
</span>
</div>
<div class="file-drop-info">Drop file on existing item to replace the asset with a newer version.</div>
</div>
<div class="row">
<sqx-asset class="col-3" *ngFor="let file of newFiles" [initFile]="file"
(failed)="onAssetFailed(file)"
(loaded)="onAssetLoaded(file, $event)">
</sqx-asset>
<sqx-asset class="col-3" *ngFor="let asset of assetsItems" [asset]="asset"
(deleting)="onAssetDeleting($event)"
(updated)="onAssetUpdated($event)">
</sqx-asset>
</div>
<div class="row">
<sqx-asset class="col-3" *ngFor="let file of newFiles" [initFile]="file"
(failed)="onAssetFailed(file)"
(loaded)="onAssetLoaded(file, $event)">
</sqx-asset>
<sqx-asset class="col-3" *ngFor="let asset of assetsItems" [asset]="asset"
(deleting)="onAssetDeleting($event)"
(updated)="onAssetUpdated($event)">
</sqx-asset>
</div>
<div class="clearfix" *ngIf="assetsPager.numberOfItems > 0">
<div class="float-right pagination">
<span class="pagination-text">{{assetsPager.itemFirst}}-{{assetsPager.itemLast}} of {{assetsPager.numberOfItems}}</span>
<div class="clearfix" *ngIf="assetsPager.numberOfItems > 0">
<div class="float-right pagination">
<span class="pagination-text">{{assetsPager.itemFirst}}-{{assetsPager.itemLast}} of {{assetsPager.numberOfItems}}</span>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!assetsPager.canGoPrev" (click)="goPrev()">
<i class="icon-angle-left"></i>
</button>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!assetsPager.canGoNext" (click)="goNext()">
<i class="icon-angle-right"></i>
</button>
</div>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!assetsPager.canGoPrev" (click)="goPrev()">
<i class="icon-angle-left"></i>
</button>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!assetsPager.canGoNext" (click)="goNext()">
<i class="icon-angle-right"></i>
</button>
</div>
</div>
</div>
</ng-container>
</sqx-panel>

4
src/Squidex/app/features/content/pages/content/content-field.component.html

@ -5,7 +5,7 @@
<span class="field-disabled" *ngIf="field.isDisabled">Disabled</span>
<div *ngIf="field.isLocalizable && languages.length > 1">
<ng-container *ngIf="field.isLocalizable && languages.length > 1">
<div class="languages-buttons" #buttonLanguages>
<sqx-language-selector size="sm" (selectedLanguageChanged)="selectLanguage($event)" [languages]="languages"></sqx-language-selector>
</div>
@ -13,7 +13,7 @@
<sqx-onboarding-tooltip id="languages" [for]="buttonLanguages" position="topRight" after="120000">
Please remember to check all languages when you see validation errors.
</sqx-onboarding-tooltip>
</div>
</ng-container>
<sqx-control-errors [for]="selectedFormControl" [fieldName]="field.displayName" [submitted]="contentFormSubmitted"></sqx-control-errors>

40
src/Squidex/app/features/content/pages/content/content-history.component.html

@ -1,29 +1,21 @@
<sqx-panel desiredWidth="16rem">
<div class="panel-header">
<div class="panel-title-row">
<h3 class="panel-title">Activity</h3>
</div>
<a class="panel-close" sqxParentLink>
<i class="icon-close"></i>
</a>
</div>
<sqx-panel desiredWidth="16rem" isBlank="true">
<ng-container title>
Activity
</ng-container>
<div class="panel-main">
<div class="panel-content panel-content-blank">
<div *ngFor="let event of events | async" class="event">
<div class="event-left">
<img class="user-picture" [attr.title]="event.actor | sqxUserNameRef:null" [attr.src]="event.actor | sqxUserPictureRef" />
<ng-container content>
<div *ngFor="let event of events | async" class="event">
<div class="event-left">
<img class="user-picture" [attr.title]="event.actor | sqxUserNameRef:null" [attr.src]="event.actor | sqxUserPictureRef" />
</div>
<div class="event-main">
<div class="event-message">
<span class="event-actor user-ref">{{event.actor | sqxUserNameRef:null}}</span> <span [innerHTML]="format(event.message) | async"></span>
</div>
<div class="event-main">
<div class="event-message">
<span class="event-actor user-ref">{{event.actor | sqxUserNameRef:null}}</span> <span [innerHTML]="format(event.message) | async"></span>
</div>
<div class="event-created">{{event.created | sqxFromNow}}</div>
<div class="event-created">{{event.created | sqxFromNow}}</div>
<a class="event-load" (click)="loadVersion(event.version)">Load this Version</a>
</div>
</div>
<a class="event-load" (click)="loadVersion(event.version)">Load this Version</a>
</div>
</div>
</div>
</ng-container>
</sqx-panel>

103
src/Squidex/app/features/content/pages/content/content-page.component.html

@ -2,69 +2,62 @@
<form [formGroup]="contentForm" (ngSubmit)="saveAndPublish()">
<sqx-panel desiredWidth="53rem">
<div class="panel-header">
<div class="panel-title-row">
<div class="float-right" *ngIf="!content || content.status !== 'Archived'">
<span *ngIf="isNewMode">
<button type="button" class="btn btn-secondary" (click)="saveAsDraft()" title="CTRL + S">
Save as Draft
</button>
<ng-container title>
<ng-container *ngIf="isNewMode">
New Content
</ng-container>
<ng-container *ngIf="!isNewMode && content.status !== 'Archived'">
Edit Content
</ng-container>
<ng-container *ngIf="!isNewMode && content.status === 'Archived'">
Show Content
</ng-container>
</ng-container>
<button type="submit" class="btn btn-primary">
Save and Publish
</button>
</span>
<span *ngIf="!isNewMode">
<button type="submit" class="btn btn-primary" title="CTRL + S">
Save
</button>
</span>
<sqx-shortcut keys="ctrl+s" (trigger)="saveAndPublish()"></sqx-shortcut>
</div>
<h3 class="panel-title" *ngIf="isNewMode">
New Content
</h3>
<h3 class="panel-title" *ngIf="!isNewMode && content.status !== 'Archived'">
Edit Content
</h3>
<h3 class="panel-title" *ngIf="!isNewMode && content.status === 'Archived'">
Show Content
</h3>
</div>
<ng-container header>
<ng-container *ngIf="isNewMode; else notNew">
<button type="button" class="btn btn-secondary" (click)="saveAsDraft()" title="CTRL + S">
Save as Draft
</button>
<a class="panel-close" sqxParentLink>
<i class="icon-close"></i>
</a>
</div>
<button type="submit" class="btn btn-primary">
Save and Publish
</button>
</ng-container>
<ng-template #notNew>
<button type="submit" class="btn btn-primary" title="CTRL + S">
Save
</button>
</ng-template>
<div class="panel-main">
<div class="panel-content panel-content-scroll">
<div class="panel-alert panel-alert-danger" *ngIf="contentOld">
<div class="float-right">
<a class="force" (click)="showLatest()">View latest</a>
</div>
Viewing <strong>{{content.lastModifiedBy | sqxUserNameRef:null}}'s</strong> changes of {{content.lastModified | sqxShortDate}}.
</div>
<sqx-shortcut keys="ctrl+s" (trigger)="saveAndPublish()"></sqx-shortcut>
</ng-container>
<div *ngFor="let field of schema.fields">
<sqx-content-field [field]="field" [fieldForm]="contentForm.controls[field.name]" [languages]="languages" [contentFormSubmitted]="contentFormSubmitted"></sqx-content-field>
<ng-container content>
<div class="panel-alert panel-alert-danger" *ngIf="contentOld">
<div class="float-right">
<a class="force" (click)="showLatest()">View latest</a>
</div>
Viewing <strong>{{content.lastModifiedBy | sqxUserNameRef:null}}'s</strong> changes of {{content.lastModified | sqxShortDate}}.
</div>
<div class="panel-sidebar">
<a class="panel-link" routerLink="history" routerLinkActive="active" #linkHistory *ngIf="!isNewMode">
<i class="icon-time"></i>
</a>
<a class="panel-link" routerLink="assets" routerLinkActive="active">
<i class="icon-media"></i>
</a>
<sqx-onboarding-tooltip id="history" [for]="linkHistory" position="leftTop" after="120000" *ngIf="!isNewMode">
The sidebar navigation contains useful context specific links. Here you can view the history how this schema has changed over time.
</sqx-onboarding-tooltip>
<div *ngFor="let field of schema.fields">
<sqx-content-field [field]="field" [fieldForm]="contentForm.controls[field.name]" [languages]="languages" [contentFormSubmitted]="contentFormSubmitted"></sqx-content-field>
</div>
</div>
</ng-container>
<ng-container sidebar>
<a class="panel-link" routerLink="history" routerLinkActive="active" #linkHistory *ngIf="!isNewMode">
<i class="icon-time"></i>
</a>
<a class="panel-link" routerLink="assets" routerLinkActive="active">
<i class="icon-media"></i>
</a>
<sqx-onboarding-tooltip id="history" [for]="linkHistory" position="leftTop" after="120000" *ngIf="!isNewMode">
The sidebar navigation contains useful context specific links. Here you can view the history how this schema has changed over time.
</sqx-onboarding-tooltip>
</ng-container>
</sqx-panel>
</form>

177
src/Squidex/app/features/content/pages/contents/contents-page.component.html

@ -1,72 +1,64 @@
<sqx-title message="{app} | {schema} | Contents" parameter1="app" parameter2="schema" [value1]="ctx.appName" [value2]="schema?.displayName"></sqx-title>
<sqx-panel [desiredWidth]="isReadOnly ? '40rem' : '60rem'">
<div class="panel-header">
<div class="panel-title-row">
<div class="float-right">
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Contents (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+g" (trigger)="newButton.click()" *ngIf="!isReadOnly"></sqx-shortcut>
<form class="form-inline" (ngSubmit)="search()">
<input class="form-control form-control-expandable" #inputFind [formControl]="contentsFilter" placeholder="Search for content" />
<a class="expand-search" (click)="searchModal.toggle()" #archive>
<i class="icon-caret-down"></i>
</a>
</form>
<sqx-onboarding-tooltip id="contentArchive" [for]="archive" position="bottomRight" after="60000">
Click this icon to show the advanced search menu and to show the archive!
</sqx-onboarding-tooltip>
<sqx-onboarding-tooltip id="contentFind" [for]="inputFind" position="bottomRight" after="120000">
Search for content using full text search over all fields and languages!
</sqx-onboarding-tooltip>
<div class="dropdown-menu" *sqxModalView="searchModal" [sqxModalTarget]="inputFind">
<sqx-search-form
[canArchive]="!isReadOnly"
(queryChanged)="contentsFilter.setValue($event, { emitEvent: false })"
[query]="contentsFilter.value"
(archivedChanged)="updateArchive($event)"
[archived]="isArchive">
</sqx-search-form>
</div>
<span *ngIf="!isReadOnly && languages.length > 1">
<sqx-language-selector class="languages-buttons" (selectedLanguageChanged)="selectLanguage($event)" [languages]="languages"></sqx-language-selector>
</span>
<button *ngIf="!isReadOnly" class="btn btn-success" #newButton routerLink="new" title="New Content (CTRL + SHIFT + G)">
<i class="icon-plus"></i> New
</button>
</div>
<h3 class="panel-title" *ngIf="!isReadOnly && !isArchive">
Contents
</h3>
<h3 class="panel-title" *ngIf="isArchive">
Archive
</h3>
<h3 class="panel-title" *ngIf="isReadOnly">
References
</h3>
<ng-container title>
<ng-container *ngIf="!isReadOnly && !isArchive">
Contents
</ng-container>
<ng-container *ngIf="isArchive">
Archive
</ng-container>
<ng-container *ngIf="isReadOnly">
References
</ng-container>
</ng-container>
<ng-container header>
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Contents (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+g" (trigger)="newButton.click()" *ngIf="!isReadOnly"></sqx-shortcut>
<form class="form-inline" (ngSubmit)="search()">
<input class="form-control form-control-expandable" #inputFind [formControl]="contentsFilter" placeholder="Search for content" />
<a class="expand-search" (click)="searchModal.toggle()" #archive>
<i class="icon-caret-down"></i>
</a>
</form>
<sqx-onboarding-tooltip id="contentArchive" [for]="archive" position="bottomRight" after="60000">
Click this icon to show the advanced search menu and to show the archive!
</sqx-onboarding-tooltip>
<sqx-onboarding-tooltip id="contentFind" [for]="inputFind" position="bottomRight" after="120000">
Search for content using full text search over all fields and languages!
</sqx-onboarding-tooltip>
<div class="dropdown-menu" *sqxModalView="searchModal" [sqxModalTarget]="inputFind">
<sqx-search-form
[canArchive]="!isReadOnly"
(queryChanged)="contentsFilter.setValue($event, { emitEvent: false })"
[query]="contentsFilter.value"
(archivedChanged)="updateArchive($event)"
[archived]="isArchive">
</sqx-search-form>
</div>
<a class="panel-close" sqxParentLink>
<i class="icon-close"></i>
</a>
</div>
<ng-container *ngIf="!isReadOnly && languages.length > 1">
<sqx-language-selector class="languages-buttons" (selectedLanguageChanged)="selectLanguage($event)" [languages]="languages"></sqx-language-selector>
</ng-container>
<button *ngIf="!isReadOnly" class="btn btn-success" #newButton routerLink="new" title="New Content (CTRL + SHIFT + G)">
<i class="icon-plus"></i> New
</button>
</ng-container>
<div class="panel-main">
<div class="panel-content grid">
<ng-container content>
<div class="grid">
<div class="grid-header">
<table class="table table-items table-fixed" *ngIf="contentItems">
<thead>
@ -166,43 +158,38 @@
</div>
</div>
</div>
</div>
</ng-container>
</sqx-panel>
<router-outlet></router-outlet>
<div class="modal" *sqxModalView="dueTimeDialog;onRoot:true">
<div class="modal-backdrop"></div>
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title">{{dueTimeAction}} content item(s)</h4>
<ng-container *sqxModalView="dueTimeDialog;onRoot:true">
<sqx-modal-dialog (close)="cancelStatusChange()">
<ng-container title>
{{dueTimeAction}} content item(s)
</ng-container>
<ng-container content>
<div class="form-check">
<input class="form-check-input" type="radio" [(ngModel)]="dueTimeMode" value="Immediately" id="immediately">
<label class="form-check-label" for="immediately">
{{dueTimeAction}} content item(s) immediately.
</label>
</div>
<div class="modal-body">
<div class="form-check">
<input class="form-check-input" type="radio" [(ngModel)]="dueTimeMode" value="Immediately" id="immediately">
<label class="form-check-label" for="immediately">
{{dueTimeAction}} content item(s) immediately.
</label>
</div>
<div class="form-check">
<input class="form-check-input" type="radio" [(ngModel)]="dueTimeMode" value="Scheduled" id="scheduled">
<label class="form-check-label" for="scheduled">
{{dueTimeAction}} content item(s) at a later point date and time.
</label>
</div>
<sqx-date-time-editor [disabled]="dueTimeMode === 'Immediately'" mode="DateTime" hideClear="true" [(ngModel)]="dueTime"></sqx-date-time-editor>
<div class="form-check">
<input class="form-check-input" type="radio" [(ngModel)]="dueTimeMode" value="Scheduled" id="scheduled">
<label class="form-check-label" for="scheduled">
{{dueTimeAction}} content item(s) at a later point date and time.
</label>
</div>
<div class="modal-footer">
<div class="clearfix">
<button type="button" class="float-left btn btn-secondary" (click)="cancelStatusChange()">Cancel</button>
<button type="button" class="float-right btn btn-primary" [disabled]="dueTimeMode === 'Scheduled' && !dueTime" (click)="confirmStatusChange()">Confirm</button>
</div>
</div>
</div>
</div>
</div>
<sqx-date-time-editor [disabled]="dueTimeMode === 'Immediately'" mode="DateTime" hideClear="true" [(ngModel)]="dueTime"></sqx-date-time-editor>
</ng-container>
<ng-container footer>
<button type="button" class="float-left btn btn-secondary" (click)="cancelStatusChange()">Cancel</button>
<button type="button" class="float-right btn btn-primary" [disabled]="dueTimeMode === 'Scheduled' && !dueTime" (click)="confirmStatusChange()">Confirm</button>
</ng-container>
</sqx-modal-dialog>
</ng-container>

42
src/Squidex/app/features/content/pages/schemas/schemas-page.component.html

@ -1,35 +1,27 @@
<sqx-title message="{app} | Schemas" parameter1="app" [value1]="ctx.appName"></sqx-title>
<sqx-panel theme="dark" desiredWidth="16rem">
<div class="panel-header">
<div class="panel-title-row">
<h3 class="panel-title">Schemas</h3>
</div>
<a class="panel-close" sqxParentLink isLazyLoaded="true">
<i class="icon-close"></i>
</a>
<sqx-panel theme="dark" desiredWidth="16rem" showSecondHeader="true">
<ng-container title>
Schemas
</ng-container>
<div class="panel-header-row">
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<ng-container secondHeader>
<sqx-shortcut keys="ctrl+shift+f" (trigger)="inputFind.focus()"></sqx-shortcut>
<div class="search-form">
<input class="form-control form-control-dark" #inputFind [formControl]="schemasFilter" placeholder="Search for schemas" />
<div class="search-form">
<input class="form-control form-control-dark" #inputFind [formControl]="schemasFilter" placeholder="Search for schemas" />
<i class="icon-search"></i>
</div>
<i class="icon-search"></i>
</div>
</div>
</ng-container>
<div class="panel-main">
<div class="panel-content">
<ul class="nav nav-panel nav-dark nav-dark-bordered flex-column">
<li class="nav-item" *ngFor="let schema of schemasFiltered | async">
<a class="nav-link" [routerLink]="schema.name" routerLinkActive="active">{{schema.displayName}} <i class="icon-angle-right"></i></a>
</li>
</ul>
</div>
</div>
<ng-container content>
<ul class="nav nav-panel nav-dark nav-dark-bordered flex-column">
<li class="nav-item" *ngFor="let schema of schemasFiltered | async">
<a class="nav-link" [routerLink]="schema.name" routerLinkActive="active">{{schema.displayName}} <i class="icon-angle-right"></i></a>
</li>
</ul>
</ng-container>
</sqx-panel>
<router-outlet></router-outlet>

8
src/Squidex/app/features/content/shared/content-item.component.html

@ -56,21 +56,21 @@
</div>
</td>
<td class="cell-time" (click)="shouldStop($event)">
<span *ngIf="!content.scheduledTo">
<ng-container *ngIf="!content.scheduledTo">
<span class="content-status content-status-{{content.status | lowercase}}" #statusIcon>
<i class="icon-circle"></i>
</span>
<sqx-tooltip [target]="statusIcon">{{content.status}}</sqx-tooltip>
</span>
</ng-container>
<span *ngIf="content.scheduledTo">
<ng-container *ngIf="content.scheduledTo">
<span class="content-status content-status-{{content.scheduledTo | lowercase}}" #statusIcon>
<i class="icon-clock"></i>
</span>
<sqx-tooltip [target]="statusIcon">Will be set to '{{content.scheduledTo}}' at {{content.scheduledAt | sqxFullDateTime}}</sqx-tooltip>
</span>
</ng-container>
<small class="item-modified">{{content.lastModified | sqxFromNow}}</small>
</td>

190
src/Squidex/app/features/rules/pages/events/rule-events-page.component.html

@ -1,116 +1,108 @@
<sqx-title message="{app} | Rules Events" parameter1="app" [value1]="ctx.appName"></sqx-title>
<sqx-panel desiredWidth="63rem">
<div class="panel-header">
<div class="panel-title-row">
<div class="float-right">
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Events (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<ng-container title>
Events
</ng-container>
<ng-container header>
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Events (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
</div>
<h3 class="panel-title">Events</h3>
</div>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
</ng-container>
<ng-container content>
<table class="table table-items table-fixed">
<thead>
<tr>
<th class="cell-label">
Status
</th>
<th class="cell-40">
Event
</th>
<th class="cell-60">
Description
</th>
<th class="cell-time">
Created
</th>
<th class="cell-actions">
<a class="panel-close" sqxParentLink isLazyLoaded="true">
<i class="icon-close"></i>
</a>
</div>
</th>
</tr>
</thead>
<div class="panel-main">
<div class="panel-content panel-content-scroll">
<table class="table table-items table-fixed">
<thead>
<tr>
<th class="cell-label">
Status
</th>
<th class="cell-40">
Event
</th>
<th class="cell-60">
Description
</th>
<th class="cell-time">
Created
</th>
<th class="cell-actions">
</th>
<tbody>
<ng-template ngFor let-event [ngForOf]="eventsItems">
<tr [class.expanded]="selectedEventId === event.id">
<td class="cell-label">
<span class="badge badge-pill badge-{{getBadgeClass(event.jobResult)}}">{{event.jobResult}}</span>
</td>
<td class="cell-40">
<span class="truncate">{{event.eventName}}</span>
</td>
<td class="cell-60">
<span class="truncate">{{event.description}}</span>
</td>
<td class="cell-time">
<small class="item-modified">{{event.created | sqxFromNow}}</small>
</td>
<td class="cell-actions">
<button type="button" class="btn btn-secondary table-items-edit-button" [class.active]="selectedEventId === event.id" (click)="selectEvent(event.id)">
<i class="icon-settings"></i>
</button>
</td>
</tr>
</thead>
<tbody>
<ng-template ngFor let-event [ngForOf]="eventsItems">
<tr [class.expanded]="selectedEventId === event.id">
<td class="cell-label">
<span class="badge badge-pill badge-{{getBadgeClass(event.jobResult)}}">{{event.jobResult}}</span>
</td>
<td class="cell-40">
<span class="truncate">{{event.eventName}}</span>
</td>
<td class="cell-60">
<span class="truncate">{{event.description}}</span>
</td>
<td class="cell-time">
<small class="item-modified">{{event.created | sqxFromNow}}</small>
</td>
<td class="cell-actions">
<button type="button" class="btn btn-secondary table-items-edit-button" [class.active]="selectedEventId === event.id" (click)="selectEvent(event.id)">
<i class="icon-settings"></i>
</button>
</td>
</tr>
<tr *ngIf="selectedEventId === event.id">
<td colspan="5">
<div class="event-header">
<h3>Last Invocation</h3>
<tr *ngIf="selectedEventId === event.id">
<td colspan="5">
<div class="event-header">
<h3>Last Invocation</h3>
</div>
<div class="row event-stats">
<div class="col-3">
<span class="badge badge-pill badge-{{getBadgeClass(event.result)}}">{{event.result}}</span>
</div>
<div class="row event-stats">
<div class="col-3">
<span class="badge badge-pill badge-{{getBadgeClass(event.result)}}">{{event.result}}</span>
</div>
<div class="col-3">
Attempts: {{event.numCalls}}
</div>
<div class="col-3">
Next: <span *ngIf="event.nextAttempt">{{event.nextAttempt | sqxFromNow}}</span>
</div>
<div class="col-3 text-right">
<button class="btn btn-success btn-sm" (click)="enqueueEvent(event)">
Enqueue
</button>
</div>
<div class="col-3">
Attempts: {{event.numCalls}}
</div>
<div class="row">
<div class="col-12">
<textarea class="event-dump form-control" readonly>{{event.lastDump}}</textarea>
</div>
<div class="col-3">
Next: <ng-container *ngIf="event.nextAttempt">{{event.nextAttempt | sqxFromNow}}</ng-container>
</div>
</td>
</tr>
<tr class="spacer"></tr>
</ng-template>
</tbody>
</table>
<div class="col-3 text-right">
<button class="btn btn-success btn-sm" (click)="enqueueEvent(event)">
Enqueue
</button>
</div>
</div>
<div class="row">
<div class="col-12">
<textarea class="event-dump form-control" readonly>{{event.lastDump}}</textarea>
</div>
</div>
</td>
</tr>
<tr class="spacer"></tr>
</ng-template>
</tbody>
</table>
<div class="clearfix" *ngIf="eventsPager.numberOfItems > 0">
<div class="float-right pagination">
<span class="pagination-text">{{eventsPager.itemFirst}}-{{eventsPager.itemLast}} of {{eventsPager.numberOfItems}}</span>
<div class="clearfix" *ngIf="eventsPager.numberOfItems > 0">
<div class="float-right pagination">
<span class="pagination-text">{{eventsPager.itemFirst}}-{{eventsPager.itemLast}} of {{eventsPager.numberOfItems}}</span>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!eventsPager.canGoPrev" (click)="goPrev()">
<i class="icon-angle-left"></i>
</button>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!eventsPager.canGoNext" (click)="goNext()">
<i class="icon-angle-right"></i>
</button>
</div>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!eventsPager.canGoPrev" (click)="goPrev()">
<i class="icon-angle-left"></i>
</button>
<button class="btn btn-link btn-secondary pagination-button" [disabled]="!eventsPager.canGoNext" (click)="goNext()">
<i class="icon-angle-right"></i>
</button>
</div>
</div>
</div>
</ng-container>
</sqx-panel>
<router-outlet></router-outlet>

237
src/Squidex/app/features/rules/pages/rules/rule-wizard.component.html

@ -1,127 +1,122 @@
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title" *ngIf="mode === 'EditTrigger'">
Edit Trigger
</h4>
<h4 class="modal-title" *ngIf="mode === 'EditAction'">
Edit Action
</h4>
<h4 class="modal-title" *ngIf="mode === 'Wizard' && step === 1">
Step 1 of 4: Select Trigger
</h4>
<h4 class="modal-title" *ngIf="mode === 'Wizard' && step === 2">
Step 2 of 4: Configure Trigger
</h4>
<h4 class="modal-title" *ngIf="mode === 'Wizard' && step === 3">
Step 3 of 4: Select Action
</h4>
<h4 class="modal-title" *ngIf="mode === 'Wizard' && step === 4">
Step 4 of 4: Configure Action
</h4>
<button type="button" class="close" data-dismiss="modal" aria-label="Close" (click)="cancel()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<sqx-modal-dialog large="true" (close)="cancel()">
<ng-container title>
<ng-container *ngIf="mode === 'EditTrigger'">
Edit Trigger
</ng-container>
<ng-container *ngIf="mode === 'EditAction'">
Edit Action
</ng-container>
<ng-container *ngIf="mode === 'Wizard' && step === 1">
Step 1 of 4: Select Trigger
</ng-container>
<ng-container *ngIf="mode === 'Wizard' && step === 2">
Step 2 of 4: Configure Trigger
</ng-container>
<ng-container *ngIf="mode === 'Wizard' && step === 3">
Step 3 of 4: Select Action
</ng-container>
<ng-container *ngIf="mode === 'Wizard' && step === 4">
Step 4 of 4: Configure Action
</ng-container>
</ng-container>
<div class="modal-body">
<div *ngIf="step === 1">
<span *ngFor="let trigger of ruleTriggers | sqxKeys" class="rule-element rule-element-{{trigger}}" (click)="selectTriggerType(trigger)">
<span class="rule-element-icon">
<i class="icon-trigger-{{trigger}}"></i>
</span>
<span class="rule-element-text">
{{ruleTriggers[trigger].name}}
</span>
<ng-container content>
<ng-container *ngIf="step === 1">
<span *ngFor="let trigger of ruleTriggers | sqxKeys" class="rule-element rule-element-{{trigger}}" (click)="selectTriggerType(trigger)">
<span class="rule-element-icon">
<i class="icon-trigger-{{trigger}}"></i>
</span>
</div>
<div *ngIf="step === 2 && schemas" class="modal-form">
<div [ngSwitch]="triggerType">
<div *ngSwitchCase="'AssetChanged'">
<sqx-asset-changed-trigger #triggerControl
[trigger]="trigger"
(triggerChanged)="selectTrigger($event)">
</sqx-asset-changed-trigger>
</div>
<div *ngSwitchCase="'ContentChanged'">
<sqx-content-changed-trigger #triggerControl
[schemas]="schemas"
[trigger]="trigger"
(triggerChanged)="selectTrigger($event)">
</sqx-content-changed-trigger>
</div>
</div>
</div>
<span class="rule-element-text">
{{ruleTriggers[trigger].name}}
</span>
</span>
</ng-container>
<div *ngIf="step === 3">
<span *ngFor="let action of ruleActions | sqxKeys" class="rule-element rule-element-{{action}}" (click)="selectActionType(action)">
<span class="rule-element-icon">
<i class="icon-action-{{action}}"></i>
</span>
<span class="rule-element-text">
{{ruleActions[action].name}}
</span>
<ng-container *ngIf="step === 2 && schemas">
<ng-container [ngSwitch]="triggerType">
<ng-container *ngSwitchCase="'AssetChanged'">
<sqx-asset-changed-trigger #triggerControl
[trigger]="trigger"
(triggerChanged)="selectTrigger($event)">
</sqx-asset-changed-trigger>
</ng-container>
<ng-container *ngSwitchCase="'ContentChanged'">
<sqx-content-changed-trigger #triggerControl
[schemas]="schemas"
[trigger]="trigger"
(triggerChanged)="selectTrigger($event)">
</sqx-content-changed-trigger>
</ng-container>
</ng-container>
</ng-container>
<ng-container *ngIf="step === 3">
<span *ngFor="let action of ruleActions | sqxKeys" class="rule-element rule-element-{{action}}" (click)="selectActionType(action)">
<span class="rule-element-icon">
<i class="icon-action-{{action}}"></i>
</span>
<span class="rule-element-text">
{{ruleActions[action].name}}
</span>
</div>
</span>
</ng-container>
<ng-container *ngIf="step === 4">
<ng-container [ngSwitch]="actionType">
<ng-container *ngSwitchCase="'Algolia'">
<sqx-algolia-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-algolia-action>
</ng-container>
<ng-container *ngSwitchCase="'AzureQueue'">
<sqx-azure-queue-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-azure-queue-action>
</ng-container>
<ng-container *ngSwitchCase="'ElasticSearch'">
<sqx-elastic-search-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-elastic-search-action>
</ng-container>
<ng-container *ngSwitchCase="'Fastly'">
<sqx-fastly-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-fastly-action>
</ng-container>
<ng-container *ngSwitchCase="'Slack'">
<sqx-slack-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-slack-action>
</ng-container>
<ng-container *ngSwitchCase="'Webhook'">
<sqx-webhook-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-webhook-action>
</ng-container>
</ng-container>
</ng-container>
</ng-container>
<ng-container footer>
<ng-container *ngIf="mode === 'Wizard' && step === 2">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="triggerControl.save()">Next</button>
</ng-container>
<div *ngIf="step === 4" class="modal-form">
<div [ngSwitch]="actionType">
<div *ngSwitchCase="'Algolia'">
<sqx-algolia-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-algolia-action>
</div>
<div *ngSwitchCase="'AzureQueue'">
<sqx-azure-queue-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-azure-queue-action>
</div>
<div *ngSwitchCase="'ElasticSearch'">
<sqx-elastic-search-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-elastic-search-action>
</div>
<div *ngSwitchCase="'Fastly'">
<sqx-fastly-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-fastly-action>
</div>
<div *ngSwitchCase="'Slack'">
<sqx-slack-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-slack-action>
</div>
<div *ngSwitchCase="'Webhook'">
<sqx-webhook-action #actionControl
[action]="action"
(actionChanged)="selectAction($event)">
</sqx-webhook-action>
</div>
</div>
</div>
</div>
<div class="modal-footer" *ngIf="step === 2 || step === 4">
<div class="clearfix" *ngIf="mode === 'Wizard' && step === 2">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="triggerControl.save()">Next</button>
</div>
<div class="clearfix" *ngIf="mode !== 'Wizard' && step === 2">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="triggerControl.save()">Save</button>
</div>
<ng-container *ngIf="mode !== 'Wizard' && step === 2">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="triggerControl.save()">Save</button>
</ng-container>
<div class="clearfix" *ngIf="step === 4">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="actionControl.save()">Save</button>
</div>
</div>
</div>
</div>
<ng-container *ngIf="step === 4">
<button type="reset" class="float-left btn btn-secondary" (click)="cancel()">Cancel</button>
<button type="submit" class="float-right btn btn-primary" (click)="actionControl.save()">Save</button>
</ng-container>
</ng-container>
</sqx-modal-dialog>

4
src/Squidex/app/features/rules/pages/rules/rule-wizard.component.ts

@ -11,7 +11,6 @@ import {
AppContext,
CreateRuleDto,
DateTime,
fadeAnimation,
ruleActions,
ruleTriggers,
RuleDto,
@ -30,9 +29,6 @@ export const MODE_EDIT_ACTION = 'EditAction';
templateUrl: './rule-wizard.component.html',
providers: [
AppContext
],
animations: [
fadeAnimation
]
})
export class RuleWizardComponent implements OnInit {

164
src/Squidex/app/features/rules/pages/rules/rules-page.component.html

@ -1,107 +1,97 @@
<sqx-title message="{app} | Rules" parameter1="app" [value1]="ctx.appName"></sqx-title>
<sqx-panel desiredWidth="54rem">
<div class="panel-header">
<div class="panel-title-row">
<div class="float-right">
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Assets (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<ng-container title>
Rules
</ng-container>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+g" (trigger)="buttonNew.click()"></sqx-shortcut>
<button class="btn btn-success" #buttonNew (click)="createNew()" title="New Rule (CTRL + M)">
<i class="icon-plus"></i> New
</button>
</div>
<ng-container header>
<button class="btn btn-link btn-secondary" (click)="load(true)" title="Refresh Assets (CTRL + SHIFT + R)">
<i class="icon-reset"></i> Refresh
</button>
<h3 class="panel-title"><i class="icon-rules"></i> Rules</h3>
</div>
<sqx-shortcut keys="ctrl+shift+r" (trigger)="load(true)"></sqx-shortcut>
<sqx-shortcut keys="ctrl+shift+g" (trigger)="buttonNew.click()"></sqx-shortcut>
<a class="panel-close" sqxParentLink isLazyLoaded="true">
<i class="icon-close"></i>
</a>
</div>
<button class="btn btn-success" #buttonNew (click)="createNew()" title="New Rule (CTRL + M)">
<i class="icon-plus"></i> New
</button>
</ng-container>
<div class="panel-main">
<div class="panel-content panel-content-scroll">
<div class="table-items-row table-items-row-empty" *ngIf="rules && rules.length === 0">
No Rule created yet.
</div>
<ng-container content>
<div class="table-items-row table-items-row-empty" *ngIf="rules && rules.length === 0">
No Rule created yet.
</div>
<table class="table table-items table-fixed" *ngIf="rules && rules.length > 0">
<tbody>
<ng-template ngFor let-rule [ngForOf]="rules">
<tr>
<td class="cell-separator">
<h3>If</h3>
</td>
<td class="cell-auto">
<span class="rule-element rule-element-{{rule.triggerType}}" (click)="editTrigger(rule)">
<span class="rule-element-icon">
<i class="icon-trigger-{{rule.triggerType}}"></i>
</span>
<span class="rule-element-text">
{{ruleTriggers[rule.triggerType].name}}
</span>
<table class="table table-items table-fixed" *ngIf="rules && rules.length > 0">
<tbody>
<ng-template ngFor let-rule [ngForOf]="rules">
<tr>
<td class="cell-separator">
<h3>If</h3>
</td>
<td class="cell-auto">
<span class="rule-element rule-element-{{rule.triggerType}}" (click)="editTrigger(rule)">
<span class="rule-element-icon">
<i class="icon-trigger-{{rule.triggerType}}"></i>
</span>
</td>
<td class="cell-separator">
<h3>then</h3>
</td>
<td class="cell-auto">
<span class="rule-element rule-element-{{rule.actionType}}" (click)="editAction(rule)">
<span class="rule-element-icon">
<i class="icon-action-{{rule.actionType}}"></i>
</span>
<span class="rule-element-text">
{{ruleActions[rule.actionType].name}}
</span>
<span class="rule-element-text">
{{ruleTriggers[rule.triggerType].name}}
</span>
</td>
<td class="cell-actions">
<sqx-toggle [ngModel]="rule.isEnabled" (ngModelChange)="toggleRule(rule)"></sqx-toggle>
</td>
<td class="cell-actions">
<button type="button" class="btn btn-link btn-danger"
(sqxConfirmClick)="deleteRule(rule)"
confirmTitle="Delete rule"
confirmText="Do you really want to delete the rule?">
<i class="icon-bin2"></i>
</button>
</td>
</tr>
<tr class="spacer"></tr>
</ng-template>
</tbody>
</table>
</div>
</span>
</td>
<td class="cell-separator">
<h3>then</h3>
</td>
<td class="cell-auto">
<span class="rule-element rule-element-{{rule.actionType}}" (click)="editAction(rule)">
<span class="rule-element-icon">
<i class="icon-action-{{rule.actionType}}"></i>
</span>
<span class="rule-element-text">
{{ruleActions[rule.actionType].name}}
</span>
</span>
</td>
<td class="cell-actions">
<sqx-toggle [ngModel]="rule.isEnabled" (ngModelChange)="toggleRule(rule)"></sqx-toggle>
</td>
<td class="cell-actions">
<button type="button" class="btn btn-link btn-danger"
(sqxConfirmClick)="deleteRule(rule)"
confirmTitle="Delete rule"
confirmText="Do you really want to delete the rule?">
<i class="icon-bin2"></i>
</button>
</td>
</tr>
<tr class="spacer"></tr>
</ng-template>
</tbody>
</table>
</ng-container>
<div class="panel-sidebar">
<a class="panel-link" routerLink="events" routerLinkActive="active" #linkHistory>
<i class="icon-time"></i>
</a>
<a class="panel-link" routerLink="help" routerLinkActive="active" #linkHelp>
<i class="icon-help"></i>
</a>
<sqx-onboarding-tooltip id="help" [for]="linkHelp" position="leftTop" after="180000">
Click the help icon to show a context specific help page. Go to <a href="https://docs.squidex.io" target="_blank">https://docs.squidex.io</a> for the full documentation.
</sqx-onboarding-tooltip>
</div>
</div>
<ng-container sidebar>
<a class="panel-link" routerLink="events" routerLinkActive="active" #linkHistory>
<i class="icon-time"></i>
</a>
<a class="panel-link" routerLink="help" routerLinkActive="active" #linkHelp>
<i class="icon-help"></i>
</a>
<sqx-onboarding-tooltip id="help" [for]="linkHelp" position="leftTop" after="180000">
Click the help icon to show a context specific help page. Go to <a href="https://docs.squidex.io" target="_blank">https://docs.squidex.io</a> for the full documentation.
</sqx-onboarding-tooltip>
</ng-container>
</sqx-panel>
<div class="modal" *sqxModalView="addRuleDialog;onRoot:true;closeAuto:false" @fade>
<div class="modal-backdrop"></div>
<ng-container *sqxModalView="addRuleDialog;onRoot:true;closeAuto:false">
<sqx-rule-wizard [schemas]="schemas" [rule]="wizardRule" [mode]="wizardMode"
(updated)="onRuleUpdated($event)"
(cancelled)="addRuleDialog.hide()"
(created)="onRuleCreated($event)">
</sqx-rule-wizard>
</div>
</ng-container>
<router-outlet></router-outlet>

4
src/Squidex/app/features/rules/pages/rules/rules-page.component.ts

@ -10,7 +10,6 @@ import { Component, OnInit } from '@angular/core';
import {
AppContext,
DateTime,
fadeAnimation,
ImmutableArray,
ModalView,
ruleActions,
@ -27,9 +26,6 @@ import {
templateUrl: './rules-page.component.html',
providers: [
AppContext
],
animations: [
fadeAnimation
]
})
export class RulesPageComponent implements OnInit {

8
src/Squidex/app/features/schemas/pages/schema/field-wizard.component.html

@ -1,13 +1,11 @@
<form [formGroup]="addFieldForm.form" (ngSubmit)="addField(false)">
<sqx-modal-dialog (close)="complete()">
<sqx-modal-dialog (close)="complete()" large="true">
<ng-container title>
Create Field
</ng-container>
<ng-container content>
<ng-container *ngIf="addFieldForm.error | async; let error">
<div class="form-alert form-alert-error" [innerHTML]="error"></div>
</ng-container>
<sqx-form-error [error]="addFieldForm.error | async"></sqx-form-error>
<div class="form-group">
<div class="row">
@ -17,7 +15,7 @@
<div class="row no-gutters">
<div class="col col-auto">
<div class="type-icon" [class.active]="addFieldForm.form.controls.type.value === fieldType.type">
<div class="type-icon" [class.active]="addFieldForm.form.controls['type'].value === fieldType.type">
<i class="icon-type-{{fieldType.type}}"></i>
</div>
</div>

20
src/Squidex/app/features/schemas/pages/schema/schema-page.component.html

@ -52,7 +52,7 @@
<ng-container content>
<div dnd-sortable-container [sortableData]="schema.fields">
<div *ngFor="let field of schema.fields; let i = index; trackBy: schemasState.trackByField" dnd-sortable [sortableIndex]="i" (sqxSorted)="sortFields($event)">
<div *ngFor="let field of schema.fields; let i = index;" dnd-sortable [sortableIndex]="i" (sqxSorted)="sortFields($event)">
<sqx-field [field]="field" [schema]="schema"></sqx-field>
</div>
@ -63,29 +63,23 @@
</ng-container>
</sqx-panel>
<div class="modal" *sqxModalView="editSchemaDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
<ng-container *sqxModalView="editSchemaDialog;onRoot:true">
<sqx-schema-edit-form [schema]="schema"
(completed)="editSchemaDialog.hide()">
</sqx-schema-edit-form>
</div>
<div class="modal" *sqxModalView="addFieldDialog;onRoot:true;closeAuto:false" @fade>
<div class="modal-backdrop"></div>
</ng-container>
<ng-container *sqxModalView="addFieldDialog;onRoot:true;closeAuto:false">
<sqx-field-wizard [schema]="schema"
(completed)="addFieldDialog.hide()">
</sqx-field-wizard>
</div>
<div class="modal" *sqxModalView="configureScriptsDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
</ng-container>
<ng-container *sqxModalView="configureScriptsDialog;onRoot:true">
<sqx-schema-scripts-form [schema]="schema"
(completed)="configureScriptsDialog.hide()">
</sqx-schema-scripts-form>
</div>
</ng-container>
<ng-container *sqxModalView="exportSchemaDialog;onRoot:true">
<sqx-modal-dialog (close)="exportSchemaDialog.hide()">

2
src/Squidex/app/features/schemas/pages/schema/schema-page.component.ts

@ -65,7 +65,7 @@ export class SchemaPageComponent implements OnDestroy, OnInit {
public ngOnInit() {
this.selectedSchemaSubscription =
this.schemasState.changes.map(x => x.selectedSchema)
this.schemasState.selectedSchema
.subscribe(schema => {
this.schema = schema!;

6
src/Squidex/app/features/schemas/pages/schema/schema-scripts-form.component.html

@ -1,5 +1,5 @@
<form [formGroup]="editForm.form" (ngSubmit)="saveSchema()">
<sqx-modal-dialog (close)="complete()">
<sqx-modal-dialog (close)="complete()" large="true">
<ng-container title>
Scripts
</ng-container>
@ -15,9 +15,9 @@
<ng-container content>
<div class="form-group">
<div *ngFor="let script of editForm.form.controls | sqxKeys">
<div *ngIf="selectedField === script">
<ng-container *ngIf="selectedField === script">
<sqx-jscript-editor name="script" [formControlName]="script"></sqx-jscript-editor>
</div>
</ng-container>
</div>
</div>
</ng-container>

4
src/Squidex/app/features/schemas/pages/schema/types/date-time-validation.component.html

@ -26,7 +26,7 @@
</div>
</div>
<div *ngIf="showDefaultValues | async">
<ng-container *ngIf="showDefaultValues | async">
<div class="form-group row">
<label class="col col-3 col-form-label">Default Mode:</label>
@ -45,5 +45,5 @@
<sqx-date-time-editor enforceTime="true" mode="DateTime" formControlName="defaultValue"></sqx-date-time-editor>
</div>
</div>
</div>
</ng-container>
</div>

4
src/Squidex/app/features/schemas/pages/schemas/schema-form.component.html

@ -10,9 +10,7 @@
</ng-container>
<ng-container content>
<ng-container *ngIf="createForm.error | async; let error">
<div class="form-alert form-alert-error" [innerHTML]="error"></div>
</ng-container>
<sqx-form-error [error]="createForm.error | async"></sqx-form-error>
<div class="form-group">
<label for="schemaName">Name</label>

2
src/Squidex/app/features/schemas/pages/schemas/schemas-page.component.html

@ -22,7 +22,7 @@
<ng-container content>
<ul class="nav nav-panel nav-dark nav-dark-bordered flex-column">
<li class="nav-item" *ngFor="let schema of schemasFiltered | async; trackBy: schemasState.trackBySchema">
<li class="nav-item" *ngFor="let schema of schemasFiltered | async; trackBy: trackBySchema">
<a class="nav-link" [routerLink]="[schema.name]" routerLinkActive="active">
<div class="row">
<div class="col col-4">

9
src/Squidex/app/features/schemas/pages/schemas/schemas-page.component.ts

@ -13,7 +13,8 @@ import { Subscription } from 'rxjs';
import {
AppsState,
MessageBus,
ModalView
ModalView,
SchemaDto
} from '@app/shared';
import { SchemaCloning } from './../messages';
@ -32,7 +33,7 @@ export class SchemasPageComponent implements OnDestroy, OnInit {
public schemasFilter = new FormControl();
public schemasFiltered =
this.schemasState.changes.map(x => x.schemas)
this.schemasState.schemas
.combineLatest(this.schemasFilter.valueChanges.startWith(''),
(schemas, query) => {
if (query && query.length > 0) {
@ -80,5 +81,9 @@ export class SchemasPageComponent implements OnDestroy, OnInit {
this.addSchemaDialog.show();
}
public trackBySchema(index: number, schema: SchemaDto) {
return schema.id;
}
}

20
src/Squidex/app/features/schemas/state/schemas.state.ts

@ -152,6 +152,14 @@ export class SchemasState extends State<Snapshot> {
return this.authState.user!.token;
}
public selectedSchema =
this.changes.map(s => s.selectedSchema)
.distinctUntilChanged();
public schemas =
this.changes.map(s => s.schemas)
.distinctUntilChanged();
constructor(
private readonly appsState: AppsState,
private readonly authState: AuthService,
@ -161,13 +169,13 @@ export class SchemasState extends State<Snapshot> {
super({ schemas: ImmutableArray.of() });
}
public selectSchema(selectedSchemaId: string | null): Observable<SchemaDetailsDto | null> {
return this.loadSchema(selectedSchemaId)
public selectSchema(id: string | null): Observable<SchemaDetailsDto | null> {
return this.loadSchema(id)
.do(schema => {
this.next(s => {
const schemas = schema ? s.schemas.replaceBy('id', schema) : s.schemas;
return { ...s, selectedSchemaId, schemas };
return { ...s, selectedSchema: schema, schemas };
});
});
}
@ -238,7 +246,7 @@ export class SchemasState extends State<Snapshot> {
public unpublish(schema: SchemaDto): Observable<any> {
return this.schemasService.unpublishSchema(this.appName, schema.name, schema.version)
.do(dto => {
this.replaceSchema(setPublished(schema, true, this.user, dto.version));
this.replaceSchema(setPublished(schema, false, this.user, dto.version));
})
.catch(error => this.dialogs.notifyError(error));
}
@ -339,7 +347,7 @@ const setPublished = (schema: SchemaDto | SchemaDetailsDto, publish: boolean, us
schema.id,
schema.name,
schema.properties,
true,
publish,
schema.createdBy, user,
schema.created, now || DateTime.now(),
version,
@ -354,7 +362,7 @@ const setPublished = (schema: SchemaDto | SchemaDetailsDto, publish: boolean, us
schema.id,
schema.name,
schema.properties,
true,
publish,
schema.createdBy, user,
schema.created, now || DateTime.now(),
version);

29
src/Squidex/app/features/settings/pages/clients/client.component.html

@ -16,13 +16,13 @@
</button>
</form>
<span *ngIf="!isRenaming">
<ng-container *ngIf="!isRenaming">
<h3 class="client-name">
<span (dblclick)="startRename()">{{client.name}}</span>
</h3>
<i class="client-edit icon-pencil" (click)="startRename()"></i>
</span>
</ng-container>
</div>
<div class="client-expires">Access tokens expire after 30 days</div>
@ -79,21 +79,12 @@
</div>
</div>
<div class="modal" *sqxModalView="tokenDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title">Access Token</h4>
<sqx-modal-dialog *sqxModalView="tokenDialog;onRoot:true" (close)="tokenDialog.hide()">
<ng-container title>
Access token
</ng-container>
<button type="button" class="close" data-dismiss="modal" aria-label="Close" (click)="tokenDialog.hide()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<textarea readonly class="form-control access-token">{{token.tokenType}} {{token.accessToken}}</textarea>
</div>
</div>
</div>
</div>
<ng-container content>
<textarea readonly class="form-control access-token">{{token.tokenType}} {{token.accessToken}}</textarea>
</ng-container>
</sqx-modal-dialog>

6
src/Squidex/app/features/settings/pages/clients/client.component.ts

@ -13,7 +13,6 @@ import {
AppClientDto,
AppClientsService,
DialogService,
fadeAnimation,
ModalView,
AppsState
} from '@app/shared';
@ -23,10 +22,7 @@ const ESCAPE_KEY = 27;
@Component({
selector: 'sqx-client',
styleUrls: ['./client.component.scss'],
templateUrl: './client.component.html',
animations: [
fadeAnimation
]
templateUrl: './client.component.html'
})
export class ClientComponent {
@Output()

10
src/Squidex/app/features/settings/pages/patterns/pattern.component.ts

@ -10,18 +10,14 @@ import { FormBuilder, Validators } from '@angular/forms';
import {
AppPatternDto,
fadeAnimation,
ValidatorsEx,
UpdatePatternDto
UpdatePatternDto,
ValidatorsEx
} from '@app/shared';
@Component({
selector: 'sqx-pattern',
styleUrls: ['./pattern.component.scss'],
templateUrl: './pattern.component.html',
animations: [
fadeAnimation
]
templateUrl: './pattern.component.html'
})
export class PatternComponent implements OnInit {
@Input()

4
src/Squidex/app/features/settings/pages/plans/plans-page.component.html

@ -14,7 +14,7 @@
</ng-container>
<ng-container content>
<div *ngIf="plans">
<ng-container *ngIf="plans">
<div class="panel-alert panel-alert-danger" *ngIf="!planOwned">
You have not created the subscription. Therefore you cannot change the plan.
</div>
@ -57,6 +57,6 @@
<div *ngIf="plans.hasPortal" class="billing-portal-link">
Go to <a target="_blank" href="{{portalUrl}}">Billing Portal</a> for payment history and subscription overview.
</div>
</div>
</ng-container>
</ng-container>
</sqx-panel>

10
src/Squidex/app/features/settings/settings-area.component.html

@ -6,8 +6,8 @@
</ng-container>
<ng-container content>
<ul class="nav nav-panel nav-dark flex-column">
<li class="nav-item" *ngIf="appsState.selectedApp.value.permission === 'Owner'">
<ul class="nav nav-panel nav-dark flex-column" *ngIf="appsState.selectedApp | async; let selectedApp">
<li class="nav-item" *ngIf="selectedApp.permission === 'Owner'">
<a class="nav-link" routerLink="backups" routerLinkActive="active">
Backups
<i class="icon-angle-right"></i>
@ -19,7 +19,7 @@
<i class="icon-angle-right"></i>
</a>
</li>
<li class="nav-item" *ngIf="appsState.selectedApp.value.permission === 'Owner'">
<li class="nav-item" *ngIf="selectedApp.permission === 'Owner'">
<a class="nav-link" routerLink="contributors" routerLinkActive="active">
Contributors
<i class="icon-angle-right"></i>
@ -37,13 +37,13 @@
<i class="icon-angle-right"></i>
</a>
</li>
<li class="nav-item" *ngIf="appsState.selectedApp.value.permission === 'Owner'">
<li class="nav-item" *ngIf="selectedApp.permission === 'Owner'">
<a class="nav-link" routerLink="plans" routerLinkActive="active">
Subscription
<i class="icon-angle-right"></i>
</a>
</li>
<li class="nav-item" *ngIf="appsState.selectedApp.value.permission === 'Owner'">
<li class="nav-item" *ngIf="selectedApp.permission === 'Owner'">
<a class="nav-link" routerLink="more" routerLinkActive="active">
More
<i class="icon-angle-right"></i>

2
src/Squidex/app/framework/angular/forms/autocomplete.component.html

@ -7,7 +7,7 @@
<div *ngIf="items.length > 0" [sqxModalTarget]="input" class="control-dropdown" #container position="bottomLeft">
<div *ngFor="let item of items; let i = index;" class="control-dropdown-item control-dropdown-item-selectable" [class.active]="i === selectedIndex" (mousedown)="selectItem(item)" (mouseover)="selectIndex(i)" [sqxScrollActive]="i === selectedIndex" [container]="container">
<span *ngIf="!itemTemplate">{{item}}</span>
<ng-container *ngIf="!itemTemplate">{{item}}</ng-container>
<ng-template *ngIf="itemTemplate" [sqxTemplateWrapper]="itemTemplate" [item]="item" [index]="i"></ng-template>
</div>

4
src/Squidex/app/framework/angular/forms/dropdown.component.html

@ -6,7 +6,7 @@
autocapitalize="off">
<div class="control-dropdown-item" *ngIf="selectedItem">
<span *ngIf="!selectionTemplate">{{selectedItem}}</span>
<ng-container *ngIf="!selectionTemplate">{{selectedItem}}</ng-container>
<ng-template *ngIf="selectionTemplate" [sqxTemplateWrapper]="selectionTemplate" [item]="selectedItem"></ng-template>
</div>
@ -17,7 +17,7 @@
<div class="items-container">
<div class="control-dropdown" #container *sqxModalView="dropdown" [sqxModalTarget]="input" position="bottomLeft">
<div *ngFor="let item of items; let i = index;" class="control-dropdown-item control-dropdown-item-selectable" [class.active]="i === selectedIndex" (mousedown)="selectIndexAndClose(i)" [sqxScrollActive]="i === selectedIndex" [container]="container">
<span *ngIf="!itemTemplate">{{item}}</span>
<ng-container *ngIf="!itemTemplate">{{item}}</ng-container>
<ng-template *ngIf="itemTemplate" [sqxTemplateWrapper]="itemTemplate" [item]="item" [index]="i"></ng-template>
</div>

3
src/Squidex/app/framework/angular/forms/form-error.component.html

@ -0,0 +1,3 @@
<ng-container *ngIf="error">
<div class="form-alert form-alert-error" [innerHTML]="error" @fade></div>
</ng-container>

2
src/Squidex/app/framework/angular/forms/form-error.component.scss

@ -0,0 +1,2 @@
@import '_mixins';
@import '_vars';

24
src/Squidex/app/framework/angular/forms/form-error.component.ts

@ -0,0 +1,24 @@
/*
* Squidex Headless CMS
*
* @license
* Copyright (c) Squidex UG (haftungsbeschränkt). All rights reserved.
*/
import { ChangeDetectionStrategy, Component, Input } from '@angular/core';
import { fadeAnimation } from './../animations';
@Component({
selector: 'sqx-form-error',
styleUrls: ['./form-error.component.scss'],
templateUrl: './form-error.component.html',
animations: [
fadeAnimation
],
changeDetection: ChangeDetectionStrategy.OnPush
})
export class FormErrorComponent {
@Input()
public error: string;
}

5
src/Squidex/app/framework/angular/forms/stars.component.html

@ -2,11 +2,12 @@
<div *ngIf="maximumStars === 0 || maximumStars > 15" class="many-stars">
Must not have more more than 15 stars
</div>
<div *ngIf="maximumStars > 0 && maximumStars <= 15">
<ng-container *ngIf="maximumStars > 0 && maximumStars <= 15">
<span class="stars" (mouseleave)="stopPreview()" [class.disabled]="isDisabled">
<span class="star" *ngFor="let star of starsArray" (mouseenter)="setPreview(star)" (click)="setValue(star)" [class.selected]="star <= stars"></span>
</span>
<button class="btn btn-link" [class.hidden]="!value" (click)="reset()">Clear</button>
</div>
</ng-container>
</div>

31
src/Squidex/app/framework/angular/modals/dialog-renderer.component.html

@ -1,26 +1,19 @@
<ng-content></ng-content>
<div class="modal" *sqxModalView="dialogView;onRoot:true">
<div class="modal-backdrop"></div>
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title">{{dialogRequest.title}}</h4>
</div>
<sqx-modal-dialog *sqxModalView="dialogView;onRoot:true" showClose="false">
<ng-container title>
{{dialogRequest.title}}
</ng-container>
<div class="modal-body">
{{dialogRequest.text}}
</div>
<ng-container content>
{{dialogRequest.text}}
</ng-container>
<div class="modal-footer">
<div class="clearfix">
<button type="button" class="float-left btn btn-secondary" (click)="cancel()">No</button>
<button type="button" class="float-right btn btn-danger" (click)="confirm()">Yes</button>
</div>
</div>
</div>
</div>
</div>
<ng-container footer>
<button type="button" class="float-left btn btn-secondary" (click)="cancel()">No</button>
<button type="button" class="float-right btn btn-danger" (click)="confirm()">Yes</button>
</ng-container>
</sqx-modal-dialog>
<div class="notification-container notification-container-{{position}}">
<div class="alert alert-dismissible alert-{{notification.messageType}}" *ngFor="let notification of notifications" (click)="close(notification)" @fade>

2
src/Squidex/app/framework/angular/modals/modal-dialog.component.html

@ -3,7 +3,7 @@
<div class="modal-dialog {{large ? 'modal-lg' : ''}}">
<div class="modal-content">
<div class="modal-header">
<div class="modal-header" *ngIf="showHeader">
<h4 class="modal-title">
<ng-content select=[title]></ng-content>
</h4>

5
src/Squidex/app/framework/angular/modals/modal-dialog.component.ts

@ -23,7 +23,10 @@ export class ModalDialogComponent implements AfterViewInit {
public showClose = true;
@Input()
public large = true;
public showHeader = true;
@Input()
public large = false;
@Output()
public close = new EventEmitter();

1
src/Squidex/app/framework/declarations.ts

@ -13,6 +13,7 @@ export * from './angular/forms/date-time-editor.component';
export * from './angular/forms/dropdown.component';
export * from './angular/forms/file-drop.directive';
export * from './angular/forms/focus-on-init.directive';
export * from './angular/forms/form-error.component';
export * from './angular/forms/indeterminate-value.directive';
export * from './angular/forms/jscript-editor.component';
export * from './angular/forms/json-editor.component';

3
src/Squidex/app/framework/module.ts

@ -29,6 +29,7 @@ import {
FileDropDirective,
FileSizePipe,
FocusOnInitDirective,
FormErrorComponent,
FromNowPipe,
FullDateTimePipe,
IgnoreScrollbarDirective,
@ -96,6 +97,7 @@ import {
FileDropDirective,
FileSizePipe,
FocusOnInitDirective,
FormErrorComponent,
FromNowPipe,
FullDateTimePipe,
IgnoreScrollbarDirective,
@ -151,6 +153,7 @@ import {
FileDropDirective,
FileSizePipe,
FocusOnInitDirective,
FormErrorComponent,
FormsModule,
FromNowPipe,
FullDateTimePipe,

4
src/Squidex/app/shared/components/app-form.component.html

@ -11,9 +11,7 @@
</ng-container>
<ng-container content>
<div *ngIf="createFormError">
<div class="form-alert form-alert-error" [innerHTML]="createFormError"></div>
</div>
<sqx-form-error [error]="createFormError"></sqx-form-error>
<div class="form-group">
<label for="appName">Name</label>

51
src/Squidex/app/shared/components/asset.component.html

@ -49,7 +49,7 @@
{{asset.fileName}}
</div>
<div class="file-info">
<span *ngIf="asset.pixelWidth">{{asset.pixelWidth}}x{{asset.pixelHeight}}px, </span> {{asset.fileSize | sqxFileSize}}
<ng-container *ngIf="asset.pixelWidth">{{asset.pixelWidth}}x{{asset.pixelHeight}}px, </ng-container> {{asset.fileSize | sqxFileSize}}
</div>
</div>
@ -64,34 +64,27 @@
</div>
</div>
<div class="modal" *sqxModalView="renameDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title">Rename asset</h4>
<ng-container *sqxModalView="renameDialog;onRoot:true">
<form [formGroup]="renameForm" (ngSubmit)="renameAsset()">
<sqx-modal-dialog (click)="cancelRenameAsset()">
<ng-container title>
Rename asset
</ng-container>
<button type="button" class="close" data-dismiss="modal" aria-label="Close" (click)="cancelRenameAsset()">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<form [formGroup]="renameForm" (ngSubmit)="renameAsset()">
<div class="form-group">
<label for="assetName">Name</label>
<sqx-control-errors for="name" [submitted]="renameFormSubmitted"></sqx-control-errors>
<ng-container content>
<div class="form-group">
<label for="assetName">Name</label>
<sqx-control-errors for="name" [submitted]="renameFormSubmitted"></sqx-control-errors>
<input type="text" class="form-control" id="assetName" formControlName="name" autocomplete="off" sqxFocusOnInit />
</div>
<input type="text" class="form-control" id="assetName" formControlName="name" autocomplete="off" sqxFocusOnInit />
</div>
</ng-container>
<div class="form-group clearfix">
<button type="reset" class="float-left btn btn-secondary" (click)="cancelRenameAsset()">Cancel</button>
<button type="submit" class="float-right btn btn-success">Rename</button>
</div>
</form>
</div>
</div>
</div>
</div>
<ng-container footer>
<button type="reset" class="float-left btn btn-secondary" (click)="cancelRenameAsset()">Cancel</button>
<button type="submit" class="float-right btn btn-success">Rename</button>
</ng-container>
</sqx-modal-dialog>
</form>
</ng-container>

4
src/Squidex/app/shared/components/asset.component.ts

@ -15,7 +15,6 @@ import {
AssetsService,
AssetDragged,
DateTime,
fadeAnimation,
ModalView,
UpdateAssetDto,
Version,
@ -29,9 +28,6 @@ import {
templateUrl: './asset.component.html',
providers: [
AppContext
],
animations: [
fadeAnimation
]
})
export class AssetComponent implements OnInit {

22
src/Squidex/app/shared/components/help.component.html

@ -1,17 +1,9 @@
<sqx-panel desiredWidth="16rem">
<div class="panel-header">
<div class="panel-title-row">
<h3 class="panel-title">Help</h3>
</div>
<sqx-panel desiredWidth="16rem" isBlank="true">
<ng-container title>
Help
</ng-container>
<a class="panel-close" sqxParentLink>
<i class="icon-close"></i>
</a>
</div>
<div class="panel-main">
<div class="panel-content panel-content-blank">
<p *ngFor="let section of helpSections | async" [innerHTML]="section"></p>
</div>
</div>
<ng-container content>
<p *ngFor="let section of helpSections | async" [innerHTML]="section"></p>
</ng-container>
</sqx-panel>

38
src/Squidex/app/shared/components/history.component.html

@ -1,27 +1,19 @@
<sqx-panel desiredWidth="16rem">
<div class="panel-header">
<div class="panel-title-row">
<h3 class="panel-title">Activity</h3>
</div>
<a class="panel-close" sqxParentLink>
<i class="icon-close"></i>
</a>
</div>
<sqx-panel desiredWidth="16rem" isBlank="true">
<ng-container title>
Activity
</ng-container>
<div class="panel-main">
<div class="panel-content panel-content-blank">
<div *ngFor="let event of events | async" class="event">
<div class="event-left">
<img class="user-picture" [attr.title]="event.actor | sqxUserNameRef:null" [attr.src]="event.actor | sqxUserPictureRef" />
</div>
<div class="event-main">
<div class="event-message">
<span class="event-actor user-ref">{{event.actor | sqxUserNameRef:null}}</span> <span [innerHTML]="format(event.message) | async"></span>
</div>
<div class="event-created">{{event.created | sqxFromNow}}</div>
<ng-container content>
<div *ngFor="let event of events | async" class="event">
<div class="event-left">
<img class="user-picture" [attr.title]="event.actor | sqxUserNameRef:null" [attr.src]="event.actor | sqxUserPictureRef" />
</div>
<div class="event-main">
<div class="event-message">
<span class="event-actor user-ref">{{event.actor | sqxUserNameRef:null}}</span> <span [innerHTML]="format(event.message) | async"></span>
</div>
</div>
<div class="event-created">{{event.created | sqxFromNow}}</div>
</div>
</div>
</div>
</ng-container>
</sqx-panel>

6
src/Squidex/app/shared/state/apps.state.ts

@ -36,10 +36,12 @@ export class AppsState extends State<Snapshot> {
}
public selectedApp =
this.changes.map(s => s.selectedApp);
this.changes.map(s => s.selectedApp)
.distinctUntilChanged();
public apps =
this.changes.map(s => s.apps);
this.changes.map(s => s.apps)
.distinctUntilChanged();
constructor(
private readonly appsService: AppsService

14
src/Squidex/app/shell/pages/internal/apps-menu.component.html

@ -1,7 +1,7 @@
<ul class="nav navbar-nav" *ngIf="apps">
<ul class="nav navbar-nav">
<li class="nav-item dropdown">
<span class="nav-link dropdown-toggle" id="app-name" (click)="appsMenu.toggle()">
<ng-container *ngIf="appsState | selectedApp | async; let apps; else noApp">
<ng-container *ngIf="appsState.selectedApp | async; let selectedApp; else noApp">
{{selectedApp.name}}
</ng-container>
@ -19,11 +19,11 @@
<div class="dropdown-divider"></div>
<div *ngIf="apps.length > 0">
<ng-container *ngIf="apps.length > 0">
<a class="dropdown-item" *ngFor="let app of apps" [routerLink]="['/app', app.name]" routerLinkActive="active">{{app.name}}</a>
<div class="dropdown-divider"></div>
</div>
</ng-container>
<div class="drodown-button">
<button class="btn btn-block btn-success" (click)="createApp()">
@ -48,10 +48,8 @@
</ng-container>
</ul>
<div class="modal" *sqxModalView="addAppDialog;onRoot:true" @fade>
<div class="modal-backdrop"></div>
<ng-container *sqxModalView="addAppDialog;onRoot:true">
<sqx-app-form
(completed)="addAppDialog.hide()">
</sqx-app-form>
</div>
</ng-container>
Loading…
Cancel
Save