diff --git a/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.html b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.html
new file mode 100644
index 0000000..6767fa5
--- /dev/null
+++ b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.html
@@ -0,0 +1,57 @@
+
+
+
+
+
+
+ Uploading...
+
+
+
+
+
+
+
+
+
+
+
+
![{{ value }}]()
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.scss b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.scss
new file mode 100644
index 0000000..a4bfbb6
--- /dev/null
+++ b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.scss
@@ -0,0 +1,102 @@
+.file-uploader-container {
+ margin-bottom: 0.5rem;
+
+ .clr-control-label {
+ display: block;
+ font-size: 0.65rem;
+ font-weight: 600;
+ margin-bottom: 0.25rem;
+ color: #444;
+ }
+
+ .upload-input-row {
+ margin-top: 0.25rem;
+
+ .upload-btn {
+ position: relative;
+ cursor: pointer;
+ display: inline-flex;
+ align-items: center;
+ gap: 0.35rem;
+ margin: 0;
+
+ .hidden-file-input {
+ position: absolute;
+ top: 0;
+ left: 0;
+ width: 100%;
+ height: 100%;
+ opacity: 0;
+ cursor: pointer;
+ }
+ }
+ }
+
+ .uploading-state {
+ display: flex;
+ align-items: center;
+ gap: 0.5rem;
+ padding: 0.35rem 0;
+ color: #555;
+ font-size: 0.75rem;
+ }
+
+ .preview-container {
+ margin-top: 0.35rem;
+ padding: 0.4rem;
+ border: 1px solid #e0e0e0;
+ border-radius: 4px;
+ background-color: #fafafa;
+
+ .image-preview img {
+ max-width: 100%;
+ max-height: 120px;
+ object-fit: cover;
+ border-radius: 3px;
+ margin-bottom: 0.3rem;
+ display: block;
+ }
+
+ .audio-preview audio {
+ width: 100%;
+ height: 36px;
+ margin-bottom: 0.3rem;
+ }
+
+ .video-preview video {
+ max-width: 100%;
+ max-height: 140px;
+ border-radius: 3px;
+ margin-bottom: 0.3rem;
+ display: block;
+ }
+
+ .file-meta {
+ display: flex;
+ align-items: center;
+ gap: 0.35rem;
+ font-size: 0.75rem;
+
+ .file-icon {
+ flex-shrink: 0;
+ }
+
+ .file-name {
+ overflow: hidden;
+ text-overflow: ellipsis;
+ white-space: nowrap;
+ flex-grow: 1;
+ color: #0072a3;
+ text-decoration: underline;
+ }
+
+ .remove-btn {
+ margin: 0;
+ padding: 0 0.25rem;
+ min-width: auto;
+ color: #c92c2c;
+ }
+ }
+ }
+}
+
diff --git a/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.ts b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.ts
new file mode 100644
index 0000000..dd96beb
--- /dev/null
+++ b/frontend/angular-clarity-master/src/app/modules/main/BuilderComponents/file-uploader/file-uploader.component.ts
@@ -0,0 +1,122 @@
+import { Component, forwardRef, Input } from '@angular/core';
+import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';
+import { HttpClient } from '@angular/common/http';
+import { ToastrService } from 'ngx-toastr';
+import { AppConfig } from 'src/app/app-config';
+
+@Component({
+ selector: 'app-file-uploader',
+ templateUrl: './file-uploader.component.html',
+ styleUrls: ['./file-uploader.component.scss'],
+ providers: [
+ {
+ provide: NG_VALUE_ACCESSOR,
+ useExisting: forwardRef(() => FileUploaderComponent),
+ multi: true
+ }
+ ]
+})
+export class FileUploaderComponent implements ControlValueAccessor {
+ @Input() label: string = 'Upload File';
+ @Input() type: 'file' | 'image' | 'audio' | 'video' = 'file';
+ @Input() ref: string = 'common';
+ @Input() tableName: string = 'files';
+
+ value: string = '';
+ uploading: boolean = false;
+ disabled: boolean = false;
+
+ private onChange: (val: any) => void = () => {};
+ private onTouched: () => void = () => {};
+
+ constructor(
+ private http: HttpClient,
+ private appConfig: AppConfig,
+ private toastr: ToastrService
+ ) {}
+
+ get acceptTypes(): string {
+ switch (this.type) {
+ case 'image':
+ return 'image/*';
+ case 'audio':
+ return 'audio/*';
+ case 'video':
+ return 'video/*';
+ default:
+ return '*/*';
+ }
+ }
+
+ get fileUrl(): string {
+ if (!this.value) {
+ return '';
+ }
+ if (this.value.startsWith('http://') || this.value.startsWith('https://')) {
+ return this.value;
+ }
+ const base = this.appConfig?.baseApiPath || '';
+ const cleanBase = base.endsWith('/') ? base : base + '/';
+ return `${cleanBase}FileUpload/files/${this.value}`;
+ }
+
+ writeValue(val: any): void {
+ this.value = val || '';
+ }
+
+ registerOnChange(fn: any): void {
+ this.onChange = fn;
+ }
+
+ registerOnTouched(fn: any): void {
+ this.onTouched = fn;
+ }
+
+ setDisabledState?(isDisabled: boolean): void {
+ this.disabled = isDisabled;
+ }
+
+ onFileSelected(event: any): void {
+ const file = event.target.files && event.target.files[0];
+ if (!file) {
+ return;
+ }
+
+ this.uploading = true;
+ const formData = new FormData();
+ formData.append('file', file);
+
+ const base = this.appConfig?.baseApiPath || '';
+ const cleanBase = base.endsWith('/') ? base : base + '/';
+ const uploadUrl = `${cleanBase}FileUpload/Uploadeddocs/${this.ref}/${this.tableName}`;
+
+ this.http.post(uploadUrl, formData).subscribe({
+ next: (res) => {
+ this.uploading = false;
+ const filename = res?.uploadedfile_name || file.name;
+ this.value = filename;
+ this.onChange(this.value);
+ this.onTouched();
+ this.toastr.success('File uploaded successfully');
+ event.target.value = '';
+ },
+ error: (err) => {
+ this.uploading = false;
+ console.error('File upload failed', err);
+ this.toastr.error('File upload failed');
+ event.target.value = '';
+ }
+ });
+ }
+
+ removeFile(): void {
+ this.value = '';
+ this.onChange('');
+ this.onTouched();
+ }
+
+ onImgError(event: any): void {
+ console.warn('Image failed to load:', this.fileUrl);
+ }
+}
+
diff --git a/frontend/angular-clarity-master/src/app/modules/main/main.module.ts b/frontend/angular-clarity-master/src/app/modules/main/main.module.ts
index 714ccd6..cdd3bd2 100644
--- a/frontend/angular-clarity-master/src/app/modules/main/main.module.ts
+++ b/frontend/angular-clarity-master/src/app/modules/main/main.module.ts
@@ -106,6 +106,7 @@ import { MappingruleaddComponent } from './datamanagement/mappingrule/mappingrul
import { MappingruleallComponent } from './datamanagement/mappingrule/mappingruleall/mappingruleall.component';
import { MappingruleeditComponent } from './datamanagement/mappingrule/mappingruleedit/mappingruleedit.component';
import { Stepper_workflowComponent } from './BuilderComponents/stepperworkflow/Stepper_workflow/Stepper_workflow.component';
+import { FileUploaderComponent } from './BuilderComponents/file-uploader/file-uploader.component';
import { Token_registeryComponent } from './fnd/Token_registery/Token_registery.component';
import { MyworkspaceComponent } from './admin/myworkspace/myworkspace.component';
import { DynamicformComponent } from './superadmin/dynamicform/dynamicform.component';
@@ -140,6 +141,7 @@ import { DynamicFormViewerComponent } from './superadmin/dynamicform/dynamic-for
// buildercomponents
+ FileUploaderComponent,
diff --git a/frontend/angular-clarity-master/src/environments/environment.prod.ts b/frontend/angular-clarity-master/src/environments/environment.prod.ts
index f038c84..4dc13f2 100644
--- a/frontend/angular-clarity-master/src/environments/environment.prod.ts
+++ b/frontend/angular-clarity-master/src/environments/environment.prod.ts
@@ -9,9 +9,8 @@ export const environment = {
// changeble url // port
captchaSiteKey: '6LfrdSUpAAAAALkYDmnvdX3GLLCArgPWNHfXasjP',
-
- //Deployment configs
-
+
+ //Deployment configs
};