Tcl/Tk 的例子?

发布于 2024-07-06 19:20:34 字数 241 浏览 6 评论 0原文

Tcl/Tk 是编写小型 GUI 脚本的简单方法。

谁能给出一个带有按钮文本小部件的好例子。 当按下按钮时,应该执行 shell 命令并将输出通过管道传输到 text 小部件。

如果您还有其他漂亮且干净的示例来完成有用的任务,请也添加它们。

Tcl/Tk is a simple way to script small GUIs.

Can anyone give a nice example with a button and a text widget. When the button is pressed should a shell command be executed and the output piped to the text widget.

If you have other nice and clean examples for useful tasks, please add them too.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

野心澎湃 2024-07-13 19:20:34

这是使用 fileevents 的更完整的示例。 这将一直自动滚动。 出于可用性目的,您可能只想在文本底部可见时自动滚动(即:如果用户没有移动滚动条),但我将把它作为练习留给读者,以保留这个已经很长的示例不再变得更长。

package require Tk

proc main {} {
    if {[lsearch -exact [font names] TkDefaultFont] == -1} {
        # older versions of Tk don't define this font, so pick something
        # suitable
        font create TkDefaultFont -family Helvetica -size 12
    }
    # in 8.5 we can use {*} but this will work in earlier versions
    eval font create TkBoldFont [font actual TkDefaultFont] -weight bold

    buildUI
}

proc buildUI {} {
    frame .toolbar
    scrollbar .vsb -command [list .t yview]
    text .t \
        -width 80 -height 20 \
        -yscrollcommand [list .vsb set] \
        -highlightthickness 0
    .t tag configure command -font TkBoldFont
    .t tag configure error   -font TkDefaultFont -foreground firebrick
    .t tag configure output  -font TkDefaultFont -foreground black

    grid .toolbar -sticky nsew
    grid .t .vsb  -sticky nsew
    grid rowconfigure . 1 -weight 1
    grid columnconfigure . 0 -weight 1

    set i 0
    foreach {label command} {
        date     {date} 
        uptime   {uptime} 
        ls       {ls -l}
    } {
        button .b$i -text $label -command [list runCommand $command]
        pack .b$i -in .toolbar -side left
        incr i
    }
}

proc output {type text} {
    .t configure -state normal
    .t insert end $text $type "\n"
    .t see end
    .t configure -state disabled
}

proc runCommand {cmd} {
    output command $cmd
    set f [open "| $cmd" r]
    fconfigure $f -blocking false
    fileevent $f readable  [list handleFileEvent $f]
}

proc closePipe {f} {
    # turn blocking on so we can catch any errors
    fconfigure $f -blocking true
    if {[catch {close $f} err]} {
        output error $err
    }
}

proc handleFileEvent {f} {
    set status [catch { gets $f line } result]
    if { $status != 0 } {
        # unexpected error
        output error $result
        closePipe $f

    } elseif { $result >= 0 } {
        # we got some output
        output normal $line

    } elseif { [eof $f] } {
        # End of file
        closePipe $f

    } elseif { [fblocked $f] } {
        # Read blocked, so do nothing
    }
}


main

Here's a more complete example using fileevents. This will auto-scroll all the time. For usability purposes you probably only want to auto-scroll if the bottom of the text is visible (ie: if the user hasn't moved the scrollbar) but I'll leave that as an exercise for the reader to keep this already long example from getting any longer.

package require Tk

proc main {} {
    if {[lsearch -exact [font names] TkDefaultFont] == -1} {
        # older versions of Tk don't define this font, so pick something
        # suitable
        font create TkDefaultFont -family Helvetica -size 12
    }
    # in 8.5 we can use {*} but this will work in earlier versions
    eval font create TkBoldFont [font actual TkDefaultFont] -weight bold

    buildUI
}

proc buildUI {} {
    frame .toolbar
    scrollbar .vsb -command [list .t yview]
    text .t \
        -width 80 -height 20 \
        -yscrollcommand [list .vsb set] \
        -highlightthickness 0
    .t tag configure command -font TkBoldFont
    .t tag configure error   -font TkDefaultFont -foreground firebrick
    .t tag configure output  -font TkDefaultFont -foreground black

    grid .toolbar -sticky nsew
    grid .t .vsb  -sticky nsew
    grid rowconfigure . 1 -weight 1
    grid columnconfigure . 0 -weight 1

    set i 0
    foreach {label command} {
        date     {date} 
        uptime   {uptime} 
        ls       {ls -l}
    } {
        button .b$i -text $label -command [list runCommand $command]
        pack .b$i -in .toolbar -side left
        incr i
    }
}

proc output {type text} {
    .t configure -state normal
    .t insert end $text $type "\n"
    .t see end
    .t configure -state disabled
}

proc runCommand {cmd} {
    output command $cmd
    set f [open "| $cmd" r]
    fconfigure $f -blocking false
    fileevent $f readable  [list handleFileEvent $f]
}

proc closePipe {f} {
    # turn blocking on so we can catch any errors
    fconfigure $f -blocking true
    if {[catch {close $f} err]} {
        output error $err
    }
}

proc handleFileEvent {f} {
    set status [catch { gets $f line } result]
    if { $status != 0 } {
        # unexpected error
        output error $result
        closePipe $f

    } elseif { $result >= 0 } {
        # we got some output
        output normal $line

    } elseif { [eof $f] } {
        # End of file
        closePipe $f

    } elseif { [fblocked $f] } {
        # Read blocked, so do nothing
    }
}


main
撕心裂肺的伤痛 2024-07-13 19:20:34

一些建议:

要将输出附加到 text 小部件,您可以使用索引 end,而不是指定第 999999 行,它指的是最后一个换行符之后的位置。 例如,

.main insert end "$x\n"

要在命令输出时使文本滚动,请使用 see 命令。 例如,在附加到 .main 文本小部件之后,

.main see end

您可能还需要考虑使用 fileevent 命令异步抓取命令输出。

Some suggestions:

To append the output to the text widget, instead of specifying line 999999, you can use the index end, which refers to the position just after the last newline. For example,

.main insert end "$x\n"

To have the text scroll as the command is outputting, use the see command. For example, after appending to the .main text widget

.main see end

You may also want to consider grabbing the command output asynchronously, by using the fileevent command.

只是在用心讲痛 2024-07-13 19:20:34

我可以开始...请提出改进​​建议。 即我希望它在命令输出时滚动

#!/usr/bin/wish

proc push_button {} {
    put_text
    .main see end
}

proc put_text {} {
  set f [ open "| date" r]
  while {[gets $f x] >= 0} {
    .main insert end "$x\n"    
  }
  catch {close $f}
}

button .but -text "Push Me" -command "push_button"
text .main -relief sunken -bd 2 -yscrollcommand ".scroll set"
scrollbar .scroll -command ".main yview"

pack .but
pack .main -side left -fill y
pack .scroll -side right -fill y

I can give a start...please suggest improvements. I.e I'd like it to scroll as the command is outputting

#!/usr/bin/wish

proc push_button {} {
    put_text
    .main see end
}

proc put_text {} {
  set f [ open "| date" r]
  while {[gets $f x] >= 0} {
    .main insert end "$x\n"    
  }
  catch {close $f}
}

button .but -text "Push Me" -command "push_button"
text .main -relief sunken -bd 2 -yscrollcommand ".scroll set"
scrollbar .scroll -command ".main yview"

pack .but
pack .main -side left -fill y
pack .scroll -side right -fill y
眼角的笑意。 2024-07-13 19:20:34

wiki.tcl.tk 是适合各种示例

wiki.tcl.tk is good website for all kinds of examples

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文