Как предварительно загрузить элементы в SproutCore ListView?
У меня есть относительно быстрое приложение SproutCore, которое я пытаюсь сделать немного быстрее.
Прямо сейчас, когда пользователь прокручивает мой SC.ListView и просматривает некоторые элементы списка, которые не были загружены с сервера (скажем, из отношений), приложение автоматически обращается к серверу для загрузки этих записей. Несмотря на то, что это быстро, все еще остается короткий период времени, когда мои элементы списка пустые.
Я знаю, что могу заставить их сказать "Загрузка..." или что-то в этом роде (и у меня есть), но мне было интересно: есть ли способ предварительно загрузить мои "закадровые" записи, чтобы как пользователь свитки, элементы списка уже загружены?
Мои ListItemViews будут довольно большими (по пикселям), поэтому даже загрузка в два раза большего объема данных не будет убийственной с точки зрения AJAX, и было бы неплохо, если бы пользователь прокручивал контент всегда, если он не загружался. прокрутка SUPER-SUPER-быстрая, в этом случае я в порядке с ними, видя индикатор загрузки).
В настоящее время я нашел решение, добавив следующее в свой SC.ListView, но я заметил некоторые серьезные проблемы с производительностью на мобильных устройствах, и они напрямую связаны с внесением этого изменения, поэтому мне было интересно, есть ли лучший способ.
contentIndexesInRect: function(rect) {
rect.height = rect.height * 2;
return sc_super();
}
2 ответа
Переопределение contentIndexesInRect - способ, которым я сделал бы это. Я бы сделал меньше, чем в два раза - я мог бы получить результат от sc_super() и затем добавить несколько дополнительных элементов в результирующий набор индексов. (Я полагаю, что он вернется замороженным, поэтому вам, возможно, придется клонировать-отредактировать-заморозить.) Один или два дополнительных могут дать вам достаточно места для загрузки материала, не внося почти такой же заметной проблемы в производительность.
Я удивлен, что это приводит к серьезным проблемам с производительностью, хотя. Мне кажется, что сами ваши элементы списка могут быть более тяжелыми, чем они должны быть - например, они могут иметь много привязок, чтобы зацепить и отцепить. Если это то, что происходит, вы можете получить больше пользы от повышения их эффективности.
Я думаю, вам лучше будет загрузить дополнительные данные вне контекста того, что на самом деле отображает список. Например, принудительное рендеринг большего количества элементов списка для запуска дополнительных запросов приводит к тому, что дополнительные данные становятся доступными, но также добавляет несколько ненужных элементов в DOM, что в действительности отрицательно сказывается на общей производительности. Фактически, эти дополнительные элементы, скорее всего, являются причиной серьезного замедления работы мобильных устройств, когда вы получаете достаточное количество дополнительных функций.
Вместо этого я бы сначала удостоверился, что ваши представления элементов списка правильно объединяются, так что только видимые элементы обновляются на месте с минимальными манипуляциями с DOM. Затем, во-вторых, я бы лениво загружал дополнительные данные только после запроса необходимых данных. Есть довольно много способов сделать это в зависимости от ваших настроек. Возможно, вы захотите добавить некоторую логику в источник данных, чтобы инициировать дополнительный запрос для каждого заполненного диапазона запросов, или вы можете захотеть сделать что-то вроде переопределения itemViewForContentIndex
в SC.CollectionView
как точка для запуска дополнительных данных. В любом случае, я думаю, что это может выглядеть примерно так,
// …
prefetchTriggered: function (lastIndex) {
// A query that will fetch more data (this depends totally on your setup).
var query = SC.Query.remote(MyApp.Record, {
// Parameters to pass to the data source so it knows what to request.
lastIndex: lastIndex
});
// Run the query.
MyApp.store.find(query);
},
// …
Как я уже упоминал в комментариях выше, структура запроса полностью зависит от ваших настроек и вашего API, поэтому вам придется изменить его в соответствии с вашими потребностями. Это будет работать лучше, если вы сможете запрашивать подходящий ассортимент товаров, а не по одному.