CachingStrategy="RecycleElement", ListView Performance Android

16 posts, 0 answers
  1. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 07 Feb Link to this post

    About a little over a year ago, there was a property introduced on the Xamarin Forms ListView called CachingStrategy, which can be set to RecycleElement. Is this built in to the RADListView? I have numerous items (60+) on 4 lists with embedded images (160x160) thumbnails in my app. When I test this on the device with decent memory, I am getting very poor performance (painting slow or not at all with the images). Here is a link to information about this property setting. I tried to set it on the RADListView but got no property found. I am using the grid layout format for the ListView.

     

    Some performance tips are here, including use of CachingStrategy...

    https://blog.xamarin.com/optimizing-xamarin-forms-apps-for-maximum-performance/

     

    I am also using:

    [assembly: XamlCompilation(XamlCompilationOptions.Compile)]

    I trimmed down the images as best I could.

    Image List 1 total size, 61 files 900KB, bit depth 8 - 160x160

    Image List 2 total size, 37 files 804KB, bit depth 8 160x160

    Image List 3 total size, 22 files 344KB (this is the only one that is snappy, I am guessing because it has the fewest elements), bit depth 24, 160x160

    Image List 4 total size, 62 files 704KB, bit depth 8, 160x160

     

    I also have Java Heap space set to the max 1G in the Android settings, and testing with release mode.

     

    Also, I have to set the HeightRequest on the RADListView to something really high, like 1500 to get these images to appear on the list on first appearing.

    Here is my XAML:

     

             <telerikDataControls:RadListView HeightRequest="1500" x:Name="RADlistView"<br>                                           BackgroundColor="White"  <br>            SelectedItem="{Binding objSelectedTumor, Mode=TwoWay}" ><br>            <telerikDataControls:RadListView.ItemTemplate><br>              <DataTemplate><br>                <telerikListView:ListViewTemplateCell><br>                  <telerikListView:ListViewTemplateCell.View><br>                    <Grid Padding="10" RowSpacing="5" HorizontalOptions="Center" VerticalOptions="Center"><br>                      <Grid.RowDefinitions><br>                        <RowDefinition Height="6*" /><br>                        <RowDefinition Height="*" /><br>                      </Grid.RowDefinitions><br>                      <Grid.ColumnDefinitions><br>                        <ColumnDefinition Width="*" /><br><br>                      </Grid.ColumnDefinitions><br>                      <!--these options cause System.NullReferenceException: Object reference not set to an instance of an object in iOS. <br>                                      HorizontalOptions="Center"<br>                                      VerticalOptions="Center"--><br>                      <controls:CircleImage Grid.Row="0"<br>                                            Source="{Binding thumb_file_image_name} Converter={StaticResource ImageConverter}"<br>                                            Aspect="AspectFit"<br>                                            IsVisible="{StaticResource showSectionAndroidWin}"<br>                                  <br>                  ><br>                        <controls:CircleImage.WidthRequest><br>                          <OnPlatform x:TypeArguments="x:Double"<br>                            iOS="55"<br>                            Android="55"<br>                            WinPhone="75"<br>                      /><br>                        </controls:CircleImage.WidthRequest><br>                        <controls:CircleImage.HeightRequest><br>                          <OnPlatform x:TypeArguments="x:Double"<br>                            iOS="55"<br>                            Android="55"<br>                            WinPhone="75"<br>                      /><br>                        </controls:CircleImage.HeightRequest><br>                      </controls:CircleImage><br>                      <Image Grid.Row="0"<br>                                            Source="{Binding thumb_file_image_name} Converter={StaticResource ImageConverter}"<br>                                            Aspect="AspectFit"<br>                                            IsVisible="{StaticResource showSectioniOS}"<br>                  ><br>                        <Image.WidthRequest><br>                          <OnPlatform x:TypeArguments="x:Double"<br>                            iOS="55"<br>                            Android="55"<br>                            WinPhone="75"<br>                      /><br>                        </Image.WidthRequest><br>                        <Image.HeightRequest><br>                          <OnPlatform x:TypeArguments="x:Double"<br>                            iOS="55"<br>                            Android="55"<br>                            WinPhone="75"<br>                      /><br>                        </Image.HeightRequest><br>                      </Image><br><br>                      <Grid Grid.Row="1"<br>                           Grid.Column="0"<br>                           RowSpacing="1"<br>                           VerticalOptions="Start"<br>                           HorizontalOptions="Center"<br>                  ><br>                        <Grid.RowDefinitions><br>                          <RowDefinition Height="*" /><br>                        </Grid.RowDefinitions><br>                        <Grid.ColumnDefinitions><br>                          <ColumnDefinition Width="*" /><br>                        </Grid.ColumnDefinitions><br>                        <Label Grid.Row="0"<br>                               Grid.Column="0"<br>                               LineBreakMode="NoWrap"<br>                               BackgroundColor="Transparent"<br>                               HorizontalTextAlignment="Center"<br>                               VerticalTextAlignment="Center"<br>                               Text="{Binding name}"<br>                               TextColor="#81AABC"><br>                          <Label.FontSize><br>                            <OnPlatform x:TypeArguments="x:Double"><br>                              <OnPlatform.WinPhone><br>                                <OnIdiom x:TypeArguments="x:Double"><br>                                  <OnIdiom.Phone>14</OnIdiom.Phone><br>                                </OnIdiom><br>                              </OnPlatform.WinPhone><br>                              <OnPlatform.Android><br>                                <OnIdiom Phone="10"<br>                                         Tablet="12"<br>                                         x:TypeArguments="x:Double" /><br>                              </OnPlatform.Android><br>                              <OnPlatform.iOS><br>                                <OnIdiom Phone="10"<br>                                         Tablet="12"<br>                                         x:TypeArguments="x:Double" /><br>                              </OnPlatform.iOS><br>                            </OnPlatform><br>                          </Label.FontSize><br>                        </Label><br>                      </Grid><br>                    </Grid><br>                  </telerikListView:ListViewTemplateCell.View><br>                </telerikListView:ListViewTemplateCell><br>              </DataTemplate><br>            </telerikDataControls:RadListView.ItemTemplate><br>            <telerikDataControls:RadListView.LayoutDefinition><br>              <telerikListView:ListViewGridLayout x:Name="gridLayout" <br>                                                  VerticalItemSpacing="5" <br>                                                  HorizontalItemSpacing="5" <br>                                                  SpanCount="5" <br>                                                  ItemLength="180" /><br>            </telerikDataControls:RadListView.LayoutDefinition><br>          </telerikDataControls:RadListView>

    Any other ideas here?

     

     

     

  2. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 07 Feb in reply to Russ Link to this post

    This XAML formatting did not show too well, here is plain text:
     
              <telerikDataControls:RadListView HeightRequest="1500" x:Name="RADlistView"
                                               BackgroundColor="White" 
                SelectedItem="{Binding objSelectedTumor, Mode=TwoWay}" >
                <telerikDataControls:RadListView.ItemTemplate>
                  <DataTemplate>
                    <telerikListView:ListViewTemplateCell>
                      <telerikListView:ListViewTemplateCell.View>
                        <Grid Padding="10" RowSpacing="5" HorizontalOptions="Center" VerticalOptions="Center">
                          <Grid.RowDefinitions>
                            <RowDefinition Height="6*" />
                            <RowDefinition Height="*" />
                          </Grid.RowDefinitions>
                          <Grid.ColumnDefinitions>
                            <ColumnDefinition Width="*" />

                          </Grid.ColumnDefinitions>
                          <!--these options cause System.NullReferenceException: Object reference not set to an instance of an object in iOS.
                                          HorizontalOptions="Center"
                                          VerticalOptions="Center"-->
                          <controls:CircleImage Grid.Row="0"
                                                Source="{Binding thumb_file_image_name} Converter={StaticResource ImageConverter}"
                                                Aspect="AspectFit"
                                                IsVisible="{StaticResource showSectionAndroidWin}"
                                     
                      >
                            <controls:CircleImage.WidthRequest>
                              <OnPlatform x:TypeArguments="x:Double"
                                iOS="55"
                                Android="55"
                                WinPhone="75"
                          />
                            </controls:CircleImage.WidthRequest>
                            <controls:CircleImage.HeightRequest>
                              <OnPlatform x:TypeArguments="x:Double"
                                iOS="55"
                                Android="55"
                                WinPhone="75"
                          />
                            </controls:CircleImage.HeightRequest>
                          </controls:CircleImage>
                          <Image Grid.Row="0"
                                                Source="{Binding thumb_file_image_name} Converter={StaticResource ImageConverter}"
                                                Aspect="AspectFit"
                                                IsVisible="{StaticResource showSectioniOS}"
                      >
                            <Image.WidthRequest>
                              <OnPlatform x:TypeArguments="x:Double"
                                iOS="55"
                                Android="55"
                                WinPhone="75"
                          />
                            </Image.WidthRequest>
                            <Image.HeightRequest>
                              <OnPlatform x:TypeArguments="x:Double"
                                iOS="55"
                                Android="55"
                                WinPhone="75"
                          />
                            </Image.HeightRequest>
                          </Image>

                          <Grid Grid.Row="1"
                               Grid.Column="0"
                               RowSpacing="1"
                               VerticalOptions="Start"
                               HorizontalOptions="Center"
                      >
                            <Grid.RowDefinitions>
                              <RowDefinition Height="*" />
                            </Grid.RowDefinitions>
                            <Grid.ColumnDefinitions>
                              <ColumnDefinition Width="*" />
                            </Grid.ColumnDefinitions>
                            <Label Grid.Row="0"
                                   Grid.Column="0"
                                   LineBreakMode="NoWrap"
                                   BackgroundColor="Transparent"
                                   HorizontalTextAlignment="Center"
                                   VerticalTextAlignment="Center"
                                   Text="{Binding name}"
                                   TextColor="#81AABC">
                              <Label.FontSize>
                                <OnPlatform x:TypeArguments="x:Double">
                                  <OnPlatform.WinPhone>
                                    <OnIdiom x:TypeArguments="x:Double">
                                      <OnIdiom.Phone>14</OnIdiom.Phone>
                                    </OnIdiom>
                                  </OnPlatform.WinPhone>
                                  <OnPlatform.Android>
                                    <OnIdiom Phone="10"
                                             Tablet="12"
                                             x:TypeArguments="x:Double" />
                                  </OnPlatform.Android>
                                  <OnPlatform.iOS>
                                    <OnIdiom Phone="10"
                                             Tablet="12"
                                             x:TypeArguments="x:Double" />
                                  </OnPlatform.iOS>
                                </OnPlatform>
                              </Label.FontSize>
                            </Label>
                          </Grid>
                        </Grid>
                      </telerikListView:ListViewTemplateCell.View>
                    </telerikListView:ListViewTemplateCell>
                  </DataTemplate>
                </telerikDataControls:RadListView.ItemTemplate>
                <telerikDataControls:RadListView.LayoutDefinition>
                  <telerikListView:ListViewGridLayout x:Name="gridLayout"
                                                      VerticalItemSpacing="5"
                                                      HorizontalItemSpacing="5"
                                                      SpanCount="5"
                                                      ItemLength="180" />
                </telerikDataControls:RadListView.LayoutDefinition>
              </telerikDataControls:RadListView>
  3. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 09 Feb in reply to Russ Link to this post

    Is there a sample custom renderer for RADListView for iOS, Android and UWP? Maybe I am thinking we can get at the CachingStrategy="RecycleElement" natively there?
  4. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 13 Feb Link to this post

    Hi Russ,

    Thank you for contacting us.

    Indeed the performance with CircleImage is very poor on Android and UWP. I noticed that the same author provides another package - Xam.Plugins.Forms.CachedImageCircle. I replaced the CircleImage with CircleCachedImage and this greatly improved the list view performance on Android. On UWP it also works great, but for some reason, the image is not a circle but square.

    In UWP we have not yet provided an entry point where you can plug your own logic for performance optimization in the native control. I have logged a feature request in our feedback portal. We will try to expose suitable API in the next internal build.

    Please, let us know if the CircleCachedImage works for you or if you have any other questions.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
  5. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 13 Feb in reply to Rosy Topchiyska Link to this post

    Thanks Rosy, I could not find the documentation on CircleCachedImage, can you send me your sample? I can not figure out how to do the init on UWP. The website is down at: https://github.com/fferegrino/CachedImageCirclePlugin ... Short of that is there anything else you can think of? I am really up against a wall here on performance and crashing. 
  6. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 14 Feb in reply to Russ Link to this post

    Btw, I removed the circle image control all together, and we still have some serious performance problems on Android with the RADListView, we need to brainstorm here.
  7. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 14 Feb Link to this post

    Hello Russ,

    I actually found the NuGet package for CachedImageCircle, but indeed the git repository does not exist anymore. Here is the package: https://www.nuget.org/packages/Xam.Plugins.Forms.CachedImageCircle/
    You can check the attached example, it seems to work great on Android.

    On UWP I also couldn't find the init method, but it looks like both CircleCachedImage and CircleImage work without init (except for CircleCachedImage is not circle). At this moment the best option seems to be keeping the circle image for android and using a regular image for UWP.

    I have logged a feature request in our feedback portal about improving the performance of the list view with regular images where you can track its status. This issue is critical but it will take some time to provide a solution.

    Please let us know if this works for you.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items

  8. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 14 Feb Link to this post

    Thanks, I will try that. But, ,my main concern at this point is the Performance of the Android ListView as is, with images, regular image control. Any updates here? or are you saying that the cached image is the solution?
  9. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 14 Feb Link to this post

    Thanks so much for the sample. The cached circle images indeed make it snappier. But try to deploy to an actual Android Tablet device and not in the emulator. It is still kind of chunky and not a smooth scroll. The huge issue is that I am experiencing 10-20 second load times on an actual device for the page with the RADListView depending if release or debug in your sample. I even reduced it to 100 items in the list from the 1000 you had it is still several seconds to load. I also bumped up the heap space allotment to the max of 1G as well in the Android settings, still no difference. I modified the sample and added a navigation page root with the RADListView on the navigated page to help eliminate app load time as the delay. Navigate back and forth a few times and the app crashes.  Now we have something to replicate the performance and stability problems I have been experiencing. I only have one more day to program this and the customer needs to show off the app at a tradeshow. Anything you can come up with here would be greatly appreciated. Here is the modified app to test with and let me know if you can replicate (we have been able to replicate on a variety of Android tablet devices): https://1drv.ms/u/s!AqgyEBnYTgiooYBS7e7JeDGDqKqy5w 
  10. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 15 Feb Link to this post

    Hello Russ,

    I played a bit with the FFImageLoading library and I managed to get some improvement on Android. I followed the example described here. Please, take a look at the attached sample.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
  11. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 16 Feb Link to this post

    Thanks Rosy, this is a very cool control and one that will help immensely, I also saw same other great tips on the site for Android specific tweaks like .... "For apps that use a lot of images, to have a all of them in memory you should use android:largeHeap="true" in AndroidManifest.xml. " https://github.com/luberda-molinet/FFImageLoading/wiki/Advanced-Usage#custom-logger and a few others.

    https://github.com/luberda-molinet/FFImageLoading/wiki/Advanced-Usage#custom-logger

     

    I am not seeing the crash now. which is good. I am still seeing about a 6 second load time from the main page to the RADListView page. Any ideas here?

  12. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 21 Feb Link to this post

    Hi Russ,

    The workaround that I can suggest right now is to use incremental loading to decrease the size of the initially loaded items. Please, take a look at the attached project and let us know if this works for you.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
  13. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 23 Feb in reply to Rosy Topchiyska Link to this post

    I gave this a shot Rosy. Your example has good performance. However, I have implemented it in my app and I am still seeing 12 second load time for the list page. The only difference I can see is that I am using actual files in the Android project instead of linked image files. Also, my images are .png instead of .jpg, and they are not generated as they are actual files on the disc and each one is a different image, not repeated. My Lists range from 30-60 items and even the 30 item list takes long to load. scratching my head now, because your demo performs well. Not sure what is going on. Any other ideas? Here is one set of images for one list of 61 files. LMK when you download these so I can remove the link. https://1drv.ms/u/s!AqgyEBnYTgiooYYMDDfjmfNr_w-kng
  14. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 28 Feb Link to this post

    Hi Russ,

    I tested the scenario with your images and I see only 1-2 seconds delay. I have attached the modified project. To run it, just add your images to the android Resources/drawable folder. Please, check the project and modify it if there are any differences between your implementation and mine.

    I look forward to your reply.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
  15. Russ
    Russ avatar
    19 posts
    Member since:
    Jan 2017

    Posted 28 Feb in reply to Rosy Topchiyska Link to this post

    Thanks! I will check this today. Is this for deployment to an actual device?
  16. Rosy Topchiyska
    Admin
    Rosy Topchiyska avatar
    586 posts

    Posted 02 Mar Link to this post

    Hi Russ,

    Yes, I tested the app on a real device.

    Regards,
    Rosy Topchiyska
    Telerik by Progress
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
Back to Top