من متوجه شدم (هنگامی که به دنبال خودم) که بسیاری از نسخه های نمایشی و آموزش است که به شما نشان می دهد که چگونه به کشیدن و رها کردن یک فایل را به مرورگر و سپس آن را در صفحه رندر وجود دارد. آنها اغلب به عنوان برچسب "کشیدن و رها کردن و آپلود" ، اما آنها در واقع آپلود نیست. این آموزش شما را که گام نهایی.
من شما را از طریق یک مثال است که شما می توانید با بازی راه رفتن: کشیدن یک فایل را به صفحه وب، و آن را به سرور فورا آپلود خواهد شد.
وظایف #
بیایید این فرایند را به وظایف خاص بشکنیم:
- رویداد قطره را ضبط کنید و داده های آن را بخوانید.
- آن داده دودویی را به سرور ارسال کنید.
- ارائه بازخورد در مورد پیشرفت آپلود.
- به طور اختیاری ارائه پیش نمایش از آنچه در حال آپلود و وضعیت آن است.
برای رسیدن به همه این ها به برنامه های HTML5 و غیر HTML5 زیر نیاز داریم:
به خاطر داشته باشید که همه مرورگرها امروز از تمام این فناوری پشتیبانی نمی کنند، اما نزدیک می شوند. من فقط می خواستم برای ایجاد یک آموزش روشن و کامل در مورد چگونگی رفتن به کل گراز و آپلود است که فایل کاهش یافته است.
نتیجه نهایی: ما قادر به رها کردن فایل در هر نقطه از مرورگر، ما یک پیش نمایش و پیشرفت آپلود، و آن را یک تجربه نرم و صاف است.

کشیدن و رها کردن #
همانطور که پیش از این، کشیدن و رها کردن شناخته شده است به کمی از killjoy. در واقع کابوس است اما آنچه پیش از این گفته شده را تکرار نمی کنم.
مثال ما این است که به شما اجازه کشیدن و رها کردن یک فایل در هر نقطه در داخل مرورگر. برای رسیدن به آن، ما باید شنوندگان ر
وید
اد
خود را ب
ه بدن یا document با گوش دادن بر روی d
ocument وین، ای
ن کد می تواند در هر نقطه ای از صفحه باشد، چرا
که document همي
شه وجود خواهد داشت. شما فقط می توانید بر رو
ی بدن
گوش دادن
یک بار
<body>عنصر مواجه شده است.</body>
در اینجا الگوی کد ما نیاز به گرفتن رویداد قطره در کل سند :
var doc = document.document doc.ondragover = function () { this.className = 'hover';return false; }; doc.ondragend = function () { this.className = ''; returnfalse; }; doc.ondrop = function (event) { event.preventDefault && event.preventDefault(); this.className = ''; در حال حاضر انجام کاری با: فایل های var = event.dataTransfer.files; بازگشت کاذب; };
من با استفاده
از ک
لاس شناور به طوری که من می توانم یک نوک توضیح به کاربر که فایل را می توان در صفحه کاهش یافته است.
در داخل رویدا
د قطر
ه، ما می توانیم فایل های کاهش یافته viaevent.dataTr
ansfer.files دسترسی داشته باش
د.
جایگزینی برای کشیدن و رها کردن #
آزار دهنده، همانطور که من این را بنویسید، من متوجه این ترکیب از الزامات API در حال حاضر تنها توسط کروم و فایرفاکس برآورده شده است. بنابراین ، گرفتن آزمون از Modernizr ، ما می توانیم برای حمایت تست و ارائه جایگزین ما :
var dndSupported = function () { var div = document.create return ('dragable' in div) || ('ondragstart' in div &&'ondrop' in div); }; if (!dndSupported()) { // take alternative route }
به جای کشیدن و رها کردن، می توانیم یک عنصر ورودی فایل را وارد کنیم (شناسه "آپلود" ر
ا
به آن داده ام)، و هنگامی که مقدار آن تغییر کرد، می توان فایل را در اسکوپ کرد:
document.get EmlById('upload').onchange = function (event){ // 'this' refers to the element the event fired upon var files = this.files; };
شما می توانید معادل به سادگی اموا
ل فا
یل های شیHTMLI
nput اسپو را
ببینید. این به ما دسترسی به همان فایل به عنوان ev
ent.dataTransfer.fil
es از رویداد قطره.
آپلود خودکار پرونده #
این بیت شسته و رفته است، و به طرز دردناکی ساده است. ما با استفاده از یک ویژگی از مشخصات XHR2
: FormDat
a. هنگامی که نمونه ای از FormData را ایج
اد می کنیم
، می توانیم موارد را به آن آپم کنیم:
var formData = new FormData(); for (var i = 0; i < files.length; i++) { formData.append('file', files[i]); } // now post a new XHR request var xhr = new XMLHttpRequest(); xhr.open('POST', '/upload'); xhr.onload = function () { if (xhr.status === 200) { console.log('all done: ' + xhr.status); } else { console.log('Something went terribly wrong...'); } }; xhr.send(formData);
ormData
بله، همین.†
بیایید به چند چیز کلیدی که در حال رفتن بر روی کد بالا نگاه کنید.
formData.append('file', files[i]);
ما در حال ارسال پارامترهای نام گذاری شده به سرور خود هستیم، به طور خاص آرایه ای از مقادیر به نام
فای
ل. بدیهی است، شما می توانید آن را آنچه شما می خواهید تماس
بگیر
ید، اما فایل نام سرور شما خواهد بود به دنبال زمانی که آن را ذخیره می کند فایل آپلود شده (یا فایل).
xhr.onload = function () { if (xhr.status = 200) { console.log('all done: ' + xhr.status); } else { console.log('Something went terribly wrong...'); } };
اگر شما با XHR آشنا, شما متوجه می شوید که ما در حال گوش داد
ن به toonreadyst
atechan
ge نی
ست, تنها onload — که (در اثر) یک تابع راحتی به شما اطلاع دهید زمان
ی که آماد
ه است 4 (یعنی, لود!). شما هنوز هم باید بررسی و پاسخ مناسب به کد وضعیت درخواست برای اطمینان از آن 200 خوب است، به جای 500 (خطای سرور داخلی) و یا 404 (یافت نشد) و یا هر چیز دیگری.
xhr.send(formData);
ترفند خوب در اینجا این است که XHR به طور خودکار تنظیم encoding از داده های ارسال شده به چن
د بخشی / فرم داده ه
ا. این encoding اجازه می دهد تا سرور خود را به خواندن و ذخیره فایل ها. مثل این است که وقتی پیوستی را در یک ایمیل ارسال می کنید، از آن استفاده می شود.
ارائه بازخورد به کاربر #
XHR2 در حال حاضر (flippin' در نهایت) همراه با
یک رویداد
پیشرفت. بنابراین اگر شما در حال ارسال یا بازیابی یک فایل بزرگ از طریق XHR، شما می توانید به کاربر بگویید که چقدر در طول شما هستند.
خيلي ساده است . اگر می خواهید پیشرفت درخواست XHR را پیگیری کنید، به رویداد پی
شرفت گو
ش کنید. یکی gotcha که من را برای برخی از زمان گرفتار : من نیاز به ردیابی پیشرفت آپلود ، نه دانلود. برای انجام این کار به درستی، شما نیاز به گوش دادن برای پیشرفت در شی آپلود TheXHR، به عنوان بنابراین:
xhr.upload.onprogress = function (event) { if (event.lengthComputable) { var complete = (event.loaded / event.total * 100 | 0); progress.value = progress.innerHTML = complete; } }; xhr.onload = function () { // just in case we get stuck around 99% progress.value = progress.innerHTML = 100; };
پیشرفت
XHR2توجه داشته باشید که به
جای xhr.onprogr
ess، ما u
sexhr.upload.onproges
s. هنگامی که این رویداد آتش می گیرد، بررسی می کنیم که رویداد از محاسبه مقدار داده های آپلود شده (بخش قاب
ل محاسبه) پشتیبان
ی می کند، و سپس مقدار تکمیل شده را محاسبه می کند.
در HTML من، من با استفاد
ه از یک عنص
ر (شبیه به عنصر، اما بیش
تر از نظ
ر معنایی مناسب به عنوان ما در حال ارائه پیشرفت یک کار) به کاربر نشان می دهد که چقدر از فایل خود را آپلود شده <progress><meter> است:</meter> </progress>
<progress id="progress" min="0" max="100" value="0">0</progress>
توجه داشته باشید که من با اس
تفاده از inn
erHTML برای مرورگرهای که هنوز پشتیبانی نمی<progress
>کند.</progres
s> سپس با یک خط تیره از محتوای CSS تولید شده،
هر دو t
hein
nerH
TML و ارزش پیشرفت می تواند همان (شاید بیش از خوش بینی، اما من به جای افتخار خودم در آن زمان!).
و در نهایت، رندر کردن یک پیش نمایش #
به عنوان یک علاوه بر خوب، ما به کاربر پیش نمایش از آنچه که ما برای آنها آپلود. این نیاز به API فایل — به طور خاص A
PIFileRe
ader.
همانطور که عملیات کشیدن و رها کردن
(یا [type=file]
ورودی) شامل یک شی فایل، ما می توانیم این را به Fil
eReader ت
حویل برای دریافت محتویات فایل. اگر چیزی شبیه تصویر باشد، می توانیم داده های Base64 را دریافت کنیم و پیش نمایش به کاربر بدهیم. یا اگر متن باشد، می توانیم آن را در یک<div>
.</di
v> نوع MIME برای فایل به عنوان ملک نمون
ه د
ر شی فایل در دسترس است.
پس فرض کنیم فقط تصاویر را می پذیریم. در اینجا بخش پیش نمایش است که اجرا می شود پس از فایل توسط مرورگر دریافت شده است:
var acceptedTypes = { 'image/png': true, 'image/jpeg': true, 'image/gif': true }; if (acceptedTyp[file.type]es === true) { var reader = new FileReader(); reader.onload = function (event) { var image = new Image(); image.src = event.target.result; image.width = 100; جعلی اندازه سند.body.appendChild(تصویر) ؛ }; reader.readAsDataURL(file); }
ما FileReader ر
ا می سازیم و
فایلی برای خواندن به آن میدهیم. در مثال بالا ، من readAsDataURL استفا
ده می شود ، اما
شما همچنین می توانید فایل ها را در متن ساده و فرمت های دودویی (به عنوان در هر مشخصات) بخوانید.
هنگامی که خواننده فایل را خوانده است و داده ها در دسترس است، آن را آتش رویدا
د با
رگذاری، که به نوبه خود ایجاد تصویر جدید ما است.
نتیجه فایل خوانده شده عمل در event.
target.result ن
می باشد. در مورد readAsDa
taURL، مقد
ار در امتداد خطوط داده ها است
:image/png;base64,ABC...
.
با استفاده از تمام ابزار در میش #
این مثال ممکن است برای مقاله ای که می خواستم بنویسم کمی تدبیر شود. من از فناوری های مختلف زیادی برای انجام کاری استفاده کرده ام که یک الگوی نسبتا رایج در وب است. در واقع به این دلیل بود که در پیدا کردن یک منبع قطعی در آپلود در سرور واقعی دچار مشکل شدم (البته به جز اینکه این مقاله را نوشتم این مثال را از پشت در اواخر سال 2010 پیدا کردم!).
امیدوارم، شما خواهید دید که چگونه هر بیت از فن آوری می تواند با هم کار می کنند برای ایجاد یک برنامه، اما به همان اندازه من امیدوارم که شما می توانید ببینید که در آن این کار اگر هیچ کدام و یا فقط برخی از فن آوری در دسترس نیست. اطمینان حاصل کنید که شما تشخیص عملکرد. مطمئن شوید که شما ارائه fallbacks. مطمئن شوید که مسئولانه توسعه پیدا می کنید.
در اینجا آخرین کشیدن و رها کردن و آپلود نسخه ی نمایشی برای شما به بازی با.