merging code

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Nitesh Yadav
2026-04-20 14:26:25 +05:30
co-authored by Claude Sonnet 4.6
322 changed files with 28779 additions and 4976 deletions
@@ -1,3 +1,11 @@
<!--
Copyright since 2025 Mifos Initiative
This Source Code Form is subject to the terms of the Mozilla Public
License, v. 2.0. If a copy of the MPL was not distributed with this
file, You can obtain one at http://mozilla.org/MPL/2.0/.
-->
<!--
Copyright since 2025 Mifos Initiative
-->
@@ -20,11 +28,13 @@
<div class="crop-workspace" [class.hidden]="!imageLoaded">
<div class="crop-source">
<canvas #sourceCanvas
<canvas
#sourceCanvas
(mousedown)="onMouseDown($event)"
(mousemove)="onMouseMove($event)"
(mouseup)="onMouseUp()"
(mouseleave)="onMouseUp()">
(mouseleave)="onMouseUp()"
>
</canvas>
<div class="crop-hint">Drag to move. Drag corner to resize.</div>
</div>
@@ -1,3 +1,11 @@
/**
* Copyright since 2025 Mifos Initiative
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*/
/**
* Copyright since 2025 Mifos Initiative
*/
@@ -158,7 +166,7 @@ $navy: #0f172a;
}
}
@media (max-width: 600px) {
@media (width <= 600px) {
.crop-workspace {
flex-direction: column;
}
@@ -1,8 +1,12 @@
/**
* Copyright since 2025 Mifos Initiative
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*/
import { Component, Inject, ViewChild, ElementRef, AfterViewInit } from '@angular/core';
import { Component, inject, ViewChild, ElementRef, AfterViewInit } from '@angular/core';
import { MAT_DIALOG_DATA, MatDialogRef, MatDialogContent, MatDialogActions } from '@angular/material/dialog';
import { STANDALONE_SHARED_IMPORTS } from 'app/standalone-shared.module';
import { FaIconComponent } from '@fortawesome/angular-fontawesome';
@@ -59,10 +63,8 @@ export class ImageCropDialogComponent implements AfterViewInit {
zoom = 1;
constructor(
public dialogRef: MatDialogRef<ImageCropDialogComponent>,
@Inject(MAT_DIALOG_DATA) public data: ImageCropData
) {}
dialogRef = inject(MatDialogRef<ImageCropDialogComponent>);
data = inject<ImageCropData>(MAT_DIALOG_DATA);
ngAfterViewInit() {
const reader = new FileReader();
@@ -127,9 +129,14 @@ export class ImageCropDialogComponent implements AfterViewInit {
ctx.clearRect(this.cropX, this.cropY, this.cropW, this.cropH);
ctx.drawImage(
this.img,
this.cropX * this.scaleX, this.cropY * this.scaleY,
this.cropW * this.scaleX, this.cropH * this.scaleY,
this.cropX, this.cropY, this.cropW, this.cropH
this.cropX * this.scaleX,
this.cropY * this.scaleY,
this.cropW * this.scaleX,
this.cropH * this.scaleY,
this.cropX,
this.cropY,
this.cropW,
this.cropH
);
// Crop border
@@ -141,14 +148,31 @@ export class ImageCropDialogComponent implements AfterViewInit {
const hs = 8;
ctx.fillStyle = '#1353a0';
const corners = [
[this.cropX, this.cropY],
[this.cropX + this.cropW, this.cropY],
[this.cropX, this.cropY + this.cropH],
[this.cropX + this.cropW, this.cropY + this.cropH]
[
this.cropX,
this.cropY
],
[
this.cropX + this.cropW,
this.cropY
],
[
this.cropX,
this.cropY + this.cropH
],
[
this.cropX + this.cropW,
this.cropY + this.cropH
]
];
corners.forEach(([x, y]) => {
ctx.fillRect(x - hs / 2, y - hs / 2, hs, hs);
});
corners.forEach(
([
x,
y
]) => {
ctx.fillRect(x - hs / 2, y - hs / 2, hs, hs);
}
);
}
private updatePreview() {
@@ -163,9 +187,14 @@ export class ImageCropDialogComponent implements AfterViewInit {
pCtx.clearRect(0, 0, pw, ph);
pCtx.drawImage(
this.img,
this.cropX * this.scaleX, this.cropY * this.scaleY,
this.cropW * this.scaleX, this.cropH * this.scaleY,
0, 0, pw, ph
this.cropX * this.scaleX,
this.cropY * this.scaleY,
this.cropW * this.scaleX,
this.cropH * this.scaleY,
0,
0,
pw,
ph
);
}
@@ -229,9 +258,14 @@ export class ImageCropDialogComponent implements AfterViewInit {
const ctx = offscreen.getContext('2d')!;
ctx.drawImage(
this.img,
this.cropX * this.scaleX, this.cropY * this.scaleY,
this.cropW * this.scaleX, this.cropH * this.scaleY,
0, 0, offscreen.width, offscreen.height
this.cropX * this.scaleX,
this.cropY * this.scaleY,
this.cropW * this.scaleX,
this.cropH * this.scaleY,
0,
0,
offscreen.width,
offscreen.height
);
offscreen.toBlob((blob) => {