GithubHelp home page GithubHelp logo

Comments (5)

gansm avatar gansm commented on July 18, 2024

Thanks for your detailed description, which helped me to find some problems with the FLabel widget.

1st problem: The widget default size is 1×1 character. This caused an unsigned integer underflow!
2nd problem: I stupidly implemented the code of setMaximumSize() in setMaximumHeight().

I have a version committed (b7639f5) that fixes these problems.

The main problem in your program is that you don't give the FLabel a size. Therefore the set size hints for minimum and maximum are ignored. The widget still has its default size of 1x1 characters. The size hints are only considered in the methods setWidth(), setHeight(), setSize(), and setGeometry().

Here is the code of the method setSize() for explanation:

void FWidget::setSize (const FSize& size, bool adjust)
{
  std::size_t width = size.getWidth();
  std::size_t height = size.getHeight();
  width  = std::min (width,  size_hints.max_width);
  width  = std::max (width,  size_hints.min_width);
  height = std::min (height, size_hints.max_height);
  height = std::max (height, size_hints.min_height);
  [...]
}

Please try my variant with my last commit.

#include <iostream>
#include <final/final.h>

namespace fc = finalcut;

class HelloDialog : public fc::FDialog
{
  fc::FLabel labelDim{this};

public:
  HelloDialog (fc::FWidget& parent)
    : FDialog(&parent)
  {
    setText("Hello Finalcut - Size Issue");
    setPos({10, 3});
    setSize({40, 18});
    labelDim.setFixedSize({getClientWidth(), 1});  // Sets the size hints
    labelDim.setSize({9, 99});  // Sets the label size by using size hints
    addTimer(100);
  }

  void onTimer (fc::FTimerEvent*) override
  {
    labelDim << "x";
    redraw();  // Prints ellipsis ("..") on text overflow
  }
};

int main (int argc, char* argv[])
{
  fc::FApplication app{argc, argv};
  HelloDialog dialog{app};
  dialog.show();
  app.setMainWidget(&dialog);
  return app.exec();
}

from finalcut.

terranpro avatar terranpro commented on July 18, 2024

Glad the report could be of help :) Your patch does indeed fix the overflow, but without setting a size it does default to size 1x1 as you mentioned.

I think I misunderstood the purpose of min/max size hints. I had figured there would be a size calculation based on text length up to the maximum size hint, thus no setSize call. From the code snippet you pasted, it looks like Min/Max size hints are just to enforce a range for calls to setSize. This seems useful for resizeable windows/dialogs - using hints to prevent the user from resizing it too small or too large, right?

Looks like setSize is really just what I need to use with a sane value for my particular layout - and not so much using the size hints for labels. Would you agree with that ?

Also not sure if this is a bug or just something users need to be aware of, but if label minSize >= parent dialogs minSize, then there are overflow artifacts drawn. I attached a couple screenshots of what I mean. Seems like child should set minSize to parent's minSize minus the borders, e.g. (2?) for width, and 3 for height (extra +1 for the top title bar).

setMinimumSize({25, 4})
labelDim.setMinimumSize({25,4})

labelbug2

setMinimumSize({15, 4})
labelDim.setMinimumSize({25, 4})

labelbug3

from finalcut.

gansm avatar gansm commented on July 18, 2024

You have already correctly recognized that with setMinimumSize() and setMaximumSize() only a validity range can be defined.

What you are looking for is a dynamically adaptive layout. For this, you can overload the method adjustSize(). See https://github.com/gansm/finalcut/blob/master/doc/first-steps.md#dynamic-layout

Also, you have correctly recognized that a child widget of a dialog with a frame must always be smaller than its parent widget. Therefore, a widget can have a top, right, bottom, and left padding space, which results in a client width or client height.

Width = LeftPadding + ClientWidth + RightPadding
Height = TopPadding + ClientHeight + BottomPadding

◄────────── getWidth() ──────────►
┌────────────────────────────────┐
│                                │
│                                │
│◄────── getClientWidth() ──────►│
│                                │
│                                │
└────────────────────────────────┘
▲                                ▲
│                                │
│                                └── getRightPadding()
└─────────────────────────────────── getLeftPadding()

A small example of how you can use adjustSize():

#include <iostream>
#include <final/final.h>

namespace fc = finalcut;

class HelloDialog : public fc::FDialog
{
  fc::FLabel labelDim{this};

public:
  HelloDialog (fc::FWidget& parent)
    : FDialog(&parent)
  {
    setText("Hello Finalcut - Size Issue");
    setPos({10, 3});
    setSize({25, 7});
    setResizeable();
    // Changing the window size by clicking with the mouse
    // on the lower right corner of the window.
    setMinimumSize({25, 7});
    fc::FSize client_size(getClientWidth(), getClientHeight());
    labelDim.setText(fc::FString(40, L'\u263a'));
    labelDim.setMinimumSize(client_size);
    labelDim.setSize({999, 1});
  }

  void adjustSize() override
  {
    FDialog::adjustSize();
    labelDim.setMinimumWidth(getClientWidth());
    labelDim.setWidth(getClientWidth());
  }
};

int main (int argc, char* argv[])
{
  fc::FApplication app{argc, argv};
  HelloDialog dialog{app};
  dialog.show();
  app.setMainWidget(&dialog);
  return app.exec();
}

By the way, I found a small error in the widget code (23ddf5d).

from finalcut.

terranpro avatar terranpro commented on July 18, 2024

Great, thanks again. I'll let you close this - I might ask some other questions in the user feedback issue =)

from finalcut.

gansm avatar gansm commented on July 18, 2024

In the meantime I have written a small chapter about the widget layout:
    https://github.com/gansm/finalcut/wiki/First-steps#widget-layout

from finalcut.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.