AlgoMaster Logo
AlgoMasterDesign Widget Palettemedium

Design Widget Palette

medium

A UI builder keeps a palette of named widgets. Labels and buttons are leaves, panels hold other widgets, and a designer duplicates any of them by copying. A copied panel has to be a separate tree all the way down.

Label, Button, Panel and WidgetPalette are provided in the starter code. Implement only the widget contract and the three clone methods: declare Widget with render() and clone() (IWidget in C#) and complete Label.clone(), Button.clone() and Panel.clone().

The provided classes work like this:

  • Label(text) has setText(text) and renders as "Label(Hello)".
  • Button(caption) renders as "Button[OK]".
  • Panel(title) has add(child), childCount() and child(index), and renders as "Panel<Login>{Label(Hello), Button[OK]}" with its children in order, or "Panel<Login>{}" when empty.

Panel.clone() must return a new panel with the same title whose children are clones of the original children, obtained through the contract rather than by checking each child's kind.

The provided WidgetPalette behaves as follows:

  • WidgetPalette() starts empty.
  • boolean createLabel(String name, String text), boolean createButton(String name, String caption) and boolean createPanel(String name, String title) store a new widget under name, or return false for an empty or taken name.
  • boolean addToPanel(String panel, String child) adds the named child object itself to the named panel. It returns false when either name is unknown, the first is not a panel, or both name the same widget. The same child may be added more than once.
  • boolean copyWidget(String source, String target) clones the source and stores the copy under target, or returns false for an unknown source or a taken target.
  • boolean setLabelText(String name, String text) changes a label's text, or returns false when the name is not a label.
  • boolean setPanelLabelText(String panel, int index, String text) changes the text of the label at that index inside the panel, or returns false when the panel is unknown, the index is outside its children, or that child is not a label.
  • String render(String name) returns the widget's rendering, or "MISSING".
  • int widgetCount() returns how many named widgets exist.

The tests call the provided WidgetPalette; your work should be confined to the contract and the three clone methods.

Example 1:

Input:

Output:

Explanation: The copied panel holds a copy of the label. Changing that copy's text does not reach the original panel's label.

Example 2:

Input:

Output:

Explanation: The original outer panel still holds the original label, so editing it shows through. The copy was cloned all the way down and keeps the old text.

Constraints

  • 0 <= name.length, text.length, caption.length, title.length <= 20
  • -1 <= index <= 10
  • A panel nests at most 3 levels deep.
  • At most 100 calls in total are made across all methods.

Starter Code

Declare the Widget contract and complete the three clone() methods. Everything else in the three classes and all of WidgetPalette is provided and must not be modified.

How the design is graded

needs 7/10 to pass
  • The contract carries the copy

    Full marks when `Widget` declares both `render` and `clone`, so the palette can copy any widget without knowing its kind. Lose points heavily when the palette or the panel checks a widget's type to copy it.

  • The composite clones its children polymorphically

    Full marks when `Panel.clone` builds a new panel and adds `child.clone()` for every child, so nested panels are copied all the way down and editing a label inside the copy leaves the original untouched. Lose points heavily when the new panel holds the original child objects.

  • Leaves copy their own state

    Full marks when `Label.clone` and `Button.clone` return new objects with the same text or caption. Lose points for printing to stdout.

Passing every test is not enough on its own. A submission is accepted only when the design also clears the bar.

Hints

Loading...
CallReturns
new WidgetPalette()null
createLabel("title", "Hello")true
createButton("ok", "OK")true
createPanel("form", "Login")true
addToPanel("form", "title")true
addToPanel("form", "ok")true
copyWidget("form", "form2")true
setPanelLabelText("form2", 0, "Bye")true
render("form")"Panel<Login>{Label(Hello), Button[OK]}"
render("form2")"Panel<Login>{Label(Bye), Button[OK]}"

The copied panel holds a copy of the label. Changing that copy's text does not reach the original panel's label.

Run checks these cases. Submit also runs a larger hidden set.