Skip to content

Commit

Permalink
feat: add power button on dashboard to switch printer on (mainsail-cr…
Browse files Browse the repository at this point in the history
…ew#1254)

Co-authored-by: th33xitus <domwil1091+github@gmail.com>
fixes mainsail-crew#897
  • Loading branch information
meteyou committed Feb 7, 2023
1 parent a1a0312 commit 9b746f4
Show file tree
Hide file tree
Showing 7 changed files with 122 additions and 8 deletions.
26 changes: 26 additions & 0 deletions src/components/mixins/base.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import Vue from 'vue'
import Component from 'vue-class-component'
import { DateTimeFormatOptions } from 'vue-i18n'
import { ServerPowerStateDevice } from '@/store/server/power/types'

@Component
export default class BaseMixin extends Vue {
Expand Down Expand Up @@ -44,6 +45,31 @@ export default class BaseMixin extends Vue {
return this.klipperReadyForGui && ['printing', 'paused'].includes(this.printer_state)
}

get printerPowerDevice(): string {
let deviceName = this.$store.state.gui.uiSettings.powerDeviceName ?? null
if (deviceName === null) deviceName = 'printer'

return deviceName
}

get isPrinterPowerOff() {
const devices = this.$store.getters['server/power/getDevices'] ?? []
if (devices.length === 0) return false

const deviceIndex = devices.findIndex(
(device: ServerPowerStateDevice) => device.device === this.printerPowerDevice
)
// stop if device is not found
if (deviceIndex === -1) return false

const device = devices[deviceIndex]
// Printer is on, if device status is "on" or "error"
if (device.status !== 'off') return false

// if klippy is not connected (service shutdown) and device.status === off
return !this.klippyIsConnected
}

get loadings(): string[] {
return this.$store.state.socket.loadings ?? []
}
Expand Down
43 changes: 37 additions & 6 deletions src/components/panels/KlippyStatePanel.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<template>
<div v-if="klipperState !== 'ready' && socketIsConnected">
<v-container v-if="klippyIsConnected" class="pa-0 pb-6">
<v-alert :color="messageType.color" dense text border="left" class="mb-0">
<template v-if="klippyIsConnected">
<v-alert :color="messageType.color" dense text border="left" class="mb-0 mb-6">
<!-- KLIPPER MESSAGE TITLE -->
<p class="font-weight-medium d-flex align-center">
<v-icon :color="messageType.color" class="pr-2">{{ messageType.icon }}</v-icon>
Expand Down Expand Up @@ -68,10 +68,28 @@
<v-progress-circular indeterminate :color="messageType.color"></v-progress-circular>
</v-card-text>
</v-alert>
</v-container>
</template>
<!-- Power OFF panel -->
<template v-else-if="isPrinterPowerOff">
<v-alert dense text border="left" class="mb-6">
<p class="font-weight-medium d-flex align-center">
<v-icon class="pr-2">{{ messageType.icon }}</v-icon>
{{ $t('Panels.KlippyStatePanel.PrinterSwitchedOff') }}
</p>
<p>{{ $t('Panels.KlippyStatePanel.PrinterSwitchedOffDescription') }}</p>
<v-row>
<v-col class="text-center">
<v-btn small outlined text :class="`${messageType.color}--text my-1`" @click="powerOn">
<v-icon class="mr-sm-2">{{ mdiPower }}</v-icon>
{{ $t('Panels.KlippyStatePanel.PowerOn') }}
</v-btn>
</v-col>
</v-row>
</v-alert>
</template>
<!-- DISCONNECTED INFOGRAPHIC -->
<v-container v-if="klipperState === 'disconnected'" class="pa-0">
<v-alert dense text border="left">
<template v-else-if="klipperState === 'disconnected'">
<v-alert dense text border="left" class="mb-6">
<p class="font-weight-medium d-flex align-center">
<v-icon class="pr-2">{{ messageType.icon }}</v-icon>
{{ $t('Panels.KlippyStatePanel.ServiceReports', { service: 'Moonraker' }) }}:
Expand All @@ -81,7 +99,7 @@
<p class="mt-2 mb-0 text-center">{{ $t('Panels.KlippyStatePanel.MoonrakerCannotConnect') }}</p>
<p class="mb-0 text-center">{{ $t('Panels.KlippyStatePanel.KlipperCheck') }}</p>
</v-alert>
</v-container>
</template>
</div>
</template>

Expand All @@ -99,6 +117,7 @@ import {
mdiRocketLaunch,
mdiConnection,
mdiPrinter3d,
mdiPower,
} from '@mdi/js'
@Component({
Expand All @@ -108,6 +127,7 @@ export default class KlippyStatePanel extends Mixins(BaseMixin) {
mdiPrinter3d = mdiPrinter3d
mdiRestart = mdiRestart
mdiDownload = mdiDownload
mdiPower = mdiPower
get klippy_message() {
return this.$store.state.server.klippy_message ?? null
Expand Down Expand Up @@ -144,5 +164,16 @@ export default class KlippyStatePanel extends Mixins(BaseMixin) {
window.open(href)
}
powerOn() {
this.$socket.emit(
'machine.device_power.post_device',
{
device: this.printerPowerDevice,
action: 'on',
},
{ action: 'server/power/responseToggle' }
)
}
}
</script>
51 changes: 49 additions & 2 deletions src/components/settings/SettingsUiSettingsTab.vue
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@
color="primary"
href="https://docs.mainsail.xyz/quicktips/thumbnails"
target="_blank">
{{ $t('Settings.UiSettingsTab.Guide') }}
{{ $t('Settings.UiSettingsTab.Guide').toString() }}
</v-btn>
</settings-row>
<v-divider class="my-2"></v-divider>
Expand Down Expand Up @@ -130,7 +130,6 @@
class="mt-0"
hide-details
outlined
attach
dense></v-select>
</settings-row>
<v-divider class="my-2"></v-divider>
Expand All @@ -140,6 +139,19 @@
:dynamic-slot-width="true">
<v-switch v-model="boolHideUploadAndPrintButton" hide-details class="mt-0"></v-switch>
</settings-row>
<v-divider class="my-2"></v-divider>
<settings-row
:title="$t('Settings.UiSettingsTab.PowerDeviceName').toString()"
:sub-title="$t('Settings.UiSettingsTab.PowerDeviceNameDescription').toString()"
:dynamic-slot-width="true">
<v-select
v-model="powerDeviceName"
:items="powerDeviceOptions"
class="mt-0"
hide-details
outlined
dense />
</settings-row>
</v-card-text>
</v-card>
</div>
Expand All @@ -153,6 +165,7 @@ import SettingsRow from '@/components/settings/SettingsRow.vue'
import { defaultLogoColor, defaultPrimaryColor } from '@/store/variables'
import { Debounce } from 'vue-debounce-decorator'
import { mdiRestart, mdiTimerOutline } from '@mdi/js'
import { ServerPowerStateDevice } from '@/store/server/power/types'
@Component({
components: { SettingsRow },
Expand Down Expand Up @@ -271,6 +284,40 @@ export default class SettingsUiSettingsTab extends Mixins(BaseMixin) {
this.$store.dispatch('gui/saveSetting', { name: 'uiSettings.boolHideUploadAndPrintButton', value: newVal })
}
get powerDevices() {
return this.$store.getters['server/power/getDevices'] ?? []
}
get autoPowerDevice() {
const autoIndex = this.powerDevices.findIndex((device: ServerPowerStateDevice) => device.device === 'printer')
if (autoIndex === -1) return '--'
return this.powerDevices[autoIndex].device
}
get powerDeviceName() {
return this.$store.state.gui.uiSettings.powerDeviceName ?? null
}
set powerDeviceName(newVal) {
this.$store.dispatch('gui/saveSetting', { name: 'uiSettings.powerDeviceName', value: newVal })
}
get powerDeviceOptions() {
const items: { text: string; value: string | null }[] = [
{ text: `Auto (${this.autoPowerDevice})`, value: null },
]
this.powerDevices.forEach((device: ServerPowerStateDevice) => {
items.push({
text: `${device.device} (${device.type})`,
value: device.device.toString(),
})
})
return items
}
clearColorObject(color: any): string {
if (typeof color === 'object' && 'hex' in color) color = color.hex
if (color.length > 7) color = color.substr(0, 7)
Expand Down
3 changes: 3 additions & 0 deletions src/locales/de.json
Original file line number Diff line number Diff line change
Expand Up @@ -510,6 +510,9 @@
"FirmwareRestart": "Firmware Neustart",
"KlipperCheck": "Bitte überprüfen Sie, ob der Klipper-Dienst läuft und ein UDS (Unix Domain Socket) konfiguriert ist.",
"MoonrakerCannotConnect": "Moonraker kann keine Verbindung zu Klipper herstellen!",
"PowerOn": "Drucker einschalten",
"PrinterSwitchedOff": "Drucker ist ausgeschaltet",
"PrinterSwitchedOffDescription": "Der Drucker ist ausgeschaltet und es kann keine Verbindung zu Klipper hergestellt werden. Um den Drucker einzuschalten, auf die Schaltfläche unten klicken:",
"Restart": "Neustart",
"ServiceReports": "{service} meldet"
},
Expand Down
5 changes: 5 additions & 0 deletions src/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -520,6 +520,9 @@
"FirmwareRestart": "Firmware Restart",
"KlipperCheck": "Please check if the Klipper service is running.",
"MoonrakerCannotConnect": "Moonraker can't connect to Klipper!",
"PowerOn": "Power on",
"PrinterSwitchedOff": "Printer is powered off",
"PrinterSwitchedOffDescription": "The printer is currently powered off and Klipper cannot connect. To power on the printer, click the button below:",
"Restart": "Restart",
"ServiceReports": "{service} reports"
},
Expand Down Expand Up @@ -1006,6 +1009,8 @@
"NavigationStyleDescription": "Change navigation appearance",
"NavigationStyleIconsAndText": "Icons + Text",
"NavigationStyleIconsOnly": "Icons only",
"PowerDeviceName": "Printer power device",
"PowerDeviceNameDescription": "Select which Moonraker power device should be used to power on the printer.",
"Primary": "Primary",
"ShowWebcamInNavigation": "Show Webcam in navigation",
"UiSettings": "UI-Settings"
Expand Down
1 change: 1 addition & 0 deletions src/store/gui/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,7 @@ export const getDefaultState = (): GuiState => {
boolHideUploadAndPrintButton: false,
boolWebcamNavi: false,
navigationStyle: 'iconsAndText',
powerDeviceName: null,
},
view: {
blockFileUpload: false,
Expand Down
1 change: 1 addition & 0 deletions src/store/gui/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ export interface GuiState {
boolHideUploadAndPrintButton: boolean
boolWebcamNavi: boolean
navigationStyle: 'iconsAndText' | 'iconsOnly'
powerDeviceName: string | null
}
view: {
blockFileUpload: boolean
Expand Down

0 comments on commit 9b746f4

Please sign in to comment.