SpinBox.qml 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. // Copyright (c) 2022 Ultimaker B.V.
  2. // Cura is released under the terms of the LGPLv3 or higher.
  3. import QtQuick 2.2
  4. import QtQuick.Controls 2.15
  5. import UM 1.5 as UM
  6. import Cura 1.5 as Cura
  7. // This component extends the funtionality of QtControls 2.x Spinboxes to
  8. // - be able to contain fractional values
  9. // - hava a "prefix" and a "suffix". A validator is added that recognizes this pre-, suf-fix combo. When adding a custom
  10. // validator the pre-, suf-fix should be added (e.g. new RegExp("^" + prefix + \regex\ + suffix + "$")
  11. Item
  12. {
  13. id: base
  14. property string prefix: ""
  15. property string suffix: ""
  16. property int decimals: 0
  17. property real stepSize: 1
  18. property real value: 0
  19. property real from: 0
  20. property real to: 99
  21. property alias wrap: spinBox.wrap
  22. property bool editable: true
  23. property var validator: RegExpValidator
  24. {
  25. regExp: new RegExp("^" + prefix + "([0-9]+[.|,]?[0-9]*)?" + suffix + "$")
  26. }
  27. signal editingFinished()
  28. implicitWidth: spinBox.implicitWidth
  29. implicitHeight: spinBox.implicitHeight
  30. SpinBox
  31. {
  32. id: spinBox
  33. anchors.fill: base
  34. editable: base.editable
  35. topPadding: 0
  36. bottomPadding: 0
  37. padding: UM.Theme.getSize("narrow_margin").width
  38. // The stepSize of the SpinBox is intentionally set to be always `1`
  39. // As SpinBoxes can only contain integer values the `base.stepSize` is concidered the precision/resolution
  40. // increasing the spinBox.value by one increases the actual/real value of the component by `base.stepSize`
  41. // as such spinBox.value * base.stepSizes produces the real value of the component
  42. stepSize: 1
  43. value: Math.floor(base.value / base.stepSize)
  44. from: Math.floor(base.from / base.stepSize)
  45. to: Math.floor(base.to / base.stepSize)
  46. valueFromText: function(text)
  47. {
  48. return parseFloat(text.substring(prefix.length, text.length - suffix.length).replace(",", ".")) / base.stepSize;
  49. }
  50. textFromValue: function(value)
  51. {
  52. return prefix + (value * base.stepSize).toFixed(decimals) + suffix;
  53. }
  54. validator: base.validator
  55. onValueModified:
  56. {
  57. base.value = value * base.stepSize;
  58. }
  59. background: Item {}
  60. contentItem: Cura.TextField
  61. {
  62. text: spinBox.textFromValue(spinBox.value, spinBox.locale)
  63. validator: base.validator
  64. onActiveFocusChanged:
  65. {
  66. if (!activeFocus)
  67. {
  68. base.editingFinished();
  69. }
  70. }
  71. }
  72. down.indicator: Rectangle
  73. {
  74. x: spinBox.mirrored ? parent.width - width : 0
  75. height: parent.height
  76. width: height
  77. UM.UnderlineBackground {
  78. color: spinBox.down.pressed ? spinBox.palette.mid : UM.Theme.getColor("detail_background")
  79. }
  80. UM.RecolorImage
  81. {
  82. anchors.centerIn: parent
  83. height: parent.height / 2.5
  84. width: height
  85. color: enabled ? UM.Theme.getColor("text") : UM.Theme.getColor("text_disabled")
  86. source: UM.Theme.getIcon("Minus")
  87. }
  88. }
  89. up.indicator: Rectangle
  90. {
  91. x: spinBox.mirrored ? 0 : parent.width - width
  92. height: parent.height
  93. width: height
  94. UM.UnderlineBackground {
  95. color: spinBox.up.pressed ? spinBox.palette.mid : UM.Theme.getColor("detail_background")
  96. }
  97. UM.RecolorImage
  98. {
  99. anchors.centerIn: parent
  100. height: parent.height / 2.5
  101. width: height
  102. color: enabled ? UM.Theme.getColor("text") : UM.Theme.getColor("text_disabled")
  103. source: UM.Theme.getIcon("Plus")
  104. }
  105. }
  106. }
  107. }