The volt view never releases memory - voltrb

A beginner volt question here :-).
I’ve created a simple volt app which pulls random images from the file system - a slide show. The image data is retrieved in a server task (in addition to the file path, I want dimensions orientation etc, so I use a ruby library) and then its passed back to the main controller. So I have a method (get_random_pic) in the controller which sets the img path etc on the page for a img tag to use in the view:
<img width="{{page._image_data[3]}}}}" src="{{page._image_data[0]}}">image</img>
(An aside: I am using an array in an effort for the value binding "signals" to arrive at the same time - otherwise the image width updates at a different time to the image path - however its still not synchronous with an array)
Then I use setTimeout in the controller to call the get_random_pic method again (via a button).
setTimeout(function(){ document.getElementById("myButton").click(); }, 5000);
This works perfectly however memory usage never stops growing (e.g. after 20min it will 2GB). I assume this is because each time the image is being loaded in the view, the previous image is orphaned and the GC can’t run. Actually I don’t know enough about JS to come to any intelligent reasons as to why, nor an elegant work around. Maybe I could load up the image in a controller instance method and the img tag references directly the binary (rather than pull via file path from file system), and on each iteration I could set it to nil, but I’m hoping there is nicer solution, before I try that.

Related

Preload (all) image assets in a Flutter app

I would like an easy approach to preload/cache all of my static image assets so that they can be rendered/served without a delay.
I've seen that there is a precacheImage() call that can be used to pre-load/cache the AssetImage. This needs a context and it is recommended to call this in the didChangeDependencies() override.
Shouldn't there be a way to make this easier and more general? My app uses a total of 1.5 MB of image data (and I've included 2.0x and 3.0x upscaled versions in that number). PNG images that are 50 KB (and no upscaled versions) takes a noticeable amount of time to display, maybe 300-600ms on both emulator and fast devices. These are local assets, not fetched over the network. I find that irritating and I'm frustrated that there isn't a better way to handle this?
I've also seen the tip to use FadeInImage but again - it's not really what I'm looking for.
I'm displaying the image in a stateless widget (a custom button). It's not possible to use precacheImage in a stateless widget afaik. So I'd need to build the Image.asset() in my parent widget, call precacheImage and then pass the image widget to my stateless widget and render it in build - this is cumbersome.
Furthermore, the images will be displayed in different places (different parent widgets). Sometimes the image widgets differ in size between widgets and since size is parameters to Image.asset() I guess I would need to precache each unique size and pass these precached image widgets around. Isn't it possible to tell Flutter to "cache" the data of the PNG so that when the Image.asset is requested it reads the PNG from cache - without having to pass around precached image widgets?
I would like a "precacheAllImageAssets()call or callprecacheImage()` with a string so that each Image.asset() that references that same asset would be cached.
I guess that Flutter internally caches the image widget (including it's size and other properties) as some internal render object that is cached. Thus pre-caching two different sizes of the same image would require two different caches. With that being said - I'd still want a precacheAllImageAssets() call that could at least read the PNG data into memory and just serve it quicker even if would need to do some processing to get the PNG data to an actual widget with a size before it could be rendered. With such a cache I could maybe get a render delay of < 50 ms instead of the current 300-600 ms.
Any idea if this is possible? If not possible - am I missing something obvious or could this be a (likely) future improvement of the Flutter framework?
Here is my similar precacheAllImageAssets(), but you need to list all image path by yourself.
final List _allAsset = [
///tabbar
'images/tabbar/tabar_personal.png',
'images/tabbar/tabar_personal_slt.png',
'images/tabbar/tabar_home.png',
'images/tabbar/tabar_home_slt.png',
'images/...'
'images/...'
}
void main() {
final binding = WidgetsFlutterBinding.ensureInitialized();
binding.addPostFrameCallback((_) async {
BuildContext context = binding.renderViewElement;
if(context != null)
{
for(var asset in _allAsset)
{
precacheImage(AssetImage(asset), context);
}
}
});
}
UPDATE: after some research I've figured out that previous version of my answer was not correct. Here is relevant one (you can see old one in edit history).
You do not need to use same ImageProvider for images to precache. So you can run precacheImage() at init time and then create another image with same path and it is gonna be obtained from cache (if it was not cleared one way on another).
Internally precacheImage() uses ImageProvider.obtainKey() which is pair of (imagePath, scale) as a key to store image in in-memory cache. So as long as you are using same key it does not matter which instance of ImageProvider/Image you are using.
For futher insights you can inspect ImageCache documentation. Specifically, take a look at putIfAbsent() method as it's main caching endpoint. To understand how images generate their key (at which they are stored in ImageCache) try to start with ImageProvider class and then look into it's implementations.

SVG loaded via objects all jumbled up

So this is an interesting one. I did a test of using the clown car technique for showing responsive images via svgs loaded via an object tag because I really like the approach.
Now this works all fine, except when you have a few of them on one page with the cache normally activated, you leave the site to go to anywhere else in the interwebs and then press the back button - suddenly all images are mixed up, even though the code is still correct, ie:
object 1 loads svg that shows image from object 3
object 3 loads svg that shows image from object 5
etc.
Totally random and I just can't explain how this can happen. And it only ever happens when I go back to the page via the back command of the browser (chrome).
Has anyone experienced anything like this before??
I guess I'll stick to good old normal images for now...
Just ran into the same bug. And so did Google!
I suppose we'll have to use inline SVGs as loading through <img> tags aren't a possibility for me.
If you only have a single page app, you could add target="_blank" to your <a> tags to ensure the back button will come into play far less.

Why would I need image placeholder service or library?

Yesterday, I saw a tweet saying about holderJS library. When I read the usage, it says it will generate the image placeholder completely on client side. So I am wondering why in the life would I need a placeholder library?
What is the scenario in which rather than placing div of some size I would use image placeholder?
Image placeholders are generally meant for a page that is either in the process of dynamically loading a real image or the page is only partially designed and the placeholder image shows how the design will be laid out and how big the image should be even though the real image is not yet available. In this way, the HTML design can be nearly completed even though the final images are not yet available or done.
Wikipedia uses image placeholders when they know they want a particular image in a page, but are in search of an image they can use with the appropriate license.
Image placeholders are traditionally served up by a service on the web that automatically creates the placeholder images based on query parameters in a URL, but the holder.js library creates placeholder images entirely on the client (so no outside services are needed).
You can certainly achieve the same look as a placeholder with just a div with a background color and perhaps even some text in the div. But, when someone wanted to plug the final images into place, they would have the change the div tags to img tags. When using a placeholder image, all the HTML tags can be final and left as they are, only the .src values need to be plugged in to finish the design. So, placeholder images allow you to have a closer to complete version of the HTML even though the images are not yet done. It's a minor different, but one that is appreciated by some designers.

The basic framework behind a simple web app, what to use where

okay so i have basic skills in html, css, javascript.
im still in the learning phases but just need a little help on where to go in regards to creating a web app.
i can figure out all the code, so thats fine, i just need some pointers as to what to use where.
So basically ill have a webpage with a few simple buttons, when clicked they'll send a message to the server and the server will hold a count for each button clicked using a php script.
1) - would it be best to hold that information in a JSON file?
then from there, there'll be another webpage which will have div tags stretching 100% across the page, with an element inside it which will move across the page according to the count held on the server.
2) - what should i use to animate it moving?. would i use javascript? or css3 or something?
the front end will need to continuously update on the count held by the server.
3) - would AJAX methods be best using javascript?
any advice would be great thanks.
And one last thing.
With Javascript animating, if i wanted to animate a div moving horizontal, is the best way to do it by animating the margin size? or am i stuck in the dark days..
1: i would store it in a database, if you store it in a file make sure that you are handling writes in a safe way(multiple writes to the same file)
2:you could use javascript to animate the css properties of a html element(preferable the width)
3: Ajax would work but then you need to continuously poll the server for changes alternativly use longpoling http://en.wikipedia.org/wiki/Push_technology#Long_polling
an alternative if you only support modern browsers and your hosting company allows it is to use websockets
If you're trying to save information server side (which you seem to be), I would recommend using a database (such as MySQL).
If your animation is dependent on the value from the server, I would use javascript to animate it. Note that you will have to poll the server in order to actually get this information (lets say, every second). When you get the information, simply update the div you want to animate with the new information. I don't quite understand what you want your display to look like, so I can't really give you anything more specific here.
Yes. I would recommend using jQuery to handle your AJAX calls as it makes it much easier and deals with cross-browser weird-ities.
To your update:
One option could definately be to adjust the (left) margin size, but you could also use the relative position. It will basically push the element however many pixels in whatever position from where it would typically be displayed. So if your box is by default right along the left border, you could relatively position it 100px to the right. You can read more about position here.

Flex 3 static bitmap issue

Interesting problem here - I'm making a small game using Flex 3 - now I have a static ImageAccess class, which first loads up all images and stores them in a static array for quicker access in the future.
Now since I address the physical bitmapdata without calling Clone() (for efficiency issues) and once by accident I've written directly onto the bitmapdata.
Now the weird part - Flex uses some kind of weird caching and stores the bitmap with the new changes made to it - no matter what I do (restart Flex Builder, delete my cache, restart browser) the bitmap data is still loaded with the extra info (even though the image is without all that data).
Please help :D
Can you give more details about what extra info you're talking about?
Correct me if I'm wrong but Flex doesn't cache anything as such, the browser does, in any case , viewing with another browser should display the original image. If it doesn't , you may consider the possibility of some forgotten function still acting on the original bitmap... have you tried viewing the application in another browser by the way?
there's also the possibility of the original image being corrupted for whatever reason...

Resources