feat: add an option to switch between fixed and dynamic Sensors/Fans widget width (#483)

This commit is contained in:
Serhiy Mytrovtsiy
2021-05-17 22:55:28 +02:00
parent 376eee80fd
commit 5fd53d717f
27 changed files with 115 additions and 23 deletions

View File

@@ -14,6 +14,7 @@ import StatsKit
public class SensorsWidget: WidgetWrapper {
private var modeState: String = "automatic"
private var fixedSizeState: Bool = false
private var values: [KeyValue_t] = []
private var oneRowWidth: CGFloat = 36
@@ -51,6 +52,7 @@ public class SensorsWidget: WidgetWrapper {
if !preview {
self.modeState = Store.shared.string(key: "\(self.title)_\(self.type.rawValue)_mode", defaultValue: self.modeState)
self.fixedSizeState = Store.shared.bool(key: "\(self.title)_\(self.type.rawValue)_size", defaultValue: self.fixedSizeState)
}
}
@@ -122,7 +124,12 @@ public class SensorsWidget: WidgetWrapper {
let style = NSMutableParagraphStyle()
style.alignment = .center
let rect = CGRect(x: x, y: (Constants.Widget.height-13)/2, width: self.oneRowWidth, height: 13)
var width: CGFloat = self.oneRowWidth
if !self.fixedSizeState {
width = sensor.value.widthOfString(usingFont: font).rounded(.up) + 2
}
let rect = CGRect(x: x, y: (Constants.Widget.height-13)/2, width: width, height: 13)
let str = NSAttributedString.init(string: sensor.value, attributes: [
NSAttributedString.Key.font: font,
NSAttributedString.Key.foregroundColor: NSColor.textColor,
@@ -130,7 +137,7 @@ public class SensorsWidget: WidgetWrapper {
])
str.draw(with: rect)
return self.oneRowWidth
return width
}
private func drawTwoRows(topSensor: KeyValue_t, bottomSensor: KeyValue_t?, x: CGFloat) -> CGFloat {
@@ -146,17 +153,24 @@ public class SensorsWidget: WidgetWrapper {
NSAttributedString.Key.paragraphStyle: style
]
var rect = CGRect(x: x, y: rowHeight+1, width: self.twoRowWidth, height: rowHeight)
var width: CGFloat = self.twoRowWidth
if !self.fixedSizeState {
let firstRowWidth = topSensor.value.widthOfString(usingFont: font)
let secondRowWidth = bottomSensor?.value.widthOfString(usingFont: font) ?? 0
width = max(20, max(firstRowWidth, secondRowWidth)).rounded(.up) + 2
}
var rect = CGRect(x: x, y: rowHeight+1, width: width, height: rowHeight)
var str = NSAttributedString.init(string: topSensor.value, attributes: attributes)
str.draw(with: rect)
if bottomSensor != nil {
rect = CGRect(x: x, y: 1, width: self.twoRowWidth, height: rowHeight)
rect = CGRect(x: x, y: 1, width: width, height: rowHeight)
str = NSAttributedString.init(string: bottomSensor!.value, attributes: attributes)
str.draw(with: rect)
}
return self.twoRowWidth
return width
}
public func setValues(_ values: [KeyValue_t]) {
@@ -170,24 +184,23 @@ public class SensorsWidget: WidgetWrapper {
// MARK: - Settings
public override func settings(width: CGFloat) -> NSView {
let rowHeight: CGFloat = 30
let height: CGFloat = ((rowHeight + Constants.Settings.margin) * 1) + Constants.Settings.margin
let view = SettingsContainerView(width: width)
let view: NSView = NSView(frame: NSRect(
x: Constants.Settings.margin,
y: Constants.Settings.margin,
width: width - (Constants.Settings.margin*2),
height: height
))
view.addSubview(SelectRow(
frame: NSRect(x: 0, y: (rowHeight + Constants.Settings.margin) * 0, width: view.frame.width, height: rowHeight),
view.addArrangedSubview(SelectRow(
frame: NSRect(x: 0, y: 0, width: view.frame.width, height: Constants.Settings.row),
title: LocalizedString("Display mode"),
action: #selector(changeMode),
items: SensorsWidgetMode,
selected: self.modeState
))
view.addArrangedSubview(ToggleTitleRow(
frame: NSRect(x: 0, y: 0, width: view.frame.width, height: Constants.Settings.row),
title: LocalizedString("Static width"),
action: #selector(toggleSize),
state: self.fixedSizeState
))
return view
}
@@ -198,4 +211,16 @@ public class SensorsWidget: WidgetWrapper {
self.modeState = key
Store.shared.set(key: "\(self.title)_\(self.type.rawValue)_mode", value: key)
}
@objc private func toggleSize(_ sender: NSControl) {
var state: NSControl.StateValue? = nil
if #available(OSX 10.15, *) {
state = sender is NSSwitch ? (sender as! NSSwitch).state: nil
} else {
state = sender is NSButton ? (sender as! NSButton).state: nil
}
self.fixedSizeState = state! == .on ? true : false
Store.shared.set(key: "\(self.title)_\(self.type.rawValue)_size", value: self.fixedSizeState)
self.display()
}
}

View File

@@ -56,6 +56,7 @@
9A81C76A2449A43600825D92 /* readers.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A81C7682449A43600825D92 /* readers.swift */; };
9A81C76B2449AE9400825D92 /* StatsKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 9A0C82DA24460F7200FAE3D4 /* StatsKit.framework */; };
9A81C7702449B8D500825D92 /* Charts.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A81C76F2449B8D500825D92 /* Charts.swift */; };
9A885B1A26513253000E43FE /* constants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A885B1926513253000E43FE /* constants.swift */; };
9A8DE58E253DEFA9006A748F /* Fans.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 9A8DE587253DEFA9006A748F /* Fans.framework */; };
9A8DE58F253DEFA9006A748F /* Fans.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 9A8DE587253DEFA9006A748F /* Fans.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
9A8DE5E4253DF4E2006A748F /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A8DE5E3253DF4E2006A748F /* main.swift */; };
@@ -71,7 +72,6 @@
9A944D55244920690058F32A /* reader.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A944D54244920690058F32A /* reader.swift */; };
9A944D5B244925720058F32A /* widget.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A944D5A244925720058F32A /* widget.swift */; };
9A944D5D24492A8B0058F32A /* popup.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A944D5C24492A8B0058F32A /* popup.swift */; };
9A944D5F24492AA60058F32A /* Constants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A944D5E24492AA60058F32A /* Constants.swift */; };
9A953A1424B9D22D0038EF4B /* settings.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9A953A1324B9D22D0038EF4B /* settings.swift */; };
9A97CED12537331B00742D8F /* CPU.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 9A97CECA2537331B00742D8F /* CPU.framework */; };
9A97CED22537331B00742D8F /* CPU.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 9A97CECA2537331B00742D8F /* CPU.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
@@ -428,6 +428,7 @@
9A81C7672449A43600825D92 /* main.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = "<group>"; };
9A81C7682449A43600825D92 /* readers.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = readers.swift; sourceTree = "<group>"; };
9A81C76F2449B8D500825D92 /* Charts.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Charts.swift; sourceTree = "<group>"; };
9A885B1926513253000E43FE /* constants.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = constants.swift; sourceTree = "<group>"; };
9A8DE587253DEFA9006A748F /* Fans.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Fans.framework; sourceTree = BUILT_PRODUCTS_DIR; };
9A8DE58A253DEFA9006A748F /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
9A8DE5E3253DF4E2006A748F /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = "<group>"; };
@@ -441,7 +442,6 @@
9A944D54244920690058F32A /* reader.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = reader.swift; sourceTree = "<group>"; };
9A944D5A244925720058F32A /* widget.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = widget.swift; sourceTree = "<group>"; };
9A944D5C24492A8B0058F32A /* popup.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = popup.swift; sourceTree = "<group>"; };
9A944D5E24492AA60058F32A /* Constants.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Constants.swift; sourceTree = "<group>"; };
9A953A1324B9D22D0038EF4B /* settings.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = settings.swift; sourceTree = "<group>"; };
9A97CE2A25371B2300742D8F /* IntelPowerGadget.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = IntelPowerGadget.framework; path = ../../../Library/Frameworks/IntelPowerGadget.framework; sourceTree = "<group>"; };
9A97CECA2537331B00742D8F /* CPU.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = CPU.framework; sourceTree = BUILT_PRODUCTS_DIR; };
@@ -624,8 +624,9 @@
9A65492224407EA600E30B74 /* store.swift */,
9A0C82D324460E4400FAE3D4 /* launchAtLogin.swift */,
9A654920244074B500E30B74 /* extensions.swift */,
9A1D5E4A25235C8100B82BFC /* helpers.swift */,
9A885B1926513253000E43FE /* constants.swift */,
9A5F191526220D510085C3CC /* types.swift */,
9A1D5E4A25235C8100B82BFC /* helpers.swift */,
9A0C82DD24460F7200FAE3D4 /* Info.plist */,
9A9D728924471FAE005CF997 /* SMC.swift */,
9A81C76F2449B8D500825D92 /* Charts.swift */,
@@ -821,7 +822,6 @@
9A944D5A244925720058F32A /* widget.swift */,
9A944D5C24492A8B0058F32A /* popup.swift */,
9A81C74F24499D6600825D92 /* settings.swift */,
9A944D5E24492AA60058F32A /* Constants.swift */,
);
path = ModuleKit;
sourceTree = "<group>";
@@ -1442,6 +1442,7 @@
9A81C7702449B8D500825D92 /* Charts.swift in Sources */,
9A0C82E624460F9A00FAE3D4 /* extensions.swift in Sources */,
9A0C82E724460F9C00FAE3D4 /* updater.swift in Sources */,
9A885B1A26513253000E43FE /* constants.swift in Sources */,
9A1D5E4B25235C8100B82BFC /* helpers.swift in Sources */,
9A0C82EE2446124800FAE3D4 /* SystemKit.swift in Sources */,
9A9D728A24471FAE005CF997 /* SMC.swift in Sources */,
@@ -1547,7 +1548,6 @@
9A944D5B244925720058F32A /* widget.swift in Sources */,
9A41530C24ABC3AF00A2BDA7 /* Memory.swift in Sources */,
9A81C75024499D6600825D92 /* settings.swift in Sources */,
9A944D5F24492AA60058F32A /* Constants.swift in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Батерия";
"Text widget" = "Текст";
"Memory widget" = "Памет";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Отваряне на настройките на модула";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Baterie";
"Text widget" = "Text";
"Memory widget" = "Paměť";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Otevřít nastavení modulu";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Akku";
"Text widget" = "Text";
"Memory widget" = "Speicher";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Modul Einstellungen öffnen";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Open module settings";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Batería";
"Text widget" = "Texto";
"Memory widget" = "Memoria";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Abrir la configruación del módulo";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Ouvrir les paramètres du module";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Modul beállításainak megnyitása";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Apri impostazioni modulo";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "バッテリー";
"Text widget" = "テキスト";
"Memory widget" = "未使用/使用済み";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "このモジュールの設定を開く";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "모듈 설정 열기";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Batteri";
"Text widget" = "Tekst";
"Memory widget" = "Tall";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Åpne modulinnstillinger";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Batterijwidget";
"Text widget" = "Tekstwidget";
"Memory widget" = "Geheugenwidget";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Open module-instellingen";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Bateria";
"Text widget" = "Tekst";
"Memory widget" = "Pamięć";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Otwórz ustawienia modułu";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Bateria";
"Text widget" = "Texto";
"Memory widget" = "Memoria";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Abrir configurações do módulo";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Abrir configurações do módulo";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Deschide setăriile modulului";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Открыть настройки модуля";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Batarya";
"Text widget" = "Metin";
"Memory widget" = "Bellek";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Modül ayarlarını aç";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Battery";
"Text widget" = "Text";
"Memory widget" = "Memory";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Відкрити налаштування модуля";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "Pin";
"Text widget" = "Văn bản";
"Memory widget" = "Bộ nhớ";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "Mở cài đặt module";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "电池";
"Text widget" = "文本";
"Memory widget" = "容量";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "打开模块设置";

View File

@@ -94,6 +94,7 @@
"Battery widget" = "電池";
"Text widget" = "文字";
"Memory widget" = "記憶體";
"Static width" = "Static width";
// Module Kit
"Open module settings" = "打開模組設定";

View File

@@ -1,6 +1,6 @@
//
// Constants.swift
// ModuleKit
// constants.swift
// StatsKit
//
// Created by Serhiy Mytrovtsiy on 15/04/2020.
// Using Swift 5.0.

View File

@@ -266,6 +266,7 @@ public extension NSView {
row.addSubview(toggle)
row.addSubview(rowTitle)
row.widthAnchor.constraint(equalToConstant: row.bounds.width).isActive = true
row.heightAnchor.constraint(equalToConstant: row.bounds.height).isActive = true
return row
@@ -304,6 +305,7 @@ public extension NSView {
row.addSubview(select)
row.addSubview(rowTitle)
row.widthAnchor.constraint(equalToConstant: row.bounds.width).isActive = true
row.heightAnchor.constraint(equalToConstant: row.bounds.height).isActive = true
return row
@@ -342,6 +344,9 @@ public extension NSView {
row.addSubview(select)
row.addSubview(rowTitle)
row.widthAnchor.constraint(equalToConstant: row.bounds.width).isActive = true
row.heightAnchor.constraint(equalToConstant: row.bounds.height).isActive = true
return row
}
@@ -361,6 +366,9 @@ public extension NSView {
row.addSubview(select)
row.addSubview(rowTitle)
row.widthAnchor.constraint(equalToConstant: row.bounds.width).isActive = true
row.heightAnchor.constraint(equalToConstant: row.bounds.height).isActive = true
return row
}

View File

@@ -801,3 +801,40 @@ public func process(path: String, arguments: [String]) -> String? {
return output
}
public class SettingsContainerView: NSStackView {
public init(width: CGFloat) {
super.init(frame: NSRect(
x: Constants.Settings.margin,
y: 0,
width: width - (Constants.Settings.margin*2),
height: 0
))
self.orientation = .vertical
self.distribution = .gravityAreas
self.edgeInsets = NSEdgeInsets(
top: Constants.Settings.margin,
left: Constants.Settings.margin,
bottom: Constants.Settings.margin,
right: Constants.Settings.margin
)
self.spacing = Constants.Settings.margin
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
private func resize() {
let h = self.arrangedSubviews.map({ $0.bounds.height + self.spacing }).reduce(0, +) - self.spacing + self.edgeInsets.top + self.edgeInsets.bottom
if self.frame.size.height != h {
self.setFrameSize(NSSize(width: self.bounds.width, height: h))
}
}
public override func addArrangedSubview(_ view: NSView) {
super.addArrangedSubview(view)
self.resize()
}
}