<%@ Page Title="Cancel Upload" Language="C#" MasterPageFile="~/Site.master" AutoEventWireup="true" %>
<%@ Register Assembly="AjaxUploader" Namespace="AjaxUploader.Controls" TagPrefix="au" %> 
<asp:Content ID="TitleContent" ContentPlaceHolderID="TitleContent" runat="server">Cancel Upload - AjaxUploader v5.2 Demos</asp:Content>
<asp:Content ID="HeaderContent" ContentPlaceHolderID="HeaderTitle" runat="server">Cancel Upload</asp:Content> 
<asp:Content ID="BodyContent" ContentPlaceHolderID="MainContent" runat="server"> 
<div class="demo-card"> <div class="demo-card-header">Cancel Individual or All Uploads</div> <div class="demo-card-body"> <p class="demo-description"> Cancel a specific file upload or cancel all queued uploads at once. Cancelled uploads
 are removed from the queue and any partial data on the server is cleaned up.
 </p> <au:AjaxFileUpload ID="Uploader1" runat="server"
 AllowMultiple="true"
 AutoUpload="true"
 ShowProgress="true" /> <div class="mt-2"> <button type="button" class="btn btn-danger btn-sm" id="btnCancelAll" disabled>Cancel All</button> </div> <div id="queueList" class="mt-3"></div> <div class="code-panel"> <pre><code>&lt;au:AjaxFileUpload ID="Uploader1" runat="server"
 AllowMultiple="true"
 AutoUpload="true"
 ShowProgress="true" /&gt;

// JavaScript API
var uploader = AjaxUploader.getInstance('Uploader1');

// Cancel one: uploader.cancelTask(taskId);
// Cancel all: uploader.cancelAll();</code></pre> </div> </div>
</div> 
</asp:Content> 
<asp:Content ID="ScriptsContent" ContentPlaceHolderID="ScriptsContent" runat="server">
<script> var queueList = document.getElementById('queueList');
 var btnCancelAll = document.getElementById('btnCancelAll');
 function clampPercent(value) {
 var pct = Number(value);
 if (!isFinite(pct)) return 0;
 return Math.max(0, Math.min(100, Math.round(pct)));
 }

 var uploader = window.AjaxUploader && typeof AjaxUploader.getInstance === 'function' ? AjaxUploader.getInstance('Uploader1') : null;
 if (uploader) {
 uploader.on('queueRender', function(queue) {
 if (!queueList || !btnCancelAll) return;
 queueList.textContent = '';
 btnCancelAll.disabled = queue.length === 0;
 queue.forEach(function(item) {
 var div = document.createElement('div');
 div.className = 'p-2 mb-1 border rounded d-flex justify-content-between align-items-center';
 var statusText = item.status === 'uploading' ? clampPercent(item.percent) + '%' : item.status;
 var badge = item.status === 'complete' ? 'bg-success' :
 item.status === 'uploading' ? 'bg-primary' :
 item.status === 'cancelled' ? 'bg-danger' : 'bg-secondary';
 var info = document.createElement('span');
 info.appendChild(document.createTextNode((item.fileName || 'File') + ' '));
 var size = document.createElement('small');
 size.className = 'text-muted';
 size.textContent = '(' + (window.AjaxUploader && AjaxUploader.formatSize ? AjaxUploader.formatSize(item.total) : (item.total || 0) + ' B') + ')';
 info.appendChild(size);
 var actions = document.createElement('span');
 actions.className = 'd-flex align-items-center gap-2';
 var status = document.createElement('span');
 status.className = 'badge ' + badge;
 status.textContent = statusText;
 actions.appendChild(status);
 if (item.status !== 'complete' && item.status !== 'cancelled') {
 var cancel = document.createElement('button');
 cancel.type = 'button';
 cancel.className = 'btn btn-outline-danger btn-sm';
 cancel.dataset.id = item.id;
 cancel.textContent = 'Cancel';
 actions.appendChild(cancel);
 }
 div.appendChild(info);
 div.appendChild(actions);
 queueList.appendChild(div);
 });
 });
 uploader.on('complete', function() {
 btnCancelAll.disabled = true;
 });
 }

 if (queueList) queueList.addEventListener('click', function(e) {
 if (e.target.dataset.id && uploader && uploader.cancelTask) {
 uploader.cancelTask(e.target.dataset.id);
 }
 });

 if (btnCancelAll) btnCancelAll.addEventListener('click', function() {
 if (uploader && uploader.cancelAll) uploader.cancelAll();
 btnCancelAll.disabled = true;
 });
</script>
</asp:Content>
