Text watermark config
This commit is contained in:
parent
213d51c23b
commit
da2803f446
@ -93,6 +93,7 @@ import { AdminBreadcrumbsComponent } from './components/admin-page-header/admin-
|
|||||||
import { UserListingScreenComponent } from './screens/admin/users/user-listing-screen.component';
|
import { UserListingScreenComponent } from './screens/admin/users/user-listing-screen.component';
|
||||||
import { NotificationsComponent } from './components/notifications/notifications.component';
|
import { NotificationsComponent } from './components/notifications/notifications.component';
|
||||||
import { RulesScreenComponent } from './screens/admin/rules-screen/rules-screen.component';
|
import { RulesScreenComponent } from './screens/admin/rules-screen/rules-screen.component';
|
||||||
|
import { WatermarkScreenComponent } from './screens/admin/watermark-screen/watermark-screen.component';
|
||||||
|
|
||||||
export function HttpLoaderFactory(httpClient: HttpClient) {
|
export function HttpLoaderFactory(httpClient: HttpClient) {
|
||||||
return new TranslateHttpLoader(httpClient, '/assets/i18n/', '.json');
|
return new TranslateHttpLoader(httpClient, '/assets/i18n/', '.json');
|
||||||
@ -176,6 +177,14 @@ const routes = [
|
|||||||
data: {
|
data: {
|
||||||
routeGuards: [AuthGuard, RedRoleGuard, AppStateGuard]
|
routeGuards: [AuthGuard, RedRoleGuard, AppStateGuard]
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: 'watermark',
|
||||||
|
component: WatermarkScreenComponent,
|
||||||
|
canActivate: [CompositeRouteGuard],
|
||||||
|
data: {
|
||||||
|
routeGuards: [AuthGuard, RedRoleGuard, AppStateGuard]
|
||||||
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
@ -258,7 +267,8 @@ const matImports = [
|
|||||||
AdminBreadcrumbsComponent,
|
AdminBreadcrumbsComponent,
|
||||||
UserListingScreenComponent,
|
UserListingScreenComponent,
|
||||||
NotificationsComponent,
|
NotificationsComponent,
|
||||||
RulesScreenComponent
|
RulesScreenComponent,
|
||||||
|
WatermarkScreenComponent
|
||||||
],
|
],
|
||||||
imports: [
|
imports: [
|
||||||
BrowserModule,
|
BrowserModule,
|
||||||
|
|||||||
@ -26,6 +26,15 @@
|
|||||||
*ngIf="screen === 'users' || root"
|
*ngIf="screen === 'users' || root"
|
||||||
></a>
|
></a>
|
||||||
|
|
||||||
|
<a
|
||||||
|
class="ml-32 breadcrumb"
|
||||||
|
[routerLink]="'/ui/admin/watermark'"
|
||||||
|
[routerLinkActiveOptions]="{ exact: true }"
|
||||||
|
routerLinkActive="active"
|
||||||
|
translate="watermark"
|
||||||
|
*ngIf="screen === 'watermark' || root"
|
||||||
|
></a>
|
||||||
|
|
||||||
<ng-container *ngIf="dictionary">
|
<ng-container *ngIf="dictionary">
|
||||||
<mat-icon svgIcon="red:arrow-right"></mat-icon>
|
<mat-icon svgIcon="red:arrow-right"></mat-icon>
|
||||||
<a class="breadcrumb" [routerLink]="'/ui/admin/dictionaries/' + dictionary.type" routerLinkActive="active">
|
<a class="breadcrumb" [routerLink]="'/ui/admin/dictionaries/' + dictionary.type" routerLinkActive="active">
|
||||||
|
|||||||
@ -0,0 +1,58 @@
|
|||||||
|
<section>
|
||||||
|
<div class="page-header">
|
||||||
|
<redaction-admin-breadcrumbs class="flex-1"></redaction-admin-breadcrumbs>
|
||||||
|
|
||||||
|
<div class="actions">
|
||||||
|
<redaction-circle-button
|
||||||
|
class="ml-6"
|
||||||
|
*ngIf="permissionsService.isUser()"
|
||||||
|
[routerLink]="['/ui/projects/']"
|
||||||
|
tooltip="common.close"
|
||||||
|
tooltipPosition="before"
|
||||||
|
icon="red:close"
|
||||||
|
></redaction-circle-button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="red-content-inner">
|
||||||
|
<div class="left-container">
|
||||||
|
<div class="overlay-shadow"></div>
|
||||||
|
<div #viewer class="viewer"></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="right-container">
|
||||||
|
<form [formGroup]="configForm" (keyup)="configChanged()">
|
||||||
|
<div class="red-input-group">
|
||||||
|
<label translate="Text"></label>
|
||||||
|
<input formControlName="text" name="text" type="text" />
|
||||||
|
</div>
|
||||||
|
<div class="red-input-group">
|
||||||
|
<label translate="Color"></label>
|
||||||
|
<input formControlName="color" name="color" type="text" placeholder="{{ 'add-edit-dictionary.form.color-placeholder' | translate }}" />
|
||||||
|
<div
|
||||||
|
class="input-icon"
|
||||||
|
[colorPicker]="configForm.get('color').value"
|
||||||
|
[cpOutputFormat]="'hex'"
|
||||||
|
(colorPickerChange)="configForm.get('color').setValue($event); configChanged()"
|
||||||
|
>
|
||||||
|
<mat-icon svgIcon="red:color-picker"></mat-icon>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="red-input-group">
|
||||||
|
<label translate="Opacity"></label>
|
||||||
|
<input formControlName="opacity" name="opacity" type="number" (change)="configChanged()" />
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<div class="actions-container">
|
||||||
|
<button color="primary" mat-flat-button (click)="save()" [disabled]="!changed" class="red-button">
|
||||||
|
{{ 'watermark-screen.action.save' | translate }}
|
||||||
|
</button>
|
||||||
|
|
||||||
|
<div class="all-caps-label pointer" (click)="revert()" [translate]="'watermark-screen.action.revert'"></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<redaction-full-page-loading-indicator [displayed]="!viewReady"></redaction-full-page-loading-indicator>
|
||||||
@ -0,0 +1,25 @@
|
|||||||
|
.left-container {
|
||||||
|
width: calc(100vw - 353px);
|
||||||
|
|
||||||
|
.viewer {
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.right-container {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
width: 353px;
|
||||||
|
min-width: 353px;
|
||||||
|
padding: 25px;
|
||||||
|
|
||||||
|
.actions-container {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-top: 24px;
|
||||||
|
|
||||||
|
button:first-child {
|
||||||
|
margin-right: 8px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,126 @@
|
|||||||
|
import { ChangeDetectorRef, Component, ElementRef, OnInit, ViewChild } from '@angular/core';
|
||||||
|
import { PermissionsService } from '../../../common/service/permissions.service';
|
||||||
|
import WebViewer, { WebViewerInstance } from '@pdftron/webviewer';
|
||||||
|
import { AppStateService } from '../../../state/app-state.service';
|
||||||
|
import { FileDownloadService } from '../../file/service/file-download.service';
|
||||||
|
import { environment } from '../../../../environments/environment';
|
||||||
|
import { HttpClient } from '@angular/common/http';
|
||||||
|
import { FormBuilder, FormGroup } from '@angular/forms';
|
||||||
|
import { debounce } from '../../../utils/debounce';
|
||||||
|
|
||||||
|
@Component({
|
||||||
|
selector: 'redaction-watermark-screen',
|
||||||
|
templateUrl: './watermark-screen.component.html',
|
||||||
|
styleUrls: ['./watermark-screen.component.scss']
|
||||||
|
})
|
||||||
|
export class WatermarkScreenComponent implements OnInit {
|
||||||
|
private _instance: WebViewerInstance;
|
||||||
|
private _initialConfig = {
|
||||||
|
text: 'Watermark',
|
||||||
|
color: '#000',
|
||||||
|
opacity: 50
|
||||||
|
};
|
||||||
|
|
||||||
|
@ViewChild('viewer', { static: true })
|
||||||
|
private _viewer: ElementRef;
|
||||||
|
|
||||||
|
public viewReady = false;
|
||||||
|
public configForm: FormGroup;
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
public readonly permissionsService: PermissionsService,
|
||||||
|
public readonly appStateService: AppStateService,
|
||||||
|
private readonly _fileDownloadService: FileDownloadService,
|
||||||
|
private readonly _http: HttpClient,
|
||||||
|
private readonly _changeDetectorRef: ChangeDetectorRef,
|
||||||
|
private readonly _formBuilder: FormBuilder
|
||||||
|
) {
|
||||||
|
this.configForm = this._formBuilder.group({
|
||||||
|
text: [this._initialConfig.text],
|
||||||
|
color: [this._initialConfig.color],
|
||||||
|
opacity: [this._initialConfig.opacity]
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
ngOnInit(): void {
|
||||||
|
this._loadViewer();
|
||||||
|
}
|
||||||
|
|
||||||
|
public get changed() {
|
||||||
|
for (const key of Object.keys(this._initialConfig)) {
|
||||||
|
if (this._initialConfig[key] !== this.configForm.get(key).value) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private _loadViewer() {
|
||||||
|
WebViewer(
|
||||||
|
{
|
||||||
|
licenseKey: environment.licenseKey ? atob(environment.licenseKey) : null,
|
||||||
|
path: '/assets/wv-resources',
|
||||||
|
css: '/assets/pdftron/stylesheet.css'
|
||||||
|
},
|
||||||
|
this._viewer.nativeElement
|
||||||
|
).then((instance) => {
|
||||||
|
this._instance = instance;
|
||||||
|
|
||||||
|
instance.docViewer.on('documentLoaded', () => {
|
||||||
|
this.viewReady = true;
|
||||||
|
this._changeDetectorRef.detectChanges();
|
||||||
|
});
|
||||||
|
|
||||||
|
this._disableElements();
|
||||||
|
this._drawWatermark();
|
||||||
|
|
||||||
|
this._instance.loadDocument(`${window.location.origin}/assets/pdftron/sample.pdf`);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private _disableElements() {
|
||||||
|
this._instance.disableElements(['header', 'toolsHeader', 'pageNavOverlay', 'textPopup']);
|
||||||
|
}
|
||||||
|
|
||||||
|
private _drawWatermark() {
|
||||||
|
this._instance.docViewer.setWatermark({
|
||||||
|
// Draw diagonal watermark in middle of the document
|
||||||
|
diagonal: {
|
||||||
|
fontSize: 25, // or even smaller size
|
||||||
|
fontFamily: 'sans-serif',
|
||||||
|
color: 'red',
|
||||||
|
opacity: 50, // from 0 to 100
|
||||||
|
text: 'Watermark'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@debounce()
|
||||||
|
public configChanged() {
|
||||||
|
this._instance.docViewer.setWatermark({
|
||||||
|
// Draw diagonal watermark in middle of the document
|
||||||
|
diagonal: {
|
||||||
|
fontSize: 30,
|
||||||
|
fontFamily: 'sans-serif',
|
||||||
|
color: this.configForm.get('color').value,
|
||||||
|
opacity: this.configForm.get('opacity').value, // from 0 to 100
|
||||||
|
text: this.configForm.get('text').value
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this._instance.docViewer.refreshAll();
|
||||||
|
this._instance.docViewer.updateView([0], 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
public save() {
|
||||||
|
this._initialConfig = {
|
||||||
|
...this.configForm.getRawValue()
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public revert() {
|
||||||
|
this.configForm.setValue(this._initialConfig);
|
||||||
|
this.configChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -21,12 +21,6 @@
|
|||||||
|
|
||||||
.left-container {
|
.left-container {
|
||||||
position: relative;
|
position: relative;
|
||||||
.overlay-shadow {
|
|
||||||
@include inset-shadow;
|
|
||||||
position: absolute;
|
|
||||||
width: 100%;
|
|
||||||
height: 1px;
|
|
||||||
}
|
|
||||||
width: calc(100vw - 350px);
|
width: calc(100vw - 350px);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -566,6 +566,12 @@
|
|||||||
"save-changes": "Save Changes",
|
"save-changes": "Save Changes",
|
||||||
"revert-changes": "Revert"
|
"revert-changes": "Revert"
|
||||||
},
|
},
|
||||||
|
"watermark-screen": {
|
||||||
|
"action": {
|
||||||
|
"save": "Save",
|
||||||
|
"revert": "Revert"
|
||||||
|
}
|
||||||
|
},
|
||||||
"dictionaries": "Dictionaries",
|
"dictionaries": "Dictionaries",
|
||||||
"user-management": "User Management",
|
"user-management": "User Management",
|
||||||
"notifications": {
|
"notifications": {
|
||||||
@ -575,5 +581,6 @@
|
|||||||
"mark-read": "Mark as read",
|
"mark-read": "Mark as read",
|
||||||
"mark-unread": "Mark as unread"
|
"mark-unread": "Mark as unread"
|
||||||
},
|
},
|
||||||
"rule-editor": "Rule Editor"
|
"rule-editor": "Rule Editor",
|
||||||
|
"watermark": "Watermark"
|
||||||
}
|
}
|
||||||
|
|||||||
BIN
apps/red-ui/src/assets/pdftron/sample.pdf
Normal file
BIN
apps/red-ui/src/assets/pdftron/sample.pdf
Normal file
Binary file not shown.
@ -68,6 +68,13 @@ body {
|
|||||||
&.extended {
|
&.extended {
|
||||||
width: calc(100vw - 60px) !important;
|
width: calc(100vw - 60px) !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.overlay-shadow {
|
||||||
|
@include inset-shadow;
|
||||||
|
position: absolute;
|
||||||
|
width: 100%;
|
||||||
|
height: 4px;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.right-container {
|
.right-container {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user