up file upload limit to 20mb and fix switch camera
This commit is contained in:
@@ -420,7 +420,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'front_image', 'front_preview')">
|
||||
</div>
|
||||
<div id="front_preview" class="photo-preview"></div>
|
||||
@@ -460,7 +460,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'cabin_temperature_image', 'cabin_preview')">
|
||||
</div>
|
||||
<div id="cabin_preview" class="photo-preview"></div>
|
||||
@@ -507,7 +507,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'ac_image', 'ac_preview')">
|
||||
</div>
|
||||
<div id="ac_preview" class="photo-preview"></div>
|
||||
@@ -554,7 +554,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'blower_image', 'blower_preview')">
|
||||
</div>
|
||||
<div id="blower_preview" class="photo-preview"></div>
|
||||
@@ -601,7 +601,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'evaporator_image', 'evaporator_preview')">
|
||||
</div>
|
||||
<div id="evaporator_preview" class="photo-preview"></div>
|
||||
@@ -1086,13 +1086,7 @@
|
||||
}
|
||||
|
||||
try {
|
||||
// Stop current stream
|
||||
stopCamera(videoId);
|
||||
|
||||
// Wait a bit before starting new camera
|
||||
await new Promise(resolve => setTimeout(resolve, 100));
|
||||
|
||||
// Get current facing mode
|
||||
// Get current facing mode before stopping
|
||||
const currentTracks = streams[videoId] ? streams[videoId].getVideoTracks() : [];
|
||||
let currentFacingMode = 'environment'; // default to back camera
|
||||
|
||||
@@ -1106,16 +1100,75 @@
|
||||
// Switch to opposite camera
|
||||
const newFacingMode = currentFacingMode === 'environment' ? 'user' : 'environment';
|
||||
|
||||
const constraints = {
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 },
|
||||
facingMode: { ideal: newFacingMode }
|
||||
}
|
||||
};
|
||||
// Stop current stream
|
||||
stopCamera(videoId);
|
||||
|
||||
const stream = await navigator.mediaDevices.getUserMedia(constraints);
|
||||
// Wait a bit before starting new camera
|
||||
await new Promise(resolve => setTimeout(resolve, 200));
|
||||
|
||||
// Try to get the specific camera
|
||||
let stream;
|
||||
|
||||
try {
|
||||
// First try with specific facing mode
|
||||
const constraints = {
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 },
|
||||
facingMode: { ideal: newFacingMode }
|
||||
}
|
||||
};
|
||||
|
||||
stream = await navigator.mediaDevices.getUserMedia(constraints);
|
||||
} catch (err) {
|
||||
console.log('Gagal dengan facingMode, mencoba dengan deviceId...');
|
||||
|
||||
// If facingMode fails, try to get available devices and switch
|
||||
try {
|
||||
const devices = await navigator.mediaDevices.enumerateDevices();
|
||||
const videoDevices = devices.filter(device => device.kind === 'videoinput');
|
||||
|
||||
if (videoDevices.length > 1) {
|
||||
// Find current device index
|
||||
const currentDevice = videoDevices.find(device => {
|
||||
if (currentTracks.length > 0) {
|
||||
return device.deviceId === currentTracks[0].getSettings().deviceId;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
const currentIndex = currentDevice ? videoDevices.indexOf(currentDevice) : 0;
|
||||
const nextIndex = (currentIndex + 1) % videoDevices.length;
|
||||
const nextDevice = videoDevices[nextIndex];
|
||||
|
||||
console.log('Beralih dari device:', currentDevice?.label, 'ke:', nextDevice?.label);
|
||||
|
||||
const deviceConstraints = {
|
||||
video: {
|
||||
deviceId: { exact: nextDevice.deviceId },
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 }
|
||||
}
|
||||
};
|
||||
|
||||
stream = await navigator.mediaDevices.getUserMedia(deviceConstraints);
|
||||
} else {
|
||||
// Fallback to basic constraints
|
||||
stream = await navigator.mediaDevices.getUserMedia({
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 }
|
||||
}
|
||||
});
|
||||
}
|
||||
} catch (deviceErr) {
|
||||
console.error('Gagal beralih dengan deviceId:', deviceErr);
|
||||
throw deviceErr;
|
||||
}
|
||||
}
|
||||
|
||||
video.srcObject = stream;
|
||||
streams[videoId] = stream;
|
||||
@@ -1142,6 +1195,17 @@
|
||||
|
||||
console.log('Berhasil beralih ke kamera:', newFacingMode === 'environment' ? 'belakang' : 'depan');
|
||||
|
||||
// Show success notification
|
||||
Swal.fire({
|
||||
icon: 'success',
|
||||
title: 'Kamera Berhasil Diganti',
|
||||
text: `Berhasil beralih ke ${newFacingMode === 'environment' ? 'kamera belakang' : 'kamera depan'}`,
|
||||
timer: 1500,
|
||||
showConfirmButton: false,
|
||||
toast: true,
|
||||
position: 'top-end'
|
||||
});
|
||||
|
||||
} catch (err) {
|
||||
console.error('Gagal beralih kamera:', err);
|
||||
Swal.fire({
|
||||
@@ -1204,12 +1268,12 @@
|
||||
return;
|
||||
}
|
||||
|
||||
// Validasi ukuran file (max 2MB)
|
||||
if (file.size > 2 * 1024 * 1024) {
|
||||
// Validasi ukuran file (max 20MB)
|
||||
if (file.size > 20 * 1024 * 1024) {
|
||||
Swal.fire({
|
||||
icon: 'warning',
|
||||
title: 'Ukuran File Terlalu Besar',
|
||||
text: 'Ukuran file maksimal 2MB',
|
||||
text: 'Ukuran file maksimal 20MB',
|
||||
confirmButtonText: 'OK'
|
||||
});
|
||||
return;
|
||||
|
||||
@@ -420,7 +420,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'front_image', 'front_preview')">
|
||||
</div>
|
||||
<div id="front_preview" class="photo-preview"></div>
|
||||
@@ -460,7 +460,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'cabin_temperature_image', 'cabin_preview')">
|
||||
</div>
|
||||
<div id="cabin_preview" class="photo-preview"></div>
|
||||
@@ -507,7 +507,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'ac_image', 'ac_preview')">
|
||||
</div>
|
||||
<div id="ac_preview" class="photo-preview"></div>
|
||||
@@ -554,7 +554,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'blower_image', 'blower_preview')">
|
||||
</div>
|
||||
<div id="blower_preview" class="photo-preview"></div>
|
||||
@@ -601,7 +601,7 @@
|
||||
</button>
|
||||
</div>
|
||||
<div class="mt-2">
|
||||
<small class="text-muted">Atau upload foto dari galeri:</small>
|
||||
<small class="text-muted">Atau upload foto dari galeri (maksimal 20MB):</small>
|
||||
<input type="file" class="form-control-file mt-1" accept="image/*" onchange="handleFileUpload(this, 'evaporator_image', 'evaporator_preview')">
|
||||
</div>
|
||||
<div id="evaporator_preview" class="photo-preview"></div>
|
||||
@@ -1086,13 +1086,7 @@
|
||||
}
|
||||
|
||||
try {
|
||||
// Stop current stream
|
||||
stopCamera(videoId);
|
||||
|
||||
// Wait a bit before starting new camera
|
||||
await new Promise(resolve => setTimeout(resolve, 100));
|
||||
|
||||
// Get current facing mode
|
||||
// Get current facing mode before stopping
|
||||
const currentTracks = streams[videoId] ? streams[videoId].getVideoTracks() : [];
|
||||
let currentFacingMode = 'environment'; // default to back camera
|
||||
|
||||
@@ -1106,16 +1100,75 @@
|
||||
// Switch to opposite camera
|
||||
const newFacingMode = currentFacingMode === 'environment' ? 'user' : 'environment';
|
||||
|
||||
const constraints = {
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 },
|
||||
facingMode: { ideal: newFacingMode }
|
||||
}
|
||||
};
|
||||
// Stop current stream
|
||||
stopCamera(videoId);
|
||||
|
||||
const stream = await navigator.mediaDevices.getUserMedia(constraints);
|
||||
// Wait a bit before starting new camera
|
||||
await new Promise(resolve => setTimeout(resolve, 200));
|
||||
|
||||
// Try to get the specific camera
|
||||
let stream;
|
||||
|
||||
try {
|
||||
// First try with specific facing mode
|
||||
const constraints = {
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 },
|
||||
facingMode: { ideal: newFacingMode }
|
||||
}
|
||||
};
|
||||
|
||||
stream = await navigator.mediaDevices.getUserMedia(constraints);
|
||||
} catch (err) {
|
||||
console.log('Gagal dengan facingMode, mencoba dengan deviceId...');
|
||||
|
||||
// If facingMode fails, try to get available devices and switch
|
||||
try {
|
||||
const devices = await navigator.mediaDevices.enumerateDevices();
|
||||
const videoDevices = devices.filter(device => device.kind === 'videoinput');
|
||||
|
||||
if (videoDevices.length > 1) {
|
||||
// Find current device index
|
||||
const currentDevice = videoDevices.find(device => {
|
||||
if (currentTracks.length > 0) {
|
||||
return device.deviceId === currentTracks[0].getSettings().deviceId;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
const currentIndex = currentDevice ? videoDevices.indexOf(currentDevice) : 0;
|
||||
const nextIndex = (currentIndex + 1) % videoDevices.length;
|
||||
const nextDevice = videoDevices[nextIndex];
|
||||
|
||||
console.log('Beralih dari device:', currentDevice?.label, 'ke:', nextDevice?.label);
|
||||
|
||||
const deviceConstraints = {
|
||||
video: {
|
||||
deviceId: { exact: nextDevice.deviceId },
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 }
|
||||
}
|
||||
};
|
||||
|
||||
stream = await navigator.mediaDevices.getUserMedia(deviceConstraints);
|
||||
} else {
|
||||
// Fallback to basic constraints
|
||||
stream = await navigator.mediaDevices.getUserMedia({
|
||||
video: {
|
||||
width: { min: 320, ideal: 640, max: 1280 },
|
||||
height: { min: 240, ideal: 480, max: 720 },
|
||||
aspectRatio: { ideal: 4/3 }
|
||||
}
|
||||
});
|
||||
}
|
||||
} catch (deviceErr) {
|
||||
console.error('Gagal beralih dengan deviceId:', deviceErr);
|
||||
throw deviceErr;
|
||||
}
|
||||
}
|
||||
|
||||
video.srcObject = stream;
|
||||
streams[videoId] = stream;
|
||||
@@ -1142,6 +1195,17 @@
|
||||
|
||||
console.log('Berhasil beralih ke kamera:', newFacingMode === 'environment' ? 'belakang' : 'depan');
|
||||
|
||||
// Show success notification
|
||||
Swal.fire({
|
||||
icon: 'success',
|
||||
title: 'Kamera Berhasil Diganti',
|
||||
text: `Berhasil beralih ke ${newFacingMode === 'environment' ? 'kamera belakang' : 'kamera depan'}`,
|
||||
timer: 1500,
|
||||
showConfirmButton: false,
|
||||
toast: true,
|
||||
position: 'top-end'
|
||||
});
|
||||
|
||||
} catch (err) {
|
||||
console.error('Gagal beralih kamera:', err);
|
||||
Swal.fire({
|
||||
@@ -1204,12 +1268,12 @@
|
||||
return;
|
||||
}
|
||||
|
||||
// Validasi ukuran file (max 2MB)
|
||||
if (file.size > 2 * 1024 * 1024) {
|
||||
// Validasi ukuran file (max 20MB)
|
||||
if (file.size > 20 * 1024 * 1024) {
|
||||
Swal.fire({
|
||||
icon: 'warning',
|
||||
title: 'Ukuran File Terlalu Besar',
|
||||
text: 'Ukuran file maksimal 2MB',
|
||||
text: 'Ukuran file maksimal 20MB',
|
||||
confirmButtonText: 'OK'
|
||||
});
|
||||
return;
|
||||
|
||||
Reference in New Issue
Block a user