Ostatnio bawię się WebGL i uruchomiłem czytnik Collada. Problem jest dość powolny (Collada to bardzo szczegółowy format), więc zacznę konwertować pliki do łatwiejszego w użyciu formatu (prawdopodobnie JSON). Mam już kod do parsowania pliku w JavaScript, więc równie dobrze mogę go użyć jako mojego eksportera! Problem polega na oszczędzaniu.
Teraz wiem, że mogę przeanalizować plik, wysłać wynik na serwer i poprosić przeglądarkę o przesłanie pliku z powrotem do serwera w celu pobrania. Ale w rzeczywistości serwer nie ma nic wspólnego z tym konkretnym procesem, więc po co się w to angażować? Mam już zawartość żądanego pliku w pamięci. Czy jest jakiś sposób, aby przedstawić użytkownikowi plik do pobrania przy użyciu czystego JavaScript? (Wątpię, ale równie dobrze mogę zapytać ...)
Żeby było jasne: nie próbuję uzyskać dostępu do systemu plików bez wiedzy użytkowników! Użytkownik dostarczy plik (prawdopodobnie metodą przeciągnij i upuść), skrypt przekształci plik w pamięci, a użytkownik zostanie poproszony o pobranie wyniku. Wszystko to powinno być „bezpiecznymi” działaniami, jeśli chodzi o przeglądarkę.
[EDYCJA]: Nie wspomniałem o tym z góry, więc plakaty, które odpowiedziały na „Flash” są wystarczająco ważne, ale częścią tego, co robię, jest próba podkreślenia, co można zrobić za pomocą czystego HTML5 ... więc Flash jest wprost w moim przypadku. (Chociaż jest to całkowicie poprawna odpowiedź dla każdego, kto robi „prawdziwą” aplikację internetową). W takim przypadku wygląda na to, że nie mam szczęścia, chyba że chcę zaangażować serwer. W każdym razie dzięki!
źródło
Odpowiedzi:
OK, tworzenie danych: URI zdecydowanie mi pomaga, dzięki Matthew i Dennksterowi wskazując tę opcję! Oto w zasadzie jak to robię:
1) przekształć całą treść w ciąg o nazwie „content” (np. Najpierw ją tam tworząc lub czytając innerHTML tagu już zbudowanej strony).
2) Zbuduj identyfikator URI danych:
Będą ograniczenia długości w zależności od typu przeglądarki itp., Ale np. Firefox 3.6.12 działa do co najmniej 256 KB. Zamiast tego kodowanie w Base64 przy użyciu encodeURIComponent może sprawić, że wszystko będzie bardziej wydajne, ale dla mnie to było w porządku.
3) otwórz nowe okno i „przekieruj” do tego identyfikatora URI monituje o lokalizację pobierania mojej strony wygenerowanej w JavaScript:
Otóż to.
źródło
location.href
zawartość.location.href = uriContent
.location.href = "data:application/octet-stream," + encodeURIComponent(jQuery('#answer-4551467 .post-text').first().text());
, aby zapisać treść odpowiedzi @ Nøk w pliku. Nie mam IE, żeby to przetestować, ale działa dla webkita.Proste rozwiązanie dla przeglądarek obsługujących HTML5 ...
Stosowanie
źródło
HTML5 zdefiniował
window.saveAs(blob, filename)
metodę. Obecnie nie jest obsługiwany przez żadną przeglądarkę. Ale istnieje biblioteka kompatybilności o nazwie FileSaver.js, która dodaje tę funkcję do większości współczesnych przeglądarek (w tym Internet Explorer 10+). Internet Explorer 10 obsługujenavigator.msSaveBlob(blob, filename)
metodę ( MSDN ), która jest używana w FileSaver.js do obsługi Internet Explorera.Napisałem post na blogu z dalszymi szczegółami na temat tego problemu.
źródło
Zapisywanie dużych plików
Długie identyfikatory URI mogą powodować problemy z wydajnością w przeglądarkach. Inną opcją zapisywania plików generowanych po stronie klienta jest umieszczenie ich zawartości w obiekcie Blob (lub pliku) i utworzenie łącza pobierania za pomocą
URL.createObjectURL(blob)
. Zwraca adres URL, którego można użyć do pobrania zawartości obiektu blob. Obiekt blob jest przechowywany w przeglądarce, dopóki nieURL.revokeObjectURL()
zostanie wywołany w adresie URL lub dokument, który go utworzył, zostanie zamknięty. Większość przeglądarek internetowych obsługuje adresy URL obiektów , Opera Mini jest jedyną, która ich nie obsługuje.Wymuszanie pobierania
Jeśli dane to tekst lub obraz, przeglądarka może otworzyć plik zamiast zapisywać go na dysku. Aby spowodować pobranie pliku po kliknięciu łącza, możesz użyć
download
atrybutu. Jednak nie wszystkie przeglądarki internetowe obsługują atrybut pobierania . Inną opcją jest użycieapplication/octet-stream
jako typu MIME pliku, ale powoduje to, że plik jest przedstawiany jako binarny obiekt blob, co jest szczególnie nieprzyjazne dla użytkownika, jeśli nie podasz nazwy pliku lub nie możesz jej podać. Zobacz także „ Wymuś otwarcie okna„ Zapisz jako ... ”otwieranie przy kliknięciu linku tekstowego dla pdf w HTML ”.Określanie nazwy pliku
Jeśli obiekt blob został utworzony za pomocą konstruktora plików, można również ustawić nazwę pliku, ale tylko kilka przeglądarek internetowych (w tym Chrome i Firefox) obsługuje konstruktor plików . Nazwę pliku można również podać jako argument
download
atrybutu, ale wymaga to wielu względów bezpieczeństwa . Internet Explorer 10 i 11 udostępnia własną metodę msSaveBlob , która określa nazwę pliku.Przykładowy kod
źródło
msSaveBlob
otworzyć okno dialogowe „Zapisz jako”. W przypadku innych przeglądarek jedyną opcją jest ręczne wybranie opcji „Zapisz jako” z menu kontekstowego łącza pobierania.document.getElementById('link').href = url;
twój kod może iść dalej i odpalić link używając metody elementu.click()
.źródło
a.click
kod za pomocą,document.createEvent()
jak sugerował Matěj Pokorný, działa na FF, ale nie na IE. Nie próbowałem Chrome.Aby to zrobić, spójrz na Downloadify Douga Neinera, który jest interfejsem JavaScript opartym na technologii Flash.
źródło
HTML 5
sztandarem i odpowiednio otaguj? Prawdopodobnie przyciągnęłoby to tych użytkowników, którzy wiedzą o tym konkretnym polu (jak sądzę, wciąż jest to stosunkowo niewielki tłum). Jestem prawie pewien, że można to zrobić w HTML 5, ale nie mam pojęcia, jak to zrobić.Proste rozwiązanie!
Działa we wszystkich nowoczesnych przeglądarkach.
źródło
window.open()
. To nie ma znaczenia. Możesz użyć tej metody i wymusić.click()
na niej, ale uważaj na czas, ponieważ Firefox nie lubi tego, jeśli zadzwonisz,.click()
zanim pozwoli elementowi dołączyć się do ciała.Możesz wygenerować identyfikator URI danych . Istnieją jednak ograniczenia specyficzne dla przeglądarki.
źródło
"data:text/plain;charset=UTF-8,"+encodeURIComponent(text)
ale tak, IE ogranicza rozmiar adresów URL danych do nieużytecznej ilości i nie obsługuje ich dla rzeczy takich jakwindow.open(...)
iframe (myślę).Użyłem FileSaver ( https://github.com/eligrey/FileSaver.js ) i działa dobrze.
Na przykład wykonałem tę funkcję, aby wyeksportować dzienniki wyświetlane na stronie.
Musisz podać tablicę dla instancji Blob, więc może po prostu nie napisałem tego we właściwy sposób, ale to działa dla mnie.
Na wszelki wypadek zachowaj ostrożność przy zamianie: jest to składnia umożliwiająca uczynienie tego globalnym, w przeciwnym razie zastąpi on tylko pierwszego, którego spotka.
źródło
w.close();
poexecCommand
Znalazłem dwa proste podejścia, które działają dla mnie. Po pierwsze, użycie już klikniętego
a
elementu i wstrzyknięcie pobranych danych. Po drugie, generowaniea
elementu z pobranymi danymi, wykonywaniea.click()
i usuwanie go ponownie. Ale drugie podejście działa tylko wtedy, gdy wywoływane jest również przez akcję kliknięcia użytkownika. (Niektóre) Blok przeglądarkiclick()
z innych kontekstów, takich jak ładowanie lub uruchamiany po upływie limitu czasu (setTimeout).źródło
a
dokument do dokumentu (ewentualnie za pomocą"display:none"
), kliknąć go, a następnie usunąć.Oto link do metody URI danych Mathew zasugerował, że działał na safari, ale nie dobrze, ponieważ nie mogłem ustawić rodzaju pliku, jest zapisywany jako „nieznany”, a następnie muszę tam wrócić później i zmienić go w kolejności aby wyświetlić plik ...
http://www.nihilogic.dk/labs/canvas2image/
źródło
Możesz użyć localStorage. Jest to odpowiednik plików cookie HTML5. Wygląda na to, że działa w Chrome i Firefox ALE w Firefoksie, musiałem przesłać go na serwer. Oznacza to, że testowanie bezpośrednio na moim komputerze domowym nie działało.
Pracuję nad przykładami HTML5. Przejdź do http://faculty.purchase.edu/jeanine.meyer/html5/html5explain.html i przewiń do labiryntu. Informacje do przebudowania labiryntu są przechowywane za pomocą localStorage.
Przyszedłem do tego artykułu, szukając kodu JavaScript HTML5 do ładowania i pracy z plikami xml. Czy to to samo, co starszy HTML i JavaScript?
źródło
próbować
Jeśli chcesz pobrać dane binarne, spójrz tutaj
Aktualizacja
2020.06.14 Aktualizuję Chrome do wersji 83.0 i nowszej SO zatrzymanie fragmentu kodu SO (ze względu na ograniczenia bezpieczeństwa piaskownicy ) - ale działa wersja JSFiddle - tutaj
źródło
Jak wspomniano wcześniej, interfejs API File wraz z interfejsami FileWriter i FileSystem API może służyć do przechowywania plików na komputerze klienta w kontekście karty / okna przeglądarki.
Jest jednak kilka rzeczy związanych z dwoma ostatnimi interfejsami API, o których powinieneś wiedzieć:
Oto proste przykłady wykorzystania interfejsów API, bezpośrednio i pośrednio, w tym celu:
BakedGoods *
Korzystanie z nieprzetworzonych interfejsów API File, FileWriter i FileSystem
Chociaż interfejsy API FileSystem i FileWriter nie są już na ścieżce standardów, ich użycie może być uzasadnione w niektórych przypadkach, moim zdaniem, ponieważ:
Jednak to, czy „niektóre przypadki” obejmują twoje, należy do ciebie.
* BakedGoods jest utrzymywany przez nikogo innego niż ten facet tutaj :)
źródło
Wątek ten był nieoceniony, aby dowiedzieć się, jak wygenerować plik binarny i poprosić o pobranie nazwanego pliku, wszystko w kodzie klienta bez serwera.
Pierwszym krokiem było wygenerowanie binarnego obiektu blob z danych, które zapisywałem. Istnieje wiele próbek do zrobienia tego dla pojedynczego typu binarnego, w moim przypadku mam format binarny z wieloma typami, które można przekazać jako tablicę do utworzenia obiektu blob.
Następnym krokiem jest skłonienie przeglądarki do monitowania użytkownika o pobranie tego obiektu blob o wstępnie zdefiniowanej nazwie.
Wszystko, czego potrzebowałem, to nazwany link, który dodałem w HTML5, którego mógłbym użyć ponownie, aby zmienić nazwę początkowej nazwy pliku. Ukryłem go, ponieważ link nie wymaga wyświetlania.
Ostatnim krokiem jest zachęcenie użytkownika do pobrania pliku.
źródło
Oto samouczek dotyczący eksportowania plików jako ZIP:
Zanim zaczniesz, istnieje biblioteka do zapisywania plików, nazwa biblioteki to fileSaver.js, możesz znaleźć tę bibliotekę tutaj. Zacznijmy teraz, dołącz wymagane biblioteki:
Teraz skopiuj ten kod, a ten kod pobierze plik zip z plikiem hello.txt o treści Hello World. Jeśli wszystko działa poprawnie, plik zostanie pobrany.
Spowoduje to pobranie pliku o nazwie file.zip. Możesz przeczytać więcej tutaj: http://www.wapgee.com/story/248/guide-to-create-zip-files-using-javascript-by-using-jszip-library
źródło