Delphi GUI Predicates
The Delphi GUI Predicates
(DelGUI) are a collection of extended predicates that allow Prolog to directly
access and manipulate Delphi controls. For example, there are predicates
that allow you to draw in paintbox controls and add lines to memo controls.
They are by no means a complete collection, but provide a framework and
useful start that can be easily supplemented with your own predicates.
They are contained in two files in the samples\delphi\delgui directory.
- delgui.pas - The definitions of the extended predicates, that can
be called by the Prolog component of a Delphi application.
- delgui.pro - Higher level predicates built using the extended predicates,
that can also be incorporated in the Prolog components of a Delphi application.
Using DelGUI
To use DelGUI you must perform the following
steps.
- Include delgui.pas in your Delphi project.
- Include delgui.pro in your Prolog project, linking it with your Prolog
code to form a .xpl file which is loaded by the Delphi program.
-
Include the Amzi! Logic Server component in the main form, or some other
convenient place, for the Delphi application.
-
Initialize the Logic Server and DelGUI predicates before loading the application's
Prolog code. (The mainform create is a convenient place to do this.) This
is done using the normal Logic Server Initialization with the added step
of calling DG_Init between the InitLS and LoadXPL functions. DG_Init takes
one argument, which is the Logic Server object.
-
(optional) For each control you want Prolog to access, you should somehow
make the address of that control available to Prolog. One simple way is
to assert Prolog facts with a symbolic name for each control and its address.
-
Close the Logic Server when done. (The mainform destroy is a convenient
place to do this.)
There is a test project in the samples/delphi/delgui directory that can be used
as a template for building applications that use the Delphi GUI Predicates. It
includes code needed to initialize and start work with the Delphi GUI Predicates
and a one button form that tests to make sure its all connected correctly.
- dgtemp.dpr - The Delphi project for the template application.
- dgmain.pas/dfm - The code and form for the template application.
- dbtemp.pro/ppj/xpl - The source code for the simple Prolog program,
as well as the project that includes it and delgui.pro and the resulting .xpl
file from linking the project.
For step 5 (above) it is convenient to define a function that asserts controls
as dynamic clauses(facts) in the Prolog logicbase. Those asserted facts can then be used by
the Prolog logic to pick up the address of the control it needs to manipulate.
The following is an example of such a function. It takes three arguments,
being 1) the type of the control, 2) the name of the control and 3) the
address of the control. It asserts these as the three arguments of a Prolog
fact dyn_control/3.
procedure TTest.AssertControl(ctype, name: string; cntl: TControl);
var
t: TTerm;
c: TControl;
begin
c := cntl;
LSEng.MakeFA(t, 'dyn_control', 3);
LSEng.UnifyAtomArg(t, 1, ctype);
LSEng.UnifyAtomArg(t, 2, name);
LSEng.UnifyArg(t, 3, dADDR, @cntl);
LSEng.Asserta(t);
end;
Flow of Control
Issue
The Delphi GUI predicates enable
you to apply Prolog reasoning to the layout and display of the user interface.
This can lead to some interesting applications, but there are some design
issues that need to be addressed for a tight integration between Prolog
and Delphi.
If you wish to have Prolog query the user, there are two approaches.
-
You can have Prolog call an extended predicate and then start a new Windows
message pump which waits for the answer and returns when it gets it. Unless
necessary, this approach is probably better avoided.
-
You can have Prolog call an extended predicate which puts up the question,
control or whatever and then simply returns. In this case you have an OnX
function in Delphi that waits for a response, and when it gets it, it calls
Prolog. This is a little more complex in the code interaction, because
you need to split the Prolog logic for asking questions and receiving answers,
but is a cleaner separation of responsibilities.
Extended Predicates
These are the predicates defined
in delgui.pas. The majority of them take, as the first argument, the address of
the control to be manipulated. This argument is indicated by CA in following text.
-
showmessage(Msg)
-
Displays the message Msg in a message box. Msg is a string. To display
other Prolog terms, see w_message in the Prolog tools.
The predicates beginning with draw_ apply to canvas controls.
-
draw_lineto(CA, X, Y)
-
Draw a line to X, Y.
-
draw_moveto(CA, X, Y)
-
Move the pen to X, Y.
-
draw_textout(CA, X, Y, S)
-
Write the string S at position X, Y.
-
draw_textheight(CA, S, IH)
-
Unify IH with the height of character string S.
-
draw_textwidth(CA, S, IW)
-
Unify IW with the width of character string S.
-
draw_cliprect(CA, Top, Left, Bot, Rt)
-
Unify the four arguments with the coordinates of the clipping rectangle.
-
draw_rectangle(CA, Top, Left, Bot, Rt)
-
Draw a rectangle using the coordinates.
-
draw_ellipse(CA, Top, Left, Bot, Rt)
-
Draw an ellipse in the coordinates.
-
draw_pen(CA, SColor, IWidth)
-
Set the pen to the color named in the string SColor and to the width specified
in IWidth.
-
draw_font(CA, SFont, SColor, ISize)
-
If the arguments are variables, then they are unified with the current
font name, color and size. If they are bound terms, the current font name,
color and size are set to the new values.
-
draw_brush(CA, SColor, SStyle)
-
Set the brush to the color and style specified.
The predicates beginning with memo_ apply to memo controls.
-
memo_add(CA, S)
-
Add the string S to the memo.
-
memo_lines(CA, ILine, S)
-
Unify string S with memo line number ILine.
-
memo_delete(CA, ILine)
-
Delete memo line ILine.
The predicates beginning with edit_ apply to edit controls
-
edit_text(CA, S)
-
If S is a variable, unify it with the text in the edit control, otherwise
set the text to the bound string S.
-
edit_modified(CA)
-
If the control is modified, returns true, otherwise returns false.
The predicates beginning with radio_ apply to radio button controls.
-
radio_group(CA, ItemList)
-
Add each of the items in ItemList to the radio group.
-
radio_selected(CA, I)
-
If I is a variable, unify it with the radio group item index. It if is
bound, then set the radio group index to it.
The predicates beginning with ctrl_ apply to any control.
-
ctrl_visible(CA, I)
-
If I = 0, set the control's visible property to false, otherwise set it
to true.
The following functions integrate Prolog with other third party Delphi
components.
Predicates beginning with graph_ apply to SciGraph controls. The SciGraph
component is available from Pierre Mertz. Information about SciGraph is
available from the web site: http://www.ee.princeton.edu/~phmertz/scigraph/scigraph.html
You'll find the SciGraph functions are commented out in the source code.
If you install SciGraph, then you can uncomment those functions and add
SciGraph to the 'uses' list.
-
graph_function(CA, Start, Stop, Inc, EQ)
-
This function maps a Prolog symbolic equation, such as f(X) = X**2 to a
scientific graph. EQ is the equation and Start, Stop and Inc delimit the
range of X values to be plotted. (It makes use of internal predicates defined
in DELGUI.PRO.)
Prolog Predicates
-
w_message(T)
-
Converts T to a string and then call showmessage. This predicate illustrates
how a simple Prolog front-end can make an extended predicate easier to
work with.
-
set_equation(SEq), paint_equation(CA)
-
These two predicates implement the complex function of displaying a symbolic
Prolog equation in a format as it might appear in a text book, that is,
with fractions written above and below and square roots written with full
radical symbols. They use two parts because paint boxes are not drawn directly,
but rather are only drawn when the Delphi program receives the OnPaint
command for the paint box control. paint_equation/1 does the painting.
See the source codes for details, as this predicate illustrates the power
of Prolog for graphical layout.
Sample
See the sample in samples/delphi/eq for an illustration
of using DelGUI and in particular the equation display function.
Copyright ©1987-2011 Amzi! inc. All Rights Reserved.
Amzi! is a registered trademark and Logic Server is a trademark
of Amzi! inc.