Placing the Same QImage Multiple Times in a Loop - c++

I am trying to build some sort of media player. Currently, the basic functions of the media player work and there is a video progress bar that show where in the video they are and how long. This progress bar is a slider and what I want to do is place tick marks on this progress bar (like bookmarks but for videos) based on user input. I have this working as a QList. However, when I save the user input into a text file containing the tick mark locations and the video location. It loads everything contained in the file properly besides the tick markers which are just QImages. It only loads the last tick marker
Currently, the code is a for loop that takes the positions listed calculates the position the tick marker must go on the progress bar and places it there.
Shown below is the portion of code that is related to this issue:
int slider_xpos = ui->VideoProgressSlider->x();
int slider_ypos = ui->VideoProgressSlider->y();
int slider_width = ui->VideoProgressSlider->width();
while(!Bookmark_Placement.empty())
{
//New Bookmark is initialized
Bookmarker_Label = new QLabel(this);
Bookmark = new QImage();
Bookmark->load("UI_Elements/Bookmark.png");
//Bookmark's image is scaled down
int scaled_width = Bookmark->width()/64;
int scaled_height = Bookmark->height()/64;
QImage *Bookmark_Scaled = new QImage(Bookmark->scaled(scaled_width,Bookmark->height(),Qt::KeepAspectRatio));
Bookmarker_Label->setPixmap(QPixmap::fromImage(*Bookmark_Scaled));
//Takes the Bookmark's position off of QList
int Bookmark_Position = Bookmark_Placement.last();
Bookmark_Placement.removeLast();
//Places Bookmark in the proper position
double offset = ((double)Bookmark_Position/(double)Bookmark_Count)*(double)slider_width;
int Bookmarker_Label_xpos= slider_xpos + (int)offset;
Bookmarker_Label->setGeometry(Bookmarker_Label_xpos,slider_ypos - scaled_height,scaled_width,scaled_height);
Bookmarker_Label->show();
}

Related

Programmatically aligning a created TButton right next to an adjacent TComponent in an FMX Frame

Referring to the picture, I would like to align a dynamically created TButton at runtime right next to a BindNavigator.
TButton *Add_But;
Add_But = new TButton(this);
Add_But->Visible = true;
Add_But->Text = "Add";
//Add_But->Position->X = 300;
//Add_But->Position->Y = 350;
Add_But->Parent=Form1->BindNavigator1;
Form1->Frame1->AddObject(Form1->StringGridBindSourceDB1);
Form1->Frame1->AddObject(Form1->BindNavigator1);
Form1->Frame1->AddObject(Add_But);
Add_But->Align=Fmx::Types::TAlignLayout::Right;
If I execute the above code, the Add_But button would align next to BindNavigator enclosed portion of the area between the last three buttons starting from the refresh button. Positioning Add_But using X,Y is not the ideal solution as I would like the Add_But to space out by certain margin padding just by using the Align property.
How to programmatically construct a TBounds margin object to resolve the issue?
Not Optimum solution using Two FlowLayout ,Believe TGridPanelLayout is much better choice , quite difficult to code correctly at runtime on cell position placement as the Main Frame is Just An Empty container refresh to hold Any child item based on selection
TFlowLayout *tlayout=new TFlowLayout(this);
tlayout->AddObject(Form1->StringGridBindSourceDB1);
TFlowLayout *tlayout1=new TFlowLayout(this);
// approximate the size of the TGrid
tlayout1->Width=600;
tlayout1->AddObject(Form1->BindNavigator1);
Add_But->Margins->Left = 10;
tlayout1->AddObject(Add_But);
tlayout->AddObject(tlayout1);
Form1->Frame1->AddObject(tlayout);
I have not written any apps in FMX but I saw no reason why you could not simply drop a TPanel on your FMX form then drop a TBindNavigator onto the TPanel unless there is a reason it can't be done this way, just trying to help.
This code works fine in Builder 10.3 on FMX Form
TButton *b = new TButton(TPanel1);
b->Parent = TPanel1;
b->Visible = true;
b->Position->X = TBindNavigator1->Width + 25;
b->Position->Y = TPanel1->Height / 2 - b->Height / 2;
b->Width = b->Width * 2;
b->Text = "Runtime Button";
How it looks when you run the code

How to stop expansion of QGridLayout element

I have couple of labels (dynamically generated on button click and can vary in numbers which read from configuration file) and added to QGridLayout. Upon load which looks like below ...
these labels are generated and added as below
QGridLayout * layout = new QGridLayout(ui->pageInputWindow);
layout->setSpacing(5);
layout->setMargin(0);
ui->pageInputWindow->setLayout(layout);
// for question purpose I take number of row and col to 3
// but in actual they will be read from configuration file
for(int row = 0; row < 3; row ++)
{
for(int col = 0; col < 3; col++)
{
QLabel * placeHolder = new QLabel(ui->pageInputWindow);
placeHolder->setText("LABEL "+QString::number(10*(row+1) + col + 1));
layout->addWidget(placeHolder, row, col);
}
}
These label are placed here for rendering video streaming by setting pixmap of captured video frames when selected. I am setting pix as ....
// I am getting img object from other class, below code is just a snap of it.
// You can assume img as valid QImage objcet
QImage img
selectedLabel->setPixmap(QPixmap::fromImage(img).scaled(selectedLabel->size(),Qt::KeepAspectRatio, Qt::FastTransformation));
My ideal scenario is when I select any label it will remain with size which it got when loaded according to configuration settings at runtime. But when I start streaming below event happened.
Suddenly selected label ( see black pictured label at 'LABEL 11' position) starts expansding to much even causing application to expand. Idealy I want above event as below ( assume white background is video frame ) without any expansion.
My question is how can I stop this undesirable expansion of labels while setting pix map on them ?
Set the labels' size policies to ignored:
placeHolder->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Ignored);

Draw a pie chart in MFC TeeChart

My English is no very good, so please forgive me. I have added my data successfully in a pie chart, but the pie chart doesn't show with only data shown in the control.
The properties of the control seem like have been configured appropriately. I don't know where is the problem since I have spent whole my night on it.
BOOL CStatInfPieDlg::OnInitDialog()
{
CDialogEx::OnInitDialog();
char temp1[100];
char temp2[100];
CString str;
// TODO: Add extra initialization here
CSeries series = (CSeries)statInfPie.Series(0);
int size = stationInfList.size();
series.put_ColorEachPoint(true);
srand(time(NULL));
for (int i = 0; i < size; i++) {
sprintf(temp1, "%s/%d ", iptostr(stationInfList[i].netaddrA), toCidr(stationInfList[i].netmaskA));
sprintf(temp2, "%s/%d", iptostr(stationInfList[i].netaddrB), toCidr(stationInfList[i].netmaskB));
strcat(temp1, temp2);
str = CString(temp1);
series.Add(stationInfList[i].bcountAToB + stationInfList[i].bcountBToA, str, RGB(rand() % 255, rand() % 255, rand() % 255));
memcpy(temp1, "\0", sizeof(temp1));
memcpy(temp2, "\0", sizeof(temp2));
}
return TRUE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
The code sample above initializes my dialog which contains the TeeChart control. I add data through function Add(). Array temp1 and array temp2 is my description inf. After I compile and run my program, the result shows in the picture blow.
TeeChart tries to make space for the long labels and the Legend, automatically reducing the diameter of the Pie. In this case the result is extreme; the Pie is left with no radius.
That can be resolved in one of several ways:
The latest version of TeeChart (AX) includes a property called InsideSlice for PieMarks.
ie.TChart1.Series(0).asPie.PieMarks.InsideSlice = True
For older versions of TeeChart, where this property is not available you can manually set the Arrowlength (the connector to the Mark) to a negative value:
ie. TChart1.Series(0).Marks.ArrowLength = -20
The Series Marks can be setup to render multiline, taking up less width:
ie. TChart1.Series(0).Marks.MultiLine = True
If the Legend is in the Chart with very long labels that can also be counter productive to chart readability. The Legend can be set to Visible false or told to not resize the Chart Series (the Pie) to fit.
ie. TChart1.Legend.ResizeChart = False
or can be positioned below the Pie
ie. TChart1.Legend.Alignment = laBottom
A thought to design will be required here. Showing long Point Value labels (the Series Marks) and repeating some of the information in the Legend is taking up a great deal of the working space where the Chart could be shown. If the Legend were to be placed below the Chart and the Panel were sized accordingly and perhaps were to use information that doesn't duplicate the Series Marks' information (using a different Legend Text Style) plus setting up the Series Marks with Multiline, with a shorter Arrowlength, then the overall result should be very readable.

Saving data for multiple items while navigating through list of items

I am new this type of c++/cli language and i look for some help. I develop a project about the ListBoxes, i got some codes and learn basic steps on it. But i am actually stuck on the hardest part in this project.
The project counts framenumbers and keeps it. Its just an integer number and i got next and previous buttons in my code. when people click somewhere in the image, gui gets x and y coordinates and write it to the listbox correctly. What i trying to do is, when people push the next button, framenumber increased by one and clear listbox interface and ready for get other x and y coordinates. When people pressed previous button, ListBox should show the previous framenumbers x and y coordinates.
My question is, can i keep this x and y data in somewhere and reach at will? What should i do for keep these data? Any helps or thoughts will be appreciated for me.
Thank you for your helps.
What I would do is create a class to hold the data you want to save for each frame, and stick it into a collection of some sort as the user navigates through the frames. You could keep a List or a Stack, to implement retrieving the 'previous' item, but I'd probably use a Dictionary. Make the key of the dictionary the frame number, and have the value be the class of data you're saving for each frame.
Perhaps something like this:
public ref class FrameData
{
public:
int x;
int y;
public:
FrameData(int x, int y)
{
this->x = x;
this->y = y;
}
};
Dictionary<int, FrameData^>^ savedFrameData = gcnew Dictionary<int, FrameData^>();
// When they click the next or previous button:
// Save the data for the old frame.
savedFrameData->[oldFrameNumber] = gcnew FrameData(currentX, currentY);
// Retrieve the previous data for the new frame, if found.
FrameData^ dataForNewFrame;
if (savedFrameData->TryGetValue(newFrameNumber, dataForNewFrame))
{
currentX = dataForNewFrame->x;
currentY = dataForNewFrame->y;
}
else
{
currentX = 0;
currentY = 0;
}

How do I register an event for a raphael elements created through js?

Say I have n objects (say rectangles) whose size and position were randomly created when the user pushes a button. How do I register a click event in Raphael such that I know which rectangle/object was clicked on when the user clicks on one of the rectangles? The trick here is that n number are created inside of a loop. I need to be able to handle when any of the rectangles is clicked on so that I can perform some operation (eg. change the color of the clicked on rectangle to blue.) Here is the code for creating the rectangles:
for (var i=1;i<3;i++) {
x = Math.floor((Math.random()*200)+1);
y = Math.floor((Math.random()*200)+1);
width = Math.floor((Math.random()*25)+1) + 25;
height = Math.floor((Math.random()*100)+1) + 50;
r1 = paper.rect(x,y,width,height).attr({fill:"red"});
}
I think I found it in another posting. That's just the way it is...you look and look and post here and then you find the answer:
I simply need to add the following handler inside the loop after the rectangle is created:
r1.click(function() { this.attr({fill:'blue'}); });
Thanks to: http://jsfiddle.net/CHUrB/298/