The second approach is to have Prolog be the master and Tk the slave. This is suitable when heavy processing is done in the Prolog code and Tk is used mostly to display the state of the computation in some way rather than as a traditional GUI; i.e. during computation Prolog often makes calls to Tk to show some state, but the user rarely interacts with the application.
In our Prolog+Tcl/Tk setting this involves the following steps:
tcl_evalto update the Tk display
Again it its purest form, Prolog makes calls to Tcl, but Tcl does not
make calls to Prolog. The result of a call to Tcl is either passed back
Result variable of a
A good example of this is the Tcl/Tk display for our 8-queens problem, that we saw earlier; see Queens Display.
We will now fill out the example by presenting the Prolog master part. The Prolog program calculates a solution to the 8-queens problem and then makes calls Tcl/Tk to display the solution. In this way Tcl/Tk is the slave, just being used as a simple display.
We have already seen the Tcl/Tk part, but here is the Prolog part for generating a solution and displaying it:
:- use_module(library(tcltk)). :- use_module(library(lists)). go :- tk_new([name('SICStus+Tcl/Tk - Queens')], Tcl), tcl_eval(Tcl, 'source queens.tcl', _), tk_next_event(Tcl, Event), queens(8, Qs), reverse(L, LR), tcl_eval(Tcl, [show_solution, br(LR)], _), fail. go. queens(N, Qs) :- range(1, N, Ns), queens(Ns, , Qs). queens(UnplacedQs, SafeQs, Qs) :- select(Q, UnplacedQs, UnplacedQs1), \+ attack(Q, SafeQs), queens(UnplacedQs1, [Q|SafeQs], Qs). queens(, Qs, Qs). attack(X, Xs) :- attack(X, 1, Xs). attack(X, N, [Y|_Ys]) :- X is Y + N. attack(X, N, [Y|_Ys]) :- X is Y - N. attack(X, N, [_Y|Ys]) :- N1 is N + 1, attack(X, N1, Ys). range(M, N, [M|Ns]) :- M < N, M1 is M + 1, range(M1, N, Ns). range(N, N, [N]). :- go.
All this simply does it to create a Tcl/Tk interpreter, load the Tcl
code for displaying queens into it, generate a solution to the 8-queens
problem as a list of integers, and then calls
the Tcl interpreter to display the solution. At the end of first
go/0 is a fail clause that turns
go/0 into a failure driven loop. The result of this is that the
program will calculate all the solutions to the 8-queens problem,
displaying them rapidly one after the other, until there are none left.