<commit_before>Guide to writing an analysis interface in QML
=============================================

QML (Qt Modeling Language) is a user interface markup language that JASP uses to show the analysis input panel. In this panel the user can specify what options should be set to what values and thereby change the tables and plots that the analysis computes. QML is a very flexible language that allows us to easily generate checkboxes, dropdowns and other common interface components. It also gives the possiblility to insert JavaScript expressions to dynamically alter the interface based on actions a user makes. To create a more uniform layout and make it easier to add new analyses we have provided a number of standardized components. These components should satify most analysis creators, although you can always [add your own](#advance-usage). 

Table of Contents:
- [Components](#components)
  * [General Input](#general-input)
    + [CheckBox](#checkbox)
    + [RadioButton](#radiobutton)
    + [DropDown](#dropdown)
    + [Slider](#slider)
    + [DoubleField](#doublefield)
    + [IntegerField](#integerfield)
    + [PercentField](#percentfield)
    + [TextField](#textfield)
  * [Variable Specification](#variable-specification)
    + [AvailableVariablesList](#availablevariableslist)
    + [AssignedVariablesList](#assignedvariableslist)
    + [RepeatedMeasuresFactorsList](#repeatedmeasuresfactorslist)
  * [Grouping](#grouping)
    + [Group](#group)
    + [Section](#section)
- [Layout of Components](#layout-of-components)
    + [Layout.rowSpan](#layoutrowspan)
    + [Layout.columnSpan](#layoutcolumnspan)
- [Connecting Multiple Components](#connecting-multiple-components)
- [An Example](#an-example)
  * [1. Specifying Imports](#1-specifying-imports)
  * [2. Adding the Form](#2-adding-the-form)
  * [3. Adding the Components](#3-adding-the-components)
- [Advanced Usage](#advanced-usage)


## Components
The components can roughly be divided in three classes. One that deals with general inputs (e.g., checkboxes), one that deals with assigning variables and one that groups components together. Each will be covered in the following section.
Some remarks about these components:
- They are all QML items, so they automatically get generic QML properties like `enabled` or `visible`.
- The properties of the components can be set directly with a value. You can use also a JavaScript expression so that the value will depend on other components (see the section on [Connecting Multiple Components](#connecting-multiple-components)).
- In several examples you may encounter `qsTr()`, it is important that this function wraps all text that will be shown in the interface. It will provide the possibility to translate JASP in the future.
- The components described below may generally be nested to an arbitrary level (e.g., a checkbox in a group in a checkbox).

### General Input
These components are quite common in questionnaires and input forms on websites, they include the checkbox, radiobutton, dropdown, slider and textfields where text may be entered.

#### CheckBox
Check button that can be toggled on and off. If some components are nested inside a CheckBox, they are automatically enabled or disabled when the CheckBox is set or not.
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the checkbox through this identifier)
- `label`: text that will be shown to the left of the checkbox
- `checked`: [optional, default: `false`] boolean specifying if it should be set per default on or not.
- `childrenOnSameRow`: [optional, default: `false`] boolean specifying if components (e.g., other checkboxes, textfields) nested within the checkbox should be shown on the same row or, alternatively, below the checkbox
- `columns`: [optional, default: `1`] integer specifying how many columns the nested components should occupy (e.g., when set to 3, with three nested checkboxes, these three checkboxes will appear side by side on the same horizontal row)

<details>
	<summary>Examples</summary>
	
  ```qml
  CheckBox { name: "pearson"; label: qsTr("Pearson"); checked: true }
  ```
  ![Image example](/Docs/development/img/qml-guide/CheckBox_example_1.png)
  
  ```qml
  CheckBox
  {
    name: "homogeneityCorrections"
    label: qsTr("Homogeneity corrections")
    columns: 3
    CheckBox { name: "homogeneityNone";   label: qsTr("None")           ; checked: true }
    CheckBox { name: "homogeneityBrown";	label: qsTr("Brown-Forsythe") ; checked: true }
    CheckBox { name: "homogeneityWelch";	label: qsTr("Welch")          ; checked: true }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/CheckBox_example_2.png)
  
</details>

#### RadioButton
A RadioButton is used with other RadioButton's inside a `RadioButtonGroup`. Contrary to CheckBox, only 1 RadioButton can be checked at the same time.

RadioButtonGroup properties:
- `name`: string identifier (in your R code you will be able to retrieve the value of the checked radiobutton through this identifier)
- `title`: text that is shown above the set of radiobuttons
- `radioButtonsOnSameRow`: [optional, default: `false`] per default, the RadioButton's are placed vertically under the title. Set this property to true to place the buttons horizontally.
- `columns`: [optional, default: `1`] integer specifying how many columns should be used to display the RadioButton's

RadioButton properties:
- `value`: the value of the `RadioButtonGroup` that is send to R when this radiobutton is checked
- `label`: the text that is shown to the right of the radiobutton
- `checked`: [optional, default: `false`] boolean specifying if it should contain a checkmark (and thus be the default); one radiobutton should have this property set to `true`
- `childrenOnSameRow`: [optional, default: `false`] boolean specifying if components (e.g., checkboxes, textfields) nested within the radiobutton should be shown on the same row or, alternatively, below the radiobutton
- `columns`: [optional, default: `1`] integer specifying how many columns the nested components should occupy (e.g., when set to 3, with three nested checkboxes, these three checkboxes will appear side by side on the same horizontal row)

<details>
	<summary>Examples</summary>
	
  ```qml
  RadioButtonGroup
  {
    name: "countProp"
    title: qsTr("Display")
    RadioButton { value: "descCounts"; label: qsTr("Counts"); checked: true }
    RadioButton { value: "descProps"; label: qsTr("Proportions") }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/RadioButton_example_1.png)
  
  ```qml
  RadioButtonGroup
  {
    name: "steppingMethodCriteriaType"
    title: qsTr("Stepping Method Criteria")
    RadioButton
    {
      value: "usePValue"; label: qsTr("Use p value"); checked: true
      columns: 2
      DoubleField { name: "steppingMethodCriteriaPEntry";		label: qsTr("Entry");	fieldWidth: 60; defaultValue: 0.05; max: 1; decimals: 3 }
      DoubleField { name: "steppingMethodCriteriaPRemoval";	label: qsTr("Removal");	fieldWidth: 60; defaultValue: 0.1; max: 1; decimals: 3 }
    }
    RadioButton
    {
      value: "useFValue"; label: qsTr("Use F value")
      columns: 2
      DoubleField { name: "steppingMethodCriteriaFEntry";		label: qsTr("Entry");	fieldWidth: 60; defaultValue: 3.84; decimals: 3 }
      DoubleField { name: "steppingMethodCriteriaFRemoval";	label: qsTr("Removal");	fieldWidth: 60; defaultValue: 2.71; decimals: 3 }
    }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/RadioButton_example_2.png)
  
</details>

#### DropDown
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the dropdown through this identifier)
- `label`: [optional, default: `""`] text that will be shown above the dropdown
- `values`: array of (named) values that is shown in the dropdown list, in the case of an unnamed array the value and the label are the same, but when a named array is provided the label shown to the user can be different from the value send to R (see example below)
- `indexDefaultValue`: [optional, default: `1`] integer specifying the index of the dropdown item that is selected by default, take note that this is zero-based
- `source`: if `values` is empty, you can use the name of a VariablesList (see [Variable Specification](#variable-specification)) to set the source of the values of the DropDown.

<details>
	<summary>Examples</summary>
	
  ```qml
  DropDown
  { 
    name: "orthogonalSelector"
    values: ["none", "varimax", "quartimax", "bentlerT", "equamax", "varimin"] 
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/DropDown_example_1.png)
  
  ```qml
  DropDown
  {
    name: "sumOfSquares"
    indexDefaultValue: 2
    label: qsTr("Sum of squares")
    values:
    [
      { label: "Type \u2160"; value: "type1"}
      { label: "Type \u2161"; value: "type2"}
      { label: "Type \u2162"; value: "type3"}
    ]
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/DropDown_example_2.png)
  
</details>

#### Slider
Slider is used to select a value by sliding a handle along a track.
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the slider through this identifier)
- `label`: [optional, default: `""`] text that will be shown above the slider
- `value`: [optional, default: `0.5`] default value
- `min`: [optional, default: `0`] minimum value
- `max`: [optional, default: `1`] maximum value
- `vertical`: [optional, default: true] set whether the slider should be displayed vertically or horizontally

<details>
	<summary>Examples</summary>
	
  ```qml
  Slider
  {
    name: "highlight"
    label: qsTr("Highlight")<commit_msg>Correct mistake in dropdown documentation<commit_after>Guide to writing an analysis interface in QML
=============================================

QML (Qt Modeling Language) is a user interface markup language that JASP uses to show the analysis input panel. In this panel the user can specify what options should be set to what values and thereby change the tables and plots that the analysis computes. QML is a very flexible language that allows us to easily generate checkboxes, dropdowns and other common interface components. It also gives the possiblility to insert JavaScript expressions to dynamically alter the interface based on actions a user makes. To create a more uniform layout and make it easier to add new analyses we have provided a number of standardized components. These components should satify most analysis creators, although you can always [add your own](#advance-usage). 

Table of Contents:
- [Components](#components)
  * [General Input](#general-input)
    + [CheckBox](#checkbox)
    + [RadioButton](#radiobutton)
    + [DropDown](#dropdown)
    + [Slider](#slider)
    + [DoubleField](#doublefield)
    + [IntegerField](#integerfield)
    + [PercentField](#percentfield)
    + [TextField](#textfield)
  * [Variable Specification](#variable-specification)
    + [AvailableVariablesList](#availablevariableslist)
    + [AssignedVariablesList](#assignedvariableslist)
    + [RepeatedMeasuresFactorsList](#repeatedmeasuresfactorslist)
  * [Grouping](#grouping)
    + [Group](#group)
    + [Section](#section)
- [Layout of Components](#layout-of-components)
    + [Layout.rowSpan](#layoutrowspan)
    + [Layout.columnSpan](#layoutcolumnspan)
- [Connecting Multiple Components](#connecting-multiple-components)
- [An Example](#an-example)
  * [1. Specifying Imports](#1-specifying-imports)
  * [2. Adding the Form](#2-adding-the-form)
  * [3. Adding the Components](#3-adding-the-components)
- [Advanced Usage](#advanced-usage)


## Components
The components can roughly be divided in three classes. One that deals with general inputs (e.g., checkboxes), one that deals with assigning variables and one that groups components together. Each will be covered in the following section.
Some remarks about these components:
- They are all QML items, so they automatically get generic QML properties like `enabled` or `visible`.
- The properties of the components can be set directly with a value. You can use also a JavaScript expression so that the value will depend on other components (see the section on [Connecting Multiple Components](#connecting-multiple-components)).
- In several examples you may encounter `qsTr()`, it is important that this function wraps all text that will be shown in the interface. It will provide the possibility to translate JASP in the future.
- The components described below may generally be nested to an arbitrary level (e.g., a checkbox in a group in a checkbox).

### General Input
These components are quite common in questionnaires and input forms on websites, they include the checkbox, radiobutton, dropdown, slider and textfields where text may be entered.

#### CheckBox
Check button that can be toggled on and off. If some components are nested inside a CheckBox, they are automatically enabled or disabled when the CheckBox is set or not.
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the checkbox through this identifier)
- `label`: text that will be shown to the left of the checkbox
- `checked`: [optional, default: `false`] boolean specifying if it should be set per default on or not.
- `childrenOnSameRow`: [optional, default: `false`] boolean specifying if components (e.g., other checkboxes, textfields) nested within the checkbox should be shown on the same row or, alternatively, below the checkbox
- `columns`: [optional, default: `1`] integer specifying how many columns the nested components should occupy (e.g., when set to 3, with three nested checkboxes, these three checkboxes will appear side by side on the same horizontal row)

<details>
	<summary>Examples</summary>
	
  ```qml
  CheckBox { name: "pearson"; label: qsTr("Pearson"); checked: true }
  ```
  ![Image example](/Docs/development/img/qml-guide/CheckBox_example_1.png)
  
  ```qml
  CheckBox
  {
    name: "homogeneityCorrections"
    label: qsTr("Homogeneity corrections")
    columns: 3
    CheckBox { name: "homogeneityNone";   label: qsTr("None")           ; checked: true }
    CheckBox { name: "homogeneityBrown";	label: qsTr("Brown-Forsythe") ; checked: true }
    CheckBox { name: "homogeneityWelch";	label: qsTr("Welch")          ; checked: true }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/CheckBox_example_2.png)
  
</details>

#### RadioButton
A RadioButton is used with other RadioButton's inside a `RadioButtonGroup`. Contrary to CheckBox, only 1 RadioButton can be checked at the same time.

RadioButtonGroup properties:
- `name`: string identifier (in your R code you will be able to retrieve the value of the checked radiobutton through this identifier)
- `title`: text that is shown above the set of radiobuttons
- `radioButtonsOnSameRow`: [optional, default: `false`] per default, the RadioButton's are placed vertically under the title. Set this property to true to place the buttons horizontally.
- `columns`: [optional, default: `1`] integer specifying how many columns should be used to display the RadioButton's

RadioButton properties:
- `value`: the value of the `RadioButtonGroup` that is send to R when this radiobutton is checked
- `label`: the text that is shown to the right of the radiobutton
- `checked`: [optional, default: `false`] boolean specifying if it should contain a checkmark (and thus be the default); one radiobutton should have this property set to `true`
- `childrenOnSameRow`: [optional, default: `false`] boolean specifying if components (e.g., checkboxes, textfields) nested within the radiobutton should be shown on the same row or, alternatively, below the radiobutton
- `columns`: [optional, default: `1`] integer specifying how many columns the nested components should occupy (e.g., when set to 3, with three nested checkboxes, these three checkboxes will appear side by side on the same horizontal row)

<details>
	<summary>Examples</summary>
	
  ```qml
  RadioButtonGroup
  {
    name: "countProp"
    title: qsTr("Display")
    RadioButton { value: "descCounts"; label: qsTr("Counts"); checked: true }
    RadioButton { value: "descProps"; label: qsTr("Proportions") }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/RadioButton_example_1.png)
  
  ```qml
  RadioButtonGroup
  {
    name: "steppingMethodCriteriaType"
    title: qsTr("Stepping Method Criteria")
    RadioButton
    {
      value: "usePValue"; label: qsTr("Use p value"); checked: true
      columns: 2
      DoubleField { name: "steppingMethodCriteriaPEntry";		label: qsTr("Entry");	fieldWidth: 60; defaultValue: 0.05; max: 1; decimals: 3 }
      DoubleField { name: "steppingMethodCriteriaPRemoval";	label: qsTr("Removal");	fieldWidth: 60; defaultValue: 0.1; max: 1; decimals: 3 }
    }
    RadioButton
    {
      value: "useFValue"; label: qsTr("Use F value")
      columns: 2
      DoubleField { name: "steppingMethodCriteriaFEntry";		label: qsTr("Entry");	fieldWidth: 60; defaultValue: 3.84; decimals: 3 }
      DoubleField { name: "steppingMethodCriteriaFRemoval";	label: qsTr("Removal");	fieldWidth: 60; defaultValue: 2.71; decimals: 3 }
    }
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/RadioButton_example_2.png)
  
</details>

#### DropDown
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the dropdown through this identifier)
- `label`: [optional, default: `""`] text that will be shown above the dropdown
- `values`: array of (named) values that is shown in the dropdown list, in the case of an unnamed array the value and the label are the same, but when a named array is provided the label shown to the user can be different from the value send to R (see example below)
- `indexDefaultValue`: [optional, default: `0`] integer specifying the index of the dropdown item that is selected by default, take note that the numbering starts at zero
- `source`: if `values` is empty, you can use the name of a VariablesList (see [Variable Specification](#variable-specification)) to set the source of the values of the DropDown.

<details>
	<summary>Examples</summary>
	
  ```qml
  DropDown
  { 
    name: "orthogonalSelector"
    values: ["none", "varimax", "quartimax", "bentlerT", "equamax", "varimin"] 
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/DropDown_example_1.png)
  
  ```qml
  DropDown
  {
    name: "sumOfSquares"
    indexDefaultValue: 2
    label: qsTr("Sum of squares")
    values:
    [
      { label: "Type \u2160", value: "type1"},
      { label: "Type \u2161", value: "type2"},
      { label: "Type \u2162", value: "type3"}
    ]
  }
  ```
  ![Image example](/Docs/development/img/qml-guide/DropDown_example_2.png)
  
</details>

#### Slider
Slider is used to select a value by sliding a handle along a track.
Properties
- `name`: string identifier (in your R code you will be able to retrieve the value of the slider through this identifier)
- `label`: [optional, default: `""`] text that will be shown above the slider
- `value`: [optional, default: `0.5`] default value
- `min`: [optional, default: `0`] minimum value
- `max`: [optional, default: `1`] maximum value
- `vertical`: [optional, default: `true`] set whether the slider should be displayed vertically or horizontally

<details>
	<summary>Examples</summary>
	
  ```qml
  Slider
  {
    name: "highlight"
    label: qsTr("Highlight")
{'fraction_non_alphanumeric': 0.10530909837749025, 'fraction_numerical': 0.006880262887656603, 'mean_word_length': 4.44050279329609, 'pattern_counts': {'":': 0, '<': 33, '<?xml version=': 0, '>': 33, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6418550', 'n_tokens_mistral': 5740, 'n_tokens_neox': 5325, 'n_words': 2255}