I have been looking for a while but haven't been able to find an answer. I have a text view in my APK that needs to potentially handle large amounts of text being appended to it a little at a time. So it could grow over time as stuff streams to it. So far I haven't seen any issues and I have let the underlying Android implementation take care of the data. Does anyone know if Android caches these all in memory or that if it passes a watermark level it could then write to file for the TextView? What if it gets too huge, would the APK run out of memory and get killed by Dalvik? If that is the case I am open for any suggestion as how to mitigate this possiblity. One solution in my mind is that have a custom textview that does exactly what I explained and caches data to file if it passes a water mark. However, I am not sure how tricky it would get to detect where the user is navigating within the TextView to pull the data back and forth from the underlying data file and populate the actual TextView object.
Thanks
While I was unable to find the actual threshold, it has been discussed and suggested that extremely long text be displayed in smaller chunks. You can also write to a file which you can then read back in as necessary for your project.
Edit: regarding the TextView bookmark (for lack of a better term), you could always programmatically check to see where the user is in the TextView (checking for a certain character or string at the end of the TextView) and reading the next few lines of text into the TextView. You would have to match the getText().toString() value of the TextView against the readable text in your file.
I'm wondering now too if you would be able to do that in either direction. To save space, you could write your text to file as the user needs it, and update the TextView to only display 5 or 6 lines (arbitrary number). You could trim the TextView in either direction to save memory. You could ellipsize both sides of your text, scroll enable it, and trim/read those points as necessary.
Related
I'm just getting started and trying to make a simple app after going through some of the Google Codelabs. I wrote a Choose your own Adventure type of game. It consists of 500 paragraphs, and at the end of each paragraph is usually a choice of the next action to take (ie paragraph to load) and possibly some game logic. For now I am concentrating on the text only.
It seems simpler to make 500 text files and load up whatever file number is necessary, however it makes more sense to load ALL the paragraphs as the entire text takes up roughly 300Kb as a text file.
How would I even attempt this? I know I would need a text array and I file reader. I think it would be more work to format the paragraphs with a delineator to separate them, as it may be simpler to just create 500 files and write a While loop feeding my array.
That should fulfill my current objective, but when I want to add the choices at the end of the paragraphs, it seems as if a JSON or XML file that includes the text and choices would be better. I could not figure out how to even attempt this.
Example Paragraph: "You hear a horseman galloping and spin towards the sound. Do you have the skill of Forest Stealth? If you do, turn to 95. If you do not, turn to 234."
How to show very large string (let's say 25 MB or more maybe even 50MB) without any paragraphs or spaces in a TextView? There no TextRecyclerView in Android. If you directly try to load into TextView you just get ANR straight away.
If you split in chucks and put it in RecycleView in a different screens and rotation the text will be look different. It should behave as single TextView.
For simplicity our file stored in raw or assets folder and called large_string.txt.
How to solve such problem and show this huge string with scrolling smoothly without any lag?
I know how to setup a listview to have an image and some text on each rows.
I know how to have the user open up a dialogue to pick an image from the file system or live.
I almost know how to downsample it in case its huge. (too many ways, no expert to recommend one).
I really need to know how the user can create db entries (notes) that contain text and an image that is user selected. In essence, the user is entering text and selecting/uploading an image that makes a 'note' and the notes get displayed in a listview.
I don't want the full code, but rather a general direction. I did some research and for me its a big forest. If you can give general directions how thats done, I'll do the rest.
Thank you,
I have an activity that's supposed to display a text file. The text file is 165 kB. Originally, after I read in the text file, I would do something like this,
textView.setText(fileText);
But that took over 10 seconds on my Nexus 4, and I confirmed that this was due to the call to setText() and not reading the file. Then, after searching around a bit, I got the idea to put it in a webview, using WebView.loadData(). This takes less than a second.
I'm curious as to why a WebView is able to load text so much faster than a TextView. Does anyone know?
From what I remember;
The WebView will only render the text that it needs to display at any given time. Meaning that when you first load it will only load 20 - 30 lines of text. Whereas when you call textView.setText(fileText); it causes Android to render all of the text even though it is not displayed. If you are trying to add a lot of text to a TextView then you should use textView.append(fileLine); in a loop which should load quite a bit faster.
I am developing a Handwriting note-taking app.
The app works in this way: the user write(draw) a text on the touchscreen, the app convert the handwriting to a Bitmap(getBitmapFromHandwriting()), then use this bitmap to produce a SpannableString and show it to the user in a TextView(In my case, I use an EditText, but to make things simple, let's say it's TextView).
Here is the code snippet in the extended TextView:
class MyTextView extends TextView{
...
BitmapDrawable bmd = new BitmapDrawable(getBitmapFromHandwriting());
int width = bmd.getIntrinsicWidth();
int height = bmd.getIntrinsicHeight();
bmd.setBounds(
(int)(height/4.0f),
(int)(height/4.0f),
(int)(width + height/4.0f),
(int)(height*5.0f/4.0f));
final ImageSpan img = new ImageSpan(bmd);
getText().setSpan(img, position, position+1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
…
}
In getBitmapFromHandwriting(), the app create a new bitmap for each text drawn by the user.
Everything works fine before the note grows big(means there are lots of bitmaps in the native memory), an OutOfMemoryError is thrown when createBitmap().
After lots of googling, I learned bitmaps use "native memory", which is very limited.
I also learned gc for bitmap doesn't happen at the same time with the gc of the JVM take place. So people would better do bitmap.recycle() when the bitmap is surely not necessary any more.
From the above knowledge, I think I need to recycle the bitmaps for invisible texts , and load that bitmap only when necessary(i.e., visible)
Before recycling a bitmap, I must make sure it won't used in the future, otherwise, will get a "RuntimeException: Canvas: trying to use a recycled bitmap…"
i.e., I have to clear the corresponding spans attached to the SpannableString. (By getText().removeSpan(), or getText().clearSpans(), but that's another story.)
For doing that, I need to tell which strings are visible and which are invisible. In ViewGroups like GridView, I can call "getFirstVisiblePosition()", but I don't know how to do that for a TextView.
I know it's possible to down sample the bitmap to support more bitmaps, but what I want is a TextView supports UNLIMITED ImageSpans.
If it's GridView or ListView, a lazy loading implementation will do the work. But how to do it in a single TextView?
Dividing the content to multiple pages should theoretically work for some situations, but in my app, user can also "export" the note. The exporting simply do a copy of the current view(How to do the export without creating new bitmap is another problem, won't discuss in this thread.). If the note is divided to multiple pages, user have to "export" for each page, so it's not an option.
My questions are:
1. Is it possible to determine the visible strings in TextView?
2. Is there any better way(patterns) to implement such "TextView containing lots of ImageSpans" without getting OutOfMemoryError?
Any idea is appreciated. Thanks in advance!