B4A Library [Class] ScrollPanel

Hello,

This class displays a small panel beside the vertical scrollbar in a scrollview. You can display what you want in its label and drag it to quickly scroll.

My first intention was to add this feature to the FastScroll class of Stevel05, but I quickly realized that I needed to modify several functions in FastScroll and InputSlider. It was faster to reinvent the wheel and it's easier to maintain.

It needs two libraries: Animation and Reflection.

Tutorials: How they do #2, How they do #3

v1.1:
Warning: the FastScroll parameter in Initialize() has been replaced by UseCache. The FastScroll feature did not work very well and I prefered to drop it.
I added a cache to speed GetTopMostView. The speed gain is huge with heavy loaded ScrollViews. Don't forget to call RefreshCache every time you modify the ScrollView content. You can set UseCache to false if your ScrollView contains less than 100 items. More info here.
I fixed the bug with containers. Now you can put your ScrollView in a TabHost.
I fixed a bug in DisplayTextLine.
I added two events (onShowHide and onTextUpdated).
I added ScrollPanelMovedByUser. It returns True when the user drags the ScrollPanel.

v1.2:
A few bugs fixed. See post #6 for details.
Function "Remove" added.

v1.3:
Two bugs fixed. See post #7 for details.

v1.4:
Removed the Parent parameter in Initialize (useless)
New function: LoadDrawable(Name As String) As Object
ReplaceBackground now accepts drawables
It waits now until the user really scrolls (solves the overscrolling issue).

Fred
 

Attachments

  • img1.jpg
    img1.jpg
    48.3 KB · Views: 2,145
  • img2.jpg
    img2.jpg
    52.2 KB · Views: 1,771
  • img3.jpg
    img3.jpg
    56 KB · Views: 1,520
  • ScrollPanel v1.4.zip
    25.8 KB · Views: 979
  • ScrollPanel v1.4 for ScrollView2D.zip
    4.1 KB · Views: 854
Last edited:

Informatix

Expert
Licensed User
Longtime User
New version (v1.1):
Warning: the FastScroll parameter in Initialize() has been replaced by UseCache. The FastScroll feature did not work very well and I prefered to drop it.
I added a cache to speed GetTopMostView. The speed gain is huge with heavy loaded ScrollViews. Don't forget to call RefreshCache every time you modify the ScrollView content. You can set UseCache to false if your ScrollView contains less than 100 items.
I fixed the bug with containers. Now you can put your ScrollView in a TabHost.
I fixed a bug in DisplayTextLine.
I added two events (onShowHide and onTextUpdated).
I added ScrollPanelMovedByUser. It returns True when the user drags the ScrollPanel.

Fred
 

Informatix

Expert
Licensed User
Longtime User
To make things clear about the cache:

When do I need it ?

When your ScrollView has plenty of views (the number depends on your device, but consider 100 to be a good number on any device) and you want to use the function GetTopMostView. This function is called internally by these public functions:
- DisplayFirstChar
- DisplayTag
- DisplayTextLine

When do I have to refresh it ?

Every time you add/remove views inside the ScrollView or change the top property or z-order (with BringToFront or SendToBack) of one of them.

How does it work ?

It uses a very simple, but powerful, dichotomic search in a sorted list. It's the same algorithm that you use when you play at "Guess my number". ;-)
 

Informatix

Expert
Licensed User
Longtime User
New version (1.2):
A few bugs fixed:
- the cache was not cleared in RefreshCache;
- cache with only one view failed to return the view;
- the Display functions didn't check if PnlDisplay is initialized;
- the panel was displayed even when the ScrollView can't scroll.

I added the function "Remove" to remove the ScrollPanel. Once removed, you must call Initialize to bind it again to the ScrollView.
 

Informatix

Expert
Licensed User
Longtime User
New version (1.3):
Two bugs fixed:
- GetTopMostView crashed if no view was found (now, it returns the ScrollView if it is empty)
- A few particular cases were not properly handled by the iterated search (e.g. very big items with lot of space between them).

Three versions in a day ! :signOops:
 

lagore

Active Member
Licensed User
Longtime User
fantastic class, one question can it be modified to work with scrollview2d, this class combined with Erel's tableview class would be super.

Sent from my HTC Desire using Tapatalk 2
 

Mahares

Expert
Licensed User
Longtime User
Yes, very easily. You have to replace every ScrollView by ScrollView2D and every sv.ScrollPosition by sv.VerticalScrollPosition. That's all.

I tried to combine Erel's TABLE class sample with Informatix SCROLLPANEL class using the SCROLLVIEW2D library, but could not get the scrollpanel to appear. I got rid of any code errors, but the project is not running properly. Something is wrong with my coding. Please see attached project in its entirety. The SCROLLPANEL is a great feature and can be super if it can work with TABLE class.
Thank you very much for your assistance.
 

Attachments

  • TableScrollAndPanelScroll2D.zip
    23.7 KB · Views: 441

Informatix

Expert
Licensed User
Longtime User
There are strange things in your code, e.g. you copied the lines that I use to create content for my ScrollPanel demo. Why? It's totally useless here.

The Table class initializes the ScrollView inside the class, so you must call the ScrollPanel from the class, not from your activity.
 

Mahares

Expert
Licensed User
Longtime User
Not versed in CLASS, I was not about to tamper with the class modules code in the sample. I did not realize it was that complicated. Although the SCROLLPANEL appears to be a very good feature to have, it is something that can wait until I get up to speed with classes.
Thank you.
 

Informatix

Expert
Licensed User
Longtime User
Not versed in CLASS, I was not about to tamper with the class modules code in the sample. I did not realize it was that complicated. Although the SCROLLPANEL appears to be a very good feature to have, it is something that can wait until I get up to speed with classes.
Thank you.

It's not complicated:
Add MyScrollPanel.Initialize in the Table class and MyScrollPanel.DisplayTextLine(PosY) in the ScrollChanged event. That couldn't be simpler. But your comment is wise: take your time to fully understand what you're doing.
 

Informatix

Expert
Licensed User
Longtime User
Here is the table class with a scrollpanel.
I just added two lines in the Table class as previously said (Initialize in AddToActivity and DisplayTextLine in ScrollChanged).
We can't use the cache with a table class because the scrollview does not contain all rows. But that's not really needed (for the same reason).
As you can see in this example, the table class can take some time to refresh its display when you do a quick scroll. This is not a ScrollPanel issue.
 

Attachments

  • TableExWithScrollPnl.zip
    19.6 KB · Views: 402

Informatix

Expert
Licensed User
Longtime User
New version (v1.4):
Removed the Parent parameter in Initialize (useless)
New function: LoadDrawable(Name As String) As Object
ReplaceBackground now accepts drawables
It waits now until the user really scrolls (solves the overscrolling issue).

Starting tomorrow, I will publish tutorials to show how to use my classes and my libraries to replicate the UI of some applications made by professionals. That will show you some advanced techniques. For copyright reasons, that will be only text and screenshots. ;-)
 

AscySoft

Active Member
Licensed User
Longtime User
I've tried your code, with less success
Every time guest os force close the main activity, "we are sorry..."
I've tried to run it on 1 real device, and 3 emulators. It hangs everywhere
Animation lib 1.02 and Reflector 2.20 are installed
This is the log

B4X:
** Activity (main) Create, isFirst = true **
** Activity (main) Resume **
java.lang.NullPointerException
   at anywheresoftware.b4a.agraham.reflection.Reflection$7.onTouch(Reflection.java:1100)
   at android.view.View.dispatchTouchEvent(View.java:3881)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:903)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:869)
   at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.java:1750)
   at com.android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1135)
   at android.app.Activity.dispatchTouchEvent(Activity.java:2096)
   at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.java:1734)
   at android.view.ViewRoot.deliverPointerEvent(ViewRoot.java:2216)
   at android.view.ViewRoot.handleMessage(ViewRoot.java:1887)
   at android.os.Handler.dispatchMessage(Handler.java:99)
   at android.os.Looper.loop(Looper.java:130)
   at android.app.ActivityThread.main(ActivityThread.java:3687)
   at java.lang.reflect.Method.invokeNative(Native Method)
   at java.lang.reflect.Method.invoke(Method.java:507)
   at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:867)
   at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:625)
   at dalvik.system.NativeStart.main(Native Method)
 

Informatix

Expert
Licensed User
Longtime User
I've tried your code, with less success
Every time guest os force close the main activity, "we are sorry..."
I've tried to run it on 1 real device, and 3 emulators. It hangs everywhere
Animation lib 1.02 and Reflector 2.20 are installed
This is the log

What's your B4A version ? 2.02 ?

I tested my class so many times and with so many configurations in emulator that I'm sure there's a problem with your configuration. The question is Where ?

Unselect the libraries in the Libs tab, then select them again. Does this change anything ? Are the version numbers right ?
 
Top