cancel
Showing results for 
Search instead for 
Did you mean: 

How to Count the Rows of a GUI Label Object

former_member709020
Participant
0 Kudos

Hi,

I was wondering if anyone has any experience working with the GUI Label Object.  I'm able to navigate through it's rows by referring to the labels like this:

lblWBS = session.findById("wnd[1]/usr/lbl[1," & i & "]").Text

where i is a variable in a For Next loop.  In the example code above where i = 1, lblWBS would render "WBS Element"; when i = 3 lblWBS renders "121476.01.01.01.013533A, etc.  The narrow space between 1 and 3 is actually a label too so I assume it would be label 2.  You can see the example below. I also attached the .png file just in case you can't read the image I inserted.

I need to be able to count the rows in this collection of lablel objects, or probably more accurately, count the labels in one colum.  I'm able to do this easily in a ALV grid but not in the GUI Label Object container.  Does anyone out there have any knowledge on this?

Accepted Solutions (1)

Accepted Solutions (1)

thomas_brutigam2
Active Participant
0 Kudos

So where is your problem ?

in the Caption of the  Dialog is allready announced how much Records were found-

so you can easily do it like this:


a = Split(session.findbyid("wnd[1].text"), " ")

    For i = 0 To UBound(a)

        If IsNumeric(a(i)) Then

            zählebis = CInt(a(i))

            Exit For

        End If

    Next i
    

For i = 3 to zählebis+3

    lblWbs = session.findbyid("wnd[1]/usr/lbl[1,"&i&"]").Text

next i

former_member709020
Participant
0 Kudos

Brilliant!

I guess my problem was that I didn't even think of using the number in the Dialog caption.   I like the way you used the array to detect the numeric characters. I would have looped through all characters until I found the numeric ones; but I like your way better.

To get your code to work I had to Dim the array first in line 01, relocate a quotation mark in line 03 and add spaces around the ampersands and variable in line 11.


Dim a() As String
   
a = Split(session.findbyid("wnd[1]").Text, " ")

For i = 0 To UBound(a)
    If IsNumeric(a(i)) Then
        zählebis = CInt(a(i))
        Exit For
    End If
Next i

For i = 3 To zählebis
    lblWBS = session.findbyid("wnd[1]/usr/lbl[1," & i & "]").Text
Next i

thomas_brutigam2
Active Participant
0 Kudos

Gary Michalske wrote:

Brilliant!

I guess my problem was that I didn't even think of using the number in the Dialog caption.   I like the way you used the array to detect the numeric characters. I would have looped through all characters until I found the numeric ones; but I like your way better

.

Sometimes life can be so easy 😉


To get your code to work I had to Dim the array first in line 01, relocate a quotation mark in line 03 and add spaces around the ampersands and variable in line 11.

  1. Dim a() As String 
  2.      
  3. a = Split(session.findbyid("wnd[1]").Text, " ") 
  4. For i = 0 To UBound(a) 
  5.     If IsNumeric(a(i)) Then 
  6.         zählebis = CInt(a(i)) 
  7.         Exit For 
  8.     End If 
  9. Next i 
  10. For i = 3 To zählebis 
  11.     lblWBS = session.findbyid("wnd[1]/usr/lbl[1," & i & "]").Text 
  12. Next i 

for sure - I wrote without any SAP (just out of my head)

gretings Thomas

former_member709020
Participant
0 Kudos

10-4.  Gottcha.

One other thing to note that will help others trying to do this is that the number in the Caption text is the count of the actual values (I know becuase I actually took the time to count them in SAP) and doesn't include the header row (1) and the space below it (2).  Because of this I had to remove the "+3" in line 9 in your code.

Nonetheless...thanks a lot Thomas!

former_member709020
Participant
0 Kudos

Thomas,

I was wondering if its possible to use a For Each loop to read all of the labels instead of trying to count them.  The labels do seem to be part of a collection but I can't seem to get it to work.  Here is what I see in the SAP Scripting Help file:

Do you have any idea on how to construct a For Each Loop with the above information?

former_member213011
Participant
0 Kudos

The solution to get the number of row is brilliantly simple.

However, I don't think the lblWBS for-loop will work until the last row. I suspect that halfway through the loop, the script will throw the cannot find by id error.

If my suspicion is wrong, do tell.

former_member709020
Participant
0 Kudos

Yes, you're correct.  I was eperimenting with it yesterday and found that if you use code to scroll down to make the next intended row visible the loop considers the the first visible row at the top as row 1 again.  So if your loop was on i = 10 and you scrolled down so row 11 was now the at the top of the form window, the loop would read the the 11th row in the current window.

former_member213011
Participant
0 Kudos

Thanks for confirming.

This is how I approached the problem in Excel VBA. Tested on transaction CR05 because it has similar screen layout except without the caption with the number of rows.


Sub testGuiLabel()

    Dim sapgui As SAPFEWSELib.GuiApplication

    Dim sapcon As SAPFEWSELib.GuiConnection

    Dim sapsession As SAPFEWSELib.GuiSession

    Dim sapusr As SAPFEWSELib.GuiUserArea

   

    Dim totscrol As Long

    Dim childcount As Long

    Dim visrow As Long

    Dim lastchildID As String

    Dim i As Long

   

   

    Set sapgui = GetObject("sapgui").GetScriptingEngine

    Set sapcon = sapgui.Children(0)

    Set sapsession = sapcon.Children(0)

   

    With sapsession

        Set sapusr = .FindById("wnd[0]/usr")

        sapusr.VerticalScrollbar.Position = 0

        childcount = sapusr.Children.Count

        lastchildID = sapusr.Children(childcount - 1).ID

        visrow = CLng(Right(Left(lastchildID, Len(lastchildID) - 1), _

            Len(lastchildID) - InStr(1, lastchildID, ",") - 1))

       

        Sheet1.Range("A1").Activate

        For i = 3 To visrow

            ActiveCell = .FindById("wnd[0]/usr/lbl[1," & i & "]").Text

            ActiveCell.Offset(1, 0).Activate

        Next i

        totscrol = sapusr.VerticalScrollbar.Maximum

        If totscrol > 0 Then

            For i = 1 To totscrol - 1

                sapusr.VerticalScrollbar.Position = i

                ActiveCell = .FindById("wnd[0]/usr/lbl[1," & visrow & "]").Text

                ActiveCell.Offset(1, 0).Activate

            Next i

        End If

    End With

End Sub

former_member709020
Participant
0 Kudos

Sayuti,

Your solution is brilliant!  I'll actually have to do the same for some other lbl scenarios as they too do not have the total count in the caption.  So in essence, what you did was:

  1. determined the last visible lbl row in the intitial view by extracting the last two digits from the .ID property using the Right() formula
  2. then you looped through all of those to extract their values
  3. Then you determined the maximum row count using the .Maximum property
  4. then you starting looping through the remaining rows but setting the scroll position to i as the loop progressed so you were always reading the last row in the view.

How did you ever learn about the .ID  and .Maximum properties?

former_member213011
Participant
0 Kudos

Thanks Gary.

Learned it from SAP Scripting API Help File.

I noticed that the behavior of the GuiUserArea with table constructed from GuiLabel objects is similar to GuiTableControl where VerticalScroll property effects the ID (for row) property. Hence, I use the same approach.

BTW, you've described the algorithm I used correctly. For point no 1, I had to use Left() function as well to get rid of the "]" character.

The limitation of using the algorithm is that there should not be any other objects other than the GuiLabel table on the screen.

Thanks,

Sayuti

former_member709020
Participant
0 Kudos

Sayuti Azmi wrote:

Thanks Gary.

Learned it from SAP Scripting API Help File.

I noticed that the behavior of the GuiUserArea with table constructed from GuiLabel objects is similar to GuiTableControl where VerticalScroll property effects the ID (for row) property. Hence, I use the same approach.

BTW, you've described the algorithm I used correctly. For point no 1, I had to use Left() function as well to get rid of the "]" character.

The limitation of using the algorithm is that there should not be any other objects other than the GuiLabel table on the screen.

Thanks,

Sayuti

I'm not sure if I understand you comment regarding the limitation.  When I tested your code I directed it to win[1] because the main GUI window, win[0] was also present.  What am I mssing?

former_member213011
Participant
0 Kudos

Getting the number of rows from ID works on the assumption that the last Children of the GuiUserArea is the last GuiLabel of the table. However, if the GuiUserArea has other object after the last GuiLabel i.e. the last GuiLabel is not the last Children, then the code will not work.

BTW, did it work for you?

former_member709020
Participant
0 Kudos

Yes, it worked like a charm.  I guess what you're saying is that if I had win[2] open and I was applying the code to win[1], then the code would fail, correct?  Here's the final code:


With session

    Set sapusr = .FindById("wnd[1]/usr")

    sapusr.VerticalScrollbar.Position = 0

    childcount = sapusr.Children.Count

    lastchildID = sapusr.Children(childcount - 1).ID

    visrow = CLng(Right(Left(lastchildID, Len(lastchildID) - 1), _

        Len(lastchildID) - InStr(1, lastchildID, ",") - 1))

    Sheets("Sheet1").Range("A1").Activate

    For i = 3 To visrow

        ActiveCell = .FindById("wnd[1]/usr/lbl[1," & i & "]").Text

        ActiveCell.Offset(1, 0).Activate

    Next i

    totscrol = sapusr.VerticalScrollbar.Maximum

    If totscrol > 0 Then

        For i = 1 To totscrol - 1

            sapusr.VerticalScrollbar.Position = i

            ActiveCell = .FindById("wnd[1]/usr/lbl[1," & visrow & "]").Text

            ActiveCell.Offset(1, 0).Activate

        Next i

    End If

End With

former_member213011
Participant
0 Kudos

No. What I meant was, let say, there's a short label or text underneath the table to summarize the number of rows. In other words, the last Children of the GuiUserArea is not "usr/lbl[(column no), (last row number)]".

I can't think of a situation where this occur, but it might occur.

Answers (1)

Answers (1)

0 Kudos

I found a solution to get the hight and with of a label container.

Dim sapWin, tCols as long, tRows as long
set sapWin = session.FindbyId("wnd[1])
tColumns = sapWin.WorkingPaneWidth
tRows = sapWin.WorkingPaneHeight
Former Member

I saw your posted answer. I'd recommend replying to newer questions or asking a new question as this question is now a few years old and the original question poster may not reply. Feel free to take our Q&A tutorial at: https://developers.sap.com/tutorials/community-qa.html. With these tips you'll be able to prepare questions that draw responses from our members. Thanks!

Best,

Your SAP Community moderator