Assets (Активы)
В Android имеется ещё один каталог, в котором могут храниться файлы, предназначенные для включения в пакет — assets. Этот каталог находится на том же уровне, что и res. Для файлов, располагающихся в assets, в R.java не генерируются идентификаторы ресурсов. Для их считывания необходимо указать путь к файлу. Путь к файлу является относительным и начинается с /assets. Этот каталог, в отличие от подкаталога res, позволяет задавать произвольную глубину подкаталогов и произвольные имена файлов и подкаталогов.
По умолчанию проект в студии не содержит данную папку. Чтобы её создать, выберите меню File | New | Folder | Assets Folder.
Чтение файлов
Для доступа к файлам используется класс AssetManager. Пример для чтения текстового файла.
Сначала на Kotlin.
button.setOnClickListener < val sampleText: String = applicationContext.assets .open("sample.txt") .bufferedReader().use < it.readText() >println(sampleText) >
String getStringFromAssetFile(Activity activity)
String text = filename; byte[] buffer = null; InputStream is; try < is = getAssets().open(text); int size = is.available(); buffer = new byte[size]; is.read(buffer); is.close(); >catch (IOException e) < e.printStackTrace(); >String str_data = new String(buffer); return str_data;
Для доступа к графическому файлу из актива можно использовать следующий код:
public void loadImageFromAsset() < try < // получаем входной поток InputStream ims = getAssets().open("cat.jpg"); // загружаем как Drawable Drawable d = Drawable.createFromStream(ims, null); // выводим картинку в ImageView mImage.setImageDrawable(d); >catch(IOException ex) < return; >>
Вы также можете загрузить изображение в Bitmap, используя BitmapFactory.decodeStream(), вместо Drawable.
Функция-расширение для Kotlin, которая вернёт Bitmap.
fun Context.assetsBitmap(path: String): Bitmap? < val inputStream: InputStream var bitmap: Bitmap? = null try < inputStream = assets.open(path) bitmap = BitmapFactory.decodeStream(inputStream) >catch (e: IOException) < // Handle exception here >return bitmap >
Используем собственные шрифты
Напишем практический пример создания приложения, в котором будут использоваться собственные шрифты, не входящие в стандартную библиотеку шрифтов Android. Для этого мы упакуем нужные шрифты вместе с приложением. Поместим в каталог assets/fonts файлы шрифтов (можно скачать бесплатные шрифты с сайтов 1001 Free Fonts или Urban Fonts ).
В файл разметки добавим пару текстовых полей с заготовленным текстом для вывода этого текста с нашим шрифтом.
В классе активности загрузим объект EditText из ресурсов, а затем создадим объект Typeface, используя вызов статического метода Typeface.createFromAsset(). Метод createFromAsset() принимает два параметра:
- объект AssetManager, который можно получить вызовом метода getAssets()
- путь к файлу актива.
Например, загрузить шрифт для текстового поля EditText можно следующим способом:
@Override public void onCreate(Bundle savedInstanceState) < super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); final EditText firstEditText = (EditText)findViewById(R.id.editText1); firstEditText.setTypeface(Typeface.createFromAsset( getAssets(), "fonts/DigitalDream.ttf")); final EditText secondEditText = (TextView)findViewById(R.id.editText2); secondEditText.setTypeface(Typeface.createFromAsset(getAssets(), "fonts/Catwalk.ttf")); >
Запустив проект, мы увидим в текстовых полях надписи Happy New Year! и Meow!, выводимые нашими собственными шрифтами.
Пример для фрагмента.
@Override public void onAttach(Activity activity) < super.onAttach(activity); // Какой-то шрифт courgette = Typeface.createFromAsset(getActivity().getAssets(), "Courgette-Regular.ttf"); >
Загрузка локальных файлов из активов в WebView
Если нужно загрузить локальные страницы и изображения из активов в WebView, то можно использовать префикс file://android_asset. Подробнее смотрите в статье про WebView.
myBrowser = (WebView)findViewById(R.id.mybrowser); myBrowser.loadUrl("file:///android_asset/mypage.html");
Получаем список файлов в папке assets
Можно получить список файлов, которые находятся в папке assets. Для быстрой проверки кода я вручную скопировал в папку два файла:
AssetManager myAssetManager = getApplicationContext().getAssets(); try < String[] Files = myAssetManager.list(""); // массив имён файлов Toast.makeText(getApplicationContext(), Files[0] + ", " + Files[1], Toast.LENGTH_LONG).show(); >catch (IOException e)
Кроме ваших файлов, также возвращаются странные папки /images, /sounds, /webkit. Учитывайте это в своих проектах. Так как в папке можно создавать собственные подпапки, то можно воспользоваться вспомогательным методом:
void displayFiles(AssetManager mgr, String path) < try < String list[] = mgr.list(path); if (list != null) for (int i = 0; i < list.length; ++i) < Log.v("Assets:", path + "/" + list[i]); displayFiles(mgr, path + "/" + list[i]); >> catch (IOException e) < Log.v("List error:", "can't list" + path); >> // вызываем метод public void onClick(View view) < final AssetManager mgr = getAssets(); displayFiles(mgr, ""); // содержимое папки /assets, включая странные папки displayFiles(mgr, "cats"); // содержимое подпапки /assets/cats >
Ограничение на размер файлов
По сети гуляет информация, что существует ограничение в 1 Мб на размер файлов в папке assets. При превышении размера у вас может появиться ошибка:
Data exceeds UNCOMPRESS_DATA_MAX
Я не сталкивался, поэтому рецепт решения проблемы не предлагаю.
Файлы js и css, а также прочие asset’ы – тонкости и нюансы работы с ними в Альто
Я не знаю, как коротко и однозначно перевести с английского слово «assets». Но те, кто работают со всякого рода фреймворками или занимаются версткой, как правило, сталкиваются с этим термином. Он обычно (в данном контексте) означает наборы файлов, которые используются на HTML-странице – это файлы стилей (css), скрипты (javascript), различные изображения и шрифты. Нередко термином assets называют только наборы css- и js-файлов.
Разумеется, эти «наборы» активно и в Альто используются. И в этой статье я расскажу о некоторых особенностях их обработки, которые присущи именно нашему движку. И это чрезвычайно будет полезно знать и тем, кто занимается версткой, и тем, кто будет писать плагины под движок, да и вообще всем, кто делает или собирается делать сайты на Alto CMS и хотел бы больше знать, как они устроены изнутри.
Общий подход при работе с css- и js-файлами
Основной подход – все css- и js-файлы собираются в папке /_run/assets/, там они (если это задано в настройках сайта), объединяются, и уже оттуда они подключаются в HTML-код.
При объединении файлов может использоваться сжатие (минификация) – удаление лишних пробелов, переводов строк, комментариев и т.д.
Например, задано подключение файлов:
$config['head']['default']['css'] = array( '___path.frontend.dir___/bootstrap-3/css/bootstrap.css', '___path.skin.dir___/assets/css/default.css', '___path.skin.dir___/themes/___view.theme___/style.css', );
- /common/templates/frontend/ bootstrap-3/css/bootstrap.css
- /common/templates/skin/ start-kit/ assets/css/default.css
- /common/templates/skin/ start-kit/ themes/red/style.css
Т.е. в общем случае принцип такой: css-, js- и прочие включаемые в HTML-код файлы не дергаются из сотни разных мест движка (шаблоны, плагины, библиотеки и т.д.), а должны быть аккуратно сложены в одну папочку /_run/assets/ и подключаться оттуда.
Важный нюанс: если у подключаемого файла указан не путь на диске, а веб-URL, то этот файл будет подключен в HTML-код без всякой обработки. Например, эти файлы будут подключены как есть:
$config['head']['default']['css'] = array( '___path.frontend.url___/bootstrap-3/css/bootstrap.css', // указан URL к библиотеке фронтенда '___path.skin.url___/assets/css/default.css', // указан URL к папке шаблона 'http://cdn.google.com/style.css', // указан внешний URL );
Объединение и сжатие
В настройках сайта задать опции для объединения и сжатия файлов. Это можно сделать либо в админке (Настройки сайта / CSS и javascript), либо добавив в конфиг-файл /app/config/config.local.php
$config['compress']['css']['merge'] = true; // css-файлы будут объединяться $config['compress']['css']['use'] = false; // если задано объединение, то они будут и сжиматься $config['compress']['js']['merge'] = true; // js-файлы будут объединяться $config['compress']['js']['use'] = false;// если задано объединение, то они будут и сжиматься
Надо отметить, что сжатие js иногда приводит к появлению ошибок при исполнении js-кода, поэтому пользоваться этой опцией надо осторожно.
При подключении файлов могут задаваться и дополнительные опции.
$config['head']['default']['js'] = array( // файл обрабатывается с опциями по умолчанию '___path.frontend.dir___/libs/vendor/prettify/prettify.js', '___path.frontend.dir___/libs/vendor/jquery-1.10.2.min.js' => array( 'name' => 'jquery', // указываем имя во избежании двойного подключения 'asset' => 'mini', // указывает на один набор при слиянии файлов ), '___path.frontend.dir___/libs/vendor/swfobject/plugin/swfupload.js' => array( 'name' => 'swfobject/plugin/swfupload.js', 'prepare' => true, // файл только копируется в папку /_run/asset/, но не подключается ), '___path.frontend.dir___/libs/vendor/swfupload/swfupload.swf' => array( 'name' => 'swfupload/swfupload.swf', // можно указывать файлы любых типов 'prepare' => true, // в HTML-не подключаем, просто копируем для дальнейшего использования 'merge' => false, // объединять не надо, даже если такая опция задана в конфиге ), );
Параметр name, как сказано, используется во избежании двойного подключения. Если встречается несколько файлов пусть и с разными путями, но с одинаковым значением name, то подключен будет только первый из них. Но если у повторного файла с тем же параметром name указать еще и параметр ‘replace’ => true, то он заменит в наборе предыдущий файл с таким именем.
$config['head']['default']['js'] = array( 'https://code.jquery.com/jquery-1.11.1.min.js' => array( 'name' => 'jquery', // указываем имя 'replace' => true, // если уже есть файл с name=jquery, то он будет замещен этим ), );
И у этого параметра (name) есть еще одно назначение — можно по нему получить URL к нужному файлу из javascipt’а на странице. Например:
$.ajax(< url: ls.getAssetUrl('swfobject/plugin/swfupload.js'), dataType: 'script' >);
Здесь функция ls.getAssetUrl() вернет полный URL к загружаемому скрипту. Обратите внимание — в качестве аргумента используется не имя файла, и именно значение параметра name, как это было задано в коде выше.
Разработка и отладка
При разработке сайта (плагина, шаблона) есть необходимость сделать так, чтобы js- и/или css-файлы обновлялись при каждой загрузке страницы. Это задается в админке опцией принудительного обновления css- и js- (Настройки сайта / CSS и javascript) или указать это в конфиг-файле /app/config/config.local.php:
$config['compress']['css']['force'] = true; $config['compress']['js']['force'] = true;
Есть и другой способ: в процессе разработки использовать URL (а не дисковый путь) к подключаемым файлам. Тогда они будут вставляться в HTML-код прямо с того места, где находятся, без всякой обработки. А когда разработка будет завершена, то вместо URL следует указать уже дисковый путь.
Похожие статьи
В продолжении к статье Файлы js и css, а также прочие asset’ы – тонкости и нюансы работы с ними в Альто хочу рассказать о некоторых дополнительных возможностях по работе с css- и js-файлами, которые будут полезны .
Здравствуйте, вопрос в следующем Рисую шаблон, а конкретно — CSS-ки Убрал : $config[‘compress’][‘css’][‘merge’] = false; $config[‘compress’][‘js’][‘merge’] = false;.
Всем привет, уже более полу года слежу за развитием altocms, даже есть собственный проект на ней. На мой взгляд, это самая оптимальная cms для создания блоговой платформы.
Долгое время с предубеждением относился к движку instantcms. Уже не помню в чем были причины, но это уже и не важно. А важно то, что LS и Alto загнулись окончательно, а instantcms живет и здравствует. Думаю могу дать .
25 комментариев
Применительно к вебдеву это обычно называется ресурсами.
Кстати, если я изменю какой-либо файл, изменится ли путь к asset-у, в котором он состоит? Если да, то можно заставить браузер всегда брать файлы по этому пути из кэша — это сэкономит десятки запросов при каждом переходе по страницам:
ExpiresActive On ExpiresDefault "access plus 3 months" Header set Cache-Control "max-age=7257600"
Отредактирован: Только что
Кстати, если я изменю какой-либо файл, изменится ли путь к asset-у, в котором он состоит?
Имя результирующего asset-файла строится на основе хеша имен файлов, которые входят в набор. Т.е. если изменится имя подключаемого файла, то изменится и имя asset’а. А если изменилось только содержимое, то ничего не меняется. Для этого и нужны опции принудительного обновления.
Отредактирован: Только что
хеш от имени файлов + размеров + времени последнего обновления? или по скорости невыгодно, много раз ФС дергается?
Отредактирован: Только что
Была такая мысль. Но тормознулся именно из-за большого числа дерганий. Тут, наверное, лучше по другому пути пойти — если уж и дергать ФС, то сравнивать даты исходных файлов и результирующих и так определять, изменилось ли содержимое набора. Но при этом обязательно предусмотреть опцию, которая будет отключать это сравнение (Смарти примерно так работает с компилированными шаблонами).
Тогда можно будет, с одной стороны, получить автообновление с опциами по умолчанию, а с другой — отключить лишние проверки на рабочем проекте, когда известно, что ничего не меняется
Отредактирован: Только что
Добавить просто к собранным ассетам хэши от исходного содержимого и Большую Красную Кнопку «очистить кэш», которая также будет автоматически нажиматься при включении/выключении плагинов. От инвалидации кэша на лету вы потеряете весь выигрыш в производительности.
Отредактирован: Только что
и Большую Красную Кнопку «очистить кэш», которая также будет автоматически нажиматься при включении/выключении плагинов
А вот обе эти фичи есть уже сегодня
Отредактирован: Только что
Когда кэш включен, ФС вы дергать не сможете ни под каким видом — браузер будет брать уже собранные файлы. А когда он только собирается, торопиться особо некуда, и возможные проблемы от оптимизаций не стоят ускорения.
Отредактирован: Только что
Еще возможное улучшение — заранее архивировать asset-ы в gzip, чтобы это не приходилось каждый раз делать веб-серверу.
Отредактирован: Только что
Кстати, да, интересный совет. А на сервере для этого какие-то допнастройки нужны?
Отредактирован: Только что
Да, понадобится что-то типа такого в .htaccess:
Header set Content-Encoding gzip
Сделал архив с простым примером. У меня на хостинге он, правда, не завелся — для распаковки gzip браузерам (по крайней мере, chrome) требуется правильный Content-Length, а там фронтэндом стоит nginx, который его не указывает 🙁 Так что по умолчанию эту оптимизацию включать нельзя.
Отредактирован: Только что
Я вам предлагаю узнать всю инфу по gzip и сделать предложение aVadim -у, каким образом это можно внедрить в Альто.
Отредактирован: Только что
У меня, прямо скажу, в очереди доработок для Alto конкретно эта даже не в первой десятке, т.к. лично мне она не особо нужна — у меня сейчас вообще нет своих сайтов, а разгрузка gzip нужна только для высоконагруженных проектов. Да и в систему asset-ов я еще толком не вникал, не мне ее улучшать. Почему бы этим не заняться вам? 🙂
Отредактирован: Только что
Ну я просто слышал про gzip, что это типа круто и быстро — но еще никогда с этим не работал. А тут речь зашла за это — поэтому и предложил. Если честно, мне пока с miniMarket-ом работы хватает 🙂
В чем отличие public и assets?
Что такое (public, assets) и что в нем хранить? Зачем нам это?
Отслеживать
задан 19 мая в 7:00
59 4 4 бронзовых знака
сейчас объясню)
19 мая в 7:31
2 ответа 2
Сортировка: Сброс на вариант по умолчанию
public — папка в которой лежат публично доступные файлы разого назначения например index.html, hello.html и.т.д. как правило это и есть корень сайта /
assets — папка в которой лежат ассеты сайта (картинки, скрипты, стили, шрифты) и которая может быть легко переписана компилятором webpack и им подобным без потери важных данных.
storage — папка куда пользователи могут например залить видеофайл или автарку но которая так или иначе учавствует в процессе работы сайта. Как правило управляеться backend скриптами.
static — папка куда разработчик кладёт ассеты сайта (картинки, скрипты, стили, шрифты). Но которая управляеться именно разработчиком, а не создаёться автоматический при компиляции webpack’ом.
А вообще такое разделение нужно не только что-бы было удобно пользоваться посткомпиляцией, но ещё активно учавствует в правильной настройке кеширования сайта.
Какие файлы должны быть в папке assets?
Подскажите, что из этих папок должно лежать в assets и почему?
- Вопрос задан более трёх лет назад
- 3456 просмотров
4 комментария
Простой 4 комментария
А почему что-то вообще должно быть в папке assets? Если только речь не идет о каком-то особым образом заранее настроенном сервере, который ни в вопросе, ни в тегах не упоминается.
myskypesla @myskypesla Автор вопроса
Moskus, Сборка идёт с помощью gulp или webpack, но структуру делаю я сам. Стараюсь использовать на новых проектах best practies и во многих проектах видел что где-то лежали картинки, шрифты, видео и файлы, а где-то и js и css, а в другом проекте папка assets при билде переименовывалась в папку static и тянулось всё оттуда.
myskypesla, это совершенно не важно, если вы не занимаетесь дальнейшей оптимизацией, не имеете отдельных настроек сервера или дальнейших шагов сборки (типа выкладывания чего-то на отдельный CDN), основанных на структуре папок, которые относятся к отдаче статики клиенту. Грубо говоря, если вы задаетесь подобным вопросом, то вам возня с этим, вероятнее всего, просто не нужна.
Сергей delphinpro @delphinpro Куратор тега CSS
я предпочитаю на выходе иметь папку design, а в ней скрипты, стили, картинки, шрифты.
Какая нафиг разница, как папку назовете?