cl-plplot-0.6.0/clg-plot/0000755000175000017500000000000011427546034015224 5ustar hbabcockhbabcockcl-plplot-0.6.0/clg-plot/clg-plot.lisp0000644000175000017500000000701011133143727017630 0ustar hbabcockhbabcock;;; ;;; Combining clg and cl-plplot to make a nice plotting window. ;;; (defpackage :clg-plot (:use :common-lisp :clg) (:export :new-clg-plot)) (in-package :clg-plot) (defun render-the-plot (cairo-context cl-plplot-window width height) "Calls cl-plplot to redraw the plot in the new window." (cl-plplot:render cl-plplot-window "extcairo" :size-x width :size-y height :external-pointer cairo-context)) (defun create-drawing-function (drawing-area cl-plplot-window) "Defines the drawing function that is used to redraw the plot." #'(lambda () (gdk:with-cairo-context (cr (widget-window drawing-area)) (multiple-value-bind (width height) (widget-get-size-allocation drawing-area) (cairo:set-source-color cr 1.0 1.0 1.0) (cairo:rectangle cr 0.0 0.0 width height) (cairo:fill cr) (render-the-plot (gffi::foreign-location cr) cl-plplot-window width height))))) (defun new-clg-plot (cl-plplot-window &key (title "clg-plot") (width-request 480) (height-request 320)) "Creates a window containing the plot." (let* ((menu-bar (make-instance 'menu-bar)) (graph-area (make-instance 'drawing-area)) (main-window (make-instance 'window :title title :name "clg_plot_window" :width-request width-request :height-request height-request :visible t)) (drawing-function (create-drawing-function graph-area cl-plplot-window))) ; menu setup (let ((menu (make-instance 'menu-item :label "File")) (sub-menu (make-instance 'menu))) (let ((redraw-item (make-instance 'menu-item :label "Redraw")) (quit-item (make-instance 'menu-item :label "Quit"))) (signal-connect redraw-item 'activate #'(lambda () (funcall drawing-function))) (signal-connect quit-item 'activate #'(lambda () (widget-destroy main-window))) (menu-shell-append sub-menu redraw-item) (menu-shell-append sub-menu quit-item)) (setf (menu-item-submenu menu) sub-menu) (menu-shell-append menu-bar menu)) ; graphics setup (signal-connect graph-area 'expose-event #'(lambda (event) (declare (ignore event)) (funcall drawing-function))) ; window setup (make-instance 'v-box :parent main-window :child (list menu-bar :expand nil :fill nil) :child graph-area) (signal-connect main-window 'destroy #'(lambda () (setf main-window nil))) (widget-show-all main-window))) (clg-init) ;;;; ;;;; Copyright (c) 2008 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/clg-plot/clg-plot.asd0000644000175000017500000000272211133143727017435 0ustar hbabcockhbabcock;;; ;;; Combining clg and cl-plplot to create a more friendly plotting environment. ;;; ;;; hazen 4/08 ;;; (defpackage :clg-plot.system (:use :cl :asdf)) (in-package :clg-plot.system) (defsystem clg-plot :version "0.1" :author "Hazen Babcock" :components ((:file "clg-plot")) :depends-on (:gtk :cl-plplot)) ;;;; ;;;; Copyright (c) 2008 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/clg-plot/test.lisp0000644000175000017500000000353711133143727017100 0ustar hbabcockhbabcock;;; ;;; Test clg-plot. ;;; (defpackage :test (:use :common-lisp :clg-plot)) (in-package :test) (defun my-make-vector (dim init-fn) (let ((vec (make-array dim :initial-element 0.0 :element-type 'float))) (dotimes (i dim) (setf (aref vec i) (funcall init-fn i))) vec)) (defun new-plot-window (&optional name) (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (cl-plplot:new-x-y-plot x y)) (w (cl-plplot:basic-window))) (cl-plplot:add-plot-to-window w p) (if name (new-clg-plot w :title name) (new-clg-plot w)))) (defun multi-window (n) (dotimes (i n) (new-plot-window (format nil "Plot ~A" i)))) ;;;; ;;;; Copyright (c) 2008 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/cl-plplot.asd0000644000175000017500000001226311427544550016107 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; ;;;; cl-plplot system declaration ;;;; ;;;; hazen 6/10 ;;;; (in-package #:cl-user) (defpackage #:cl-plplot.asdf (:use #:cl #:asdf)) (in-package #:cl-plplot.asdf) (defsystem #:cl-plplot :name "cl-plplot" :author "Hazen Babcock " :version "0.5.0" :licence "MIT" :description "Interface to the PLplot Scientific Plotting Library" :components ((:module :src/system :components ((:file "loadlib") (:file "defcfun" :depends-on ("loadlib")) (:file "misc" :depends-on ("defcfun")) (:file "api" :depends-on ("misc")))) (:module :src/window :components ((:file "package") (:file "utility-functions" :depends-on ("package")) (:file "macros" :depends-on ("package")) (:file "classes" :depends-on ("macros")) (:file "color-table" :depends-on ("classes")) (:file "extended-color-table" :depends-on ("classes")) (:file "text-item" :depends-on ("classes")) (:file "text-label" :depends-on ("text-item")) (:file "axis-label" :depends-on ("text-item")) (:file "axis" :depends-on ("axis-label")) (:file "plot" :depends-on ("classes")) (:file "x-y-plot" :depends-on ("plot")) (:file "bar-graph" :depends-on ("plot")) (:file "contour-plot" :depends-on ("plot")) (:file "3D-mesh" :depends-on ("plot")) (:file "surface-plot" :depends-on ("3D-mesh")) (:file "window" :depends-on ("plot" "axis" "color-table" "extended-color-table")) (:file "3D-window" :depends-on ("window"))) :depends-on (:src/system))) :depends-on (:cffi)) (defsystem #:plplot-examples :name "plplot-examples" :author "Hazen Babcock " :version "0.1.0" :licence "MIT" :description "PLplot standard examples in Lisp" :components ((:module :src/examples :components ((:file "plplot-examples") (:file "x01l" :depends-on ("plplot-examples")) (:file "x02l" :depends-on ("plplot-examples")) (:file "x03l" :depends-on ("plplot-examples")) (:file "x04l" :depends-on ("plplot-examples")) (:file "x05l" :depends-on ("plplot-examples")) (:file "x06l" :depends-on ("plplot-examples")) (:file "x07l" :depends-on ("plplot-examples")) (:file "x08l" :depends-on ("plplot-examples")) (:file "x09l" :depends-on ("plplot-examples")) (:file "x10l" :depends-on ("plplot-examples")) (:file "x11l" :depends-on ("plplot-examples")) (:file "x12l" :depends-on ("plplot-examples")) (:file "x13l" :depends-on ("plplot-examples")) (:file "x14l" :depends-on ("plplot-examples")) (:file "x15l" :depends-on ("plplot-examples")) (:file "x16l" :depends-on ("plplot-examples")) (:file "x17l" :depends-on ("plplot-examples")) (:file "x18l" :depends-on ("plplot-examples")) (:file "x19l" :depends-on ("plplot-examples")) ; (:file "x20l" :depends-on ("plplot-examples")) ; Requires cl-png (:file "x21l" :depends-on ("plplot-examples")) ; SBCL specific NAN handling? (:file "x22l" :depends-on ("plplot-examples")) (:file "x23l" :depends-on ("plplot-examples")) (:file "x24l" :depends-on ("plplot-examples")) ; Requires unicode handling. (:file "x25l" :depends-on ("plplot-examples")) (:file "x26l" :depends-on ("plplot-examples")) (:file "x27l" :depends-on ("plplot-examples")) (:file "x28l" :depends-on ("plplot-examples")) (:file "x29l" :depends-on ("plplot-examples")) ; Can trigger floating point exceptions. (:file "x30l" :depends-on ("plplot-examples")) (:file "x31l" :depends-on ("plplot-examples")) (:file "x32l" :depends-on ("plplot-examples"))))) :depends-on (:cl-plplot)) cl-plplot-0.6.0/doc/0000755000175000017500000000000011427546034014250 5ustar hbabcockhbabcockcl-plplot-0.6.0/doc/cl-plplot-manual.texinfo0000644000175000017500000014631210760161017021027 0ustar hbabcockhbabcock\input texinfo @c -*- Mode: Texinfo; Mode: auto-fill -*- @c %**start of header @setfilename cl-plplot.info @settitle Cl-plplot User Manual @syncodeindex tp cp @syncodeindex fn cp @c======================================================================= @copying Copyright @copyright{} 2008 Hazen P. Babcock @quotation Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the ``Software''), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. @sc{The software is provided ``as is'', without warranty of any kind, express or implied, including but not limited to the warranties of merchantability, fitness for a particular purpose and noninfringement. In no event shall the authors or copyright holders be liable for any claim, damages or other liability, whether in an action of contract, tort or otherwise, arising from, out of or in connection with the software or the use or other dealings in the software.} @end quotation @end copying @titlepage @title Cl-plplot User Manual @vskip 0pt plus 1filll February, 2008 @page @vskip 0pt plus 1fill @insertcopying @end titlepage @c======================================================================= @menu * Introduction:: * Installation:: * The Low Level Interface to PLplot:: * The High Level Plotting Package:: * Index:: @end menu @c======================================================================= @node Introduction @chapter Introduction Cl-plplot provides a CFFI based interface to the PLplot graphics library. The PLplot graphics library supports the drawing of many different types of 2D and 3D graphs using a large variety of output devices including X11, postscript and png. PLplot can also be used to make scaled drawing, diagrams, etc... At present, cl-plplot consists of two packages, one is low-level interface to the PLplot library and the other is high-level plotting interface that attempts to make using PLplot with Lisp easier. It has been tested on OS-X and debian linux with SBCL. Since it interfaces to the PLplot library using CFFI, it should work with any combination of lisp implementation and operating system that is supported by CFFI. @c======================================================================= @node Installation @chapter Installation Cl-plplot depends on a working installation of the PLplot plotting library. This is available as a debian package, but it is also not too hard to compile from source on most systems. You will need PLplot version 5.8.0 or later. Once you have installed the PLplot library cl-plplot will hopefully not have any trouble finding the library. If you do encounter difficulties with cl-plplot finding the PLplot library, then the you will probably need to edit the function load-libraries in /cl-plplot/src/system. All that should be necessary is to provide the appropriate path to the library file 'libplplotd'. @c======================================================================= @node The Low Level Interface to PLplot @chapter The Low Level Interface to PLplot @section Introduction The low level interface @code{:cl-plplot-system} provides both 'direct' and 'wrapped' access to the functions in the PLplot library. What this means is that each of the functions in the PLplot library is available in two ways. The 'direct' form expects that all arguments are in a form appropriate for handing off to the C library function. In cases where the C function returns an array or a string it will be returned as C pointer. On the other hand, the 'wrapped' form will automatically convert Lisp variables to the appropriate C variables, fill in any array size arguments and then call the 'direct' form. In the case where the C function returns an array or a string the 'wrapped' form will automatically convert this into the appropriate Lisp type. Furthermore, the 'wrapped' form takes care of allocating and deallocating the necessary memory to make the C function call. The 'wrapped' form is recommended for general use, but the 'direct' form is also available in situations where speed may be important or you are already using C pointers and do not want to pay the overhead of converting them back and forth to Lisp variables. @section Example (the PLplot arrows function) @lisp (defcfun ("plarrows" c-plarrows) :void (u *plflt) (v *plflt) (x *plflt) (y *plflt) (n plint) (scale plflt) (dx plflt) (dy plflt)) (defun plarrows (u v x y scale dx dy) (let ((c-u (make-ptr u :double #'(lambda (x) (coerce x 'double-float)))) (c-v (make-ptr v :double #'(lambda (x) (coerce x 'double-float)))) (c-x (make-ptr x :double #'(lambda (x) (coerce x 'double-float)))) (n (length y)) (c-y (make-ptr y :double #'(lambda (x) (coerce x 'double-float))))) (unwind-protect (c-plarrows c-u c-v c-x c-y (funcall #'(lambda (x) (round x)) n) (funcall #'(lambda (x) (coerce x 'double-float)) scale) (funcall #'(lambda (x) (coerce x 'double-float)) dx) (funcall #'(lambda (x) (coerce x 'double-float)) dy)) (progn (foreign-free c-u) (foreign-free c-v) (foreign-free c-x) (foreign-free c-y))))) @end lisp @subheading Notes @itemize @item The name of the PLplot function as defined in the PLplot manual is used for the 'wrapped' form and the name of the 'direct' has @code{c-} appended onto the front. This convention is followed for most PLplot functions. @item The function @code{make-ptr} handles the creation of a C array from a Lisp vector. @item The argument @code{n} required by PLplots arrows function is automatically determined from the length of the vector y and does not need to be passed in. @item The call to the PLplot library function is wrapped with @code{unwind-protect} so that if the C function fails the memory occupied by @code{c-u}, @code{c-v}, @code{c-x} and @code{c-y} is still freed. @end itemize @section Exceptions @itemize @item There are a few exceptions to the above naming conventions for the 'direct' and 'wrapped' forms. Typically these occur for functions that have very complicated arguments, for example functions that required callbacks. When in doubt the best approach is probably to peruse @code{src/system/api.lisp} where all of the PLplot functions are defined. @item Not all of the PLplot library functions are available in cl-plpot. Some were deemed to be too esoteric, or better handled by an equivalent Lisp function. However, if you find a function that you feel should be supported please let me know. @end itemize @section Supported PLplot Functions The current best reference is the manual that comes with PLplot. TODO: a list of the supported PLplot functions and their arguments. @c======================================================================= @node The High Level Plotting Package @chapter The High Level Plotting Package @section Introduction The high level interface @code{:cl-plplot} tries to make PLplot a little more Lispy using a CLOS based approach. You create window objects, then associate axis objects, text objects and plot objects to the window objects. When everything is set you call the @code{render} method on the window object to display the plot using the display device of your choice. This approach was adopted in part to make graphing easier in a multi-threaded environment. The PLplot library supports drawing multiple graphs simultaneously using the concept of plot streams. However using these in a multi-threaded environment would be a challenge as just about every call to a PLplot library function would have to prefaced with a function call to set the correct stream. As all the calls to the PLplot library are gauranteed to happen during @code{render} one only needs to threadlock around this method to avoid confusing PLplot. @section The Object Layout @example window object |--axis object (1 for the x axis, 1 for the y-axis) | |--axis-label object (0 or more per axis object) | |--text-item object (1 per axis-label object) |--axis-label object (0 or more) |--plot object (0 or more) |--text-label object (0 or more) | |--text-item object (1 per text-label object) |--color-table object (1 per window) |--extended-color-table object (1 per window) @end example Note that this is @strong{NOT} an inheritance diagram. Each of the above objects is a distinct entity. @section Object Definitions @subheading The Window Object This is the main object without which it is impossible to actually create a plot. It always contains references to two axis objects, one for the x-axis and one for the y-axis. It can also contain references to additional axis-label objects that might be used to provide a title for the plot as well as any other axis labeling that is needed, references to plot objects that will be drawn in the window and references to text labels to draw in the window. When you call @code{render} on a window object it determines the coordinate system and size of the plotting rectangle in which the plots will appear, then calls the @code{render} methods of the axis-label, text-label and plot objects to create the final plot. @subheading The 3D-Window Object This is the main window object for drawing 3D plots. At present these include surface mesh plots (3D-mesh) and solid surface plots (surface-plot). This object inherits from the Window object and adds a z-axis as well as altitude and azimuthal viewing angles. @subheading The Axis Object This object is used to set minimum and maximum values to plot in the window, as well as specifying how to label the axis, major tick interval, minor tick interval, ticks, grid, ... @subheading The Axis-label Object This object is used to draw text relative to one of the sides of the plotting rectangle. It specifies where to draw the text relative to one of the edges of the rectangle as well as in what orientation. @subheading The 3D-axis-label Object This object inherits from the axis-label object. It uses a different convention for specifying which axis to label. @subheading The Text-label Object This is like the axis-label object except that it is typically drawn inside the plotting rectangle and its location is determined by the plot coordinate system. @subheading The 3D-text-label Object This object inherits from the text-label objects. It is used to draw '3D' text and as such requires a number of additional parameters to specify how to draw the text. @subheading The Text-item Object This object is used to actually draw the text. It specifies font, size, color, superscript, ... @subheading The Plot Object This object is used to convert data into a plot. In its most generic form it contains two functions, one that returns its preference for the x and y (and z if relevant) ranges of the window coordinate system and another that draws the object in the current window using @code{:cl-plplot-system} function calls. Specialized forms currently include x-y-plot, bar-graph and contour-plot. @subheading The 3D Plot Object This object inherits from the plot object. Specialized forms currently include the 3D-mesh and surface-plot. @subheading The Color-table Object This object handles the use of PLplot's color map 0. Typically it will consist of 16 colors, each of with contains red, green and blue values as well as symbol (like @code{:blue}) that you can use to refer to the color. This color table is used by PLplot to draw essentially all of the 'basic' items, i.e. lines, text, axises. You can have more then 16 colors but not all of the graphics devices will handle that many colors. Some in fact may only handle black and white. @subheading The Extended-color-table Object This object handles the use of PLplot's color map 1. Typically this color table will contain anywhere between 128 to 256 different colors, though, again, not all graphics devices will handle so many colors. It used for shading plots, such as contour plots, where it is often desirable to have continuous range of colors rather than a few blocky colors. @section Examples Note: These are also available in @code{src/examples/window-examples.lisp}. @subheading X versus Y plots @lisp (defun x-y-plot () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y)) (w (basic-window))) (add-plot-to-window w p) (render w "xwin"))) @end lisp The vectors x and y are created using the function @code{y = x^2}. A x-y-plot object is then created to plot the vector x versus the vector y. Finally a window object is created in which the x-y-plot object p can be plotted. The x-y-plot object p is added to the window w by the function @code{add-plot-to-window}. Then the window is drawn by calling the @code{render} method and specifying what PLplot graphics device to use for the graphical output ('xwin' is the X11 graphics device). @subheading Bar Graphs @lisp (defun bar-graph () (let* ((y (my-make-vector 10 #'(lambda(x) (* (* 0.2 x) (* 0.2 x))))) (b (new-bar-graph nil y :fill-colors (vector :grey))) (w (basic-window))) (add-plot-to-window w b) (render w "xwin"))) @end lisp A vector y is created using the function @code{y = (0.2 * x)^2}. This vector is used to make a bar-graph object in which each of the bars will be filled with the color grey. As in the X versus Y plot example, a window w is created, the bar-graph object b is added to this window and then the window is rendered using the X11 graphics device. @subheading Contour Plots @lisp (defun contour-plot () (let ((c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :x-min 0.0 :x-max 1.0 :y-min 0.0 :y-max 1.0 :fill-type :smooth)) (w (basic-window))) (add-plot-to-window w c) (render w "xwin"))) @end lisp A contour plot object is created from a 2D matrix of data. Additionally the coordinate system of the matrix is specified with @code{:x-min}, @code{:x-max}, @code{:y-min} and @code{:y-max} and the contour plot fill type is specified with @code{:fill-type}. The function @code{my-make-matrix} is defined in @code{src/examples/window-examples.lisp}. @subheading 3D mesh plots @lisp (defun 3d-plot-1 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w "xwin"))) @end lisp A 3D-mesh object is created from a 2D matrix of data. A 3D-window object is created in which to draw the 3D-plot object, with the viewing angle specified by @code{:altitude} and @code{:azimuth}. The plot is added to the window and is then rendered using the X11 graphics device. @subheading 3D surface plots @lisp (defun surface-plot-1 () (let ((c (new-surface-plot nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w "xwin"))) @end lisp This example is essentially the same as the mesh plot example, except that we now create a surface-plot object. @section Cl-plplot Functions in Alphabetical order @subheading add-axis-label-to-axis @cindex add-axis-label-to-axis @subsubheading Argument List (a-axis a-axis-label) @subsubheading Documentation adds a-axis-label to a-axis. @sp 2 @subheading add-color-to-color-table @cindex add-color-to-color-table @subsubheading Argument List (a-color-table new-color) @subsubheading Documentation adds a new color #(r g b :smybol) to the end of a color table. @sp 2 @subheading add-plot-to-window @cindex add-plot-to-window @subsubheading Argument List (a-window a-plot) @subsubheading Documentation add-plot-to-window, adds a-plot to a-window. @sp 2 @subheading add-text-label-to-window @cindex add-text-label-to-window @subsubheading Argument List (a-window a-text-label) @subsubheading Documentation add-text-label-to-window, adds a-text-label to a-window. @sp 2 @subheading backspace @cindex backspace @subsubheading Argument List none. @subsubheading Documentation This (and greek-char, hershey-char, italic-font, normal-font, number-symbol, overline, roman-font, script-font, subscript, superscript, underline and unicode-char) exist to insert PLplot escape sequences into a string. Cl-plplot uses the default PLplot escape character ``#''. @sp 2 @subheading basic-window @cindex basic-window @subsubheading Argument List (&key (x-label x-axis) (y-label y-axis) (title cl-plplot) x-axis-min x-axis-max y-axis-min y-axis-max (background-color *background-color*) (foreground-color *foreground-color*)) @subsubheading Documentation creates a basic window object with ready-to-go axises. @sp 2 @subheading basic-3d-window @cindex basic-3d-window @subsubheading Argument List (&key (x-label x-axis) (y-label y-axis) (z-label z-axis) (title cl-plplot) x-axis-min x-axis-max y-axis-min y-axis-max z-axis-min z-axis-max (altitude 60) (azimuth 30) (background-color *background-color*) (foreground-color *foreground-color*)) @subsubheading Documentation creates a basic 3D window object with ready-to-go axises. @sp 2 @subheading bring-to-front @cindex bring-to-front @subsubheading Argument List (a-window a-plot) @subsubheading Documentation organizes the plots so that a-plot is drawn on top. @sp 2 @subheading default-color-table @cindex default-color-table @subsubheading Argument List none. @subsubheading Documentation returns the default color table. @sp 2 @subheading edit-3D-mesh @cindex edit-3D-mesh @subsubheading Argument List (a-3d-mesh &key line-width line-style line-color grid-type contour-options curtain) @subsubheading Documentation Edits the visual properties of a 3D-mesh plot object. @itemize @bullet @item Set the line width with :line-width (integer, 0 means no line). @item Set the line style with :line-style (integer between 1 and 8). @item Set the line color with :line-color symbol. @item Set the grid type with :grid-type to one of (:gridx, :gridy or :gridxy). @item Set the contour options with :contour-options to one of (:magnitude-contour, :base-contour or :both). @item Set the whether or not display a curtain with :curtain @end itemize @sp 2 @subheading edit-3D-window @cindex edit-3D-window @subsubheading Argument List (a-3d-window &key x-axis y-axis z-axis title foreground-color background-color window-line-width window-font-size viewport-x-min viewport-x-max viewport-y-min viewport-y-max plots text-labels color-table altitude azimuth) @subsubheading Documentation edit-3D-window, edits the visual properties of a 3D-window. @itemize @bullet @item Set x-axis to a new object of type axis with :x-axis. @item Set y-axis to a new object of type axis with :y-axis. @item Set z-axis to a new object of type axis with :z-axis. @item Set title to a new object of type axis-label with :title. @item Set the foreground color with :foreground-color. @item Set the background color with :background-color. @item Set the pen width for drawing the border with :window-line-width. @item Set the font size for the tick labels with :window-font-size. @item Set the location of the left border with :viewport-x-min. @item Set the location of the right border with :viewport-x-max. @item Set the location of the bottom border with :viewport-y-min. @item Set the location of the top border with :viewport-y-max. @item Set :plots to a list of plot objects to change the plots associated with a window. @item Set :text-labels to a list of text-label objects to change the text-labels associated with a window. @item Set :color-table to a new color table object to change the colors of a plot. @item Set the observer altitude in degrees with :altitude. @item Set the observer azimuth in degrees with :azimuth. @end itemize @sp 2 @subheading edit-axis @cindex edit-axis @subsubheading Argument List (a-axis &key axis-min axis-max major-tick-interval minor-tick-number properties) @subsubheading Documentation edit-axis, edits an axis. @itemize @bullet @item set the minimum value with :axis-min. @item set the maximum value with :axis-max. @item set the spacing between major ticks with :major-tick-interval. @item set the spacing between minor ticks with :minor-tick-interval. @item set the properties with :properties. this should be a list containing zero of more of the following symbols: @itemize @space @item :draw - draw axis on both sides of the window. @item :draw-bottom/left - draw axis on the bottom/left side of the window. @item :draw-top/right - draw axis on the top/right side of the window. @item :fixed-point - use fixed point labels. @item :major-tick-grid - draw a grid on the graph at the major ticks. @item :minor-tick-grid - draw a grid on the graph at the minor ticks. @item :invert-ticks - draw ticks inward rather than outwards. @item :log-axis - draw the axis on a log scale. @item :major-tick-labels-above/right - draw the tick labels above/right of the ticks. @item :major-tick-labels-below/left - draw the tick labels below/left of the ticks. @item :minor-ticks - draw minor ticks. @item :major-ticks - draw major ticks. @end itemize @end itemize @sp 2 @subheading edit-axis-label @cindex edit-axis-label @subsubheading Argument List (a-axis-label &key axis-text-item side displacement location orientation) @subsubheading Documentation edit-axis-label, edits a axis-label object. @itemize @bullet @item set axis-text-item to a new object of class text-item with :axis-text-item. @item set which axis to draw the label on with :side. @item set the displacement from the edge of the the graph with :displacement. @item set the location with along the side of the graph with :location. @item set the orientation with (:parallel or :perpendicular) with :orientation. @end itemize @sp 2 @subheading edit-3D-axis-label @cindex edit-3D-axis-label @subsubheading Argument List (a-axis-label &key axis-text-item side displacement location orientation primary/secondary) @subsubheading Documentation edit-3D-axis-label, edits a 3D-axis-label object. @itemize @bullet @item set axis-text-item to a new object of class text-item with :axis-text-item. @item set which axis to draw the label on with :side (:x, :y or :z). @item set the displacement from the edge of the the graph with :displacement. @item set the location with along the side of the graph with :location. @item set the orientation with (:parallel or :perpendicular) with :orientation. @item Set which axis to label (:primary or :secondary) with :primary/secondary @end itemize @sp 2 @subheading edit-bar-graph @cindex edit-bar-graph @subsubheading Argument List (a-bar-graph &key side-by-side line-colors fill-colors line-width filled) @subsubheading Documentation edit-bar-graph, edits the visual properties of a bar-graph. @itemize @bullet @item set whether the bars are plotted side-by-side or on top of each other with :side-by-side. @item set the line colors of the bars with :line-colors. @item set the fill colors of the bars with :fill-colors. @item set the line width of the bars with :line-width. @item set whether or not the bars are filled with :filled. @end itemize @sp 2 @subheading edit-contour-plot @cindex edit-contour-plot @subsubheading Argument List (a-contour-plot &key line-color line-width fill-type fill-colors) @subsubheading Documentation edit-contour-plot, edits the visual properties of a contour plot. @itemize @bullet @item set the line color with :line-color (this should be a color symbol in the current color table). @item set the line width with :line-width (integer, 0 means no line). @item set the fill-type with :fill-type (:none :block :smooth). @item set the fill-colors with :fill-colors (should be a vector of color symbols) @end itemize @sp 2 @subheading edit-surface-plot @cindex edit-surface-plot @subsubheading Argument List (a-surface-plot &key line-width line-style line-color light-source surface-options) @subsubheading Documentation edit-surface-plot, edits the visual properties of a solid surface plot. @itemize @bullet @item Set the line width with :line-width (integer, 0 means no line). @item Set the line style with :line-style (integer between 1 and 8). @item Set the line color with :line-color symbol. @item Move the light-source to a new position with :light-source #(x y z). @item Change the surface-options with :surface-options to a list including zero or more of: @itemize @space @item :faceted @item :base-contours @item :surface-contours @item :curtain @item :magnitude-coloring @end itemize @end itemize @sp 2 @subheading edit-text-item @cindex edit-text-item @subsubheading Argument List (a-text-item &key the-text text-color text-justification font-size) @subsubheading Documentation edit-text-item, edits a text-item object. @itemize @bullet @item set the text with :text. @item set the color of the text with :text-color symbol. @item set the justification with :text-justification (0.0 = left justified, 1.0 = right justified). @item set the font-size with :font-size (relative to the default size). @end itemize @sp 2 @subheading edit-text-label @cindex edit-text-label @subsubheading Argument List (a-text-label &key label-text-item text-x text-y text-dx text-dy) @subsubheading Documentation edit-text-label, edits a text-label object. @itemize @bullet @item set text-item to a new object of class text-item with :label-text-item. @item set the x location of the text with :text-x. @item set the y location of the text with :text-y. @item set dx for drawing text at an angle with :text-dx. @item set dy for drawing text at an angle with :text-dy. @end itemize @sp 2 @subheading edit-3D-text-label @cindex edit-3D-text-label @subsubheading Argument List (a-text-label &key label-text-item text-x text-y text-z text-dx text-dy text-dz text-sx text-sy text-sz) @subsubheading Documentation edit-3D-text-label, edits a 3D-text-label object. @itemize @bullet @item set text-item to a new object of class text-item with :label-text-item. @item set the x location of the text with :text-x. @item set the y location of the text with :text-y. @item set the z location of the text with :text-z. @item set dx for drawing text at an angle with :text-dx. @item set dy for drawing text at an angle with :text-dy. @item set dz for drawing text at an angle with :text-dz. @item set sx for shearing text with :text-sx. @item set sy for shearing text with :text-sy. @item set sz for shearing text with :text-sz. @end itemize @sp 2 @subheading edit-window @cindex edit-window @subsubheading Argument List (a-window &key x-axis y-axis title foreground-color background-color window-line-width window-font-size viewport-x-min viewport-x-max viewport-y-min viewport-y-max plots text-labels color-table) @subsubheading Documentation edit-window, edits a window object. @itemize @bullet @item set x-axis to a new object of type axis with :x-axis. @item set y-axis to a new object of type axis with :y-axis. @item set title to a new object of type axis-label with :title. @item set the foreground color with :foreground-color. @item set the background color with :background-color. @item set the pen width for drawing the border with :window-line-width. @item set the font size for the tick labels with :window-font-size. @item set the location of the left border with :viewport-x-min. @item set the location of the right border with :viewport-x-max. @item set the location of the bottom border with :viewport-y-min. @item set the location of the top border with :viewport-y-max. @item set :plots to a list of plot objects to change the plots associated with a window. @item set :text-labels to a list of text-label objects to change the text-labels associated with a window. @item set :color-table to a new color table object to change the colors of a plot. @end itemize @sp 2 @subheading edit-window-axis @cindex edit-window-axis @subsubheading Argument List (a-window which-axis &key axis-min axis-max major-tick-interval minor-tick-number properties) @subsubheading Documentation allows the user to edit the axis of a window. which-axis should be one of the symbols :x or :y. see edit-axis for a more detailed explanation of the meaning of the different key words. @sp 2 @subheading edit-x-y-plot @cindex edit-x-y-plot @subsubheading Argument List (a-x-y-plot &key line-width line-style symbol-size symbol-type color) @subsubheading Documentation edit-x-y-plot, edits the visual properties of a x-y-plot. @itemize @bullet @item set the line width with :line-width (integer, 0 means no line). @item set the line style with :line-style (integer between 1 and 8). @item set the symbol size with :symbol-size (1.0 is the defaul size, 0.0 means no symbols). @item set the symbol type with :symbol-type (integer or nil to use the default types). @item set the color with :color symbol. @end itemize @sp 2 @subheading get-cursor @cindex get-cursor @subsubheading Argument List (a-window device &key (size-x 600) (size-y 500)) @subsubheading Documentation get the location (in window coordinates) of the next mouse click. in order to do this the window must first be rendered so that the user has something to click on. @sp 2 @subheading greek-char @cindex greek-char @subsubheading Argument List none. @sp 2 @subheading hershey-char @cindex hershey-char @subsubheading Argument List none. @sp 2 @subheading italic-font @cindex italic-font @subsubheading Argument List none. @sp 2 @subheading new-3D-mesh @cindex new-3D-mesh @subsubheading Argument List (data-x data-y data-z &key contour-levels (copy t) (line-width 1) (line-style 1) (line-color *foreground-color*) (grid-type :grid-xy) contour-options curtain) @subsubheading Documentation new-3D-mesh, creates a new 3D mesh (surface) plot object. @itemize @bullet @item data-x specifies the x values of the points in data-z. If data-x is nil then data-z will be plotted against its row index in x. @item data-y specifies the y avlues of the points in data-z. If data-y is nil then data-z will be plotted against its column index in y. @item data-z is a 2D array of z values for the plot. @item contour-levels specifies the levels at which to draw contours, if desired. If this is not specified, default values are chosen. @item If copy is true then copies of data-x, data-y and data-z will be made, otherwise reference will be kept to the original vectors. @item line-width should be an integer line width, or zero if no line is desired @item line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. @item line-color is the color to use for the lines in the plot. @item grid-type should be one of :gridx, :gridy or :gridxy. This specifies whether to draw lines only in x, only in y, or in both dimensions between the data points. @item contour-options should be one of nil, :magnitude-contour, :base-contour or :both. nil - no contours. @itemize @space @item :magnitude-contour - draw contour lines on the plot. @item :base-contour - draw contour lines on the x-y plane below the plot. @item :both - draw both magnitude and base contours. @end itemize @item curtain should be t or nil. This specifies whether to draw a 'curtain' around the edges of the plot." @end itemize @sp 2 @subheading new-3D-window @cindex new-3D-window @subsubheading Argument List (&key x-axis y-axis z-axis title (window-line-width 1.0) (window-font-size *font-size*) (foreground-color *foreground-color*) (background-color *background-color*) (viewport-x-min 0.1) (viewport-x-max 0.9) (viewport-y-min 0.1) (viewport-y-max 0.9) plots text-labels color-table (altitude 60) (azimuth 30)) @subsubheading Documentation new-3D-window, creates and returns a new 3D-window object. @itemize @bullet @item x-axis is a object of type axis. @item y-axis is a object of type axis. @item z-axis is a object of type axis. @item title is a object of type axis-label. @item foreground-color is a color symbol in the current color table. @item background-color is a color symbol in the curretn color table. @item window-line-width is a floating point number specifying the pen width to use when drawing the border & the tick marks. @item window-font-size is the font size to use for the tick mark labels. @item viewport-x-min (0.0 - 1.0) is the location of the left side of the border in the device window. @item viewport-x-max (0.0 - 1.0) is the location of the right side of the border. @item viewport-y-min (0.0 - 1.0) is the location of the bottom side of the border. @item viewport-y-max (0.0 - 1.0) is the location of the top side of the border. @item plots is a list of plot objects. @item text-labels is a list of text-label objects. @item color-table specifies what color table to use. @item altitude specifies the angle by which to rotate the plot around the x axis. @item azimuth specified the angle by which to rotate the plot around the z axis. @end itemize @sp 2 @subheading new-axis @cindex new-axis @subsubheading Argument List (&key axis-min axis-max (major-tick-interval 0) (minor-tick-number 0) (properties *axis-properties*) axis-labels) @subsubheading Documentation new-axis, creates and returns an axis object. @itemize @bullet @item axis-min is the minimum value for the axis. @item axis-max is the maximum value for the axis. @item major-tick-interval is the spacing between major ticks (0 means use plplot default). @item minor-tick-number is the number of minor ticks to put between the major ticks. @item properties is a list of symbols as explained in edit-axis. @item axis-labels is a list of axis-label objects. @end itemize @sp 2 @subheading new-axis-label @cindex new-axis-label @subsubheading Argument List (axis-text-item side displacement &key (location 0.5) (orientation parallel)) @subsubheading Documentation new-axis-label, creates and returns a new axis label. @itemize @bullet @item axis-text-item is a object of type text-item. @item side is one of :top, :bottom, :left or :right. @item displacement specifies the distance from the edge of the graph in units of the default font-size. @item location is the position of the label along the side of the graph (0.0 - 1.0). @item orientation is one :parallel or :perpendicular. @end itemize @sp 2 @subheading new-3D-axis-label @cindex new-3D-axis-label @subsubheading Argument List (axis-text-item side displacement &key (location 0.5) (orientation parallel) (primary/secondary :primary)) @subsubheading Documentation new-3D-axis-label, creates and returns a new 3D axis label. @itemize @bullet @item axis-text-item is a object of type text-item. @item side is one of :x, :y or :z. @item displacement specifies the distance from the edge of the graph in units of the default font-size. @item location is the position of the label along the side of the graph (0.0 - 1.0). @item orientation is one :parallel or :perpendicular. @item primary/secondary is one of :primary or :secondary. This specifies which of two possible choices for each axis should be labeled. @end itemize @sp 2 @subheading new-bar-graph @cindex new-bar-graph @subsubheading Argument List (x data &key bar-widths side-by-side line-colors fill-colors (line-width 1.0) (filled t) (copy t)) @subsubheading Documentation creates a new bar-graph plot object. @itemize @bullet @item x is an array of size (n) specifying the centers of the bars with x[i] < x[i+1]. if x is nil then data will be plotted against its index. @item data should be an array of size (n x m), where m > 0. @item bar-widths should be an array of size (n). it will specify the full width of each bar. defaults are chosen if this is not specified. @item side-by-side is t or nil. it specifies whether to draw the bars on top of each other or next to each other. @item line-colors should be an array of symbols of size (m) specifying colors in the current color table. @item fill-colors should be an array of symbols of size (m) specifying what color to use when filling in the bars. @item line-width is a number specifying how wide of a line to draw around the bar. @item filled specifies whether or not the bars are filled. @item if copy is true, then copies are made of x, data and widths, otherwise references are kept to the original vectors. @end itemize @sp 2 @subheading new-color-table @cindex new-color-table @subsubheading Argument List (&optional rgb-colors) @subsubheading Documentation creates a new color table instance from a vector of rgb triples, which also includes a symbol to refer to the color by. for example: #((0 0 0 :black) (128 128 128 :grey) (255 255 255 :white)). @sp 2 @subheading new-contour-plot @cindex new-contour-plot @subsubheading Argument List (data &key contour-levels (line-color *foreground-color*) (line-width 1) (fill-type none) fill-colors x-min x-max x-mapping y-min y-max y-mapping (copy t)) @subsubheading Documentation creates a new contour plot. @itemize @bullet @item data is a 2d array of z values. @item contour-levels is a 1d vector of floats specifying the levels at which the contours should appear. if this is nil, then default contours are created based on the minimum and maximum values in data. @item line-color is a symbol specifying which color to use in the current color table for the contour lines. @item line-width is an integer specifying what size line to use for the contours (or zero for no line). @item fill-type is one of :none (contours only), :block (a single color between each contour) or :smooth (color varies continously between contours). @item fill-colors is a (optional) vector of colors from the current color table to use when fill-type is :block. @item x-min & y-min specify the location of data(0, 0) in plot coordinates. @item x-max & y-max specify the location of data(max, max) in plot coordinates. @item x-mapping & y-mapping are either 1d vectors or 2d matrices specifying how to map points in data into plot coordinates. If they are 1d vector, then data(i,j) is mapped to [x-mapping(i), y-mapping(j)]. If they are 2d vectors then data(i,j) is mapped to [x-mapping(i,j), y-mapping(i,j)]. They must be used together and both must be the same type & also match the dimensions of data. They will override x-min, y-min, x-max and y-max if they are specified. @end itemize @sp 2 @subheading new-custom-plot-object @cindex new-custom-plot-object @subsubheading Argument List (min-max-function render-function) @subsubheading Documentation allows the user to create their own custom plot object. @itemize @bullet @item min-max-function must be either nil or a function of no arguments that returns the vector #(xmin xmax ymin ymax) that specifies the ideal window size for this object. @item render-function must be a function of one argument that specifies how to render the plot object. generally the rendering will be done with a bunch of calls to functions in the cl-plplot-system module. the current plot number will be passed to this function. @end itemize @sp 2 @subheading new-extended-color-table @cindex new-extended-color-table @subsubheading Argument List (&key control-points (color-table-size 128)) @subsubheading Documentation creates a new extended color table instance from a vector of control points. for example: #((0.0 0.0 0.0 0.0) (1.0 255 255 255)) will create a gray scale color table. see plscmap1l in the plplot documentation for a more thorough explanation. @sp 2 @subheading new-surface-plot @cindex new-surface-plot @subsubheading Argument List (data-x data-y data-z &key contour-levels (copy t) (line-width 1) (line-style 1) (line-color *foreground-color*) light-source surface-options) @subsubheading Documentation Creates a new 3D (solid surface) plot. @itemize @bullet @item data-x specifies the x values of the points in data-z. If data-x is nil then data-z will be plotted against its row index in x. @item data-y specifies the y avlues of the points in data-z. If data-y is nil then data-z will be plotted against its column index in y. @item data-z is a 2D array of z values for the plot. @item contour-levels specifies the levels at which to draw contours, if desired. If this is not specified, default values are chosen. @item If copy is true then copies of data-x, data-y and data-z will be made, otherwise reference will be kept to the original vectors. @item line-width should be an integer line width, or zero if no line is desired @item line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. @item line-color is the color to use for the lines in the plot. @item light-source is a 3 element vector #(x y z) specifying the location of the light source that will illuminate the plot surface. @item surface-options is list containing zero or more of the following symbols: @itemize @space @item :faceted - a network of lines is drawing connecting the points that make up the surface. @item :base-contours - a contour plot is also drawn in the base xy plane. @item :surface-contours - contour levels are drawn on the surface of the plot. @item :curtain - a curtain between the borders of the surface and the base xy plane. @item :magnitude-coloring - the surface is colored according to the z value of the plot. If this is not set then surface is colored according the intensity of the reflected light from light source." @end itemize @end itemize @sp 2 @subheading new-text-item @cindex new-text-item @subsubheading Argument List (the-text &key (text-color *foreground-color*) (text-justification 0.5) (font-size *font-size*)) @subsubheading Documentation new-text-item, creates and returns a new text item. @itemize @bullet @item text is a string specifying the text. @item text-color is a symbol specifying the text color. @item text-justification specifies how to center the string relative to its @item reference point. 0.0 - 1.0, where 0.5 means the string is centered. @item font-size sets the fontsize relative to the default font size. @end itemize @sp 2 @subheading new-text-label @cindex new-text-label @subsubheading Argument List (label-text-item text-x text-y &key (text-dx 0.0) (text-dy 0.0)) @subsubheading Documentation new-text-label, creates and returns a new text-label object. @itemize @bullet @item text-item should be an object created by new-text-item. @item text-x specifies the x location of the text reference point (in window coordinates). @item text-y specifies the y location of the text reference point. @item text-dx and text-dy specify the location of a second reference point (in window coordinates) the text is drawn along a line connecting (text-x,text-y) and (text-x + text-dx, text-y + text-dy). @end itemize @sp 2 @subheading new-3D-text-label @cindex new-3D-text-label @subsubheading Argument List (label-text-item text-x text-y text-z &key (text-dx 0.0) (text-dy 0.0) (text-dz 0.0) (text-sz 0.0) (text-sz 0.0) (text-sz 0.0)) @subsubheading Documentation new-3D-text-label, creates and returns a new 3D-text-label object. @itemize @bullet @item text-item should be an object created by new-text-item. @item text-x specifies the x location of the text reference point (in window coordinates). @item text-y specifies the y location of the text reference point. @item text-z specifies the z location of the text reference point. @item text-dx, text-dy and text-dz specify the location of a second reference point (in window coordinates) the text is drawn along a line connecting (text-x,text-y and text-z) and (text-x + text-dx, text-y + text-dy, text-z + text-dz). @item test-sx, text-sy and text-sz specify the location of a third reference point (in window coordinates) the text is sheared to be parallel to a line connecting (text-x,text-y and text-z) and (text-x + text-sx, text-y + text-sy, text-z + text-sz). @end itemize @sp 2 @subheading new-window @cindex new-window @subsubheading Argument List (&key x-axis y-axis title (window-line-width 1.0) (window-font-size *font-size*) (foreground-color *foreground-color*) (background-color *background-color*) (viewport-x-min 0.1) (viewport-x-max 0.9) (viewport-y-min 0.1) (viewport-y-max 0.9) plots text-labels color-table) @subsubheading Documentation new-window, creates and returns a new window object. @itemize @bullet @item x-axis is a object of type axis. @item y-axis is a object of type axis. @item title is a object of type axis-label. @item foreground-color is a color symbol in the current color table. @item background-color is a color symbol in the current color table. @item window-line-width is a floating point number specifying the pen width to use when drawing the border & the tick marks. @item window-font-size is the font size to use for the tick mark labels. @item viewport-x-min (0.0 - 1.0) is the location of the left side of the border in the device window. @item viewport-x-max (0.0 - 1.0) is the location of the right side of the border. @item viewport-y-min (0.0 - 1.0) is the location of the bottom side of the border. @item viewport-y-max (0.0 - 1.0) is the location of the top side of the border. @item plots is a list of plot objects. @item text-labels is a list of text-label objects. @item color-table specifies what color table to use. @end itemize @sp 2 @subheading new-x-y-plot @cindex new-x-y-plot @subsubheading Argument List (x y &key (copy t) (line-width 1) (line-style 1) (symbol-size 0.0) symbol-type (color *foreground-color*) x-error y-error) @subsubheading Documentation creates a new x-y plot. @itemize @bullet @item if x is nil then y will be plotted against its index. @item if copy is true then copies of x,y,x-error and y-error will be made, otherwise references will be kept to the original vectors. @item line-width should be an integer line width, or zero if no line is desired. @item line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. @item symbol-size specified how big to draw the symbols (1.0 is standard size). if it is zero the symbols are not drawn. @item symbol-type should be set to a number (that specifies a symbol) if you want specific types of symbols, otherwise default symbol types are used. @item color is the color to use when plotting the lines and symbols, it should be a symbol that specifies a color in the current color table. if it is not specified then the current foreground color will be used. @item x-error should be a vector of the same length as x that contains the size of the error bars in x. @item y-error is for error bars in y. @end itemize @sp 2 @subheading normal-font @cindex normal-font @subsubheading Argument List none. @sp 2 @subheading number-symbol @cindex number-symbol @subsubheading Argument List none. @sp 2 @subheading overline @cindex overline @subsubheading Argument List none. @sp 2 @subheading remove-axis-label-from-axis @cindex remove-axis-label-from-axis @subsubheading Argument List (a-axis &optional a-axis-label) @subsubheading Documentation remove-axis-label-from-axis, destructively removes a-axis-label from a-axis. if a-axis-label is not specified then the last axis-label is removed. @sp 2 @subheading remove-color-from-color-table @cindex remove-color-from-color-table @subsubheading Argument List (a-color-table &optional color-to-remove) @subsubheading Documentation removes color-to-remove, if specified, or the last color if not. @sp 2 @subheading remove-plot-from-window @cindex remove-plot-from-window @subsubheading Argument List (a-window &optional a-plot) @subsubheading Documentation remove-plot-from-window, destructively removes a-plot from a-window. if a-plot is not specified then the last plot is removed. @sp 2 @subheading remove-text-label-from-window @cindex remove-text-label-from-window @subsubheading Argument List (a-window &optional a-text-label) @subsubheading Documentation remove-text-label-from-window, destructively removes a-text-label from a-window. if a-text-label is not specified then the last text-label is removed. @sp 2 @subheading render @cindex render @subsubheading Argument List (a-window device &key filename (size-x 600) (size-y 500)) @subsubheading Documentation renders a window and it associated plots and labels using device. @itemize @bullet @item device: a string naming a plplot graphical device such as 'xwin'. @item filename: where to save the graph for file based devices. @item size-x: the size of the window in x (pixels). @item size-y: the size of the window in y (pixels). @end itemize if you are using cl-plplot in a multi-threaded environment you should thread lock prior to calling render, as the plplot library only handles rendering one plot at a time. @sp 2 @subheading roman-font @cindex roman-font @subsubheading Argument List none. @sp 2 @subheading script-font @cindex script-font @subsubheading Argument List none. @sp 2 @subheading send-to-back @cindex send-to-back @subsubheading Argument List (a-window a-plot) @subsubheading Documentation organizes the plots so that a-plot is drawn on the bottom. @sp 2 @subheading set-color-table @cindex set-color-table @subsubheading Argument List (a-window a-extended-color-table) @subsubheading Documentation sets the color table associated with a-window to a-color-table. returns the old color table. (set-color-table (cl-plplot::window cl-plplot::color-table)) method documentation: sets the color table associated with a-window to a-color-table. returns the old color table. @sp 2 @subheading set-foreground-color @cindex set-foreground-color @subsubheading Argument List (color) @subsubheading Documentation switches the pen to the desired foreground color, or the default foreground color if the desired color cannot be found. @sp 2 @subheading subscript @cindex subscript @subsubheading Argument List none. @sp 2 @subheading superscript @cindex superscript @subsubheading Argument List none. @sp 2 @subheading underline @cindex underline @subsubheading Argument List none. @sp 2 @subheading unicode-char @cindex unicode-char @subsubheading Argument List none. @sp 2 @subheading update-color @cindex update-color @subsubheading Argument List (a-color-table color-symbol new-color) @subsubheading Documentation changes the color specified by color-symbol to new-color, which should be a rgb triple in the form #(r g b). @sp 2 @subheading x-y-z-data-to-grid @cindex x-y-z-data-to-grid @subsubheading Argument List (data x-grid y-grid &key (algorithm grid-csa) optional-data) @subsubheading Documentation calls the plplot function plgriddata to turn irregulary spaced data as (x,y,z) points into the 2d array data[i,j] = z. please see the plplot manual for further documenation. @itemize @bullet @item data is either a 3 x n matrix of (x,y,z) points, or a list containing (x-vector, y-vector, z-vector). @item x-grid specifies the locations of the grid points in the x direction. @item y-grid specifies the locations of the grid points in the y direction. @item algorithm is one of :grid-csa, :grid-dtli, :grid-nni, :grid-nnidw, :grid-nnli or :grid-nnaidw and specifies what algorithm to use to grid the data. @item optional-data is a floating point number used in some of the algorithms for determining how to best grid the data. @end itemize @c======================================================================= @node Index @chapter Index @printindex cp @bye cl-plplot-0.6.0/README.txt0000644000175000017500000000711211427545774015214 0ustar hbabcockhbabcock; ; The Common Lisp / CFFI based interface to the PLplot Scientific Plotting ; Library. ; ; hazen 08/10 ; ;;; 08-08-10 Going forward from release 0.6.0 I'm simply going to be trying to keep the Lisp binding in sync with the PLplot library (cl-plplot-system). Due to time constraints, and also because I do not actually use it myself enough to have good ideas about what does and does not work, I'm not planning on any further updates to my attempt to make a more Lispish interface to PLplot (cl-plplot). ;;; Older This is in fact two packages, one is a "low-level" package (cl-plplot-system) that contains the interface to the large and hairy plplot API, and the other is a (hopefully) easy to use front end (cl-plplot). It was written and tested with CFFI-0.9.0 and SBCL-0.9.9 on OS-X 10.4. I have also verified that it works on debian (2.6.15) with CFFI-0.9.1 and SBCL-0.9.12. It should all be Common Lisp & ASDF installable, but let me know if you find otherwise. cl-plplot: This is currently 18 files (in src/window). 1) axis-label.lisp handles the axis-label and 3D-axis-label object. 2) axis.lisp handles the axis object. 3) bar-graph.lisp handles the bar-graph object. 4) classes.lisp specifies all the cl-plplot classes. 5) color-table.lisp handles plplot cmap0 color. 6) contour-plot.lisp handles the contour-plot object. 7) extended-color-table.lisp handles plplot cmap1 color. 8) macros.lisp contains the important macros. 9) package.lisp defines the package & the global variables. 10) plot.lisp defines the plot object as well as providing an interface whereby the user can define their own custom plot objects. 11) surface-plot.lisp handles the surface-plot object. 12) text-item.lisp handles the text-item object. 13) text-label.lisp handles the text-label and 3D-text-label object. 14) utility-functions.lisp is a collection of low-level functions. 15) window.lisp handles the window object. 16) x-y-plot.lisp handles the x-y-plot object. 17) 3D-mesh.lisp handles the 3D-mesh object. 18) 3D-window.lisp handles the 3D-window object. Things should be fairly stable now and the interface should not change much for 2D plotting going forward. The file src/examples/window-examples.lisp contains examples of how to use cl-plplot to generate different 2D plots. cl-plplot-system: This is currently 4 files (src/system). 1) loadlib.lisp defines the package and loads the PLplot library. 2) defcfun.lisp defines the macro that is used to facilitate wrapping all the CFFI calls. 3) misc.lisp contains some helper functions and macros. 4) api.lisp contains all the plplot library / CFFI interface calls. Not every function in the plplot API is available, though all the ones that are associated with drawing/graphing should be. Others can of course be added as desired. The file system-examples.lisp contains some examples of how you might directly use the functions in cl-plplot-system. Also, src/examples/ contains Lisp versions of all the standard PLplot examples. Other useful resources are the documentation that comes with plplot, the examples that come with plplot, the (admittedly somewhat sparse) comments in api.lisp & possibly plplot.h. You should be aware the cl-plplot-system exports lots and lots of symbols (approximately 2 for every plplot function). These will generally be of the form "c-pl*" or "pl*", so if you like function names that begin with these characters then watch out! A callback has been added that should trap PLplot when it tries to call exit() and instead cause a Lisp side error to be thrown. If you find a PLplot error that is not trapped by this callback please let me know. cl-plplot-0.6.0/src/0000755000175000017500000000000011427546035014273 5ustar hbabcockhbabcockcl-plplot-0.6.0/src/system/0000755000175000017500000000000011427546035015617 5ustar hbabcockhbabcockcl-plplot-0.6.0/src/system/api.lisp0000644000175000017500000013205111427277532017266 0ustar hbabcockhbabcock;;;; ;;;; Calls to the plplot API. An attempt was made to have the pl-defcfun macro ;;;; handle as many as these as possible, but eventually I gave up and just wrote ;;;; out some of the less conventional ones. As a consequence, not all the 'raw' ;;;; cffi calls will be name "c-plfunctionname", they are likely to instead be ;;;; "c-pl-plfunctionname". ;;;; ;;;; hazen 3/06 ;;;; (in-package #:cl-plplot-system) ;;; ;;; plplot API functions, these are in more or less the same order as they are listed in plplot.h ;;; (pl-defcfun ("c_pl_setcontlabelformat" pl-setcontlabelformat) :void (lexp plint) (sigdig plint)) (pl-defcfun ("c_pl_setcontlabelparam" pl-setcontlabelparam) :void (offset plflt) (size plflt) (spacing plflt) (active plint)) (pl-defcfun ("c_pladv" pladv) :void (page plint)) (pl-defcfun ("c_plarc" plarc) :void (x plflt) (y plflt) (a plflt) (b plflt) (angle1 plflt) (angle2 plflt) (fill plbool)) ;; ;; This function is deprecated and may dissappear at some point ;; (pl-defcfun ("plarrows" plarrows) :void (u *plflt n) (v *plflt n) (x *plflt n) (y *plflt n) (n plint) (scale plflt) (dx plflt) (dy plflt)) (defun plvect (u v scale &optional (gridx nil) (gridy nil)) (with-plcgrid (plc-grid gridx gridy (array-dimension u 0) (array-dimension u 1)) ; this macro creates the variable plcgrid (pl-plvect u v scale plc-grid))) (export 'plvect (package-name *package*)) (pl-defcfun ("c_plvect" pl-plvect) :void (u **plflt (nx ny)) (v **plflt (nx ny)) (nx plint) (ny plint) (scale plflt) (pltr-fn plfunc) (pltr-data plpointer)) (pl-defcfun ("c_plsvect" plsvect) :void (arrowx *plflt npts) (arrowy *plflt npts) (npts plint) (fill plint)) (pl-defcfun ("c_plaxes" plaxes) :void (x0 plflt) (y0 plflt) (xopt plstr) (xtick plflt) (nxsub plint) (yopt plstr) (ytick plflt) (nysub plint)) (pl-defcfun ("c_plbin" plbin) :void (nbin plint) (x *plflt nbin) (y *plflt nbin) (opt plint)) (pl-defcfun ("c_plbtime" plbtime) :void (year *plint 1) (month *plint 1) (day *plint 1) (hour *plint 1) (min *plint 1) (sec *plflt 1) (ctime plflt)) (pl-defcfun ("c_plbop" plbop) :void) (pl-defcfun ("c_plbox" plbox) :void (xopt plstr) (xtick plflt) (nxsub plint) (yopt plstr) (ytick plflt) (nysub plint)) (pl-defcfun ("c_plbox3" plbox3) :void (xopt plstr) (xlabel plstr) (xtick plflt) (nsubx plint) (yopt plstr) (ylabel plstr) (ytick plflt) (nsuby plint) (zopt plstr) (zlabel plstr) (ztick plflt) (nsubz plint)) (pl-defcfun ("c_plcalc_world" plcalc-world) :void (rx plflt) (ry plflt) (wx *plflt 1) (wy *plflt 1) (window *plint 1)) (pl-defcfun ("c_plclear" plclear) :void) (pl-defcfun ("c_plcol0" plcol0) :void (icol0 plint)) (pl-defcfun ("c_plcol1" plcol1) :void (col1 plflt)) (pl-defcfun ("c_plconfigtime" plconfigtime) :void (scale plflt) (offset1 plflt) (offset2 plflt) (ccontrol plint) (ifbtime-offset plbool) (year plint) (month plint) (day plint) (hour plint) (min plint) (sec plflt)) ;; ;; Coming on this a couple months later I had a pretty hard time figuring ;; out what I was trying to do in the first place, so here I attempt a ;; better explanation. ;; ;; In the case of 2D gridded data, as you might have for a contour or ;; surface plot, plplot allows you do one of four things to specify ;; how to map that data to world (i.e. plot coordinates). ;; ;; (1) Nothing, meaning matrix element (0,0) goes to coordinate (0,0). ;; This is done with the plplot function pltr0. ;; (2) Map to a grid defined by a vector in x and a vector in y ;; (0,0) -> (x(0), y(0)), handled by the function pltr1. ;; (3) Map to a grid defined my a matrix in x and y. ;; (0,0) -> (x(0,0), y(0,0)), handled by the function pltr2. ;; (4) Completely arbitrary. This is implemented here by passing the ;; data contained in gridx through C to a callback function that ;; you specify "on the other side". Since the "other side" is back ;; where you started, i.e. in Lisp, you also have the option of ;; using in your callback function anything that it is accessible ;; to it in the current Lisp environment. ;; ;; The functions pltr0, pltr1 & pltr2, along with the relevant callback ;; closure, pltr-fn, are defined towards the end of this file. ;; ;; The macro callback-closure creates a closure containing the callback ;; function as well as getter, setter and query functions for ;; changing and querying the current callback function. ;; ;; If you want to use your own callback function it *must* take the ;; same arguments as the default function(s) for the particular callback ;; closure. ;; (defun plcont (f kx lx ky ly clevel &optional (gridx nil) (gridy nil)) (with-plcgrid (plc-grid gridx gridy (array-dimension f 0) (array-dimension f 1)) (pl-plcont f kx lx ky ly clevel plc-grid))) (export 'plcont (package-name *package*)) (pl-defcfun ("c_plcont" pl-plcont) :void (f **plflt (nx ny)) (nx plint) (ny plint) (kx plint) (lx plint) (ky plint) (ly plint) (clevel *plflt nlevel) (nlevel plint) (pltr-fn plfunc) (pltr-data plpointer)) ;; Draws the completely arbitrary in every was contour plot. ;; Useful for making contour plots of user defined functions. (defun init-f2eval-data (f2eval-data nx ny) "Create C version of f2eval-data, if necessary" (if (equal (pl-get-feval-fn) #'plf2eval2) (if (and (= (array-dimension f2eval-data 0) nx) (= (array-dimension f2eval-data 1) ny)) (make-matrix f2eval-data) (format t "Matrix dimensions are wrong for f2eval-data in init-f2eval-data~%")) f2eval-data)) (defun free-f2eval-data (f2eval-data nx ny) "Frees C version of f2eval-data, if necessary" (when (equal (pl-get-feval-fn) #'plf2eval2) (free-matrix f2eval-data (list nx ny)))) (defun plfcont (f2eval-data nx ny kx lx ky ly clevel &optional (gridx nil) (gridy nil)) (let ((c-f2eval-data (init-f2eval-data f2eval-data nx ny))) (with-plcgrid (plc-grid gridx gridy nx ny) (pl-plfcont c-f2eval-data nx ny kx lx ky ly clevel plc-grid)) (free-f2eval-data f2eval-data nx ny))) (export 'plfcont (package-name *package*)) (pl-defcfun ("plfcont" pl-plfcont) :void (feval-fn plfunc) (f2eval-data plpointer) (nx plint) (ny plint) (kx plint) (lx plint) (ky plint) (ly plint) (clevel *plflt nlevel) (nlevel plint) (pltr-fn plfunc) (pltr-data plpointer)) (pl-defcfun ("c_plcpstrm" plcpstrm) :void (iplsr plint) (flags plint)) (pl-defcfun ("c_plctime" plctime) :void (year plint) (month plint) (day plint) (hour plint) (min plint) (sec plflt) (ctime *plflt 1)) (pl-defcfun ("pldid2pc" pldid2pc) :void (xmin *plflt :in-out) (ymin *plflt :in-out) (xmax *plflt :in-out) (ymax *plflt :in-out)) (pl-defcfun ("pldip2dc" pldip2dc) :void (xmin *plflt :in-out) (ymin *plflt :in-out) (xmax *plflt :in-out) (ymax *plflt :in-out)) (pl-defcfun ("c_plend" plend) :void) (pl-defcfun ("c_plend1" plend1) :void) (pl-defcfun ("c_plenv" plenv) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (just plint) (axis plint)) (pl-defcfun ("c_plenv0" plenv0) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (just plint) (axis plint)) (pl-defcfun ("c_pleop" pleop) :void) (pl-defcfun ("c_plerrx" plerrx) :void (n plint) (xmin *plflt n) (xmax *plflt n) (y *plflt n)) (pl-defcfun ("c_plerry" plerry) :void (n plint) (x *plflt n) (ymin *plflt n) (ymax *plflt n)) (pl-defcfun ("c_plfamadv" plfamadv) :void) (defcallback plfill-fn :void ((n plint) (x *plflt) (y *plflt)) (c-plfill n x y)) (pl-defcfun ("c_plfill" plfill) :void (n plint) (x *plflt n) (y *plflt n)) (pl-defcfun ("c_plfill3" plfill3) :void (n plint) (x *plflt n) (y *plflt n) (z *plflt n)) (pl-defcfun ("c_plflush" plflush) :void) (pl-defcfun ("c_plfont" plfont) :void (ifont plint)) (pl-defcfun ("c_plfontld" plfontld) :void (fnt plint)) (pl-defcfun ("c_plgchr" plgchr) :void (p_def *plflt 1) (p_ht *plflt 1)) (pl-defcfun ("c_plgcol0" plgcol0) :void (icol0 plint) (r *plint 1) (g *plint 1) (b *plint 1)) (pl-defcfun ("c_plgcol0a" plgcol0a) :void (icol0 plint) (r *plint 1) (g *plint 1) (b *plint 1) (a *plflt 1)) (pl-defcfun ("c_plgcolbg" plgcolbg) :void (r *plint 1) (g *plint 1) (b *plint 1)) (pl-defcfun ("c_plgcolbga" plgcolbga) :void (r *plint 1) (g *plint 1) (b *plint 1) (a *plflt 1)) (pl-defcfun ("c_plgcompression" plgcompression) :void (compression *plint 1)) (pl-defcfun ("c_plgdev" plgdev) :void (p_dev plstr 80)) (pl-defcfun ("c_plgdidev" plgdidev) :void (p_mar *plflt 1) (p_aspect *plflt 1) (p_jx *plflt 1) (p_jy *plflt 1)) (pl-defcfun ("c_plgdiori" plgdiori) :void (p_rot *plflt 1)) (pl-defcfun ("c_plgdiplt" plgdiplt) :void (p_xmin *plflt 1) (p_ymin *plflt 1) (p_xmax *plflt 1) (p_ymax *plflt 1)) (pl-defcfun ("c_plgfam" plgfam) :void (p_fam *plint 1) (p_num *plint 1) (p_bmax *plint 1)) (pl-defcfun ("c_plgfci" plgfci) :void (pfci *plunicode 1)) (pl-defcfun ("c_plgfnam" plgfnam) :void (fnam plstr 80)) (pl-defcfun ("c_plgfont" plgfont) :void (p_family *plint 1) (p_style *plint 1) (p_weight *plint 1)) (pl-defcfun ("c_plglevel" plglevel) :void (p_level *plint 1)) (pl-defcfun ("c_plgpage" plgpage) :void (p_xp *plflt 1) (p_yp *plflt 1) (p_xleng *plint 1) (p_yleng *plint 1) (p_xoff *plint 1) (p_yoff *plint 1)) (pl-defcfun ("c_plgra" plgra) :void) (pl-defcfun ("c_plgradient" plgradient) :void (n plint) (x *plflt n) (y *plflt n) (angle plflt)) (defun plgriddata (x y z xg yg type data) (let ((sx (length x)) (sy (length y)) (f (foreign-alloc :pointer))) (plalloc2dgrid f sx sy) (let ((zg (mem-aref f :pointer))) (pl-plgriddata x y z xg yg zg type data) (let ((lisp-mat (make-array (list (length xg) (length yg)) :initial-element 0.0d0 :element-type 'double-float))) (dotimes (x (length xg)) (dotimes (y (length yg)) (setf (aref lisp-mat x y) (mem-aref (mem-aref zg :pointer x) :double y)))) (plfree2dgrid zg sx sy) (foreign-free f) lisp-mat)))) (export 'plgriddata (package-name *package*)) (pl-defcfun ("c_plgriddata" pl-plgriddata) :void (x *plflt npts) (y *plflt npts) (z *plflt npts) (npts plint) (xg *plflt nptsx) (nptsx plint) (yg *plflt nptsy) (nptsy plint) (zg plpointer) (type plint) (data plflt)) (pl-defcfun ("c_plgspa" plgspa) :void (xmin *plflt 1) (xmax *plflt 1) (ymin *plflt 1) (ymax *plflt 1)) (pl-defcfun ("c_plgstrm" plgstrm) :void (p_strm *plint 1)) (pl-defcfun ("c_plgver" plgver) :void (p_ver plstr 80)) (pl-defcfun ("c_plgvpd" plgvpd) :void (p_xmin *plflt 1) (p_xmax *plflt 1) (p_ymin *plflt 1) (p_ymax *plflt 1)) (pl-defcfun ("c_plgvpw" plgvpw) :void (p_xmin *plflt 1) (p_xmax *plflt 1) (p_ymin *plflt 1) (p_ymax *plflt 1)) (pl-defcfun ("c_plgxax" plgxax) :void (p_digmax *plint 1) (p_digits *plint 1)) (pl-defcfun ("c_plgyax" plgyax) :void (p_digmax *plint 1) (p_digits *plint 1)) (pl-defcfun ("c_plgzax" plgzax) :void (p_digmax *plint 1) (p_digits *plint 1)) (pl-defcfun ("c_plhist" plhist) :void (n plint) (data *plflt n) (datmin plflt) (datmax plflt) (nbin plint) (opt plint)) ;; deprecated (pl-defcfun ("c_plhls" plhls) :void (h plflt) (l plflt) (s plflt)) (pl-defcfun ("c_plhlsrgb" plhlsrgb) :void (h plflt) (l plflt) (s plflt) (p_r *plflt 1) (p_g *plflt 1) (p_b *plflt 1)) (pl-defcfun ("c_plinit" plinit) :void) (pl-defcfun ("c_pljoin" pljoin) :void (x1 plflt) (y1 plflt) (x2 plflt) (y2 plflt)) (pl-defcfun ("c_pllab" pllab) :void (xlabel plstr) (ylabel plstr) (tlabel plstr)) (pl-defcfun ("c_pllightsource" pllightsource) :void (x plflt) (y plflt) (z plflt)) (pl-defcfun ("c_plline" plline) :void (n plint) (x *plflt n) (y *plflt n)) (pl-defcfun ("c_plline3" plline3) :void (n plint) (x *plflt n) (y *plflt n) (z *plflt n)) (pl-defcfun ("c_pllsty" pllsty) :void (lin plint)) (callback-closure map-fn #'(lambda(n x y) (declare (ignore n x y)) 0) :void (n plint) (x *plflt) (y *plflt)) (pl-defcfun ("c_plmap" plmap) :void (map-fn plfunc) (type plstr) (minlong plflt) (maxlong plflt) (minlat plflt) (maxlat plflt)) (pl-defcfun ("c_plmeridians" plmeridians) :void (map-fn plfunc) (dlong plflt) (dlat plflt) (minlong plflt) (maxlong plflt) (minlat plflt) (maxlat plflt)) (pl-defcfun ("c_plmesh" plmesh) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint)) (pl-defcfun ("c_plmeshc" plmeshc) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint)) (pl-defcfun ("c_plmkstrm" plmkstrm) :void (p_strm *plint 1)) (pl-defcfun ("c_plmtex" plmtex) :void (side plstr) (disp plflt) (pos plflt) (just plflt) (text plstr)) (pl-defcfun ("c_plmtex3" plmtex3) :void (side plstr) (disp plflt) (pos plflt) (just plflt) (text plstr)) (pl-defcfun ("c_plot3d" plot3d) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (side plint)) (pl-defcfun ("c_plot3dc" plot3dc) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint)) (pl-defcfun ("c_plot3dcl" plot3dcl) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint) (ixstart plint) (ixn plint) (indexymin *plint ixn) (indexymax *plint ixn)) (pl-defcfun ("c_plpat" plpat) :void (nlin plint) (inc *plint n) (del *plint n)) (pl-defcfun ("c_plpath" plpath) :void (n plint) (x1 plflt) (y1 plflt) (x2 plflt) (y2 plflt)) (pl-defcfun ("c_plpoin" plpoin) :void (n plint) (x *plflt n) (y *plflt n) (code plint)) (pl-defcfun ("c_plpoin3" plpoin3) :void (n plint) (x *plflt n) (y *plflt n) (z *plflt n) (code plint)) (pl-defcfun ("c_plpoly3" plpoly3) :void (n plint) (x *plflt n) (y *plflt n) (z *plflt n) (draw *plint n) (ifcc plbool)) (pl-defcfun ("c_plprec" plprec) :void (setp plint) (prec plint)) (pl-defcfun ("c_plpsty" plpsty) :void (patt plint)) (pl-defcfun ("c_plptex" plptex) :void (x plflt) (y plflt) (dx plflt) (dy plflt) (just plflt) (text plstr)) (pl-defcfun ("c_plptex3" plptex3) :void (x plflt) (y plflt) (z plflt) (dx plflt) (dy plflt) (dz plflt) (sx plflt) (sy plflt) (sz plflt) (just plflt) (text plstr)) (pl-defcfun ("c_plrandd" plrandd) :double) (pl-defcfun ("c_plreplot" plreplot) :void) ;; deprecated (pl-defcfun ("c_plrgb" plrgb) :void (r plflt) (g plflt) (b plflt)) ;; deprecated (pl-defcfun ("c_plrgb1" plrgb1) :void (r plint) (g plint) (b plint)) (pl-defcfun ("c_plrgbhls" plrgbhls) :void (r plflt) (g plflt) (b plflt) (p_h *plflt 1) (p_l *plflt 1) (p_s *plflt 1)) (pl-defcfun ("c_plschr" plschr) :void (def plflt) (scale plflt)) (pl-defcfun ("c_plscmap0" plscmap0) :void (r *plint ncol0) (g *plint ncol0) (b *plint ncol0) (ncol0 plint)) (pl-defcfun ("c_plscmap0a" plscmap0a) :void (r *plint ncol0) (g *plint ncol0) (b *plint ncol0) (a *plflt ncol0) (ncol0 plint)) (pl-defcfun ("c_plscmap0n" plscmap0n) :void (ncol0 plint)) (pl-defcfun ("c_plscmap1" plscmap1) :void (r *plint ncol1) (g *plint ncol1) (b *plint ncol1) (ncol1 plint)) (pl-defcfun ("c_plscmap1a" plscmap1a) :void (r *plint ncol1) (g *plint ncol1) (b *plint ncol1) (a *plflt ncol1) (ncol1 plint)) (pl-defcfun ("c_plscmap1l" plscmap1l) :void (itype plbool) (npts plint) (intensity *plflt npts) (coord1 *plflt npts) (coord2 *plflt npts) (coord3 *plflt npts) (rev *plbool n)) (pl-defcfun ("c_plscmap1la" plscmap1la) :void (itype plbool) (npts plint) (intensity *plflt npts) (coord1 *plflt npts) (coord2 *plflt npts) (coord3 *plflt npts) (coord4 *plflt npts) (rev *plbool npts)) (pl-defcfun ("c_plscmap1n" plscmap1n) :void (ncol1 plint)) (pl-defcfun ("c_plscol0" plscol0) :void (icol0 plint) (r plint) (g plint) (b plint)) (pl-defcfun ("c_plscol0a" plscol0a) :void (icol0 plint) (r plint) (g plint) (b plint) (a plflt)) (pl-defcfun ("c_plscolbg" plscolbg) :void (r plint) (g plint) (b plint)) (pl-defcfun ("c_plscolbga" plscolbga) :void (r plint) (g plint) (b plint) (a plflt)) (pl-defcfun ("c_plscolor" plscolor) :void (color plint)) (pl-defcfun ("c_plscompression" plscompression) :void (compression plint)) (pl-defcfun ("c_plsdev" plsdev) :void (dev plstr)) (pl-defcfun ("c_plsdidev" plsdidev) :void (mar plflt) (aspect plflt) (jx plflt) (jy plflt)) (pl-defcfun ("c_plsdimap" plsdimap) :void (dimxmin plint) (dimxmax plint) (dimymin plint) (dimymax plint) (dimxpmm plflt) (dimypmm plflt)) (pl-defcfun ("c_plsdiori" plsdiori) :void (rot plflt)) (pl-defcfun ("c_plsdiplt" plsdiplt) :void (xmin plflt) (ymin plflt) (xmax plflt) (ymax plflt)) (pl-defcfun ("c_plsdiplz" plsdiplz) :void (xmin plflt) (ymin plflt) (xmax plflt) (ymax plflt)) (pl-defcfun ("c_plseed" plseed) :void (seed plint)) (pl-defcfun ("c_plsesc" plsesc) :void (esc plchar)) (pl-defcfun ("c_plsfam" plsfam) :void (fam plint) (num plint) (bmax plint)) (pl-defcfun ("c_plsfci" plsfci) :void (fci plunicode)) ;; This is inside a closure so that the file name & its associated storage ;; is preserved until the next time this function is called (let ((c-fname nil)) (defun plsfnam (fname) (when c-fname (foreign-string-free c-fname)) (setf c-fname (foreign-string-alloc fname)) (c-plsfnam c-fname))) (export 'plsfnam (package-name *package*)) (defcfun ("c_plsfnam" c-plsfnam) :void (fnam plstr)) (pl-defcfun ("c_plsfont" plsfont) :void (family plint) (style plint) (weight plint)) ;; ;; Note that for these functions you have no choice when it comes to the fill function, ;; as this is what the plplot docs suggest. You can set a user defined exclude function ;; and a user defined contour function by setting my-defined-fn or my-pltr-fn inside ;; their respective closures. ;; ;; Note also that left, right, bottom and top are ignored as it is (as currently arranged) ;; impossible to set the pltr-fn to null due to the fact that it is a callback. ;; ;; use the no exclusion function or set your own with this closure (callback-closure defined-fn #'(lambda(x y) (declare (ignore x y)) 1) plint (x plflt) (y plflt)) (defun plshade (a left right bottom top shade-min shade-max sh-cmap sh-color sh-width min-color min-width max-color max-width rectangular &optional (gridx nil) (gridy nil)) (if (and gridx gridy) (with-plcgrid (plc-grid gridx gridy (array-dimension a 0) (array-dimension a 1)) (pl-plshade a left right bottom top shade-min shade-max sh-cmap sh-color sh-width min-color min-width max-color max-width rectangular plc-grid)) (pl-plshade-simple a left right bottom top shade-min shade-max sh-cmap sh-color sh-width min-color min-width max-color max-width rectangular (null-pointer) (null-pointer)))) (export 'plshade (package-name *package*)) (pl-defcfun ("c_plshade" pl-plshade) :void (a **plflt (nx ny)) (nx plint) (ny plint) (defined-fn plfunc) (left plflt) (right plflt) (bottom plflt) (top plflt) (shade-min plflt) (shade-max plflt) (sh-cmap plint) (sh-color plflt) (sh-width plint) (min-color plint) (min-width plint) (max-color plint) (max-width plint) (plfill-fn plfunc) (rectangular plbool) (pltr-fn plfunc) (pltr-data plpointer)) (pl-defcfun ("c_plshade" pl-plshade-simple) :void (a **plflt (nx ny)) (nx plint) (ny plint) (defined-fn plfunc) (left plflt) (right plflt) (bottom plflt) (top plflt) (shade-min plflt) (shade-max plflt) (sh-cmap plint) (sh-color plflt) (sh-width plint) (min-color plint) (min-width plint) (max-color plint) (max-width plint) (plfill-fn plfunc) (rectangular plbool) (pltr-fn plpointer) (pltr-data plpointer)) (defun plshades (a xmin xmax ymin ymax clevel fill-width cont-color cont-width rectangular &optional (gridx nil) (gridy nil)) (if (and gridx gridy) (with-plcgrid (plc-grid gridx gridy (array-dimension a 0) (array-dimension a 1)) (pl-plshades a xmin xmax ymin ymax clevel fill-width cont-color cont-width rectangular plc-grid)) (pl-plshades-simple a xmin xmax ymin ymax clevel fill-width cont-color cont-width rectangular (null-pointer) (null-pointer)))) (export 'plshades (package-name *package*)) (pl-defcfun ("c_plshades" pl-plshades) :void (a **plflt (nx ny)) (nx plint) (ny plint) (defined-fn plfunc) (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (clevel *plflt nlevel) (nlevel plint) (fill-width plint) (cont-color plint) (cont-width plint) (plfill-fn plfunc) (rectangular plbool) (pltr-fn plfunc) (pltr-data plpointer)) (pl-defcfun ("c_plshades" pl-plshades-simple) :void (a **plflt (nx ny)) (nx plint) (ny plint) (defined-fn plfunc) (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (clevel *plflt nlevel) (nlevel plint) (fill-width plint) (cont-color plint) (cont-width plint) (plfill-fn plfunc) (rectangular plbool) (pltr-fn plpointer) (pltr-data plpointer)) ;; The "friendly" form of this one was deemed to be adequately covered by the above ;; functions, so only the "cffi" version of the function is provided. (defcfun ("c_plshade1" c-plshade1) :void (a **plflt) ; According the plplot-5.5.3.pdf this should be an array [nx][ny], but in plplot.h its type is plflt *... (nx plint) (ny plint) (defined-fn plfunc) (left plflt) (right plflt) (bottom plflt) (top plflt) (shade-min plflt) (shade-max plflt) (sh-cmap plint) (sh-color plflt) (sh-width plint) (min-color plint) (min-width plint) (max-color plint) (max-width plint) (plfill-fn plfunc) (rectangular plbool) (pltr-fn plfunc) (pltr-data plpointer)) (export 'plshade1 (package-name *package*)) ;; Left this one out for the time being since its documentation is a bit thin. ;; I believe that it would let you make shade plots of functions. ;(defcfun ("plfshade" plfshade) :void ; PLFLT (*f2eval) (PLINT, PLINT, PLPointer), ; PLPointer f2eval_data, PLFLT (*c2eval) (PLINT, PLINT, PLPointer), ; PLPointer c2eval_data, PLINT nx, PLINT ny, ; PLFLT left, PLFLT right, PLFLT bottom, PLFLT top, PLFLT shade_min, PLFLT shade_max, ; PLINT sh_cmap, PLFLT sh_color, PLINT sh_width, PLINT min_color, PLINT min_width, ; PLINT max_color, PLINT max_width, void (*fill) (PLINT, PLFLT *, PLFLT *), PLBOOL rectangular, ; void (*pltr) (PLFLT, PLFLT, PLFLT *, PLFLT *, PLPointer), PLPointer pltr_data ;(pl-defcfun ("c_plsfam" plsfam) :void (pl-defcfun ("c_plslabelfunc" plslabelfunc) :void (label-fn plfunc) (label-data plpointer)) (callback-closure label-fn #'(lambda(axis value label length data) (declare (ignore axis value data)) (lisp-string-to-foreign "not set" label length)) :void (axis plint) (value plflt) (label plstr) (length plint) (data plpointer)) (pl-defcfun ("c_plsmaj" plsmaj) :void (def plflt) (scale plflt)) ;; ;; plsmem is broken into three parts: ;; ;; plsmem-alloc : allocates the memory to be used for plotting ;; plsmem-get : gets a lisp friendly version of the bitmap plot ;; plsmem-free : frees the memory associated with the plot ;; ;; These are all inside a closure for user convenience (hopefully...) ;; (let ((xsize nil) (ysize nil) (mem nil)) (defun plsmem-alloc (maxx maxy) "allocates memory to be used for in memory plotting" (when mem (foreign-free mem)) (setf mem (foreign-alloc :unsigned-char :count (* 3 maxx maxy))) (pl-plsmem maxx maxy mem) (setf xsize maxx) (setf ysize maxy)) (defun plsmem-get () "gets a lisp array version of the bitmap plot" (let ((image (make-array (list xsize ysize 3) :element-type 'unsigned-byte))) (dotimes (x xsize) (dotimes (y ysize) (dotimes (rgb 3) (setf (aref image x y rgb) (mem-aref mem :unsigned-char (+ (* 3 xsize y) (* 3 x) rgb)))))) image)) (defun plsmem-free () "free memory that was used for in memory plotting" (when mem (foreign-free mem) (setf mem nil))) (export 'plsmem-alloc (package-name *package*)) (export 'plsmem-get (package-name *package*)) (export 'plsmem-free (package-name *package*))) (pl-defcfun ("c_plsmem" pl-plsmem) :void (maxx plint) (maxy plint) (plotmem plpointer)) (pl-defcfun ("c_plsmin" plsmin) :void (def plflt) (scale plflt)) (pl-defcfun ("c_plsori" plsori) :void (ori plint)) (pl-defcfun ("c_plspage" plspage) :void (xp plflt) (yp plflt) (xleng plint) (yleng plint) (xoff plint) (yoff plint)) (pl-defcfun ("c_plspal0" plspal0) :void (filename plstr)) (pl-defcfun ("c_plspal1" plspal1) :void (filename plstr) (interpolate plbool)) (pl-defcfun ("c_plspause" plspause) :void (pause plbool)) (pl-defcfun ("c_plsstrm" plsstrm) :void (strm plint)) (pl-defcfun ("c_plssub" plssub) :void (nx plint) (ny plint)) (pl-defcfun ("c_plssym" plssym) :void (def plflt) (scale plflt)) (pl-defcfun ("c_plstar" plstar) :void (nx plint) (ny plint)) (pl-defcfun ("c_plstart" plstart) :void (devname plstr) (nx plint) (ny plint)) (pl-defcfun ("c_plstransform" plstransform) :void (transform-fn plfunc) (data plpointer)) (callback-closure transform-fn #'(lambda (x y tx ty pltr-data) (declare (ignore pltr-data)) (setf (mem-aref tx :double) (coerce x 'double-float) (mem-aref ty :double) (coerce y 'double-float))) :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr-data plpointer)) ;; This is a lame hack to make it easier for the user to reset ;; PLplots universal coordinate transform function. (defun pl-reset-transform () (c-plstransform (null-pointer) (null-pointer))) (export 'pl-reset-transform (package-name *package*)) (pl-defcfun ("c_plstripa" plstripa) :void (id plint) (pen plint) (x plflt) (y plflt)) ;; Expects colline, styline & legline to 4 element lists containing the ;; appropriate color, style and name for each pen (defun plstripc (xspec yspec xmin xmax xjump ymin ymax xlpos ylpos y_ascl acc colbox collab colline styline legline labx laby labtop) (let ((c-col (foreign-alloc 'plint :count 4)) (c-sty (foreign-alloc 'plint :count 4)) (c-leg (foreign-alloc :pointer :count 4))) (dotimes (i 4) (setf (mem-aref c-col 'plint i) (round (elt colline i))) (setf (mem-aref c-sty 'plint i) (round (elt styline i))) (setf (mem-aref c-leg :pointer i) (foreign-string-alloc (elt legline i)))) (unwind-protect (pl-plstripc xspec yspec xmin xmax xjump ymin ymax xlpos ylpos y_ascl acc colbox collab c-col c-sty c-leg labx laby labtop) (progn (foreign-free c-col) (foreign-free c-sty) (dotimes (i 4) (foreign-string-free (mem-aref c-leg :pointer i))) (foreign-free c-leg))))) (export 'plstripc (package-name *package*)) (pl-defcfun ("c_plstripc" pl-plstripc) :void (id *plint 1) (xspec plstr) (yspec plstr) (xmin plflt) (xmax plflt) (xjump plflt) (ymin plflt) (ymax plflt) (xlpos plflt) (ylpos plflt) (y_ascl plbool) (acc plbool) (colbox plint) (collab plint) (colline plpointer) (styline plpointer) (legline plpointer) (labx plstr) (laby plstr) (labtop plstr)) (pl-defcfun ("c_plstripd" plstripd) :void (id plint)) (pl-defcfun ("c_plimagefr" pl-plimagefr) :void (idata **plflt (nx ny)) (nx plint) (ny plint) (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (zmin plflt) (zmax plflt) (valuemin plflt) (valuemax plflt) (pltr-fn plfunc) (pltr-data plpointer)) (defun plimagefr (idata xmin xmax ymin ymax zmin zmax valuemin valuemax &optional (gridx nil) (gridy nil)) (with-plcgrid (plc-grid gridx gridy (array-dimension idata 0) (array-dimension idata 1)) (pl-plimagefr idata xmin xmax ymin ymax zmin zmax valuemin valuemax plc-grid))) (export 'plimagefr (package-name *package*)) (pl-defcfun ("c_plimage" plimage) :void (data **plflt (nx ny)) (nx plint) (ny plint) (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (zmin plflt) (zmax plflt) (Dxmin plflt) (Dxmax plflt) (Dymin plflt) (Dymax plflt)) (pl-defcfun ("c_plstyl" plstyl) :void (nms plint) (mark *plint n) (space *plint n)) (pl-defcfun ("c_plsurf3d" plsurf3d) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint)) ;; See x08l.lisp for an example of how to use this function. (pl-defcfun ("plfsurf3d" plfsurf3d) :void (x *plflt nx) (y *plflt ny) (zops plpointer) (zp plpointer) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint)) ;; These are helper functions for plf... functions, they ;; return a pointer to a "zops" function. (defcfun "plf2ops_c" :pointer) (defcfun "plf2ops_grid_c" :pointer) (defcfun "plf2ops_grid_row_major" :pointer) (defcfun "plf2ops_grid_col_major" :pointer) (export 'plf2ops-c (package-name *package*)) (export 'plf2ops-grid-c (package-name *package*)) (export 'plf2ops-grid-row-major (package-name *package*)) (export 'plf2ops-grid-col-major (package-name *package*)) (pl-defcfun ("c_plsurf3dl" plsurf3dl) :void (x *plflt nx) (y *plflt ny) (z **plflt (nx ny)) (nx plint) (ny plint) (opt plint) (clevel *plflt nlevel) (nlevel plint) (ixstart plint) (ixn plint) (indexymin *plint ixn) (indexymax *plint ixn)) (pl-defcfun ("c_plsvpa" plsvpa) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt)) (pl-defcfun ("c_plsxax" plsxax) :void (digmax plint) (digits plint)) (pl-defcfun ("plsxwin" plsxwin) :void (window_id plint)) (pl-defcfun ("c_plsyax" plsyax) :void (digmax plint) (digits plint)) (pl-defcfun ("c_plsym" plsym) :void (n plint) (x *plflt n) (y *plflt n) (code plint)) (pl-defcfun ("c_plszax" plszax) :void (digmax plint) (digits plint)) (pl-defcfun ("c_pltext" pltext) :void) (pl-defcfun ("c_pltimefmt" pltimefmt) :void (fmt plstr)) (pl-defcfun ("c_plvasp" plvasp) :void (aspect plflt)) (pl-defcfun ("c_plvpas" plvpas) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt) (aspect plflt)) (pl-defcfun ("c_plvpor" plvpor) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt)) (pl-defcfun ("c_plvsta" plvsta) :void) (pl-defcfun ("c_plw3d" plw3d) :void (basex plflt) (basey plflt) (height plflt) (xmin0 plflt) (xmax0 plflt) (ymin0 plflt) (ymax0 plflt) (zmin0 plflt) (zmax0 plflt) (alt plflt) (az plflt)) (pl-defcfun ("c_plwid" plwid) :void (width plint)) (pl-defcfun ("c_plwind" plwind) :void (xmin plflt) (xmax plflt) (ymin plflt) (ymax plflt)) (pl-defcfun ("c_plxormod" plxormod) :void (mode plbool) (status plbool 1)) ;; Why do plgdevs & plgfiledevs take a char*** when they expect you to allocate enough ;; space for a bunch of pointers to strings anyway? Why not char**? (defun get-strings (c-ptr n) (let ((c-strings (mem-aref c-ptr :pointer)) (strings nil)) (dotimes (i n) (push (foreign-string-to-lisp (mem-aref c-strings :pointer i)) strings)) (reverse strings))) (defun create-char*** () (let ((c-ptr (foreign-alloc :pointer))) (setf (mem-aref c-ptr :pointer) (foreign-alloc :pointer :count 50)) c-ptr)) (defun free-char*** (c-ptr) (foreign-free (mem-aref c-ptr :pointer)) (foreign-free c-ptr)) (defun alist (lst1 lst2) (let ((ret nil)) (dotimes (i (length lst1)) (push (list (elt lst1 i) (elt lst2 i)) ret)) (reverse ret))) (defun generic-devs (devfn) (let* ((c-menu (create-char***)) (c-dev (create-char***)) (ndev (funcall devfn c-menu c-dev)) (al (alist (get-strings c-menu ndev) (get-strings c-dev ndev)))) (free-char*** c-menu) (free-char*** c-dev) al)) (defun plgfiledevs () (generic-devs #'pl-plgfiledevs)) (export 'plgfiledevs (package-name *package*)) (pl-defcfun ("plgFileDevs" pl-plgfiledevs) :void (p_menustr plpointer) (p_devname plpointer) (p_ndev *plint 1)) (defun plgdevs () (generic-devs #'pl-plgdevs)) (export 'plgdevs (package-name *package*)) (pl-defcfun ("plgDevs" pl-plgdevs) :void (p_menustr plpointer) (p_devname plpointer) (p_ndev *plint 1)) ;; These would enable callbacks to user defined functions at various key points in ;; the graphing process. We use plsexit to set our own error handler that will ;; throw a Lisp side error and keep PLplot from calling exit(). ;(defcfun ("plsKeyEH" plskeyeh) :void ; void (*KeyEH) (PLGraphicsIn *, void *, int *), void *KeyEH_data ; ;(defcfun ("plsButtonEH" plsbuttoneh) :void ; void (*ButtonEH) (PLGraphicsIn *, void *, int *), void *ButtonEH_data ; ;(defcfun ("plsbopH" plsboph) :void ; void (*handler) (void *, int *), void *handler_data ; ;(defcfun ("plseopH" plseoph) :void ; void (*handler) (void *, int *), void *handler_data (defcallback trap-plsexit :int ((message plstr)) (error "PLplot error encountered (~A). The current plotting stream is likely corrupted." (foreign-string-to-lisp message))) (defcfun ("plsexit" plsexit) :void (plsexit-fn plfunc)) (plsexit (callback trap-plsexit)) ;(defcfun ("plsabort" plsabort) :void ; void (*handler) (char *) ;; "Set the variables to be used for storing error info"... ;; FIXME: What does this function do? ;(defcfun ("plsError" plserror) :void ; (*errcode plint) ; (*errmsg char)) ;; These functions are designed to be passed as arguments to other plplot functions like ;; the shade series of functions. pltr1 & pltr2 let you interpolate your data onto other ;; non-rectangular grids, but you have to pass them the appropriate information via the ;; pltr_data pointer or they will exit & take down lisp in the process. I've tried to make ;; this a little easier for those functions that might take these as arguments by taking ;; care of the formatting of the pltr_data structure. (defcfun ("pltr0" pltr0) :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr_data plpointer)) (export 'pltr0 (package-name *package*)) (defcfun ("pltr1" pltr1) :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr_data plpointer)) (export 'pltr1 (package-name *package*)) (defcfun ("pltr2" pltr2) :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr_data plpointer)) (export 'pltr2 (package-name *package*)) ;; set which one of these function you want to use, or pass in your own with this closure (callback-closure pltr-fn #'pltr0 :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr-data plpointer)) ;; This one is not supported, if you want to use it then you have to properly handle the formatting of pltr_data. (defcfun ("pltr2p" pltr2p) :void (x plflt) (y plflt) (tx *plflt) (ty *plflt) (pltr_data plpointer)) (export 'pltr2p (package-name *package*)) ;; These are not exported ; ;(defcfun ("pltr0f" pltr0f) :void ; (x plflt) ; (y plflt) ; (tx *plflt) ; (ty *plflt) ; (pltr_data plpointer)) ; ;(defcfun ("pltr2f" pltr2f) :void ; (x plflt) ; (y plflt) ; (tx *plflt) ; (ty *plflt) ; (pltr_data pointer)) ;; No mention of this function anywhere in the plplot docs, but it was in plplot.h. ;; Doesn't seem to be exported however. ;(pl-defcfun ("xform" xform) :void ; (x plflt) ; (y plflt) ; (tx *plflt 1) ; (ty *plflt 1)) ;; These are functions are used by plcont (&others?) to evaluate data on an arbitrary 2D grid (pl-defcfun ("plf2eval2" plf2eval2) plflt (ix plint) (iy plint) (plf2eval_data plpointer)) ; **obj, as created by make-matrix (pl-defcfun ("plf2eval" plf2eval) plflt (ix plint) (iy plint) (plf2eval_data plpointer)) ; *obj as created by foreign-alloc (C ordering) (pl-defcfun ("plf2evalr" plf2evalr) plflt (ix plint) (iy plint) (plf2eval_data plpointer)) ; *obj as created by foreign-alloc (Fortran ordering) (callback-closure feval-fn #'plf2eval2 plflt (ix plint) (iy plint) (plf-data plpointer)) ;; FIXME: These were left out since it wasn't clear to me how to use them. ; ;(pl-defcfun ("plClearOpts" plclearopts) :void) ; ;(pl-defcfun ("plResetOpts" plresetopts) :void) ; ;(defcfun ("plMergeOpts" plmergeopts) :int ; (*options ploptiontable) ; (*name char) ; (**notes char)) (pl-defcfun ("plSetUsage" plsetusage) :void (program_string plstr) (usage_string plstr)) (pl-defcfun ("c_plsetopt" plsetopt) :int (opt plstr) (optarg plstr)) ;not supposed to use this one? ;(pl-defcfun ("plSetOpt" plsetopt) :int ; (opt plstr) ; (optarg plstr)) ;; Options should be a list containing strings of command line options. This ;; works but is commented out due the dangers associated with using it. Uncomment ;; it if you like, but heed the warning... Otherwise plsetopt is a better choice ;; since it won't kill your lisp process if it gets an unrecognized option. ;; ;; Warning: If you get them wrong your lisp session will almost surely meet ;; an untimely end. ; ;(defun plparseopts (options mode) ; (push "foo" options) ; need a dummy zero argument... ; (let* ((nopts (length options)) ; (p_argc (foreign-alloc :int :initial-element nopts)) ; (argv (foreign-alloc :pointer :count nopts))) ; (dotimes (i nopts) ; (setf (mem-aref argv :pointer i) (foreign-string-alloc (elt options i)))) ; (pl-plparseopts p_argc argv mode) ; (foreign-free p_argc) ; (dotimes (i nopts) ; (foreign-string-free (mem-aref argv :pointer i))) ; (foreign-free argv))) ; ;(export 'plparseopts (package-name *package*)) ; ;(pl-defcfun ("c_plparseopts" pl-plparseopts) :int ; (p_argc plpointer) ; (argv plpointer) ; (mode plint)) (pl-defcfun ("plOptUsage" ploptusage) :void) ;; Returns a file pointer that might be useful for passing to another C sub-routine ;; that wants to add something to the current plplot output file. (defun plgfile () (let ((fp (foreign-alloc :pointer))) (unwind-protect (progn (pl-plgfile fp) (mem-aref fp :pointer)) (foreign-free fp)))) (export 'plgfile (package-name *package*)) (defcfun ("plgfile" pl-plgfile) :void (p_file plpointer)) ;; Opens a file, typically used with file output plotting drivers. ;; FIXME: what is the right file mode?? Does it matter? (defun plsfile (fname) (let ((name (foreign-string-alloc fname)) (mode (foreign-string-alloc "wb"))) (unwind-protect (pl-plsfile (fopen name mode)) (progn (foreign-string-free name) (foreign-string-free mode))))) (export 'plsfile (package-name *package*)) (defcfun ("fopen" fopen) :pointer (name plstr) (mode plstr)) (defcfun ("plsfile" pl-plsfile) :void (file plpointer)) (pl-defcfun ("plgesc" plgesc) :void (p_esc *plchar 1)) (pl-defcfun ("pl_cmd" pl-cmd) :void (op plint) (ptr plpointer)) ;(defcfun ("pl_cmd" pl-cmd) :void ; PLINT op, void *ptr ; ;; These seem to be used for finding system commands & executables. ;; Currently not supported since there are probably better ways. ; ;(pl-defcfun ("plFindName" plfindname) :int ; (p plstr 80)) ; ;(defcfun ("plFindCommand" plfindcommand) :char * ; (*fn char)) ; ;(defcfun ("plGetName" plgetname) :void ; (*dir char) ; (*subdir char) ; (*filename char) ; (**filespec char)) (pl-defcfun ("plGetInt" plgetint) plint (s plstr)) (pl-defcfun ("plGetFlt" plgetflt) plflt (s plstr)) (pl-defcfun ("plAlloc2dGrid" plalloc2dgrid) :void (f plpointer) (nx plint) (ny plint)) (pl-defcfun ("plFree2dGrid" plfree2dgrid) :void (f plpointer) (nx plint) (ny plint)) (pl-defcfun ("plMinMax2dGrid" plminmax2dgrid) :void (f **plflt (nx ny)) (nx plint) (ny plint) (fmax *plflt 1) (fmin *plflt 1)) ;; Mouse events, this structure has a lot of members... And a 16 byte string right ;; in the middle to add to the fun... ;(defparameter plg-offset (+ 16 (* (foreign-type-size :int)))) (defmacro init-plgraphicsin () `(defcstruct plgraphicsin (type plint) ; 2 bytes (start plint) ; 2 bytes (keysym plint) ; 2 bytes (button plint) ; 2 bytes (subwindow plint) ; 2 bytes (string :pointer) ; 16 bytes (pX plint :offset ,(+ 16 (* 5 (foreign-type-size 'plint)))) (pY plint) (dX plflt) (dY plflt) (wX plflt) (wY plflt))) (init-plgraphicsin) (defun init-slots (pin) (with-foreign-slots ((type start keysym button subwindow pX pY dX dY wX wY) pin plgraphicsin) (setf type -1) (setf start -1) (setf keysym -1) (setf button -1) (setf subwindow -1) (setf pX -1) (setf pY -1) (setf dX -1.0d0) (setf dY -1.0d0) (setf wX -1.0d0) (setf wY -1.0d0))) ;; This works in that it seems to return the correct X & Y coordinates of the mouse click (in pixels). ;; I'm not so sure about subwindow, but maybe I don't get that parameter. (defun plgetcursor () (with-foreign-object (pin 'plgraphicsin) (init-slots pin) (pl-plgetcursor pin) (with-foreign-slots ((start keysym button subwindow pX pY dX dY wX wY) pin plgraphicsin) (list start keysym button subwindow pX pY dX dY wX wY)))) ; (list start keysym button subwindow (foreign-string-to-lisp (foreign-slot-value pin 'plgraphicsin 'string)) pX pY dX dY wX wY)))) (export 'plgetcursor (package-name *package*)) (defcfun ("plGetCursor" pl-plgetcursor) plint (gin :pointer)) (defun pltranslatecursor (dX dY) (with-foreign-object (pin 'plgraphicsin) (init-slots pin) (setf (foreign-slot-value pin 'plgraphicsin 'dX) (coerce dX 'double-float)) (setf (foreign-slot-value pin 'plgraphicsin 'dY) (coerce dY 'double-float)) (pl-pltranslatecursor pin) (with-foreign-slots ((wX wY) pin plgraphicsin) (list wX wY)))) (export 'pltranslatecursor (package-name *package*)) (defcfun ("plTranslateCursor" pl-pltranslatecursor) plint (gin :pointer)) ;; The following functions are in plplot.h but are deprecated. ;; Presumably they will dissappear someday. ; ;(defcfun ("plParseOpts" plparseopts) :int ; (*p_argc int) ; (**argv char) ; (mode plint)) (pl-defcfun ("plHLS_RGB" plhls-rgb) :void (h plflt) (l plflt) (s plflt) (p_r *plflt 1) (p_g *plflt 1) (p_b *plflt 1)) (pl-defcfun ("plRGB_HLS" plrgb-hls) :void (r plflt) (g plflt) (b plflt) (p_h *plflt 1) (p_l *plflt 1) (p_s *plflt 1)) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/system/loadlib.lisp0000644000175000017500000000355410745233560020123 0ustar hbabcockhbabcock;;;; ;;;; Defines the cl-plot package. ;;;; Loads the plplot library (libplplotd) and the standard C library (libc). ;;;; ;;;; hazen 3/06 ;;;; (in-package #:cl-user) (defpackage #:cl-plplot-system (:use #:common-lisp #:cffi)) (in-package #:cl-plplot-system) (defun load-libraries () ; linux (pushnew #P"/usr/local/lib/" *foreign-library-directories* :test #'equal) ; OS-X / fink (pushnew #P"/sw/lib/" *foreign-library-directories* :test #'equal) ; OS-X / darwinports (pushnew #P"/opt/local/lib/" *foreign-library-directories* :test #'equal) (define-foreign-library libplplot (t (:default "libplplotd"))) (use-foreign-library libplplot) (format t "libplplotd library loaded~%")) (load-libraries) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/system/misc.lisp0000644000175000017500000001700611416201173017434 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Miscellaneous functions & macros that are used in the cl-plot API ;;;; ;;;; hazen 3/06 ;;;; (in-package #:cl-plplot-system) ;;; ;;; These are for dealing with passing in the plcgrid structure, which is then passed ;;; to various coordinate transformation functions (i.e. pltr0, pltr1 & pltr2). ;;; (defcstruct plcgrid (x plpointer) (y plpointer) (z plpointer) (nx plint) (ny plint) (nz plint)) (defun check-size (a mx my) "checks that p-d has the right dimensions" (and (or (= (array-dimension a 0) mx) (= (array-dimension a 0) (1+ mx))) (or (= (array-dimension a 1) my) (= (array-dimension a 1) (1+ my))))) (defun init-plcgrid (pdx pdy mx my) "initializes plcgrid given user supplied pdx & pdy, if necessary" (cond ((equal (pl-get-pltr-fn) #'pltr0) (values (null-pointer) 'empty-p)) ((equal (pl-get-pltr-fn) #'pltr1) (if (and (vectorp pdx) (vectorp pdy) (= (length pdx) mx) (= (length pdy) my)) (let ((tmp (foreign-alloc 'plcgrid))) (with-foreign-slots ((x y nx ny) tmp plcgrid) (setf x (make-ptr pdx 'plflt #'(lambda(x) (coerce x 'double-float)))) (setf y (make-ptr pdy 'plflt #'(lambda(x) (coerce x 'double-float)))) (setf nx (length pdx)) (setf ny (length pdy))) (values tmp 'vector-p)) (progn (format t "Array dimensions are wrong for pdx or pdy in init-plcgrid~%") (values nil nil)))) ((equal (pl-get-pltr-fn) #'pltr2) (if (and (arrayp pdx) (arrayp pdy) (check-size pdx mx my) (check-size pdy mx my)) (let ((tmp (foreign-alloc 'plcgrid))) (with-foreign-slots ((x y nx ny) tmp plcgrid) (setf x (make-matrix pdx)) (setf y (make-matrix pdy)) (setf nx (array-dimension pdx 0)) (setf ny (array-dimension pdx 1))) (values tmp 'matrix-p)) (progn (format t "Matrix dimensions are wrong for pdx or pdy in init-plcgrid~%") (values nil nil)))) ; this has fewer safeguards... (t (cond ((and (vectorp pdx) (vectorp pdy)) (let ((tmp (foreign-alloc 'plcgrid))) (with-foreign-slots ((x y nx ny) tmp plcgrid) (setf x (make-ptr pdx 'plflt #'(lambda(x) (coerce x 'double-float)))) (setf y (make-ptr pdy 'plflt #'(lambda(x) (coerce x 'double-float)))) (setf nx (length pdx)) (setf ny (length pdy))) (values tmp 'vector-p))) ((and (arrayp pdx) (arrayp pdy)) (let ((tmp (foreign-alloc 'plcgrid))) (with-foreign-slots ((x y nx ny) tmp plcgrid) (setf x (make-matrix pdx)) (setf y (make-matrix pdy)) (setf nx (array-dimension pdx 0)) (setf ny (array-dimension pdy 0))) (values tmp 'matrix-p))) ((not pdx) (values (null-pointer) 'empty-p)) (t (values pdx 'user-p)))))) (defun free-plcgrid (p-grid type) "frees the plcgrid structure, if necessary" (cond ((equal type 'vector-p) (progn (with-foreign-slots ((x y) p-grid plcgrid) (foreign-free x) (foreign-free y)) (foreign-free p-grid))) ((equal type 'matrix-p) (progn (with-foreign-slots ((x y nx ny) p-grid plcgrid) (let ((dims (list nx ny))) (free-matrix x dims) (free-matrix y dims))) (foreign-free p-grid))) (t nil))) (defmacro with-plcgrid ((plc-grid pdx pdy mx my) &body body) (let ((type (gensym))) `(multiple-value-bind (,plc-grid ,type) (init-plcgrid ,pdx ,pdy ,mx ,my) (when ,plc-grid ,@body (free-plcgrid ,plc-grid ,type))))) ;;; ;;; Some plplot functions require callbacks. These callbacks are inside closures so that user ;;; can more easily provide their own callback functions. This macro is for making the closures. ;;; (defmacro callback-closure (fname default returns &rest variables) "Encloses a callback function in a closure so that the user can substitute the function of their own choosing" (let ((var-name (name-cat "my-" fname))) `(let ((,var-name ,default)) (defcallback ,fname ,returns ,variables (funcall ,var-name ,@(mapcar #'(lambda(x) (car x)) variables))) (defun ,(name-cat "pl-set-" fname) (new-fn) (setf ,var-name new-fn)) (defun ,(name-cat "pl-reset-" fname) () (setf ,var-name ,default)) (defun ,(name-cat "pl-get-" fname) () ,var-name) (export ',(name-cat "pl-set-" fname) (package-name *package*)) (export ',(name-cat "pl-reset-" fname) (package-name *package*)) (export ',(name-cat "pl-get-" fname) (package-name *package*))))) ;;; ;;; Some plplot functions need a pointer even if they aren't going to do anything with it. This ;;; function wraps CFFI's null-pointer so that user doesn't have to load CFFI just to pass a ;;; null pointer ;;; (defun pl-null-pointer () (null-pointer)) (export 'pl-null-pointer (package-name *package*)) ;;; ;;; These are the structures for interfacing with the plf... functions ;;; in PLplot. There are also some macros to make things a little ;;; easier. ;;; (defcstruct plfgrid (f :pointer) (nx :int) (ny :int)) (defcstruct plfgrid2 (f :pointer) (nx :int) (ny :int)) (defun is-matrix-p (item) (= (length (array-dimensions item)) 2)) (defun lisp-data-to-foreign (lisp-data) (if (is-matrix-p lisp-data) (make-matrix lisp-data) (make-ptr lisp-data 'plflt (lambda (x) (coerce x 'double-float))))) (defun create-grid (c-data size-x size-y) (let ((ptr (foreign-alloc 'plfgrid2))) (setf (foreign-slot-value ptr 'plfgrid2 'f) c-data (foreign-slot-value ptr 'plfgrid2 'nx) size-x (foreign-slot-value ptr 'plfgrid2 'ny) size-y) ptr)) (export 'create-grid (package-name *package*)) (defmacro with-foreign-grid ((grid lisp-data size-x size-y) &body body) (let ((c-data (gensym))) `(let* ((,c-data (lisp-data-to-foreign ,lisp-data)) (,grid (create-grid ,c-data ,size-x ,size-y))) (unwind-protect ,@body (progn (if (is-matrix-p ,lisp-data) (cl-plplot-system::free-matrix ,c-data (list (array-dimension ,lisp-data 0) (array-dimension ,lisp-data 1))) (foreign-free ,c-data)) (foreign-free ,grid)))))) (export 'with-foreign-grid (package-name *package*)) (defmacro with-foreign-matrix ((lisp-matrix foreign-matrix) &body body) `(let ((,foreign-matrix (make-matrix ,lisp-matrix))) (unwind-protect ,@body (free-matrix ,foreign-matrix (list (array-dimension ,lisp-matrix 0) (array-dimension ,lisp-matrix 1)))))) (export 'with-foreign-matrix (package-name *package*)) cl-plplot-0.6.0/src/system/defcfun.lisp0000644000175000017500000003714211413122171020113 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Functions & macros to facilitate wrapping of calls to the plplot API, ;;;; ;;;; The goal of all this macrology is to have : ;;;; ;;;; (pl-defcfun ("foo" foo) :int ;;;; (x plint) ;;;; (y *plint n) ;;;; (z *plflt n) ;;;; (n plint)) ;;;; ;;;; Expand into (progn statements removed) : ;;;; ;;;; (DEFCFUN ("foo" C-FOO) :INT ;; "raw" cffi function ;;;; (X PLINT) ;;;; (Y *PLINT) ;;;; (Z *PLFLT) ;;;; (N PLINT)) ;;;; ;;;; (EXPORT 'C-FOO (PACKAGE-NAME *PACKAGE*)))) ;;;; ;;;; (DEFUN FOO (X Y Z) ;; "more friendly" lisp function ;;;; (LET ((C-Y (MAKE-PTR Y :INT #'(LAMBDA (X) (ROUND X)))) ;;;; (C-Z (MAKE-PTR Z :DOUBLE #'(LAMBDA (X) (COERCE X 'DOUBLE-FLOAT)))) ;;;; (N (LENGTH Z))) ;;;; (UNWIND-PROTECT ;;;; (C-FOO (FUNCALL #'(LAMBDA (X) (ROUND X)) X) ;;;; C-Y ;;;; C-Z ;;;; (FUNCALL #'(LAMBDA (X) (ROUND X)) N)) ;;;; (PROGN ;;;; (FOREIGN-FREE C-Y) ;;;; (FOREIGN-FREE C-Z))))) ;;;; ;;;; (EXPORT 'FOO (PACKAGE-NAME *PACKAGE*)))) ;;;; ;;;; ;;;; More complicated function definitions with different type are also supported. ;;;; ;;;; hazen 3/06 ;;;; (in-package #:cl-plplot-system) ;; ;; Setup the form containing the list of types and their initializers & destroyers ;; ;; *type-forms* is an associated list containing functions that generate the forms ;; necessary to create, coerce, pass, return & free a particular type. ;; ;; A *type-forms* entry for a simple type (i.e. single element & only passed in) contains: ;; (type-name conversion-function) ;; ;; A *type-forms* entry for a "complex" type (everything else) contains: ;; (type-name arg-function creation-function passing-function returning-function freeing-function) ;; ;; These functions will be passed the form associated with a particular variable. ;; For example, if we have the form for the variable x as (x *plint n), then ;; creation-function will get '(x *plint n) as its argument. Creation-function ;; will use this form to generate a form to create the variable, or return nil ;; if no creation form is necessary. For the above example it might return: ;; ((c-x (make-ptr x :int #'(lambda (x) (round x)))) ;; (n (length x))) ;; ;; Expected behaviors: ;; arg-function : Returns a form containing variables that do *NOT* need to be included ;; in the lisp function call. This might be because this is an output variable or because ;; this variable is only used to pass in the size of another variable. Can be nil. ;; ;; create-function : Returns a form that creates the "c" variable that will be passed to the ;; c function created by cffi's defcfun macro. Can be nil. May optionally initialize other ;; variables such as those that are used to pass in the variable sizes, etc... ;; ;; passing-function : Returns a form or symbol to be used in the call to the c function. ;; ;; returning-function : Returns a form that creates a lisp object from the "c" variable that ;; will be returned as a result of the function call. Can be nil. ;; ;; freeing-function : Returns a form that will take care of cleaning up the "c" variable ;; when the function call exits. Can be nil. ;; (defvar *type-forms* nil) (defun name-cat (name1 name2 &rest more-names) "returns the concatenation of a and b as a symbol" (let ((final (concatenate 'string (string name1) (string name2)))) (dolist (name more-names) (setf final (concatenate 'string final (string name)))) (read-from-string final))) ;; FIXME: ;; Paraphrasing Norvig, "If you are using eval you are probably doing something wrong". ;; How do you do this without using eval??? (defun add-simple-type (type-name cffi-type conv-fn) "Adds a simple type to *type-forms*, i.e. a type that we do little to no handling of" (eval `(defctype ,type-name ,cffi-type)) (push (list type-name conv-fn) *type-forms*)) (defun add-type (type-name cffi-type args-fn create-fn pass-fn return-fn free-fn) "Adds type to *type-forms* list of types" (eval `(defctype ,type-name ,cffi-type)) (push (list type-name args-fn create-fn pass-fn return-fn free-fn) *type-forms*)) (defun c-name (args) "Returns a symbol that is used as a temporary variable name for passing a lisp argument to a c function" (name-cat "c-" (car args))) ; (read-from-string (concatenate 'string "c-" (string (car args))))) ;; Functions for adding functions for standard types to *type-forms* (defconstant p-in 1) (defconstant p-in-out 0) (defconstant p-out -1) (defun in-out? (args) "Returns whether this argument is passed in, passed out or both" (cond ((and (> (length args) 2) (numberp (elt args 2))) p-out) ((and (> (length args) 2) (string= "IN-OUT" (string (elt args 2)))) p-in-out) (t p-in))) (defun ptr-name-dir (args) "Returns pointer name & direction" (values (c-name args) (in-out? args))) (defun std-args (args) "Standard arg-function" (let ((tmp (in-out? args))) (cond ((= tmp p-in) `,(elt args 2)) ((= tmp p-out) `,(elt args 0))))) (defun std-creating (cffi-type convf-in) "Returns standard creating-function" (labels ((create-fn (args) (multiple-value-bind (name dir) (ptr-name-dir args) (cond ((= dir p-in) `((,(elt args 2) (if (eq ,(elt args 0) 'null) 0 (length ,(elt args 0)))) (,name (if (eq ,(elt args 0) 'null) (null-pointer) (make-ptr ,(elt args 0) ,cffi-type ,convf-in))))) ; `((,(elt args 2) (length ,(elt args 0))) ; (,name (make-ptr ,(elt args 0) ,cffi-type ,convf-in)))) ((= dir p-in-out) `(,name (make-ptr (vector ,(elt args 0)) ,cffi-type ,convf-in))) ((= dir p-out) `(,name (foreign-alloc ,cffi-type :count ,(elt args 2)))))))) #'create-fn)) (defun std-passing (args) "Standard passing-function" `,(c-name args)) (defun std-returning (lisp-type cffi-type convf-out) "Returns standard creating-function" (labels ((return-fn (args) (multiple-value-bind (name dir) (ptr-name-dir args) (cond ((= dir p-in-out) `(funcall ,convf-out (mem-aref ,name ,cffi-type 0))) ((= dir p-out) (if (= 1 (elt args 2)) `(funcall ,convf-out (mem-aref ,name ,cffi-type 0)) `(get-ptr ,name ,lisp-type ,cffi-type ,convf-out ,(elt args 2)))))))) #'return-fn)) (defun std-freeing (args) "Standard freeing-function" ; `(foreign-free ,(c-name args))) (multiple-value-bind (name dir) (ptr-name-dir args) (declare (ignore name)) (cond ((= dir p-in) `(unless (eq ,(elt args 0) 'null) (foreign-free ,(c-name args)))) (t `(foreign-free ,(c-name args)))))) (defun ptr-name (x) "Returns name of pointer to type x (used for 'standard' types)" (name-cat "*" x)) ; (read-from-string (concatenate 'string "*" (string x)))) (defun get-ptr (c-arr lisp-type cffi-type conv-func length) "Copies a C array into a newly created lisp vector" (let ((l-vec (make-array length :element-type lisp-type))) (dotimes (i length) (setf (aref l-vec i) (funcall conv-func (mem-aref c-arr cffi-type i)))) l-vec)) (defun make-ptr (arr cffi-type conv-func) "Copies a lisp vector into a newly created C array" (let* ((n (length arr)) (c-arr (foreign-alloc cffi-type :count n))) (dotimes (i n) (setf (mem-aref c-arr cffi-type i) (funcall conv-func (aref arr i)))) c-arr)) (defun make-matrix (lisp-mat) "Creates a two-dimensional c array, initializes with lisp matrix" (let* ((x-dim (array-dimension lisp-mat 0)) (y-dim (array-dimension lisp-mat 1)) (c-mat (foreign-alloc :pointer :count x-dim))) (dotimes (x x-dim) (let ((cur (foreign-alloc :double :count y-dim))) (setf (mem-aref c-mat :pointer x) cur) (dotimes (y y-dim) (setf (mem-aref cur :double y) (coerce (aref lisp-mat x y) 'double-float))))) c-mat)) (defun free-matrix (c-mat dims) "Frees a two-dimensional c array" (dotimes (x (car dims)) (foreign-free (mem-aref c-mat :pointer x))) (foreign-free c-mat)) (defun add-std-type (type-name cffi-type lisp-type convf-in convf-out &optional (want-arrays t)) "Creates items in the *type-forms* list for 'standard' types, i.e. those things like integers, floats, etc.. which are all created & returned & destroyed in the same way. If want-arrays is true, the a type of name *type-name will also be created. This type can be used for passing in/out arrays of the values of this type" (add-simple-type type-name cffi-type #'(lambda (args) `(funcall ,convf-in ,(elt args 0)))) (when want-arrays (add-type (ptr-name type-name) :pointer #'std-args (std-creating cffi-type convf-in) #'std-passing (std-returning lisp-type cffi-type convf-out) #'std-freeing))) ;; Initialization of *type-forms* (alphabetical order by type name) (setf *type-forms* nil) (add-std-type 'plbool :int 'fixnum '#'(lambda(x) (if x 1 0)) '#'(lambda (x) (if (= x 0) nil t))) (add-std-type 'plchar :char 'character '#'(lambda(x) (char-code x)) '#'(lambda(x) (code-char x))) (add-type 'plfunc :pointer #'(lambda (args) `,(elt args 0)) #'(lambda (args) (declare (ignore args)) nil) #'(lambda (args) `(callback ,(elt args 0))) #'(lambda (args) (declare (ignore args)) nil) #'(lambda (args) (declare (ignore args)) nil)) (add-std-type 'plflt :double 'double-float '#'(lambda(x) (coerce x 'double-float)) '#'(lambda(x) (coerce x 'double-float))) (add-type '**plflt :pointer #'(lambda (args) `,(elt args 2)) #'(lambda (args) `((,(car (elt args 2)) (array-dimension ,(elt args 0) 0)) (,(cadr (elt args 2)) (array-dimension ,(elt args 0) 1)) (,(c-name args) (make-matrix ,(elt args 0))))) #'std-passing #'(lambda (args) (declare (ignore args)) nil) #'(lambda (args) `(free-matrix ,(c-name args) (list ,(car (elt args 2)) ,(cadr (elt args 2)))))) (add-std-type 'plint :int 'fixnum '#'(lambda(x) (round x)) '#'(lambda(x) (round x))) (add-simple-type 'plpointer :pointer #'(lambda(x) `,(elt x 0))) (add-type 'plstr :pointer #'(lambda (args) (when (= p-out (in-out? args)) `,(elt args 0))) #'(lambda (args) (if (= p-in (in-out? args)) `(,(c-name args) (foreign-string-alloc ,(elt args 0))) `(,(c-name args) (foreign-alloc :char :count ,(elt args 2))))) #'std-passing #'(lambda (args) (when (= p-out (in-out? args)) `(foreign-string-to-lisp ,(c-name args)))) #'(lambda (args) `(foreign-string-free ,(c-name args)))) (add-std-type 'plunicode :uint32 'fixnum '#'(lambda (x) (round x)) '#'(lambda (x) (round x))) ;; ;; Create the form that specifies a function call ;; ;; Helper functions (defun args-flatten (lst) "Flattens list lst" (let ((out nil)) (labels ((fl (cur) (when cur (if (listp cur) (progn (fl (car cur)) (fl (cdr cur))) (push cur out))))) (fl lst)) out)) (defun setup-flatten (lst) "Flattens setup list lst, as necessary" (let ((out nil)) (dolist (obj lst) (if (listp (car obj)) (dolist (s-obj obj) (push s-obj out)) (push obj out))) (reverse out))) ;; Generation of different parts of the function call (defun lisp-arguments (lst) "Creates the list of arguments that the lisp function will take" (let ((setup (args-flatten (remove nil (mapcar #'(lambda (x) (let ((type-info (assoc (elt x 1) *type-forms*))) (when (= (length type-info) 6) (funcall (elt type-info 1) x)))) lst)))) (passed (mapcar #'(lambda (x) (car x)) lst))) (dolist (elem setup) (when (member elem passed :test #'equal) (setf passed (remove elem passed)))) passed)) (defun lisp-setup (lst) "Creates the code to setup on the lisp side for the c function call" (remove-duplicates (setup-flatten (remove nil (mapcar #'(lambda (x) (let ((type-info (assoc (elt x 1) *type-forms*))) (when (= (length type-info) 6) (funcall (elt type-info 2) x)))) lst))) :test #'(lambda (x y) (equal (car x) (car y))))) (defun lisp-call (lst) "Creates the code on the lisp side to call the c function" (mapcar #'(lambda (x) (let ((type-info (assoc (elt x 1) *type-forms*))) (if (= (length type-info) 6) (funcall (elt type-info 3) x) (funcall (elt type-info 1) x)))) lst)) (defun lisp-return (lst) "Creates the code to return variable values if necessary" (remove nil (mapcar #'(lambda (x) (let ((type-info (assoc (elt x 1) *type-forms*))) (when (= (length type-info) 6) (funcall (elt type-info 4) x)))) lst))) (defun lisp-cleanup (lst) "Creates the code necessary to clean up after the function call" (remove nil (mapcar #'(lambda (x) (let ((type-info (assoc (elt x 1) *type-forms*))) (when (= (length type-info) 6) (funcall (elt type-info 5) x)))) lst))) ;; Sews together the forms generated above to create the final function call (defun %pl-defcfun (cffi-name lisp-name fn-returns args) "Creates the lisp wrapper code for calling the lisp function created by defcfun & called cffi-name" (let ((setup (lisp-setup args)) (retrn (lisp-return args))) `(progn (defun ,lisp-name ,(lisp-arguments args) ,(if setup `(let ,setup (unwind-protect ,(if retrn (if (string= "VOID" (string fn-returns)) `(progn (,cffi-name ,@(lisp-call args)) (values ,@retrn)) `(values (,cffi-name ,@(lisp-call args)) ,@retrn)) `(,cffi-name ,@(lisp-call args))) (progn ,@(lisp-cleanup args)))) `(,cffi-name ,@(lisp-call args)))) (export ',lisp-name (package-name *package*))))) (defun cffi-defcfun (c-name lisp-name returns args) "Creates defcfun macro call. The defcfun macro is used to create the call to the c library function as well as its lisp counterpart" `(progn (defcfun (,c-name ,lisp-name) ,returns ,@(mapcar #'(lambda (x) `(,(elt x 0) ,(elt x 1))) args)) (export ',lisp-name (package-name *package*)))) (defmacro pl-defcfun (name returns &rest args) "Function creation macro, wraps defcfun to handle most styles of function call in the plplot library" ; (let ((cffi-name (read-from-string (concatenate 'string "c-" (string (elt name 1)))))) (let ((cffi-name (name-cat "c-" (elt name 1)))) `(progn ,(cffi-defcfun (elt name 0) cffi-name returns args) ,(%pl-defcfun cffi-name (elt name 1) returns args)))) cl-plplot-0.6.0/src/examples/0000755000175000017500000000000011427546035016111 5ustar hbabcockhbabcockcl-plplot-0.6.0/src/examples/x25l.lisp0000644000175000017500000000465311422632173017576 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 25 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example25 (&optional (dev default-dev)) (plsdev dev) (let ((xextreme (vector (vector -120 -120 -120 -80 -220 -20 -20 -80 20) (vector 120 120 120 80 -120 20 20 80 120))) (yextreme (vector (vector -120 20 -20 -20 -120 -120 -20 -80 -120) (vector 120 120 120 120 120 120 20 80 120)))) (plssub 3 3) (plinit) (dotimes (k 2) (dotimes (j 4) (let ((x0 (cond ((= j 0) (vector 0 -100 0 100)) ((= j 1) (vector 100 0 -100 0)) ((= j 2) (vector -100 -100 80 -100 -100 -80 0 80 100 100)) (t (vector 100 100 80 0 -80 -100 -100 80 -100 -100)))) (y0 (cond ((= j 0) (vector -100 0 100 0)) ((= j 1) (vector 0 100 0 -100)) ((= j 2) (vector -100 -80 0 80 100 100 80 100 100 -100)) (t (vector -100 100 100 80 100 100 80 0 -80 -100))))) (dotimes (i 9) (pladv 0) (plvsta) (plwind (aref (aref xextreme 0) i) (aref (aref xextreme 1) i) (aref (aref yextreme 0) i) (aref (aref yextreme 1) i)) (plcol0 2) (plbox "bc" 1.0 0 "bcnv" 10.0 0) (plcol0 1) (plpsty 0) (if (= k 0) (plfill x0 y0) (plgradient x0 y0 45.0)) (plcol0 2) (pllsty 1) (plline x0 y0))))) (plend1))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/window-examples.lisp0000644000175000017500000004151210756454561022136 0ustar hbabcockhbabcock;;;; ;;;; Examples that demonstrate using cl-plplot to make 2D & 3D plots. ;;;; ;;;; hazen 12/06 ;;;; (defpackage :window-examples (:use :common-lisp :cl-plplot)) (in-package :window-examples) ;;; Helper functions (defun my-make-vector (dim init-fn) (let ((vec (make-array dim :initial-element 0.0 :element-type 'float))) (dotimes (i dim) (setf (aref vec i) (funcall init-fn i))) vec)) (defun my-make-matrix (dim1 dim2 init-fn) (let ((mat (make-array (list dim1 dim2) :initial-element 0.0 :element-type 'float))) (dotimes (x dim1) (dotimes (y dim2) (setf (aref mat x y) (funcall init-fn x y)))) mat)) (defun my-make-bar-graph-data (rows cols) (let ((data (make-array (list rows cols) :initial-element 0.0 :element-type 'float))) (dotimes (i rows) (dotimes (j cols) (setf (aref data i j) (+ i j)))) data)) (defun my-contour-plot-fn (x y) (let ((tx (- (* 0.02 x) 0.5)) (ty (- (* 0.02 y) 0.5))) (- (* tx tx) (* ty ty) (* (sin (* 7 tx)) (* (cos (* 7 ty))))))) ;; You may need to change these to reflect the plplot drivers available on your system ;; If the Slime REPL hangs when you run one of these examples, it may be because the device ;; was not available. When this happens you should be able to specify a different device ;; in the inferior lisp buffer. (defparameter g-dev "aqt") ;;; X-Y-Plots ;; The simplest plot (defun basic-plot-1 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y)) (w (basic-window))) (add-plot-to-window w p) (render w g-dev))) ;; The same plot with a user defined y-axis range (defun basic-plot-1.1 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y)) (w (basic-window :y-axis-min -5.0 :y-axis-max 50.0))) (add-plot-to-window w p) (render w g-dev))) ;; Here we add our own labels to the plot, change the size & add another piece of data with ;; a heavier red line. (defun basic-plot-2 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p1 (new-x-y-plot x y)) (p2 (new-x-y-plot x x :color :red :line-width 2)) (w (basic-window :x-label "x" :y-label "y" :title "my graph"))) (add-plot-to-window w p1) (add-plot-to-window w p2) (render w g-dev :size-x 400 :size-y 300))) ; (render w "png" :filename "/Users/hbabcock/test.png" :size-x 400 :size-y 300))) ;; Here we change the background and foreground colors & the x axis ticks & the ;; y axis format and the x axis font size. (defun basic-plot-3 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p1 (new-x-y-plot x y :color :blue)) (w (basic-window :title "" :foreground-color :red :background-color :black))) (edit-window-axis w :x :major-tick-interval 0.5 :minor-tick-number 10 :properties '(:draw-bottom/left :major-tick-grid :invert-ticks :major-tick-labels-above/right :major-ticks :minor-ticks)) (add-plot-to-window w p1) (render w g-dev))) ;; Here we demonstrate some of the text capabilities. (defun basic-plot-4 () (let ((w (basic-window)) (l1 (new-text-label (new-text-item (roman-font "x" (superscript "2") "!") :font-size 2.0 :text-color :blue) 0.5 0.2)) (l2 (new-text-label (new-text-item (roman-font "test1 " (italic-font "test2 ") "test3") :font-size 2.0 :text-color :red) 0.5 0.4)) (l3 (new-text-label (new-text-item (roman-font (unicode-char "967") (unicode-char "968")) :font-size 2.0 :text-color :green) 0.5 0.6))) (add-text-label-to-window w l1) (add-text-label-to-window w l2) (add-text-label-to-window w l3) (render w g-dev))) ;; Here we plot one set of data as points & the other as a dashed blue line. (defun basic-plot-5 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p1 (new-x-y-plot x y :line-width 0 :symbol-size 6.0 :symbol-type 1)) (p2 (new-x-y-plot x x :color :blue :line-style 2)) (w (basic-window))) (add-plot-to-window w p1) (add-plot-to-window w p2) (render w g-dev))) ;; Here we make a simple plot & then get the x-y coordinates of the next mouse ;; click (on the plot). Note that the coordinate scale for the mouse click location ;; is the same as those on the axises of the graph. Once we have the mouse ;; location we generate a new graph with the line going through this point ;; by taking advantage of the fact that by setting copy to :nil we have told ;; x-y-plot to store a reference to the vectors x & y rather then copying x & y. (defun basic-plot-6 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y :copy nil)) (w (basic-window))) (add-plot-to-window w p) (multiple-value-bind (mx my) (get-cursor w g-dev) (format t "You clicked : <~,2f, ~,2f>~%" mx my) (setf (aref x 20) mx) (setf (aref y 20) my)) (render w g-dev))) ;; Here we make a plot with some error bars in x & y ;; Note that error bar is drawn with the total length given by the error bar ;; vector & centered on the data point. (defun basic-plot-7 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (x-err (my-make-vector 40 #'(lambda(x) (declare (ignore x)) 0.06))) (y-err (my-make-vector 40 #'(lambda(x) (declare (ignore x)) 1.0))) (p (new-x-y-plot x y :x-error x-err :y-error y-err)) (w (basic-window))) (add-plot-to-window w p) (render w g-dev))) ;; Here we make our own color table with 2-3 colors, set window to use our new ;; color table instead of the default & then change the foreground color in ;; the color table. ;; ;; See also: src/window/color-table.lisp for a brief introduction of color handling. (defun basic-plot-8 () (let* ((c (new-color-table (vector 0 0 0 :color1))) (x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y)) (w (basic-window))) (add-plot-to-window w p) (add-color-to-color-table c (vector 255 0 0 :color2)) (set-color-table w c) (render w g-dev) (add-color-to-color-table c (vector 255 255 255 :color3)) (edit-x-y-plot p :color :color3) (edit-window w :foreground-color :color1 :background-color :color2) (render w g-dev) (remove-color-from-color-table c :color2) nil)) ;;; Bar graphs ;; Here we make a simple bar graph (defun bar-graph-1 () (let* ((y (my-make-vector 10 #'(lambda(x) (* (* 0.2 x) (* 0.2 x))))) (b (new-bar-graph nil y :fill-colors (vector :grey))) (w (basic-window))) (add-plot-to-window w b) (render w g-dev))) ;; Stacked bar graph (defun bar-graph-2 () (let* ((y (my-make-bar-graph-data 10 3)) (b (new-bar-graph nil y :line-colors (vector :black :black :black))) (w (basic-window))) (add-plot-to-window w b) (render w g-dev))) ;; A Side by side bar graph (defun bar-graph-3 () (let* ((y (my-make-bar-graph-data 10 3)) (b (new-bar-graph nil y :side-by-side t :line-colors (vector :black :black :black))) (w (basic-window))) (add-plot-to-window w b) (render w g-dev))) ;; Bar graph with custom spacing & widths (defun bar-graph-4 () (let* ((x (my-make-vector 10 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 10 #'(lambda(x) (- (* (* 0.2 x) (* 0.2 x)) 1)))) (s (my-make-vector 10 #'(lambda(x) (+ 0.05 (* 0.005 x))))) (b (new-bar-graph x y :bar-widths s :fill-colors (vector :grey))) (w (basic-window))) (add-plot-to-window w b) (render w g-dev))) ;; A side by side bar graph with custom widths (defun bar-graph-5 () (let* ((y (my-make-bar-graph-data 10 3)) (s (my-make-vector 10 #'(lambda(x) (+ 0.1 (* 0.05 (sqrt x)))))) (b (new-bar-graph nil y :bar-widths s :side-by-side t :line-colors (vector :black :black :black))) (w (basic-window))) (add-plot-to-window w b) (render w g-dev))) ;;; Contour Plots ;; A simple contour plot (defun contour-plot-1 () (let ((c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue :line-width 2)) (w (basic-window))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot rescaled with filled contours (defun contour-plot-2 () (let ((c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :x-min 0.0 :x-max 1.0 :y-min 0.0 :y-max 1.0 :fill-type :block :fill-colors (vector :red :grey :blue :yellow :green))) (w (basic-window))) (add-plot-to-window w c) (render w g-dev))) ;; Plotted on a user defined simple grid with smooth shading between contours (defun contour-plot-3 () (let* ((xp (my-make-vector 50 #'(lambda(x) (+ (* 0.1 x) (* 0.01 x x))))) (yp (my-make-vector 50 #'(lambda(y) (+ (* 0.1 y) (* 0.001 y y))))) (c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :x-mapping xp :y-mapping yp :fill-type :smooth)) (w (basic-window))) (add-plot-to-window w c) (render w g-dev))) ;; Plotted on a more complex user defined grid (defun contour-plot-4 () (let* ((xp (my-make-matrix 51 51 #'(lambda(x y) (+ (* 0.02 (- x 25) (* 0.01 (+ y 50))))))) (yp (my-make-matrix 51 51 #'(lambda(x y) (declare (ignore x)) (* 0.02 y)))) (cl (my-make-vector 20 #'(lambda(x) (- (* 0.12 x) 1.0)))) (c (new-contour-plot (my-make-matrix 51 51 #'(lambda (x y) (my-contour-plot-fn x y))) :x-mapping xp :y-mapping yp :contour-levels cl)) (w (basic-window))) (add-plot-to-window w c) (render w g-dev))) ;; The same as contour-plot-3, but with a gray scale color table. (defun contour-plot-5 () (let* ((ct (new-extended-color-table :control-points (vector #(0.0 0 0 0) #(1.0 255 255 255)))) (xp (my-make-vector 50 #'(lambda(x) (+ (* 0.1 x) (* 0.01 x x))))) (yp (my-make-vector 50 #'(lambda(y) (+ (* 0.1 y) (* 0.001 y y))))) (c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :x-mapping xp :y-mapping yp :fill-type :smooth)) (w (basic-window))) (add-plot-to-window w c) (set-color-table w ct) (render w g-dev))) ;; Use PLplot's ability to grid data to convert your (x,y,z) data into a ;; plottable 2D grid. (defun contour-plot-6 () (let* ((x (my-make-vector 1000 #'(lambda(x) (declare (ignore x)) (- (random 4.0) 2.0)))) (y (my-make-vector 1000 #'(lambda(y) (declare (ignore y)) (- (random 4.0) 2.0)))) (z (make-array 1000 :initial-element 0.0 :element-type 'float)) (xgrid (my-make-vector 21 #'(lambda(x) (- (* 0.2 x) 2.0)))) (ygrid (my-make-vector 21 #'(lambda(x) (- (* 0.2 x) 2.0)))) (p (new-x-y-plot x y :line-width 0 :symbol-type 2 :symbol-size 0.75)) (w (basic-window))) (dotimes (i (length z)) (let ((tx (aref x i)) (ty (aref y i))) (setf (aref z i) (- (* tx tx) (* ty ty) (* (sin tx) (* (cos ty))))))) (let* ((d (x-y-z-data-to-grid (list x y z) xgrid ygrid :algorithm :grid-nnli)) (c (new-contour-plot d :x-mapping xgrid :y-mapping ygrid :fill-type :block))) (add-plot-to-window w c) (add-plot-to-window w p) (render w g-dev)))) ;; Mixing different plot types is also possible, though care must be taken ;; to draw them in the right order. (defun mixed-plot-1 () (let* ((x (my-make-vector 40 #'(lambda(x) (* 0.1 x)))) (y (my-make-vector 40 #'(lambda(x) (* (* 0.1 x) (* 0.1 x))))) (p (new-x-y-plot x y :line-width 2)) (c (new-contour-plot (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :x-min 0.0 :x-max 4.0 :y-min 0.0 :y-max 15.0 :fill-type :block :fill-colors (vector :red :grey :blue :yellow :green))) (title (new-text-item "..." :font-size 1.5)) ; create a text object for the title (l (new-axis-label title :top 1.5)) ; create an axis label containing the title object (w (basic-window))) (add-plot-to-window w p) (add-plot-to-window w c) (edit-window w :title l) ; replace the default title object with our own title object (edit-text-item title :the-text "Wrong Order?") ; change the text in the title object (render w g-dev) (bring-to-front w p) (edit-text-item title :the-text "Right Order?") (render w g-dev))) ;; Roll your own custom plot type & have it get drawn like any other plot type (defun custom-plot-type-1 () (let ((cp (new-custom-plot-object #'(lambda () (vector 0.0 4.0 0.0 4.0)) #'(lambda (plot-number) (declare (ignore plot-number)) (set-foreground-color :red) (cl-plplot-system:plfill (vector 1.0 1.2 2.8 3.0) (vector 1.0 3.0 3.0 1.0))))) (w (basic-window))) (add-plot-to-window w cp) (render w g-dev))) ;;; 3D mesh plots ;; A simple 3D mesh plot (defun 3d-plot-1 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot with a custom z axis range (defun 3d-plot-1.1 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue)) (w (basic-3d-window :z-axis-min -2.0 :z-axis-max 2.0 :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot with (default) cantours drawn in the x-y plane (defun 3d-plot-2 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue :contour-options :base-contour)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot with (default) cantours drawn in the x-y plane and magnitude ;; coloring on the plot. Additionally, only draw lines in between points in ;; the x direction. (defun 3d-plot-3 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :grid-type :grid-x :contour-options :both)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot with magnitude coloring on the plot. Additionally a "curtain" ;; is drawn around the plot. (defun 3d-plot-4 () (let ((c (new-3d-mesh nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :contour-options :magnitude-contour :curtain t)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; A simple demonstration 3D text labels. (defun 3d-plot-5 () (let ((l1 (new-3D-text-label (new-text-item (roman-font "Label1") :font-size 2.0 :text-color :blue) 0.5 1.0 0.1 :text-dy -1.0)) (l2 (new-3D-text-label (new-text-item (roman-font "Label2") :font-size 2.0 :text-color :red) 1.5 1.0 0.1 :text-dx 1.0 :text-sz 1.0)) (w (basic-3d-window :altitude 30 :azimuth 60 :x-axis-min 0 :x-axis-max 2.0 :y-axis-min 0 :y-axis-max 2.0 :z-axis-min 0 :z-axis-max 2.0))) (add-text-label-to-window w l1) (add-text-label-to-window w l2) (render w g-dev))) ;;; Surface plots ;; A simple surface plot (defun surface-plot-1 () (let ((c (new-surface-plot nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :line-color :blue)) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;; The same plot with a curtain and coloring according to the magnitude in z (defun surface-plot-2 () (let ((c (new-surface-plot nil nil (my-make-matrix 50 50 #'(lambda (x y) (my-contour-plot-fn x y))) :surface-options '(:curtain :magnitude-coloring))) (w (basic-3d-window :altitude 30 :azimuth 60))) (add-plot-to-window w c) (render w g-dev))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;;cl-plplot-0.6.0/src/examples/plplot-examples.lisp0000644000175000017500000000447011421146773022134 0ustar hbabcockhbabcock;;;; ;;;; Lisp versions of the standard PLplot examples. This ;;;; particular file mostly just defines the package. ;;;; ;;;; hazen 06/10 ;;;; (defpackage :plplot-examples (:use :common-lisp :cl-plplot-system)) (in-package :plplot-examples) (defparameter default-dev "xcairo") (defun make-float-array (length) (make-array length :element-type 'float :initial-element 0.0)) (defun make-int-array (length &optional (initial-value 0)) (make-array length :element-type 'integer :initial-element initial-value)) (defun min-max (matrix) (if (= (array-rank matrix) 1) (let ((m-min (aref matrix 0)) (m-max (aref matrix 0))) (dotimes (i (array-dimension matrix 0)) (when (< (aref matrix i) m-min) (setf m-min (aref matrix i))) (when (> (aref matrix i) m-max) (setf m-max (aref matrix i)))) (values m-min m-max)) (let ((m-min (aref matrix 0 0)) (m-max (aref matrix 0 0))) (dotimes (i (array-dimension matrix 0)) (dotimes (j (array-dimension matrix 1)) (when (< (aref matrix i j) m-min) (setf m-min (aref matrix i j))) (when (> (aref matrix i j) m-max) (setf m-max (aref matrix i j))))) (values m-min m-max)))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x26l.lisp0000644000175000017500000000600611422634177017577 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 26 ;;;; ;;;; This example also require unicode support. ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example26 (&optional (dev default-dev)) (plsdev dev) (let ((x-label (vector "Frequency" "ЧаÑтота")) (y-label (vector "Amplitude (dB)" "Ðмплитуда (dB)")) (alty-label (vector "Phase shift (degrees)" "Фазовый Ñдвиг (градуÑÑ‹)")) (title-label (vector "Single Pole Low-Pass Filter" "ОднополюÑный Ðизко-ЧаÑтотный Фильтр")) (line-label (vector "-20 dB/decade" "-20 dB/деÑÑток"))) (labels ((plot (type index) (let ((freql (make-float-array 101)) (ampl (make-float-array 101)) (phase (make-float-array 101))) (pladv 0) (dotimes (i 101) (setf (aref freql i) (+ -2.0 (/ i 20.0))) (let ((freq (expt 10.0 (aref freql i)))) (setf (aref ampl i) (* 20.0 (log (/ 1.0 (sqrt (+ 1.0 (expt freq 2.0)))) 10.0)) (aref phase i) (* -1.0 (/ 180.0 3.14159) (atan freq))))) (plvpor 0.15 0.85 0.1 0.9) (plwind -2.0 3.0 -80.0 0.0) (plcol0 1) (cond ((= type 0) (plbox "bclnst" 0.0 0 "bnstv" 0.0 0)) (t (plbox "bcfghlnst" 0.0 0 "bcghnstv" 0.0 0))) (plcol0 2) (plline freql ampl) (plcol0 1) (plptex 1.6 -30.0 1.0 -20.0 0.5 (aref line-label index)) (plcol0 1) (plmtex "b" 3.2 0.5 0.5 (aref x-label index)) (plmtex "t" 2.0 0.5 0.5 (aref title-label index)) (plcol0 2) (plmtex "l" 5.0 0.5 0.5 (aref y-label index)) (when (= type 0) (plcol0 1) (plwind -2.0 3.0 -100.0 0.0) (plbox "" 0.0 0 "cmstv" 30.0 3.0) (plcol0 3) (plline freql phase) (plcol0 3) (plmtex "r" 5.0 0.5 0.5 (aref alty-label index)))))) (plinit) (plfont 2) (dotimes (i (length x-label)) (plot 0 i)) (plend1)))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x31l.lisp0000644000175000017500000001514411427374621017576 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 31 ;;;; ;;;; hazen 08/10 ;;;; (in-package :plplot-examples) (defun example31 (&optional (dev default-dev)) (let ((status 0)) ; test family parameters (multiple-value-bind (fam0 num0 bmax0) (plgfam) (let ((fam1 0) (num1 10) (bmax1 1000)) (plsfam fam1 num1 bmax1) (multiple-value-bind (fam2 num2 bmax2) (plgfam) (when (or (/= fam1 fam2) (/= num1 num2) (/= bmax1 bmax2)) (format t "plgfam test failed~%") (setf status 1)))) (plsfam fam0 num0 bmax0)) ; test setting / getting page parameters (multiple-value-bind (xp0 yp0 xleng0 yleng0 xoff0 yoff0) (plgpage) (let ((xp1 200) (yp1 200) (xleng1 400) (yleng1 200) (xoff1 10) (yoff1 20)) (plspage xp1 yp1 xleng1 yleng1 xoff1 yoff1) (multiple-value-bind (xp2 yp2 xleng2 yleng2 xoff2 yoff2) (plgpage) (when (or (/= xp1 xp2) (/= yp1 yp2) (/= xleng1 xleng2) (/= yleng1 yleng2) (/= xoff1 xoff2) (/= yoff1 yoff2)) (format t "plgfam test failed~%") (setf status 1)))) (plspage xp0 yp0 xleng0 yleng0 xoff0 yoff0)) ; test setting / getting compression (let ((compression1 95)) (plscompression compression1) (plsdev dev) (plinit) (let ((compression2 (plgcompression))) (format t "Output various PLplot parameters~%") (format t "compression parameter = ~A~%" compression2) (when (/= compression1 compression2) (format t "plgcompression test failed~%") (setf status 1)))) ;exercise plscolor, plscol0, plscmap1 and plscmap1a (plscolor 1) (plscol0 1 255 0 0) (plscmap1 (vector 0 255) (vector 255 0) (vector 0 0)) (plscmap1a (vector 0 255) (vector 255 0) (vector 0 0) (vector 1.0 1.0)) (let ((level2 (plglevel))) (format t "level parameter = ~A~%" level2) (when (/= level2 1) (format t "plglevel test failed.~%") (setf status 1))) (pladv 0) (plvpor 0.01 0.99 0.02 0.49) (multiple-value-bind (xmin xmax ymin ymax) (plgvpd) (when (or (/= xmin 0.01) (/= xmax 0.99) (/= ymin 0.02) (/= ymax 0.49)) (format t "plgvpd test failed~%") (setf status 1)) (let ((xmid (* 0.5 (+ xmin xmax))) (ymid (* 0.5 (+ ymin ymax)))) (plwind 0.2 0.3 0.4 0.5) (multiple-value-bind (xmin xmax ymin ymax) (plgvpw) (format t "plwind: xmin, xmax, ymin, ymax = ~A ~A ~A ~A~%" xmin xmax ymin ymax) (when (or (/= xmin 0.2) (/= xmax 0.3) (/= ymin 0.4) (/= ymax 0.5)) (format t "plgvpw test failed~%") (setf status 1))) (multiple-value-bind (wx wy win) (plcalc-world xmid ymid) (declare (ignore win)) (when (or (< (abs (- wx (* 0.5 (+ xmin xmax)))) 1.0e-5) (< (abs (- wy (* 0.5 (+ ymin ymax)))) 1.0e-5)) (format t "plcalc-world test failed~%") (setf status 1))))) (let ((fnam (plgfnam))) (if (= (length fnam) 0) (format t "No output file name is set~%") (format t "Output file name read~%")) (format t "Output file name is ~A~%" fnam)) (plsxax 3 0) (multiple-value-bind (digmax digits) (plgxax) (format t "x axis parameters: digmax, digits = ~A ~A~%" digmax digits) (when (/= digmax 3) (format t "plgxax test failed~%") (setf status 1))) (plsyax 4 0) (multiple-value-bind (digmax digits) (plgyax) (format t "y axis parameters: digmax, digits = ~A ~A~%" digmax digits) (when (/= digmax 4) (format t "plgyax test failed~%") (setf status 1))) (plszax 5 0) (multiple-value-bind (digmax digits) (plgzax) (format t "z axis parameters: digmax, digits = ~A ~A~%" digmax digits) (when (/= digmax 5) (format t "plgzax test failed~%") (setf status 1))) (plsdidev 0.05 -42 0.1 0.2) (multiple-value-bind (mar aspect jx jy) (plgdidev) (format t "device-space window parameters: mar, aspect, jx, jy = ~A ~A ~A ~A~%" mar aspect jx jy) (when (or (/= mar 0.05) (/= jx 0.1) (/= jy 0.2)) (format t "plgdidev test failed") (setf status 1))) (plsdiori 1.0) (let ((ori (plgdiori))) (format t "ori parameter = ~A~%" ori) (when (/= ori 1.0) (format t "plgdiori test failed~%") (setf status 1))) (plsdiplt 0.1 0.2 0.9 0.8) (multiple-value-bind (xmin ymin xmax ymax) (plgdiplt) (format t "plot-space window parameters: xmin, ymin, ymax, ymax = ~A ~A ~A ~A~%" xmin ymin xmax ymax) (when (or (/= xmin 0.1) (/= xmax 0.9) (/= ymin 0.2) (/= ymax 0.8)) (format t "plgdiplt test failed~%") (setf status 1)) (plsdiplz 0.1 0.1 0.9 0.9) (multiple-value-bind (zxmin zymin zxmax zymax) (plgdiplt) (format t "zoomed plot-space window parameters: xmin, ymin, xmax, ymax = ~A ~A ~A ~A~%" zxmin zymin zxmax zymax) (when (or (> (abs (- zxmin (+ xmin (* (- xmax xmin) 0.1)))) 1.0e-5) (> (abs (- zxmax (+ xmin (* (- xmax xmin) 0.9)))) 1.0e-5) (> (abs (- zymin (+ ymin (* (- ymax ymin) 0.1)))) 1.0e-5) (> (abs (- zymax (+ ymin (* (- ymax ymin) 0.9)))) 1.0e-5)) (format t "plsdiplz test failed~%") (setf status 1)))) (plscolbg 10 20 30) (multiple-value-bind (r g b) (plgcolbg) (format t "background color parameters: r, g, b = ~A ~A ~A~%" r g b) (when (or (/= r 10) (/= g 20) (/= b 30)) (format t "plcolbg test failed~%") (setf status 1))) (plscolbga 20 30 40 0.5) (multiple-value-bind (r g b a) (plgcolbga) (format t "background/transparency colour parameters: r, g, b, a = ~A ~A ~A ~A~%" r g b a) (when (or (/= r 20) (/= g 30) (/= b 40) (/= a 0.5)) (format t "plgcolbga test failed") (setf status 1)))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x14l.lisp0000644000175000017500000001447311413752023017572 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 14 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example14 (&optional (dev default-dev)) (labels ((plot1 (xoff xscale yoff yscale) (let ((x (make-float-array 60)) (y (make-float-array 60)) (xs (make-float-array 6)) (ys (make-float-array 6))) (dotimes (i 60) (setf (aref x i) (+ xoff (* xscale (/ (+ i 1.0) 60.0))) (aref y i) (+ yoff (* yscale (expt (aref x i) 2.0))))) (let ((xmin (aref x 0)) (xmax (aref x 59)) (ymin (aref y 0)) (ymax (aref y 59))) (dotimes (i 6) (setf (aref xs i) (aref x (+ (* i 10) 3)) (aref ys i) (aref y (+ (* i 10) 3)))) (plcol0 1) (plenv xmin xmax ymin ymax 0 0) (plcol0 6) (pllab "(x)" "(y)" "#frPLplot Example 1 - y=x#u2") (plcol0 9) (plpoin xs ys 9) (plcol0 4) (plline x y) (plflush)))) (plot2 () (let ((x (make-float-array 100)) (y (make-float-array 100))) (plcol0 1) (plenv -2.0 10.0 -0.4 1.2 0 1) (plcol0 2) (pllab "(x)" "sin(x)/x" "#frPLplot Example 1 - Sinc Function") (dotimes (i 100) (setf (aref x i) (/ (- i 19.0) 6.0) (aref y i) 1.0) (when (/= (aref x i) 0.0) (setf (aref y i) (/ (sin (aref x i)) (aref x i))))) (plcol0 3) (plline x y) (plflush))) (plot3 () (let ((x (make-float-array 101)) (y (make-float-array 101)) (mark0 (make-int-array 1 0)) (space0 (make-int-array 1 0)) (mark1 (make-int-array 1 1500)) (space1 (make-int-array 1 1500))) (pladv 0) (plvsta) (plwind 0.0 360.0 -1.2 1.2) (plcol0 1) (plbox "bcnst" 60.0 2 "bcnstv" 0.2 2) (plstyl 1 mark1 space1) (plcol0 2) (plbox "g" 30.0 0 "g" 0.2 0) (plstyl 0 mark0 space0) (plcol0 3) (pllab "Angle (degrees)" "sine" "#frPLplot Example 1 - Sine function") (dotimes (i 101) (setf (aref x i) (* 3.6 i) (aref y i) (sin (/ (* (aref x i) 3.14159) 180.0)))) (plcol0 4) (plline x y) (plflush))) (plot4 () (let ((x0 (make-float-array 361)) (y0 (make-float-array 361)) (x (make-float-array 361)) (y (make-float-array 361))) (let ((dtr (/ 3.14158 180.0))) (dotimes (i 361) (setf (aref x0 i) (cos (* dtr i)) (aref y0 i) (sin (* dtr i)))) (plenv -1.3 1.3 -1.3 1.3 1 -2) (dotimes (i 10) (dotimes (j 361) (setf (aref x j) (* 0.1 (+ i 1.0) (aref x0 j)) (aref y j) (* 0.1 (+ i 1.0) (aref y0 j)))) (plline x y)) (plcol0 2) (dotimes (i 12) (let* ((theta (* i 30.0)) (dx (cos (* dtr theta))) (dy (sin (* dtr theta)))) (pljoin 0.0 0.0 dx dy) (let ((text (write-to-string (round theta)))) (if (>= dx -0.00001) (plptex dx dy dx dy -0.15 text) (plptex dx dy (- dx) (- dy) 1.15 text))))) (dotimes (i 361) (let ((r (sin (* dtr 5.0 i)))) (setf (aref x i) (* (aref x0 i) r) (aref y i) (* (aref y0 i) r))))) (plcol0 3) (plline x y) (plcol0 4) (plmtex "t" 2.0 0.5 0.5 "#frPLplot Example 3 - r(#gh)=sin 5#gh") (plflush))) (plot5 () (let* ((xpts 35) (ypts 46) (xspa (/ 2.0 (- xpts 1.0))) (yspa (/ 2.0 (- ypts 1.0))) (tr (vector xspa 0.0 -1.0 0.0 yspa -1.0)) (clevel (vector -1.0 -0.8 -0.6 -0.4 -0.2 0.0 0.2 0.4 0.6 0.8 1.0)) (z (make-float-array (list xpts ypts))) (w (make-float-array (list xpts ypts))) (mark (make-int-array 1 1500)) (space (make-int-array 1 1500))) (dotimes (i xpts) (let ((xx (/ (- i (/ xpts 2.0)) (/ xpts 2.0)))) (dotimes (j ypts) (let ((yy (- (/ (- j (/ ypts 2.0)) (/ ypts 2.0)) 1.0))) (setf (aref z i j) (- (* xx xx) (* yy yy)) (aref w i j) (* 2.0 xx yy)))))) (plenv -1.0 1.0 -1.0 1.0 0 0) (plcol0 2) (labels ((mypltr (x y tx ty pltr-data) (declare (ignore pltr-data)) (let ((tmpx (+ (* (aref tr 0) x) (* (aref tr 1) y) (aref tr 2))) (tmpy (+ (* (aref tr 3) x) (* (aref tr 4) y) (aref tr 5)))) (setf (cffi:mem-aref tx :double) (coerce tmpx 'double-float) (cffi:mem-aref ty :double) (coerce tmpy 'double-float))))) (pl-set-pltr-fn #'mypltr) (plcont z 1 xpts 1 ypts clevel) (plstyl 1 mark space) (plcol0 3) (plcont w 1 xpts 1 ypts clevel) (plcol0 1) (pllab "X Coordinate" "Y Coordinate" "Streamlines of flow") (pl-reset-pltr-fn) (plflush))))) ;;main (plsdev dev) (multiple-value-bind (fam num bmax) (plgfam) (plsetopt "geometry" "500x410+100+200") (plssub 2 2) (plinit) (plsstrm 1) (plsetopt "geometry" "500x410+650+200") (plspause nil) (plsdev dev) (plsfam fam num bmax) (plsetopt "fflen" "2") (plinit)) (plsstrm 0) (plot1 0.0 6.0 0.0 1.0) (plot1 0.0 1.0 0.0 1.0e+6) (plsyax 2 0) (plot1 0.0 1.0 0.0 1.0e-6) (plsyax 5 0) (plot1 0.0 1.0 0.0185 0.0014) (plsstrm 1) (plot4) (pleop) (plsstrm 0) (plot2) (plot3) (plsstrm 1) (plot5) (pleop) (plsstrm 0) (pleop)) (plsstrm 0) (plend1) (plsstrm 1) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x13l.lisp0000644000175000017500000000515111413712372017565 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 13 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example13 (&optional (dev default-dev)) (plsdev dev) (plinit) (pladv 0) (plvasp 1.0) (plwind 0.0 10.0 0.0 10.0) (plcol0 2) (let ((text (vector "Maurice" "Geoffrey" "Alan" "Rafael" "Vince")) (x (make-float-array 500)) (y (make-float-array 500)) (per (vector 10.0 32.0 12.0 30.0 16.0)) (theta0 0.0) (dthet 1.0)) (dotimes (i 5) (let ((j 0) (theta1 (round (+ theta0 (* 5.0 (aref per i)))))) (setf (aref x j) 5.0 (aref y j) 5.0) (incf j) (when (= i 4) (setf theta1 500)) (do ((theta theta0 (+ theta dthet))) ((> theta theta1)) (setf (aref x j) (+ 5.0 (* 3.0 (cos (* (/ (* 2.0 3.14159) 500.0) theta)))) (aref y j) (+ 5.0 (* 3.0 (sin (* (/ (* 2.0 3.14159) 500.0) theta))))) (incf j)) (plcol0 (+ i 1)) (plpsty (+ (mod (+ i 3) 8) 1)) (let ((tx (adjust-array x j)) (ty (adjust-array y j))) (plfill tx ty) (plcol0 1) (plline tx ty)) (let* ((just (* (/ (* 2.0 3.14159) 500.0) (/ (+ theta0 theta1) 2.0))) (dx (* 0.25 (cos just))) (dy (* 0.25 (sin just)))) (if (or (< (+ theta0 theta1) 250) (> (+ theta0 theta1) 750)) (setf just 0.0) (setf just 1.0)) (plptex (+ (aref x (floor j 2)) dx) (+ (aref y (floor j 2)) dy) 1.0 0.0 just (aref text i))) (setf theta0 (- theta1 dthet))))) (plfont 2) (plschr 0.0 1.3) (plptex 5.0 9.0 1.0 0.0 0.5 "Percentage of Sales") (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x07l.lisp0000644000175000017500000000431111413705637017573 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 7 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example7 (&optional (dev default-dev)) (plsdev dev) (plinit) (plfontld 0) (dotimes (l 20) (when (= l 2) (plfontld 1)) (pladv 0) (plcol0 2) (plvpor 0.15 0.95 0.1 0.9) (plwind 0.0 1.0 0.0 1.0) (plbox "bcg" 0.1 0 "bcg" 0.1 0) (plcol0 15) (dotimes (i 10) (plmtex "b" 1.5 (+ (* 0.1 i) 0.05) 0.5 (write-to-string i))) (let ((k 0) (base (vector 0 100 0 100 200 500 600 700 800 900 2000 2100 2200 2300 2400 2500 2600 2700 2800 2900))) (dotimes (i 10) (plmtex "lv" 1.0 (- 0.95 (* 0.1 i)) 1.0 (write-to-string (+ (aref base l) (* 10 i)))) (dotimes (j 10) (let ((x (make-float-array 1)) (y (make-float-array 1))) (setf (aref x 0) (+ 0.05 (* 0.1 j)) (aref y 0) (- 0.95 (* 0.1 i))) (plsym x y (+ (aref base l) k)) (incf k))))) (if (< l 2) (plmtex "t" 1.5 0.5 0.5 "PLplot Example 7 - PLSYM symbols (compact)") (plmtex "t" 1.5 0.5 0.5 "PLplot Example 7 - PLSYM symbols (extended)"))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x11l.lisp0000644000175000017500000000620211413705541017561 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 11 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example11 (&optional (dev default-dev)) (plsdev dev) (plinit) (plscmap1n 256) (plscmap1l nil (vector 0.0 1.0) (vector 240 0) (vector 0.6 0.6) (vector 0.8 0.8) 'null) (let* ((xpts 35) (ypts 46) (levels 10) (opt (vector 3 3)) (alt (vector 33.0 17.0)) (az (vector 24.0 115.0)) (title (vector "#frPLplot Example 11 - Alt=33, Az=24, Opt=3" "#frPLplot Example 11 - Alt=17, Az=115, Opt=3")) (x (make-float-array xpts)) (y (make-float-array ypts)) (z (make-float-array (list xpts ypts))) (clevel (make-float-array levels))) (dotimes (i xpts) (setf (aref x i) (* 3.0 (/ (- i (/ xpts 2.0)) (/ xpts 2.0))))) (dotimes (i ypts) (setf (aref y i) (* 3.0 (/ (- i (/ ypts 2.0)) (/ ypts 2.0))))) (dotimes (i xpts) (let ((xx (aref x i))) (dotimes (j ypts) (let ((yy (aref y j))) (setf (aref z i j)(- (* 3.0 (- 1.0 xx) (- 1.0 xx) (exp (- (* xx xx -1.0) (* (+ yy 1.0) (+ yy 1.0))))) (* 10.0 (- (/ xx 5.0) (expt xx 3.0) (expt yy 5.0)) (exp (- (* xx xx -1.0) (* yy yy)))) (* (/ 1.0 3.0) (exp (- (* (+ xx 1.0) (+ xx 1.0) -1.0) (* yy yy)))))))))) (multiple-value-bind (zmin zmax) (min-max z) (let ((step (/ (- zmax zmin) (+ levels 1.0)))) (dotimes (i levels) (setf (aref clevel i) (+ zmin step (* step i))))) (dotimes (k 2) (dotimes (i 4) (pladv 0) (plcol0 1) (plvpor 0.0 1.0 0.0 0.9) (plwind -1.0 1.0 -1.0 1.5) (plw3d 1.0 1.0 1.2 -3.0 3.0 -3.0 3.0 zmin zmax (aref alt k) (aref az k)) (plbox3 "bnstu" "x axis" 0.0 0 "bnstu" "y axis" 0.0 0 "bcdmnstuv" "z axis" 0.0 4) (plcol0 2) (cond ((= i 0) (plmesh x y z (aref opt k))) ((= i 1) (plmesh x y z (+ (aref opt k) (ash 1 2)))) ((= i 2) (plot3d x y z (+ (aref opt k) (ash 1 2)) 1)) ((= i 3) (plmeshc x y z (+ (aref opt k) (ash 1 2) (ash 1 3)) clevel))) (plcol0 3) (plmtex "t" 1.0 0.5 0.5 (aref title k)))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x12l.lisp0000644000175000017500000000424611413707500017565 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 12 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example12 (&optional (dev default-dev)) (plsdev dev) (plinit) (let ((pos (vector 0.0 0.25 0.5 0.75 1.0)) (red (vector 0.0 0.25 0.5 1.0 1.0)) (green (vector 1.0 0.5 0.5 0.5 1.0)) (blue (vector 1.0 1.0 0.5 0.25 0.0)) (y0 (vector 5 15 12 24 28 30 20 8 12 3))) (pladv 0) (plvsta) (plwind 1980.0 1990.0 0.0 35.0) (plbox "bc" 1.0 0 "bcnv" 10.0 0) (plcol0 2) (pllab "Year" "Widget Sales (millions)" "#frPLplot Example 12") (plscmap1l t pos red green blue 'null) (labels ((plfbox (x0 y0) (let ((x (vector x0 x0 (+ x0 1.0) (+ x0 1.0))) (y (vector 0.0 y0 y0 0.0))) (plfill x y) (plcol0 1) (pllsty 1) (plline x y)))) (dotimes (i 10) (plcol1 (/ i 9.0)) (plpsty 0) (plfbox (+ 1980.0 i) (aref y0 i)) (plptex (+ 1980.0 i 0.5) (+ (aref y0 i) 1.0) 1.0 0.0 0.5 (write-to-string (aref y0 i))) (plmtex "b" 1.0 (- (* (+ i 1) 0.1) 0.05) 0.5 (write-to-string (+ 1980 i)))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x32l.lisp0000644000175000017500000000627111427543562017602 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 32 ;;;; ;;;; hazen 08/10 ;;;; (in-package :plplot-examples) (defun example32 (&optional (dev default-dev)) (labels ((plfbox (x y25 y50 y75 lw uw) (let* ((spacing 0.4) (xmin (+ x (/ spacing 2.0))) (xmax (+ x 1.0 (- (/ spacing 2.0)))) (px (vector xmin xmin xmax xmax xmin)) (py (vector y25 y75 y75 y25 y25))) ; box (plpsty 0) (plfill px py) (plcol0 1) (pllsty 1) (plline px py) ; median (pllsty 1) (plline (vector xmin xmax) (vector y50 y50)) ; lower whisker (let ((xmid (/ (+ xmin xmax) 2.0)) (xwidth (- xmax xmin))) (pllsty 2) (plline (vector xmid xmid) (vector lw y25)) (pllsty 1) (plline (vector (- xmid (/ xwidth 4.0)) (+ xmid (/ xwidth 4.0))) (vector lw lw))) ; upper whisker (let ((xmid (/ (+ xmin xmax) 2.0)) (xwidth (- xmax xmin))) (pllsty 2) (plline (vector xmid xmid) (vector y75 uw)) (pllsty 1) (plline (vector (- xmid (/ xwidth 4.0)) (+ xmid (/ xwidth 4.0))) (vector uw uw)))))) (let ((y25 (vector 0.984 0.980 0.976 0.975 0.973 0.967 0.974 0.954 0.987 0.991)) (y50 (vector 0.994 0.999 1.035 0.995 1.002 0.997 1.034 0.984 1.007 1.017)) (y75 (vector 1.054 1.040 1.066 1.025 1.043 1.017 1.054 1.004 1.047 1.031)) (lw (vector 0.964 0.950 0.926 0.955 0.963 0.937 0.944 0.924 0.967 0.941)) (uw (vector 1.071 1.062 1.093 1.045 1.072 1.067 1.085 1.024 1.057 1.071)) (outx (vector 3.5 6.5)) (outy (vector 0.89 1.09))) (plsdev dev) (plinit) (pladv 0) (plvsta) (let ((x0 1.0)) (plwind x0 (+ x0 10.0) 0.85 1.15) (plcol0 1) (plbox "bc" 1.0 0 "bcgnst" 0.0 0) (pllab "Group" "Value" "#frPLplot Example 32") (dotimes (i 10) (plcol1 (/ i 9.0)) (plfbox (+ x0 i) (aref y25 i) (aref y50 i) (aref y75 i) (aref lw i) (aref uw i)) (plmtex "b" 1.0 (- (* (+ i 1) 0.1) 0.05) 0.5 (format nil "~A" (round (+ x0 i)))))) (plpoin outx outy 22) (plend1)))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/system-examples.lisp0000644000175000017500000001201211413763754022142 0ustar hbabcockhbabcock;;;; ;;;; Examples that demonstrate some plplot graphs that can be made ;;;; with the cl-plplot-system package. ;;;; ;;;; hazen 3/06 ;;;; (defpackage :system-examples (:use :common-lisp :cl-plplot-system)) (in-package :system-examples) (defparameter gdev "aqt") ; set this to the appropriate plplot device for your system ;;; Helper functions (defun my-make-array (dims) (make-array dims :initial-element 0.0 :element-type 'float)) (defun example-func-1 (x y) (- (* x x) (* y y) (* (sin (* 7 x)) (* (cos (* 7 y)))))) (defun example-func-2 (x y) (let ((z (+ (expt (1- x) 2) (* 100 (expt (- y (expt x 2)) 2))))) (if (> z 0) (log z) 0.0))) (defun example-matrix (sx sy fn) (let ((mat (my-make-array (list sx sy))) (dx (/ 2 sx)) (dy (/ 2 sy))) (dotimes (x sx) (dotimes (y sy) (setf (aref mat x y) (funcall fn (1- (* dx x)) (1- (* dy y)))))) mat)) (defun make-levels (levels min max) (let ((clevels (my-make-array levels))) (dotimes (i levels) (setf (aref clevels i) (+ min (/ (* (- max min) (+ 0.5 i)) levels)))) clevels)) ;;; Examples ;; A 2D plot (defun plot () (plsdev gdev) (plinit) (plcol0 1) (plwid 2) (plenv 0 6 0 36 0 0) (plcol0 2) (pllab "(x)" "(y)" "y = x#u2") (let ((xs (my-make-array 6)) (ys (my-make-array 6)) (x (my-make-array 60)) (y (my-make-array 60))) (dotimes (i 6) (setf (aref xs i) i) (setf (aref ys i) (* i i))) (plcol0 4) (plpoin xs ys 9) (dotimes (i 60) (let ((tmp (* 0.1 i))) (setf (aref x i) tmp) (setf (aref y i) (* tmp tmp)))) (plcol0 3) (plline x y)) (plend)) ;; Contour plot of data (defun contour-plot () (plsdev gdev) (plinit) (plenv 0 34 0 44 0 0) (plcont (example-matrix 35 45 #'example-func-1) 1 35 1 45 (make-levels 20 -1.0 1.0)) (plcol0 1) (plbox "bcnst" 0 0 "bcnstv" 0 0) (plcol0 2) (pllab "x" "y" "Contour Plot (Data)") (plend)) ;; Contour plot of a function (defun fn-contour-plot () (plsdev gdev) (plinit) (plenv 0 34 0 44 0 0) (pl-set-feval-fn #'(lambda (x y p) (declare (ignore p)) (coerce (example-func-1 (1- (/ x 17)) (1- (/ y 22))) 'double-float))) (plfcont (pl-null-pointer) 35 45 1 35 1 45 (make-levels 20 -1.0 1.0)) (pl-reset-feval-fn) (plcol0 1) (plbox "bcnst" 0 0 "bcnstv" 0 0) (plcol0 2) (pllab "x" "y" "Contour Plot (Function)") (plend)) ;; Shade plot (defun shade-plot () (plsdev gdev) (plinit) ; (plenv -1 1 -1 1 0 0) (plenv 0.0 35.0 0.0 45.0 0 0) (plshades (example-matrix 35 45 #'example-func-1) -1 1 -1 1 (make-levels 20 -1.0 1.0) 2 1 1 nil) (plcol0 1) (plbox "bcnst" 0 0 "bcnstv" 0 0) (plcol0 2) (pllab "x" "y" "Shade Plot") (plend)) ;; 3D surface plot. Also demonstrates 3D text labeling. (defun 3D-plot () (plsdev gdev) (plinit) (pladv 0) (plvpor 0 1 0 0.9) (plwind -1 1 -0.9 1.1) (plscmap1n 256) (plscmap1l 1 (vector 0.0 1.0) (vector 0.2 1) (vector 0.2 1) (vector 0.2 1) (vector nil nil)) (plw3d 1 1 1 -1.5 1.5 -0.5 1.5 -5 6.5 60 30) (plmtex "t" 1 0.5 0.5 "3D plot example") (plbox3 "bnstu" "x axis" 0 0 "bnstu" "y axis" 0 0 "bcdmnst" "" 0 0) (plmtex3 "zpv" 3.0 0.5 0.5 "z axis") (plptex3 0.0 -0.4 -0.5 1.0 0.0 0.0 0.0 0.0 1.0 0.5 "Surface") (plsurf3d (make-levels 40 -1.5 1.5) (make-levels 40 -1.5 1.5) (example-matrix 40 40 #'example-func-2) 0 (make-levels 2 -1 1)) (plend)) ;; Unicode labels, a nice feature of plplot. ;; ;; The escape sequence #[..] tells plplot to expect a unicode character ;; code point. You can also pass in a utf-8 encoded string, but depending ;; on how your lisp deals with the arrays of type 'character this may ;; or may not work. ;; ;; YMMV depending on the capabilities of the driver itself and of the ;; fonts that are available to the driver. (defun unicode () (plsdev gdev) (plinit) (pladv 0) (plvpor 0 1 0 1) (plwind 0 1 0 1) (plschr 0 4) (plptex 0.5 0.5 1.0 0.0 0.5 "Has#[238]t#[238]") (plend)) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x16l.lisp0000644000175000017500000001373411422400064017566 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 16 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example16 (&optional (dev default-dev)) (plsdev dev) (let* ((ns 20) (nx 35) (ny 46) (tr (make-float-array 6)) (cgrid0-x (make-float-array nx)) (cgrid0-y (make-float-array ny)) (cgrid1-x (make-float-array nx)) (cgrid1-y (make-float-array ny)) (cgrid2-x (make-float-array (list nx ny))) (cgrid2-y (make-float-array (list nx ny))) (z (make-float-array (list nx ny))) (w (make-float-array (list nx ny))) (clevel (make-float-array ns)) (shedge (make-float-array (1+ ns)))) (labels ((my-pltr (x y) (values (+ (* (aref tr 0) x) (* (aref tr 1) y) (aref tr 2)) (+ (* (aref tr 3) x) (* (aref tr 4) y) (aref tr 5))))) ; (setf (cffi:mem-aref tx :double) (coerce tmpx 'double-float) ; (cffi:mem-aref ty :double) (coerce tmpy 'double-float))))) (setf (aref tr 0) (/ 2.0 (- nx 1.0)) (aref tr 1) 0.0 (aref tr 2) -1.0 (aref tr 3) 0.0 (aref tr 4) (/ 2.0 (- ny 1.0)) (aref tr 5) -1.0) (dotimes (i nx) (let ((x (/ (- i (/ nx 2.0)) (/ nx 2.0)))) (dotimes (j ny) (let ((y (- (/ (- j (/ ny 2.0)) (/ ny 2.0)) 1.0))) (setf (aref z i j) (- (* x x) (* y y) (* (sin (* 7.0 x)) (cos (* 7.0 y)))) (aref w i j) (- (* 2 x y) (* (cos (* 7.0 x)) (sin (* 7.0 y))))))))) (multiple-value-bind (zmin zmax) (min-max z) (dotimes (i ns) (setf (aref clevel i) (+ zmin (/ (* (- zmax zmin) (+ i 0.5)) ns)))) (dotimes (i (1+ ns)) (setf (aref shedge i) (+ zmin (/ (* (- zmax zmin) i) ns))))) (dotimes (i nx) (dotimes (j ny) (multiple-value-bind (x y) (my-pltr i j) (let ((argx (/ (* x 3.14159) 2.0)) (argy (/ (* y 3.14159) 2.0)) (distort 0.4)) (setf (aref cgrid0-x i) x (aref cgrid0-y j) y (aref cgrid1-x i) (+ x (* distort (cos argx))) (aref cgrid1-y j) (- y (* distort (cos argy))) (aref cgrid2-x i j) (+ x (* distort (cos argx) (cos argy))) (aref cgrid2-y i j) (- y (* distort (cos argx) (cos argy)))))))) ; plot1 (plspal0 "cmap0_black_on_white.pal") (plspal1 "cmap1_gray.pal" t) (plscmap0n 3) (plinit) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 0) (plshades z -1.0 1.0 -1.0 1.0 shedge 2 0 0 t) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (pllab "distance" "altitude" "Bogon density") ;plot2 (plspal0 "cmap0_black_on_white.pal") (plspal1 "cmap1_blue_yellow.pal" t) (plscmap0n 3) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 0) (pl-set-pltr-fn #'pltr1) (plshades z -1.0 1.0 -1.0 1.0 shedge 2 0 0 t cgrid1-x cgrid1-y) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (pllab "distance" "altidude" "Bogon density") ; plot3 (plspal0 "cmap0_black_on_white.pal") (plspal1 "cmap1_blue_red.pal" t) (plscmap0n 3) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 0) (pl-set-pltr-fn #'pltr2) (plshades z -1.0 1.0 -1.0 1.0 shedge 2 0 0 t cgrid2-x cgrid2-y) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (plcont w 1 nx 1 ny clevel cgrid2-x cgrid2-y) (pllab "distance" "altitude" "Bogon density, with streamlines") ; plot4 (plspal0 "") (plspal1 "" t) (plscmap0n 3) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 0) (pl-set-pltr-fn #'pltr2) (plshades z -1.0 1.0 -1.0 1.0 shedge 2 2 3 t cgrid2-x cgrid2-y) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (pllab "distance" "altitude" "Bogon density") ; plot5 (plspal0 "cmap0_black_on_white.pal") (plspal1 "cmap1_gray.pal" t) (plscmap0n 3) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 0) (dotimes (i nx) (let ((r (/ i (- nx 1.0)))) (dotimes (j ny) (let ((th (* (/ (* 2.0 3.14159) (- ny 1.0)) j))) (setf (aref cgrid2-x i j) (* r (cos th)) (aref cgrid2-y i j) (* r (sin th)) (aref z i j) (* (exp (* -1.0 r r)) (cos (* 5.0 3.14159 r)) (cos (* 5.0 th)))))))) (multiple-value-bind (zmin zmax) (min-max z) (dotimes (i (1+ ns)) (setf (aref shedge i) (+ zmin (/ (* (- zmax zmin) i) ns))))) (pl-set-pltr-fn #'pltr2) (plshades z -1.0 1.0 -1.0 1.0 shedge 2 0 0 t cgrid2-x cgrid2-y) (let* ((ppts 100) (px (make-float-array ppts)) (py (make-float-array ppts))) (dotimes (i ppts) (let ((th (* (/ (* 2.0 3.14159) (- ppts 2.0)) i))) (setf (aref px i) (cos th) (aref py i) (sin th)))) (plcol0 1) (plline px py)) (plcol0 2) (pllab "" "" "Tokamak Bogon Instability"))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x06l.lisp0000644000175000017500000000425111411400510017551 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 6 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example6 (&optional (dev default-dev)) (plsdev dev) (plinit) (dotimes (kind-font 2) (plfontld kind-font) (let ((max-font (if (= kind-font 0) 1 4))) (dotimes (font max-font) (plfont (1+ font)) (pladv 0) (plcol0 2) (plvpor 0.1 1.0 0.1 0.9) (plwind 0.0 1.0 0.0 1.3) (plbox "bcg" 0.1 0 "bcg" 0.1 0) (plcol0 15) (dotimes (i 10) (plmtex "b" 1.5 (+ (* 0.1 i) 0.05) 0.5 (write-to-string i))) (let ((k 0)) (dotimes (i 13) (plmtex "lv" 1.0 (- 1.0 (/ (* 2.0 (+ i 1.0)) 26.0)) 1.0 (write-to-string (* 10 i))) (dotimes (j 10) (let ((x (make-float-array 1)) (y (make-float-array 1))) (setf (aref x 0) (+ (* j 0.1) 0.05) (aref y 0) (- 1.25 (* i 0.1))) (when (< k 128) (plpoin x y k)) (incf k))))) (if (= kind-font 0) (plmtex "t" 1.5 0.5 0.5 "PLplot Example 6 - plpoin symbols (compact)") (plmtex "t" 1.5 0.5 0.5 "PLplot Example 6 - plpoin symbols (extended)"))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x09l.lisp0000644000175000017500000002077311413705541017601 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 9 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) ;(defun my-pltr-fn (x y tx ty) ; (multiple-value-bind (mx my) (my-pltr x y) ; (setf (mem-aref tx :double) (coerce mx 'double-float) ; (mem-aref ty :double) (coerce my 'double-float)))) (defun example9 (&optional (dev default-dev)) (plsdev dev) (plinit) (let* ((xpts 35) (ypts 46) (xspa (/ 2.0 (- xpts 1.0))) (yspa (/ 2.0 (- ypts 1.0))) (clevel (vector -1.0 -0.8 -0.6 -0.4 -0.2 0.0 0.2 0.4 0.6 0.8 1.0))) (labels ((my-pltr (x y) (values (+ (* x xspa) (* y 0.0) -1.0) (+ (* x 0.0) (* y yspa) -1.0))) ; polar plot (polar () (plenv -1.0 1.0 -1.0 1.0 0 -2) (plcol0 1) (let* ((perimeterpts 100) (px (make-float-array perimeterpts)) (py (make-float-array perimeterpts))) (dotimes (i perimeterpts) (let ((theta (* (/ (* 2.0 3.14159) (- perimeterpts 1.0)) i))) (setf (aref px i) (cos theta)) (setf (aref py i) (sin theta)))) (plline px py)) (let* ((rpts 40) (thetapts 40) (gridx (make-float-array (list rpts thetapts))) (gridy (make-float-array (list rpts thetapts))) (z (make-float-array (list rpts thetapts))) (lev (make-float-array (list 10)))) (dotimes (i rpts) (let ((r (/ (float i) (- rpts 1.0)))) (dotimes (j thetapts) (let ((theta (* (/ (* 2.0 3.14159) (- thetapts 1.0)) j))) (setf (aref gridx i j) (* r (cos theta)) (aref gridy i j) (* r (sin theta)) (aref z i j) r))))) (dotimes (i 10) (setf (aref lev i) (+ 0.05 (* 0.10 i)))) (plcol0 2) (pl-set-pltr-fn #'pltr2) (plcont z 1 rpts 1 thetapts lev gridx gridy) (pl-reset-pltr-fn) (plcol0 1) (pllab "" "" "Polar Contour Plot"))) ; potential plot (potential () (let* ((perimeterpts 100) (rpts 40) (thetapts 64) (pnlevel 20) (gridx (make-float-array (list rpts thetapts))) (gridy (make-float-array (list rpts thetapts))) (z (make-float-array (list rpts thetapts))) (clevelneg (make-float-array pnlevel)) (clevelpos (make-float-array pnlevel))) (dotimes (i rpts) (let ((r (+ 0.5 i))) (dotimes (j thetapts) (let ((theta (* (/ (* 2.0 3.14159) (- thetapts 1.0)) (+ 0.5 j)))) (setf (aref gridx i j) (* r (cos theta)) (aref gridy i j) (* r (sin theta))))))) (multiple-value-bind (xmin xmax) (min-max gridx) (multiple-value-bind (ymin ymax) (min-max gridy) (let* ((rmax (+ 0.5 (- rpts 1.0))) (x0 (/ (+ xmin xmax) 2.0)) (y0 (/ (+ ymin ymax) 2.0)) (peps 0.05) (xpmin (- xmin (* (abs xmin) peps))) (xpmax (+ xmax (* (abs xmax) peps))) (ypmin (- ymin (* (abs ymin) peps))) (ypmax (+ ymax (* (abs ymax) peps))) (eps 2.0) (q1 1.0) (d1 (/ rmax 4.0)) (q1i (/ (* (- q1) rmax) d1)) (d1i (/ (expt rmax 2.0) d1)) (q2 -1.0) (d2 (/ rmax 4.0)) (q2i (/ (* (- q2) rmax) d2)) (d2i (/ (expt rmax 2.0) d2))) (dotimes (i rpts) (dotimes (j thetapts) (let ((div1 (sqrt (+ (expt (- (aref gridx i j) d1) 2) (expt (- (aref gridy i j) d1) 2) (expt eps 2.0)))) (div1i (sqrt (+ (expt (- (aref gridx i j) d1i) 2) (expt (- (aref gridy i j) d1i) 2) (expt eps 2.0)))) (div2 (sqrt (+ (expt (- (aref gridx i j) d2) 2) (expt (+ (aref gridy i j) d2) 2) (expt eps 2.0)))) (div2i (sqrt (+ (expt (- (aref gridx i j) d2i) 2) (expt (+ (aref gridy i j) d2i) 2) (expt eps 2.0))))) (setf (aref z i j) (+ (/ q1 div1) (/ q1i div1i) (/ q2 div2) (/ q2i div2i)))))) (multiple-value-bind (zmin zmax) (min-max z) (let ((dz (/ (- zmax zmin) pnlevel)) (nlevelneg 0) (nlevelpos 0)) (dotimes (i pnlevel) (let ((clevel (+ zmin (* (+ i 0.5) dz)))) (if (<= clevel 0) (progn (setf (aref clevelneg nlevelneg) clevel) (incf nlevelneg)) (progn (setf (aref clevelpos nlevelpos) clevel) (incf nlevelpos))))) (setf clevelneg (adjust-array clevelneg nlevelneg)) (setf clevelpos (adjust-array clevelpos nlevelpos)) (pladv 0) (plcol0 1) (plvpas 0.1 0.9 0.1 0.9 1.0) (plwind xpmin xpmax ypmin ypmax) (plbox "" 0.0 0 "" 0.0 0) (plcol0 11) (pl-set-pltr-fn #'pltr2) (when (> nlevelneg 0) (pllsty 2) (plcont z 1 rpts 1 thetapts clevelneg gridx gridy)) (when (> nlevelpos 0) (pllsty 1) (plcont z 1 rpts 1 thetapts clevelpos gridx gridy)))) (let ((px (make-float-array perimeterpts)) (py (make-float-array perimeterpts))) (dotimes (i perimeterpts) (let ((theta (* (/ (* 2.0 3.14159) (- perimeterpts 1)) i))) (setf (aref px i) (+ x0 (* rmax (cos theta))) (aref py i) (+ y0 (* rmax (sin theta)))))) (plcol0 1) (plline px py) (plcol0 2) (pllab "" "" "Shielded potential of charges in a conducting sphere")))))))) ;; main (let ((mark (make-int-array 1 1500)) (space (make-int-array 1 1500)) (z (make-float-array (list xpts ypts))) (w (make-float-array (list xpts ypts))) (xg1 (make-float-array xpts)) (yg1 (make-float-array ypts)) (gridx (make-float-array (list xpts ypts))) (gridy (make-float-array (list xpts ypts)))) (dotimes (i xpts) (let ((xx (/ (- i (/ xpts 2.0)) (/ xpts 2.0)))) (dotimes (j ypts) (let ((yy (- (/ (- j (/ ypts 2.0)) (/ ypts 2.0)) 1.0))) (setf (aref z i j) (- (* xx xx) (* yy yy)) (aref w i j) (* 2 xx yy)))))) (dotimes (i xpts) (dotimes (j ypts) (multiple-value-bind (xx yy) (my-pltr i j) (let ((argx (/ (* xx 3.14159) 2.0)) (argy (/ (* yy 3.14159) 2.0)) (distort 0.4)) (setf (aref xg1 i) (+ xx (* distort (cos argx))) (aref yg1 j) (- yy (* distort (cos argy))) (aref gridx i j) (+ xx (* distort (cos argx) (cos argy))) (aref gridy i j) (- yy (* distort (cos argx) (cos argy)))))))) ;; plot1 (pl-setcontlabelformat 4 3) (pl-setcontlabelparam 0.006 0.3 0.1 1) (plenv -1.0 1.0 -1.0 1.0 0 0) (plcol0 2) (pl-set-pltr-fn #'(lambda (x y tx ty p) (declare (ignore p)) (multiple-value-bind (mx my) (my-pltr x y) (setf (cffi:mem-aref tx :double) (coerce mx 'double-float) (cffi:mem-aref ty :double) (coerce my 'double-float))))) (plcont z 1 xpts 1 ypts clevel) (plstyl 1 mark space) (plcol0 3) (plcont w 1 xpts 1 ypts clevel) (plstyl 0 mark space) (plcol0 1) (pllab "X Coordinate" "Y Coordinate" "Streamlines of flow") ;; plot2 (pl-setcontlabelparam 0.006 0.3 0.1 0) (plenv -1.0 1.0 -1.0 1.0 0 0) (plcol0 2) (pl-set-pltr-fn #'pltr1) (plcont z 1 xpts 1 ypts clevel xg1 yg1) (plstyl 1 mark space) (plcol0 3) (plcont w 1 xpts 1 ypts clevel xg1 yg1) (plstyl 0 mark space) (plcol0 1) (pllab "X Coordinate" "Y Coordinate" "Streamlines of flow") ;; plot3 (plenv -1.0 1.0 -1.0 1.0 0 0) (plcol0 2) (pl-set-pltr-fn #'pltr2) (plcont z 1 xpts 1 ypts clevel gridx gridy) (plstyl 1 mark space) (plcol0 3) (plcont w 1 xpts 1 ypts clevel gridx gridy) (plstyl 0 mark space) (plcol0 1) (pllab "X Coordinate" "Y Coordinate" "Streamlines of flow") ;; plot4 (pl-setcontlabelparam 0.006 0.3 0.1 0) (polar) ;; plot5 (pl-setcontlabelparam 0.006 0.3 0.1 0) (potential) (pl-reset-pltr-fn)))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x08l.lisp0000644000175000017500000001032011413122237017556 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 8 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example8 (&optional (dev default-dev)) (plsdev dev) (plinit) (let ((alt (vector 60.0 20.0)) (az (vector 30.0 60.0)) (title (vector "#frPLplot Example 8 - Alt=60, Az=30" "#frPLplot Example 8 - Alt=20, Az=60"))) (labels ((cmap1-init (gray) (let ((i (make-float-array 2)) (h (make-float-array 2)) (l (make-float-array 2)) (s (make-float-array 2))) (setf (aref i 0) 0.0 (aref i 1) 1.0) (if gray (setf (aref h 0) 0.0 (aref h 1) 0.0 (aref l 0) 0.5 (aref l 1) 1.0 (aref s 0) 0.0 (aref s 1) 0.0) (setf (aref h 0) 240.0 (aref h 1) 0.0 (aref l 0) 0.6 (aref l 1) 0.6 (aref s 0) 0.8 (aref s 1) 0.8)) (plscmap1n 256) (plscmap1l nil i h l s 'null)))) (let* ((xpts 35) (ypts 46) (clevel (make-float-array 10)) (x (make-float-array xpts)) (y (make-float-array ypts)) (z (make-float-array (list xpts ypts))) (z-row-major (make-float-array (* xpts ypts))) (z-col-major (make-float-array (* ypts xpts)))) (dotimes (i xpts) (setf (aref x i) (* 1.5 (/ (- i (/ xpts 2.0)) (/ xpts 2.0))))) (dotimes (i ypts) (setf (aref y i) (+ 0.5 (/ (- i (/ ypts 2.0)) (/ ypts 2.0))))) (dotimes (i xpts) (dotimes (j ypts) (setf (aref z i j) (+ (expt (- 1.0 (aref x i)) 2.0) (* 100.0 (expt (- (aref y j) (expt (aref x i) 2.0)) 2.0)))) (setf (aref z i j) (if (= 0.0 (aref z i j)) -5.0 (log (aref z i j)))) (setf (aref z-row-major (+ (* i ypts) j)) (aref z i j) (aref z-col-major (+ i (* j xpts))) (aref z i j)))) (multiple-value-bind (zmax zmin) (plminmax2dgrid z) (let ((step (/ (- zmax zmin) 11.0))) (dotimes (i 10) (setf (aref clevel i) (+ zmin step (* step i))))) (pllightsource 1.0 1.0 1.0) (dotimes (k 2) (dotimes (ifshade 4) (pladv 0) (plvpor 0.0 1.0 0.0 0.9) (plwind -1.0 1.0 -0.9 1.1) (plcol0 3) (plmtex "t" 1.0 0.5 0.5 (aref title k)) (plcol0 1) (plw3d 1.0 1.0 1.0 -1.5 1.5 -0.5 1.5 zmin zmax (aref alt k) (aref az k)) (plbox3 "bnstu" "x axis" 0.0 0 "bnstu" "y axis" 0.0 0 "bcdmnstuv" "z axis" 0.0 0) (plcol0 2) (cond ((= ifshade 0) (progn (cmap1-init t) (with-foreign-matrix (z foreign-z) (plfsurf3d x y (plf2ops-c) foreign-z 0 'null)))) ((= ifshade 1) (progn (cmap1-init nil) (with-foreign-grid (grid z xpts ypts) (plfsurf3d x y (plf2ops-grid-c) grid (ash 1 2) 'null)))) ((= ifshade 2) (progn (cmap1-init nil) (with-foreign-grid (grid z-row-major xpts ypts) (plfsurf3d x y (plf2ops-grid-row-major) grid (+ (ash 1 2) (ash 1 7)) 'null)))) (t (progn (cmap1-init nil) (with-foreign-grid (grid z-col-major xpts ypts) (plfsurf3d x y (plf2ops-grid-col-major) grid (+ (ash 1 2) (ash 1 3) (ash 1 5)) clevel))))))))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x19l.lisp0000644000175000017500000000776611416000233017576 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 19 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example19 (&optional (dev default-dev)) (plsdev dev) (labels ((map-transform (x y) (let ((radius (- 90.0 y))) (values (* radius (cos (/ (* x 3.14159) 180.0))) (* radius (sin (/ (* x 3.14159) 180.0)))))) (map-fn (x y xt yt data) (declare (ignore data)) (multiple-value-bind (v1 v2) (map-transform x y) (setf (cffi:mem-aref xt :double) (coerce v1 'double-float) (cffi:mem-aref yt :double) (coerce v2 'double-float)))) (mapform19 (n ax ay) (dotimes (i n) (multiple-value-bind (v1 v2) (map-transform (cffi:mem-aref ax :double i) (cffi:mem-aref ay :double i)) (setf (cffi:mem-aref ax :double i) (coerce v1 'double-float) (cffi:mem-aref ay :double i) (coerce v2 'double-float))))) (normalize-longitude (lon) (if (and (>= lon -180.0) (<= lon 180.0)) lon (let ((times (floor (/ (+ (abs lon) 180.0) 360.0)))) (if (< lon 0.0) (+ lon (* 360.0 times)) (- lon (* 360.0 times)))))) (geolocation-labeler (axis value label length data) (declare (ignore data)) (let* ((label-val value) (direction-label (if (= axis 2) (cond ((> label-val 0.0) " N") ((< label-val 0.0) " S") (t "Eq")) (progn (setf label-val (normalize-longitude value)) (cond ((> label-val 0.0) " E") ((< label-val 0.0) " W") (t "")))))) (cffi:lisp-string-to-foreign (if (and (= axis 2) (= value 0.0)) direction-label (format nil "~,0f~a" (abs label-val) direction-label)) label length)))) (plinit) (plcol0 1) (pl-set-label-fn #'geolocation-labeler) (plslabelfunc (pl-null-pointer)) (let ((miny -70) (maxy 80)) ; Most of the world (let ((minx 190) (maxx (+ 190 360))) (plenv minx maxx miny maxy 1 70) (plmap "usaglobe" minx maxx miny maxy)) ; The Americas (let ((minx 190) (maxx 340)) (plcol0 1) (plenv minx maxx miny maxy 1 70) (plmap "usaglobe" minx maxx miny maxy)) ; Polar, Northern hemisphere (let ((minx 0) (maxx 360)) (plenv -75.0 75.0 -75.0 75.0 1 -1) (pl-set-map-fn #'mapform19) (plmap "globe" minx maxx miny maxy) (pllsty 2) (plmeridians 10.0 10.0 0.0 360.0 -10.0 80.0)) (pl-reset-map-fn) ; Polar, Northern hemisphere w/ PLplot-wide transform (let ((minx 0) (maxx 360)) (pl-set-transform-fn #'map-fn) (plstransform (pl-null-pointer)) (pllsty 1) (plenv -75.0 75.0 -75.0 75.0 1 -1) (plmap "globe" minx maxx miny maxy) (pllsty 2) (plmeridians 10.0 10.0 0.0 360.0 -10.0 80.0) (plcol0 2) (plssym 0.0 2.0) (plpoin (vector -76.6125) (vector 39.2902778) 18) (plssym 0.0 1.0) (plptex -76.6125 43.0 0.0 0.0 0.0 "Baltimore, MD") (pl-reset-transform)))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x30l.lisp0000644000175000017500000000543211427302015017560 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 30 ;;;; ;;;; hazen 08/10 ;;;; (in-package :plplot-examples) (defun example30 (&optional (dev default-dev)) (plsdev dev) (plinit) (plscmap0n 4) (plscmap0a (vector 0 255 0 0) (vector 0 0 255 0) (vector 0 0 0 255) (vector 1.0 1.0 1.0 1.0)) ; plot1 (pladv 0) (plvpor 0.0 1.0 0.0 1.0) (plwind 0.0 1.0 0.0 1.0) (plcol0 0) (plbox "" 1.0 0 "" 1.0 0) (let ((px (vector 0.1 0.5 0.5 0.1)) (py (vector 0.1 0.1 0.5 0.5))) (dotimes (i 9) (let ((icol (1+ (mod i 3)))) (multiple-value-bind (r g b a) (plgcol0a icol) (declare (ignore a)) (plscol0a icol r g b (- 1.0 (/ i 9.0)))) (plcol0 icol) (plfill px py) (dotimes (j 4) (incf (aref px j) (/ 0.5 9.0)) (incf (aref py j) (/ 0.5 9.0)))))) ; plot2 (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind 0.0 1.0 0.0 1.0) (dotimes (i 5) (let ((icol (1+ (mod i 3))) (px (make-float-array 4))) (setf (aref px 0) (+ 0.05 (* 0.2 i)) (aref px 1) (+ (aref px 0) 0.1) (aref px 2) (aref px 1) (aref px 3) (aref px 0)) (multiple-value-bind (r g b a) (plgcol0a icol) (declare (ignore a)) (plscol0a icol r g b 1.0)) (plcol0 icol) (dotimes (j 5) (let ((py (make-float-array 4))) (setf (aref py 0) (+ 0.05 (* 0.2 j)) (aref py 1) (aref py 0) (aref py 2) (+ (aref py 0) 0.1) (aref py 3) (aref py 2)) (plfill px py))))) (plscmap1n 128) (plscmap1la t (vector 0.0 1.0) (vector 1.0 1.0) (vector 0.0 0.0) (vector 0.0 0.0) (vector 0.0 1.0) (vector 0.0 0.0)) (plgradient (vector 0.0 1.0 1.0 0.0) (vector 0.0 0.0 1.0 1.0) 90.0) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x04l.lisp0000644000175000017500000000475611411137452017575 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 4 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example4 (&optional (dev default-dev)) (plsdev dev) (plinit) (plfont 2) (labels ((plot (type) (let ((freql (make-float-array 101)) (ampl (make-float-array 101)) (phase (make-float-array 101))) (dotimes (i 101) (setf (aref freql i) (+ -2.0 (/ i 20.0))) (let ((freq (expt 10.0 (aref freql i)))) (setf (aref ampl i) (* 20.0 (log (/ 1.0 (sqrt (+ 1.0 (expt freq 2.0)))) 10.0)) (aref phase i) (- (* (/ 180.0 3.14159) (atan freq)))))) (pladv 0) (plvpor 0.15 0.85 0.1 0.9) (plwind -2.0 3.0 -80.0 0.0) (plcol0 1) (if type (plbox "bcfghlnst" 0.0 0 "bcghnstv" 0.0 0) (plbox "bclnst" 0.0 0 "bnstv" 0.0 0)) (plcol0 2) (plline freql ampl) (plcol0 1) (plptex 1.6 -30.0 1.0 -20.0 0.5 "-20 dB/decade") (plcol0 1) (plmtex "b" 3.2 0.5 0.5 "Frequency") (plmtex "t" 2.0 0.5 0.5 "Single Pole Low-Pass Filter") (plcol0 2) (plmtex "l" 5.0 0.5 0.5 "Amplitude (dB)") (unless type (plcol0 1) (plwind -2.0 3.0 -100.0 0.0) (plbox "" 0.0 0 "cmstv" 30.0 3) (plcol0 3) (plline freql phase) (plcol0 3) (plmtex "r" 5.0 0.5 0.5 "Phase shift (degrees)"))))) (plot nil) (plot t)) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x29l.lisp0000644000175000017500000001745011427544051017603 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 29. ;;;; ;;;; Fixme: This example may have a problem with floating point ;;;; exceptions. I was unsuccesful in my attempts to figure ;;;; out why as the numbers that it passes to the PLplot ;;;; library are identical with those passed by the C ;;;; version of this example. ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example29 (&optional (dev default-dev)) (plsdev dev) (labels ((plot1 () (let* ((npts 73) (xmin 0.0) (xmax (* 60.0 60.0 24.0)) (ymin 10.0) (ymax 20.0) (x (make-float-array npts)) (y (make-float-array npts)) (xerr1 (make-float-array npts)) (xerr2 (make-float-array npts)) (yerr1 (make-float-array npts)) (yerr2 (make-float-array npts))) (dotimes (i npts) (setf (aref x i) (* xmax (/ i npts)) (aref y i) (- 15.0 (* 5.0 (cos (* 2 3.14159 (/ i npts))))) (aref xerr1 i) (- (aref x i) (* 60 5)) (aref xerr2 i) (+ (aref x i) (* 60 5)) (aref yerr1 i) (- (aref y i) 0.1) (aref yerr2 i) (+ (aref y i) 0.1))) (pladv 0) (plsmaj 0.0 0.5) (plsmin 0.0 0.5) (plvsta) (plwind xmin xmax ymin ymax) (plcol0 1) (pltimefmt "%H:%M") (plbox "bcnstd" (* 3.0 60 60) 3 "bcnstv" 1 5) (plcol0 3) (pllab "Time (hours:mins)" "Temperature (degC)" "@frPLplot Example 29 - Daily temperature") (plcol0 4) (plline x y) (plcol0 2) (plerrx xerr1 xerr2 y) (plcol0 3) (plerry x yerr1 yerr2) (plsmin 0.0 1.0) (plsmaj 0.0 1.0))) (plot2 () (let* ((lat 51.5) (npts 365) (xmin 0.0) (xmax (* npts 60.0 60.0 24.0)) (ymin 0.0) (ymax 24.0) (x (make-float-array npts)) (y (make-float-array npts))) (dotimes (j npts) (let* ((p (asin (* 0.39795 (cos (+ 0.2163108 (* 2 (atan (* 0.9671396 (tan (* 0.00860 (- j 186))))))))))) (d (- 24.0 (* (/ 24.0 3.14159) (acos (/ (+ (sin (/ (* 0.8333 3.14159) 180.0)) (* (sin (/ (* lat 3.14159) 180.0)) (sin p))) (* (cos (/ (* lat 3.14159) 180.0)) (cos p)))))))) (setf (aref x j) (* j 60.0 60.0 24.0) (aref y j) d))) (plcol0 1) (pltimefmt "%b %d") (plprec 1 1) (plenv xmin xmax ymin ymax 0 40) (plcol0 3) (pllab "Date" "Hours of daylight" "@frPLplot Example 29 - Hours of daylight at 51.5N") (plcol0 4) (plline x y) (plprec 0 0))) (plot3 () (let* ((tstart (plctime 2005 11 01 0 0 0)) (npts 62) (xmin tstart) (xmax (+ xmin (* npts 60.0 60.0 24.0))) (ymin 0.0) (ymax 5.0) (x (make-float-array npts)) (y (make-float-array npts))) (dotimes (i npts) (setf (aref x i) (+ xmin (* i 60.0 60.0 24.0)) (aref y i) (+ 1.0 (sin (* 2.0 3.14159 (/ i 7.0))) (exp (/ (if (< i (- npts i)) i (- npts i)) 31.0))))) (pladv 0) (plvsta) (plwind xmin xmax ymin ymax) (plcol0 1) (pltimefmt "%F") (plbox "bcnstd" (* 14.0 24.0 60.0 60.0) 14 "bcnstv" 1 4) (plcol0 3) (pllab "Date" "Hours of television watched" "@frPLplot Example 29 - Hours of television watched in Dec 2005 / Jan 2006") (plcol0 4) (plssym 0.0 0.5) (plpoin x y 2) (plline x y))) (plot4 () (let* ((scale 365.242198781) (offset1 -678940) (offset2 -0.3641639) (if-TAI-time-format) (npts) (title-suffix) (time-format) (xlabel-step) (xtitle) (xmin) (xmax) (ymin) (ymax)) (plconfigtime scale offset1 offset2 #x0 nil 0 0 0 0 0 0) (dotimes (kind 7) (cond ((= kind 0) (setf xmin (plctime 1950 0 2 0 0 0) xmax (plctime 2020 0 2 0 0 0) npts (+ (* 70 12) 1) ymin 0.0 ymax 36.0 time-format "%Y%" if-TAI-time-format 1 title-suffix "from 1950 to 2020" xtitle "Year" xlabel-step 10)) ((or (= kind 1) (= kind 2)) (setf xmin (plctime 1961 7 1 0 0 (- 1.64757 0.2)) xmax (plctime 1961 7 1 0 0 (+ 1.64757 0.2)) npts 1001 ymin 1.625 ymax 1.725 time-format "%S%2%" title-suffix "near 1961-08-01 (TAI)" xlabel-step (/ 0.05 (* scale 86400.0)) if-TAI-time-format (if (= kind 1) 1 0) xtitle (if (= kind 1) "Seconds (TAI)" "Seconds (TAI) labelled with corresponding UTC"))) ((or (= kind 3) (= kind 4)) (setf xmin (plctime 1963 10 1 0 0 (- 2.6972788 0.2)) xmax (plctime 1963 10 1 0 0 (+ 2.6972788 0.2)) npts 1001 ymin 2.55 ymax 2.75 time-format "%S%2%" title-suffix "near 1963-11-01 (TAI)" xlabel-step (/ 0.05 (* scale 86400.0)) if-TAI-time-format (if (= kind 3) 1 0) xtitle (if (= kind 3) "Seconds (TAI)" "Seconds (TAI) labelled with corresponding UTC"))) ((or (= kind 5) (= kind 6)) (setf xmin (plctime 2009 0 1 0 0 (- 34.0 5.0)) xmax (plctime 2009 0 1 0 0 (+ 34.0 5.0)) npts 1001 ymin 32.5 ymax 34.5 time-format "%S%2%" title-suffix "near 2009-01-01 (TAI)" xlabel-step (/ 1.0 (* scale 86400.0)) if-TAI-time-format (if (= kind 5) 1 0) xtitle (if (= kind 5) "Seconds (TAI)" "Seconds (TAI) labelled with corresponding UTC"))) (t nil)) (let ((x (make-float-array npts)) (y (make-float-array npts))) (dotimes (i npts) (setf (aref x i) (+ xmin (* i (/ (- xmax xmin) (1- npts))))) (plconfigtime scale offset1 offset2 #x0 nil 0 0 0 0 0 0) ; (multiple-value-bind (tai-year tai-month tai-day tai-hour tai-min tai-sec) ; (plbtime (aref x i)) (plconfigtime scale offset1 offset2 #x2 nil 0 0 0 0 0 0) (multiple-value-bind (utc-year utc-month utc-day utc-hour utc-min utc-sec) (plbtime (aref x i)) (plconfigtime scale offset1 offset2 #x0 nil 0 0 0 0 0 0) (let ((utc (plctime utc-year utc-month utc-day utc-hour utc-min utc-sec))) (setf (aref y i) (* (- (aref x i) utc) scale 86400))))) (pladv 0) (plvsta) (plwind xmin xmax ymin ymax) (plcol0 1) (plconfigtime scale offset1 offset2 (if (= if-TAI-time-format 1) #x0 #x2) nil 0 0 0 0 0 0) (pltimefmt time-format) ; For reasons unclear this sometimes throws a floating ; point exception on every call after the first call. (handler-case (plbox "bcnstd" xlabel-step 0 "bcnstv" 0.0 0) (error () (format t "plbox problem"))) (plcol0 3) (pllab xtitle "TAI-UTC (sec)" (format nil "@frPLplot Example 29 - TAI-UTC ~A" title-suffix)) (plcol0 4) (plline x y)))))) (plinit) (plsesc #\@) (plot1) (plot2) (plot3) (plot4) (plend1))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x10l.lisp0000644000175000017500000000307611413657240017570 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 10 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example10 (&optional (dev default-dev)) (plsdev dev) (plinit) (pladv 0) (plvpor 0.0 1.0 0.0 1.0) (plwind 0.0 1.0 0.0 1.0) (plbox "bc" 0.0 0 "bc" 0.0 0) (plsvpa 50.0 150.0 50.0 100.0) (plwind 0.0 1.0 0.0 1.0) (plbox "bc" 0.0 0 "bc" 0.0 0) (plptex 0.5 0.5 1.0 0.0 0.5 "BOX at (50,150,50,100)") (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x21l.lisp0000644000175000017500000001260711422577550017577 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 21 ;;;; ;;;; This example *may* have some SBCL specific ;;;; handling of NaN? ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example21 (&optional (dev default-dev)) (plsdev dev) (let ((knn-order 20) (threshold 1.001) (wmin -1.0e3) (randn nil) (rosen nil) (xmin -0.2) (ymin -0.2) (xmax 0.6) (ymax 0.6)) (labels ((create-grid (xp yp) (let ((x (make-float-array xp)) (y (make-float-array yp))) (dotimes (i xp) (setf (aref x i) (+ xmin (/ (* (- xmax xmin) i) (- xp 1))))) (dotimes (i yp) (setf (aref y i) (+ ymin (/ (* (- ymax ymin) i) (- yp 1))))) (values x y))) (create-data (pts) (let ((xi (make-float-array pts)) (yi (make-float-array pts)) (zi (make-float-array pts))) (dotimes (i pts) (let ((xt (* (- xmax xmin) (plrandd))) (yt (* (- ymax ymin) (plrandd)))) (if (not randn) (setf (aref xi i) (+ xt xmin) (aref yi i) (+ yt ymin)) (setf (aref xi i) (+ (* (sqrt (* -2.0 (log xt))) (cos (* 2.0 3.14159 yt))) xmin) (aref yi i) (+ (* (sqrt (* -2.0 (log xt))) (sin (* 2.0 3.14159 yt))) ymin))) (if (not rosen) (let ((r (sqrt (+ (* (aref xi i) (aref xi i)) (* (aref yi i) (aref yi i)))))) (setf (aref zi i) (* (exp (* -1.0 r r)) (cos (* 2.0 3.14159 r))))) (setf (aref zi i) (log (+ (expt (- 1.0 (aref xi i)) 2.0) (* 100.0 (expt (- (aref yi i) (expt (aref xi i) 2.0)) 2.0)))))))) (values xi yi zi))) (nan-p (x) (handler-case (/= x x) (error (se) t)))) (let ((title (vector "Cubic Spline Approximation" "Delaunay Linear Interpolation" "Natural Neighbors Interpolation" "KNN Inv. Distance Weighted" "3NN Linear Interpolation" "4NN Around Inv. Dist. Weighted")) (opt (vector 0.0 0.0 wmin knn-order threshold 0.0)) (clev (make-float-array 16)) (xp 25) (yp 20) (nl 16)) (plinit) (plseed 5489) (multiple-value-bind (x y z) (create-data 500) (multiple-value-bind (zmin zmax) (min-max z) (multiple-value-bind (xg yg) (create-grid xp yp) (plcol0 1) (plenv xmin xmax ymin ymax 2 0) (plcol0 15) (pllab "X" "Y" "The original data sampling") (plcol0 2) (plpoin x y 5) (pladv 0) (plssub 3 2) (dotimes (k 2) (pladv 0) (dotimes (alg 6) (let ((zg (plgriddata x y z xg yg (1+ alg) (aref opt alg)))) ; this part deals with NaNs by averaging non NaN neighbors. (dotimes (i xp) (dotimes (j yp) (when (nan-p (aref zg i j)) ; why isn't the coercion automatic? (setf (aref zg i j) (coerce 0.0 'double-float)) (let ((dist 0.0) (ii (- i 1))) (do () ((or (> ii (+ i 1)) (>= ii xp))) (let ((jj (- j 1))) (do () ((or (> jj (+ j 1)) (>= jj yp))) (when (and (>= ii 0) (>= jj 0) (not (nan-p (aref zg ii jj)))) (let ((d (+ (abs (- ii i)) (abs (- jj j))))) (when (/= d 1.0) (setf d 1.4142)) (incf (aref zg i j) (/ (aref zg ii jj) (* d d))) (incf dist d))) (incf jj))) (incf ii)) (setf (aref zg i j) (if (/= dist 0.0) (/ (aref zg i j) dist) zmin)))))) (multiple-value-bind (lzmin lzmax) (min-max zg) (setf lzmin (- (if (< lzmin zmin) lzmin zmin) 0.01) lzmax (+ (if (> lzmax zmax) lzmax zmax) 0.01)) (plcol0 1) (pladv (1+ alg)) (dotimes (i nl) (setf (aref clev i) (+ lzmin (* (/ (- lzmax lzmin) (- nl 1)) i)))) (if (= k 0) (progn (plenv0 xmin xmax ymin ymax 2 0) (plcol0 15) (pllab "X" "Y" (aref title alg)) (plshades zg xmin xmax ymin ymax clev 1 0 1 t) (plcol0 2)) (progn (plscmap1n 256) (plscmap1l nil (vector 0.0 1.0) (vector 240 0) (vector 0.6 0.6) (vector 0.8 0.8) 'null) (plvpor 0.0 1.0 0.0 0.9) (plwind -1.1 0.75 -0.65 1.20) (plw3d 1 1 1 xmin xmax ymin ymax zmin zmax 30 -40) (plbox3 "bntu" "X" 0.0 0 "bntu" "Y" 0.0 0 "bcdfntu" "Z" 0.5 0) (plcol0 15) (pllab "" "" (aref title alg)) (plot3dc xg yg zg (+ 3 (ash 1 2) (ash 1 3)) clev)))))))))) (plend1))))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x18l.lisp0000644000175000017500000000700311415106663017572 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 18 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example18 (&optional (dev default-dev)) (plsdev dev) (plinit) (let ((opt (vector 1 0 1 0)) (alt (vector 20.0 35.0 50.0 65.0)) (az (vector 30.0 40.0 50.0 60.0))) (labels ((test-poly (k) (let ((draw (vector (vector 1 1 1 1) (vector 1 0 1 0) (vector 0 1 0 1) (vector 1 1 0 0)))) (pladv 0) (plvpor 0.0 1.0 0.0 0.9) (plwind -1.0 1.0 -0.9 1.1) (plcol0 1) (plw3d 1.0 1.0 1.0 -1.0 1.0 -1.0 1.0 -1.0 1.0 (aref alt k) (aref az k)) (plbox3 "bnstu" "x axis" 0.0 0 "bnstu" "y axis" 0.0 0 "bcdmnstuv" "z axis" 0.0 0) (plcol0 2) (labels ((theta (a) (/ (* 3.14159 2.0 a) 20.0)) (phi (a) (/ (* 3.14159 a) 20.1))) (dotimes (i 20) (dotimes (j 20) (plpoly3 (vector (* (sin (phi j)) (cos (theta i))) (* (sin (phi (+ j 1))) (cos (theta i))) (* (sin (phi (+ j 1))) (cos (theta (+ i 1)))) (* (sin (phi j)) (cos (theta (+ i 1)))) (* (sin (phi j)) (cos (theta i)))) (vector (* (sin (phi j)) (sin (theta i))) (* (sin (phi (+ j 1))) (sin (theta i))) (* (sin (phi (+ j 1))) (sin (theta (+ i 1)))) (* (sin (phi j)) (sin (theta (+ i 1)))) (* (sin (phi j)) (sin (theta i)))) (vector (cos (phi j)) (cos (phi (+ j 1))) (cos (phi (+ j 1))) (cos (phi j)) (cos (phi j))) (aref draw k) 1)))) (plcol0 3) (plmtex "t" 1.0 0.5 0.5 "unit radius sphere")))) ;; first 4 plots (dotimes (k 4) (test-poly k))) ;; second 4 plots (let* ((npts 1000) (x (make-float-array npts)) (y (make-float-array npts)) (z (make-float-array npts))) (dotimes (i npts) (setf (aref z i) (- (* 2.0 (/ i npts)) 1) (aref x i) (* (aref z i) (cos (* 2.0 3.14159 6.0 (/ i npts)))) (aref y i) (* (aref z i) (sin (* 2.0 3.14159 6.0 (/ i npts)))))) (dotimes (k 4) (pladv 0) (plvpor 0.0 1.0 0.0 0.9) (plwind -1.0 1.0 -0.9 1.1) (plcol0 1) (plw3d 1.0 1.0 1.0 -1.0 1.0 -1.0 1.0 -1.0 1.0 (aref alt k) (aref az k)) (plbox3 "bnstu" "x axis" 0.0 0 "bnstu" "y axis" 0.0 0 "bcdmnstuv" "z axis" 0.0 0) (plcol0 2) (if (/= (aref opt k) 0) (plline3 x y z) (plpoin3 x y z 1)) (plcol0 3) (plmtex "t" 1.0 0.5 0.5 (format nil "#frPLplot Example 18 - Alt=~d, Az=~d" (round (aref alt k)) (round (aref az k))))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x22l.lisp0000644000175000017500000001372411422577550017601 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 22 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example22 (&optional (dev default-dev)) (plsdev dev) (let ((arrow-x (vector -0.5 0.5 0.3 0.5 0.3 0.5)) (arrow-y (vector 0.0 0.0 0.2 0.0 -0.2 0.0)) (arrow2-x (vector -0.5 0.3 0.3 0.5 0.3 0.3)) (arrow2-y (vector 0.0 0.0 0.2 0.0 -0.2 0.0))) (labels ((circulation () (let* ((nx 20) (ny 20) (cgrid2-x (make-float-array (list nx ny))) (cgrid2-y (make-float-array (list nx ny))) (u (make-float-array (list nx ny))) (v (make-float-array (list nx ny)))) (dotimes (i nx) (let ((x (- i (/ nx 2.0) -0.5))) (dotimes (j ny) (let ((y (- j (/ ny 2.0) -0.5))) (setf (aref cgrid2-x i j) x (aref cgrid2-y i j) y (aref u i j) y (aref v i j) (- x)))))) (plenv (/ (- nx) 2.0) (/ nx 2.0) (/ (- ny) 2.0) (/ ny 2.) 0 0) (pllab "(x)" "(y)" "#frPLplot Example 22 - circulation") (plcol0 2) (pl-set-pltr-fn #'pltr2) (plvect u v 0.0 cgrid2-x cgrid2-y) (pl-reset-pltr-fn) (plcol0 1))) (constriction () (let* ((nx 20) (ny 20) (xmax (/ nx 2.0)) (ymax (/ ny 2.0)) (cgrid2-x (make-float-array (list nx ny))) (cgrid2-y (make-float-array (list nx ny))) (u (make-float-array (list nx ny))) (v (make-float-array (list nx ny)))) (dotimes (i nx) (let ((x (- i (/ nx 2.0) -0.5))) (dotimes (j ny) (let ((y (- j (/ ny 2.0) -0.5)) (b (* (/ ymax 4.0) (- 3.0 (cos (/ (* 3.14159 x) xmax)))))) (setf (aref cgrid2-x i j) x (aref cgrid2-y i j) y) (if (< (abs y) b) (let ((dbdx (* (/ ymax 4.0) (sin (/ (* 3.14159 x) xmax)) (/ y b)))) (setf (aref u i j) (/ (* 2.0 ymax) b) (aref v i j) (* dbdx (aref u i j)))) (setf (aref u i j) 0.0 (aref v i j) 0.0)))))) (plenv (/ (- nx) 2.0) xmax (/ (- ny) 2.0) ymax 0 0) (pllab "(x)" "(y)" "#frPLplot Example 22 - constriction") (plcol0 2) (pl-set-pltr-fn #'pltr2) (plvect u v -0.5 cgrid2-x cgrid2-y) (pl-reset-pltr-fn) (plcol0 1))) (potential () (let* ((nper 100) (nlevel 10) (nr 20) (ntheta 20) (cgrid2-x (make-float-array (list nr ntheta))) (cgrid2-y (make-float-array (list nr ntheta))) (u (make-float-array (list nr ntheta))) (v (make-float-array (list nr ntheta))) (z (make-float-array (list nr ntheta)))) (let* ((rmax nr) (eps 2.0) (q1 1.0) (d1 (/ rmax 4.0)) (q1i (/ (* (- q1) rmax) d1)) (d1i (/ (expt rmax 2.0) d1)) (q2 -1.0) (d2 (/ rmax 4.0)) (q2i (/ (* (- q2) rmax) d2)) (d2i (/ (expt rmax 2.0) d2))) (dotimes (i nr) (let ((r (+ 0.5 i))) (dotimes (j ntheta) (let* ((theta (* 2.0 (/ 3.14159 (1- ntheta)) (+ 0.5 j))) (x (* r (cos theta))) (y (* r (sin theta))) (div1 (sqrt (+ (expt (- x d1) 2.0) (expt (- y d1) 2.0) (expt eps 2.0)))) (div1i (sqrt (+ (expt (- x d1i) 2.0) (expt (- y d1i) 2.0) (expt eps 2.0)))) (div2 (sqrt (+ (expt (- x d2) 2.0) (expt (+ y d2) 2.0) (expt eps 2.0)))) (div2i (sqrt (+ (expt (- x d2i) 2.0) (expt (+ y d2i) 2.0) (expt eps 2.0))))) (setf (aref cgrid2-x i j) x (aref cgrid2-y i j) y (aref z i j) (+ (/ q1 div1) (/ q1i div1i) (/ q2 div2) (/ q2i div2i)) (aref u i j) (- (/ (* (- q1) (- x d1)) (expt div1 3.0)) (/ (* q1i (- x d1i)) (expt div1i 3.0)) (/ (* q2 (- x d2)) (expt div2 3.0)) (/ (* q2i (- x d2i) (expt div2i 3.0)))) (aref v i j) (- (/ (* (- q1) (- y d1)) (expt div1 3.0)) (/ (* q1i (- y d1i)) (expt div1i 3.0)) (/ (* q2 (+ y d2)) (expt div2 3.0)) (/ (* q2i (+ y d2i) (expt div2i 3.0))))))))) (multiple-value-bind (xmin xmax) (min-max cgrid2-x) (multiple-value-bind (ymin ymax) (min-max cgrid2-y) (multiple-value-bind (zmin zmax) (min-max z) (plenv xmin xmax ymin ymax 0 0) (pllab "(x)" "(y)" "#frPLplot Example 22 - potential gradient vector plot") (plcol0 3) (pllsty 2) (pl-set-pltr-fn #'pltr2) (let ((dz (/ (- zmax zmin) nlevel)) (clevel (make-float-array nlevel))) (dotimes (i nlevel) (setf (aref clevel i) (+ zmin (* (+ i 0.5) dz)))) (plcont z 1 nr 1 ntheta clevel cgrid2-x cgrid2-y)) (pllsty 1) (plcol0 2) (plvect u v 25.0 cgrid2-x cgrid2-y) (pl-reset-pltr-fn) (plcol0 1) (let ((px (make-float-array nper)) (py (make-float-array nper))) (dotimes (i nper) (let ((theta (* 2.0 i (/ 3.14159 (- nper 1.0))))) (setf (aref px i) (* rmax (cos theta)) (aref py i) (* rmax (sin theta))))) (plline px py))))))))) (plinit) (circulation) (plsvect arrow-x arrow-y 0) (constriction) (plsvect arrow2-x arrow2-y 1) (constriction) (potential) (plend1)))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x03l.lisp0000644000175000017500000000427311410652047017567 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 3 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example3 (&optional (dev default-dev)) (plsdev dev) (plsori 1) (plinit) (plenv -1.3 1.3 -1.3 1.3 1 -2) (let ((dtr (/ 3.14159 180.0))) (dotimes (i 11) (plarc 0.0 0.0 (* 0.1 i) (* 0.1 i) 0.0 360.0 nil)) (plcol0 2) (dotimes (i 12) (let* ((theta (* 30.0 i)) (dx (cos (* theta dtr))) (dy (sin (* theta dtr))) (offset (cond ((< theta 9.99) 0.45) ((< theta 99.9) 0.30) (t 0.15)))) (pljoin 0.0 0.0 dx dy) (if (>= dx -0.00001) (plptex dx dy dx dy (- offset) (write-to-string (round theta))) (plptex dx dy (- dx) (- dy) (1+ offset) (write-to-string (round theta)))))) (let ((x (make-float-array 361)) (y (make-float-array 361))) (dotimes (i 361) (let ((r (sin (* dtr 5.0 i)))) (setf (aref x i) (* r (cos (* i dtr))) (aref y i) (* r (sin (* i dtr)))))) (plcol0 3) (plline x y))) (plcol0 4) (plmtex "t" 2.0 0.5 0.5 "#frPLplot Example 3 - r(#gh)=sin 5#gh") (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/lena.png0000644000175000017500000056421511416201072017536 0ustar hbabcockhbabcock‰PNG  IHDRæ•" pHYsHHFÉk> vpAgæU¥.í€IDATxÚl½IeÙuž}º}Üè#3«cR$H‰­%KlÁ¶ðÁ Ø‹Ul¤?è‘'†g <° Ëj,C H«XÙEFF{£{ÏÙßàÉõpÝHÇ ‘y›söÙ{5ïz×»êÿïÿý0 }ß×u= C)¥ëºÙlVUUUUu]×u]UU)¥išûûûûûû®ë¦Óét:ÍfwwwWWW÷÷÷www×××www÷÷÷u]—RnooG£Q]×ëëë³Ù¬iš¦iº®ã+J)Ã0ðQKKKwww ³ÙŒ÷6MS×õt:mÛv†aêºîº®mÛétZJñCº®ãsêºîû¾”²°°À‡Ôu=Ú¶­ªŠ,¥,..ÞÞÞv]WUß2 ƒ¯ªªmÛ¦iøŠétº¸¸xwwW×5?›ÍøÞRJÛ¶www]×±2£Ñˆ•\XXð3]º¾ï›¦†/b…ù½+Ï'øúÕÕÕ›››ªª¼;Ö„‹ç^ú¾g‰ªªº¿¿_]]­ëúúúz6›-...--M&^_UÕ0 <î‚Ïô/\a]×mÛrïËËËÇk†a:ú˜¸;[¥ŠŸ¯gGñ—ÛÛÛRÊl6ó¹¸?ù@^ÆÃ†±´´Ô¶íââbÓ4ì·¶m¸TÖ“ýàVw͹e¾ˆOvÍf³¥¥%.€Íæ’r‚|1wÍ^½¹¹á¹]]?ă–7-‹À˸}ÏÅýýýl6[XXàHrÍ[[[›››[[[KKKMÓpNyÉËøs¬ÊåååÙÙÙ_|ñêÕ«öÓO?å˸ÛÅÅEïÖ'Ç¢ð˜¹D7—Å[îïïù®ë¸îŸÁy6X5ž=—[×õÚÚZß÷¬]Û¶˜§Ç•ã½¼‘-ŵùFož¯pdz °2ÞQ×ul_V܇:›Íø(Ï¿ç8ñÙ lhîËEç€q ¾LËÈp,¹Gw‰GEËÎËKÍÇ`6› 𼼌¡¹»»c‰†aà¿´¡|Ñh4º¹¹áÓø%¯†Eó.X=×àEê0Lü÷“ßî‡,--iqX^·_ͪòô———ïîî¸*_éæö¤¹ìî”U¦h.½r¬€¯ç-&öŸáÖ ³10ë£Ñˆ+tp~8ß;ØumÛv]ÇZZZâ,¸¦Wäâ«5оåÁõkÍ}{‰k3˜à2noo¹°üJ¿7€ËçŽ\·ìz5U\§&LÓÆ³®ëzaaaaaÇïùÕù<°¬ î°ýôÓOyX¾åÊse³ò'Ñ_ò!}ßO§Óªªîîî4+++|¥»M£ÆÃfÃqÑ···lSVŠ­€µÖ²‚ì$N#÷ÌgCø\±\®µ›ÌÍ'hžÜ¬Ä\óâ⢓ý¤³òIhvq¼€øëÁþæs è0pn5.~qqQ_Í¢åUÒêñQˆˆa”ľ†²,:@Š&ûÝ=ÄSÖ\ºbÆA¿ÙXmK¼©Õskòz/»æú¥|þýý=‰*_¡‘ÍŒ ãÅn‹ëqµ/\äÛ礑ÅïÝÝݱìÄGW32·[Ÿãd,éÍê{ ^Þ5LÆw|—»0r>0§®>>Ï$á6kå¦t»Ú\dÎø"#bÌkxoêj0ÅQ70Fã+ÜÆZílå5UyÏÚä ÉâðˆñFO&³Æz—çßDÉOnšƒÎÔÇÃäpƒç±ç£|¸a×™ÿ5®wóóÍŸ!ˆVRÛÍW¶ä#ã·h¦}Žl›û"{#É—š¡¢ÎÕë|› "ù8¹_ç6>¿¹¹1’ÂLOÝÝݹŸ´»Ù˽ýÖØÆAUU-//ƒ…e·–“26œ([Yçã)òòŸùbJ)‹‹‹.7ßë&ÐÆçK]\\4EbÝ]?·”Þ p!{£›étêjrûü Sh²ÃBéÁ°æü©Ñףɻë€ó3Í™)™nF#¢ÕãtyÒÜdøp oŠ k+êÄBqyù±ÂÆÅì~l´'ÜDÌ/ʆ@‹ìƒf‹räˆõøj_V¥ $E´T‹¹¸¸Èä{¬ñP˜Šðùl-ž#_ÊfX*ï%NÞo Ñ^þn¨a8fzèƒÐj»ýÊ<&õ #3Ðfý59¢FåÀg+Fl…3फº´ Œ¼5JþçžO‚·äêè?ñ$|½æ_#ÅsÒ!°!Œ{µ}&:+ö:kç¹2½¿¿¿wù°JB>T¯œƒ³u øL6⃇¡“t¨ BçH„ç§Ë†ÃÐß=XÃ:0NGŽÝ0%Ù†úá\FN<–Äì9ÉP2Lð®Áu{é-g³ÑAŽê= n¸œ;ˆ»gÀ[Àíà~òi, V÷Ìkt„À¹ þú)ZänÆã!<–.ˆ‘õEóÊu“âŒFÁ¦o2|—G1LvXyÍMŽh€ƒ×ÖÖø=v¹ ôÇðQÕÞÕ œ>Æ\úuòhÃ[w+oΨµÈŒÛ_XXкànEþ®­4ò2žÈ>2[."_!8íÏ3[×uûé§ŸÖ©¼’#gÝ){ W_—ãÕÛÛ[>Ô5 qÏU •îK¥ÿëÕkÝ%dI˜kÇSqßä§Î‰Êy“!•‘JhÖºËb¢ªcK ™%ùg9H6«¥°˜Ë¦ÙHóZàs`‹ÖI°Ëšl ×¹´´dðÈeXµÉU!³€ét:™LVVVò¬ëšm—³f=M•½:ª´Ùm·jGJ` FùëÜ©>k?¡‰*˜Ï×ååÃyš¢6žÃüg®QK²æÂUTÐxLËËË3S׋‹ BÈœ gTn4]__ç²XÒìQª„¬iˆM»r"–ó˜|µìÀ’JðÃ0ÜÜÜ@pXòÙ©SþÈ5IÔ÷pµ———Ø—1GUú`O ×suuÅ‚aDO&®!#ã9±3 kðƒ¸ „Ù9ã¬C:Q ìûþî!¥_\\4Mó(.--ñ.×KCVÄ7òP›T ó°>ï‡Æo ¼>jyy™[üʱkH-‡™‚&¯&d[¯®®Îx/M*·Ñh…áµ®Còe‘»6/Ât:Í%<Ì'‡LÇþA²y¯Î»Á+äK½’ œ•sû¬^Aãkz+ú†®rìë-}'‰ål¥Š,À¬eÉÏÝæ g¬Ãú¬‡àÄøÕZ4¯ŸË3žµZg|¡¥ ÃÆæcqrù¤‘=q/`U^LNrbëFÊþÀj¨$ θL÷S§’ ‡"UrÔ–jMOÎæ ‹ü«mRሕ )#6+++‹‹‹ËËË‹‹‹kkk£Ñ,›eáÏ|šÞ:ü1é·k™/yê†(š0³¹µ\ü}4]^^ÖQcæYÖuM¥Ö`š`àç>ÆôfÄ$ïN˜Y†²š•öE¿šÓ ØFUšTmƒÉ¥Yô©è‘àcÝôùY²Vn~Ÿß5D…^W¡;½½½ÅDêâòã”õÃsÒÁ§±Úï)Þ`I$k D<¯@No1XW~†˜–f·geãà½Ø‡>Æg”Á>žW˜]Ní}ÜÞ—ù©°†'\¯VEÙ‡O`#ñ9µb!þ­Ë4‰6vkeϪqoû™¼¸IUïl&“,†.[yMª.¹JUQ×Ö˜«ÌWâJ)ËËËœh187Ûh ÙíU©ŒÓ¤º­á›— ÜÎFÕa7‰Ÿ‘Ïô-ÊNÔê6͘_6ŠŠÂI| —ÂYFFx¢¤0%•“Ùvâ¸Ùÿ瀖çD½NÕÐ:jÿ^ª—ÍÃÆò½f>È.~ &=Øú\!Ÿ¬«tbÉrqq ëƒÉ5×nxŠÙÞy‰Ú–TôÓ$T©ÈeUêÒ%âÞ}jdˆ:«üù»šT”¨Üã7r1úùªš ƒ€€¤Ö‰ŠeˆÄ+q§¢%Õsy9ß—ýë 4þ5$áRÝÒn¡ì¥/>6©Èk0ëƒö)à‡2Ã`ÖXïîînmmPKÌNWäý$fÓü+p}|@–trjlR–Q3w# þN”×Ì— ÜþhõtW9Ô2ät‰Üílc6¹o‘ˆÓDõ£ë:É„5%°`MUÆ+›¦iøÃïÈ®ƒRQ˜’¸¹@tD±©¨Ç’O[ZZº¾¾6—ÓñÌðKYfõ|ÅÝXI[ã5W‹x˜-òdw›…yÒLÜ–ÆÍ<·ÓM%¦™KÒÃUcL-—HFå)4$Mrâü¯&±ÞÙ‡T)JÔa²ÍôɨBö¯æ µÈþÏÍßD­ Ìˆ³AÏS³5¤!µ4äØÍgg,Œ‘* x†Á’¥®Hêœßký*û3Tþ)¥¼ÍKâ\dF¯Q™^ *Þ!Y ¸Ê•&  ˜&³ øÍôÊg<¤>=ƒÏ^s&Z¯åÖ$k µñwô1ôó_ +¹•`A•J{hË?ƒœR6(®Ø“ÐÎsŽ| y×6©ëŠGŽ¿»»ãïºG¼“H޳9ÈÛ4#vÉîŽ}CE¥ž¯?4Q¥Í}aúö°Wê ³%u#yœú ßµA[­R1ºNͦëyZ³Ü‹™l•hÓ|¦^r––Wä(Û2ýåMM´¬iråÔ˜È(ÜæA“o%ÖQú 'j[;ûfßn‚bÊ"®š®*U!ü‘‰&º½…yŸpJ¾AL'oç sa4üèŠ5i ™''½}L}¢D‹ƒˆþxë(0Ír¶ Çø¨€” ²¹¥vÎã×Tõ} ž·hŒš º¹‚Ö}ƒ¼ùì:\b>?CzMê+6©t»Ë#ŽÐ²QÖ©à†°úi3„<@I%†~ü[`»Kѧluu•³ô tÕ?ƒ­ '3'_õ|ÁÛCây3¢išF0UCCœÂC— ÈÃåO£iV’'…¸Ä1X#%hÆCªÑg†[õÂÜœ®p6›]__ßÜÜðzá?rŒ\JiÿìÏþÌt7?×Uó½ úáÙlv{{KÀߊÎóO”»8ŠFÂuê°çíz †)±(˜« CZ›¢5ÔU–`ñ˜H²uJpör—OF\LŸèétZz¯óž%Êð<ÏæEJª›¸ ”È¡{“ŠUt¥Ê ¨ßBÃÝ¥v-M¶×™@®áþþ~eeÅ2™¹?{T;žSò&ñÂÚÔøà¨×AÀiR•ã݃TŸ6nÍ–ˆo÷Ød ž®«¤ÖË!vôœ6A\p“çí×}?—;¬aEïË}›ýº!§Î@~‰öÔA“ªš’!Æu‚PšÔ*Ȃۯcà©|@Ÿˆ¯ ¥CÔ %âÕѯ'3EÈ’·i¤¦ÿ0^s»jïü}ŽàšT¾sGaİ:r àãn?ýôÓœÔ4 GÏä’Ú‘XG®X4‘ðkâGuÑ•º¼¼|{{;N766pA«««¼ÑÌ« Ö†ÏÉ/Å0P`ø¹H›±óñRÍÛÝ ©Õsî‚bOóãáù+ Qa4OÿÀí’áÙÒætžUá¼:•Šü_æŽ'ˆâÇ]ëž^̈ûƒ°¿JzúmO~öUCôèºq›Tö€pV‰‹dúæ=Vó°·ÿ—Q+©þåžÎ‰|ímÊ|ˆ*J`^|—4…,/hµý%1¬PÆ,Éå`§™¯9ð”M,J@–ÙfáqëDVÈŽJómîãwñ!™MâÉ÷îÄ^Ky-}úuú˜œMëÂsèSiÏT•zàªùš˜ÈF‰ºGð·1~5/q1ë`qqц“:±ÞÄ­ªªjüãû}ý;dÅœ z†âp (ôÉ%œÛÛÛÕÕU’|¾îööÖÝÆÖÑÕë¢ ÂŒƒ€ûDµ·ö'𑳃n^@Çd¡ÏëdkZ«;rÖëâg/HËì’rV wwww¼Kg˜#y£0 ´Ñ„©A›:T}¨©Ø'$xaÖPGý*”æ+ãµ¢¨téĹ%•ÌÙ‡T¾‚ œmeF”­j•DkôU©ÙËÌœe a¬:áî$)Cªo²°î;ÃÞEб\öçëê¼A#,Y~ºÆ:Z>ª¨‹ ©zcfäékpë(8T ÀÎש‡Îõµ!±@ß5"º£Z89ªõÑd ¨’7‰=ï“Y{/`y}ôiêÆúñð±2 ]¦Ž¿Ê8ÌǬå®RÛDàÝ7<6ƒäâ¼8Ã+"¬•••:ðrälà&–$Ö˜Û°PÞB’l#>Ö nÇß\¦DwaL¼¼Ê%§Jpvôo9“²¨T§YIœòc|Ú‚+D^wHôß|8ÝC%ñÎÝÄZÒ&ZK´€¹¹kÚÔrå•·IÿÀÌÑ“ixeØŸÝÝ×[`åüH‚©¢éªI…m7M勌?ºøfÖ%÷ÚÙzž`ù±×fž·¥ewظO†ÔkB:Ég#+†˜Á~Þˆ{ss ¡ä}h¹Ód˜§Îø€üØÁ©{^[C¿¼‹êh/o×?§xÝ|C«yM†Ts>>¿¢–—q·!è–>\‘M!fí×ÊÊ [HOŸóÓ·çúã?αz;¯²–ÓŸ6è?^ßd2Á0M§S*Vu”´†¨d[SW%FèP+'#Š[is¡‹bí9›ª>)´ðP}YNÖÜÄmðÐ2[ÝzVÆwèªæKi‚¸u"æ`ô môÒy÷T©MoVH¼¹¡ÎÊ讨˜Ö¹ÏèDõûL‡  ÆgW¤íÐ8Ø7QóÚßßgï¶m»½½M»˜ð­ú{šBMªòôI×mjŽì¥••Î’Òü‰ÙÍ^=ÇÅæ×U¤ÝÉ2ËꤨU%é+Ø!N¸Á”'­JM®›ÖÐ$CD¬IÅßAggiQ×w¯¤Iúkæbn}¡Ößj£Ñ¢ Ã€±N%ì.ú¥þŸ¨Y´ƒ>©k°‹äU –õ±æ¹$^…ODO©‹Z^^VI¦š§ü&lãKKœwJ†u*XJ¹Âÿä‚.”—)ob41$%Á×±Ë'Iû(ý½ŽŠW›;ù/‹»™0BÔ&½ƒÁ& Øþ…J‰ÎñN€‚»ªJr¦u]“¦„úÕ9zõ‡ÜÖ¦6+^æ­Ã•¬®®îîî6M3¿öµ¯íìì`Sž>}úÞ{ïq1{{{?†—¼±±±¹¹YBàØ`ÊXÒ³d•ß³8º…Õêk’²‚†ÃMëój“N“‰d}„MT‡MŽª¤;ÒÕ |/ëe[iÑ ëòÖAbÐû² zJÌ–ÝÂ~¯v6 Í|QÂÚ‚µWƒ;‚‰BþKÚ8>/©N ÝwsLóDÿî.-‰3Ñ&ºÏ8I^Œ‘£+#Fiäñ6êÿÁ~`,Ú&êjF…«TeÏ; I0Œ$}ø(ÔÊõi]ûùÝcfµ¶Á#-ój½ÜøÜ’†h‘scµÁê"M« 'éÃnR…K,VãE®½óÛsú]Qª¢å5¯aކêÀGu³M(´¸cX`/ Æþ’{©á¦“Õø6Qœêƒ`Õ¦v½½=®aee…4–»^^^Þßß¿¾¾^XXøêW¿º²²rxxXUÕûï¿?/..f³ÙãÇWWWÉú÷÷÷ß{ï½………ååå'Ož<~üxee¥¥|N¾;ÇʻȕMìB=ÏðZ-ñ¼±I¬ Xª/©Ï¦„ÖŸ£dv ªKêzSŸàðNß‚.ë,UƒÒ$Þ¢§,3f›y&¤˜£.Ä;27 ©ßÃÝÕ§eƒ¬>õëhÍÍ‚KB ³Y¬’Š–¹…Ab.5´Iiˆfµ á/--ÝÜÜdºY†øP£!­«Ñ~òÉ'%þÚ¤‘š)Ú† 9’ﺎ¯g/fäKoÆ )Õ©êOJt·aJØy³øé¢—=Çw<ãœô¶¡{×$vœ1pޱKà2Yq-§ßY,Ç5žsã;íp@6ñÍ;j'†ÁÄ9‹ä—'CÔœ)¸Î%ÉÉ—¤²V¸ÅBÕ©Ÿ‹ ËÁv×uŽ£ÑèÑ£Gt¡+>‹Y\___[[†auuõƒ>¨ªêÕ«W£ÑèñãÇÓéôì쬪ª­­­aNNNÖ××www///»®ÛÙÙÙÚÚZ]]mÛv<ïíííííõ©ë[¾^ûÇÖ'’ßUGYPŒ"§uþ™ó}ª ljˆ%布 #—©R}9»ó²›׉qZˇ’nÎWêÄ&/¡£[¢¤ãé¨R᫼ƒ…»ý´n9ÌØ\“Š?¹˜×¹™/©åS<$ÚJ.¿°Ù  ü/¯ª›—-Ñ4›~¨³„’z}“ Au]·?üáµ¾mÈŸótuMÀæt])Ά¨Šq2þ¾™goY<2Ð$çðM°¶ ^•­s¾7ßž~)£×b 9ªd¥›êÓr;dNÓòÛ}f777uBÊ`a%Únø‡˜à0D“š¦Sc*Pêã4,óõ/CZû2Àä®âhÁ¹å̬­­ÝÞÞ1Jggg§iLL(ïââ¢ÕÛÕÕUÞutt´µµµ½½}ss3™L¶¶¶.//onn¶··766nooONN·¶¶Ú¶½¼¼¼¾¾^[[ÛÙÙÇ\Ÿ@(×'A’|ñ9¿0[7êá‡*m“ÈGž=}ÎY|e41ò»&‘'ŒŽsþ"ÂP%W;ƒ8%JcÞš&C+Ú©&I}¹çr¹£ †Ñ}“ ;U”ÌŠrÚá/‡T:ôì¸3r'ÖÜ&r¥W>Ì÷T•4‰‡}ˆå¢‡hŽs]m|-4Úÿ§FË[k•CqÞÜÍkiª²ß0S ±&h¤f¢nœŒ¶TIÅŽ£Š ö¡PÏó>ª˜)à‡xDë¨tä´®à¼JðdŸt}»ŸfêÚ%ù!cZHž|02»ÒØ8ƒAFÝ ÚdJ?¤n!É\Eö¬ºíÊôxkŽ766F£Ñâââx<¾¿¿___ÇÓ­­­¾ï %êÀþ ½!noo_^^///¯®®Ò6ˆ†áôôtyyyss³iš««««««íííÍÍÍ«««³³³¦iÖ××onn.//§ÓéæææÎÎÎÎÎóxVVV677¸xý??DeÔÀrJ.0åT(;žYRÊ6µ´ Fž6 ó7-Ò d¿H!¸úaá¢Â!X&žþÉ w]ÇFʶ†oy6–¨ƒç .#A9ª*1æš%YçŒûS%~ŒEIõ»œ-êË]y•»ºNå!ÚÚ {³;φυ5Ôi×ÚO?ýÔ‰oÒ|<ùÊr>œun ò'±£ÜœæÏ9”€‹©M“ú×3$¯UÎU¿:qsªD»Z¢M“FdðHG§‘¥ü§ÍfCfqZä÷ÓØõóíA$Â%UŽÜ»u]«Ê`2o1 ­ú\ë¨öщVÊ\ n]×LÚØØX__ÇSÙL GÓco†mÛ’»F£½½½Ñhôúõ뺮Çãñêêêåå%.‘Te6›­¯¯/--]\\ðÄ×××뺾¸¸@} àéòòr2™ŒF#í; ¾²²‚ÝF+++ËËË@¶Úõk…õí¼*†YŒ½5B]1CŒ>)‰]˃L¹JøcŽ;¬J©ÃTp OË)UŸºó܇u1 d@? $5¾n~-W•ªÆÂ3¯FÓ¥ÙÍ Ãl6cÚ³Åô.ô"ÂvúQcX}@p~•T̲=õ¦JªG»CÔ ðœzjÚýèG\DîòBK*u{M¼Øe-¥\__CDÖõI¹) ´õ 9qZrW°nj–Æ4Â%굄W‡D\BÂÁ˜Åm—çñø°½Bß.¥vm(Ku*Éóz*¯¹Ý·N"¿”yÃG› ªI™[Þ Ë> ýxoaˆFŸ¸µm‹ãh4Z]]êâTähwqqñøø¸”‚å²-‘ÿÂvÌf³“““¶m·¶¶¦ÓéÕÕÕÂÂÂÊÊ íSØšRÊùùùúú:7~{{{{{k—ÕåååÕÕ•ìä:•öb…WVV¶··ÉI%ئ|‘[HÐW?§Ãhš¹F×lʇ`‡èhsÌ•7ŒP¦z98R#·I5þ*º8Č쥹ÌBUÉEXÀP©|V-Ë;¢²9‚B$dæ»Þý/?§ ¦Â`§N$uCªœ9Ö‰}iôÇ‚TÁã3Vꣿ²‰ÇsdÂ$Çà`,댵âÇn?þøã ³i2LÄݵ¦C¢ÃðSB¡ŠÒž­‹9Cp^™'œs¨œ¸Ö‰¥ëÚ;¯o°‰vüYRÛ©’zt•³›­“éÂí¼ŠcIŠQm’O´ÑÍËæ9[a”&, £ra³ù9]Óétee…?õ3b¾½O}-Ëx K¬: Ùÿ•••Éd²¶¶F2Õ÷ýåå%@{¤>µÂmoo×u}yyÙ4ÍöövÛ¶]¨;ÞÞÞ2e·ªªóósrƺ®m¨ZYY†áàààææfuu•vKKwuuussãDbÖÄî°ñxŒå‚ú‹$uÒÔW';³f^§Jœ8L®Á{¤+4%Zœåì& Ù‹3„L¾µO}M€ˆ[•Ø­„á8’ìl¸Bj¬nKáN7¡„‰>XÓUª€ePÏÓ'²æ…exË]Ô&®¥¡â ü9×®š6Ì÷!k7†yª”¢o†G`û@²ÜÛuôœ‰¾ýØO>ùD“é Ïy“Wï"ö¡ ØÄŸét p+»ûÂÖ|ÔAÄðñK<É zÓ4ôÙ ™-ædŠª¥KÜ&аK߉cˆF¿7uH0µâ÷¦1°ÚœÔ³¡Îr_vœÎæe­|{“ZgsÂB*ÍÇæê Û¤6sðLÃ!ƒ³dHõû›››ååå¶m¯®®ú¾G€ fUUÔ @޶¶¶–——onnnnn666º®;;;£[ˆ’ÖÒÒ§(‹‚a€–––xÊL'­ó¨Sº¯®®R‘œÍfmèv¹Å±€ËËËãñx}}Ã~~ÞÏ7TòÙŒ•Mš-$DÕÇ[";’üDhÕðY{–0ß™ˆ_%æQ=/~íFÒü„êê2²9‹)[‚†uí¼f^N¯r¼™«}´åìzÓ&u2y¹ZšiC¾¾„®¤æìA–;WL³ëïëijíCìp49üÁ3þ›ø‡?üaŽ0sž™Ù…À…Ø!³®†¤ói ¢u°x»4“Ý íC‘ÎaŸn #)ë:ÃYš›æ(0¿7g uô¯e„¹‰Ñ¦=ôMtçÈKc”ëÁ¥”••¥3¼žvž˜g ‹“y.qæôÇ€<ç­f"¼€-ÔÄàÁâ3———ÄqM ò‚²`5ãôô´”²¹¹YUÕÕÕ• U'qÙh4º¾¾fMˆ¡&“ 7¾ººjü¿¾¾> Ãd2)¥¬­­1œêþþþêêªm[ưA1¦üü×x<^[[ë’º‹ÍÄ0ÔŒ‚ÒÑ%q¨’pôl­ª„Cóz¥„UyÕ€ÿ ÄYùÉé¾|{îä4F5ÓñŸMš—WEE¬ž¯£Y§¯S̓§h÷@IÂOmj®“Šrš†Íu¢ùV! ÞMùòòÒ^Š*¡‰ö?ÈÍõº˜—çïy6r|=<'Âã.µ^¯¬¬jaSêÚI↘„(eÔýDUއæM o}}½ïû³³3LÆl6;;;ƒÙpvvV×õÆÆ•ô±º®‰æ°›˜°ÕÕÕñx¼°°pqqqzzÚ4 5A‚ñ>¸£ 8Uêøá—+++°Ã$ôµ1žO[Цþ½ì .¹fß'šK'ªbC¾'§Ю‡á—ænä€ã$ñ|áydQ#BË ë MtJb‰”ïùÒoUó„›>~ :6lSç¿G/ÿ¦ÌSID¬ï"_9˜¦Q{U”8=ÈžŽ\Áð:5‘~2Ñ=xb]×í~ô#¯ÉGÛDK´ña•Z+1=bX§%Aý¼žyÄSŽ•/QÌ!.L K3Ìæ3%¬c@zê.hveÆ ¹ͳ+åîñ)v¡‚ÒDG¡A: 5áü rfZªOÍzæ\ªA“º.¶=f ÀhëcÌÕ4ÍÆÆÆÖÖ¯ )t³0R9™Ð\3FMéõõ5᥮ë...¶¶¶8www+++œ"AkÞ‚u;::ªëšk ˜ œt~~ÎöÅÔb=高L& ÛÛÛdÇ'''÷÷÷Ð)@Ðø|ª–î¬'5%>‹¶¶¶ñ‚h®„l‘~›ý0Ì÷ý–y± G“fÄšš4Ùàù¬b®mŸÆMcæMÞrü(ÐüHç$g2KËúùîŸ. _Èу¶)ŸíŠv$GLì OY$ÏŽ/3Ê i‰¢^N´s6K³²0¦ì|£-±ãÄ a¬¥ ö¤ë,Á½ýä“O¼‚6u"É%yõå ­Ò3æ5-ID¸$ޝÎjˆy'ì‹,C´_Ñq2/nnnÈt¸×5·9¯®ç ôÂUu0êD•*‰x¢ÓQ—Ä06Q5]W2éósܬ¦mçqsÜ&Œ¼žz$bÃ¥¥¥ žÜx<Þßßg•ŒŒîïïá[r8IÐ,ëv]ũښUí›››ûû{^OcMß÷ëëëRpw¹A²¿RÊåååòòòîî®(/îûžÔ¯®ë³³3°ž’Ê÷ëëkóµËËK2A5FRË n¾»G-3ÙxÁM±Çزëëët_cìªD¤Ê1¯`?•»u½*)œ`͵†ží>HUF^MÒ> ½Eßܺ#…&Í(‘©¢'—ÛÔU'´þÁ¨  £!1ûÿ§!(‰QÌÂæ-[œ’¤ÓêùÙEMЀXR½þ0?ã£$NoIêLVÛêÐ'Â}àöö'?ù‰‘”µ9Ãö«È‹W3›ÍnnnLò9Zòè¼Oê>|(kéPœþ,Á]òr¢*Æiˆ˜3Áñ0Èe{Õ ºN¬£šfJŸ½ ¥ÄJ9*®’¶Ú칤:aŸe›ú¶Ö×׿ùÍoîïïÚÚbc3@—êåF{ Y„¬ô ¼ÉPÌôN28B$ pÍ=X&¬w %°…¼>š¢Ý777P½Ö××Ù 0˜oìp>îÅÅ— %•([ž /:ÀNq…å°³ëëëÜ…¥XûìÔüaAªÔ7„¦EüLó}w~•È´"âCj1郌:$ú¸éáZêð¦V™û$Ì‚9v¤37>¤>¾*Q,šç˜È¯6‚¼bgO™—šrY„<)9}æÉúùÔ·iDž9xÆŽÜç}ôZh•ŒÄpÊ|Ç›‹Væ©ín楥¥öÇ?þqŸ¶3D—LÙ(h}y#ÇÃH{µ‹€•ì»rµX5Ã+Öžú¾§ F’‚ôJ×uš*ò;ìÖß.Ð!ˆi†6 ìmےІ[¹?`œ÷iêÇùù9€÷íííýý=ÂU„6”É...Ö××wvvªª&·£ȉ¢ ÎP!s;rØ Ü7[×õåå%¥ G90†ˆ›ýFH8KÚgÖC¹;¢¶íím(W“ÉDPi-AÏ:@e?-gf º¨2ÏWðPÂç `•h™ü3«M5©3Nc¤ÓjÓ$Ž!±óŸ&b ’fžÛ5—ÒÚдÐÐðKóÐ ï4Iù3ƒ³&˜F!sc±ì r’ؤֿl°\Ü—pT©t®-¦,Ó~òÉ'„xi-‚é¥O¥ 8û¹€<­FÍbò H ÄóÃaêÆs+ÉôŠ&ª­]hNg [„8Àš`‰‘ADCÒd°G¤÷@]XO"&¿Z›ëñö~õc^‰Ï»¤ö޼Ö&#>3#p0霞œœ¼yóƤOýU ¨6¾ˆz™ë¥&ÈãËi…;RøHëööVC‰•„ÛI¦¦­ÜÜÜì¢;š{ÌÊ›7oJ)›››øÉ››,×ñññÅÅ%BˆLa"å-×××GGGUUAÅb•€ç¬ªáÕ'Iö¢Q$ÔÛ³P:ç¡ _:ÌâP¥ªZŸÆ€ç»¤RzIÜÈ*Øáü—C têD|’°ÚàÁk1¹A¯A†¯¤ºPù±”µ2uMÒ´õiw¶ M’¬Ñ ÿÛÍp{¦¤™"¸áuáu"ÁÑ"æ7¦eˆiÃM KBº‡è ^\\lô£e¨§”˾Y,@—Â&`‹‹/Är8»¤ÓHÞ&fy“ô¤ó“"Ó¤ A~ðàv~˜BŸÄ!jä—›aŒîîî Hmü¶‘ MºÌ^¤™¹ÑøZ ‡¨ÚZä®www¿ñoTUuvv6DCå0 jì@¿Tß½JcD5¸n÷:Êu”œ\Íùgi}}Ï'0¡õP**z¥¤©Ž0Ä———lJÀEA¯ À·!o_×5UE S¦ƒ‚©]\\ô}O¿4÷ÏKèó]BjJÙì4žãÒÒ’5†„oŸ²Þg‘ý¼%o#_#ës>]>tµÌ†3ÆÊc¹òêÿÕ1cXø¥KÃGšÄÎñ’´9ó„wI ÆpO‹V§ŸT%M4‘ŠŒi¹LŠM؇È!ž¶Ì·ûi%õ‡7¡Óï/sžØ¤nêl…|ÛO>ù$‡&ÄM±Ð}jM”+„c™Æ4yn†AwŽŸæÆ›ÄèTIeM!”¼W\¾2ÏêÌý–]’›03}g£±H9ÝÐͼxƒ–ƺD×X•ÈzÔ’Th†Ô.ë#YYYùÚ×¾¶¿¿ÿ«_ýêèèhcQЦ¼ÍÍͺ®¯¯¯)ò‚Oœœ ò‡cx<»ûIÁã9Ÿpè-ð8®¯¯acBÖQ,³zöö.FÆã1„ >\hÜØ¹Kº}ôEZùk'‡fn°QšÊÃu”¯Î©JTÿ^GùÌìC{¯Iý(um’®S†ròÖêAßV»Ìiúi’t„îÜž>A†fW»;gš9ŸÊß.N’ù7u"ý”` TV©éUcä\ÕYÒ}/óuvi´^?.N3ßîâMå CkèžoÓ|ƒY`‘ ë]Ò_jüãuiÆŸü!º“êè T„ïAR‚è¨up Œ#ºPgwi2Ù*ß*Èîœë;æ>|ƒtFÒÞºžöÈÖ}\%2aÓ4-üÍ´>@â,ä©¢¬\5Ô‚—¢¶UØ8KjËYSŒrIý˜w(Ÿiznm§ É&Á7s“ø%듨ƒÑî,ä9M„ëTÓÌt¶ëœÙ§MÒ~ÈÑ‹3Ú?þx”flxö2:“4žŸ³N t©Ð&Ò¶-Šn¥(<¬CñLP‡TàÏÁ…¡Jà$cã!QÝpVš<å &IÇxŠÂºÁ ‚–$~fbÈÎ E”bÅØ2âPE=È„ôæææàà"8,PáÕl^Å =Õ¹ÐÉ£¬FŠ W§¢’«J×q¤yî,¬Ÿ”ãV~s°x‘µµµûûû““n ÐÕÕU²9RH.Op[7!_KÌ…i&|k‚#ZR›¤5eÌ8Ñ4æÂaÓÅõ…!jÀAÃ}Ö¡M–jÑØa¾5ZèǤoHê=î.]‹‰Ç£{îB€!'q]Œnö[œ†ý „/©¢çÖ-Ñ6©+uÀpú‡¦ÈÍ;äd°†Àž0óI¬Á’‰F•ÏUq2µÙæðìÝÜUÄæ¯¡™át“Ц†Tø|©Ãe¾Œ­•©RÍö–A,ûQ§Éd‚hç[¤0õ&Õ1‰æú`à õÑPªDDIˆ¹EÎ3Ú,‚L:@=¸UŒS«ëÚýæææøøŠ9ﺻ»ãÑàý` lnnRž£·¦”r~~ê´¹¹ÉÓá|uu;Ô_ˆÑ<ÈWYÁ «øS&ôimGpZwHºœp¬îáúúš¨çªËÉÙ{ÛXFë/cf–äôÜÆþ¦Ù÷ 1 Gà{»$°eF™ëNž [UØ}j+‰xeA9×Ù3Šd×G›Š54ÐÔ¤JÅh—¥ bZŸ$òë5)yŸgK§é0ëÊ’±yaaÞÎjnÌ•ˆÉ"ïªJd+ƒjÕÙ)ré(°;Ù/åPˆo°D²Ò–1W_0Ë’„ŽC’ízÎÕ‡`åU1±.× |`:¥œ–û`4ö%)fäñ_:ÞŒ‰ŽF£>ø&QÎ|PÉ|­H°t`Þu4WÛôc|š½=ù¦ ºžùßøs¦lÉšAlm!Mó¿4TÓsÃ. -‚šét ? ZiUU———ççç´@ommUU…uîbz3C ˜(Á"ЗÃgÁiÀìBâÅZ×7w|µ¬–ÓºœR±&|peYÒtµ²&­¯ö&ÏTQ0-Bí„l?)HfI£4$Ü ± ¼ »A–§T‹&©Žš ˆ‡9ãÐÊԩ殬HXpó/õß2„2ª«pµ›ÔáÔ¤²fUÑ!ÉŸäJb>Y™P%¢™À–´•å½­ vIf7c9u7âÈ5A€ƒ>ô=pïNURÉ  fZH_%HL¹³¶¶æñ3=Éð“ÉhËñlþ4p%f½F#œ¼'¸¸‘P§¹$WOšÄÉzðÔ§19Îk<WUE_£PǸ‡µg®Al…`gH¬b£?6‘XáúúúÝÝdKÏíúú:du+b¬ñ‚y {ÑyÇÓ!ßD£† &5ªªÎÏϱ§ëëëUUžž^__SC”ÔNøÆP/¾íE·†#0¬XUB¶&xÿ¢0.ˆj_d„x|‘Ib•8º¼žÔ•›VІ‡×‡âB]5÷hp…³ùÎ8:×PE¥¬Ÿ8”‰j!=&b7GO8‹ ºžyÏ…u0UÞê`Õûäºg•Š˜Ö2§¡4l‚µ <©ZsÜ9W3ªT©Řá:•ŒªT3i§Ù4MûÓŸþ4Û°pýƒµ5ž+3¨¶‡¾O#Q½PލL"'¶¤p¹ã 1rV†ŠWe í¢Ë¦µ Y‚Þ¤ÙBZU¢r ÁÕ*IM¡ º‹`x,LXå„óËÇ=:::’uiNºcÓYº¶m¹)‚uÔ†½_Α ©(k…‰”?Ù4 êÃ0ÓÇÇïÇãñÍÍ #~zzzww79‡¼luuõîîn2™€1~œœ6’»! J9Rk†ËËKò>¢§j¾ˆ†AV@߈úqymhh‰Ø'X:²*ž£E7/E]‡€ýúú:·™³!c+½f•DÍÙÏ’ZºP°‘Ê›K±ÊŒSwÁ$€á¥ŠQ ‰»Ó%õz/»MBµ‰Cê™%tpëjzš ¡ÖQ®éÓ„”l\üdŸ³+†¶5«ñdŠVF]Úù¢cSû*:Üüìùö'?ùɃr˜ÏL°-,…T“s æš A˜¶&’ãÉ:É›±³±)Ê*TIç óÛëÄ î’2ôBŒí2kÒ„"Y—MÒt6¥¯Óøòë=r#‘æ_ãØ‡üËw¾óåååÏ?ÿÜIÈ‚Vµæò¨Î”$óªXJ ¾¦iP,àTCÔ¤e¨uÁN†À‡IX„U*¥Óa Æãñ0 è²cª®¯¯ÏÏÏ·¶¶à7œžžÞÞÞ®­­QbhˆVNNNK———wvv8ó“ÉÄ{TE÷(;¸ þ·À4 §ÛSj¬ª ã•ó3>7’ Õ,FòÆj¼8™ÌŽžÅ, Ñ4û.†ho¢¥ÙýÖ$9쌖d„ ë,«³¯C¯®V¶i(Žs.¼k1,C *FpMÔpÑrøYâÇ–É!z1›q7ZªÛ@³«ëÒ`m7×GBŽiaÆžº=—M!ƒ^1ÜRIb­slúh4êTÑŒU \¯Sso >+K Ty/Ùô–•`~uiæX›ÔÙ»$pPÃ5¹ÓÙ99ñêAn\E?„|K2W—f¨yüª(EêcJ óL'3’W' é:)Qd”‘í¨¬eãÉÔ´ÍzFØ+e]< ÖÖ9VsÌ÷ò¿J}¯9H’&œ½ûû{V^°I+Ì_,ê[%Ñ®¡{%PÅŽé“`£ŒVLÕÉÉ ´R˜SZCrUîˆçuqqµ pünkk‹lK„e2™ÜÝÝA¼¼½½…;¶»»«ÀžÜ›“½bC7"Æ+׈ƒl…±éÉ€·ÑŠEgÍÝ…˜T>“~ A}.l<ïìììïïïîî>~üxoo6oñµ6uÿ5IŠºªª››ù÷„HîŠbU0°šÐEá «çÕ?³Ÿ~^bE¿;¤N½&±ØEJ´4s Z5ÁiƒY¥1w%&h¢Ø•¡’LÍ©ƒ8Z¢)?…Cåuª+‰ÀÕ¤*á,Àyʸ!õE71ܬ3ß6µÇ)r¨I3¿äÎ*Íách‚+`ŒZ¥B€ŸÃ7^__onnâÍØ%¦6Mß8 …lWs–¤Aq)f¢ õ¼«Ô`]6WI¤°º xÒMš¼h¢Y´àÒ©l ÈÌô/¿üòüü\L±bšP«ë`Y€DÀb¨Á}—ËËË›3Ìê …ÎÏÏG£M3ˆÃ¬­­ùÕÂØTSº¿¿ß4Íñññåå%º›z}} ƒÓÀßI0ŽŽ677××××ÖÖJ) ú˜{¿s †‰ð0׉xšÜ`)…Љ“FÝ$>Z‰ª´ô+‹¿dµ<2Vo ;uô]òÔræD×uÿóþO¬•Ì –”4j ¤Ûî:X²ì7{ø ‘Ü3Úb®šî»¡™(„;3ãkM4™ø±æ=ì ÛümHÜMcÊT›‡ëhBq«ç;LrŽœY æËù\ûáRg› (“ÎB[%k–š-V1B£fÆÝ4Í[íPŸMÝmF4CRÛÒJ,4u"1D¯£Œ¤|îl¬Ô°ùLÉMÀ›=™9?7”5œÖꬪÄc}7í÷QyãM•Êcpf\ÆJM*5Ö:¢¦ivwwÛ¶}ùò%È yŸzôå×T!ê ¨ÿÀÆ]\\lnnÂÆ¼¾¾¦Ó˜ÐO>É…?b®>Taù%Ï"ÆôÍÐýãtRVo<1qþM¾ÐG‡Ôw||L•ô°m[ˆìš ¢ºÿ4–T7¾¾¾–wgÆÔ…„k•˜øìNáÆÌŠô]ÆP6©ä²«x––¾VI­-矈ƒt“4i¸ ™êååeUnœe_'©e)<†ÒšªTx’„}vv&<7M&›¦!âhC%Š S®®Óô yOVÇô¢uе۶L&vÕ\^^Î’Î*wD} $žN[ 6a™FMÕÂÂÂõõ5¨D*ðþ®ë­ØR̉À-Ä”ÝÛÛ[ çläJ€ˆ5xçççT*VWWyîè”’6ŠaC=ÅÈÒuH½R–ƒ[®Iœ†’X?‰6$ÒOOOŽŽ›äY›ï[Yò TóCäµ ¸e~J Yp>íÖìºÔ];¤žm„ÿ[EQ’¸ aØ>d2³¨¯wmÅ §ZöŒ^å¼DdÊ›u•ª¤`=J]ÃlU2 nµªIUÅŒÐ[îû¾ýéO:$½½aöó-׆µâVì$«*_š Ã­X‚¹+ÔÃcÊ4CR­1·ò7¶>"HïCmBCR˜ü=óJm¥Ùœx–›/' „QüMhì• ìÐR#ç×iÂB“T!óЧ^ 6Áââ"-¸uð!‡aÀ:XR±.ŽuÈpU1ëÜ| SEt†{ç÷UUíìì,--œœ8Âkño %Œ 2mÛnnn"Ôw||<™LžÌuFï´Á2£¯°”r¯7b‡ü¯ãÆÀ쬎±DÔ=666˜ýÅRˆÂ2¡ÏQÏ“­³ë(î}õêGÏŽªçõXf1$U˜ÆÍ9K£ýxî„–öâÙ«-ÖÔAE¶Vð›#šæo‰¯oÍÇjˆI9ì.…‹*©èBq[KÄÁ4¨2Ë!’åæ’~\@•ضæJ:{›]g¤åÀy@ høÃ¶‰YÞaÍšæX,7ªâä +–¦·icÜ)»MøÉb‡Ö´z„·"“L&„f"ñd—ø<±p\¤v)uv¡‚L­­­aÊM‹Jb?ꨇyM¥œæ?8–—«««ÓÓS¬¡ri¾ËHÍfC¢@{6lè±2T\ó&“×MŒV†¤]W'—ºOB¾uššÞ‡–¯§€¼‡/Å„Òjõ´È}³7ÕÍE€’Ô&Œ@…ê5å³4h]útÔx¼wMžÇ™O«ªÊGp~~Þþå_þ¥ÏÏ•{ÖŽ>0´C¨Á þì[û7„ãN|† O ¸é™VÐ…’ò¢±§6„®KÒŸê’¸DαëTp}€dUÑŽ#!He­Ç0•hàFXï—ƒ£!ÙȰ¸H¢Ï•[œóFX¤&Œý4~”"DCR¿-5N±x-N4÷ÛÛ[Ž4U>&]ÍÆŠ•ßÛ¦¦툉§thúåMÓh§ê4c)ƒM¢tW©ÿF,Õ\oö% ã{³à8¯·”1JCd°Í¿†4Ó¬‰ž!AŒœ›‡ÕóÙ !Ü‘RÀC¢¤j^µSìÀ 2Xžž¶Ÿ~úi†úÛ$6k·&P®H²v³˜«LÌYG E‡Àµê©dl²Mp—Úèh3©£¡· y³!C3s4.oªfCbªf NöÔ MÖJb«“ ú¬Ú˜Šz;u]<è‚l*rC {K.å«¥‰’JÅÆQÑcÓà¨1)L¬Ž"(†_B↠~G¾Ö÷ýææ&÷‹$iÄ"’;L ÙÛÛÛ éÜ&cŸ Š©â‘Þv¡^Å”6ûaœÒÆØ»øææ?‡¹ÇvloocÑH!õö%õT©{4ƒÄš¡C*ÝujÿÔ푱RÆ¥>ø€ëÔ'N²Ž\Ø—DþA”daK ¥ËÛÛl  ui¼)Á&òõÁ¦8Ú)¥® u3ÞŸ™·†<¹fâÒ¤–5±mXn²XRpÓöÜê>;ƒ)‚tƒ, ¢äþþþèèèèèèõë׿é¼y@–×:–ÔYbb¨É¿—°®sLmØÃŸ­¡Ð˜=&íݚ£˜>o_…ïe±H x\9²5ˆó¦ªÔ@ }Ù0§JíQyùêDi•™G‚þ»Ä×TÁitÞêl¾Wt“9£¬ßÂyp@)I"ãêêêææf{{»„KMc`Ü1Æ’ö1vhaaáøø¸”B‡Æ¸5ƒMçPá…ÑNÍ®vÞÕÕ–6<™&cuº˜}ËîÏòUtÂÌÒâ$}ÀauR&—`Ö#ø”y¦¢k¢®m´ø^yVqÇÇÇgggªU©áVÃ'¹Ì ŸÍå, `ê9Û0oš$FDØ5$Á™.ÉyÙ,EIm¼%Q´dÒ‚œ"}qssc²l]'õ÷>õ{| Ä MŒ62ñJ_.ŒU%†g ÑíŒëe-­.É|¿Õ„ ¤»åÄ—/_>{öì-—ý]o SÒ(Uæð;CWDžÜ™¹-õlÖv^XÖ8źØ(T{Øš*ËÆ©w©hòG†(?{_¾Ñ\ JmúÙ$ ±åÀ;oANZc@[z{¶G¡ÞUU:yÊí碧ø,BM(µ¡œIÌ!ïûÞ N(­6¹â06ét³Ò¢LV·ÛT×5MÒ̪ªNNN03p¶f“ôrÙÛb’ÈÄnJj”ËW˜C¼Rx¿¸L!HÀ~‚6)lFfÌ‘›Ðéæ¹ ˆ†¤á5¤Ñ-šé*‘WóÃò`¶1(çò"Å” ...ž?þùçŸ_\\´ü±VS¨rH|“’D'ðùU´1[&ë£OÝjIìþ|6®Õ´¹J­çºýŒysl@X³qÉ•#RM²¡is¨,Rä¨Ê>jcIaøY S$ödf UôIòEw׆»ßXMG–äúcéÈU­p³ÿàI—¬Ù{‘\¶ FÕöö6\ "†Œ€ð Çã1\°BપæÝÙ¨ÁäZmÛ¶ð­hT”kb>K‹Ã€­d›‚D`Ÿ䱯ã1JÒ;=“Æòº„a¾ovHÜÀg^XW ˆ{»¤òqˆ‡Xóóósš.»¤gë­è{ÎKÐJT¨º4ng”Æaä2T›¦B˜…‰‚ ©/¨”m7e?€Üz–ZO#‚QÇLSa“(i­’-לç%“C×ål¯.dÕc“}Àõõõááá³gÏ(¼EÙÛD`m£ƒqHƒ«(@°"’¾†P’S  a0³u2Ö­Üë¼r–t‚4sVXë˜IÕ&fsnXÁšŒæžA Ýgmêðª2­ÃxÕ:±§*Jª¢M¨ æ° |¦ ¿.¬IÓ%Èv«ª‚ͯ‰¢ø|/–»ß¦"‰ °‡a ž@BÊí³Ôlw±m¬{Ö%Fím…8eå€_ì5Msqq[ݬŸ§Éƒ`¶M ^ߊc/±÷ÈçlmmíïïÁA +iÜ@ƹÝýâªÖ='M’%©ßá(TÁדa[ÒôÀ¼åÉa¡¤¨ÂŒcÈ,ƒqY5}Òä+‰Õ&Á[öî¤Ý Y.YŠ¥zxñl0Þë&4lj*åä4I7$¤'N–1cÄÝüpƒ&õ^h¼4¦¹êe>hŠÝ'ÉVc V&;¶ýÝÝÝË—/¿üò˃ƒê-oÕø²¦ª™á7èå†Y§6‹ÇÕÄ(p-î„åLÊJÔw¹¬€=™Êw¡]/¢©É7ÕoÓg+ ‚h™õWÏOæ›àY8ýÏ, `×u S”MkCâ¦Ê°§ÎJ¥Tlò8âÓ:æ¬Ø•Z×5‚âgggmÈ(HbaÑ;¢’EÚB3ÍÊÊ {šé¤Ã0 ݹ±±A>2™Lˆ§0:D@–V†a¥Âöã´Q­á‰0ÆfcVå¦RÚƒaOd §Þ)ÑâÊÊÊ{ï½·¹¹IÈV‡0ˆ‡|Ó‰úÔÖŸCC€ ¨›3æ &'š;¤!O:} Þˆ€ôððÆ?ÏŽïíCTÓ¯Ë1 àƒ8ºšˆUê51²È—šmk›Hù%º—sö ùÆi±‘nnnš¦!*4éɶÔL3¡ÏÎÒU‰6 óÅTp­›ŸÛ4 A'y[³4è £Ì,ãÕÕÕÅŦ ¬v6›µŸ~úiÆä³QÏ©Víæ}ÌæêÿØ_–RÔ æâò¥×óÌ—*}bô‹DœK‘»”Ã"oÛÙz\,Mc+>JHŽ€%sMùRa#+¡]ØvvVƒíèa0+Éú ?‚³.ÌüšȘž.ÆO‘1™Ûrt©:c JçbàÖƒ©¡;ÜÄzÛúðÀçr3»3›Íˆò<'Ä ;Pº0Idp`d&d…UUM&¦‡t]‡~–ê}¦fjfX†³ó¡JÄÝ,ZŸ·»©_Κ [I Ÿ*:·Œ¾« Sc¡á[6óºMÔûkSµQ¹å)=«Q•!B›$7›PòŽšw´r&D`U¥‚~)…ÚÈ0 hUƒ´š r:šD73RëÂ.è’~\çLV‚Z¥™¯]’nÓ œ:DÁF¬üèu®¯¯ÏÎÎ^½zõòåKÐÃÛÛÛöÓO?µ®‘«¾±Ê@2ñÅ|'¤9­’˜rMðÊ : Ió3‡‚mRÑ4ÌÎ43â)!ŸV&ãz¢€F1ŽAÐTX4'áz’6šEɰÌóñÀØè|[°×Š5¡÷8¤ö+t$.$7fdHe=±ï{ä7×××¢2H$Bp˜5Š‘Â¨åY÷P­˜§Ó†„€ù5K8¦ö½¬˜ÝQ˜HÒT-ü3t Ù?Å NOOA©`ÿîïïïïïÓmî“‘Ó* }´Cä}"î¦+­S_t/,2¶JØV%P¡nÝU]“ÇÇÇpÓr©N£Móc(¶˜FsTÁb«£æ˜Áœ„øƒS›ZÛùÉWšÅ*5(ç 2C”›mä¶UêѲÑoÒ¤Õ!zãŒ@½ª— !/Ì÷Á‘Î|åÚ:‘{p¥‡‡‡¿þõ¯ŽŽ¨8-,,|ðÁoq«œ[ÎÒÄ:}8Ç^Á~q)< j¥,\NÖô!Fæ¦]Ú8÷“i‘x6çœ@µu²?ôïæ¡³\ˆq%pµY%ŠGÜ »I¬–\µ…ˆŠåí%-KŸ.½\3V†“Ïå“ê©ð¨ä×@ ×××MÓ0ƦJ_6 &ƒh= }ˆÎMR-Ì fžQ0ª/£Ñλ´(×Qü¾ººRHËPq5~ð‡ðEå©’3ÞÄÏÝÝÝ“'OÞÿ}$%ˆæt0þ¨©P’"¸s§¶ØHyŸV”¨ÆT©¬n}9ÌNŸ~˜¹åØf˜¥‰žUàD •3^±ˆÎJƒ©¬¤j`.¤«Ìß2JopÉ’³f1‹Œ whg«V‰°Ñ)p˜H «ózã¢ò% mòÉ}Rå¿P4,QX¬ç‰c"È̺ºº:>>><<<>>-ª;::j?ùä“Öf̲Ÿw¡e©kÁ®f˜i&b#%m[âÑr×Q*®DÇ›Ui|ôRÿMª°ZUô”ZÍ,³JÀ‡Wó|÷¨hÙbI]%‘B&±]ÄĆã«q_jõŠI!äV‚I$gÆj!œ­Ãn£@ÆC¡u™,<‹ På-ИRÇ<GE`z@—<Š@=x%Å£c#Sü[Ó4àÜ ,S¼w)eccƒþtÜ///MQ›¦ùÊW¾òèÑ#såã:¤>'þ>ÅI‘9ûȵscpm„Ÿ¦ÃÇ_Š©ÍB§ŽÞ:Q!7y“šxÚ¶%¿¾¹¹yõê•Ç=§]’0«ÍgÕèIf¾læøÀ\š(i¶ ä«dƒÉ|4˜ Ô%1çÛPdÃqÓ !Ræç¸ìÃ<Ó€®Ÿ×ÚÍËÉé62Ä\Rgˆá[‚z}}ýâÅ‹/¿üòÍ›7Ú¯·ùÊøÃœûY,w²ïbíP¤¨L¦3áÅŠ¸©«C«q–k5Áqu²äx¸âD/uR’æÑ“TGÔ}Y¥éB³¹Ô¨½7ä´`ãÞ8%êÙŒl¨Ò3ôð|~\ž‘Z ‡³³32²R ])]tS‚±/!‘‚¤2ôãî¡.³j¸_„1Ô ~ÛPL%ÁYZZ:;;;??ïºn<sNÀkó š……z¡Qãá²iÄßßßSõ£=ðüüüÑ£G»»»[âu’.É[EÈ™Ù<öu·Ñòí¾xΊ"ÁØB¿.&*çÜ 3Ç)‰ aV!€¸ùòåKcvérµû^R¿[•¦À è´Á­£Šš®ÅŸ!éyVQ©4ørïU©(»¢öqÐgWEÛ†›sÍØž¯¹¶)aŸ4àJ’T×+›_»næ}³$e#ÐV%áã 2ò±ÐS^¼xñêÕ+zËEußfëpÙóxΰ‘{jÉUˆ³¡!t”_áæ+!½L`¢/âÆã1‡¿¤n#ŸË4‹éçN'Îϵ ™*ë%uhÓ°3ªÔñ ¨abÑ„¬'iC¼‰s…€œÏ¦JJ@C´Zíöj§1ˆ¥Iºq>“, nw´J677Ùj„ßKKK`?Ôu}qqQ×5Ù"[“ÖJ–Ð/i²m¥OÈ@x&æ•bz8l”11¬_ŠÕ£­o}}̧õòåK61½Á«««_ÿú× ©à»W‰LXÍ·Ê“¶¥æõ%èC´6{o.ŸŒ¾OŠ+î:ž ûʉß׉4¤v¶&žgñc`Ÿðdùú €WÁwq˜pà¼Å¹s6jhŸ/×b’ëáâòˆ–@„¥¹gÃhz( ³¶¼¶Ó[v¡V'}÷’:·«$ý<¤‘ÑÙ=·ImfHR‚mRè¥ú|||üâÅ‹³³3kçÂÂÂ[vèl~–FÆ›«Tkó›¸ëñ¼wkk‹œ. ä‹&5Ñ :;LB¡w¡¤&Ié[Úlæ“gÌe¨ŽyΆµ9•ëÒ@$÷Ÿ[MYÔ¼5‘‚›…´¦™©Jþ–ÿš`ÓHÅuð.Œ¹RÔg7Y!âv{{{ÐÀʼn°t p.//—––¤¼£ƒeÉa#X>O «º®mävÐAnc&Âåå%©Ÿ½ ¨ÄàÏ/..†aØÛÛÛÙÙÙÜÜÇv¥dĽ›Sò.úÞq„:'ž² ærQ$¶„Ÿœº:µX•ÔϹ­ƒõ¦¬¹ôÁVÿbG­®®ŽÇc‘»:Z÷3Ðnßy€ì6úãÌ•2½‹R§)âÏêuó”4›*ç\fÄÖ^œ©±²²²³³S¢Æí`•Ì–X`1Êev-ÜuN¢DXC®0 链»¸Š9 \PÚ†à^xÛ¿ø‹¿È•—l,…º4½†ÈY,†k%°¢D=9ïìšÍàŠë”ú«‡ïÕ¦–IÖEßoŸ¦'ÔIKÏàÃî=¯Ž¾BvOŽ«ÝÑŒ6I£I"˜v¸—UTOf³™Œ»……éÂ%IÄJÃÎÄÐw]ÜS_äþþÙ.sØÙlfA”Ї°gúÂ,/- HpJONN  °õ–˜*Š•ûûû< °[vó4æú‰ÍO§Óày*›oÞ¼¡ÅHTŸ~ø¡²¨™£$kÆ]R ?kH"C ŸÝž•xBE-6ÂêØ}šf¦ûlS_æĉÈÔ1ÑvgggwwörvPiU»gy7C `‘91lÛÞh.wžbj:Z«lœGˆ!Ȳ'''lH¿ Fc›ù6ÞV¡È–סIì¶6wÖ÷×1üÆ]$,îíX~ø§ŒCëò—_~Iß{­Ý’°Ú?þØä³Oúâ:ŸAŽØ…Õ ›ý' £–XO%Ô]R nˆNàä*n]¾6‘ë`o×!D§…Xaí,û$R¼¼¼ÌÚ™N7A–!?ÅtvIÇ~rbmÛbépSÕüèmÊUF<6 mèó°yÙÊÊ Ghaa\ØoÇÐ@Jäë¶¶¶f1×§ªª bÑõBà3›Í6771ă € ³¾¾NåÎH‰áWžì‰3`ñË0‘`TjF£}³$°Èƒ¦£ô XªfCŒÞ3ð¸q0Ú`ö¢ºCT\éÒDeeפ༌bHý»ÿ¬’´“pG•J4î1tå777···‰4ONN 4åJ:U“df ÄD”Û`xµózäÍüàô*¦–("9¶óÓE“1ÍÖU2w&G8è>æâxúÀ8#]’´<)‰ud§GI!U4ÉöÑöÛÌ˲¹ª\ðåååñññgŸ}vzzªÍà]UUíÇœ“Ì>Mʲz’ëÁC¢êVólãYˆÜÇç\%AlOó<Š!†™•î%öIQËØ'M+A¶‰’U¹ Œ–5á%ºX°›Î_csXÐT-›=Mýkaaáää¤Dó6ãÆÛêDUå§h1ù@€C›&ɵ!hÃVëRstJÞ E©ëììlˆÙ–A¥ÛÁKÀ™Ã%(Æö1SZ#‘ ½>ǶmÇã1…pŽ1•ð„†P*tû¾þõ¯øá‡4ШPl¸a”Qs›šMÁtÖX;³Ú@Þצ ™ñUE‘i}••¿ÔkhÞ‘r”°êÇíonnRÇ  ¦DÞ… ½ Ž%š{Ìv)(“Y^Ž8” ‡×àéeôA }`°ØíÐâLYÀàó@&ö!…¨EÔ¬é›=´iDIMHùA ¿j挪,Íס¿xppðå—_¢M$0ÚÎ7!µŸ|òI¾y]D5ˆh?%Ià÷„÷Ät&`4øs fNàsVA}Å’ºsr6güÂ+] ¯ìv²uo‚§K¡'³ ©s¹˜üÒÒ4Íõõ5ŵ®×ÁÙáhÌx‡ž™¥© »\«ÚD/!Ù_)B&Ô*ƒ;ùx¤"Gƒ8yRö"Y}ßC‰âª,Bô‡š ‡0'« ®®®’ýG2 Œ}Ö÷ýÎÎÎW¿úÕ÷Þ{®yݯµT½ã,Ía2ÁÒu&X›¥™•8_æíBЮN*NÒ‚Ú47S ¬I=qÕ|;HÆFÌ ­Im[[[cš¡F0Çqšé Õ©ç&c”£$ˆ, ݧÉ.ªF$Ö,‡¸UÍq"t˜.U¨ãb ú˜‘¥˜‹6JÓ±´Ù”Ô>nšæÉ“'tü9'ݵ¢ãºO,M—Ñž{ôK°~úÀ1Ù!º$`i‚¾KŽl¤fg6ЦöO7†1”Àp“HÙTùš:•eª˜B‰ƒzV®NA+Š‚™…è[zU]j£«ßÊ8%_aóPG1ˆ[3”³lJ´€Œ`U%1û(õ}Oð^Å`Á5c…l¹Jjð7CP»ëDLb4¡qI›ša `Ùù“ÉäÕ«W-è{ÞEñ~c­\ÚèæÍuIC5ü,aK²¡÷!È/}ti©‚ÂÚlÌ5ÞÉÊ:µ¡òJ@iCh÷øÊ:Á~îÝ:PÕü lÂ0×?Èç|’\p†…]´ã†i¦:ÚÙ!èiM赩ÕK­t°$Î9¿±­¶€^X ÔïJ)Hmlnn:Ʊö••s7-‡{÷¡Ë÷ª~Edw{{{~~NŒ<›Í8œd;;;ÀdCjµe}X(+1­¢SW릯{Ð\ƒ'^¢Ý yœìÿuàž|ƒ”*‘œ™*õú÷1%³NuLBU32M"Ð7oÞœžžöÁ³ó2ªD"+1ÉÍòˆ»´M­‚ØõÏa^wW¯/A¡Ä p¸ Ø2‡§ùÊzžbéaä^ºèÓj®öA^÷³ñÊŸ1fΨ„)å?œœ|ñ҇‡ 1—`CêsV·¾¾ÞþèG?R¿çÍH'G.ðAÈ{)‡‘†ÜÇ„Aç(Éï·Ák“2x<'Ή'YÐQŒ¶ Å?Ð*CŸ„ú¤×œÏ@•ù½ÑY-TAÛÛÙÙUÄQ1lÖ¡y rüªhe3¹­©‹±“Ì˺P¼$Ï‚ØÁó–Ú‡ q ½8(Á‡T´“ů£_¤ QÓ¥¥¥•••ëëkÈŸä¶â,œ·aP¢}¯ë:F4;Âëàà`4Çãëëëããc˜Y;;;?¦í9»SMašu+½:è{–hr8L `ÆÊŸM°=Ø£ÐÒ唚‰ i¤•ç*WN,´åXIè@Ìä± •Ç!ñžkÄÈ_ ä%QK\—lš À— FˆCk%û4LKW¥)’™‹àåUÁvA/êÓ Ñ Ó^.•‹_XXØßß_ZZzýúõ}š96™LªVƺ»Ÿ$­p*,§6IgR2 O½ª*N;`6¢×IEé­m[‡ æë€ZÅðžiŒâ«iýÖg(Û„ãbìvš…8Ê™¤þ¸¶¶¶¿¿Oi¬íp¥Ú>ÆXé#ýôä7ÁN6*1©Á:=[‚MLª’{h°&m×ÍR9r}4™íV‰(äfÐ%kÜØ|¬jeÙœék«Ô÷Ë:“Ô ¡$–ܤöØ…A¦”¡¢Uš!© ØÖãN6tuÏ^d Ož0@;ѽjb 4äeT¸Ÿ…ö³­,AþšÅtQÛsÎZ=àÖL&“ƒƒƒçϟˈöÅn$opaa¡ýôÓOsxLY-7”Ÿ—`÷{Â%.(ú5D7CÍÉrl5Ãì…˜¯U…RõBB…óo¢7eHŒ5ᛯD¯OŽÞóÆÕç7©¡G³È³ì“FÇãÇ¿ýíoŸžžN&h–D­J.’¯Š“s9´Ç}B¬>…6)÷ -CJE™€ `c(q¾…oWc‡P[–c*zÃ0NÚ-0 3kŽžCBKv!ÃÆÆÆoýÖoÑÀÌýBñç †S§Ž Q­uXzu'¬ŒÄ4R`áykU0cE…õpõü@Lw²X‰p!›+gå¾tó yÝüÐS¾…gáðž×¯_Ó]`¾iôÄCwo·I¦FÛT’ÜhIPCÑ Ÿ‰Šš•è}aö-ÞBn„Ö3§ÃÞ²@sÆÈ ”êù.Ë ")"œ’#¡œ "*{zzúúõë/^<°þuÛâM“æúé§RC Øèl)Wc.³‰*4nØ@%5+ŽªÕD¥_(8…°ÓxJsn|¤#e—˯u;ò›!ɘ5Áv³¤Ò‡$«3‰K3ðÕÕÕï|ç;ëëë¿úÕ¯ Øª}!Vƒ©I –Mªï–ù¦h.g@ìLNqÐCv+°¶¶è؇¤ —‡ §],}Œ¼¦vÉ ¼œ ŠSºàŠ)÷1!áéé)WõVa6B³¯ýëOž[¥Æ 9víƒ>xÿý÷ß¼yÃlQðõ>éf4`òíS8g†oç‚. Ú¸á666T`»Sqƒ9™vN½в=^uÀRÊ£G …œE“ ÅlØaÎÏϪbdß÷ä2ú¡*ºU766>üðÃGa\0³˜ gƒŽÀ*WÛFëb“ú™°¡TôÄ +–`r±>æG³4Ù¤#'<‘L%½¾¾†Ö$šÏø\CÐ}g>ZÙB‰%åB¹Í:£`vóüùó¾ï···3ÃŽ7RCl’L{Tõ:ÑhÞõÄžÊ>4d ýDØŸ²,dpy¬\I£>¸ø]ˆLu!ÊÜÎwÉdŒE0r‘3®åòϺ®OOOÏÎÎ>ÿüó7oÞ­f3³ahnnüã”ÄrÒ{ô1pxH#¹ÚÔ¡!7àšÍfôÄ‚)ÖQ’«ƒ9ù€8W3oý•A»>ŠÛôÐ]+¢©Ár›¶mKÊhãE Q ŒÍÍÍï}ï{‹‹‹ggg§§§'''„9¨¸çsª‰(áôZM­YŸ¼!†aPÞ@ ³³……­Ü|JºÐ`„œ‰ÝA1†6ãËËKx牒JèFiÈ...°kä\ô¥#ߌ®ÐÆÆÆ{ï½'‚KõbØ’61d„iübS©&è<º£­èOåŒ#³Xíõ3Eš¤€P¢æ¨ýªRéÖ!ƒVm’²Ô WAgeŸŒÒ|¦ìJH¿iXKtØÐû¦Þލ«{I[ÐÑ¡M=ü²€eÜ6m"'7¡RÀ'ÏB?VJrÍU¼&1«¤¤ÞF÷x£ *Äu°2M•Ú$ÎÇCÌgSÇ »j2™~ùå—°X Jˆ1~Up™§ù›>Ao£„ÆK¸NþݨŠ%•B lŸ -Ä ¤íiÂôl³èb¯BzI¢Jµ˜¼p_KÔ« G>@ îf¡9ùÑ´Õ»iš÷ßÿéÓ§u]O&“çÏŸÓ“ˆ2ðÒÒ]8òŒ„•Ác‡É±2°W7’{äHs”`ˆwš`6‹ÑÈb]ȃ.k´Öíã—§§§ëëë;;;UÐMø|âA[ðx°*Àx*žHkqØVVV¾ò•¯|å+_q;rýäY| ¾´IãËE1$‹fëPJöÍ*-Ätœ2cΚù³ìÛ›¤‹«¨ƒíküÉ!^®¸›ý —T ÏšŸ£4Ô-¤µâÖì¡áY¼yóæððà%³Ï1U„–nW¡¨’ºD†¤2ì• ©o±J½JF1̺ºq­\³è~î!ó¤pšÄËó׉*yxuu•ÍzЇNN †?žSöØÑÑѯ~õ+Ìh“/˜¯ä `·¼¼üV1Æl¹Dƒ¢˜Ž`û4—œŽŸY m®BY4š‹–e«á̱bn†Òr‰Y ¡vÔ¤ž’,¹Y‘)CE+²-ÑG¡Š¥¥¥o|ã=‚šLmuyyÙ™TÜxÒÚº& ®œdE9L3% Ú«Ñ9 FË~1¸ì˜!O©"ϘjfC¸ì¤fãñøææ†ú@J•¤Šš¾ï ² ë30y’ÐÃ0looõ«_ÝÛÛ5 ,·Âö!J×…v +O+¢ý±<_šŸ‰émTÎhgÎ<È€f »„lÅKt¥”¨T–yus£é&8½j]e¢¹/B_¼™g½W©–b:âßa3ŒF££££ããcj,%š±1U¶C¹ÿùv¢T«Ÿñû4'AèJ3Áaä7j±Q™q¹Øù†ÿoq%ÛÔ£§vÌž¯~õ«ûûû»»»Hì?yòdooAß™5Í/ ¥9˜×××'''¿úÕ¯}^2ì8t!fÙxÖªªÚŸüä'Ub÷4©‘§JÔG/—]Efч"ëGÔ&î-Óµ5(XÍ_•Ķ]¸ªØU"æÕIô+ו…ÏJjžŸ’4,ÞTB¨KJtöþûïÿû߯ëúìììÙ³gе‡˜×Ô¦â8:Zøv[äÌ‚ Q!1TÑ@£«ç `tà+ìôÑÌeÂ5 ŠÆ€¦$w$P4dÝÇ< ²-˜MÓ Û€u–ÝŽ!#ŽƒNE¡ðêê ”ê£>Çëëë:.X(]3DÕI3abËö£Èض­£n2­ÆŠ?F=>hcŸœ•˜à{˜U)©£ƒJÊ(/`õª !çʉU…úÅ$¯ªI,Í’ÈzêÅ%\]]}öÙgì:xüo•²QHŲ=à"dõ1À•¯clÌ,”'úèñâCÈFgI_¿›Tî1g*sGû4×Ê8taaáÃ?üÆ7¾ñÍo~Ó‘Ú[[[4ÌÓW@P×õ£G=zôþûﯭ­¡ÈF9ûðððÍ›7Ïž=³ÁKWGN†ï´Eìž­^UUûƒü $-ê*µãåcªþÓ’VIšâ¶ã˜T ]×ÁÓå óœ¸hãa&qÙ!uu6iô6½ø% ó~ª šm°ì« L Ññ‡í_]]ý'ÿäŸìííÑ prr‚ö&Ûšof2;®“þ¬áa›úÔð-Øêh…Û|ݶ-úè}ðï9ç˜;NK°–f¡)9 ¨rccK§<±9¿_*!ƒ´Ž…L&ÆDÛÛÛ{{{ï¿ÿ>!›,  t^ÏJŸ…ž=Ö¼K3Ð9T°Õl¬eœW®Ò©MЇ’ã£>žDÁªDPâ7ÄìuÌpìç‹Pôg}øÊéÏe¬.eú…¥á#÷ÌXÔÌ“~ñŧ§§]/ú‰…ª’¤EÃ*©AXÃ…ª§›M`»ö“n|‹ÏÃr*]ßxj– %ÖÏb|'ÁþÒÒÒãÇÿàþàûßÿþ£GØ®à˜CšÙ.À½¶¶FT….—MîÿÅ_¼|ù’Kª“báöËVä·°O›såBƒNƒ›‘ÁhÄH}]ï¤Z Æâââ‚”A°*#™ÆÐfp.®Þϱ"3 …?6®¯ éní4÷,Øß$¯Ñð™¥r«««þ•9õêW2éu6d©ˆÓáÙȤ,±³cØ”ZÔûå71‘A£Æ»JÖÀe (ÐMÇ1H¢ Ö(ÖŠ©ÙpœžžVÜßß?~ü˜o÷“¤ìîî¢JJèVÌ(Ä0y²@idÇÐ ™¸£ÀHQN%cÅ… *ÁýÊ·n’8õ ¦þÔÁŠ$s”ãî¦*‰×š)#ÊËø2VOÈ&§n~.ƒñ̇0š«bªh"Ù¤ÂÛ®?9p•ñKm}j27ªòŽjªÄ­¢V ™‘⯧‰î?¦pÃS©SœÃÒ†¬Î¸¹gè,_ûÚ×þÅ¿ø?-•“ÌÙÁÏQ7ﺎöUŒ _ .±¸¸ø«_ýêøøøôôÔ`—IäEŒ¦Š7G[gÀ§µ?øÁ†f!"lV?$RRŠ1br¶wI2Ä…ñ##1ûÑAýjÎü›àòõi¢ê0Oüцq{³sâ2é·yº(´Ô‰´–o3ñÍo~ó«_ý*tÓÓÓ/¾øâââ–ó#º4€ž¼ÌØ-ëpm¼WJÑ,•9?Óé¹t2SÞÈsbßX ˱-†ÉˆÀëÁŽp§ÄAfdÀ'''§§§¥,2cµµµ§OŸ>zôˆù€ÙååeŒL1ŽþÀþârX‡›››óósÚæQË謚/C7!€ë!ôXŠ"™Ñ ¹|r®îó›išZšéuô{IDÈa~´€äf„DL'ïÌ ðsm777_|ñ«g×=Ä÷&ÉZ•2gô– ïöÌ×!3‹ûÉÍ7³ÙŒ‚†È Ç\»¯8¥Ùh4"ÝûÃ?üÃÿïÿûÿ>üðC‚,ªØ:2ТoòÁ.„äëൂÜÜÜüŸÿóHV¤Pxº©¼ÏB(fó\ëh&oš¦³dÃahcÈJ™oRÕÍBroHND 1 /hàÝM4s-ÄŒV-ùÍúó&Í´RÆq"FëÒ°†’†ÊÕÑíÌÐÐäÒÁ4ÍžX__ÿÊW¾‚ú g•F¼!†YØ)MØ…ýeXis´›h¨6Jgà ­ÈL$Qb³J‡L BW…6.ÏFeC¢´`t0¾¬FöíäÚ”Û¶ÝÝÝíbø³Kmö÷Þ{ïå)/šŠ‰%”]OOOqE°Uú¤5Ä™ý€0ó‡ÿŸÍfäæžp²!€QÅ\g©βä¬ÅŸQh¢ÂŒµ+·Þ’Q¢%™þ"çÓ_‚Û ,Ô©Ðlf*fÚ¤± ‹‹‹ï½÷ó ,þò¥n‘{ïWKçFmç¥ïšÄ‚nbÜ·‡T‚Ëòò2fÚJ²â¼ 'ÙF¯¯¯//,,ìîîþ«õ¯þðÿðÑ£GÜ‹¹•eb¢ååeQ3ÒíÑ"Z[[[Ïž=ÓãäøSOÏaå袭˜° ËŽE§*Ѥ>)AÐwS÷*j¨ÖVð·ÚïŒ/Ô!ÀîÏy²-‘e~Ø‘!XIíA|&N²K=÷¹ J¸Ä5ÙqÏIùeûÖu½½½ýäÉ,ÝÉÉ ‘‘MóÊQiV¸}ØFüÝŠË8??_[[#'¢n8N·¶¶HÌ ž÷Ñå+‰ ca‘Öç”™f!ÁJ‚|qqaÌE€ƒäÞ,D¾Ù”£ÐÒæ©­¯¯+ï—»¦onnÄkYCr7ZU9áôT²ó†aÀ#È5ÄÉ&Hs¹ T§d}}ÝI%ÊEÙ4Cæ«DÏÅ·¢âØT©‘lÍhºña^n$¡.‰ÁòTA£µ¼£'ØÛÛûú׿Îh¼:æ_@×xÉT७*-'ðšÍS>ufÑ4üÁL »$§Ví öfvõd2ºñÕ¯~õßü›ó;¿ó;dv\^v*·=ª†¨ñâ]|ÝæææÓ§Oÿáþ¡ŠŽq.˜MåÇ,²˜‚æßšV”4¹š¢/~rii‰*©Ö¹‹& [|—€IDATµ*†Ç±V|)n–gœ"|æžÔSHÀ¾®kí”± þSºÖÖÖ¥@BwŒãÒÒÒ“'O>úè#’Sñ#UºÛÅ’ÎbØçÄ£%áoiT¢«‘wQ¡ã¸´ób6ÌæS%QÃs6'@aNä#0å ÙâVúêÄ2oò7f~Ô0?0¹N˜fa9Žk扚Eï¢ ’ÄñññÑÑQƒTYäRb„º™¨Ñ½#ÆAžˆž›3b?³¸•µo³„FP‰=žþîîî¿ü—ÿòOþäO>üðõµ5.o:ÞÞÞN&Ä666¶··ÙÌ4)Q§òWÆà²áÏ~ö³—/_Žbn6xy«T êïmˆö‡?üa†Ûy¹'mˆî_Ó1 ˜«±Âr£–Â<¿ 9j›i²5œ%mò*jv¹I˜XÌß«"Êã3sÚjñÒ€ÌÝü4ð§OŸ~ï{ß+¥L&P#ØY4ic;ºèÁ~àܸqø&UTÍ1a\úáJ g|òäÉÿñÿÉŸü âú¸\Îëׯ?ÿüóRÊÓ§OwwwñFÄVu’Ó&”èi©ç©‘z.x:þò—¿|ýúu q”7B–‘Q…4¶¸»»ûM[ÏwQfVÞ(F\”hXq‡¹Gsù fH}ȳ$³7MÂ2|¸»GÁ Üã—#y9/ÜžnÙÆ`K? n pKu]ïïïC8æ7oÞ¼i’ð.1£%o¿ï{ÌÛZ¦G]¶V©ªª«««ËËËÅÅÅ v GÎù}ôëÁx`[ÀSN§=b†¼JHL(|ŠR¡úÂ>88¨ªêÉ“'ûûûЩ!碮B¬C“Ã亮!Ý0þ—ÇÊZB XOeãKH©°°)jXO>Ö…| 9=…å0‘úè#60•_ã !DÐ<}B<Æ— ó:éìºÝÝÝ* zÎ(Ó¬“C€0 •ÒuÝÛ®f(siWª òÕ©gå>ÆÕñ“§}dþ…Oˆ¤M}¤ºûû ¦ÌR›$’3dùež© ê¡éiB¦]CÉ%}ë[ßzòä  ’³³3娭!ò#íWpSÅMNÙŽà…€AÙØØØØØ¨£(ë ÜÞÞÚ™ À‰\ Lì$-#ÙP:a³zx777dLr,>øàƒÇ£ÈNÇÌêêª:¼˜{Ôfi0´œÌa`(1”rXþÒ'Ý%RÈé¼4×–YN„T6Ù#1 Aaûø@ì/ìê¬)Z'ÄY:·Á>/I§!ÇGÙ%^¹Ϲý ÍF1oÁè’{rrò7ó7‚Ü\%ÿ(Fòðçl6ûÍ2eJ‹)hÆw¬€â]DV8ßòÝ&=I3³EÜ/Ö‘R§çbX !éÆ ‰ú̃Ï{¥¤ÎïÅGp ä5ËËËܼ{…«R2%·•T°ùÎÁ!u4¯[väT¿yóæòòree}•³³3>¤‰5_ §'Štúy†’ ¯Ån`•ˆdAÙ,8*Yó•¯|…n N¸Íî|Èùù9«‡6%¿>f©â¡{Õ4 ÚÕÕU='¦CãT×Ü]… -€x%Ü#ê}úúõk2b² ˈ%º|ºÔ¼’¯§Î›a~.U¦*¨6¼:KcœYÞÇï{ßû£?ú£§OŸ²Kq~···‡‡‡···}ôÑÎÎ{ÏÓ¤A0kiR¿$_Ä¡˜Î´:ˆJVê«D3ÓÄçh ݤN%fÅÂG›¨ý¹&j®XE+9»ÄâˆRù&ç^ ¶¿ "ï(ôÀ„´†hz`-,Ó˜ ùw©G½—";u];e«išÕÕÕ½½½!ÍJ9<<ÜÛÛûâ‹/¸/Q+[7û¢"œ¥)°(yò˜} ðŠà‚"œhþ²¬Ã0 çççAðæ:_Û蜠ž2¶¶¶°p£¸SÌ1Úîî.|+88ãñ؃‡í ·;Ñ$ÑcÑmVVVÆã1[ò(k…] 4¸( 7N¨ˆÑ\çp”ö—––®¯¯ß¼yrÇ:€äXdnÙÙ-óJù¢}häÏB>%›*3kƒ£QŒ)é“´7¹y›Æ×!¢í‰Éò½Mêa^__úôé³gÏ(˜ŠõˆyXªyQfA[²”²€Ñ§ÉŽ 8==…ÉIaÑliié£>úgÿìŸýîïþîÞÞ ^rˆ‹‹ Ô¸ú¾òäÉîî.xbxF@}ª¨ ­ƒ‚S…š“ai.ñ{1ÂÜB:ÆËM d˜†ÕH%a ¥Pnñ>鬸û8gÑÍ×§6ŽËËKÖ%ãS³4ߨ:…8%Èôƒ@‘ë4:¿ocxTFÙKêŒo‚ ;Ä|:]š4ˆÀSÑ___?::"§íš…F À!&)ÈÃ ÐÆ*ƒdËŠÄi 4ÑöÊ*¦{pÞØ²:=zDÖ)Èʶ¶å•§Ì•+ñhÐÉ#ØœL&$ƒürRÛ,úõM جX¾‚šL&ÇÇÇJwŸŸooo›ž“yÑBÄoH™1[š¿>¦Æ ˆ]9^Xœ»Žf`”…Ž î“ù}˜'Ç—¨É5MBQVúrþ˜9îáj¾íÙ¨Çóþûï÷»ßýÙÏ~Fvl5É0ªÞÀ&Ôý½lC<,»çÑÑ&&CL!ÚÙÙùÆ7¾ñ{¿÷{ßþö·‘sBæìâââÕ«W“Éduuu{{{kkkC•Êü|S1>kšœ&#PC$ã#ƒ2Ã(ƒ)SH±#ø_WWWTfÙN ¿)-cªr¥6×J»Pïäeœ7}Km4l>ÒÇ Å±/sÅD“äan¢‘•’p.ßX Å׉üâ? vJò 7–––  ôÑKˆÄ±ªx¥”££#Ñ7+ŽlÀšðr°×ÖÖЙӰšRUQ]fõA(ÑÒnà@ŽÇã¬Àç©Êá7ÛÛÛÞ vȉ:&css±e “Pl“Oœ¡@ïBŒçšL&çççãñxmmÍ|¿NâYt¥‘ f椌õa¡†a@‚O&ð4ýÌÂ[üìììÀЫS…·’Xà¶”®!¨ßÁD‚e©!Ùná\Ó4HHçpLQ#ssœZ4MR…u¡Þv„¾öx<þö·¿½¼¼üË_þ  É* 1á-!cèÀé`y‰‹1(öñ‘ÿ.//#Úƒ¼âw¿ûÝßùß¡.,¦˜Í8[ºÐõ Ú©2? ˆûB’´ ÑZ–9®ÊH^s±0£¸˜:< RNÍo„.‡yjÝy6µ›|6¡ ¤ÇsÕüUÁV‡»Ð®a2Âë!æä†«\¢̈cŸCû~ê(`ã‚l5`4q“fû¾___õêX#Á‘h Ñ þ û£®kÔQD¦Ä2‰¼Hyü¬ á†ã¿êºÞÝÝÅ"cJ¨|a8!¤c¼»w„Iΰ„Èþˆ¡Úh4¢¢ã‡‚†áêê l¢;”6 tÙ)žš \*‰C&‹Šé(ôãõ¬õÐõõõÉdryy { ßFè Ê‹ñÒ.جÛ%ÝaÝR®4©íåâ×1sô>ÄŠ׉žnS›óêêŠD’m@ˆÍÇ–Dñ©BÄÿÍÉXONåh²#ð|ùò%>GböäÑ­R¿¡æÀ(†k“N¤¾ÅÅÅDbœÍ·¾õ­ï~÷»ï½÷ÓÕªèý&[Äuííí1`f!f^B›&"Ï’ütö&iÚäz}®o¹I•LüZ&£e Þ»¹¹É–¶ÔiD«wL…´š y’6ªs`RÊ*/--]\\Œbl瓤 eqÏŒÂCË'Ð,´D™Ã¶éªq2¬IÝ0C{+‰õëÎàeûûû¼åòòr<?þ|QðÌxc%Tbª¨Wr ©ÔN*!þ]G›‘SzOخǑîâý€D.§ÎV“………ÓÓST>=zDHEÈwrsssqqqwwG¨OnÈãà7Lú&–æ~{{Ë_JHåÙ„@㎈›øòòruuummM%#ãwj¦9F¡{vvÆÿŽÇãíííaTàs%åè儈’¨¼\QÛ!I§aQ/SlV‚!n•f£Ùlvzzº²²²½½Í9‘½¬·ä~P̪SÆ4oµŒÒbº®ƒÅ²¿¿ÿ«_ýêàà`%Ï:)O XzkÒ¨`¾WÍ ÃÿíííýýýúOÿ)R-Ô|X¼‘¢Û»»»12BÊê刡JÃè ¢Û$²’ "Ujжò!ÀGÆn¬•Ždó0G£Ñùù9ÜßèU Z»Î‹ð{ïc–ŸèC™ï–4máÈë¹/ózÛn²¾ïé_±6§QI1EÉoë2òt|½j&L-,,<~üœ‚7²eÉ8/..ªDF¦¡ŠU‡4S„Ęo—ŽÈÒÔÉGƒÂ ÈæàäƒBcÜ8ÃM µHßÀG‘ïØÛÛ£#ÇVJÀx2_n[ƒÓ$ÏfÀ©H°Õ@2ꀳèfÇ\Zçâ1œœˆ1±€hrsÚG¡³lµ”r!+ä,¸ÉWë2¼`ÌjAfI•fÕØcЄ֊‡ê>f;ú{ÎÚ°òØn1—:H øË?ù$Ù”Dݬí@€¬åµµµ5µ·lE0tuÛdåñ r“ zÈ ^=zôÁ|ï{ßûàƒÈï¨r¾A¡àÊ··· óe¥ªYƒ˜zžvë7[¬£ç1CòCbA.XzbÏsp¬8‰j©>`¡ÿ75Á.Z¢§i|›ÀáLk `³/Ñ÷×'õ>³¨ÐÔ§%ê$«ùñ¢øšäÙüÈiÌe"m®”Q·ÞD{º{W Æê¯¬¬ J“鈬 Þdé³ï{œ’p*:´È Áºèû~ssÓÞFâ,0~ãj#/ (3à7ß4Ô¦DÊô?«««8¥AM§Sv#pWWWŒt†íuzzzttªwTì³ÄÄ'«uF >2¶ª}ß_\\“ƒ‰Lc®Dí™,ò›7o°SäŒäÚ}ŒÎù’ˆ›ú£Ù§Él¹1ÛX0NÉñ×ÖÖ¶··Ýš‰:䱆$÷ž¹~ež“hJ˜c1+ô³ÖÝuÝÎÎÿ…Özö&DžARNþ÷_ÁL j1ÐØ‡~¸³³cA²åÅÅÅx<ÆR“r>¸õ>÷@•ØjUôQ‹Í• ƒxË<ݧÒb ¥ÛXˆáµ>£ÛÛÛííí7oÞstI’D©„´dËU´wbsu/ãmÉUTšYnÛ8„‡5‹æ¤Š.¸ÕX¬Of=‹Hg3¿d÷sÌxÌMÌb `Y†a899á\‘Â…e˜ƒWæ6” U€”cLá ±KìP9;;“й··g­Ô϶B°˜½Mbà4íºnsss}}‘“ÆÛ”hl>;;SÝ[…>f³Ùáá!ñÊôØh .#ne^èÝ…š+Wtõ“‘ß*ax{£O«$/“‹€y‡ëzúûhZ.égšf2 r±‹>úè#PÈ*È=Bõ9ݾ1µÉAé$õCò…6,ŠƒKèßB<æ  óM3ÙWµ1¤=ß‹±ˆgAg°R¥YD&^}ß+f‡ã4Î×€%vA²½3.ÍËI 6<ûAÖ}û½Î€Á\ȰûlŠ­a!Æ~äüÎýAœb"I~a ^ª}1ê\Ð4¡m[I(ï¿ÿ>]ģѠm<ÿüç?·Â8QSlBD!ƒÇ°ï<œ˜˜DTî!@jÎÎ΀äÙ Æ¡TºFcHÔifæ[ˆ) c?€'8Ì ÊÄÅXc^: Û˜H8óå—_Ó-//3ä¦n½gø;²¿¿? ­ËËËÍÍMNB轔—‚£åºõt:}óæÍÊÊ ©kÒ@žLÕšèI(éƒÆÜÅlIð%5cbÒ‡Ê:ɨ΀4SÑ·Û© ýr«ì÷lR—X“ä̇ÐzÌ(¾§É ’Þ4mnnîìì¼xñ¢Ný@b: h›zÅmß©ªj<ollÒ„º»»»GGG’]­”˜,krÐ…²«ÕçÍÍÍ÷Þ{omm)5<Šà¸[¥YR Õ©ŒÎ<›U´ÜÖó3e|™ˆ°^•t}›¤t: ½9ƒPth-äæë­í;2èoo\{9 íÊl¹ Vë˜ “1©YÒ¯0ÂÂè(œ¹mä2U4Öˆ2pò›¤’£W‡ i9™f‰Á=ÝÆ¸!¨ŒU’Xt[»š¶zòà9½œ+fóY²$aáF¤ µœ¡È1‡a8;;ãˆfý*:Jô»öÑBeÔ)¸Fo31 èFª$Ѳ……… .Ž1<æ ”–ÝÈê±qÑq†•#xˆ>}ëÓÔ1/..¤àB’8¢ƒjatÀC§...(M>bA.…Ù‡kÆG×T¦…ûì4Xmô‘iXE:ú˜‚“ƒ;²Ôƒƒl%a¦~¾N‚Ut~ØvcƒN3߯j<<ô“­Ì`éÔޱˢ뺭­­>úˆ!ïàèIJ‹©È»1gDî9*¬Rý—cÚËæY7î«jÓüÍYƯK øO@‹Iüž“Efš-@z8†2£Ñè­®K•*‘:1ɾ>*è®~c!ñ Fc©Ûˆ· "ò}ã§1QÊ}£`PFúë—0%¿5d5¦#óСý€7C^ŠHŠÊÝòò2ðpUU“É„°… Žº‰ (M4ñ€)+Óétuuuss³Q­*uuÏCY(IRÕ~®YÒ6"m+ŒZ×5Ä«&T%©¯©çqqaˆ-€Ç}ßñÅØBd0’ÈÞ&^ó„LCþP–Vhʤ¹‡bß0 ô9Aöòò¸R.KÄ'x 8`×Eß÷T*eT¨i¨O«€ UUUðT¹r1r_ .â)aY¾N檠X̬|ƶfIzÛ]:K¢zÖˆ…§!‚Š«fÁÛ¶ÝÚÚb&€çÇ/̪r:¨«Ð"CDeœJ]׈‹,--Ñ÷ î—Vóì¥Ù|sx††ÚÔöT’NÔ3Ð^§FÉÌ}ßSÌ)Q"ã¿@Zû$Ü:Ie§á¢- „ȧ=cX÷>f[µó¢´VOÅ’rmŽªB„BØ&›¹mó—*Ia ÁêÄýÏ1ù(M¸ò{³:šø¾»»ûèÑ#ËU‡‡‡¼H§ONN¸eÉ>VÐûPÀ¦8Ç ‚Ì¢‹©®mL<ã _^^ Çä,£Í?!E… …Þ0ˆëëëûûû`ðŠÍ‘±Â8Õ6„åF!eÕ÷ý³gÏÎÎꮃDª‹b–/Á` Ñ¥"MxzŒ(VQR†'†a2™Pcjbò«ÊîÀYH^Œ ½ *ú}4™ºwÁ/Ø{êŽòh”í¢éOÖú[•g).//á—¡[Rƒ± E|Q×!• Ê IäâÕIš]=#Y@ RÛ<üh戣Ù`æ•–¶¸>$®677?øàâw%–ˆM8N¡ÝI¯#Boƒ¯¯%ʱ€Ö¹‰ú{6ú¾>¯vFû4_ÚUõwww¯_¿¶%(;TF.… 64ĹåËËË.‡¾f J„].º8JL="îàÈY¤Ð-<`µŠS‰È·Ävðt3†W’¶lf–yŠ‘¿‘”HÛ¶øvÞÎÍQ€§/©mÛÓÓSâAè‚ÊëÆkÍÙ@¤¨`™|,ò¡Ìe¤?ôôr&©úó ´s$s¬g1Ci{{'YG)iõÃV=ä¢~؈ûû{T———)#ŠdßÇh(²Ü{“9©BTž/‚~EF ”3‚¬ Z¤úY^\=é›TUÐ\©ÌÀ™´Z7Š‘HH®„}huâÔØÊ.–ï•Ö‹X—AdÚÇ`1ºX0sDÐîvË9-IgÑ@Ç – €—ÄçG> fZ_ƒî«ê±Ї‘„ò*¥(ßÌ®cÒ¸ì¹QšÉä>ÑbzX2:^G¿QIídzù&çœÐd¬J½Æ www‡‡‡ÖdX«­­-ÚQqê9Û­òÖµûh…9½â¼^™Kee½Jl,ÿ2‰„b^„uô41PáÖóÉv]³wíV·ñ æ·ÔSá6›W›Ðçæ°¿d@OvüraÊ0! †²‘°Ó€±vt-gfoo¯‰ÖR8ål÷­­-‚± 1Œ$ŒÚÂÂÂæææM|–bIwvv˜`ÚG›!ø ,ì(ô¼Émq!ÏŸ?`zòä è!I†®æúÚÚa Á€”@! Ñáââ‚^e†€aËø_`GÌPÞK³h»åÊÙ©çççjoñ|ÙЖƒÃŃnC2ÓÍ-–Íf3jÉzE‡P^îctñ KJ¬JƒEBFé$:+ÍCõ¿Wy±™—:‘Mt5˜®®ò‡18HåÎΨ%®\½Yò}JÉ`aà uôÉy=CšÂ÷ å9•KÅ]7©…»N¡&­˜~H؞לžž:Y^þèè¨Ñ £–¢ýƒÓG)¯3ÎÕÄlžš4"­Y‰šÞ!ôX„uG¡;\EñØdJ?S…V2®imzUªï ôX À·scŒêíæGBj=1ó–'ráÄqkk˪?gËr||ì”P)¨ŠUöJ4 #DÂùG÷÷÷Œ8µ‡ ͽë’U”c-çÓÉE‘;2 ±°6MÜ©BØÇœš›L&°®`i[ð2òŸÅ„(þDQ‡(ÃøW<±‰&8B饥%>¼ïû½½=ø+Ž&&8¥PEœÂU¢;µ Æ#_ö)§ÒÊá'Ãå¿J)´[sÁÖ¦gi–Ëä;Š_Ušý1 é%žÖß= Aôœ.µ!ê?‰ÿÌñ:} ËÌs+!ä’´äëºf­|Á±¶¶¶ðvãpîHù9žÄ­ r£Ñhww—]й×<•DÚœÅ(õ¸ø óujbiRr¦Î΢å[n‡p•%Ô&¤^½zurr"W¹ ™} »BeÊ.´UÞ~]Ü6Íá,‰Æòhí*°›oHÜ\=$@/âÙÂêÜFÆ24¦iÞž¦Ê, `^—;W(ª`lõÑ%PÚÆTñ:ž×ÖÖ“maátI}ÝZ–`Aj‚|}tM¹¸Ð}ßïììÔ¡¶Š)A6»CÀHT]°˜Z\JǰIm~-òpö}¥ƒ­°½½]×õááá›7o »ïìì°ˆkÚß!irÎýýý‹/¶··•s’BN ¥Íííí££#ú¥é×EBK%óåé¨ie8DG½¥pa,2\xºy R¶!€A(ÄsJ+É…Â.šñâs›››\ ''Wiù%Ë%“Åš`8Ôùr+x³u âD`m8«CÞžgZA=ztqqÁvÂŽÓSÕÅàå¦i€x‚¤ r<å%arpd€sý]jM3¬ÞQL­R¥Ï< Ãw#‚Ê|W܈ZM’®Äñì†Ä?J·ŸLU#BÞ>£O?ý´Mó#†D6 6¤yR[‡Ë*A¶®¢dÎá†g•·¶¶´èURÑ«B©¶žoþÌYƒ¨§†Õ4Ê\ÏŠ¡Kƒ;Õ7²ïÁz?~ü­o}‹Ofc½zõŠ<ÇƒÌ aõÆù‘«—ԃƘ)N¯pµ71—ÕCÖ+S¢‹eD#t6›ÑÉEAÇ@ÕÚë4äɃH6Ù£WWWh¨#PÅÙH¨§…À_P4MsW ˜Ëpå]R’r`¡»®ÛÞÞ¶3ÉÝ)´ÏOs̰Jª3ÎBË_«m.9‹>2Crv3;­.¤šp$–Gi¨*'Ât¿6ºÇu~Öì<Š9Né£ÑÊ$#Ç_œ:‹‰uRC¶9ŸTTb0Æ‘O ôèÑÎÎΣGXF*]´42¸|MêgµK“_¤ ˜¹hü—Y[—Dè˼VØÛ¤~f#&3žøÍÍÍßüÍßüýßÿ½Ûž"¯ú$¿ìHŚȷÅ" ¢&™%Z޽82ÁB¹:­ØWÈ C xÌ¢EÃ0ghw,¸Ti®o¶ëï.ñ,&ÐuI ÎhVb½È—À³Y Ö zl]Ð÷ÍÍM„bˆYÎÎÎ,´«êc v)‚;O>>‹´°`㚦Š©âÊ{ë`‡z§8™ªªèæ+!·ÈÛÉ´8ø+À‚ÏŸ??::‚'½¾¾Î1æÊéÖZáÖš¦9>>nb†0ç@] {K9š¢èíííׯ_#aˆÜà.[¢A%¼Ÿ± X%»¸Ô*€yN£Àœé$˜Šý•M’šj£iÔ7ZÍÌ`0G«þ Ëܤ!£$¬lxE.ÙEƒtLˆ.$_œ‡„UjR£«íû˜gÞë}gg§ï{º ¸ZïT–§Óéææ&Ðü5O¾ é, ËøgI#;›àx7©!<ƒâÂDuj<ê“Ê…'¢N-;%é#ÌÒˆÀRÊ‹/®®®º V¥Ê){xHRý0<§777]\êæI<ϼ² ²¥‰’ì§i_ `Æã©B×…»3iýðzó6V~{þdÍyIcEDR8ÏCÌø*IšÞD(œ¶J•=:?????çy±ce@|`ÜÑ"“³ncWÂôÉ8¥¦Érô±ò–„Àû‡Ð›ÅPV¯”Bˆ>GrFF#¾YRA—±q¡…¶m©Z*ûg‚ß„& eAnÄ>!Ø‘iˆ5c=ávŒ³Ãˆã¸Î!´Æ°øà(k¸—ª(æâÉr›Í=د»»;—×S§;¡rC–Ö„+{Ãw’‹ýõÑS2„ª:O“°×Š ÏZŸÊÆ®N3zþº¤ÙưaÙ:F“”4V¯iFÚlŒ¹gµ-DP]QÛ³##_ƒ"|–‹ŒuÒ•Ít*­Oüp3ž6Z8„º„k´Jžb£ ¾…RkJHlË«‚;ÿììŒM^bMûé§Ÿj› hë ìp¤-xÍBå¯ ±UUÏbꉮxfa¯&t¯²øï(Iˈ³Ù¢ )÷ŠZàMÁo|£’˜,™iLÀüÁàšú¾¿ººâ‚OOOG¡ú$’e½RßHFæÆRûqΚ>ÁØ8 ÅèìÈáŽðäHÞx<Þßß•(1 Ýž¸!fÌ”˜ôµ°°0_¿~M‡öÎΤ|aAé4a6C¾·ÙÈt€ƒÁãfI¥pG@æ,>jš‚AîH¿½ Íe|€Ä¨6dÎxгÐAwU={@£GˆB4ç_b‡ Éè^ÊšÔ,¦)ý­ŠEFÁM‚âÝ9¦™9[Ìm!Þé'6Ô:f"Î2!¸åzÚhM[èºßÃR»`û)Oª/l’L@I Su’Û-A5 ðÔ›Žø—*\[$ᙊ#UµiŒ£)ðÏþóÿüŸÿó,G[Ò°Jª£J‹³ïíøéOjœÖ%]ýa^²¾ ÎTeˆbTÍÅbp³Ô¨U'2wŽÌµ\Âaî°*†6KA†|áêW1RÍÍQG“¼Ð> (‰Å·¹¹ùï|gss“×P‡(äÄÓñxL0hŒÀ/E(•” ù2æç)jͱn¹ÆŠŒÁ†F ‰êóûï¿O8`™U§­Œ_‚<(ÁO&à®–0D¢c¤Š*fÏAb?f•ðêMÓ¨hâÖ%Õc®™":÷Åí Æ×†Ò1*1’ ›¤Û‰¼—jËU0U¦цj*Ûnè:‘º¹rkÚ áuUÐÍöï}iÈ&Á‰6!ÆïV´B¥íƒß+U¥M}¸U¨»ÌbZJ뚘ý)þE®g\À¤ ÁVXÒlLíQŸºµ ®s® z<35W˜¼‰&!ÅÇ9ªT)Ööå÷ò|ÿ÷ÿþßÿý¿ÿwƒö„ À:XÔ·Y(viß÷oÁÚ. TU‰&jYmHûš ’gìI$Ìždù»%8S|½[¿„|­©“õVyÝ ‹ÀÂ>·“ËË«CÅ­¥Íü‚hiƒMÌ,,Ùy W’`Bdž#B¶¸²²‚^Ì Éo<~Ζʩu1õ‰0a;;;\Ï,¤D)á+mÜ–/‚^Kˆ­¯T ÔsœQ››®fJà¹w—º¾V¸À%†ÉœXrÛÑh¤ +\!‰—Ü)gj³‹ôWÁûw–]ñOª–|õéé)ÖÁƒš 8}0ª­Ž¡f%ÒÔF³½IC>´žsë3UŒ&b²ñJh«6AZ®BêDÈYN–fŽHç6 Œ¥ë‹kJ¯ë¡ a&‚wQâ§Y§}(ÍçO0'‡l¡ óü‚ʉü6Iô…3ÒF?Ÿ`úââbûñMRS±:à-•¤³%©'Ç´CšÚJꤠZ¶P¬ˆ{Âʳ™ðm…EêšAi†tä‰l>Â×!-àþÛÚÚúÝßý]ÃClÍÆÆÆÝÝÝ«W¯vvv°Ô•¨ŽaJš»ÃÆ5æs¼-20·ƒ$+o„Õ-!¹q‰àši±Qš$Gµˆ‡ÅAELâààjezó!—ˆz°˜ÃÃCheDp&_LåÛ ä5%*nxÓxV‡à&Ï€ìÏ(qRYF7F.÷1Õç„ÑÔyrÒ=ztppÀR .Ñ|tåñ¦1[ƒÑª>À£ÌD ꃜ:œñxLï™Ð/´im4¥ºgÏžA’šN§ÔûY ‰Šù·}ZÏC¬DÑ´„*üÕÕÕÞÞ^cÖ———ONN¤•[CÝØØ˜L&º”>Dõ­ïý9¯ÅáTr±¶?²$9k4Ê[Áu[÷AjmÛž½JL;99az;Tõ*EQWkmm ¯ÎêY ŽsÌhiÞÚÚâžžžBÁ‡Ñγ¾Iˆ„QŒ%DÚhÈ xd¦)ø”Ey-M¨³W1l1Ë^·Á ×q• 7 Ñi‚ ÊvícB*u¢×6i¹XÊ xb*P§&y«rB]ájmŒÏ!r¼ººB3@ae}¼"”Á¥B:¥sÖ€ÇW!R®Ö3k"á«Oj%Æ[ä*g|‚Úk!pÑq«Â/&4mÛ¢EýGd€d³JzêÆ:ù òu'''÷wÇæÁåR¯Ä®è†Œ=à t>¤’˜%ö{a5ÑíÉÁÓ5[kßù±y¥ŠÞ½¼)]è6 ýº&µº”€GÂF~ˆÔØ*©YÍ$ü§œÍfh–Z‘ˆq°IˆØÇô[As'.%vX[[ØÆ¬ð{¾ˆ`ž˜ 7BzÕ¶-ÿ4ÔÍ—––677é£PMbT5¼7$¦û˜OÑ4ͯýkªÚJ;øÔØú ÒKñ :ÏcÙ‚CÞÞÞA¡¦ûÏl*alí‚Gæ–ÀXc %IêäÒ´G™sØ€¥Ù¯¹ÓEí0Q-,#&æoÔ«à7©Ã νa ^p#jrùšæ¹MP¾1€ä"¾··Gj©J*õ÷öÖÖM\Òåå%lO2¬­­-]²¸wjyQ»™m‹à9Í/ ªJ,œ!:ú$·ëÙÏ,eBoÌ.ë©rlµñLUÔôaðÉSûÅ/~¬UŒq6^κ˜ÑYÒL0"¬·S4rCè(ô!%ZE-ÓÞQ¼O"×5ûèpk–4‘Ý,ÁL`Oæ…yœ!âئoúí:Mèm3 $Ö»j™I`ꊣ*bḩõõõ““æ!ã`®ékÏ`Šõ£Pe#laY°\†ãE©%Yt¯¢ƒ”à߬§ª**DÀÏ]hÚð9jrÎ14)&†š†$î,䢨[|>ÖÄ9], |<’M¦ø2w„u;??G³üž|´NÚŽm"¢$Ä899YXXX__ïÇ´Áö@àí,;4zÖ–Tº JêÏzë>äTcÍY(3D¡v#A%‘ª$š|S3<“f²œÀñxÌ”cŒ2DVn\¤<á ½½=e0g×××8¡¾ï™V[•Ìà¨MrTCj®™±¶^’Ì‹ˆÞ¨}Ge‘Œ©›3¶i¶ù,‰¬b܇P’`eqWWWoÞ¼!1Ò2hšL&ÿãü("¨®ŽÏä7’EŒxØo+Nù—Y'>~4ñ*UðôsMQ„Œµ€Pƒ£ÎÔeUÑœ…}8— á‚¶!“@üR%A~ü›†É[2vÕ6±^Ó˜4á-pxxËÆÆÆ·¿ýmœùÉÉÉxÄt¹iŒDÇØ-Ä,/¨¸_Íí#Ò@D¶¼¼ ¢ŸÑœœãÔ©A×HÝfþFûÅ¢9ëd ±f¾T¬–0ÖÊ8àÚîîîþþ>š9UU' 2ŒÒ~iîn“5=úPw©‚næÕzLªyJA¾»%Ô‰¥ä1,©Hᦘ“:éŒ Ì΄ŠxssóùçŸÛÞŒíö»ªªú‡ø‡ÿú_ÿëÕÕ•ºOˆ€Y J0^,uúh¦wo™îuúÂ-—$˜[LÌÈ 1Œœu˜û>©S÷I 1SºfIÛl)¿Y TXQ3Ñ„€“»–ÿ´qRáMuìtC »^Jáïì9Þ >ä Ô,@f!I„…6~UUJ)€^ŒÔuÍ/¡mÂæÞÝÝ}0>¾ ZæÙÙgÌé{¶^²§IÖÜŽuÅ„Xœ‹‹ ö²é¹_bû{Lý@-ˆ>ŒÙ!éÿVÑ~lÑD“&Vcsª‰°À ¬ –è…àYc²»PïbhíÆLëùP:åá*-_%uß÷L»¼kc4‘'ÁÙˆ„ZMjg³Ð&Ggmm­e'/T]ׇ‡‡ˆŽ@awت»»»lþ—âÚúú:©ŸPæJÚ2C3°Ì­`lN„ë$ІÊ~Í}£°’˜¢õ¼*Ž© L:¨Ùh‚‘ÿøÿHŸ©Ó@xôÐ*§ÓéßýÝßQ°Væêê ìElǦÁBªRƒuƒNF‚7_Åluþä¢sE¯M=4Ä™òÑIÅuŒö.HYÈ^Bà0ˆ=7 A>6Ÿa<_!»Bаޢ¤6Ã&ºIáéXý)A\†ÉýèÑ£Édrxx8™L?~|}}}rr2™L:4…¬IUU°y6œ@l ›¶F“u¡ñ6 U)²é'Ož@.if‡¥.?6™L˜©e¡8…Ÿe•ã•'Åè»9„-a~A#j£/‡³D×—/2ER!O»‚]¡‚Ž ›KdÑÏÏŤœ6ZU$б†HtIyá_¿~MI®o|é“H€˜4ð…¤Ðz^в‰ÎJág±á&HªBì]Ì á¤pJ±§|N.OÁúዺ®C [rC ÌÜK seÄ‚1aÚ}Aî:‰Þ˜â•ù†—nˆÎ¾:*õTèNNNð%ÓP-3…Àqÿ³ŸýìôôÔf ©ˆüÉ“ú«¿ú«::Õ1 ›››Ì:€Ó`Ìh4B+ܧi€ühÎåkd&)Bm@©k¤Sµ®LÔ7Ä- Þ3Í[N&òW)bz £w¤ÑdîÜÇ›6éÆqGTm¬EbVàLsa@ì»»»¼ñþþ~ww׸úÉ“'À"×××ÛÛÛH¯p ¸»|Ô‰Y˜-Š mÛ¾ ¾¢ yo®jccƒöz«lòK 4¬Z‚LÕu¨~•øÎî9‚5¼™ŽÄÔ;b(4€«½ºº:::Z\\¤ÊÞ‡Ïd2!Ìä±rà/D@`înßV§YŒçÒÛBc¹8ù.”M·¶¶NNN†h$ª¢C» òÎúú:5©®ë (2[ȤƒxœPŽSׯp{b4 …d%Iƒ¢´Y¢É® Y^UTªÙ™’ZüÞóóóÍÍMCÆù&V1ìÓ¹P“„5sqq‘¡Ûh?-Ä<Èׯ_?yò„e:::zúô)Döããc ™š¬@Q×÷òˆ(ápàW\—…DÜææ¦së4m¥Ž1h%µ7:6æóÏ?÷€F#â>Ã1~° Jð,HHG¡Í&èß ª!‡5 @O}†íímxX&qB\§Pu ‰F&ªåw¦Çꇧ¨hòl6CžÆ b–Y`V€€8—cG¡lw£±´³º:«x]ˆDÖ1(×NCʬ˜ .¯®kÖj41›‚Â0 ðÚÈÈ•ØEoŒNÚ‡’¹| v[¤ë…u¯CuS—oÞW%Nùš·ۤΤ&´ ‡ÐÒ¸¾¾~õêœÞY(—Z’4üüç?õê©+1>¶L<‹ñQÿá?ü‡_ÿú×URj5ˆ¶8C‹«›ß,˜$¦ñÆ¥”NHҔʿ‹¨Ypñ®² *Ae+ˆC ô²51·6%"ãÖ!U:‹¡›„ «««˜€Qš>oŽimN³¨;R3”Qt %z†ççç[[[³‹0 Ѓƒf긨âQÔ+ÁÄiXjlšÑßm¨‘Ìf3(‚ûûûÀê%DºPY2³ËŒv_ŽÙÉÉ Ä%ì£ê§!k5‹ÎOšªª0‹Ð(D...Âñ™Íf¯_¿þ裤h×!ce“ÌNMTˆ`̶ʦf DJÄÇ@-¸* yù˜‡w?b¿ø ‡3Ð$}N,÷h‘‘«µ8ø»,©·rײXIB×z¾ƒ‡S Ðá[°­0Z»®ÛØØØØØp4!ðâùù9:_#(›°;rÌò0:þ“0Ò>ì"ù6¨ÀÍ’˜Œô_^ßGg_3ß ÐG;n-ŠJÍ«¨Dƒ§<-†žÊP=::Âôàx„s~~§]UÕx<†µ i¨ï{ÏpUU Z€b†~²ØsHë• #[?½áN†™2¿OOO©ˆÑ¹VMŽãº-..’_T‰°#K vvvÆïÿ…Î_‚bäw”Õ›˜ºz||Œ ÂB´š©–ÃÞÞ†@V1ø2çœ7Fq’©îq¶¹ëƒƒƒªªÙÜÂ"ðp3<Ìš0%ˆ—Eù œ?,_£ ÈGGëô Š¿ä›¬Z‰}³ÙìððT`† ü§‰EHDS’›–JÌXò¸Òœ!QŽ!éÛä¼õÁí7u!OR+ÇSušcÊ5¸ÈÄq7‡aøùÏNó(¡.]%ua;—+cXæ€Mê(Ÿ£¤öµ:I h¶Jj`¾¿¿þüyI²ëML?>>¶Õò°©+Œ<ùNNúÕ¯~‚‰E#šfãÙ™À”$ÁԌׯ_k:1—œ¸………ÎÊ®“äkIJM°®äSLCBO«Ïh¦êz†iž"lÙŠ±{Ž=dÿš­¼V óìwU"­VLàÕ¯ÒøÂL¹$b¨2çíõë×Ã0@eŠÁ{ï½'Õ‹ÓÎEîïï?þ|A(cµ>ÈP0U;;; 1"ìI0 ©#Þ²¾¾NÜqtt4™L0s³PCµªYg'Ý^Ct8>þ|ccCè¡ Á¬ûyOòø$_‡€¯eP»š x›¥ÅmN§SöqUUX+ûþ˜–Su“±3ÄZÒ«ÍÍMöºãdÓ4äµOƒ‘Úè½geîîîhÜ?;;ÃN)O„4ªeo@%­‚íL(D\iÙ—®o(rN¢ý›Àà‹øF¨ØH•Z)JûçG1 ÏMKdf$X’د*2Y£~N ‚·8݃têàààâ⢎Á.Túf³Ù³gÏ(_Ð>5 i@É®Ž ÷ôôô¯þê¯ÄdY%Âõ[<8+D&& ;4‹ýÚÐþøÇ?6¼ïC'°JS14걂qCBÕ(q —¦NÒ«Õ¼ò ]B7þ¯Á*1sþ‹dB³nëþ¦‰Q=ÓÐÏ㎾ûÝï~ë[ߢ[pŽéÉɉûî €}§|ðµ6ˆmÀÃX@¡³$‘ÊSäÑîîî’ä*èáFd4Ö<³ƒƒPa¼4ÛŽrž%¶|ìsSk3ÖÏÏÏ1¸"ßD%¦c|),vTJˆ Ì ukî{ Ã@Ë‹ ŸÊD“žÂá'ã—DOu]ÓÙ~<éyUUrëš ³£Jã–”÷˜…2¡D‹5íå|— <…ãLÖD[Ï,àÅij’¤øVVVvwwY%!‹<ŠaÈx,²!u{l;㌘Ðën|çA˺ ÛL¤2õ³JžK•~¼r™{»…#5Nî—_~iv°Àwmm ñ5 ÜoÞ¼X^^ÞØØ`®ñ¿øÅüÿÑ»Bþ€•4¡d¶7¸dÛ¶ÛÛÛŽ;°¥÷m•F`¸ e›(•”¥¼(–®dúXFáOb ã²\¿0æÂ©NcB„KLÊ)ИW[žy'òeٸäµë:˜ÌC2…ëäääúúú½÷Þ£‡‹iÀ8¯¶xgg‡0° }j@%š×¡ª×u ©Jš P7–Õj|2JèªQ找,+1ÿà >Æ‹çx~~þúõkB.€Ä‹‘%Öಷ¶¶04³ük\#ÌŒoäyñTâ IšÔpcjŸÀŒƒHu•¨„v_mMg i½œCg‹qø‰ePb'xûÐY[[Ã2RÿÅB€^j¯axr÷1:D$»ëº½½=à‰T¤9 ØÙ»»;rOëžV„8‡mè¬WóÒ}ÖÜ9Õâ#) ºä!©ÈšÖd'ÝÏÐ6IéÄXaˆ¾Îº®_½z…YÛ¶Ú××ׯ_¿¾!õìI,ö4¿ö÷÷ß¼yr:¢SÞ‡p¡,z~­àX³òP‡©4 ÃA­Â–•Ô6Á¦bà1ó°P$õ³ëç ªÂ>뺹Aâ£&Æ™t¡ÿ‡¡B ÓKÌÈV†ýhF )ŸÁÏÏÏg³A"w{{ûÅ‹JoÞ¼988xúôiIÓ 0=j‡æs[bŒHR\‹A–}4º’*rû¶XÉóà$“¿5|î ó¾6úàTO]—Ì÷cY‰n G °}`œ «rpa.Ä@ÓìŽ|Y†Ì åˆÏu¶ÞO «:ø_Ô2¶µ½½M-?ŽŽ†a`êÕÕÕ«W¯h¼ºº¢·¾ïû‹‹‹ÉdBÁ‚B!ÅÁããcþNfçÕ‚ÙÃ0´V¥­÷¥±éà\Ð͙]__§¹äK£_—-û^ÄmÚè£ì—VGÐA† Ä1[[[&Çz»Qf†&JŠtpp`¾É.ìBŠ`žó 3‹ÙÃ0@ÅÅ[]]ÝßßgfÇúúú³gÏNNNvwwyjl«ìm Á&ìçb­ˆ©HöIœ„Žk˜Íf Hçç燇‡{{{ŒÎ‰'£<;;ÛÞÞ&Ü£˜H¸½¸¸øøñcÐt¶ÊÉÉ cÜ}è dæ aøUjÉH¶Èñ $98Ê刜µYA´@BtDGÞG4£Zy«<°ž ·@Tº`Á òóó󃃂,Šæ´XPF™cuu•P¨Äøxd¿ ækÅ´MÒ”:é¼2÷ü’îT¡’ÆÖêòÒ4AÅ4Š1+t]d‚@Ÿ…j}ƒ?ͼ2ü$%+KÌâÃb<½ T¶žÙø˜eÔщ^ɘ*iÎöK °íC¢ àõrPÕ••ÍÍÍ‹‹ hV»»»H /--=~ü¸Ž±ò,±™ŒDÂBŒŒµƒÔÁÉà<[Ö躎€NZ™›ÀýÚ…(¨l#aJ±ÄYXÉdz9¢Ø\® }®ÝÝ]UÆÝåmHÅ#hupp@àIw¶|||¬¯¢Lovoo¯®kg½èéé)ë@yÛ ˆ0WœG1€ sëÙi‡‡‡ìÀ¥¥¥ñxL,/ÜcDÓE –ã8™L~ñ‹_<~üøw÷w¹kêœ.ʯ\%¡1Æh:žœœ¨Í™¤3δ.ÃÆn9Ë‹ «]´=Z×Óô`µIšÉGŸM±!FÒÖIœN„(W´„·Œ92›xöìœÁ¶mOOO§Ó)M²Ÿ}öÙáá!ÉX¦­­-xËTr¹Èׯ_ÿ¯ÿõ¿f!&ÆÍ‰&û!˜Öp qÖ4duµKlïN?à'Ž’ÖG Éí¼d a¹‚>ÄXGöM›ðZZÂŽò £$5m®W¢ç@àÜnØi ÅÔ¥ô¡¦jd§€Ôa±* *{zJ)DRtKŸÃr¤mM¦èææ&)ÌÉÉÉ“'O8Ï777ï½÷«ˆ³/²KL!=´8EÊ- ‚Ú¸¦Š 0Œ76¡›§Z\bá‰ð„¸†›MPwŸF¿±È¸5²žƒƒƒÍÍÍ>ø;²ƒ§noo¹Z$›ÒqKì6ª;;;ÜŒSEí“““¿þë¿~üø1%‹õõuJNÃ0`AȦ!dFÑ0 ÇÇÇþÐy"ôH7!ã÷êÕ«‹‹ È¥/^¼øì³ÏêºÞßßGð‡¬–Vs:· ú<„ TÇÇǦ¥”ɰÚu´û´¡¨U¢­¢ yOí‚¡™Êb m$ËÅ»æ¶ä* W™BjÅ Êfi0ŸÑSsÜ–º(ê¹/_¾¤”Iq‰°ýøøø¿ø²è¾úX]×bUÛÛÛ=’¦ÿÙgŸ‘f³(ÆßD °îf²-«õ–ìJ ŽƒoÜ}ždË%¤Õ%A;—‰O¤rd^cñ¨Áëäk<`ü›•5&âŽÍ@Jú–+VB÷'MFm¨>ão-xç>]JûðªÁ¢Ÿœœ¼~ýz:îîîÞÞÞi ÃpzzúæÍGÐw—˜}ÊsßÞÞÖ±³y.¨ñ|öÙgl-…“$RäQŸ­ƒCxþìÙ3RÝïÿû Â§§§dˆLŠ.¥ •޶êçŸþ_þËÙßßÿýßÿý?üucÓž!ÉOjÃm`ie/¥só%c·³ÙŒ€Î@´‰‘“†Z~×ÙÙ½/ûûû[[[üWæ‚Ús£›µ êÅ‹¯^½zýúµÝ6X™6¤,1¾ Sv†£€›9;;{þü9AôÆÆÆþþþÓ§O™t; ƒŸFî¹¶¶öòåË¿ù›¿yÿý÷ $ö³Ÿ}ãß ”;99Y]]}úôéÕÕÕþþþd2yùòå‹/è˜!"“Í .IètzzJ‹E–µ™œêJ–—pÙG2>ÕF‡•—YŽïÒàÞ6Mv0J²dH,vK=u"ë ©ç©OBÏ2ú¾ýú5Ó±îcàè¯ýë/^PL "®b00,vö'¬ˆ 6ÀßÜÜüÕ_ýÕÀ*F:jæšÄžë’¨!’è¡OsjhJ)(ö±P¿a¢ç›4×è“ å}šj ï&Ç®CjW–¯ ýÓþÿŸ­÷lŽ,?®¼¯+ a eP<Úaz†CI™XžÑGØm„ö#®»Ú¥B)R¤D‘íp¦§{ÚÁûòU¦êÞû¼øuf7Ÿ~11ÓTÝû7iNž<éù›C§žFu9q™A79L tI?e¼”ŠxY0í®‘I}V§ã’e=t Ä™àVÔéä™Ã0ì÷ûÇÇÇår¹V«5›Mên #S-ØdæÜ¦Àû6:B$®Øy2”ô‡E&Ž@¶àO(!9NnÚFãñ¸Ýn‹É…ʵ’_¯c7ÁŒ°VŠk@ÖÄ¥€Ê  )`§ï‡ÛBé×Û4eXççç+++,»¦i(5´ ] ±ñæyBb1Úî.//ÏÎÎ i©ßqœ–——kµÚ`0X\\ìõz(“\^^žžžîîîÒ4C £Y(F«Õê÷ûÏŸ?ðà$aà|Ùt§Ó9??§å[”qbgNTlb™SRó½ú‘œÀ‰0Y¶@Ç2pÚx©›ŠâQcî¥ÖÕ¨Jø—ÿ=’ž¤`²ˆÌè÷ûðÑA¶··ÏÏω!øIµpeÆï/ NÐu¤Nǯ_¿þÞ÷¾'J iõÜÜ]ñ3B™Àæ°°„Z¢âùïS˜~›JŸAå¶èý¡XÂ>#SwNMÒ”³+ŒÖ×É/`WÆ®AQuhÙ¹ÍȺRkÕçïÕ1£ÜS †ÜµFtNˆ³Â`0f&ãñ5À—,˘*¨Ë“““­V«ÛíÂóäOLLlll *EQ½^eW¬.vÕÈ4ËÕ\­Ê×ÉÉ @Œ2©MŽM¬JµÙ¾?µ•N§®ÿF›H{góŠ(]1B‰”ÆDÒc&|Q<)´Mš`aÙ}‰(ŠÊåòùù9P F5 À,%D———ÝnÅ º2² &Ü=.4›MÌúÌÌ ,ç»»»½½=º^ |ð]¸–n·{zzÊ—¶ÛíÿøÿØÜÜœžž¦IÓ¹³³³¸¸ˆ“§VH;4¢Tä¼ x,E¯8ƒÀ䉓ޑ·–µ’yR¾"Æ€ÿ›Ð5®&(¦Rð~¡PÀ¨Ç­Æ¦¶$,XY§~R ”(‘±†'''½^/´^k^Nx 6‹xjqq‘N{o.»ÝîøÃÓÓÓ‚ q ™H”»öi~¶³jyY©NyU(^áÝ´«±Ia‰"¤^eË#7Tš´V++HLP ¸(yŠñ¦ñd‘랣ÕÙ¿³JÚz[Õ Åö 4•Ã}OòD‚\ q¤T`å’ôÝÝÝÕëu°¤Å@Y¾½½m4•Jåððã…;bÖq­V‹ß—¦$ÇgÒ¥LO².ƒ8ýê#)˜RUl½ È_ˆÌUV“f_72xÖ‡À„ “9mBà°ñx æµ¼¼,9±9¸ü NX¨%¼3Ž(~’$j*K~º"l=t "PR?â/P'J"Ķ,[¶¾¾Þjµö÷÷a-À2ÅÔ6›M^„‘`ÿ |.//_½zU­VA q«½^ïüüüÉ“'ÕjX®Ý««+U‡È 7•˜ølKžF&©`r’™› ç«êÊ-"Ó•ô¬â ùb>pS8ìyÊ`}`°àÍ"»|yy Î3í ’–œ RbPΘ=®¹Dj¿ûÝï~õ«_¥6ý¨`;°:D‡^T}LÃÜf)ðólº®£ÑH<Žx©¥×oæÖH•Y»Fè8MÉxo4%ÈEsë]ˆמ§”²Rn¼DyìÜ:–C'èƒ SJèI%‰ü§ŸÆ…Ô5KM¹º;ÿ 1èk9ôìåÚÚÚõõõÙÙY³Ùœšš«ÂÆ­®®âyÚí6^h8R¥b³á Þ¹ÉtÔ§ÐÿÃ"_\\°ñ±BQø£¾q>çââú«š 6]†ÜV„[±X70¢ƒÜ´Fë¹»»;??ïõz”ÿĽ‚pwwÇÉfe¤”€ufÓGöâ‚Nù¾,Ÿ ’ªâÕÕ =`#ÚÌ‚MŽÔA¿ßgeÀVBë@‚ÊáPnnC†å mÖN†óóó år9Ïóv»M%‹Bzœ OÎ#¶VVo,<CÔÓ¬gF½/Áƒ0ñûŠ Bú4e&¦žº¶ÁÜ sŠÜx×Ì©‰r³Þ¾}Ûn·Qƒ¡ö×jµÀ4Ô¦˜ÊUæzb¢("„‡ÒÁ”&µˆòÏf³ùÏÿüÏ„ªxBÛX?ÙT6:6=kÙÈø*§§þqŠDh=1J³µÖ JC×0˜›€”V\_ 4]½ò¬°EbúðÊÝS8HMRFGÑ`f]²Ü=í>Ø‹l!\†ž¾V«Õh4¸uª”‡aØjµnnn–——y< š$ ,˜õ&¾JêmAjW‘QÌGà㸟c› AìXCi?GG±näDAUO§F•;__Î`›3ûÃý”±ó6K@¶Ö7©"a¼ºº Î$ çÄ+++Åbð¢\.ƒgÑ6Híxraaabb‚ä_S°èFŽ„M’Ë}æ™™[Þ¤FIE‘ú„˲°UéªÓÔEÅV"ßÊd ·”Qg@^ƒ&$å)Ø´>œÊm€³€aR-E…=M3`vvz/ÎHìþ„9ᘇ–™hZÇØÐVš%—––@ONN^¿~̓377·Põ6€'<²Á”Xº­­­O?ýt}}½V«ÁÕ­)‹år™J®çFåFõ$âó;Ù¦ÐiEy»–™(›²ªÐIå)YS•¹.‘Ø ã™dìˆ Áy€8¶9 ý~ÿôôôää„sK/¤ÊÇòy¢8©î¡6Äêõºdöx†Èä7ž?þïÿþïwwwý×ýÓŸþ4²fÖR{Á”štVÓ4­T*DÖ¬? r#½µ†w½; ‘¨¤š›î*1·–f¢z]$%¹i‰)ÉM–@©µb.Á½7Vžm@C2³©™|ZnÍ}5I¨eGMÅ|ˆÐ !¶†Oò‚€_Zã/..Ðr%«åZ†¦®×ï÷—––V_ˆø@7F6hS©Xµ9¬¤$E“b¹¬$…sõ`2!Jn\û¥I«±é¯R®ŠN;µ6K™HEèjµ*/‡ …K“JµZ¥Gº Ý'qSš%€¢—¶Zš¦ô ѵ‡¢&óŠÃ0ù¸zª=z¦ûæÍ›££#ÊÞÜ.òLa«ÕÒU÷hwžçKKKaîíí¥i:77÷ío‚î£G¶¶¶&''¹ÉÝnÃ:777???HÜèŸXȘ¬#“OâÀáÿõ÷éW;˜ri°9=ÂlÝRe "UÖO76ù-þI??iýãNR«ªV«pÄ¡b¡.ñ’(‘Ð£É Ò § Qf2‰I’LOO«È@¹1BjQ ­o>Š"4d0%*¿Š§:#7GUŽÐÔû"£‰Žm| ?L–7 €Õs'FIÓ\†”«ñ.Íf“ó—˜ *A4W÷üüœ–ì]©T¢–?©]M$ÎEIÄ#gMLL<~üxiiéôôô׿þu·ÛE÷ŠçoµZív[4Ù øP”¬9ªL¬Òâââææ&€¥@^” °¬^¯Ó0¨U‚þA%&”CÞ=pŠã¹Sà”AÑ ]ö~K?ì/|=ýtLßxuuÕjµNNNvwwqÊ(1Láãx ƒ‚MjàÁX ÊÖÅìçć/^¼øÁ~ðìÙ3‰¤Ö¢Œ…RÍadó0Ä­ÎÝ´_?Åý ìÈš¿ë"PîšU%¦l+û§Þ_Zâ€%ÑF.:{ØŠ¸‘¸ù½* ÄÖø¦â V@ˆilºzl¿ߨåP\]àÿÐÍ[¾ºº:::B”®]Т}ò[ ##U6(¹•Z­šŽÕ'©!´äíðä‰Y jí¼EEsssâC‹>ãsa  •RD†¡œœ¡â&(T«Ä‹õÌMÐŽün8‹E%Ž5„=ÌdVƒ4­ÕjñޤBS˽{÷ƒˆÏÍÍF#Æ kHùubbbuuõöööêêŠ!Ô*ƒä¤ŸþùÙÙYÇËËË8öÁ`¹VÔôô4¶¦Ñh¥¦®!DB¨3Ïóóó+++4u»]~Ù&GP¥ œt‡.…ŽôöK *±(‘™ÓùÔ‘.˜Øwn(ìêët#Ø_Ý…!‘¶9ü‡‡‡_~ùe»ÝÆ|L%wb” ´g:X1í„æù¨Ö€…ö¼’Äu“Š6“”•¡'ð}( ‚*MtÄŒ„‚³,sss<€\Áüü|š¦ü;N ³9€pÛ˜:G$…5—˜¼¿¢zzG³,k6›2y‰5c;t ~¹!”ð¨‘L9·ÖN…WæøEF“ÉåÂ#/¾¼¼DEÇsÓØbøeÇÇÇHã rôÕùù9FMHåÅÅÅÜÜÆõõõ©©©/^0 ›ä‹àqaa¡ßïÿò—¿$ ÂGSIŽû÷ïÀ±:;;£ææE'Qo}ë[?^[[«T*ý~Æìååe£Ñ`´²[1NFnL–ò¬Àñ0UÈóVIÉàT¡T‚ŸØ>M¢š‘#”&&ö­ïUy„Ó"x¯n·ÛOŸ>}þü9Õ~Œ2KlÃ@#Gyç’&Ö¡­: ÉP¥RaÕ^ Öbl ‡ÃŸüä'?úÑ a¥nJ–ïô]žZ$ ›ºE8²{RE…ZÞ,ÔëuÆ5¾ÖªŠÇ’Î‰Ï ³ÿ?izþ>°[í±Lcf­OüÖ»îDKõõ»c“—Á´y%¶ÐŸ °¡º®º™ª]òël¨n8töN§ƒ´ôkÊUD¼£Ñ¨ßï—ËåñxÜjµÎÏÏ©sQ#Ã#ÑÇ7== 3~zzzyyùèèÏÏ+àê©!úFnP•jpŽÄt×ÖòëêVR Yƒ'GV<61Žc”E§§§¡¼¦n܃š‰æ€º•r’v:}Ûí6íxQ5›Mµ„Nm‚Ç ~¡ÁøáÇårùÙ³gp0pyž7jµúúõëׯ_¯®®ÖjµF£qvvö«_ýJ p&ÎÏÏëõúüü<ë7¾¹¹¯¨„ˆé›ßüæ“'OÖ×׋Åb§Ó988ØÛÛ ‚ T*5û÷ïs¸6‚üÈûÀ?7}AŽ_è¦êæFøÖ©fã|Ð$ö¦ °Èš•Êé`+_óÀ™ç%¨göèèè—¿ü%ì¿‘©? å6K¼NœmnG±X$ì`¯¹ÌÈà„ó/ Œ···?ùÉO¾ÿýï‡ÃØM£Q0AS!‰çMÅ4-ãìì,~=Pר¨æš–š| Wƒ”eÙ¹ìŠPpà‘µkˆ EÈ'ÀÈ×S#›k¤¸Ié´l á±}>-·B¡âa˜Š¤Á¬²Ú²CëF™ö>ÍÀž½ˆs#¾†âDl"úÓkkk€(s£0dåry~~þüüåR?UU57üÞ½{•J¥Ûíöûýåååb±H]_Ž4´žUn>šAäh<Ù–÷“˜ $JÔ(ÃÂfNLCƒp#6™‡0 ÉÝ2›EìÅìIWY½Èšoä•ÝSB†:ÛívÙ>½Am…Ö ì›b¨ gyò››V’u¾½½ÝÜܬÕj_ý5eÙÛÛ[f///F£çÏŸïìì,,,¬¬¬ÌÌÌ\]]}þùçd.‹‹‹ì?6Ñ>ZgxýN§ãI³Åbñ¯þê¯>þøãåååñx|xxxzz \U«Õ–——×ÖÖ`®`\4^`›íÓ…\_Zàf ·NMy›nÛ§-“ MA·Zÿé “§hå®:ùöíÛÝÝÝÝÝ]¤ÍB£FúLEÍj¹õKPmÇ}¢•ˆ8­ÌžgÁD„]OŸ>ýÇüG‚£Ü*žJå$Ö³ÍÉÄÿiI>ÈfrÓ·š°AËž>Fâ Ï L3Q9@ž]&‡†¾ÖØXæ±5©â›š¶4¶&6Í ‰ÜªŠŠ¤Àt‰/"'1‘¾?ß-°)ó#d ΄àƒÈ‘÷=Tϧù\z<ïììü×ÿú_ …B·ÛE0„‹M—‡áN¤¢œrÒ¢µµ5îFÇ€>à5sss8ÿܦH.б¬Ò²l·nì¦Ô¾iÌAhëÃ`SUÜ~§³§QU§ÜÚôù(Š:N†+++þ6&IƒåÞÂâÞfÄQá2ƒ%ùI"ð›Æ ß N@žçWWW‹‹‹¯^½jµZõz^îÉÉI½^§E†æ§•••ùùy1Ë‘O‚ \.CqœœœÜÚÚâs'¬À|jccã;ßùC!ÏÎÎŽŽŽ ”ÎÎή®®Âáò•8n-BàZ^Ô«Ø-Â@±©pÒR7¥5±^÷ØÍþœ/ï«dPCÙ&EÖxMÊçççý~J-õ:'#5&„žŠ-ž™™aº-jÛÂÎ’ª°N4ÇñÁÁÁ÷¿ÿ} á_©µš MRS ˆ„.¦€3¡®ŠxˆàD.•e>*‹Tuâ8N'ªL[‘ˆ0rÏÔÂ)”•MRZy2).²!× º.gè „Ñ„Öü¬°œï*ØlEýº¬5±a¥RiµZâ‰p£èõ! E ”0 ©«;Œ*;ø)^¥R²Da±ßú@Zp¯DÉ›ÖhYmpîĦ]h#ÄRQIAç^Ù· 1á&Utày>~ü˜³¨h‘˜CO0… iÍ€Y–A½!@Óg¢Ù‡u„‚RX«Õˆ÷öö€äÑüæ £oÁ1€òìÙ³4Mûý~£Ñ˜ŸŸ'0év»:ËkÒ©ƒ7RF­V«V«Ÿ|òÉ“'O*====<<”ŽÂÚÚÚÊÊ ÉulCƒ2ðS’ž™Ð°¿•Î(­T„º®IÅS¸[Õ‹äÔù(¯¼qT„•¹1œ«/¿ür{{›²€Pjê¢ P»ÐIã«y$€sÎ|b³XØ‚Û!K‡¿?;;û?ÿçÿ¼|ù’tOî[¬ò½â8qSÅLJß×øÄ(…Ä6‹Å““åÚ777È“÷åyþ# ¨…q‰F6²éîOfÌf6‹ Lzbb‚q,½dL ¦A60R¥Ž…ü•,¦}xìt£X&Qû#ë:« q½»X::-ƒÁ­4%!˲N§@KSnE`"ØßËËË»»;%nT£ÑÀØ.‘MˆùU0±}öƒƒÅå$‡ ÇÑ'lSNq8/®A;©ºù ‹Ì&AHîG= µgì Š,˘6633Cœì2Ë2dÙ,ú½ÑA‘ EªŽšŸŸ¿ÿþùùùÍÍ ’{Ífs~~^š×*• æŸþùÈfÁ¢9uttDg¥„†©ØŠ¢™š8‘ï§Ÿ~º±±Q«Õeív»———QÕjµ••ºyTã«â£D2Èl&P榺+¼RÔ36 XÝÉ`AÚ¦Üõ÷êß=w!w‚ ²SpONN^¾|ypppwwW*•DOÄeF&‹¬› ÏFé3%?6ˆ×TÐ':•دׯ_ÿã?þãW_}…]V…G×™ü ›%DŸÐÆÊaž4T‘Õ+˜8˜þÜÉÉɽ½½(Š’óqŽDÖ.69‹ÐD`„ωr%«Ÿ¸¡ ”Ç| SM‘RÁUb¨À¾‚l|‹¦¶01ÕªÌ}pÚ’1Ãú‡Œœv­9”¹Q²,ÃG=zôÖ‰f:ÝÞÞ¶Z­0 )uw:F£Aô{yy‰2o`ªFtÞR¥iº¿¿Ï¼|5’„© Ñå2ó$š EùŸüqdƒ0Y%‰Lp·1Ó¼‹x!™1³äÞµ›0¿Àþ8j âo2S°‡´ñóÉáVg&tã åÈ  %Ôb8à Æ}3'''ègæÐUŠe¡PøíoûöíÛ……8 hv»]6ˆ¯ºzúô©z8HårùÉ“'Ÿ}öÙÖÖÖÔÔÔîî.i>éáüüüƒØ)æp„Da¿d÷uÂ÷µ=}ò!Ñ1‚±”ñù±&6)tÚx±ë¼ñÑ«„<FAŒ6¶Q©SéâÕ$°AE½Ð&Ôi^ŒÏ£±_Iª"×ÇñÞÞÞßýÝßmoo§NÄ9vCX%¢<žGíwsssx>±±Ô|‚/×ø p÷0 5¯3°þPˆ>ïP)u‡nÞof½Ä Vlñvè&5æŽ^ Ù¬£†Ó¨² ìÆÛ”Кþ¹–\].¿ô§ÙWªØ> JºòÙÐ üÈÜ|*}!Ãád Ë=hŽŸŸÏó âììl·ÛE®R©0Ÿ™/väôô´^¯C\‡ÃáàK!$per|]b­àrÅ777NGª•¡S![d›±ÚÒ—ÍÂÍR ˜°™t:Žª1Aéjåóao"õ &‚\*‘9=÷`ÐÙt²*ö…¸ ×M^žçËËËKKKÅb‘©̾fIwwwýVæyŽ<éÌÌÌ—_~©i@¸ápxpp€R¸ðP&åÜÞÞ~òÉ'¯^½‚y°¸¸ø­o}kkkëÁƒ333GGG­V %8÷‹‹‹‹‹‹k×WŽ},32ùN}ï§4vãdtƒmÕ¸x±0 _¾|ù÷ÿ÷¯_¿ÆONÖÌË…‚£¾TÙýÌZ²1¯¡)¸D6³=729%ڱ͗'BÇþÊȾãpDN7:pRv·r¹5"ÉÉdn`™êå²wD@Â>£÷g”²Lª‚en2˜X"UkWM°`¢ÀBÐïÜXyñ52§¯(¼LhÂÅÅÅþþ>ó—Â0DŒœ}ʲ¬Ùl"J‡ hžçkkk ]è…²•J… Š#§MžY ">Dû![C1…Oßh¶0¾ŽðAœX–} 5ø´ÜZptÒfHLxšCIçãüü<}dð˜È@///1=„•JåñãÇÔ0UºHš—©´%wš˜'ˆ£ü0€/..¤È̆ÖjµÏ>ûlaaá÷¿ÿ}³Ù,‹óóóœ:D,i“òGqq1˲õõuäž§§§WWW?ûì³ÍÍÍÕÕÕ(ж··Ù®+—ÊЧÌwøYtB'_¥a´ÊYueø¨Ê£é**; cKt¶RvÒ‹/^¿~}vvh òšd‚øpÌx9³ã0¸À=± .»Yâü fT¶•ˆžãšçùþþþÿþßÿûåË—<Ò„ÍÔÂ;J¹´^ÌÜXf]~¹ 4Ém©¯¡ÇàãUÖç_4£0²*Q½š‰œÀ³?y"+à®Ù*n‚@%ôíÔ­b™ 9%YèÔ4v nbElÚÊÊ¢ +B“á:ÎôyŠ) ^ÊOõþ#œY'0^ëã?ž™™!¾`Ÿ0U൧³,[[[£T·¼¼Çñåå%l#õëȸãêURЉåUÇ.E–e첞{ÛbÖ„¤WØÀAØ1™M@!¼ÊŒÜÈ‘L¥Î¨¹¡yžÓ”O%”؊ͪV«|Ëîî.p¸XÝì÷¬A€¶€Q1“““ív»T*¡6s}}½¿¿¯ ‚ÔSµ¸¸øæÍ ‚l!<¤sÒðR©¼8‹Åb¿ß?<<üä“O&''WWW¿óïlmmU«Õ0 OOO{½§bb˜_MŽò¦\TÅA¹ã7yá…B\!Í;PšÙì<ßÞ¤Œ¿ä¬Š:$‹½?3‚ggç—¿üe¯×{üø1 ˜ø!Q¥ðI< ×žÄ 1Ñ2DÈܤ¨ÐéÿE&u͆"411±¿¿ÿÿþßÿ{ùòåÈÄÿ8®˜¹ÜýYUŒHKªkÎ'€!Lʉ=‘&ZlÄF£!›[°Ñ­ï.ƒ¾žˆ‰/Pn/ë›úˆP’OõÄ„NmGGPÍZ5•He‰>¸]’”Q%Xtzô„°Š‚Ó_ÇEÉ ©¶D¢H²žb±HW8Dg*ôý~rrrss“Œšú÷æææþþ>ˆ/X2£ÃáP--#yäNÙ' Cï<Ï•6Òâ ˜ÊBìÄìs›*†ä#«J#&l5tªI òkÀs¡*×étà»ò»ŒÖÖÖ&''ÏÎÎð*6Kø¡P(Iè2³ÅÐÖ8gÔ¹K;;;Ò§¦n533óäÉ“­­­ÃÃCdy` gggÄ*„cdlñôéÓV«µ³³óÑG=|ønÄx<~õêE H3›››õz]Ì~%×lÜ8Ë› ¸:~9x„ ‘›Ñ@"¬-‰!trz‘kÔ¿{Ö•ð þþòòrooï¿øÅ×_¦)à)Ç KMs;ˆ'œ22ž‘¤N96™‡Ü)Ï&€9M i·Ûÿú¯ÿúôéSNWd š‰×ä_8´=¢(¢n+  è™[烉‘éwò+µZ‡eÃñ Iæ”n´”ŠŒTÄõØ!ÿWu ß<(3Ä®ÖÒ:9”Ì„ ñWR2(Ø>6#³ÉÏÊ"Å–1ެ;És|°˜X3†@¾Žº´uîu½B¡ÀôÛÈ{ ¡ÌÏϯ¯¯)äyŽÆc²@(ù",ªU"‡qJCuä&ĉ‘¯•,Øø&_Ü$Z\ZZ‚ìÓï÷;pR¥RaÀ~XwÌžF0u»]EdlúÂÂCbÖdãoàé‰hŠƒ³H’dkk‹Is_}õU«Õâó;Žº8U«ÞÚÚb‚l·ÛåJ€Þ»wï믿>>>mÌÄòòòÁÁ( ¬^’$ËËËëëë«««õzýúúã ¼811Q«ÕöñÔV 2æóÈFRrDå¡%Æ’ZÏ[Ú°8&&n@C`-G`¹YQ¶¨ØM™ÚÍ?úÑ‚ 8;;c+Á›+•Êh4Bë‚"†’w±í¤Ÿ¡Ú”œtèô¶“ó‡StPâ¦óóóþð‡?ÿùÏ=GLY°ªjT¼¼¼ÄÞåy®QR>È‚@:à KqÛdââ“““Xg2M6šhK)s’;E`o†<êævÚcí7Åx5¬ÉzuL®`êW±ÌÊMŸLãØ5dæ®1g¢.N§Ç›æf>0m jðÅbAúâ8nµZt>ëj·Û\T¸”ÛîR«ÕÊåòÑÑä2k ©Õj­Vkoo¡³+++x¬‹‹ 0,víÓO?}òäÉíííÏ~ö3ö«R©üÙŸý¢‰>Œãx{{›(˜Bö·°°0;;ëÓ1Ý„ÔÍžÁo‹‘ ìI!OÁF=ùZSdrª«dn.|`T%“jˆL(þûõë×÷w·³³#7NÑ"s. Nç’ØCeAјTþ¾Lû„Í£¦Ž b•ºÝîÏ~ö³ýèGpM8? vDPÙG¡“šêI%n¤Kj] ‰PbI ÔðO|çìì,ÒþÊÉK†HÛH•8m¶OÍDµÐÕÂH©‰QŒPfäù–äUòÛ@ªèý¨²˜â×&6Q¹!`¡ÒX‚”E‘UM­UÁ¤ßïñŵZÖ3šû*• W„ÆuòÖår™ÆƱœŸŸK@–èL‡Uª§´ ½Ã½¼»»£YÏû¶®Q"<— ÄW€tïw“ÑMÞ7??ßh4Úí6C"ÀÔ¨¯áÕ±§¨²ˆg˜ÚTv ˆ=I’ÉÉIòGlYd9 ßÄÄÄáááÒÒa&)p`,q]¥Riuuuÿìììöö¶^¯¬1nk82Èovvvyyù£>Š¢èõëש©³Â™ Ãðþýûiš¾~ýz0Ð#U(êõúêê*œþÀd§rÓ†ÌLæIÙœX»ŠzÄ÷ápª÷E$ÑG%õ«,‰[À^Çnp¯’³§Ü¯ñxÜëõ¾þúë/^.A‡þAЩ¨ž1˜¯T*aS¸(•J ·IJ|<82…þÀ”S=$) _~ùåþZ0E€IDATç¾xñÐÓ î‹&àI%‹Ü©Ä ¡ãI$a[ÛÀØ)»Ê\p<kÝÃsUu~dòâ¿ýÛ¿ýSâ_k•iPx¥ÌKŸ„ßqüñSj”H‹s¡Ï”ùçh¸êCfi”x+€R - Õ?¡.1€S{“ØT¶áîî6#FBcÊ ˜ÑlÂ(œ‡333 \¸#èתѪJ{L«3.–&Ì)é1*PʬRdTcª¨k[²Ç’‘£ÚØl6wvvcÉÊŽ Q`:Ä­-..‹Ån· ã,0MqfÖƒ55£¥ÓédYF-ˆ|Ÿ¬Û*v®xÔünä$LåìÅ{¢nEQ§Óù÷ÿ÷ø‡@¢’Ä`Wàþ›ëÙ˵ø#³5¶©ÆBfT[S&9<*ìL/ºR]î] Á§xP2×î7X´zmð‹È„M0ò'dy²Y ³%361Ù >ì‰g¾óH0-—mlB/Åbú^3ëéù£PN’à8£/_¾ÜÜÜ” sÈæsVÀ¼+• Ha¥R¡¥îì&øº %ÕÚD” Æ§z-n‹'ú"ËN˜G‰ž)â3WÊ󜺣 ÅJ¿¸¸ äÇ4Sö«ÛíR—$ƒ ‚«Á€%A»ÿ~½^¿¸¸ØÝÝUóªê˜¤!,2‘c»Ý¶ JB‰' Cx¸YJ¨Èï$I²½½Í%¹wïÞâââƒÀûaf0QâáÃ‡à†»»»Ä‰,æÂÂX˜ Õ…DMГ«§äÈ$Ù—ÌXÍ‚ 8x  ›W$7,;•º6ÈÑ s« >’ù@¤KéììŒh½V«ñ]LÄbìîòò23¥áÊhŸœœP#ŽL³T¨¿,á>@l °„´?øÁ~ÿûßÎsy©<²nD ¾â)-&†›Îƒ" Á™Äú¦6! žø+vß···ˆYóžì­êæææ-æ#7¿O0“ReÝ‘Í<¯X:0b.üÉ*Å4'áPª\P<â%}_UìDxõbÑïÜØ=† ÖȉØ*”Ó¿ìíí}ùå—ñQ«ÕÀ­€¨0©Åbq<ÏÍͬ²&¸ „¨­h(<¡2o­ú7YÕ `¾ÈI%" 4‘äF&ÎO„‚Õ¦¡:³y_„âD4˜6¦cèÃG£ÑÊÊ ­ŽÜŸ0 iÄ?céƒÅ«ËÄò!á„![L/~’]žžž®V«Dˆ£sÂ!W>È^Ü»wlèöööw¿û]†°Õª›Íf·Û…Å^*•jµÚêê*ñˆzæÇ6’Kàzþ~w7™S¤z·¯÷‹Q)ÔR qd‚¢Y‰£ €]`|ätâ8·°=777'&&€îG9EéËËË€ŽÁqýúë¯Ñk& ‡Õj4@Mx$*'¢ó^ªÄ‹EÚÚž>}úóŸÿüùóçäé’ðàç'&RãÀB±‰›MLJÖ|R©)‚¨P˜Ô2ëÆÜ9áhê·—‰xÄá(ôV"Å+–‰­¥Ù3žEn\-·ŽGÄ‚Œlì³~xlSՄ͇Æ7KÜLDáS‚¸ö¹õ6{‰˜Ü& dÖÍ@J%ìÓs›L#Mt,ËW_}U¯×™M€õ$±ŽÈ¨tŠñœ„ߘ›ùùy•Zy;a·RwaYÈ.±È¤½„0Òl—GPFG‚hC»¯â_zò<M›˜˜hµZDaªÒJÛ¤P(ັÄ_¤`䛹ñbJ¥Òúú:ô%„·8aì ðÁÔÔÊÉþÈRYÂ(B>D1øõõ5*k333ÇÇǪH ~uuuxxØn·×××———§§§×××5ž;Ùh4ÖÖÖêõ:y„pq66æRÕ!¾H7þIPßPõì8††—ÿ‰LU¾(™£ên@éøx¢* t¯×ûÃþð£ý¨Ùl‚0²ì$•ç«*­z—6š YÒ™™ž‡ûÎ.c.UÄ&jšZÇ‹tÐ0UÀ5È–ÜPq'ª¸åŽ£ÁNã*#7Há®@ÄÄ´úÉY©v Ž(×U´ƒÀuQ¥¦ ¡GäÀÛR8Æßsõ"ÎÊ=l°!A›Ècäæïîî®Õja°€Ÿ[2kOÓ`çÀªÝ\~r«J¥‚Ò1 E,“º)¾ä˱ ÝSM33F¨)ÍÃC/ŒÇc&µ®òO’;…r|Ôää$œ{ÚD%C½ twqqAþ¨Þ4ž­X,Rȃ¿§MQÓOnm_b H$pÄ”ÄÔÓ#ãÊà Im.f¡!uÿƒït:õõõo~ó›\Â8ŽŸ={÷•/’R•gÕx~Ð@Ÿý)Œ9 ÕÜzÂ(€êzŒl$‡O,RëhS"£D!7Œ”ðDéF©j–eÅhv‡þÓáp¸µµõðáCUr+• Æ­¡ããã  ñBTÐ ªÀ¸T˜WÌ®¨×ëýö·¿ýñÌ„JUKØ#^_m‰*hjtÑdÅÓžÍß—9Á…fÀ ¦‚µMlà‡t^Q…÷=…B!â®îJB‰‰.EN‰E9¯Y Iwlªc:ñB©=9•}Åä«Ô(pTg%w‚ÅÊc•?{RLìÆçNÖ=rº1¼ àŽpú4M¾øâ á;™Ér¸Aþˆ§ œ}õÕWÃá°T*IÆ?¾ƒ4²¶OrÕÂe¬YD•Ã`kx¢sVQ,p£ÜTPõÔ)QŒÛô½Øiò…a(W“:=Ä&îùÄ0MST¦ò…[¸Õj°‹Åv»-ˆÍÓ4EC&yì¸v œ×¿»»#?k qVóPbSé1%ñ$I ôû}x€ ˜NØI’t»ÝØ:rØÙóóóÌÚË~$éø"%oøY333ÒêF¾±±qxx8uc–äÎÌÌГD”Šªú°Ã€„^¼x!–Æx<¦0Ï¿'I²ººJ·üÍÍÍG}´±±ë‘ UŽÆ¦ê¥:©a /Â=Tø0/=œÌ&Š+ÖáÛÔTê…IŽ-) "†„­Z)eãl0%TñºÝîééi’$F,Ž'˲³³3P-½)DU<«Ýn·[­V¯×ët:@~*R'Ía ¬¹î»R+åÝXeäªBųõÈ2ß‹SÔ€XÁ†Í¬‡<0Æ–rü·û·Ê=ÂÚ Y¨Àõ…¦N²šs ÀõÎfÌLGœ0J°ºÚŽt@‘ 2Æ4rŠ´JÎ9>NQ¨wÆ|d&–¦¤<ƒ88‘àƒ ˜ŸŸ‡ÃoyMwyòN§Cà è bHät¸8ä€d¡i³DÄSüÎd}â8F£n<ÃGçbø¢¬¯@ÚAô4rœ'!éØM!T.Ã[hܼt)Ø)•J<¥î“““Àz&<’(ÏG´H\ÃÝ–ñâ•§§§›Í&ô ’0šóóójµº¼¼Lhvyyɸt&°§œ(MÒ$÷À†â8¥= o S?°jíüIL(-qóÀeÐ#"¡(–Rk¹ ]ˆÞÌ:@9Ãwö'3^¿ÕétZ­ÖÇçççÛí6¿EqB&2j¹1H9¨ ©¥î;…™ºÇ;5±OnR;¡`,â¦Èõ‡‰½¨0ÍÛ E ^ð”ªt¦WÃ8%E…”Â'á¹§¦¦âÿößþ›7™rûC§p˜;ñ>QÿÄÕ@‘³ò Wf£ègf6rCZqÍ”Cóv-²þïÀqùrã|ÅFY¾X)]XŸKËe`D…ÔHÈmùˉ‰‰z½Î¯Àê†É= ”Ÿ‚}b&}‹wî=+FJ ²åð¹ñ4 …P ™²£³”£=Š"r[iKdÖaã}¿ò)™­ÔµɾËcaJ`–Ð`;OOOWWWçççûý¾æÈöûý¥¥%ņÄѤêTBÔ ÊÐ e Êj‰Ás7vD\sÄ'w#Ú€ãÔøÆc“ÒÄ¢ &王©Ã‡PvàÀˆÃܸ"BŽmÚ&yF¤’œçRæNa#rä`#²b©ë Í+È—MÁR´:\hâÆØðLäÌ™µ2¨þ8ÝœÈi?è6z +wJ¤¹ém†ŽéÇãaÑ ¸-JÓ8»±“ÜfלEhæ}š6vóþÔûJè¤XK‡ `ÙJN!qhâ$l¶zúˆ)Àò‘=c¹(É…aØl6=l‘es•ã°¼¤`Ò;. hã)àĈÑx]~wee%)ÙÃst„±² ’T$þç5Cke‰¦§§ËåòÚÚ°ºÊÿ W$ª™†aX,iå‘iZ,’‡®GQC-˜ñ@˜(›¥tIbl(û èFÆ Çð‘»nâ)yVÅ)ÍøÈm\9ËásŽD§ÓùùÏŽ!¯C~Ÿ ä<ÏIü|(‰£0MW™~…Åä:6% ‚öÆNnPR3Âyq™øƒ‚©cÙù-n¶,4âF#2 7©bˆš;v†ï5p ŽU¢äχŽLŽ‹§;±cvšåÓá`9ØæÐX6j¼´©¦%«"ë6*°TX¤À*µ¦¶˜B@›ŠGÚ×ÐzVS¥ @zÂàƒ ›ƶ3-F9¯jIL¼ÞL7gdsznoo1UÄ} 0Q©Á…¯VT# ¡‘ñÐäƒ*¡¯( ý~?° Qü$O Š/¥ô;§øë‚áQü …[6Eïë{Ó<ƒ{ ÊLGû…´MK¥R |Mõæ-#‚À±jê¸kQdtÐ}Q(³ÉL Q•Â(12­À\äõÜd<ÄÏʬ±‰s(Ddª$" ÆN@Æ#Â|‚O#có‰kªS€Q ½ÓÓÓ<Ï?ýôSÊÃá°X, :/`annÇÁ†§Îfñ`¸±ÏDQ䑸®‚ Ê]ó‹ÃEßàªã•‘ªé+TZôD=ejjJ¦Ÿg&FKÜ|xÝèwð¿"C™ØÜ¸ËÊS„¡&n„rnlu_žË«X•Q_îU_+&ÿÎM~»–w·ÌLJ‰p&pâÿÞÄ((Õ·è:­5Z½xr/84Ý NÔ<°ÎoâvnHdâ-Ýn·Ùl2»e4qÿ9JmPÖ À½`Aë¹H˜6¾ZòÍ‘égƒò¨ü¨Ýn£«Ew«H°PÚTÎ5©%&JÁ£âœÊår¹\&ÞöA;`¿ß§ãÙ*ò±ŠÚrcŸ¨Î¨ïb[Sû£Æxöb~~~mm !Ó¥Riaaáþýû4 ÑF® ¯ø¹(ùE6HÀØ>Áé ¦QGü«Ê½¬81q«Œ±0«477ÇÖpT"§ÿ‘;9ãÜ Tè}“ÞÅ»L®/4M$–ëææ†a’¾¸¸èv»µZM\pRcyuG¤Fµlº°4S×1’:5p%à‚(S Ã+ ?†ž‘X´JÇ(]#'ÄÏMØ,¢Ü涉µ€ %j㜿[ñØúéX¾‚M$9@Ž"u=%¾4àóamª|f²`c-”_¨9C‰®¶S1§x@ªÍªªÂ&Å®Á01qµÌMEÔˆøGê.ÿ&ôJÛ)#¨%ãš’§¨y›o Œ%Ïžáè®3 KÈ A„“Àäq¥‘įTC; Œ¨Aùh4!qEÑ[ûC!2µŽhÌ+6´%Žc|2ßBû{ît²øwÎÇÛ·o¢àlAÄÕiá­Œöü±Õ4å^E¶¹ñjµZ.—×××iåEÑ{»°°£•sŒj+ÞX”Å‚ ¤,uÍØ ïSDÖg‹•›d-F„ÆÃOMM‰t9EI]…™ë¨UhàéÌ$!å®p]¡•I•×¼¾¾ÞÙÙá¥èš ºOm XE`º¢MEÖ]$Ð&2± u/ ª“YuÒ ›¨ˆûaÜ7a¸²¨B¡À̡ț©kä†95žƒ.Q„áDiâÚR¬÷g,R©B¥}y†Ø‘×å##pfÖÔÊ&¥Æ^UÇóÑ ì¡¨ØDéåëø)Wö°¥|M®›•&—; wÂDè†ß¨½;u#s…SxÓæklR¥`ÌÍf³ßïㇵ÷Êä#Y'´É”¨çnHºOa—¢ièT.0å———‡‡‡ƒÁàôôôèèèüü.(ð$üB ۾ĵ‚©puuE’HH…ÉC˜×'¤‰GÚÞÞM«š! áû-P¡I…éçypé"©P‚`cc}H&÷ÖѤ¹¶¶¶¶¶&`4Ïs[|.•JTù lðÑœ@ß‘M’¢L©‚Ìz0Y° Ò %QÅŽ)ª‡?ò޹kQ˜Ë}¬i_~Wö.1=~Î-w‹ _˜¦éÁÁî«Úl6Ià Ã#cç`q½×šK€§âÎñNÝDq¥‡(h*¹¦Cml=»œeš´2ÁЉH »Tmà£æ*%©ÎÁFÖŸ0þ(ˆ!‡Éœâ•nuê8õJhêû¶09Ј œDh¥ᚉə >YÇÐXc5sJÄ6¯PE–ØÔZYYkl¥YdrJìçôÉÇÇÇ™io*U|ÄsŠªËçPÌñÅ4D6Ë735þÉ Rð)IÑòÚjµšÍ&ÚÔ_y{{; :!+¦ fŠø”Ëø ¥Kµ÷”Aƒn2¸´Óé&ñÌ xiʲcd¥ÎëC"cYÛr¹üÉ'Ÿ¬¬¬ßá®1IFãÑ£G".pBp¼r$± ¦(ð×eP÷Œ@"µÈJ„Ö©›Y×á'ON¼\(”ó*±Ð]àTþÎ]«VätÙô3©Q•®ª-IÕpN/ªa^‚Ri·Û%V€ÐétðÍè HíõzjÀ’V&`Â4šk·ŠÞRI? Ö–ÆÌ‚ 1‰MŽMl†± 0ÎKÄK ´åÅÉy$YØA’Ö<Ϲà’dÇïz e¤ë¨¿O„*{¿täòdN_ Et€£x¬’Ð8Álò*™Ó¥ Þ—ÞS|§þ!" QT’S̸¢2ÆQyAl³¿®®® 6™U†?0œn·‹ˆŠ²VBd3'(õ(NÕòÁ(Ѝ<ÆN~LuqÞúêê …Ré„(M¦Ef]NA‰ [EdF­9ô*£H%†QµZ¾ÁLèØ]\\œœœÐƒÿáÇLÇõ‰KN÷2µ<þ]p2–âÉ“'kkk<*Õ.fI¬¯¯3ª‡Ã ^+EÐÀu2ÈÒ‹E Œa/HA§ÝÛïØø{‚)0i•ÇåFïâH($ÓJ(gjTä‘ (Ë¡ê_B§Ð ª¶^¼…¨ì ¶Z/ÃÅlÖ·<S€ƒäƒ¸˜\ì²àQŽTv l&ž€p‰[¤FãÉ%!Џ»ù ‚Ï1F*;J¸<1¡•M‚ ˆÿæoþ&1Ñ ˜È™hãœ{$ÞËq°<_lSC&œÌ¾XÂJPO±1B=2kôÍ *µnÁÔ„¥eŒyxÁ䉉¯ë €ÔÛ)\]Ý3°^sgnÒï÷Ÿ={†‘ÂOõ[ ¤øÜáÀêú4š§&S=¶±E$­cr#®Ðh4‚Õ¥¶ ¨ÔÔT¤S8ºYŠ‘±Ïe”!æ s ùK]+++wwwˆ+pnà@A;æaP¨×ëõzo:QA 3M!nl©TúÆ7¾±µµµ¼¼œe ÆÁ`P,ëõúæææÆÆù ë¦bEnÌL]oñ¤UuÅ\*’MþDíWÎ|ìÚz‰J"§A.»ö@þȾÆRZ*H÷Sh žGVÕ;otuu5 dÁuj¯®®Ø~Ax,Èõõ5Y˜¶JÅDÒ:îfá¥ç6Fœóä'¡èÀ«‹¡œ hJ8;;‹èU¯×k·ÛBm¦§§1‘rdaÊ2úý>Ö|~~žïZRg¶Iñolóuéò)¡ÛíÒEïüáLj™H¢ChEÇÅbq}}ýßøÆêêê½{÷ºÝî`0ˆ¢¨\./,,p]__·Z-~Fe¨¼¹I;©2Àw¡HGTÎåáô‹ ¬sÈÝÎM†™ J"Ç݉¹ÀìÀ)»)Üû [œ°1Î:<¤«¨¶*ðuÙø÷Ät¸¸ ðþF6÷4°.>îõz|x¹\~øðáÒÒ©3 ó«ßï«›ú#ùü¤0rÙV9Œˆªº]lJÀ(hÈî¡Ó™‹¬Í-rü#vJ! Ÿ/Ã$P…OŒè± á ¤WÐDT!ñÈ/¬FN>¬¸ÖLf‚¾Äm/•JTT¸ðw6ŠQW/´9¦Âòrëf2Y#‘ gV¹‰%ä&Ø;u„0IÜ—<Ïi/U–G‹]&¶óU2q‰b§×¤Jà»IP"Îj›Þ€ì”2s$:®Œƒ°(2RRêÆòˆ`‚ ĹÌmÔOnÒ*|bJ4Û9´®…ÀM¾ ’⓵4ªdN('y´àµÐ¬Z³Ùl·ÛŒ•—]Ëó "Úˆ"^±%(ŽM²zbb(¼bþ¾öqJ·Û$Òcw:$ÓX(•Y–ùùyn*ÆW 3±SÄР-I·Û%¾ 4™šŠŽ‘”9ñ2¸MØ0öã(TqlÉ>Ð9ºÿþgŸ}¶±±qsss~~÷‚«««ËËËqk¤3ߥª‡¾`£zXaBHÌÀêEcþHŠ]Ë­1ë€&=W76õ%Gâ…ÆïÏbÐ?ùûìO&3knˆ2Á 2Jedò“Q¼W<˜ÁUñFZe&¸Èà[×b›äʾ³éS I¿ °ÞF^Ÿl `úy|¹§¦ãÁ‹õ'6s£©EÀ2p‹éˆàñ$ª³qº„) O̲,Q1åƒ äĪbëK’&œû™eÌ :0§BD¹/>A‚8‘i*©„¬,’O ..Á¹»±)mÿ1ŵ‚c¸‘CÛ ¹ŽÄ5Áª¨ œÙét>|¨3‡OÃ:xüŽ×‘¥ãd³Ät>Óv—ç9³àW!‹(‡#pñò^±QÌd¿x…©©)Re|Š%©íh2«Ð=U9Þµ¿×ðà¨ÿŽÌÍWx "8¶Îu”=îÝ»Ç`û± *`ÚÙ*ÚMB'x–ýZ›Aa…]ÑîÆ&=ªTѧWª\)\]]]YYùꫯ8¸¡“=ÔÉ­¢ÿ _œª­/‘„¦‘ÈÎIONÂR_2)È âñvãñ˜æ> kê÷wwwp BSì'C' ã~”* ¿¼¼ÄÍæŽø–$ @¶&º0Ûqww×jµ2ÔL̘?Gœlaa)^Qžž.,,lnn¢~Ù8,š· Á,—ËŸ}öÙ£G’$988h·Ûoß¾¥‹uii‰’"ó{27¹OõMšõÙ®&&´á»MÕMM6RH«ïý*˜ p[§ÓQù\‡Æ£Ör?6u#U…±b¹„z]éŒ@[Å&‘)Ø(!UôÁ òСÄðØz^ ?===÷÷÷WWW1D»Ôݸw EªïÏÌÌ æ†(šÎœ ño7~_€eW$­çÐÈÕž š™t* ÀÂb£ì æÆ ã_ ôTçM„ùñÿ´ŽÂÛ×§%ö •6#5Rxî£7‰ùO¿Wžv}d$õÄZ}Í…F\ÅÃ#“T™(­¦o‘"Åq¼¶¶öÍo~sooO$²–.öCg‹—"äÑ­kµZ‡‡‡ náodbǘÜiöŒ@¯ÈÔQ䨋Å"MöN§T*Q" ðÕjñiÔìˆe´Îð91yY–1j¼×ë)Ñà ‰®ñ¢Ø >ºùiD‚cp‹g%U¹#àI1”^^^îïïß¿_Râ‰SAÊÑ&ŽãR©ôñßøÆ7 …Âé驆¬ÌÌÌ,//Suít:¢nè%…·oßr| 1rå"æF¨§Æáœ†¿Â¡'–§GŠ1-Åb1s­dÐ)1±r™n/¹°æ÷ò“D*©è&ƒºw&bẈúÅcDÅÃx/4ZEƒÔuMdNbW§42þ³_§ú€û’;ùv¯£ Ì_æn8 [Làää$¥êÀýú|ê$A@ ÚCtÔ‹%R1MöŽåÍìð(Ç&µæ¤Ü:ˆu…&{è]ÃnEFÁ¥nDVhí, \P$:tê<ìejb*‚x³ªÛÚ,9L`䦸¦Ö`™›ò÷Oƒ™Pv™5<²F0å®ÞƒŽêéë5BDvvvž={&²©ŽÅ®õ½{—g ¶Tl¸YcÊÉCëwóÜ6ñYR×gÇßÞÞbÞ0ÍáçSIÑŸ6…ñ/1C"§EnÚÁTì¤?îÝ»·»»‹ %Ï“¹Ž"ÃåNÒ‹tc<÷ûýíím:Ý)íaÕ›xe…¹¹¹ùùùØš asÍ ¦Dªs£ì’»Š`ÿ¹?7ñ ,°_*ÃÃ\W#®šæbk… ÃÙâÀ„)èâMMMñâ„xИ„ª-Õj"…XÁ uÓÓÓ>ÜÚÚ*—Ëð? ô’$YXXn 싇T}9_Iáždï‘f¸rJ DñÙ¸V›‘Ô8¯ãª£ºÊlŠx6¼Ò×IÙâÌÉŽž¦Ü4¾2 ¼5æ)v‚”Y ¬bã6ó´ê[æÈ!4v||ÌÆÉ`q–x¶ÙÙY „ÌÌ ¹dŽ#ª 2´Æ’Èu¥&=Ì¡ X•À)ßž)*æéÞ½{Ì Q‰6p,ÙÌü‘“Šöðt†‰j+‰µej¿ym~YX^ƒ 9³9¦Y–U*äŽ" ¸)r„c˜‰"Ÿ£ÚœZˆ Ú嬄¯‡N Yq»˜YY–Á„Ù@Cèôè`‘ %¦Ç:v’$9:::;;»ÿ~¡P(‹Åbq8+‰aÉ@ý b °eDð‰Deñïîîúý>Zz}¥ÆsssÍf32Å‹ z½^ìd¤"ë8FK¢¢h÷AÕUâ–”ñbqÑ󟇌Û:??øð¡ôç”›ÌÎÎ>xð P(0PK¡w’$=úôÓOQXo6›ø‰©©©ùùùÕÕÕÙÙYÍ¢–§ÔC(þ™‚ç⪙–L¼`sÌãV³WI‹Üð}UÈ)ÐÊfÅNÛWÉcL<áÈIB $ñ©‰2¾±Í=Ë(ã:ït3ã)BOMcðN×J‡¤Ñ^äïÅb‘“Omg4U«U|ÏÓjµÔàɧ‰k¢‡'QHœj·˜½Ö¨AZ¹¤*qn¦”B`þ wC$(S#H×ÍT½?áÝiWQ#uíNÚZ™½‰„¼:_Üëõ ©¨©ÖVUÁظ*>@KmNª‚dri…ØÄ¶p&JõyŸôýræÄi9(n÷ÆN½ÐÞÀ+µäðð̈\²`ãOb([   „ˆ³ )<¼»»C«hlÓAðè|âµà­¬¬¹ËM©™Ç5gãYO"ü‹‹ ’8|`lcÐpV|2LKm¹Ð:·™Ç I¥ÂË ÐŸH/k£Ñ€³Î¾ƒ€ÈŠ­­­=zôˆY„̂ǾLLL¬®®Â]ìv»ByAä@aBaÔGIA] M¹±ˆßÁqS§·KÆ¡ðÛì¬Ä&zú»‘™>šgýeæ&×y»¦Ë"ϤS™"3вâwŸ„zDDŸÄž©â«ùNu>P2Ä §§§å¥ðš™5rsãô±oß¾=;;“"¹OßRë%”=ÍŒê8vâ#•Ä`I_P)¹¢€#Í„–¬á@üáǤ9I( Qöôôôq+ÅÀ¾Š¹3¹kôRk—ÔTâÄRÓŽÐÞ`x ÙÙÑÜ”ôirn© 6éÉSĽ?T5SG$XELA"ËÈwŽÆ†—>99ÂăE®í‹Ez)tS'8֌ꔰ@tÎAš¦Ýn·ßï‹Eˆ²abæ`9‰`Á匧®V«Õëõ……@…®…Bx-q3ë‰étg»-ÇCCLLjyâ?onnNNN^½zµ½½½³³óâÅ f¨ÐP­C¶¸¸øÝï~·^¯—Ëåf³ÉkR ºÿ>rP=…1«Ç"3¹•Ðt@ÊR×&G½ðÖŠ“Œ“]¦Hï á|—w¢úOaU‰S¬Ujæ!þ„Ö²¦Û‘Y Ž—ØÉ‚ë_b§L©¨_ •ÏC• Ž£ëa~4‹...Êår–eûûû2Ü‚‰kµ $í#`\ãdî8½ê³¹³yˆ’'›îHè°± [L %±QÇÜ& d<7—KW[1‡6Wz°úŠ@íµ ciÕjÊ3°|¨Ø:B²"kaWõZ©u`Lœ‚Iÿ©MglzCr>¡•ê@Á`lyÒŠIEÉá¤N²yzzš¡Ä4¬DÖˆ„ƒRF­³•9Î^èÆeÆ~þü9u1òÜQh‚oß¾e'ØrL†¾+·á©pÍ@ˆÈúý~«Õêv»è‘CEY^^ÆlÀKP,•"¢©×ëÔÚ½%IR.—±ªqg‘`[­Vjý1°%PÚ£¬©ÞT¶{8ÎÍÍÁÂ'PÙ<±¯¾úŠÒÞöö6.j~~þÉ“'èÉìííqëõz£Ñ “?HmçJÚ/ÿð†0vµZ#¤ó‰ù¦é—ýR×À f«`°skl`ST~ÒéJl\w•DUXL`Toy;E⡱Ãü!ôhƒça…NŠ/ÿ]&ðML-Ó˜9K0NSµÒÄM÷( ­V 7‘¦œeü¾´ƒ[½½röÜ©Äõ·”J%0ÉÉIÊ#‰ UNm•¢ ˆÐ¸‡‚e€E¡6aþ²`<±+3¥Îê»È”p ´*!yÁûj>@b*§¦j*xÌ—0ä¦bצ”¦©¤Ä÷J,w£DeÈm AÇ(±î-!î ¯B£;ñ`ˆ~héE|¥Mð¼¼®ÐP9 r·f³yzzªÞ7ð~zhooo™R)8 ª®,ÉE~ õóóó—/_2ܘ缹¹YZZZ__'©¤WY å/,/’5t&“Z²V ³ªÕj¶ãiÚÙ,u Oå˜rhÆã±T´Ð` AS‚€ƒýúë¯ã8F<Ã÷ï|g}}iÔ5 …ÂÜÜÜòòòÊÊ ©®"Ó™ð±IÁæ_ò3tohf‡dpŸ·0³~xÈÉ@øüJd ^nŽB•ØiŠ àRLM“OVI<‚¡ìOµéÜ5ÆN=Ÿú»6騨^¦M.ó*r\Á)¸ „þÈëÃob¬$ï^©T0%0Útm¹Ëú%¼ØA®ž®ª¿²xaG©uש1ŽSJ ˜OÀÊc…• Há^0r#¬–¾ÃþرÎëDQÉ)p¢ cSX—k§ã"€MF77f©v.51I gù”`ûÈ_ *žžˆQ‰M÷*˜ ˆ¾ÀBw ¶‘¢§Ðq¦y( Åóc&X²ëëë½½½““hxGàjŠE-wD’Ô¨å#¶GP›=OØU»»»ñ;7:9cf´ vvv =lN'~~³¬r¹œç98ÚÜ8Ž ?Átæçç1U$_oÞ¼ét:€¼š:«ºÝîîî.¬ôJ¥òñǯ¬¬,..Ò´t8Êåòƒ¸H…÷‡˜«*¢Åׂëö‚ÐmÞ¯ºP·Àš«‘Ì…@#sädBWÃÄX%>7ÎÚ\„ •eTÂ(Ò¶Æjùw¿ŒÊ!‚÷yÿ± ]’d)ˆãl«åK È$k0ÝÆÕÕÃe}‰M,">ÀœÇÖªR¡âðh‚¤J®¡ ©Ù(OŸº*O”IQ£ C¹•‡Å®©[ל0¼àæÂŠo *Ó{Ê0¡k­RBž9‘iýÑÅþ €D¢%»éU±5K«PM‰=wsÄrcÖ( dó<©•ÊmˆHú¾~£pêPü=zÛJEea¶xÞsd:G±‰®FQÔn·(¥«ç“B!F“XW(žø¢Ì‰¡ˆNá†ñ¹€£4ôêº6›M$ vwwobð¸)´Z­ÖÁÁ}v ¤)‹‹‹‹¡U£ˆ4–´­lgƒNiY{GzÕn·+• '¡¾Ðа|Èííí›7oøÒo~ó›kkkËËËa^\\`ÝWVVМÄÐTPT0JM-$±®º8Žið° »IU‘/@P°¦À#] ¥i²;JÄ’ÒR]?´ÖbEOºþ± …+Ì]k½,”â/a–U¼)Ò"žCšH’Ä%XW~)’AõB‡a833Ójµ¸€œ>ŸJ ÷ˆeç-ˆ <5WY-FŠd‚V`¥bÈÅ% ´^¯W«UéáˆDç9·ÂdR7ÙÏc8ïÒU±ò÷5."S_ñÞ@tað‘qµBS löºüï/Gç·ú™ S²w¹ “Ф'ð>6ò±ÈÕM¢0P]#ÊÉ–‰GÔ¤Êz©¼ˆpssðO@–ÀZmaZâêU܉­K^"D<^·ÛeÄîÝÝmIsss»»»ü}b}´ [ZZ`šžžž™™¡X&;`òDeª‚J°S 0ÂìHÃ9£¤T8méÀñú\þz½ÞívBër‚àòò’!Q…BáÛßþ6Çãìì ›ééé¹¹¹•••ÉÉIÄ¿| ˜AbÚU¾.Aõ º°°€7ÈuKº©›éküʰÆ6Œ+·¶‡Ð(B“cô ©ÌŠja‘çV¹ðu]¢Øxð™£Ê({óç‹hµàoý àØFåN­ˆ{1XIŒ4‚'lf¨ÊÐÈ™E¦žÛV@ é€&k®+™j#,‘S1V@Ãe‡¢6"4)3…¿ÐbzAoaÂ?‘Þ‹DÌ‘)ÕZG¢'%SªìÔ·,zKÁeSõ„[!^+#çðdÅÆ?}ÔþÑyLM!žŒ¦Qmgb33T”µÅ~Q QCé@’$ôa]^^w»ÝgÏžÑq2èc€CÀRÊS‘ÖeN]‡ Sü˜èà…j‹òSÉ?bkàåÓíÈs*ÀìAºùä“Oh&]-¸YöjSþ^­V³,¡‡hH¡êŸ˜XøÙÙÙÝÝ]­V«V«ðìs7V–„ôÍ›7¬ÀÔÔÔÑÑ‘˜÷ÕjuccciiIº]>øÍ­z#&¡rÀØuíIŒ0°êÝ3ªÍ«@”[3Ù¢GBC+1Ç6¹2uŒv…í‰õxoºIòü%ÑeîZ²Ô1ç3Aýúຢ3þ¨mS \ÌÀtcB#ñ`¯ÇnhyôÞÞÞ"—¦R¯×qŠø$ÏA,Pg>s3ëd%å0Ͷ˜â,Yy곡ã<]^^ŠÂ8•Å•Ùû z²ÝrÞ $²÷ ä|–¹aîÞ9˜p =zò1…Y l0)’’U©k)«œUbb‘)dIÅ û¥ƒ(¯Ågª Tp¢E:s…U˜?éúúúäääìì ˜yvv–…*•Jçççª)ôS+²®¢RNøD *|H¹\nW°#‡·€˜‰‰ FF£R©”eY½^§—X]uI’¬¯¯ã0Ž) !›çù%M¡>÷åÇêõúäääþþ>m1­Vëîîãããã½½=b1¹“<ϧ§§ëõúÄÄÄéééÔÔT·Û…ñ»´´Ôh4(œ`)ÊP°)6•˜ «vþ +Œ‡;­Kõ*(1WZ U‡vèäô ¦Ï'hß‘ ©<'vóý=ŠMÛÀ—†d”3#1y^¾6sÜ ÌúskîMMD¨  ¢•Tz¡$T±Åìì,Ð;/ˆýRi‡­¶dXT¤™j”„”·ìŠÖc›$H5Éeçc0êL¦Ömã±öÈÆ8ú Dyå{\vô*´­•ML;IXµ6ÝO|Bb=èL²¼VàtCWæ%—¡uÁ .õ¤î€bu®¥\„‚¹îÔ¦xù¬[D‚ͼ¶×¯_“ -..®¬¬lúí¸ ²¡€ ö4Ž››Ò4]BÚY’$ÙÜÜœe$of]#‚-dÊå2“#Xpú8ŽËå2Gáúúº\.omm%IòÅ_€"±øêûÕ…TFAµZeÜ!ØÍÍ ó²*Ñ®pÿþý4M÷»ß5›MŶ”¢(Z\\|üø1c–點šš*•J‹‹‹kkkHM䦜É(O\— "yXá•6ðg ÒœJ œRn‚p:-5¹­gE%&¼9JzàZ¾ü-R ¤ÓÂa³\‘¦Çì#7ñDîVï+hÙud#Ý›)Jsf"H÷îÝS½/w=§ŠPÀR¯¯¯ÏÏÏ×ÖÖ¤*d ‚€Lü1A«õëèî ¹ó‡œ ‹_¿³a·ª_A:Á®a•Ñ‹³šÛ<‡ÜõÀ+ªMý«ðPAåh4zÇ'–·QZ'ç ŒÆG°ëf’ àC$ƒ/¡ßRAG­¹ös×f¥CbÝÅÑû1ŠO…N7"´ÆKù‘é ËzÆN'K^W~ â%êÃõzH„†aPC1žp>pŽUO „$M {žz_·Û%k£®OL—Û\hžA¸¼¼<;;ÄAŸA'“;|ss3??¿´´433C%šÜõu†®•’^*¨¸Å®×* ÃZ­¶¿¿Ooc¡P¨Õj?þñ{½AŠæúÝÞÞ®®®~ó›ßd 5RãÅÅÅ4M´Z[ã®to&lR–üVìÚ¹RSš•¯âV“V ÈW^'Ûçà¡ëò‹œ2Ÿ”³VƉÜ`…±©Œ«J«DRá’¼ GÖSëe¬ÏOL%"µ9rÂ+Æá®ˆô1ñ¸¼ ²lñ„M[cÍÈS1Æo¤Xœšè ‹O Ug8³‚‚b †‚K`_æææ0r$wüb7K4w£³xr0E¬ªfJ‰3Žã?Θßo¾ó+™²ZèT }èë³HŽBÁT Ã÷Õ9^ÂY#c!ôJ/Q½c±µzJú¼ÓS+ˆ dOYQoÅ®PÍB€"{)Ù?}þýû÷iÍ%Ud:' ÑhxHj¦ìC—“Óèøø˜Æ7î ïƒD3ŽãùùyXKŒÚív5!IÅLLLìììÐ@NQ R•¼i‹,•±ˆE þóì•NxÍìMÊGU™k¥L3V@ˆ“œJ"r¹‚ÌÈ©ghË}ì#Ö ­ê&¹k õ}3fÂ^ƒø •Z!¦<±Rq}ln5xˆìzÖå¦BÇjaSÇ61”yå\àÈt„áp’xjz HÍëׯkµÇQ# ®HSpFSµgо'''p#‡¹ºº*—Ë···ív[×m9:P45}^x$/¡ÙlÂQh6›@?„?Â>A%B“ÙžœœœŸŸ???WiF—VzÐyžÓÂýõ×_ãçi ¥‡f<òÉ'FãððâØÔÔÔÆÆÆæææÜÜ@›šÎT{Qo­Üxy ¡4¦œ“?àØ ƒƒƒƒƒƒ*‰µZÚBàzedÝ|Ðsbm³?ÑPS@Á Q»I ÑGå¤sGCWõÙcSM<á1uÝ&9]•s›·¢ûöm§ÓñÝyJå¤ñåÕj•Ò³>6¶IŽ7OxqqÁ)òÐÚå…Ö'(ðZ1,…¦^¯G®VúÔÔT­V›ššBçS§‡ÏÔ¸J2/ú'ˆœ)ÉOOO_\\‹Å½½=Mç!Qe¡f¿··ÇÍ$¥Mlv¤N§Bÿöí[B¿‹‹ Õ%}õ#±®TJ,{¿ß—¼ßÄÄD£ÑÀ ñ…™f«Õ"óššZYYyüøñòòò`0w›ššj4<¨T*L$+Ø,pF†t)Äèò -ŽÅ—H (Š¢V«õë_ÿzoo‡¬ÕjÒÿ ‚€ŠßHè§néF(Lˆlwø¾j›8ƒ¡ci—‰«-è#2j¡‘0=L!g: 6þ~l“û2›8ǧŒ€cÀ|PãKmø¹[æ Ð@JçüÄQk塉GL½²›@ã™QÁshJoµZÐîÝ»Gø ZJÂObqd@D”Ǿc°¦§§Ùh^A¨w`ýL‰ „en҂ϵßUÞÆ&¦¸ve™yy¹\º™“yŠŒU'uT>MÜ òŽà}±ÇÐX:(iš^]]1”E¨qzÁå±p::¬ŽÊ:º·¡é— VÏm¦ÓÒÒÒ_þå_AÐï÷‘RhµZ?ÿùÏÛívdbûÚ4UèÊÁLDQ(Î¥ê÷ûNçí۷иÊår†õzýèèˆÐàìì,vÝ @E+++äèµc²ÑGæÛ¡›æ6̹X,lð’_Õ5°‹µí÷û ƒRàP©Túýþââ¢Ð„J¥Bo4ŸŸ“sÑWôçþç¥R)Žãýý}t±X\YYY[[»¼¼ì÷ûš‰Ñ œ¬«)pVÙ+·Iqwww/_¾üÅ/~Ámá5¹xXü‚É®çN0— Ànlr‰™ãsê &…ä]Nü'Uãê?•ïŽN•ذ™Ø L•‘9ãç@–A+8öqîú ñ…¹Q¯ST#šåp8ŒL+Ù38 ¤…B²ž:þލ± ÔC6²ùêŠ]BG6‚N,8œø=r4×Àª7ʈ)&ÖþMX˜–}<'ªV䎤ëÃ1WâFËø,L¨<à—Aá¿Îm MèK&Fg%s“œó<§êï.N¾qÂf¢…Ö]¬j¨Šº·2m‘S R@755µ´´´¸¸xrrò‡?üáàà I’ÃÃCŒÔÈæD*s™™™Y__ϲŒiÉÝn÷ððœK%XìbäìÜÒÒ¹}¥R‡çççBIy#)µßÜÜP Öä5R)jzzºßïS–©R3¸$&•;>Z©T’ð“d‹‹‹N) ÌFåœqí¿ûÝï´Z­,ËîÝ»·¾¾NŠNlŠA¢&²†QQÛ7:àt~Bǽ$ÆiµZ¿ÿýï···ñ<ªR¿Â ƒ ‡4ŸRÁ¤*JÌ:‰eyrØÊëáå ?ꯋ¤W°ÿ.U±ù&DÄ Ä„*®&Û`>\ÚÛ·o´ÑjµX|Y7ÑÓ„ËÐǦßy˜ÕÖÅY^^FM?Š"T€î éOØËËŸÊLF%T]‰}‹÷ 24°ü"›µ£jÑ R8¦ ¯©)µë»”¨%*„&|ä!? úEnœ@Œ½2õŸ© 6‚ãåd„jÖäË=‘u)xV&H6+¬ABZªT•'0<¡ª¹MX˜—K`ÏÓétvwwƒÁ×_­È62ê öº&1öÂÂÂÖÖVE'''@øt#ONNß_#qØÝÝ]\\l4¿øÅ/xBkJu‘ é{#kjW9¿hJmŽ;¯©))|)~Oœx&êD L꺾¾n6››››årùìì pŠÉš>²Ñû÷ïÃäØÞÞFfÁB÷ïߟžžn·ÛJÆC£GkÇêçÆ5Ñ,ÒÌià)G—¦ßï“ùjÎHnƒ¹8T”¥(ZqíÁS0ÖŒ#$öä†pWñüªö¨ª“[{ ߥÂtìæô)¡Ó]R‘X;±“y ­}M@°7@ ¤lq¿ßÇ_\\ÐðP¥ÀS¼Â.&‘«w}}}pp°±±ÉoI¤{8NMM¨’D˹ Œ›˜˜ jÄz #Ö*)V Hªn>–N+¬Ê#;¥» á)´î]™‘ÐêP„¤.MÓD{8þ”òjµØt]1¢ŒÞŸ=£'ë£ÍôQ<·Î¥à|×Ôõ[É~éUS×”«h\è•bÔÄÚP¬&NQ,pe)þWÁ&t___Ó׿« ¸qÐdÅ———©ÌÌ̽³———4-F#|*„Dƒýû裮®®ˆÅ ,P£©V«<óÒÒR³Ù,˜‚0NL²,,;æ—à‹Å"Å©¡jõ¸„§§§iš.,,ÀÆ€Ön· @¨lÊQiÈ PçZ­öñÇ3mVÇB¡°¸¸øàÁƒ{÷îљĎãœÅÌ"ÜβkØOê¦r@onnvww÷öö‚  ¾ùæ°a÷Qøâ™¦)‚ñÄn|]±X¤óYT” tªSkæ]×± óȵpMؤBO’𘔠͂wåÅå€õ¦w6!•˜*šHo1Á"úˆ«é™“¾0`·q—///™G‘„ô‹OùˆóLKËug#;1”ü''Vx;KžÄ’*©WrÇsà'Âj¨!¯àÆ©)”Q&.$×3ÚÞñ­bkµá߱豉*°”3Qéê¢O m€àÒÐ(6>A›’wžçT´åJ¤e u ”².0r£Òh>‚±8ßœ`)®´s©Ów»]†-..æyŽ#ê÷û|>T¦Ðx( gggŸþ9·)€@1?pÆõõõýû÷Çã1ªíøÃ|r^,———ù±F£¡;ÌgRõÃ@½¾¾†Åù&¶L§ŒW¾¸¸PeCö¢Ýnß»wïáÇÕjõéÓ§oß¾]]]eAúý>Êë >€©L¢Ÿ™™ùö·¿ oãàà€¿¸¸¸¹¹Y¯×™Ñ W©Ä„#„eas9©@~’ô½œ···/_¾7Í"Ù, ¢tôÇn8£( ‰)Áá>ùa‚P;àô¾Ž‰± / `#‰ ëš wFª€•¤$•¸éŸ e¸òª Šô“¯;w&*æ&¾Ü&6ƒ~ZÞƒçP¶/†×Æ#É?ÿ©JÁ¦˜lƲúTB×ë—ºéÇÊÑ|©15-4/\ŠŠ :c§ï·6qÏ›Wî @2¡X,Þ¿¿×ë)8 œNChññx< ®®®NNNPü!´i6›ì.å¨Lð•’$‡kkk_~ùåÉÉIÁ&Yåy^­VáCÐ듦):0~'‘3€E€áp8??¿¾¾þõ×_ÃÉBKÃ;D§ ¨Bj³Ùœ˜˜ =::"œ$0©V«¥R ‘?éÍF£………ÅÅEÚ›ÿ+•Êýû÷=z”e™,Qð¾ä çGdNv w"¡Tý¨ª~ýõ×h–ªé/0‚ˆp¬˜Þ»»;„â8\ÅËËKÌ:¶¾Óé‹ÅÁ`pvv†äV½^'¾›°é¶ú›JŸ\ßो¤ƒ˜Èš,¿®bÝþ™i0(¬ÛíR/îv»`&Ýn—B3±çÜÜŽB„^¯Ç ]ÿ°L¡²qÄôµZ ºœŠX@xËœl¨æ òÕ9?ÂÑEÞI%¦À(sŽ7ˆ(F¡vÖc‚BåU—Ò«RVZŸÂZ>Ýr@ì|9ˆ*nf$¿¥ðGrÎ| ᕎ£~ùO=€¸XFQÀë8Ë\ã’,ŽH’Dþ¤?<-ûJ$577EQ³Ù4¦?¤NØÓ›››££#Õ@A¬¡ˆ®E___ÏMŒ¼“5 ëëëKKKÀOWWWlc˜ÈañQÕjµV«åÆqåü•ËåÕÕÕÛÛÛJ¥†!åêÜÑ»r D †çy¹\þøã‹Å"@x—çÏŸ7›M¸jµúøñãz½^01Ï$IVWWÑá;??‚€–#Ϋ¶f»SkúÅ °ø m¸Ýn÷‹/¾ ±)t”%`Î e2ʦ@‡:~|#ròÝn.ª­Q(ȼ¨ÛÞÜÜ0Æ‘°+qϹµ¶(•¦ØÏ·€Á ¾IÝlMªx?2´ ¡ÉÕétNNN¤«ÃáAX}~~>ÏóF£AÔ¯ðVu7œ f‘ÿ5²T¨B ÷ðr©ØÎ A"+QÆNø—ÒØ‰÷§prO1¼ãÜÜ„ÂX¶ÜŠŸ „È&´ŽÎÈÍÓ*8™váQªéÉÚ$úÛÈuNñMTÙbÓµÐøÏÒ‹)í’)×Itþ/Þ•½¯`›SåÏŠ×T \§´r±“Ù<ž–J( G:ùvˆ D j馥OZ ™çùüü|»Ý—ÒG,“Ú4ù«««GÑâ‹ÿì÷ûqkrçÍÍÍÜÜÜöö¶ ÏÜÉÅÅÅùùùN§ƒBiÇý~uuuccë)ÀØŠ¢HãÉq~õ«_) Ãp}}È ·©5:ÆGt“fi7¹0KÁúÏÍÍ}üñÇKKKÅbQc————––fggÅ®‘‡Ý”!õââ"q bp5…ÝÞÞîìì|ñÅyžÓäyñ;ôèèhaa¡^¯gNe'!õ¦lÜä6˜66ÁÛ‹‹ P¼Üzø3›ÿšØx _þÓmŽg`‰J¢Ã¬û©T”B­V«Ýn«) ¯0 kµM¦———è‘r¶a«Ë^$ïË.éÎ+¸eˆ¯bŸJ¥rtt„-æ>ƒJ¥B,š$Uáëè£H@YC¤t•…ŽŒšºNfBc ž/˜}êÚ ¥(™›,¨XWüçùVÙûJ¡›(+ä{Âf/‡®mœ‹J6ïãYx>ÎL}”j=Æ®#Ñ.÷ãrzX:s¬ôÌæ«2:Qo¦õâÔyñÙãñ¸Õju:Z>Ñ€-˜î0f Ú–´X,¶Ûm¼ÅÅÅ=ª„’¬1»“@RƒHsSøÒ†6ÝK$¦F£q||¬f&(ï …6ãN¹[E< FSÛ øÃòrØàˆè–a ‰Àm¸þš± õô õý¤®7&MÓ?–cÇ_¬­/}_¢SîZmJŠüsƒ¥^6%·¹ó$$ƒœc!S¡{ƒc­Q6+>²1vzHÞ{Lχ§rÕC'64¶‰C1 ¹TŸ|òÉíímµZ%®ÕjãñÁß™™ê8³³³ÝnSu||<â8 hÃñÁ*ÍÍÍDàØgggqÑØ# ïonnšÍæÝÝJy°ËËË Þ”]Ù\ >GQŒêýbœDnþ˜j[_ˆ-^^^&(SúÓO?¥óæË/¿ÄÖëu”sºÝ.a?e iêãíU\+˜Jg–eTcÙë$INNN~ö³Ÿííí‘ŠŽ¦(î:¶žöØFœu:ÓÓSLsÀªaÉOu»]D ð”#r#ÇrW‘EÅ @+ƒÍèñu!):ÉüŒî‹œ\j K ᦣÈØ &t·IH{½Þéé)‚b < ”aˆP¢s&`ˆ5Ç£“JGÖc”š˜A¡PØÙÙÑŽ¢¨Z­¢A¤½£\£;V¸¡„*îg6S&tBz|9„#^X‚Ái…Ö-(  ®Šjh-Æï\‚hè¡ò–K1¹gµ戜ä> ¯`s tÓr£Gâ9|¬¦j½™“]ÎŒt²žYc½p>>?rÊmµçŒ†¦\b›Ô–á+u=8û÷ï“?Ò ö´··‡B»Ýžœœ†€E](0.ø:ÑK¥¿û»ßýŽ‹T©TȉÎÎΘ=•ÛtEy…ÛÛÛÓÓÓÕÕÕW¯^iéfgg5»,°nÞÜö ƒjµ EãáÇÛÛÛØMËê—æ2(ê£m·Ûpú‘„ðZ­Ò¥Ìè§0 +•Ê£G°À°A"tEåÉ#ëöR¸¡ç$<88øþ÷¿ª †•PQ ÃÙh2¦{÷î5›MµæÒá|uuÕétˆ§Æw»Ýååe.$X˜qÊ åW HÙNBò¾" }p8åC×(ãÂ5ÁP‚Pj˜œœdÁ`€n53q™xÑ#ÔŽ¿§iæêêJ@>.Ÿh3J¸ HˆÞL ½È)êq[}hÃêeÖU^0w±Ãˆæb›l ƒ@ÐEQ©Tš››“þGꆧñF¤ç’6é“my[å¯Äæi‡L–ÏLqal3fumxyé¦+'¢FðÙï÷!ï+ƒÃâ²^T¸b7l™ÿKS¸<OÆãŠs¡ó'[ΩRShäZçEÉ MÞ4wbb‚)çŠÅd—U@Qv D¥™ˆCc…:ÎW_}uttT.—É/rxÀ]wloo”ñÀ{{{çççw(ÆA³âÌõz=1fy¤©©©ÃÃÃ………R©tzzÙ•­åôdNn nçÑÑ"î@!â@(üë/~A½)Ïó£££z½®³øíoU*¤ÓÓÓ[[[àJ®1 jP _¥1¾À¯ûêÕ«ïÿût´ ©?›ï!0fßééi’$8 —ŽŽŽè©–oo·ÛŠƒÒ4}òäÉñññôô4*û¡5Ljï"D"2Áo[ånÇnЇ”‰ôÃη’ŽŒF£“““‰‰‰ƒƒƒÓÓSPóÌ ßUÐÈ ð-7j‘ªR…B¸›%ͬ[ #¾\ý:š< I(µZ …[t"EÕyPžD$!&&NØœŒ¾Š’ªEçÒ¨á¨:ë]øÌÀ:üd°DKx÷W¾ê/ÂîØF‰°°Eâ™’d‚žø0BQICÓreE®®®ÄcÀÐdÖº†l¶S©ÁØÆÖcAÄ7BXÖh48a° 8ß¾ Éæ®ÑTqñ^¯×ív1spDùI†Slˆ9nÀçè舙ìÜÉ4MK¥ÒÂÂÑ>ž‡$®Z­Ëp`ò0ß&ê³³³F£!Íb©ªª’ ª­°ÏN§sÿþýF£Q(Þ¼yÓív¹ºâ÷SÃVÑ SØ8hÄÿ …ÂG}ôàÁƒR©tvvF`µ¾¾ÎT›N§#ÐGÀ¿÷4Þ…h‹9Áqùå—ÿò/ÿÂÌWŽ#|nžb7•QŸxMà €§ÈÄ*=þ¨;1©ëëëÕj52ÚFŸ¾wޱt;|p¤ŒUUi…Qª!ˆl%ãÂÀÔ¦ÎÏÏé<::¢ZÇIæôâNTC MÚ”@–o¡ãŠÅW·ÒCÙSžœî¬ÃÌÌÌìì,Ôe€ð Úí6wì^tú"¤ ªLJ·{dⱋ¹ ’ÀÔ%ÚH¬tXf‘sÂÛŦ§¢HV„w%;Å´‘Ó„ST÷AAÿŽÌõf¦õ3111 T‚-˜®^n,غ®B'‡ H]£¶Î„b=n2hKbê(bl³²ÕjåÏÙÙYØ+¿ùÍoB°‘¿Ïë­%54]!µËp{[­u=$Ïy‹Ø40ÉÓ€´2c“ÒQ8QàM©<\__3šAµÂÔfF±tišžœœÔjµF£g7œ†‡þDh“»vww766§¦¦ö÷÷Õ @íL¸'SBÅJ...~ãß(—ËH}åyŽx1‚ôº?\°Äi+LÛHuwLÌW_}õ½ï}Ù‚|¸§bã hé¼qÍ4¿G¤'ú°8hÚû ý¡=ì÷ÆÛ)tâ-¤¸/|60>0×AsaSAŽÝÄcÅ_™ébª:Ñîáá!ƒ’9l…>ÑE‘%%­#ÕRØ(’!]õÐÄ”I•¸&jÙÑï‚<ð©„€óÊúaqy`‘]d27¢F¥Þééi^AŽqêçUª,MT™`ÙŸw5%A㪪#‡£çÃá i­K¬÷?2^±k_ ÀÂ7á"© *à#±önØñ†\3mL`mJÅb‘>ØÉÉÉ­­­‰‰ :°ˆ°„ÇyÑÕ˔ŴÛm82z„\ÄR°MvS¯×>|\K—¦)SQ¿øâ‹ÑhT*•8ÇhãiQVäð Âøp_6766Pæ£öL€ÃÚz"áj¹\~ùò%ò[q?|ø°R©0ºUî.qÓÕ³,ÃH ˜œœÜÜÜ\\\œ}þüy¿ß¯Õjkkk‹‹‹777Ãá00†]fÂçrxÓçá¶DÖ§Á«W¯þå_þ…hͬТº¤åNt=BÓ*ÁÖëujg’rUMŒâåË—www‹‹‹µZ ‹/*¯¦ÏÃ8‰Lò‰H6v£Ã"Óõ–iÆVWrD[òÁÁÁëׯáÐ{52&#éØF"*ÚÊ[„£ö™>:‰ØŸV†ö=¼¬ møV´ „¹/ õzb»/-þÇ Ûç½cjÝ0w6ŠX9cš¦TQ»d@½*=¾–˜ñT¼SþåsCþÐ{)ßÈQ~ˆ_™© `"1Rº{ÁûÓÄ2#¸ûà ÂÞF¼æÀcÞÜÜDÅ•‹Šß©z³ê£|ˆiHš¦N‡„îìì Áb]Îîâââòò2½²Y–aVîîîžùL_êR[˜ÒçÈ ‰à‡•4„ÖÁm§˜ûêÕ«gÏžñ¦œ7j5ÄGÐ¦æææJ¥ ª‚JSÓ;%xôùhÌ„Ÿ˜c®‡*v*Z>#áÕ$ÐFž˜eTÅWHMíà²r“»âÉ.Ǧ[Ò Zª L+¦’´ê¡#ÙÆnÚ‹òúÀ$±dAän†ÇI_n¢ú™ÐÒ‚*’‚mº)„¡i­€ºL¶•ã‹‘R_Žêâ¦MøÂÇŠÔô2jm^a£Ñøîw¿»¹¹ÉökëÑÑQhÍŸx¶ÐôŒ”Ó‘™>WžçÝn—ßÂÂý%_ʃ‘¥ÿ—ÿò_¦¦¦Úív·Û…©œ¦éãÇ—––vvv€‡™ËÀŠ—ËeàÍœ4Jj"k8$ë¥Réã?NÓ”¾K¦ÆzcA Fš,JjBÊD÷QÅ#³®=Yú UtNÓt8–J%be-‚_ÆFÆÕÌMª€À30z½<%˜ÊýÈ%~+iÉŒ A;‘t+:üÊ7£üqZ·È#ФB§‹(|Êû™À±™2×ß'ìÚjâ¤lù'8âØ$ØSS­÷s”À“óë¹…¦s ¹l|ìüüüÆÆá(íÊh›(šSÚ,ÒÇÕÕU³Ùl·Ûëëë¸;*Čƻ½½eœ2ßB#MÓb±ø­o}kii©Õj]\\¼zõŠ2ÐòòòãÇÏÎÎP8`óàI+jzzš éèè(5í‘,˨Eª¡—ð³rL1‘âCîÈñª~P||õêÕÆÆÆíííùù9Ê¥ög6 ¾øâ ^!7J‹p“ÍÍÍÌÎÎîìì·Öj54E™aÁ‘õà‚Žxn€WWqcss“Éííí««+X¦õzµ×© ÃÊè¥Ns]—¿ÝnÿèG?:;;[¥`GÖ6AìA0A~F¯×›žž®V«yž“¡s¬÷öö>|Á›7o†Ãá'Ÿ|ÂïRdŒÐ`02‡ ¹ººš$ < ê°*ù £fºÛÛ[¨¤©úqb¥hÎ_ÊD¦izuuõêÕ«ƒƒƒáp(â.šPBx¹Ã ÂÒìdgff åã`X¹ä6ÏJ¹…\¯Œ˜@h7*y äbýƒ¢l€Pôx*¾ÆV†Ö,¨w;11¡%­^hšÚÌÍ„ä¨%œ®¯î¸p÷ܨ”±M]tN@™¦»,Oâ=ÕÑSͪ‡V“½ˆ?GÐ¥ÐfÉPÝ“0 ÎA®‰{«¯ÖëñU1¥eÛ¸J• Ÿ©†AÙÛÛÛÝÝÝÜÜäÌÝ»w¯Ñh À« ¡ÉH{ *@½^‡Õn·www[­aÅÑÑé÷È”Æàsžž ãA¥RYXX˜œœ|öì™'ÑðáH‚P·ú¹¹™…îÀÀéžžr9 ´æD+èvôÑG¨Í#P*ÂËΪ®OÙK¯‰Ô·8ÖÓÓÓËËËQu»Ý(Š»,˜Ÿã=77×ív]yþv±X<==Å-•J%4àéÓAÍ]óF,(9‘©+é#¦ ¨@«ŠO✄ÖZ¸æðÐéÃ2S¡ol ®ï"ªÜ)ʃ)¼Â!¨6œ[,²$Ù‹ÀºX¸ÌMm•¿ðEeWÙ l±Ô"'‘óA½SœoùÜ)áO¿ß‡TI3;;K°À¤,ŽH¶œ(IE ;———ðÎÇã1=(R ðñøñcºêÏÏÏi@žžžžž^\\œ™™yþü9ç€| \@(I©°ƒ¡Ñ»ŠÅ"À°üv=ÏsˆZx6¼B»Ý~ð༨ôdTÒ(rñâayÙÊv»þo£Ñ I Å›ÅÅÅÕÕÕ™™¡dìT,Ç-‹æçQHÊíøÃ+• ðgƒ¶^ÊRY–©Ûm&H¶I’Ôëujÿ>–––0L X™4Mëõz­VS' %´áñˆË&Xa˜*EE®oùƒ¼ÏC¿Ãáððð">¤:‡z†/a;À×_ǼÊOÓá8YL*‘@QOT(È`´Z-…~‚€ÆqÆAu´#ÏsREª“““Ò{ˆLh¬@€ofd·ÌÀÕuKÑ_ 7Xj˜ôœ´ÔFû¨„­Ê› ˆê¯ëñ[‰ (áëj‚Uœ"•ýÁx>äSCÆ’mV'žGB z……$2©“—ÕyÚ=ߨ×ëÉÕ‡ax~~þ‡?ü!Ë2æn­®®Öj5ÔxZ%Ý•¦)¸õåååëׯ'&&Hîðu¹I÷½Óí d> †Ã!‹>== ‚ÎAÄÔB&P± Éɘ…Ä477'¼L¥F­›v:qú÷qC{ôèÑp8dGRkgei$âŠ*öw˜ÀþŽl€Ýíííêê*>éÙ³g¨GmllÔj5ø¤oLs‚8橪òX"²AÞÌñ•Ç*ÝÜÜT«Ut`ÀàT¨‘#œ››[]]Ç;;;Ëˢ~.áÍÍÍ›7oƒA±Xüè£w2 ÔjH½^¿¼¼ìv»ý~¿Z­ÎÎÎB ó§È#))¬¥®=P‚rý:=mIˆMÓùÀi$ G>X ´þðÚÚ$a¡êóW‘ŽXË–ak¸2{{{øÁÞ˜WÊô: xYö7³y3Ð÷…0¢ë/nJj†*©Ç¦Œ†»âÛ'''¹ÚjÖQ(ÀEó™`h|QѤÄ:ô$Ä*²&Öá]šÓΜB`äæ*)‹œ¦¨¯êänØr`Ry0;X5€pIÓ꼎l†¥0¹À推0éOƒ§@n¤l{{é¥0 ~~ûÛßNLLd8îîîžíììH6$5Y!ñ`(õz]r}GGG±Éž@h:88 ª  ƒäÐ r<;;;¤ƒ*¨$DSòþб;I.ïHâC76qA™wÔ5#¨ œˆX¹\.•J½^owwwff¦R©D'6EYÊP+ÄÌÜT…<ÏŸ?þÕW_±†ÄJÊ\T§§¤K°ÃƒA˼¾¾žŸŸ/—ËõzýððM1*ËL®Òúì³Ï>ûì3.‰çÈw"[©T€«ØÐî‘©Ö)?­TBÀUQÏMbóZ€\Åxà¡=]*•ˆVÆãñöö6Á¾âY‚¸Èš^=z>4µ6ŽÛ¹ŘE"Y.?,BŠü .¡`#f!‘ðNºq¤4ª¤®®žMÒc#S7Sø;µâ îÀ.£p»¡y\d_õ–WÖ™‘“Öëg¦Û£Ì=Ä.¾If¢ ’‚‰Mq1´éX‚ŸTÒA¹ñææFDþÐ;•Ó §OLŸ_!p©ê2iš"ë1 hk`É2SíF¿ùÍo¶¶¶ªÕêÊÊJ£ÑXYY2 ¦®T*PŸi©Ûßßÿâ‹/  M1*±`r ³³³ËËËI’Ð}vqqÁfst¤xlö†¤:"xöÌÌ ƒàŒ¸c¾˜Ý x.ŽcMÇãñ¨+ßÝÝu:†ÂJÐJ fsaø(ÝL üARùáÇÅbq{{›  X,–J%d©Äa›hÆ×W§*7úUš¦˜*˜® àÈm4)Ä&Aœžž¢Mžç9ã3...fff–––Â0<>>FsYwoaaa}}ý³Ï>ãFnV§—hƒµ°°€Ê;_=77‡nglcÍIŠÙeŸ ¨v‰w¤–ŠF«|0W«Ýn“.Á!en·ÛQs¹WDQôÙgŸmmmŲ€pqÆ&­#¼œ)D™›Š"_:,í½ÀvD¼P2 Ø''4åÌÆØðÖh„ˆãYG5œÌI§$¦«-”.tH [5½)@R¤0Èû–kÃ&*¨)Î`[hm;6cCeKÕDâ8¦õ,wC›űyxržC}‚*X¦&{â•©/¨Rsww777W,›Í&ÉNv ”ÓŒ&7£±?þøãr¹<²9(µZ ^\±X<;;ûíoûÕW_aþÄsc;%;Á»,..âs:7ô‘ŸžžÆ€’Ÿ‡Ã••/²ô*´ˆ!«Gò‘¦Õ«®Jˆ.y>üÕ«W¼qFAñý*Ú"„‘ºè4sMOOë[ߢhÐn· …B£ÑØÚÚ¢0:99Y.—5øOX›R%°˜ÅííígÏžÇã¹¹99$l:õÀ7)ÑÌÎΖJ%Tý0÷D¸8ZÓé_'ÜØØ Ò§ÞiOÅÇP´˜Í%å_4ùët ÝÀøþ`‡Æ­‰ŒÅ¿‹ÀA±{‡µ múû~qqqttÄQIMäþ£>úÆ7¾1??¯ Ýã±iÿóóŠ3£› ά«\¹ËÍîT§!?_0©bn¾˜S‚Dû༡ÚD®ýSö…ÌÆo™²„ÐNrÆâ„«À56yY´ÜpÒ•ç´€ô%ºdnU2ûÀÕè9ä…¤0/禔õÎ&SŽMãA+_tè¸îah-Wïg3`èüáà… jÐ<áRAÂiW«Õ««+ÊðÔ¤çççQòf_¼xñ“Ÿü$ŽcfRidn3‚ëÇF‘ WIéwgr A5…|v–V–eÅbd·ÛíÒ!,öóèù@l.‹" :B±Xìt:ð¼äë¨Q@Èb­¨O«75¶¦qÜÌfÌ…(3š˜˜XZZ¢ñðôô–üãÇkµ€šT´Sëaà9Å Š­ÿv4½~ýúóÏ?‚€ô'6É*Î誴q)w(w LÀ6°A^Hî0¨ynn®^¯///Ó°í/ƒrPmº;±åry{{›¥ -%¶…µD©G^94XQIÁئÀäz•ÑàÂ0‡ì5V€¡g$×Ô(XêÅÅÅû÷ï3†VÜý,ËnmŒylšåJ—± |À1Àò0m¼;,6öp“ŸrA)V!v¶Óé&5…™P[æL žÜDSqÀQ-..F6²D;´–õ3‰»é¶*”Éú nRz¨‚ï»ÂhnÔPæªi±27*VÑ„žL!9af°> ¬©){)JTÿü­€d…Ù@¹···N‡®’&Vmcc=³›››J¥²´´455…BEˆº"­o¨\.§i: vvvþïÿý¿¿þõ¯1yKKK‚6¸EÒ'H’daa†••ø&ý~?MSŒgEªÇqnà:%IBà @ÅQ–…p b·Ò6¤þ/–>—8J^EZX;ø ŽEd "±þ”±>|øÍo~s~~~;ûàÁƒ ª«â| Ï67ýµj’B‚È`Ç#'Õ™¨4¶IÚXrc]BS[æï ¢uPå§çææk¢÷­T* äM¬é—Â4±p¯×CIÆNNNbñe_äï"XÛ;›T:aS#ë0Màœ»€E¦SRW"Uný˜®³>9´añœÈ² ·$ û*=ë·ùÅrPä1ßÄ#ø[E<ÂvÕ‹Þ¡¹:X" Œmzjè¤õc“è MÆLÂâ@©;Q_¯Œ’íWজh/ƈ®—Çÿã?þ#(© (%¶™™Òi¥OØDØFd wwwFãêêêÍ›7»»»?ýéO¥;ι999)—ËÀ±d¯årymm­V«ìŒÇã³³3¸BoÞ¼! ç/ÐJ§–¹¾¾f, ù]¹\ÖœNF¶ ‡Cà[¥ ÐľüòË$IàÓ{ׄsÓ½<ÏIyx)HØìÎÉÉ ·–CVž>ÊÅÅÅ………¹¹¹ßÿþ÷×××°ˆP°kŽ œ;ûâÅ‹/¿ü’· Ý +c‚ œ%¶†Ry¾B¡°°°À÷2µP(T*b1RZyS~…¼Z&“îQÝ+‹0‰¦—Ä} RˆL,H-µœa3¸Ã¹k²•Ùb˜#Ýì ŰDÍbÞp/%qfÔL@0éd„€Î=­¡ë›Ñ-Ëó¼V«¡Ì'½ÃÜ´¤ýB”¤²yë J¹SÇ;077‡{M Ãô–ˆ¶'¸Á±ÓWÀôlôå£Ìd”wóÞQ8¦*S`|Z¡ ‰p¨ÔTŠB'ç’¹©3òÿÚi¹Pjíl: _©u<&Ö * -Åk¬µ°ØÀäúÉ¿@O PA¿wïáôÚÚZµZãz4™9C ÈÁ˜—ùüùóÿøÿ888ÀM¥nìÕåååÚÚÚÆÆU|ö€‹wzzzzzÊ%_\\„yX›8žƒÚ4Îô¤&Ïó~¿G‰Pëêêjee¥R©Ä¦ãƒ‰'.¸wï£$IZ°SzÙ)Y >¦( ø¢”™©þÈŽäy^,?~Üh4ÎÎΰ˜õz}uuõÞ½{¬øWa‘j2rHT*@£žØP{Šx)¬À£’ à_ˆ)øI(ïøž‹‹‹Á`€'&å•£(ªÕj`†(Š Åª›esÛ ^F¦õ,=?iËp‹pQSšÔºéÉeµù "q^¯ÃÆa/¸t8 µ ,ê6 q3QLó~îvâŽjed’6Œl~"Ï36¦R©ÔjµHSfff8Ÿ²ãX[b.L*üíÛ· žH¾\ò¯þ꯶··µ\Dmb'&F:a³DU(ôË«¸!·–dYFU„ßé²£i¯ Ý . Õ  [®ê¡41|í/sÓÀ 6òH¿K, €\eGYèÁ` Ò»vqaaú:ö¥ÕjMOO3ljS2 ˆ­Êå23ÓÿíßþíóÏ?‡²¬å#c Apÿþ}&jꇇ‡° AOÍ"[[[”À¸T8ä±ÃY÷’ðò.B‹Å"Y9Ó§öYgÎîôôôãÇ KÏÎΰnþonnèöÛHMWxK¾š³øõ×_?þœ$Wq´ø‡±Ó†õM¹ÞНy*J‰ K# b†!¶†¥§aÌùþp8\^^ÞÜÜ m™P‹`V2kNš°a¹L]~²"©îÍ7‡32}>B¼Üo±AY–á´ ªÌÍͽzõŠI·òýaV*•±ilò™„Ì¡5Àñ‡§Bÿšÿ¤ n¶2)Öª`Ó=8ÿ`  rp˜c'UŠÇÅ6›ë xÊFß»wïË/¿ÃF@Pø¾ø}bòXrW‚À"7”3ã3D¼Bê†ÆAhé½õQšÆ/‹Ë.ú™Ê“2äªm«óVeD–2s‚j>OŒÜKY1Ôz½~~~N]¿Z­®¯¯SÕ†EEŒÖëõ\¨‹@éààà¿øz/Åb-$2fff”†Ãáëׯ?ùä“åååÁ`ðâÅ ¾±ßïS–ÚÜÜœŸŸÿÝï~Ó7¶A˜¤åø¾‘{E‘‘³Óé,//+m·ÛY šZÒ4ít:KKK<ˆ¢hww—IߺW,pB´Šwƒ}!×ÈlÞ}d ÊÎVWW×××Ëå2C ã8n4ˆmAn’À[h\Ya‘J ž={ö³ŸýìîînaaÓLl•˜@;ǸZ¶,2¦±"w!Jò‘Üù‹‹‹R©DI7¾,bzj‚´d»`êÀ£ªIÑQàgˆH¡_¥"÷Ì$³3SM°¥,Lð b[P•>ðÐ܆,Ë“€.#ÓÏŒ¬$I˜ wœÀ 3ÄÓRµ÷A‡„«‡ø'*0ZêJÓÄÿ—nÃ, DŒèOº7ú‚çÀ=€\§6n=vÓt„Riƒ<*ÅvßÝÝ%²ˆÕS¬®G=ŸžT¥åó²°TS$À)Ã!­JX€IDAT³¨Sé4±á”Ãáp}}Èü‹•¢¢O°Z*•VWWù›Á`€öÔÔPáîääd¿ß‡K©z\fŽZ­ÖÞÞÞG}¨D•wuuuaaO.•J¼®¯¯)±CTaÑàFQ±.•JišÖj5Êç ¹‰HT»Ý.­Î”½¦§§_¿~ý«_ýjdãˤю™cÒ æÐJÍS.á@½Jœ’Žãø£>¢qrww—®šééiHäL¸R•M`¢:¾îÕ«W?ùÉOè&Ñ¡TU[y–¨4xrOOLAH6BdA arû¡“gÔÀoÍTŒ”S€ƒ*R•ê…6ÛB8šÀ”̉+  À˜ªª‚,וÀ­àtªP’ó³D ô$‹&ýU\yHx0M€jŠ<›D„2Y&rIh¢˜Ü)À5}>«W,5›‡§šI!ªž‡—el-„{ ÜšyÕ°-^ˆ,GÑ3ĬäÊgÖ°¡¢êËüÌS“9Ž–»"/bÂÀÕÔ‘¹i£¸÷± «¹!õre”or§_ŒýVþÂçÌÍÍÇãG)Àë#°¢M%è—ý~ggçä䄼š@>Ôêêêôô4rQ¬#ë®;% ®æÓ§O¡q­®®(‘oÒDŸ«P(¼~ý:³N’µV«Ål.ÌõõõÒÒ}õz½ßï”a ‡]ªV«„Td~ñ‹_x-M•{4YOîZ-‘f`ä[–]2ääeT@W‹k³´´T©Tpžâ%sL±7%äÍ›7?ùÉO@ý¤"Ÿ˜<†ê†‰õ¬bÎx6 §ôMú|úûÐ&Ô½+µáðh6°”ÒO¨¹zà;›Ö™8)K¾=6R~läSœJ¢tLP7;¢MQ¶"®å6å,…BAX¸Oy8ÿ”ÿXsü(ŠBZñÂx)xX>f‘eïõzŠsÓÂDb¤AÒˆÚà"œ(‡ŠB!€ë:Á]à·r'[™^`n,¿ÈtÁHx5À53Ia¬DS>§”+s#*¢(ú£’© tŸÊ)5ãMTb(9BüOè‹h'¥&2¸QŽBR…,ò—’yPÇubßéé)o¨26iK¿ßßßßïõzý~Ÿü‹4³ÓéLNNÖjµ$IšÍff£“ðó¨PÎÏÏsš¥-{qqñùçŸ___öÙgår¿Ýï÷aHpa˜N†¢d××׃Á R©@ùŸŸŸ'¾#<¡ær{{Ûl6™0˜ÙJð¬Ñhôøñcˆ`¤ N¬¼›ÜFÕ²”Gä#›Pw>O¸ Ît¡PxôèÁÝþþ>[377·¶¶ÆéQ4”8©U%wyžïïïÿøÇ?ît:°ÌÉÂÄÀùILQCÐud]Á’jS&(¾¥ŠaK4‘›¬‚‡8ã+SLÆ’Q®â·¤IÀ>ªË"s¾ʞtVá¢Ï¥ŒØcXXa⑱I§â/Fc7L³`ò¾¹õ”àtóH¦àÍžž†·æÊÿÅÐp¬a„îíí)U~Ùn·›Í&à.•o}q3FÃDUÂÀ¯ 6¾¾¾ÞÞÞ®×ë(@Åš™™9<<$*mEMôÍ›7JKKK®è@íïïs(±Œ:ø@u®IcGÁ2Ç+¤Ljaa¶&€O7F£¡ò«è<øUÈÜf³ùýïÿììŒøŸãœHXû(Ô¡ÌMœ$ôÐÖŒ+ŠL¬ß^gÌG ¡1W•ÊŽ(¢ä&ˆ»  ìSá¹Éjg‰¤$."ä[æÃßÌ‘M0έkO÷SÇð_Ä)lì‚ê$˜$òVOOõåHòŠÎ kØ>q87í‚,˜C+½VPN‘u+r×ñž9æØæ´gY¶´´¤m•‘RGŠHKªQhÁån…Ÿ°†Äb“a=Æ65#³†ùD`mhšJºu¹c· qZ‘9E‹À(é¡)‚²Ê~E Ð*Kªî®„_9<åÅÅE³Ùœ™™A –€ëúúúüü\9,^…º 'P‘/…˜ÃgÒH¨éÇÐ#0µTôáÅ f‚«—52á”[Šº}ýõ×}ôQµZ…ÁA£ÑàøRðBq8Š¢ýýý“““$IVVVˆº±Œ>ÆIŽ0›Ê-ÅŠ…6Q16Õ-©PÈÙÙÙ>úˆ¶N§ƒ­,—Ëd©wwwL#§ëäi‡½^ï‡?üá›7oªÕ*&š‚â&Ž»¼={¡© ÀNj¯p>´1BÄ©›Qˆ/!ÊóM…¾kßwžD2d÷ùu¢†ÈúlùIÔ+ÿ Áˆ­$,ÙÌáÀé«Ê™¸¹vÊtTR_÷ø/^ðM7vd3ëT÷Ì­)ÚË ës•èÖ𥪌iv¼P!ƒÈ½dAW¦;5ôÌÄTIWiž/•J‰u\‹¯™×ØÍŽŒâ Ó‘©KMØ0ºÔÍú‹Ý\Ä$ŠŒ¡)ÿüs=~®ï„ýñ%3Õ1µëQçËÇJ…ûB4 Ü ¾Tµf¼×›Ú¡+ä’ÙÙYâPÑt+ijòØPÍ€¾“S”ð' „g¥@¡\øƒŠ†¡õÓpI%Q›îUj#©úÈ+w]Âc›ˆŒÈJš~QVl’-ïœdl­-JÝY¥¾¡S³RÉ96å-!îZÇØt¯Pz þŒ`õÀ˜fJ!ÅLó!Qn«ÕÊó¼Ýnã'qÚ———´S†CáìŒ( DVz¶ sP,Ë岌Úâââp8$ð¡é]M°¡f³ÉgòúÈ×¶ÛmzÓ`ÄT«UF£Üô×ý×47¤iŠ 8º1‘/^LMM}üñÇ}ôQ³Ù<::R¸.gü›¶¬º”Äd¡"©Ù|)‰Ñ633óøñãR©g•˜nzzzeeŧüªÇ&ÿÄüÕ¯~õ“Ÿü\C?8ÝLº£tÈäy b%;:…‘IZóšã:0‘œÔWÇ6)+p㔚Ŧ³Ùh’Àuüˆ‹ ìUÌgY.i8Bd4E]ŒEàt qÏ*ØŽlŽ)ÆÂ#Ç aäò…'ðâôçÖÆ¬ö1<2›s£8ÎßÊÐh÷äc“I€„: 6ú3q3Œ*âKl¦‘ÿ;e5Ãø²oøþ|ÓÈMVÑ °Á´B»DÈx—h¨ È8ëŠÍ|´&Ö•x=±±–Uˆ¾”7ÛPo<¨82®“““ÄS¼6›Ám¤ƒýõ›››ååe„\ô '''èí±j¤ŠKžç”Æs›÷IòOM‡‚±n{¹\æó»Ý.:|b¦°+ív+@X;K„ì×ÞÞÞãÇS|ùòe¯×ãQìþè£>ýôÓÑhôüùóÐúq‰\H UE1%:ÜXgl‡¬ä>äÏjµúæÍ¼(Ùââb³ÙD‹J‘‘öšÃ´½½ýOÿôO ‰ëËM–CE@¸?‰×9‰!Ö„°ˆ W ®ÈÀ‘ioËhžíD±QÆc§Y*8Få$áå···l¥°áÐZ²7¤@Y·1vJ$©ÉûAP©TøF…*¡Ñª#Ói;‰sî]¾ª ÞìêùWÞšY¥¨­²’껊V¶Û.ç˜ñ»$œüÈØyž˜„ᕽƎœ©X„CN#ºô}ÎËyP¥…ǯ%qšÝŠÈ„ôe&»:úqܻՓPÄ¥ÊÎèÿoª© ÞÿÐ Y8¿¯P¥|e‡ÏWt¦w€4¦*PaXWH²ÁÞ\XX@L: C Jžç¬»ïÿæcIÊæææh$$cŸ˜_„̶f&?~ü¸^¯·Z­·oßžŸŸ+rQöZ·6œ)‚j¡rÔÑNNN¢(Z__Gž) ó³³¥¥¥(Š677?ýôÓ$I~ó›ßÐÆÙhŸ‹>Ž#˜_Cð" UÕ«4Mççç777é§ÃÒÁcÔ«owk¢péøøøþÏÿ‰SÁ¢ád’„ G“ÑQ}M÷ÙÛ¯Ü(,¾î¸Á”‘ÓÑû\.-pÓÀÆGNŽŒ[]JúÀȺ/ÔLƒ#Q”Ä «‡«SÛØTåna#~A ¦íéÿ¨D(¼FäöšæsRîl‚ + IÁ#éᄉPCÜÁshjU‘¨ÁBq¯×ÃÉÉ~޲§*$¥L…B2ñªâiI°PÓÏLøXi“’èÜ)²yh/³‰îc›óx^W¶ŽÐA•]tŸ³v*(;õù¼þ x¬"èØ&ñæÖ’»..$_-úŒœ6<®ä<;;W37uÙÜù’Á—Ømuuõêê áÄz½~{{»¼¼¼¼¼Üëõ°eÐç„z`ø1°û0Ê ¬Ìòò2¾îêê*‚·oß^\\ÌÍÍ•J¥‡"µA¹óÅ‹¿ùÍo¤@ -ªñxÌ0%©ÓxTä›_„l•ÖÒ4Eñ0´  ylUÐŒofîõz÷wG;ž²œª²öTpgàšc“Äcqš•pIÄ'Œ¡çåtjŲnü¤_Ò¢Ôu– O >¦g£Y‡Ú¢¦Ì‰NÉ-€+‹)ƒ«ÛûAa‘&ð8rZ‚zY«Ô°áÓÛbAZû0εpž£(‚ÍÇ+óÌ ¦(§{._çI¼yžŸ³h²û¶çÙ¦¦¦h{Ë_X„’°ØZ‚T˜fXØÀD•tëä(9P š¹Ù…A$ † ”W„–á ÆöG'1…üÔ¦§ÈÑ)íÔqÑ'gF€"}ð Ï"×@e&>¢²¦†äÉÉIšÔùF0ct‘„G‘˜J¾F€Í1¢œAUŽñÅ(áAÀˆàÅÅÅ^¯W«Õ*•J§ÓÑ'‹á Réš°üüüüââ‚ίJ¥Òï÷Aµ(¸ düòå˹¹¹¿ú«¿¢Z¹á矎.Ù.^‘µM’äøø¯ J¬.R³;K]\f ­Ñ¥¥%˜ƒãËà4 l4ÖGn ç ÄûÓŸþôÍ›7œQ=ø:GÜ—n#êÈmÒò5¹JkçRïÛ!f©œ¤ˆI–Bѱ@41¡eÈ"Ç]Šß—SÉÜ瀉 Šè=ƒLÒÃ2R‚ÉDjˬA—LJ9eÔÐÈîcc)âœsÄ×ϲŒ:ŸÏ«iJ„;õîp¤–‹µX,RÂuaˆ Ï9Kx&žPºµúЧ®4Paf`CƒBkx ]“Œªv‘#©(P­äÌ×ßUÕ²÷ugT‰œJFü~·¡â4Žxl8ŠÂÀPTŒMË´"7ºZlÇØÅB¡€¬pl±XÄ(H‡$ŽcLL†Ìò;??‡¤Îbq{½3 ù£õåRþë÷û\N,ÎÓÎÎ`$—qá~¿vvvtt¤ÐCh(xg`õ# ¾kaa¡Z­ÂNN’„ÑÊ,ž>}úàÁª«_ýõ`0øÖ·¾5??O,999‰ FŒ¦(¦(22ÑµÜØÛ^!@X@ÕjuuuubbbooO3{«Õ*£è„ËRà9F£Ñ_|ñƒü@,…HbR_1ô©\f ¡Ñb ¦³(j¸ÌJÀr–ÈQyüAæ,w³¾¥Æ eÁûœx{ñ'|ˆª³Íê‰1Ÿ»Yª‘5Ÿ#d¦® àÀœ²§ ó£&¡(Š1uD=9#°ò¢ú®¨Éä&‹'¤¢½h:ê˜lÍ ”+Wåçåá¸>°s˜ý16©XÅ™ÍñÅ²èŽ ï–CÜ´4EŽ©›ïÙšrH›bAÞgUw¾8^ß’±I#äÆÁ™%°áò6#ã£üV#ÞOb=lU¥R)—ËôLɳ‘“µÍÌÌLMM ‡Ãb±¸··÷ŸÿùŸ½^ù zD“ U‰ÜôJ‚u–pVØc4ÿwvv¢(ªT*óóóD¹Dm‚„ˆÌiŽáP")Ãjp:éR<99¡§çÉ“'Xf7U*•»»»ËËËŸýìgÝn÷Φ&6¢Já€Hd<1IB^Ôì}{¡+2NðÊÊÊÌÌ ÓY„‰‰ + eÊMƒäq<ïîîþ¯ÿõ¿¨C¡o—ÛXPM!2¥C)¼æìÉÇæœ¨‚©…FõdÇN}%³A,$2òyxcn…kˆ†îÃ#ýßôýi)*dN Èm©»­Ø0pâ‘“BR2{–šRlú‚÷G®)NTV(¶DfUtÆsŒA!•Щ„§M¥|@[I§¡rÅ> Z*ØäPÐ}úë  &&µ¤“ÏQá« c$ßàK·êi×ÿÍÞWÓ MdX±pâá16ÿïië—µCÊ*ubÿƦÄiS¤'›È ¦iŠèá «Üï÷Y—ñx 0˜¹Øišîíí=}ú´Óé …ápH/¸X³Ùd³ù|%np‚œ ­¿œ—B¼áÕ«WQ­®®Þ¿¬4M™¬C-2±®}YÛ``u®P©¬ÕjŒ8}óæÍÆÆ¦¹ó;;;¯_¿NMÖ·Ærcap¯®®Úí¶tè%>@[žšæ*wÃ×€ÖÖÖ–——ggg…ßsÎJ¥ +®X@5áÛ`0ø‡ø‡V«56ÕGaºpàk…ÛÒ~ð³‚C'™ÛW§ŽL­R$ÝaJ9•åéb$&5£ 23´N¬Ì«D"¯âÀئ¥6È we™‘~s'B™Ù8,YÆÈfX î LFY°ÉØF¥û(Œu \›ˆ™f÷11¬†˜±éd6Ï<7¦4ƒðžÄsT_«V«çççyž3ˆ34 LžA-ÐÍ€Lâe²hì—ÐgÝ…Üé‹¥!?äWdeŽÚ™ÇíÝÞÉ'än„‡¨ä²ÔKå˪§äÆ^áœ]ÿ·È kÁD 8ù.z¡!ƒ`ª…ÇSj½ººb„2*‹|E­V[^^¦ü¡µÖ‘Báý3ýæææ˜Úív1”ËË˃kµÚÚÚÜìììÉÉÉÎÎÎÈM" MƒÿdãIý(rkæ(À-â6ççç¿ýíoñ9µZmqqñðððððP¡1&ð¯@‚«”^Õh2vBKÊß1¦´…FËZZZš™™ÑìE¶ïÚn·É»åÛÙ‹ëëëŸüä'Ïž=Só9q‡ïÂÑÏë 8'n•Uš,ÔVA™”Èr׌å+wr ž™™ï; lY싸ʑÑÖUkS$¢´‹gVÙKaòÐÈíòÅ!¹q sëÉÞï€ ]Û‹\Iâõ"+”ËÖ  gâââb~~^0”÷ÈØ^RŒ‘qפN~˜°@Q¹-€&BáœI€Q• Ò4•&² ¼Ìqô÷eN(ÁƒŒr rZZ%y;›¡u#†¦„q{{e®=ŠŸ–£Û€Èhî˜[¡©Mþàùï.³Á6±õ…òb‚6Ûív»ÝØÅ„£RJäüÑeaii ¼i=àI¦@£„333Óh4†ÃáÑÑQÔ㘘P¯×88øû¿ÿ{ø–Äœ8"uðÆï÷ý)¦V€ ¸;2R»b…êä×Î#×Ë’¹ÐÀHLªuŠC#PbäÆ5Gï7—)ä'Âð)0V€ãäôzS%£¦Q8š`€’ÁÙ5Þª^Û4µÔéZ¦¦JöÇKQχ¾ ©Ì‘ìL¬ËëëkÆ2*¶ ¬™—å///¡J‘ÍmêZn1¹_ãµò‡rfwúêÃcûãs¯Ì8V2C‰ —,˜ˆ•g{è‰"ØÈñw_!âå?w6BG€òvõ *PªèûÝ“Á̬eŒ=ÖôP_6ÂØkï‘ú¼¾¾>::jµZD¼¸ú$IjµZ¡Pèõzd‚Åb16àÞ½{³³³Õjµ^¯C×f DÁFÕCŒ¼ßÛÛk·Û­Vk0¤izuuÅÿeM4L\3Ÿ1`&Tjä¶··ƒÁòòr¹\æCgR°a±éÞ±ÓX[BÅû÷ï3ÕͣCˆÑ¡žòØLºÈÛ“““>l4Åb‘žJh;ðòs£‰+ëÌê÷ûßûÞ÷NNN”é°;XyñQ4J^‘Ø91 sE1¼à¶ÃCÈ>q“ÓJ­……¸52±FÄÅ8µ©©tŽ­M_­mÄÂþÜÊâp´rGÈô\œÐÑ©=¥&wŒÅŒÊH<ŒëÙ?#@¨¼ 4ÊGv¹kBÂC+& ¬Ìª†'i×ñcŠûð|I§ê}ÁgU!áLBÍ¡xG„ŸQ®'; ‹¸\p#•–ªH´¡DÛ×€g®]YDNy#%+ÊŽ¹¹yÇôW¤0v#±M[|\[ ‚È©bf*RS:ŠÉݬ:AΪ1Cõ”H.Ûp}}ÍÈfóF#8gffîß¿Ïʪ`Çñìì,ê16OPPT½^g¸ÖùùùëׯQ†ÁÀMØÄm…*c@­DFêºðñ8@ê*@vŠTeooo?·1ôX@í"· ×J²‰Qƒ;33ÓëõØx4gè@fãåyZ>ŸJüââb’$½^&éÛòòòÜÜÜp8$ÅS®455u{{ûùçŸ?}úTŒ_?Ü +Ù©ñû³ñûâ±ì²g!qÛ11ºŸ±‰ÛÊ´‘#³±ã¯«â9ò´Ü[îhÅbUý“$0TVX©Ô22™æÔ½Ä6£H63ù-þ¾àÆb*ß—t%—ýК«a=e&'¯Õ‹ß¦' ?w£.Tò’׉Œ#)Ô56þ-gXé°71D 'ÕýÇçÜÙ„ÝÀqYôš „õœrTª“è¤iÁ}䤢Pî8îï•iuþt„¡Èûï÷‘©Ybgè”dH½†¿È̸8•Æx 8Ÿä€cˆ’²,cÂø14ñGѻښŸŸo4 ”ŽŽ0IÄ´Q©i„Zfommíìì3¥"0¹2ü<·‹c'’!ýz±u½rGÖ³†ó)UQ”p9£(&óˆØÕ+¤Ò¹Tä"l°Œ¡°‡‡‡ŠyK¥ÒæææÈô¦UGÃr‘’ ±’eF6}‡çQ\8yÅÀ:Òñ7 «#ã…cë™ejÅæ!eyI—°Ëãñ€ÏŸøÀ؃)ÈÕò\yÝ+-‘ºî¼±Mˆ š/\'Pæ~lJžJ~•GÇN7N[`„†Ð:"Çn¨"ÞBÅ…27<’¨ 2âÀÿ‚®„$*ÜVz®¤$ …ŒOÜŽÀZ ó11qtttww·²²277 }rrrmmÛÛÛƒŽ¼ÂSq (ÿËj$Ö§ªÐ@%Ð4åêôÄ Ä®˜¦>™#¿Øl6YLš!Ö××9F¬‰zè…0¢nšš²‚94„+< ‚`qqQcÖ#c¢cM.//ÿõ_ÿg“»2¿oœöÑtbb,²‰):±üdü¾¦° &¹Ñg×R˜VXRâ´LUp䪫T1µZ[>àsËGÊ’ªÞêŸD¾VàNl’{¥fw6™V/¦Ü-°v*áeý~öùææf©TZ__ßÚÚªÕj×××;;;ûûû£Ñˆ”§ßïÓÝB.¶¼¼¼°°P«Õ®®®^¿~-dñé,ËNNNŽŽŽƒA¯×›åïi¢æ [­ç ,IÐïØ6˜šåËÛ¼l¥RAI&Š"ú®Iéûý>¤V¹%êŒÄ•www´ûÐÃä®F£w¢›çÆrÉ@s(———ÑÒbÂöhrrree…=UEƒÁ³gÏþó?ÿóúú¶±•Þ.4 I‚96Å„Eú{1›Ä€ [G4[OÜ}{{Kèªô–eW<¢P æcÿÌXÇr¥ÿYçÙ$W~÷›º1©s÷äˆ6`—")Z’Uz!›”äïç*—]V•-K(K¢e’K-w‹°&çΓ§ûÞë?œgÏ€ó fºoÿà ÏyÎs‰S“á “ÂfƇÊLÓŽ e°¦öW$A!´IKü“çµÕ[pÃ#k,—¯äÆÖ’Û-e"* MlšI]«'Ä'qƒ$€tq$^'ð©Ü(>äÓ|o¢3b1MSÕKáH³Ùœœœ|ôè‘>©Ò¯Ði«!Ã¤à‹µï$°’‹Or¿Uì¸ÞQ…j:mòž]¢„(µ/ µDÑQAY43†·Ðé1Ë2÷.--}ó›ß\YY*5==}xx¸³³Ón·©ôU*I*Ó‹ z£Ñh·ÛÛÛÛtSƒaeYFþÈN÷z=$:+• x! »8²QNÀ©ÓÀäãp·¢cRç9•¬g«ÕZ]]ýðÃ9Ìæ(P,ƒÁÉÉÉ`0àS MzqqñÕW_¡)¼¼¼¼²²òþûï/..bD´©ÿÂiƒ ­®®¢eJlÅ&¶Z­jµª¯Ü Âò£££ÿù?ÿ§æcÞi.(¶ 1ýbkî÷µ3u N’¯‡ðT¢2)5ŽLÎEÕnÑt=d•xNš¸H¡±g< ËÚzôDYXn Œ¹õ0‰¡+$<ŽÊ1”B+€æ6àC骧S¨‡.p¢ ‚lÔÊXsÂÈfÏ\__cÐ)Ï© -D•ä°;ÄG8YLÿÊxS%ï¢òÒh–Ý×<±”ƦÊ ‚ßétJ¥×_þ[9¯_]Õæª§M±ŽV`­2_·AÈ*ç®SQIœÂ¹ÐiBÊïé˜ú4ž<ŽÛŽ '—Mª¬¹J^Rž Æ·±±•áôô´Ûíîìì'•J¥åååR©Ôn·ïîîö÷÷ÇãñÚÚÚÆÆFš¦/^¼xýúundÚÑK„"O>Ün·™úIù¬X,ÎÎζÛí««+\аÀĪb“ôÒî겉f!M4‹‹ aÌàÓÒÒ­ÎËÂ`Hâëׯÿý¿ÿ÷°F>øàvtôZll#0ó<_\\Dªtwwä¿B«Mhc2ù* ççç?úѰ˜u“µèÃ3KRQ‡,2ù$_o!Ù÷8nàæ/ ›Ï­'Ã×ÔB#[*À÷„d™3¼´ŠØi T® †ú;‡Y•~Ru¨ÄIY #Ì¿üÀ>sŒ-Ej¬¡Ÿ„—Pé³ðâȤÖs#£eŽ&†ö˜*e38™zì YQ­ ‹Lœƒ'@rù>¯€'9×Èu‰óð4ºó„ô](ñ»¬À9q3c×bì­²62÷œD5!q‹BÓâÊ{ÅÁÍî÷ˆE n„æ>úxÑb8z&nv‰â8¦°hã@F£ÑÉÉÉññ1QÒÑÑQ­VËó¼^¯ƒ ³I‡‡‡€P?. Ÿ~ú)·Zw`eee M†Èôfæâ•LOO'I²ºº Ý\e JÅb‘“§#3i`IÁ²ô”Ø(ÿ%IòæÍ›™™ƒ úHA 3Ey¤ooo_¾|Ùl6ûýþâââÚÚ‡ûäääââ¢\.kv®`ÇÉÉÉF£Q­V3›!D”:555;;K`¯r‡ikkë?øŠÐ˜W\« kÐ àÈÐXr0¤Â›†\êÚ\S§âô{²ÊÁ".VŒ:OgCGÏ\óJîÊOÜ=ÁªåVø¾! ¡.ÂËalÅNO¨¶ Gj”iY1%Å”Œ$:âï¡l|?¤M>lѦyr#¨ó cÂ<]6vÖI#xñÄf>sZ˜€ÇÉ„^swwW*•hÉ")ÆULOOW*•Z­¦;¶‘݉ãVãgv_%AJŸ"ÙÀ5ci‰B7t^|)¹É„ÌÓ3ú2²þV{§W}~¿Ê‘5 ’à°²ÚQ\Ɉ`…0™™É£äÃáð³Ï>ÛÝÝ…×;2µb4¤VWW‹Å"ÓÛ{½ÞÊÊÊÆÆÆÔÔÔ矾³³CÌõC}ww—-ª8Žß{ï=F ¾ŽF£ããc 1ؼ/敽!˜ššêv»JÊXP@q> ªŒ777ççç½^¯R©Hå†,¿Ä$1Üãüü<ñ9XæÁÁÁ'Ÿ|‚’Ñææ&œ†µµµëëk:Á‰9²¼2§àôšÃ¾´´T*•(VÆnöZ§Óùþ÷¿ûzMš@DÆÇ¡ÌªJÈŽ—bkD°–Õ ƒðx*6È㡨bq8$<€¢$…r*}âSÕõ’9bAW±cç÷ûfö!ŠVÁ´:Õš£äedÚê86™ãÜJ¢Â¿G6ñeìt2};UƒÀƲ¨‡Éç>Ø;]u–÷æ'¹h”¶5sò›ª$Š_Ž•gŽ\ÇÌ(ÇÃáŸ$úˆž¦‰E%W„M”œVàôKõy#§3™þ]h’DpZC…>žuà ‘J­¤*’ÅÈ]›Ð.¿/¬ÄÖ™˜†h Dõ‘ÀêòòRüÖ¢Z­.--}øá‡kkk("ÐŽ³µµµ¿¿xx¨r<ƒùùyô?)s ‡Ãz½¾¶¶–eÙ¯ýëßüæ7¹Z,‘Í Më‹[YY÷À~cN377‡…ò1Âìì,Ñ2RH§O‚Ø`\¢¨1uѧ†a¥RáËår£Ñ  8êõúììl¥R™œœœ››#´ÜÚÚbð$3åËå2C•²SÜáõõuØùBj),Xnh6è¿øÅÓ§OG6KMøNbs‰fËXxŠ\bªOl·÷„Þ« ÷Q5FE=Qˆ£(¢yM¹'—JÕ½ÌäS2'é™Èo§¶>å ¡£° G÷´Oñ™`ܘ†Ðj»B”˨2¨¿¢ß&´Nj¼ffâªÜóÑ„óc*†Æ¥TTË“ÃïóëOv&¿è-5šÛñ(¡53°†|j%nÈïENU¸˜\¡‘¥CÃÑAžRñôÚ„N¤¦GâË‹_WSÓ”Èlž¢¡Ìf·‰]Ê’· 3"2¥gOœáÎÌÌxÊFlšgˆ"4 Y–A%ÇÒ3þÝå€^__S,•Júy€§………4M?ýôS”­øäƒÁ€( ¢öh4Z__´"çÂØóÒÀýýý“““ÙÙÙ………ãããÀhàqÚp†œKk…v1tšd¥R‰FÜ;Ä4à¡ÅÅEÌw£Ñà'ã8æçÛíöÑÑ[Ýnwooïææ¦ÝnñÊ£°5…B¡Õj½÷Þ{ÕjuooŠIªóœB¥]Y–½zõê¯ÿú¯Y.å5`¥ $Uã×ÕÞ¥Ó¯’\î Ê#°2b TR;ï%=!ô3A°\¹Èi3®/•WSe] ç2HàD{USV%K¡À*³)ç 3k[ãEg¡@»¹;>•Þ§¹G®×Òƒý8U'všV¯ÏÐ}!20ž‘.N`l#A1¬LnC.˜¶:Ö›Š] )T„»À?)¶xÅÇZ­†oPh¢ça­tn9åÕ¿‘Ýg“…aèõ#Uß%Ñ{»Ï+óðb䇦Ø!ç¤àTHÙh4úÚÔÉ(ÆŽœò™*¡›:Bæ™SÞêiÎ{†L‚èt:×××õz}cccqq1MÓÓÓSŒ«Iˆ{qqlù9êT€bggg‡‡‡4ïííeYöøñã÷ßÿþè|Bg????99) „udaˆÌQËã£ñúõz=Š¢^¯rÄá í#uTØÈúÎä®Å,CFí&½^}Q ñr ò¢ŠÁåå%R‚€Èãâ8FÏ‹|ðÙ³gÛÛÛºQBOQ/// Nu‘H±ص4Mö³Ÿ}òÉ'©õîòóăM´•,· R¢¯U°9`(˜qeOʼƦ«†¡À)_b“A‘Ê0¯@D)•˱“Ó9­E‘ìµ<¹PHýÓ327°KF0pý}Bñ€®Å}WæEe94š‚b1Ý ~^‘fâÄæ|¥NVP½ô6Aä°I¿ºß™p®eB¤Ì@ Bë¸b³H TÜ÷oŠ«ˆ`o§TZV‘”jwêe%cׂš[O¥â!Õjä{Dñã8$™Ø°¬ØÈë¡M ø´ØJôTüNÝHkNïYTŸ˜sE¤Í0Q ª4MéÂUbo›SÕív/..Ð\‚àøø8˲¥¥%4¡nnnö÷÷Ó4}õêÕÅÅE©Tª×ë333ÕÅb‘ ëððU@L©Rêú”i“$999ùüóÏñiÝnW2@|(Ú†Ø1Âc7µ…앪J–e»»»»»»Lý lÚG£ÑøÖ·¾µ¶¶¦ó×ëõž={öå—_j› ¦þÌÇ ðE…Ñj³bŠP×Í" ‚`~~~qqQ<çõÙ³gñÁðØ½§ØU•ÚpI_ª÷pFèT³Åx‡¤.ë@¹]–EˆJ X¡ij9Te𲸊?ÀJTUú LŽNRâºç¾t¨p,5â«R«fbDH¨…ëç®5G8´7Lº_’ÑÉCp4’Z¦„_ möíØÆyeV䑸 ñ} r¤>ì ¤¿Ð¨˜Y–Á%‹GN±:°(E¸ÊN®¦NÖE6]ñ©=ÊAÐÌJ–zÔÄip¿-ìȱNÌ»+38%†ÌJÅ`¼Ÿ Àú!†Œmïéé)@¶yrry_> UÑÆñɈAdÓwÁƒHЦ§§§§§OOOQ ˆMâšÖ¼f³y~~ef8ÞÜÜ\^^ÄÍÎÎF¦TÇñÕÕÕÑÑŒpµ¶EQtyy “S+ˆç!LPE½!¦ò€ˆÇãN§£þ˜r¹¼²²òo|cggû’¦)š‚ÿú¯ÿzuuµ¹¹™eÙùù¹ô‰ˆ4¥Ks~~®—(ŠZ­ÖÜÜÜôôt»ÝÎlàÊäääüü<Ü´Øô-ONNþÛûoÝn7Ë2j»¸Mò8•PY|ß GÔP´ÙÈ ã37!2Þ¦¬ÆÈfmñ“H\êaÝ4C©/1ç6Ý2tŠþ7ÀGôŠ•ˆ¿” (Kðt9TÅ ŠïB )Dh±ê¡ÊMtoÈ0—³’¸Ž¹ÌÚkçñ ü] £Ð¢‘iï)rß„‚)aðrè†DðšœÆÈ¤ý7L8FnÚ­år97‘/šáØ2”°¸žd h¨©<ÂKa˨¾(š‹Èh’6È­7(3²Av¿\£R`îºýqje9îüSVY £Â.À÷ÊŸèi(0i;;{}}Mó`š¦ ÿöoÿ“@:‡šôÇÛY±F£¥¥¥Ï>ûLE¢Ðˆ‘‘ë´¸³‘‚|RÔïb“œ'HA‰lŠ,b¢!½5uƒüÇ|ùò%*£Z4²Q*†Ãá0IZR!øÍÏÏSôÄ[²\Fcnn‹?ІþÙÏ~vxx8vcij,ƒµ/€wЇZš¦ØeáÖ¢°gÖXÕ_H¹N7ŠÎ¤Ìõî+¶Êî æ åÑM‹œô•ÓÄõÄ)bR"¬„”TH’>³Ó…ɈUäƒRkZˆLˆ&4^ìÐM5—Å ¬_-sDy!} ˆ|‡3÷EI¨0¡déô‰7©É(«fZ©ThíâòßÝÝ‘0¯TéžÎ3´m<ÿØ}Vp)R›¤­4V±gìF»gÆeb#µGƹS²ŸY—Û<$¹ÅÕîýÞj€À÷ÓµôÙ»·bjÿÑf X•$ÙMb#†"fÜ\òd§H é^&F%)PÌ"Ñ+dùÈiËT½&MSô‹×××႟ŸŸ“cBM¸¹¹‡H;pÒ\M¯ÀÄ>K»Ý^__¯ÕjÝn×gÇü/ŠÌ@ŒŠòÒ4Ëáóf³¹³³ƒ9€âU}zzúÍ›7LZ¢èêêêôô-SôY®÷h4BÉKð-+ƒ¤Å„,Ëh£'_ˆMØ C°³³C³$B 2%cÓ;ÆâÇ)9"¾¬ ļT˜W4Õ 2]§ÜÆšläŒêh¼•äFæR³Hf2*8úâ]æÆ‘©­O9{lÂ/:¢Pru¨r“µIMþgS0t#mT] sJžÛ§.t|îØæi+ QN:±³Ð&t®K7·ö:JU\² tJò<¯T*§§§ µdÁa]+±wø'zod:á!ÑN K9±&¾Ðæ•©(4€ï >WÖ,'x.tME¹éóñÚ32+§N÷å-§ÿð¶“ ˆLÊ2´±"êÿÒ™ô•à‰±Í2Sƒš<%=1³ØäÔN§suuÕív¹¢ççç4»Ñd³´´ÄÒu•ËåjµªqÄ/_¾¼»»[XXè9;;ëv»Õ óóó§§§$ö÷÷¹ÌìF}ø¨!Žãýýý‰‰‰•••ئ‡aˆt¿¸Íf“¢ êð$H~G£Âggg½^iº”ÔÌÊ‹BÑl6ŸvæÚ2Ü¡÷…¾Ë#Eè¡‹$ ä1´9¬@g•¼°õÑ}ª¤Oy0xAÑÁ3«!ª† §U‹?5a©ØXïJ»XF!kÀ&ü päM0eûF6° @*ç9ÜÅ(ÝÆ»HðƒßW0mUª ±VÌ]“ÉÈuÒø¨ìxìÆ)dF2OLV$6MÐ,Ë…Hú9/5¥2gz_Ö×Tv µ„Ç¢\*åü‰‰‰ÙÙYÅYWWW¬/&Y¨›°àC™Qfã…ð9…ý~ŸuO’äèèH ?8Âââb–eTÜHÍJ¥<ƒÌô˜2Si6›ø^¶yqqñùóçÄ (Øð´“““+++¬@»ÝæEˆ1ã8.•J˜rƽÅq¼ºº†á§Ÿ~†áãÇÃ0„ÓÀÜŒ§„vH5ðQ…ÙØ#¶`ssóƒ>@0K0ÍÈ&wcö÷÷‰ÚPyžššzï½÷NOOONNxeÂLiËñ'H¢z.‰À@C"Dåz²PŠ¿T l^ddÜEåzśʠ¢ Âç3‹%pÞõ3>Z LÎhl¢Æ8p+ê‰5iêS䦉uFTK€¬.Œ$ThÊÒ­üTm:ú¾¯æ¦ë¡Œº¹Öööö–|PÑÜx<G–³¡2®øW­?à0~ùE qÐò Ãįcì=+÷{¬ÄÑXêÈdíuF}ÝÓ)N9ÜÅÅE·ÛIG K yyyI C£Ñ žžžÕ8,¦3` ®®®†ÃáÌÌ Î-Ë2†ªŸžž±*ßRò`·B£{zîîî.--5›Ív»-¦‚ª$*«;h.F†ôÙ¡PüðáÃZ­Æ$±ÃÃÃn·ûoÿöo/^¼¨T*~øáêêjµZ¥Çèààò=Ñ%&’´NüR¶ðáÇÿá?üäÒÓ4 ···h†ax}}­Ù«ÓÓÓ­VkzzºÛí¿zõŠuà´©¹úöövzzzuuukkKy"®›ÝQg‚Ü› /^B#ºÏë“aân÷ÎO ޲²ÑÜŒïOÙQ®§´BûÐèW¾š©w!k"âˆÂþèóJ~ƒ.µòÐ ÇäsE¦ž¤# UôUë ݘµÔšÛøÝñxÜëõ øa‚9B®’Ri"ÎÌÌ0Lp³\%>”èþ™ë[¢p/´ gˆÓ®ÆƒËËKMâámÞšI“Cz„X˜/žªeÊ×ëTX,‹Q’ÀQ ½[Š]£|nà|x¸40%Y2€aØRt,kæ£LÕAN‚*°™SX°Y;DUFc<·ÛíV«µ´´Øn·›Cù; †Òl6Ó4EPAGM\dî*-ÇÊÏonnNNN666TÞ†3Ëáôô4³ñ£Ñ9a”Su}}=??ÿ{¿÷{ÌI®ÕjÇÇÇ;;;Ìc¢ê¦ÛÛÛççç<ÕØ„hŠ6¿;tìÇB¡ðío{uumÅjµZ¯×£šzÌÔÔT½^W°&æ‹âY&5åy~ss³»»+Ô<°©0Ü~86¹+R<­ºš0<þYû±®XIjS|”W*} v'W¶+§Âæct*äq •Ã}ùH8—25ÂUsÕ%sûÂxavyHu§égô0ú¾o6Ìû42¹Æe²&ÄÚ„üT%,JŸÔ•”Šà£`m8BëA_LC¢ûÁ`à³°ÔVl¼«°-_]ÉlhðÄÐXÈLj§|K ˜»~L抅åœ6üÛnƒÀ5|宓Yª€Kà¢JK*Lè‚q¸›Í& (µZ œ‹‹‹~¿OÅMqÂ%åxþËËKfCw0Æf<“Ùq///ŽŽÈé†Ã¡ÚkƒÃØòÍÌzF¦TËÇ„w~ttT¯×ÓfMÎÎÎ …Âúú:Š}333G4¬”™á†Ji“$¹¸¸üº¹¹yùòeÇGGGiš¢‘gšÊ ˆi­V£º²™8ëyyy©öÀÅÅÅ>ø@‘gÎMªÜÕ©©),u§Ó988øõ¯½¿¿¯ƒ¹ »G"‚Wã€Ò¬'MH6åüü|vv¸Y;xBºÕ"§Ð¤K;I†ÄÄ•T6Rs öB²)S5SW¤ÏÏ«!E’¡ª5ñ„â+dPë ioDŒƒÉÏ@wXÎ8³Á<‘1ÂùxËtËË’Ê Š°¢T—P ÷#V²f e÷ÔÈ÷ì²€$r‘8ŽQ|Ó<ÔФÔßSpÓ1ÄÔÁDÆ–ÐvÎVMP†"0í Ø¤äWü?=M] ¡·Àb`ŠÔï€S©ŒÜ­‚4uP~V·€Æsë7Ê´EÆÖán(%$¡S¯6î¥Ûí2Çb§8çççèV«UúŸ_¾|‰×RTØn·WWW‰ˆÚív¿ßgv4ÄH‚Þ,ËÞ{ï½W¯^u»ÝN§Ã͡ËEÄe,:~T£Þ÷É'Ÿð©1%AÀŒãMÔ~¿¿¾¾Ï+´ñޱMÜ!TxüþûïS€Ú³£¤7_€J½â”…Â3²|RÍ€Áâ*bš©–ŠGSp3N¨&ÉËg*’I%ˆö`3!0EFB qS•Q@”±Ëm]bREz/nQh2•üæ þ©bedºWúöK‚’RÈ­‰Oeäž%';6e^lm­±µ+ó~@Æš[[*7…b Ü’g*¨äŒ)8â˜MMM±†¹ëVIL|³H?3AjÙëõä9”BáudÍ¡æhê}hLl±7¿PŠ}QOæ)µañru'wSú]bvvf¹ñnßI •dÆn ÛÈ´ÃBs-¹3çççXâRµexg(ÏÆÍ'êáîQkãŽÁ¦Å2E™Öl6Ñ™"ªíâ¥>þøãÍÍÍ««+ÔÖ³,«T*ív{d¬P( %ˆæÂ0$v{ñâ·÷üüüƒ>XYYá]Héñ1Mò<¯T*Üj¤€H(†®©u>V«U´¶··iHêt:r „zh¢Á“'O°J rË©ªƒºÝn÷z½§OŸîììx>:oÁÁ‹Lî•bFŸC(&r–"£Øúéµ¹ª¦&mÚ C¥šÒ¦ŸQ8¦£¥Ó,ÒVv¿6²•©]RK&¿Š'ésg•I“±õÂg#§¬$P‰©àLN"rá'9á½^ö2Ñ“JZ"UˆcV9Ýíím¿ßç ¨®’Û¨˜;ú,€ÛÃÖ‡&z¡¹©±&áâÉô‡Fd£Q„k‹ ½€ú/œŠØKï$a*ó)%—H]Ÿ¦˜SZ[Ï•“çãiGN 6¼?v(Qb"˜Pÿ8ícÕ}T(ŠÉÇ£"žÛtL _:„ïk2×J­€Õ·jµº³³ì•e‚M„rb<ûÌÌÌt»]‰‡ó =xðà½÷Þ+‹[[[¨»A@Ï ¶<ÏacåÖC@Õraaaÿúú”b …Âââ"ÿ‹7&ÂÆÌÌÌ è –t ð>I’o|ã§§§»»»ûûû¬¯ 964­5¥ÞQ¡…½ˆŒ<œ<µó±iPøÑ~´³³CEgû6ÿ7Õ·¯²Âp¦ RDzêhž¦$˜&2 Y“Ш:ăÂã3“X‘˜/΀õÔŒ&½©Ø‘ãyÉtfNNÏãñ¤êЬ‹Ån·ûæÍz¶Â0]E¢ƒó¯s+NÆÅÅH<>[ž‰ÎydŒÇ&B I%m"^òú1%ŽB›Ø©îi/p°¹Í"xÇ ª+bNõ“Ü:18Œ :(LÖ¾+8Ò1È]‡€ ‚Z·À©!DÖ<:}úÐÉÀ„Öà)Æ&ŽF£(sr÷Z%eS UÔ]´™qá}Éût#š: }:pDºW—ÌëׯÃ0D)Þ9F¤\._\\ ‡CìT­Vãtò¦àS±Ér1E¢×ë1úôôŽÁ-è• @Z©¡J!¡Åáf@´`µÌº^S‰¬Õj“““SSSôfn:]'''§§§Y–¡BÃin4ßüæ7766¦§§Þ¬¨D;0†4f³Â¯°/è4`ŸRŽ6>ÿüó§OŸv:rºÔ¦9Å6ûƒ¼€ß¢°…ÄDj¤ /q‡ŠÂº ‘ÉÎùÌ[²&ß ýX0|hBn22‰™S­w•?‰Ô·¨ýBüÌÀ”Þnoo;ÎÙÙP4>¯Ûí2ÿ PB ,:ÑNþw4á87K›+šrp‘ñãQ.Ò¨@Ò܈±›º*ûÅçÂúë*e!»ô ,…釺Ñ|ãñ¸R©dAŠ$jS{ƒºñtR› ™š¤½J ›>˜H§ÌI¥«ÒÂá×êENé:˲¯áw庩c—rž„wDÖ‹˜šî—ª„²z8vâƒñŸùý&‰ÌÖËKð²Ãá°ÛíbÎÔ~IìF [¯×C›ùÌ"g¡ …Âìì,E=ø››„ñ8LLÉ\Çýüüœ4&TÏ™pšÄšççççææ—"ÀQ°Qެ$ÈÚÊÊÊÊÊ ¨<ÿÍÍ Õ²ÂÄd´\ ¼„årùÃ?D"sƒgXÕ§ùóÇ?þñøCêŒøa2;•½õ)Œˆï&5I)^ø™7|‰…¤›“ÛP9%;B…µ×Êy ªW¹•·cî:öØ45¨˜(ìV AàDàbÓ˜×ÛñH?<'IÂ$7¨„®2yÃáðøøøøø˜ó,Ÿ«SØ›eÀï!€¼˜{¢\;¥*§HÑ$ ‘‰Lù !³¥Ò ¸‡á}#Òy¥MJ;B'1Lb¨:#öï‹y"rWºšÛH´Ä8ˆ.«\{‡?ãÓ±A ¦Ç4UaArGГÁ Ælâë¸ÂÀ§LjÖìäUQ­b­[¹1Öâ"øŠ¡"R{™qè ¦º ¦[× 5Qa@$bìG·Û7òã?ž››Ûßß¿¹¹éõzWWW“““‹‹‹êyqqÁx{ö —rùø¾ _h32tŸUÊQçªPªÌ´+#s6”Y² ›92¦Ÿ//ò1•HR9s4: ‚™bÓtô¢ •äõ1I „ ëÍDÖ´Ïó“áøÔØšÔFcyŸŸ÷z=ºÄTüâÌp´Pß'2Uw±OÕøUcILÏ©»^§¡iΟ‰m̆˜õDï_Cê],#ž23ïË1Hª›Ì)Jª¹¹9‚;êÚ¹X4EЧ¾$:!V!è¢Aç<à]Ô!›“:}Ù„¯’Ü ªƒ¢²¢/7jí”uGnRŸ|‘¦,†„+5Λ*²¾d#hLê…Âæy²ííí0 WWWáôc¹kµÚÚÚÚ{g ” 6c¯ò99a”C£Ñ899RÐjµÌmçÍÍ YM¦³Õëu¢¹Àæ¼§n–z±X<;;cØýÌÌÌÞÞÞ‹/—#øÇcn¨€éüü<õr¼ïÙÙ™0 Ò™ËËË­­-&e(d&€â¢j&]nêŽÜ:ªBæ<Ÿ™%ËÖUÁ†ˆ" /…¹q•/ÃðÐ9Μš?Cl®ì^¤‡Üf7èñôY@g„‘‰ÊÅÈM쉿c›Æ6C™NlÁXFÜ0%޽í8{R”UÎë󌱓¨„`9v"s0uÚív`t'¾9“¡:°Å¢ŒDÆá‘0OJ¨¿ÐáÏiäCÍÌÌ€]\¨ØéÊcéO-lÇï΃nOS^KÌõS«{ ö-ÏJœ©¬;´ruÁ  '§P°¦qud[™$YbÊòšÌ§b›Qt@àFïG}”çy§Ó ççç4@I(6MSj:ˆ"u‘r뮯¯‰ì`B,..R§ù††çÄ›µZ­Çîïïw:«9‰zøð!bUoÞ¼Q“6¦¹ÔÕÕUZ 麽½­×ëä{{{ÈÉsÁððš155Õï÷ÿå_þåùó癵àÇ6eÞBæCP7‚Ú¼ü¡úÕY^j…Ø Ì±Âjḡ!ˆM·CV#7ñ&ê¿2Žr­ºíWWWH§Ò~ ßUR_äxFcRð…R!¤ Alš¦â¸.'CV’Òa½^¯×ëŒJÊ\ÿVêÿB«Ç‹Î’ÞçLJCÐzK×ckíÀ¢êAf£‰DÄå¿D¬W† Õ?áŽMJS™kÛï÷i†W÷20ˆÔô“ ¬ƒ/¸¯*¬2¥&5b›)8Á¯ÐH-Rß×R«eZyâØ0ŠÅb"3¦-ï¡ ¬\gNÈ¿² ÙÂP0F™)]ès‚ÜÐSW(ÌáL FMOOÄó …Ú ¬Ë‹‹ À ‰(lnn¾ÿþû…Buà……ÞŽ¾?&?ŸÙÖ““:fgg¯®®ö÷÷ŸŠ zpp Ô•Eâ]bz­¬¹È™Õj•HŠ= ­ñ^IAilÐ`0?ð"0Šv»¿¡“YùMàè¸*\hOC£× RÚ†M^Mû•;ŠœòbUåé£D¦æž(|­ç;µñ!ÞOîÏ€óŸ$r”«ÌúQÕkì{fã @àÔ{¥T.6¶qE½^ïÕ«WÒx œì!Id›šÊèÌÌÌòòòìì,"v[[[0GÈþ€á$Z­ôNÌÁÕÕ?e¸ØÞÞÞÆÆb  fý~ÿÁƒËËËtâ‘%”Ô\\\,//ŸŸŸôÑGwwwÛÛÛ,¬=I’““F™†FÚҋ݃Ԫ`>!Öœr8n@%ôPyÂ¥€CÒ©Õ RJ%ã¢ÊHOzT/Þ —; uゥÛè½StÓ­“n—  –Š3ùˆ>5ñ/q2²IÅü釹ÊI+UÁ‚®ý64š€ŒÚÕÕÕÉɉòYƒ¾t;Ñw¶ôÿÒvQù¸kõ5Mëöö–"8é…¨¤`ütÚ²P=§{Ù×CTÜ÷†LÑ¢v62:•â›Èˆ8¾¦©J±Ê/|v9ÑбFCãßë³ÉîwZNúÞg=‰ n„VŠíPþD@˜lQut #Ѥ®eš)^Ê73ëo"ï£ç“;‰g›œœ|üøñ“'O¸±È{SO•ª3gŽªŒœZI8ŒÇã«««ÝÝ]ô‘Ùê­V+6©Ã»»;X‚¬R·Û…/Ã8 î6¥e–kjjjmmíôôôéÓ§È&I²¹¹¹¾¾¾¶¶®É½EHoee¥Õj-,,yò„Å€ëÈ„ç‘0bxȃƒÐõ»s£ˆ5¨‹0Z÷z½‘‰…ÎÍÍaæT:àÐCˆe ‡ÃáîîîÁÁAb*Ì­V+I’ׯ_ ‡CâÿR©´¸¸Èdyª! ƒà-Ø”R©tssóóŸÿ<<üó?ÿs•ƹWcSÝÌóB¶hA¾W^e¬ÔHÉZjü<«¤ãg:±v £D"Mª:µKU µtz)¾±QjÇÖ>­xÊ'}¹Íì‘X¾÷ü2X‚oôëA ŒI RƒBˆ¿À9R¤¦wôPoî&€)hJÖ×àU=¤…>säÚÑÄì lô<Ùœ•±Ib)=ç¥ø“bWÁ&¡$®m(°ãÉp+sRìÃï2\.°FnèÞ*r ­3IØ´j¬XRÉŒmò ßÌltn„j1»Ð‡íJ¼Ä•UД[-UE[\UT.ŒEKBÇÀ ]ćÀµ”²5")¿¾Í]C<×#0Ý’¦¢36Õ=°(?mmm¡]GŒ#1“ÑhÄЙ™z“$™žžît:{{{GGGl$JX|Aç¥ ¦àÌc€(Ó‘@WT¯×C%7~xxX­VËåòÙÙ™ïk#Þ mx$ÒŒã”ÔëuÔr@jȉƒÁÒ© ‘®ÕjWWWôÄpUðQBI{½cJ'''Ûí6ËEe€øëöööþá~úÓŸÂêZ‹@ôð>ŸyxYçÀÈDì‘(oªøIìols÷”| ´R¹JÅ8ÝޝJ.¾%Ѓ¬¾z#Ó#d:ºßO›¹Žz.ƒO{‰Ëd tsTXô×&µÞXU» §°’l ísœØ”X@,Zæ†3çÆf ï€ø j”´OÉØ©6•Ú ÐZ| …î*3ÕÐF ã*¨\#"Â%‡˜Ý§›’ æVëmââe›"´Q44>c§)—S°™ÑwEÉT-1·ºœÄWôñ=†.¡§ ÞÎVô^Ñ3YâûÓÖü«Èø±.JËõ£nž’g^ S0&o_>v g‘ÊýÅÅÅÄÄÄòòr£Ñ [b8öûýÏ?ÿœÓ@¼–¦`3#yS´\‘ÊÌó-¡,ˆÃ!…ÂÐ&$F£/^0šøkyyЭ\.÷z=vÓS.—Á³yœg¿ß#4«Ë0;;ûíoû£>* oÞ¼‰¢76a,‰p¿zõŠöšÐú–I®®®êõz–e¿úÕ¯þþïÿ¡z8ôxv]mޣш­Ö™‘ñ“ô3QKm6›TBöc:%b±ÄMÓôƒ‘Cçõ J‹`ÃzœKΫ¡—Ü—­Q:æ “~E@~àf)ðÉ·:•$ÖlŸšü±ïŠ íË["JéùòqØÍÌé«p½ïîî æ6ÓÁ§&‰Q6D~”šVT` !°«ÀO•JkõøyÕÃá°Ñh—ùž§,˸yww‡5T)#rÝZJV¤öã!9E¾ªŸS|9ªù;Å‘1¶“Pöm<«=‹M„TY+GGî‹[qPYº¾ã1/ñYI(·yò4O699 ‹g0Au‚eš1[Â5^[[[\\l6›a~õÕW_|ñÅëׯq8*u!}ýŒÀ‘&®r H!6.ŒÂöññ16e4moo£•L‘‘VjÒ70v½^¯£Ñét$xÐéthþÂià¾⦦¦ PqÉ¥€ˆ(S¶àÙ³gÀ=š^‘çy­VCá~ooïý¯ÿE¡j>58>¯¨’*ã*Ô'ÙÄð³\SãVyDÞsƒšRdCíe,b×ô®˜NMÚªÞ0z¢ƒŠk8?ÅM¹Ô¬°(rí«bÊËR™RÖ#¤ ÷)~²§5ª^ÆÒI^]µ*õ~+ðñ¨œRi¡Â¹íåû’QJZÃp8„ÌfAÉW3Ç<›öKv¿!?0 \U–‘ò…aâr¹c©ÐQ­V…|ŽY9¶‚þ+wÌÐ …\P0%85ÀFgó8P€¦ÖÁw,ÉvGg*&tMx˜ð³ØÄLDÒS0´aò3àXJØÿ¸ºsss`UÄÆ’7˲¬×ë1>ž¼¾¾¦®ŒþÜÞÞÞ³gÏŽ‰b§ UÍqP^õ•ÓyyyI¨¿¿¿Bj!°Š...îîîÝ9$M8%è”d‘årEft?üãp\]]ÑV$Éòò2ܨååå Ñ™T¶ÂmaÜVÌ@E­802Q¥R™››ƒ ñWõW”Óùñõ²ÔZs²ÂZâÏÏÏ¡áDÖ WˆŠˆ%¨"Ñ·r«Ìñ3=t­øZùoêš]¥Ÿ¥@C‡»*k(ƒ„Ïcðù"¯Ýÿ’«¦+:oÓñöËßLíþ¦Ésc…kèøi;ô <ùöö64ñUaÐ=Ь‹–jfr•ä¤Ššƒ  9ä&fã«D4S&.¾Un68e$.€§¿m¡"›8鯄÷¹ì¬.SÿØGól¬¹L³|‰¢~ÙâÀTßÆÂŠŒ<Å+wÚ@ÊØSërR¹:tÊ|±ÍÝö?/"»tì ©meYvxxHf¡N=n2m8©©)‚¦4MÏÏÏqõˆº4›ÍõõõÄDfÄ9”¶ÿÈäz‰¹ÔZHÄÛét€`èÂÁ.ðód©¨/²šóóó49A0;;[¯×‘=€h‡d«Õ*—ËRÎÂÊ”Ëe†'''LÐl$2û'ñ³½½½§OŸR1QŒfmm- Ãø‡øâ‹/p3ŠVPü Èˆ|«òvSsÒ9%A"7bk° äTÙñØ<˜çLËD¦=¹¶•Ðè|ÂÎrÇ“ŒÜä‘‚“fï&tÚ¡>éMOç±)yèÜ‚NFnæ³x©}ñT¹Ñ‚ÄH↋;žXg¯’8ÞTDµm’q#ùI ·ƒ]„®t˜ç9ôT_žÇ l—‹†ÈlºÀêªÞðÊSQ„«$N+Ïs°0E‹øØQÄ=Ð.«'…÷Cr]Âû#:«È+7š-«$ß&y²rÕ©Yº4M#Aôþs¤ôöž.¡»ùH¹•C›(C@4râŠp •¢Ð8^¿~Í6«‘’&w#‘F€C9‘XÀÛàvvvàÌÍͦþ%zA±X¤Oª^¯³© Ž,¹è9°ÕoooËå2UHš¢y°©©©åååB¡°¾¾Þh4(Ì1ýSH¼°²²Â ÍÑh4Y– ¬›bøÀ†‚D6²ág?ûæÉɉZ…!XÍÎÎ>}úô—¿ü¥VÌJM|‘GËœ,·@"‚D¥N œG6ßÌ—i´TÑZ¾QÁâU¥&œ0vÓ·kÖ‰­óAà&nÖ'€VþP½Oi¦DÅïñxL‰†»ÁK ÖÕ ÷…ËÌL¼`r¿›[¬i¦Þø*ŸâQ%ŠèŽ™dî±ÄøŠ¡$ $ Å ç®™I©17¾Ž*˜¤&¾=›ÂŸrC:Šò‘SH®FbR(Þÿ)Ö‘NÛ;œáÐäÉÔ캺°âµÄÉÌâPY™·i»Š€>ôÑSnL³à¾rHâÆ‹CÂô˜¿$®ÈZÉ;ÈQÃ0¤…=Žã7oÞ¨ ¤¨ @„z½N~¤Žð šðíîîîõë×ð @À/©k ®Üëõ¸Æ”f²,ëv»åryaaa{{;MÓ³³³ÛÛÛ'OžÀOMMãÓàF­®®2ëììŒ4–h±Ýn+Ûzÿý÷)Š¿S|à­1µ ±¹üØOúÓápˆv•p™Z­¶±±ñþûï¿|ùòüÿÁóÃÓ5ãÜkú–«X,‚”«·5Ô0 ™”š°¬xzœ]JŸ<?réD%¡¹l áðIOÊÒžg C¥’´"ˆÔMµÂbfÆ· W93™ÐQäe… DnP°Ro6µïª”,\_Itl_òâTȤ„âˤ¦¦&26#¶Z[uº0 áO!¼EêÙDÞTuíÈ” îì €ØàÄ8¥´H‡Sy_èÚCãšûz{Ê©óµáx2ÝP¬ ¹¡paË_æN*0Jcnd´ÛÛÛ¯»“Tkˆ]Xbì37p\±ØØMp䙄•f÷9©#LU­V«V«µZlˆûÛŒÏÐ>øEºó˜‰¦ân¿ßç®bªòy ¼102Œ\=$fK8 ›óóóZ­V©Túý~¿ßßßß§Q†f=4ö£(B ùÃ?$æ:;;#'ŽÄ6•¨Z­.--µZ-¢qì^”³(?L— Û³gÏ^¿~M)“áÌT3[­Ö|pqqñ_ÿë¥|I[,çizzšª¥ê,‘k‚g°Jº‡‰5ÓÉ”À¤ÕiVžˆ~“ǔ°Yú1ÜàÌi¹dŽø’ÝoíÊÜ v¥‡ì¾à[!DÊë¥ÿ81ÒÌÈŸlDnÖ3£D  x‡ ʯèM…C‹ID8)Bœ ¤ð‚ÉÒûŠÞþþëJ¿~ýšV™­« *6…‚zÁÁ©É4ùgæeAôÖH,üMëZƒv90æ]ý©)LÅ®±T|õ9ë9 xEXÄP,)pS¹¤ämuÏ–Z•Üü¾Z™Š¹&‹ãø^©ü^QQñ˜>$kŠß­ ì~^œ(Tà ü$±¥úZï‚à Žƒƒøë @àN„[¹'\¸n·«Z/þ ’z?pÕÌÌ VƒÍX¦‰IëëëÏž=ãÂw»]–euuu}}}ww—ï3Å+MÓ½½½ú§ê÷û¢€ƒ”#‚ÌÁ¼`ÓñP¤çBáöäääg?ûÙƒªÕêþþ~EÔïªÕêÇã8þÇüÇÓÓS±éXa8¥Êò”Hu•Ùñ)ˆ)°SlÊÝÝ3S½3”ÿÀ:(ÏR:É¢q”aqG ‰ ¸“Œ„zTÛlÔdè(KPDåCyc§¨-2áM!ôdJ^ülðÀøÄªT+u` žž™ŒX³½“ù‹ðSø›ïSr åÒ\nòx*¦óéð‚™‰[¨HŽ¢^ ?ÉxM1Ne ¨xÈé3ŠGšÙPED5\\\á±)ñÇnJ³¡ìÝØéP+ÓÒβ&E£+°ˆ7õÉ‘ãŽæyžèÂó ”! ]¹Ô["ŒKàz¯¸ JÄL-³ÙlÖjµËË˃ƒ¦iÅ®AúêêŠü\@ÝÉÉ xø™ Èt„ç‘ïÔj5´9m N¹uHDQT¯×¡Ôëõ܆_Jô–$ˆ=n4=ÚÙÙ!ô#Ø8«T*4ÍC`9==}ùòe»ÝÎm^Èx<®T*=š››kµZ00^D̺b|.ûÿó?ÿ3J7%àÒTsss¯_¿þùÏžeA(¶¿Ç” ÖSû­œŽ²,…N– H®uÙ4Â3°Q†þ;…B¡Z­ªœ8-±OÅᎌrÍa•}‘áæ„ŽÓÇ_ÆNuS  *†±ÓíðyŸTŒE†OA¥œ™5(q#ä!öQ/A¹\Fc4 0S]‡™™%žl®°'¥?¹IŒlmm)žÒg¿³‰‡âdŠz‚e¤˜»&“Ø'…î%¦²¯¦H2J ´œÖùù9û†!ŽÀX92 V[Ou›‘ÀJõé´qiòÜ»‚©N Ý¢¯ó#ƒƒþ­|ÃØ‰ ŽF£·õ‚‚º/™øY >ño GRä5²©'RÏ’?ײNMMµZ-fÕ¼~ýšyDëÉ—ÆÿdYF/Õùùy©Tš›› AĦ§-6M%žîîî lïíía®¯¯1š~Y‰ÿÏÎÎZ­± ©Íùùù›7o¾¸¨Ö1oåÐ(¨3›X4ÏóV«µ¸¸È󜜜4›Íf³Érþ†ÃáOúÓãããJ¥R°1ј¡z½þÁ\]]ýùŸÿ9üXâmU ¯ð#„$Ž‹­G]éQEàÜ[QÆ•šF#0¸ÀT(•›ˆ­›îšja#§›.jBàXšômnˆž_?·H¨“8I)ÆØµâçFø Œ¾(ËèsdÍ=J#„%óqT¢Æãº£¨ùb¶°ªS—l"ÓÝß ÀäààP¥ÿc7É™ÁByX¢±éC¼àb#ëCo/MS9r‰©iY´JDÜXl:挾·ÀIBóHØUiUÿ­ÒÃX¼ç¤%&×[Û³º—d}ál´ÂÞÜq;äɾ–”«[Ãdîæž&nèžæÕô¯²¨’…Ü銰"Œü|óæÚtX5ÂQªÃጜcM£ ÿ˵'ãSm75 ¤åˆÑd~}†gggdgÍf³×ë]^^Rd¼ººªV«,™` ¢Z­¶¾¾žçy·Ûã˜1_\ò<Ÿ-•JNgjjj~~þ£>úä“O8ˆÌC¬ÕjgggN(z}}dúJ¥Ïn%IÒét~õ«_mooÓëà "ÿ™™™õõõJ¥ò¿ÿ÷ÿfÒ×Ȧó ³ª²ÅÄû´^¤ÈîgFS‚`xttáëêêŠU˜ 7ZŸKüRrÚ›U \÷Œ/æ ÈVYVû¨9ªäb1ïÜøn>ŽÌ±/’NAP£ê9þy!X¢~±"J‘¨ÆÙ—?×_„\(„fó`²ÅqÜh4noou9 Ø)`—Øæ2²܇‘ixmmmÑ)R«Õ>T’ðUO¨[ûŠÝÊV«E€P*•(ÆqŒWôïääd<onn>|øPŽ«R*•0^ý~ñÏýýý¥¥¥÷ß‘†‰‰ ”AhJ„BõPNF÷ùÕ¯~RNƒ!F­Ñh€ u»Ý¿üË¿”¶êÝÝÔ*Ôi×YÇH "AeŒ‡µZíúúš¬FÈÀ°‚ ò%˜õVUÅDÑÁ1=ü€$I#ÅæQÓª•»! 20akà|¢*qñUTo”:¸Ü×Y+­F`ÓD‘SîIÂË¡ZfÒØhêÓÄ5§LÁ ` n ÏÞÞpªzƒñ×óM%qâñb*²ø‰)µ³ƒ¡ãAd¶EµZeRº¨3lŸ{•xP'!6AŒÕåûJ«7£[¦¤`#TC£ƒm¼›ü™Lßöš»~uOK:ñžúÀQË^åÕ2…Úð(X.!Ù ùšV,ÆÊÊJžçÌÅ›ØOMé[nJç@È­V+ÏóÝÝÝëëë/^4›MŠ5¸ò‹b±¬NÕ†ý`'`3Q›Ëó¼V«Q•çôPÚït:ªÐL ƒ½½½ÕÕÕÕÕU:õÐÅ.p븟/^¼ˆãxyy;µ´´Ä†AYVÁNÉw ä«Ýnÿä'?a¦§§±f¹\n·ÛàÙ‚Þu¦1 äœ\™ˆ€Û±SYµRG\¹p_!—cÊržžžœœ#¡)½@*VE›2GÝ@‘ {­€E@•8«ªÍ‰!Á£Ñïöööää„ö '¤[˜ô6»F4-ÞS|E7Sb¡<&²þG\8CtDñ:”ÈÁÚ$cÉò*Âá™8Ÿä(*PÅâ“’ÝsöתDÕëP+­SÊ©K5‚JvA² ò¹uelX$ß”ç#[JmN`ð[CÞâa¹ÿw‰Ç ‡Ps(˜Ö£ƒZz²Ü(Šfgg=z411q||Œ]nü øæçç)Áp¤ñ+Æq¼¸¸(=)ò¸Ü88\¶‹‹ ü‰8DHPqn1 <—¦éìì,’ž\00µÙÙÙËËËÁ`$I¹\†nŽÐÇ766˜3äÜn·Q祿±^ª{gggt8§i:77·¾¾ OÈ }èì¿ùÍoŽÏ)"âìììÆÆÆâââþþþøCµï…6B½hƒNqPD‘ðÈ'¶sgóŽÆn\þPU])pˆ}†#¡Î Flp“ƒ `ÊŽ/)Õ2¥0\¤ØdHåNÇð’£RRéKæØDY£(º¸¸P³7–BÑŽ.°¿HL­"—P#‹]+d}PÖ ƒÁ€žˆª-òYèÜÀ€z¸Ž.•J²_j-,‹ªÞ¨¨|œWŽŒ&ª’®.n8´q~œ(Š ‡Caï¬'Bi,—á15•S…´(ÓDø›3†éð•ÈéµÈqì±;dE±ŠPíOÁ—ò\e‚ØúD~ ¯¸näªþj+`SS'È-\ A»ÙÙYT¢ÎÎÎÿW´ñ°h%MMM.Äàü'&&æçças™ÏÏÏÕÀI_KžçƒÁ€õJ’„S…6qìTGØõ,Ë4S*°FV¹w¢BÈ¢Aa=|øPœ=æÁŒÇã/^€Í¡ówxx¨ËÀmb@(¸Èrw¤Š¯_¿¦œEñEÀF£±¾¾> þê¯þêôôTɸÐbBMÁKÓ' 0džñ<²±Z¹µeIOVá3ÆT€4 5í'"åÐâ™)ÆñA4wRá:¿[û:îM…½EàØ@ø<þLÜ…üpµZ½½½Eñ‚]Å„¿ÂÍxµÓKÿ‹Zw¯`êw<³FIˬ“m %š›67½˜Î± z¡éUÉ)éÛÖÖhUTjŽ RDaå ©Ÿä—ʲœÃĤ ÕeYF…DÀV¥bœt‘«¹ 333$å,ã÷]QÕÈ&ëPðA¢hO‘™íÂI`pÕ“§c©ï‹›£2Ê·ŸÜ?¢g©ÈQ(é‹MÝÕ—0CkO¸A½^ßÜÜ\^^îv»gggèº*ßLÓ´T*±ßÓÓÓH¨0~~ޤ/q † PpÇB¡@¸Kç0Ç¡ë,˪ժöOÏ“¦)û ¦ÎÓrâAÙDb&Ÿ"Øît:ï½÷ÞÔÔÔÎΓ¬d";4…±ìX‡»»»ÝÝ]òÜ‚ÍVâŒÞÞÞnoȯaxppÀÊÐÓóðáà þßÿûŸ}öÎÛJ=ˆÓ&ôA”]3,£²Âà>•1˲óós/· I/>¶Ra (2@ñg‰°‰5©‰€Ê×- Œ:ÜWެ)L‹ÿN[†®œRÅr¹ÌI¾’7¢Ù-MSMÓ ¬mMQ x(ü-õ9+±å ¦6î…‡GUT}ýú52g¾ö'⋆aXÏvlcß•+qUEßeËœz`”NÐø¼777aü¥ã3âËK¥’H­ù}™Õyu~T舌ãêíZàZÆNoV´ÐOU*õ+Þ¦NÏK(ÊÛ:nh A‚9€d®á‡ ¶*µRœœ\ZZzôèÑÍÍÍÁÁA¿ß§¯ª`#p˜,ÂÖéN M’„²}lºüÚ#Ûí6IB”šÂÎìììééih}ùŠÅ°Ó*«æÅRöÓ©Ch¯K~nn–ÃÅÅz@üÉR°§VÀ˜™Á`°´´Ä•Æ_\\ììì£BA¯b¥R©×ëkkk?.•JÏŸ?ÿ»¿û;.$¯).’ÐúÅКa(oqÓøŽ*kjê$@#âSÍ70z©_µZM’~lŶIßjÌ5‡O¦'·ÞWq÷TÒ…‘… ÃD,±FÙØ ÿ“px.±dC"úñ)3ª†é‰žy¨Ð€ä.±YU¹ ¬gõ:ŽBK)VAgNq%êv»¨KÆÖ*ÈæBJÑŧ~ Xô‚ÄM<†ü¿H2XK9Ñ+5_X½^/µ LÙýɬ©Í#Š™œœTí+4F·:< >fZ’/Ûã0  f1Ñ#·é*;€9‡Cbde9ªîAKä›áF¦ ¯| ÍøÁ`À†ÜêØF m^Qp(_ªäj£=ª ½æhÉ ËwÊSª³E/8:kbzÙ“#ÖY"ýa)2 îwfÇFGöœ®Üh‡¢‡)ÊU¾¶¸¸X¯×ÇãñáááÖÖÖñññØ&Êñ:b·ÏÌÌ\^^^^^ò¬©!ƒÕZ»òääd£Ñ`º7,›ô¾þ™‡6Iè%\ZZÂÆeƾe-0gAP“&¯è@¸MÁ³K0§§§www.W«U$«»8Í,ŽRfšâÀíím§Ó9>>þꫯò<,@¦Ñh|ôÑG333ŒžÿÉO~BrJ®ÊÉóˆ¡*z=ºªš •äcb²ã8¦Ó-0½´Üf‹+1Tô¡$‘Ph44ÊA›àl¨K–Sˆ¼Wh’O<ƒGîlV0oÊnz„Ô¯¡¸9ŠñZÒQ B˜[†ïÑ 'j&³¦ Š…&¾ˆM&±°Ì´7#'è¦37ÚñhØÈL²N9/Ká öÉ ã¶ª®/Ž´’t¨ ÚR!õææ›Å$ÈÂÚâTDžPM s1™É{i+ý¯ˆ ÕNÜ`AŽÓØ$›Y(±[b'±À“Ħ69Q|i<PRáX¿Çñ[¾•˜vKæPÉ'GS†ŒYŒQíïïïîîžyP-4®|­V#œ9>>¦‚ËÕe¡…aÈÌëååår¹üúõk.ƒjy™ë#¡VB$ˆ!‡b‡®Õjª ¦úLx_*•Тa23`¤G» ²I¼{»ÝFXæöövvvVl•GYY t¬'Èú‹/z½ÉnnnО_XX` Úíößþíßv:ަjµºÒ™ ‡CÅ¡i6Ѻ433ƒ'PQÜTZŠbÜvPv•ÞdgAÁ s{¥r9²ác›«; ´82Å;U¾‚û¡ <ˆEAÉO@ ý nOìÝ„\¢"&±‚óP¤I¸-,2ÜÅÅÔ6ìo–eD"Jú¸E˜TÊD¹ËõÜK¾³··G¶%0rC«üäx%&DGôkW ùx–³¥ŒXíý°úý>:‘$¹¹‘ËS'ÿËqŸ•“ˆÝÀQßÄßnš:•D¼E Œ¿ÎÒiºB`Sþrëú¢Ò%¢r³x^‰56FQô–þ/è~lYUÒ48.|bÓ.6Äfæ^œœlooò)ðcŸŠ6„a(L‹E¦1ó3(I-//ƒãFQDhZëV©T Œ2‚ÝÅÒ‹£é PÞ"¹#º¡ðÚœ5ðKè‰M¦m6›ØVp%î°ÈlX(mFfBB8˜AÝëõ>ýôÓv»=77Gb???K‹~uuõÉ'Ÿ¼zõ*4 ºÜ‰Iä&ÉRçÆÏíÖÁ•Fjí,¢ÈX‹92åY®46Z]x\ñáô‡'6¡K¤-5Âns£Åñ“(ÉÉ—ƒS>•Z›*éªü<©ŠÙêæi3ë’‘iÆfá$$B02-fl.)slcì"ëR"‹§-G(f!’Jiüof½,žz½ÞÎÎŽD¬ ÄGNM¥T*õz=µ˜ˆ+À'adò›RdŽ(Âb¯%6ÉãI6 Ã~¿”£2÷Ðb$ÜÎ>JŒLoìºö"7‘L(¡bó‘Í d,i k#›¬ºÐŒIfrÌ©“ %p#lG£ÑÛ®klþ½qbŠ«õ§"FõC®¬¬à©‚ èt:GGG(ÿŽM*S”ŸJ¥ÒjµhU£fç#É~¿ßëõ0pÓÓÓsss333ggg¨w²ü0ŸFâÈ4‚Q:îõzý~ee¥V«¥iŠx àÍb`ž(QFóöööìì¬Ñh|ðÁÍf˜Ÿ¡§XO2\ÌP"öã~ssC¯²R¤$IÆêê*¬O?ýôàà`vv–\£Ñh P\©Tvwwƒ øüóÏ?ùäí™·8 ª’LM ÕWSSÝ–Q–»³9Ï40ú \Åšééiz¼±2 ƒÂòÕˆ{îÆ‰'èm_‚ºhÈìúP†ø\#6t‚BrSw+T*A:,%u¶*OawB',»·''ºòåå%Ùqä”*DKTž~ssÃ@LQv=ºÇ:‹[#˜˜_$Ò­ÉŒ¢©Jex_9z4¡™F€í¢õz]|QÕ”Çnºmn}<™Ñµ†²J²;b0äNSA%Ñ´±©tÉ‘Ž+/S#œW… ~’­Í—9aåHYl|jÌÑÐ ù`Ñ% Ä6s=0ÑZqÓ€IDAT@TmŽÛív¯×ƒ¯ ú>A©TZXX8==ív»©¢¸ÃDR¢$ŽÚìì,Â+ÄX1P̯HT{ee¥Õj·+¿ƒœ5 €]ÖÖÖfggÙu¥PUG£Ññññ³gϲ,cdV–eFT£ÑH’™=fäBò¡`Qª‚©¸onnŽÞÏ?ÿ¼V«Õj5Ú777Ó4]]]%5{õêÕO~ò˜2l×#t}QcTeQÎK¤f\HÁtÓcÓK¡y@É')ÈJL0¡‰ˆ«/Ï,ó;]@qþœÈfGV8Ú˜‰™£ûó„D•RR"ãG¢‹; r©26‰(ñ?BcºÇÖ1“›f±Œó¡V‹:!×)wrkºÿ©º¥ £¨'µyÑ*·'ÖÁ+~€às§lÅ÷ck—KL›”ðSO€B¹35MdÙšÔJXI¾Cg(—\ºF²õcS¼â'ó‘É*Ü-~ ü9 ,‹\ ÖŒ?p¬%ŸîøìcÇGOØ"kžV«¹ ¿È&*.0çgÕmÅHíS ÌÞ%n¾|ä¬T IM1˜gÈÜ„ÄÀ ¢ùêdÇoòÈ J‹\S»"';wjDDØ‘»»;±"t¨kÎÍÍÁ 3Ùt0¾à b¨.‹V.-j; ÎAKL²Ó½^/Žcg‘äW*•,Ë8spüÆãñêêêÂÂÏCm¨\.“šõûýóóóÏ?ÿ|<ÏÏÏgY¶¿¿_,kµÚââ"Œ‡R©4 ›Ę&¯Û˜Ò`0@åV£R———Ù{HaÛÛÛŸ}öÙÞÞv™(€€p†ºÒcSòÛD/ü³(Ú¯Ô5Ðâxy6N¶ˆNJXw‰|æyo…Ì–èðȹÿú¼™ñz”V¤6Kî72!*,ˆWz’™S9E†#3&sb³”Õ%Ú—"kLã™u{e:ùìde•ËãiÔ*[¶/5ÈF“X°G^ï˜)¶qª#ÆC8U•räÈ5„ë&æN_0¶ U#c•[c\b^Ò£;õºÐÆâª 8mŸÐÈ JS:×Îò‚’όᘞ:_¾’À+"í.sã$ø'k˜ÞÛ)*(fnøªL¦’µÌé…êc«¸02ÕJ5X‹Ã”J%\Óþþ¾$‰Yn¼ C´POçRQÑÏóÆV’$ÕjUä†0 ¯®®ì®Óœç9ZB\'7t· ˜<;Îééi’$ëëëõzäŸ(†R]¡P8;;;<<üꫯdø¸ä¹‰ŸÑÆ|~~Îp08b 4Çz"kcc£Õj­¯¯W«Õ^¯÷øñãÑhôôéÓý×}öìYl£z2§Û¯x÷ˆ½‚€MÕ97OÅU¤HÄ…‘Ÿmž U!zY$@:¶-\>UWRcñ¼Uk“)Áù§n°MäÚ\õÑcŽlJëØ&ú¼&rcZ„I‡Ær ³§§§···¿ño‹Å“““§OŸ2&CŽ(p]µœcõ»PJ’„È+µq»,Zd3]Ÿ+‘×ð¸ÌIV‚@q'É€RëÓä­_”­G&×­´‚Ý'ºÌJ[šôÇØôà‰Žù8‚fdÅëšP`%n„B3~Ý#ªºö"é¨u†ØMñ‡‡Y.®®®0O`\l¬ [­V‰}Ä·ML†OÔn·iPÇÄc.ïÜDh#ùų$Sƒ™‚  gpz ¥É)ÀeŽ1C…„!F&#ð„Š×Y hß"œG‹œ:y<¥i™ëô›DEØÜ¨RƒU<˜;6¿( r·ìV˜ñâkÈSÊëj½r§•š”š¡¡c]y7¨rFb;Ô½¬JmdÓLqkx!!s˜'®„2J¬;Q(¶ ÝnÃóÔÅÛÝÝÅô$I²¶¶V.—á†@›Èó|8Ò`Hã4FðöL×Ñh´»»ûæÍd¶xæ‹‹ &Ú“9žžž‡ÃÁ`®/ÏXw1DüZ­6Æ«W¯æçç›ÍæÙÙÙÏ~ö³§OŸ^]]áA—@ßF&v, š| 4m8a̧€ÈÎb# ’ !Te 5~mÙÈ+qˆ…›`‰MTM‹ë]7ìM„ÏLœGiiê¦êfn’UîÆ/«X†H]§½b¥~ž+ºA*Ðy.2Aê^ѹIü®`a2ê'œ~R5;®‹öå—_’yA %°å^Œld¬8"  T\£¨*¯¢2v³8ñÌR–àëÃòØ,šÔ%©&‹3œ¹ZvP fhú™ÑdVrëÈÜH!â±Í1Ò /ò’ØMœ•1Ñßñ ‰kV›„ÿÛ¢_îÔÖýùS]YuÈt¶Bë?P´&º–¯ìúÚŠ¨ç¢íú•º¹¹aè–ªéI’”Ëe€È)äùªàbhQçÑ®Sè%`î÷û¨>2Ÿ“DVˆîpL­V«×ë›íA½Z ÔMê’üsii©Ñh¢ú@]éúúºÓé`ŽÙrÔ@ʶ··!ÅdYöðáÃv»ý‹_üâç?ÿ¹E2VpŽÿW1Eø’Í333™MÌT[÷_Ç‹‹‹b a YR²'émñOUT¼iÐeK­;Zü">ɰ±³©} $–]ð²™,ŽZ |ð.J´.‰¸/j@áàâðÄlôi‹.UdB})eÓÜÌÀM¦œF­Vk4Õjd@òLì¬ TÖðàà¥éÔ ™ð‰Ù§ˆáHLE+MSÆÇDCá¢)DâbÂÕö)Åëˆ*¡Ó"®,–®Ùlª ¤'ñÅ»ô~£eì†ikCskgw|t¢:ièD„¸˜ïÔCeƒb#Ùf&#£êÄØqÉD&©)øøÔLW!Åi¡§‘“¾†ï ”ñò–̆Hl,0m.àÐ’[¹ƒ1º¼¼<<<N.üˆUnD¢-êJŠ šÍf½^‚€h¨Ñh4›ÍËËË­­­ñx ?‹€KoÈÑðñ———ù½½=µÚ¡†Š\ J’ªŸŽÇãv»MÂXÃ]Eh%ƒ©ç;ß¹½½ýñü÷ÿ÷ ÔjÆóCÙ—g(_ Ñ,1ý±i­eYFS¤òfpD0‚R ‚;&s@NÁ73ãµk>0tyj‹ML:«$Üpoþ éT຅€„VDÖßÔ+÷d9*ÜäØô¸¥¡œ;B©¯+)ºá¿”¦)â`#jÁ&c Mù‹Hìøë××× ÷Ž­£@1”rã©Ñš`Ç#³†*ö+¹/¦€€›d©Ê  ±39Fjs#øóèèHšEckV-.pݲ¢[Æ÷Ç dT ¢E»86u³Ð(l±£}ò^EU£”Nf]¸äØ « ¡òåCy*Χi„FÄÀi+çÃÀ-R1Rõ£ÈMßU&Ün·QVdÚí¶¶œó=ŽŽ¸*ÊÀ9¸|òG<-¨<9 í ”ÿ£(Ò©©©›››ÃÃC˜bèmNMMu»]Éf!Î?55uww·¿¿ßëõ˜LAK6Aò°ª………±Í¥Ù7œœ|ôèQëëëSSSŸþù¿þ뿇CBW‘Ř(ŽÝp­3»+fÖYš'¿ÈÈͲÅv 8—_Tomn„)Õt2›§@¬*ŠÐÈ”Õq+K­ÍETš¢ðŒL•,7êf`Cº”°p`@U‘sFWSdu ¼×Œ@|Ê¢ÉÉÓD!‹ƒL–’:†81%<Ñ‹¶¶¶ÊˆM6µ®”wØÞc›<È«a¶€ö nŽÂáÔ)Òw”¡«è,„(µIwDëõÓÓÓ'''ZÉÔš|> Ì)6±Øx¹ªäf6ò:7Ê•}Ëb& DS$«”+s Šc7;ÃSçôH fHÌwÿ™õ%狆‘õ” ôÞ„ÈYj}öx ¾¡ C@QÕØ´»ÈÃî P°‘ŠYÃâ…O#™f433C`…Éç}‡ÃáâââÚÚ”®ÍÍÍF£!pš777Ô€îîîvvv€N{½Þêê*KLJx~~Þï÷‡ÃáÒÒRjͲ,ùéhNMM­®®$-..îíí½|ùòàà u*®*¤ÂÅÖ¨!NøÈDQ6kÑ Ñà`””&8%«16)8Êa‚U_‹LV819)x×§`J̹Þk„î„d)+â‰<Ú¾ÈÍdYðsh”…ÌÍÜU 2zà†T @?YéXjLwÙq,ŽÀ`Ñe½ú‚°^gŒï¦¨J­­V«ón hìäƒÇ&„%˜k©1¨>#‡Sh¢ª`!—÷J!³O?‰.鯧r§¯•iI…÷‹ë š&TC“Ù‘¢Tø-Œ@h=ƒ MˆæŽaÒÓr%¦|'#ZäÈ(²ëôÖ} gâm…RSàf &NèG”ß×uÄÀeÆÆ“B×LD;Ît¡P ±Cµ>-¥YY¸{yž3CTcï´ßü°‚X°^‡2ôúƒƒªlÀ¢ðEQ˜bà{¿ßï÷ûXL1Èüëõz°Þ©f‹ÅíímšŸI%Z­â‰#...P­Rûáìì,§g4µZ­»»»/^üò—¿<>>–‡¿AðMêf~Ä‘ a1aEdÆ m€#ɲ®®›Ï¬md2CǹÉwøc$×¥ ‘¸×Ê bè¦Ü?t„õЀïÄ}rȼ¦ŸŒ^Ã#Sñý‘™‰)¾g&Ä&^¾n¡`"?£‰5¬‰îaê4çÈ+90O‚Zy~Ž: uÒ(5 MHŽaú[£K1N7·N@ö[Q7{¡?´¶>_!ò§Mèܺ|•¾ñÀÜ=$ Žˆ6 ³_ô:Ù8ÕÅ•\ˆ‘/w¨Nªñ¥N9’S.òº7UÅ™‰Lá>Y(Õ"”˜é{«;M^½£Öáæææõë×#'J·ÒmœKÁÊû¹âxân¾,…])âE‹?¤ðMæ5±Px©Óã×…(xg;x}©Í¨<ª Td1E‘›„¨ònìÚå]<ž¸Æ %¹2=©uqêTË[DÆÝ] ·)Ü ‹›:½Ç5 &œÆ!­L;'|75b´^ŸÍ*Œ­‘X«†!Jl™Íï­D¡M“ «%&Ó5rŠŽšÊG:I‰„3ªÚ-}lX¥R ÃðôôôêêŠ: Á ZüZ%VõzI™_ ®&Mäy~||Ì¥}ùòe»ÝöŽÁ÷Íp¯àpÀ›–¡~%5™µ¹ø#trw6+´ú´VLÞ"pú¿hææTÜ7•bœBjuš!ˆQ…`‘›„éØ$€pa¹0ˆ 3C#©FÖ¼¹V[mFè{ÇwæŽ;J¢-Q ]]Aõ¡I˜ Üd/ ³ Mŧ©¤~Mè$ê‰U¾ÈU#£PñúT¨¹ÆLàÌCô+—ËŠ[UÕÑ•x¤"1é1¥r:®d3‚†9$Ҁˌ 8eòŸ'†NÉ#´N ïe%Rš9–Vnü¡L¢PÈá©­ŒOg—šðÙÛÎ%}ïäíÊ ……†Ê§¿¥ï# AA»<˜Z=ó?¶æ’üþl‹,Ë »¨‘…QI©qÄc“VM[Ž»Í†²,$©uYãìq‘…ñ5«ì¾`æÄZsëòƒr‘™BC`SZ¢c›v¡Œ˜½Óh/ù¡ÌqëLVD°5¾S“ð"ùÔè¾T:Ö_Ì,±)i3'Åõ6JÕçÌáîý§* :™u–¤&£Ø/±Î#…WpùmfÑÆgw:´†Ñëõz\¶F£Á½sCU•+æ”ö1&I¼î±'’ÒÒ|xxøêÕ«/¾øâõë×yžÏÎÎÆqLï-Ð䉴3ÚKólB ¿éõQ»"¹-8“““×××gggôm`Ç'&&–——uè‰æ¤´Ç_fÃl&ªŸŸŸWÔ©ú @[Ù0«ÌhÁ ¤c“òˆŒKEÊLöÊ^Èâ`&TûSŽäE äz¹ñŠ&ÂËS1³–0ŠF.qV昮œ{8¨ ©ô¹þËuÅÖð \52V´ª–|"qVöÀù¤ý 3ÖRhÝc‚obÓç8Û‘T>A¸Ä½ÂÚÒåÛä‹ÈÄ¿”"ôq>å瀞YpÚäçFÜQ5̸æbÌÉ‚ˆ‘§ïdÖ Å‹ÊÄÖˆÂê£-esÊ yr¬áè¾0¿²¹ÄT@b7–9wäRABú´øÂ <½•8È™å„~ùvGÙH9öÀ 5Þ`”COÅ#Víüü¼T*¡{ϨrG233óæÍ›±i-¨îΕ–£0¬<Ïi›Ð¤IñIØ(Ísj®®®677+• ×’î¿Á`ÀðdJă7)AFùúúzvv–ôðñãÇt ‚’ìïï?}útmm ‹Ææ0 Eªb¡d&T@ázc¯®®*•ÊÖÖVh=+¹S°Ö©ÞìÙ”„°ø¡MÐAT3ñItæV9Vó-1[).ÈKdëÔmÕ(xe^93QFnTbcõd5—ŠÓ(f©l™0&òë”ÊÀy@×##b«éW”cúÐC˜,ßGð:uÓ S¶¢LŸ:ÍþI€#•êÜJœüš ¾|l‚÷zZžmrr’VÄÜi^+g•rÃËLi–HúB ŸØyßÍr©†„TL9Lž(ÁJÏcˆ%só”$„A€ø¼¦²Ìø¨:‰Ì§l¤~G!™çVhhuîêb©(Å»O~O/Nä}ùE¼´[ÓÓÓ¼ìȆ#ð‘4✠Ð7´ wºc„Ù¥R ´Õÿà±™5¼yófnnnaa'ÉÀu Q["21fŽ¢è þ˜$IˆÚLÔÁ`ð—ù—8ó,--}õÕWl¤°•4Mid‘z—ζF—VÀAÇ´Y„V«"õÃ+ЬÏIÊŠÝ”«ç¥x—»»;‘KSÓò…¹%,¬*§„´µZMœ\E`OŠ!Ò«Éóº/Ó.¸B*Mª–§xA>ìFÀÜIÄñýÄ&ƒ*›HLEW¢ ‘ÓŸñ)î7·6·À¨m‘‰.TÄ6G âšéíd%­ÎBÉ9á+€Åycß#'9G…JA7oªr¼êhALOOÓ+{ö Y÷………$IƒšÈŒeæ$½~ýšƒˆÏôÓúøâìL§%µ¹ :[lŠÔ‘£ƒª*«-À%0}»À4ó„ys´w¼¯Pvà#5EmÕž”ÍñA¸â”Êò¦¦ß@Ù„·æª«)ZÎ '!$.2NVäFoy2 0/–V[´/b ñb¸Þªi†®¯*·vYöð8têº+'IB “¹¼XÞBc6ó¡‹à}±eQŠA%Â)놠ƪb±´nð7*Š>ð²Ò õåαëì]wQ›>‚f%º'c÷¥[\‹¦?qœ=öWÀ( rÌ%Ñß´È)äÅnšžêW8cðP_“A(†»#¤ÌóW•ëæã¤¥ÕQ°–R’›$IËZï„Sm¥ÆÔMݘ áV©c± R›ªbìt•nÖT™¼Lnƒï…š«FÄཫHMÜQ廯U«ï½ÃŒˆ}9µ™é²y|…Ž*&óÉšŽ]3'^:Ïóýý}•ØxŠh¼m†ƒÁ ²Î€Ì‘b¹d‹©ÍW¬ÇbãÁ¼…ôsª ùæVÀ&¼¢¬36-$«XS°R Gm$59 HÜÄÄÄÊÊJ¥R9<Õ áu´qãñ} î¡2 þÎ]Ý:wê lä&#²:6‘¼Àè0ôÇcIÔËzŒ\\\ tww×ëõtÇHñT9­ƒd Iø_ ˜à©øP òp¯•¼WlÂ)±õl‰_[O5^slòê‚D|ÊY/‹bÙk&³™u‰õW‡FßͯYO ðfQãærÓ>MyX‚±BQ'¬’‚8ëÊ2Ó‡z«VH›[¡V¶Ó#WÊ— #²þ5N 1LLÂ8rc=v®Ð¬èÆ\«Y†w V°Á(ü3þÏÿù? Ô ŒÒª[íÃ.~SÉcfdל?n&GŒ€Žp­Vƒ@ ÒzVI7’$Y]]…gY40jËM×1§‡ëX?'g‚[´¹¹É0,uç!ö"”hl4¡]•ç9óM9$€ƒ™ÈÜc j¼/…ÅÃÃÃn·+|ñîîûÈQ)\CñTn<,%&Q'‘‰¨c$Ÿ’UGJa¡ÑUS2¨ýY95BSîÔ¸#ªÆ»çnŠ@L®47 XJI¢Œ¾˜BUSbCÇW yMSޏ÷…21йäöõÏ‚ÍXŒŸ¡2±O›eE‹¿¨­2uâË2db8Ó€… dGrãy)nœÈ„ –Ô¥£(‚ …µeL«Ív«’¨Æ/²!òÉcPjã?J=7tMõÌ7Q:V.—×ÖÖPmS²F,/ؑƌ4§âcf´^qb#ëØÝŸë®”‰WÚ: šÌX™²_2/ÚÊ·>•ŸÖølAüÉ–mæS)½×cQñ ±)=#ÓN6ÂÍbn¸DLµZyzzÚëõÔ‚‹Gˆªh‚œ¼ˆŠ¯XL94â)ÚâIÚyTèƒÁ€Z!™&bµÊØl6ûý~ÇÃá°ÛíV«Õ………f³‰ôUžç§§§Y×8LÕjummíåË—<$Ƌñ³³szzš™X…€IJJ÷òåA*`«î£„ŠЃ¦ÂiD˜f‹C£2‰—9ùZÜ’ »™k.• õÙ‰¶rO+óSÏX‡‡çÝ ƒJ¥2Ã0@ŒÐªã•DëÜŽø±r–uæMZúΆbÈ…«!WDf Â+¨H§+'©/N dry`eÓáРob…uì2—”KÂß‘EQ%ÌA¦r6,póŒ3£kRÕQ.9¶>ÿ‘In)<|§š¡×÷Æalrì‘£×È(‹®!÷£Ê€¬­£ÞÖ•Õ.ØfŸËFÆnâ£@VU¦Æ-&Ô t·°°P¯×‹ÅâÑÑ}‚O>ù„ÇÒ<ˆjµš˜bïåå%ˆ’l<ÓYzúõ®®®h*ܤ¹ÉÉITÞ„T” \oKºW¤' †(—Ëârµ°&Fò*¨v©T| ¿9Žã………ÙÙYxÉÔ&&&Z­Öññ±è¬’éà 2WÎ/ RóæÄÓ§9æ·’/2~*¸?4tìâɼØeÐ+ 0p¼¡”·OMŒE,6©V«©/§Z­J%O!¹ív[ÃÁÎÎÎt„¸~¸þ—3€#¹æ2«=“+¡t8²öUÜ’0 N©¼º3Q&%HŽ F`Þn·%}1e1Õ;<'ÿ9›رø¹µc¸óA055Ê~~~â~uuõòåKìK™|‡Ö o&+‰G¢¦™˜ £X¿òWüÊÄÄD¿ßÏ­O 5róØ„%Òk§|9w›Œ¡Jnär!†òÃüsdj×©Íæ¼†!c>Ò4­Õj4¸*2aÒˆž˜Âù~bÍðüɦãÃAñGN‘®àÔ£xóqgÓ•R§TSTaˆ°-qèKŽ4ÏÂiA¨6µñŽâL$ö8Á&¡fRB'Æ’;ApŽ"¤bõ æ&ßÝÿÎæÖ@nÀJŠáÁ±‡Ë"!3Ys¡:ÂOi"¢ ‰”×ô5„̤ ×* £"FhÁôù¦§’ zSÄ=¶IB¡A¸àw&ÆÈ¶©ó;rÂZ™£±ÅÉì©>¥:¶ÑÞÌÝ{øðáãÇWVVò“Ÿp˜#úìٳܬÕ݆`PêÊxhÜ)ûQ*•( xÀøx]¥ÇÁƒƒƒ‚i³ÌÌ̬¬¬Up ‚ Û"Œª×ë½^olÊñèó Λ#!óBb°^¯#ö€Yyøð!"¨$k‰ÎHØâíÌšïu!ôaå¦t¬(CP¿(¨B*—‘MC:¶Q™irªDÙÐ:Áy U¸ŸSûÒG¦Œ¨ßb6™¾ª]<9yÐAá’gÀóÌK%U쫇™*¡MI!ªÜ¬]#lQáKæ˜65irŒ &±Ä‹ÜÙ rOiZ‰µà _œ Ί3¯þÁÐZ^„Ù…¦„‰Ô¯äF-Òœ.,Îùù9~]AÑåå%?}gl„ÏÆîÞÞÞÖëu´xŒJ¥98°ùW„T|rñÚ=0IuF)ýØšT …B­V[__?99!µD÷#²Q`Q¡àÞh4ˆž‚ è÷û“““ÇÇÇÅb‘Y ý~¿ÑhÝTnŠYd1¾¹¹9¹¸8Ž=zÄÑùíÒ‰|»×ZQK-U!d@tEÎTJ-G(ièht*-+¤+ ­O hÂoÒHðõx¢} «Þ(´ÖþÎØjEܬñ?›B3ù~ä˜Ð<°QÌé¼Ñ¤)7ÉbrÃ)øSXg¸ááuQ!!c­¸™ª«L/Á "×.ÄÛÊVNOOã’$A7 ûNÀ‚5á¨ü{á•ùIÂ\]]Ñ Ä“ã-mlswH#„* ]\\P:çl˪zk%Æ}ŒÎTÈ)l't=ƒ:º*£ Ñ&Ôº ]ƒ012œ2®N¶”ZÒzÄœ¨ˆ3¶q:¾iF40A$¹UÊSGoUýEÕÐ………ÍÍÍ>úè½÷Þ›žžþÅ/~ñþÏÿ!±€µ+ѽ¹¹i6›#“XTi€{’Ûì  Sâ=Ší%[–ú z´Y]]]mooû™`¤'ûûû³³³Ýnwvv–ªá/U©TªÕêÁÁÁÞÞÞ`0øøãkµÚ`0À2žŸŸ_\\|õÕW+++år¹Õj•ËåZ­6—––Â0ÜÛÛ;99ñšÂÔDÎ’ &¨pZc—Ð_¨Ò¸ßN¡É'ûº?©µ­ªL‘›xÈØFFYÄÉ˦ûÑO‰ Ƥd*5é^‚P(zȧu…ÛW“ÇÇçJlfÈAXðØtAU:€W¬4»à×Ì:9<ƒISmÔ§-,,s,J•è3U2+O€GŒ{-‘Ue53 ãHíWMÕBÓ|åÀ¸´¤dˆ‚®Á4¥¬HK§†v…c€Vª ŒmLƒDåS§§S§³!x4·V§Ñh¤æ6żꗊ¬A’ÔÁg‹ØR›[ÏRcöõ˜ü~;¿›–ØoûŒ¥¬¬4°ê‡~ãßxÿý÷'''ÿïÿý¿÷wǰI •J¥X,îííé•ùS i Èxú´tm>$;àdÊᘪ4µoff’úêê*^ЈZù9³é¾ˆŽÀpÆ^QÉ:::*‹Ož99Y«ÕÖÖÖ&''©ùÌÌÌÜÞÞRÚº³Á.¹±‹çŽl lvŸKœ;1ÛÀHŠùà¾æÃK)<— Ìï7Ÿ{ÐØøOÿôO…Â޼«of÷õ";q´`Rr3 sssÌÖëõ¸B©@ý&¦íV„;rãprÓ#˜¥(^'Jm¼\‡±Ó’ά¹GÊ• Äx IýÙŸýYà„“ýUð/>µ&¯Ìd·tpù›››ï¿ÿþ£G®¯¯þóŸÿÍßüÍùùy½^o·ÛŒŸ¹½½­T*SSS’-­ëUp2Ó•ICîlèL9‘È%U1??E‘¬ ¾è Åb±ÕjmX&ÿ{vvF¬Ç!P_H–eœ6ÎPµZ]ZZªV«’›Í&x'mCˆ{T«ULØåå%6bÿøø¸ÕjU«Uœ›\Öû￟:häI䡜¿`ò88Xz°¹*´ã§¦¦XÒããceR­¼²®·*M*òr!½jGäæ!å&M˜à»:H@Ø‹Ôz° °‰¤„êb/”éÙÈ;Ô):ª—þ»®£ÜúUù"õÎY¯¯!¶N]‚*)æ6 (³!1ØúÜ&' S—æû@“³³³ÕjµV«±2øW|XææÇø2¢¬¤¶clãTÉ빃­VëúúšlƒÀV£Ë¥P©TºÝ®dÔðÁªr7¾ÀdqqquuUz I’\__ÕawfffüPäC27×Rçjl²Ú¦Ðúj#ãèbÚr×{ç‰[/Ëå –Ïá„‚Åßýîwå…*¤R>Y_˜ï;È[‡ðÂÂÂÇçææŽ¿ÿýïÿð‡?ìõzðλÝ.2’q?yò¤Ñh¼~ý=³Ðº€¥ðZê#e}…´eYFiÌãSËËË£ÑÞ aTh£}e¼a?qÓ-Á ˆM›¼ÝnK÷gff¦ÑhÔëõÙÙY\ñ …ž/^Ð÷ƒñ-•Jþ4kµDdÂ+®+Œÿ^¯G¢Ä0…Lœ%ê€YP8Á ³,ëçyNÙNбŒ@åz± †„N·Z!˜Þ1µVa¾D[¶ª´WÄ"ì‘ú¨3›GÛ)(ݢȆÚË2†Ö$ŸZ×…¸gWøðß;ZUåïl.!Ë¢bVhÄ+e4¹1ï|ü¥ ÏÇ€"vÁfMOOW*•ùùùz½ÎxpAcž&%èGŸä›Õ¬L”f§Ž þ+Š»¬¤-CÇ‘ëòsç)£·Z­<ϹJXM`KL ‰lÉœfNn<¬Ð±jdŒRk1µJ†,w-#nÎ\W2hdlDáô,`ñw¿û]&b§2“›T˜Èx™±æôÐüóÁƒFcee¥V«½yóæûßÿþ_|ÑívYn|hËæææþá?}ú”^B½{õŽÄÄKs$&¨Ç1Ú2²¡«««ÐöX¸óósMgÓ¤‚Κñ ‡C|>QÛåå% ³dˆóóó#Óš˜˜ÀmAðÕW_½yó† ú—ø–P" Ó“qFÀq¹®ÈΜžžöû}þŽÄûÑÑ‘U™‰ ªÕªðšr¹ Ô•¹)!l¤Ë ¿?µ¾9‘ž &Å‹Ÿm€•øÐ ™Jñ©èâMñ›u¤äK(ù|vG‚|DŠ8RyÏSù*{ÁæAäFU“íˆî7 »ð ÝØdrÓPlYk4‹k<1ù@Áyþvø;L\«ÕjµZ£Ñ¨Õj «S2—]ÖmwG~BvVo•J…÷­T*ò`¨bòHûý¾’\^âŘŸŸßÜÜFÙ H•ˆb°˜úȺìâëÄN_ªÙ™“šÎÈ)åxh)8áSéàiùìDy©à¦+ÿéŸþiäFTŽÝ€Cñ‰óù¦*A¼1a«Õzüøq±X|þüù~ô£ýý}ž¯ÙlÎÌÌ ¯’¦iµZýÃ?üÃ………­­­ííí±ÉïG&Ûˆxðà|«4M™¡‚õeÛ`!ý¢Þ“ÔìTcÕ`xÔ05ž½<99‡€úJ 9g•Jè tÙ±)_}õ‰çÕÕU­V«V«Lu ­5ZZìoÞ¼a’óââb³ÙLÓtvv™ãããã»»»n·[©Tæææ8mƒÁÀ;F¬¤®´hÙ¼Wn:ˆ©µžA¿r! jä¦ç.ÚíÌ” rÇ–‡Ô½â‹Ð¨Ê­Œßåõ›ç®Â"²«Œ€u[O_îæý1 \Ÿ§xmêô×¼­h`ZFþcê• ÝóE½‘¿t“c7¸8sbUÕjµÙldÑð(Ír2ÚÁayÁáp˜L˜eir”½ pP€è…Mo<C–ú Vôjccá.8 6‹½#ŸUPš<¿ÚW}i%p ^ãAÿ%0!61x5cd&Ÿbá¨çŸŒA¨Eü'ò'¡1JeJS›D8IÿptXXXX[[ËóüË/¿|úôéÁÁu4x:¨èA|üøñ·¿ýí4Mõ«_õû}`)ù=åÃàSÉq€%©c“%V:11±¾¾.SÅѤ;ZO‹h­ˆdvXzÔK*• ÷ÌÌÌìì,¾qnnnrrÈŸ²c¿ßÿì³Ï ülü×ìì,Õ=¢qð‚8à°»»»r¹ü»¿û»œƒÅÅE8Yyžooo¿yófccƒkEq3±¡8‚°———Pø4à„Ú2ý~Ÿ_—;[_k` ‘ÓW^ãS0Lž×-<¸1ŽB|BÇmQY66®|lŠ ²ò½*-é(+_ЕPþ•;Vm`Œ-L\ØŽÐ8œ„ªDn XnòêjÜ•Ÿæç},9ÁxÁ|‰)¬Öï]*•šÍf«Õj6›Ò}3[?øƒ^!5¶¤Ò+ŒZv¥RáüøäK#¥6ïÀøS$wL™›ššzøðáüü<8L`Íj©ÍCN§D[“®y`ID„¦=+ó­f Ey"ÓŠâ¯(êë˜2¸|(ÖÚÍ4Mã?ù“?Ñx’›pJ%ù:Öº Ј*•ÊõõõÓ§Oß¼yÓív¥ÓÄ’1qèææfccãÃ?,—˯^½úå/ÉMNœÒ“B6ê†À4jÝQΜ -Éœ‰ØÁ»Óyâ³ GymmÍ÷a×|™#žB^+øÅ_¼zõ ë€}‘1"EÒ– "ލR©^1|P@ïÉÉÉöööÌÌÌãÇÉòç%ÜQ}D pG¢\rdáUøÌš‚ŽÐ%Ý ( fYk½ÊL¨75­]ZÝ܆Üp`4ðcD~-í^º‡¨OÞHÅn Ó;©–BI½&ªúyÄ]ÎI´Ÿ©&ŸÎvèFò‰ÔÜCÖ#ðÁÇYø2kÉœHœL>¦R©ÌÎ΢—KÇ(UÝð¾²ÊØ Ê‘húôôôt’$dmåry8ÃSŸ—R…øƒ89®q {©TÚØØhµZ”‰r›Ï&Ð@@iJ`T{yGݬwz ù¦ú@åB„¥æF Lûï«â?Öiñâyž¿Å­< ZEY顼±øÁÔ¡øxƒÁ`oo›†© Œô•ebç…Báw~çwJ¥Òþþþ_|qvv†éa'•…éfÖŒ’™ìT½^'ÇŒMšš÷’&!T©Tâ~ŽF#Jˈdqogff–––¨Ól|qqñüùóÃÃÃËËK“,Ë0»Ta’$ÙÙÙÙÚÚâdDQÄHÔ8ŽyåZ­ÆØçÔÚh¢(‚Éø ¬öúúzµZ=999;;ƒj< «Õ*䆓““óósŒQ溤.¯yædÿaâPÊÐè3ËĦ žºžäܾ„þÈjŒMN[@xEf*ä…D6ZÉ# •,¶ û•Øx¾À:rb§Ö9¥$Á·jyåc&<9õîÔ©Y)  8‚Ÿ +¹^Õ <|®"r²_ÞyÛ'ûêŸ9ifºÐ¢CœO25žSVî¨IØ 0\ŒN†Ôvúý¾. vŠõ$Jâ:hô™ D7ËËËÍf“C˜„¬úÕd¯'&¦Ø£ôPæXÇL$²‘͘„§ÿ¾ðA^Ü‹O!(CP½v3˲¯q+…m>?:+WÌშvuuuvvvqq›À >Žãjµº±±Ñëõ~ï÷~oee¥ßï?}ú”IîjYÀj¾–ëƒU_¦izpp0²YfªCì¨Då—‰i4'''˜pBåjµZ.—¥QC 9…úñåååÞÞÞÅÅÌõóóóýèG···‹‹‹E'ŽÌ3C4ŸŸoæliÆUpwòåßüæ70c‰F£Ñööv† Y–½zõ*5’:^.2\J4rû«[,gff¨øÀzK­Ç[È%¯ÃiïWí™+˜Jzj;\†È)Þ²†E›\ïÑ¨ÜÆUrZ¨À*@PšÊ ¡³”›j@:ÅP¡ã@É u é¤"ÿ¬™LöZÙ¨ÖÁ€±›+•»þÙÀJœÓ·‚î€ÍÂÐø†•ø¾,² …D1FC£ßï«K4”[˜œ&ÏsZÍÒ4Å%ßÜÜT*•^¯·°°€XÕ! Vl x«Â¨Àмú˜¹uÃÈB妯ëñâ(ŠØ_V; Cl¨î¦BQ½¬|¼KDýZqãÿøÿcÑ {®º¸>¶D»Qù!lÃâxRÌ955µ²²ÂŠÿþïÿ~š¦?þñ·¶¶úý¾(è‹S¥~199 Ø„78>>fù4k¨hvv– @I/¢³³³ûûûì®<ê`0€„•[ï&˜³K‡ {‰ü^»Ý~þüyE³³³pA9‚„¬^·ÛêÆTÑó¥K•¦)˜:̬­­-ø777 X=<< ›››A´ÛmÝXͧA E‡Ô¤&xÀÿ¢GPLcN\9m±ÇËeqt˜@îÅ$”®: vнVf-(ZíiE›Ü£âŒ/ÛEFbŽMD·Òœ Ò%Å›:–‚VÓeW>âËAòpžB¨ÂŸ©àæŒÆ÷‡Wê1| 1MmEŽTßo ÀfÕëõz½^«Õ€tc)äËŽœ”Á)¤ÞÝÝÑoÜï÷q¨e%&Sñ‡ ëqn>,ØëÜÜ’Ü¢ÕÓC^:§ÐáÄiKä&Ý!û ¼O ?rf$L¢VHßÊC–ÂLǦ²ÍcmcÀ¿óð½ï}O¡¬JùºÌºIC#4c‰È½…þاÀÁ:Öjµ“““ÍÍÍ'Ožþà? E6' œ‚ѯe€©S8;88h·Û‚Ürë­Ã^<°”$I¨H1]U î>55577‡­©V«8±Ðøxív›ó455uxxOõ³Ñh`õ‰á 0ÕàKiyjm½èöñÄ6wwwµZíìì ]šjµÚn·766>|Øëõ$·À®B‘Þ*)ÐÅà\__CÓç 錜 ëMD8,”4u:¹£_ uæÓRƒoo(.*Î:çJŒ•™|T’™v¥LOdíÁ*¤¦¤*Ifëm¾µX¦A”9f¬®Ÿ@bžDÿTÄäí»—ä¶S'•¸a+>Ü \ASUãÁƒshŸD(‰ ¨íÀN‘ú)íÅŠ@®š‚3)6Í’ TÛ)&`~~~vv–n%¡|RŠ¡û€D(À”PZË‘ˆ*Ñà"7¨Be=ÒÔZÐBc´¨nÀuN’$þOÿé?…NŸ,¶¹§r ò‡r­À|ÎÜÊ–WWWäƒàsõz}mmm<þñÿq½^ÿéOúüùs‰4h§E±… %R™:Y–­®®Æq¼··ÇÄæk bX]]åw»Ý®^–îåÃÃCÖ‘T™ÕĤB_ ÄKzÍ¥eyy¹Ñh …_üâív; CÔå¥ê](ˆÅÚíöäääÚÚý_„ÖA0§‡§luuu<¿~ýš†Ç<Ïçççüõï|'˲­­­Ìõ»¶†aH’?²yèìÚôô4ý­8aE“Kæ^rç6¤€ÜAéb*—2ʘd2üc„®o^w6Þ.11¬sl_“TÅS¦Pȯ„‡(¸1K‘ mæŠÎ§jâ7Ž%çÏ m暨àNg=wTlÅk¹ëD =UO’;Újàè¯ü“–½z½Ž¤Õ$ï„(­ 3Ê—PUù²¦QÈF@"U¶Uì|iiiyy™‹µ1…»Yg®òúÄu}$´ê°@•'æV).ØÐVÅž<¶óÔ$1TËH/Ú fýP¥0*³Að beI@r×5ªJ"±Rlý÷kkk?ýéOi ëõzoÞ¼¡îFøÊ²ªw‰'ÖXàr¹ FËZ§6å©àí…F5&bJ³Šô´ŸžžK3 Pñ#üﯾúŠ4vuuõáǼãéééÄÄÄêêj³Ù„‰ŽQÆeÜÝÝ}üñÇð•Õ(°··7??ÖÂññ1”T¶wŒòÔÔÔúúz»Ý><<$°‡}ôÑÖÖðÖêêê«W¯0± ­Í­ýEuß±õœc5”¸ñFšM ÕZ8ˆ­V‹3~RVìænÙ)kËì lN"¨ìþÈ´’1%,V‡sdL"™*Eû‘»U¿'Q.ÃΟçFFõ8‚EàÔSL6ÉGL¢’ËEެ#<(0êâ¬ÈÉ6DN÷ër»Í»‡Q†O±ý¤år™Jô³gÏDNHßÍÍÍéééÒÒRî:„6‘„P)ƒ÷%Uäry!ê’<¶X#ãûB.¡É¥N=Æ×d3£¡ë;œ1 I˜+‰O%”QÀŽ1š™™QWŒZY=@7,lVü½ï}/rí5¼åØt2§ŠËº{`L_È éÞØØ˜ššúì³ÏjµÚ“'O^¿~ýOÿôOl¼fç ÌŒ•Xcm³ÙüðÃéƒ5~qq¢¯&¬È„ú>úè#<Ïþþ~§Óán4óóóíímD,YzоV«µ¶¶ÆZŸžžB^ív»M¢(‚—ßétž?þúõk®1T‰ñx )Ÿ GA’/Ü™R©Dð;_1¡Á<’ išž1ؾ{§ÓY^^&ÎRÿ õ)q>Hq@!^t»Ý x65[h•$n§ä*¦ ~N Äµ³ "R£F €ŠW x•„׆sâ¢RÿMLXð³âz.€ç`¡À ¬>:í-½‰v+5·‹uéÕ‹ôšü]£c7 Ooêã3UÖTLôÄ®´]61pm¹,òääd£Ñ`Z± yWVžçy£ÑàŒasÕ»£0–}Ñ#”-ú;²|+++«««¸|õáÊ"ŒMî*3Æœ?0™)½(×R¹!²ŒºÑÚq E¡«"p¿bS㓹gMXR©ï{ßÓÒ žð«é}‚¨UGÇ„“?Ã3HÓôßøÆþþ~¯×£´ÿüùógÏžù’Š–F Ž~jäËËËsssH¤àÉÕ€ô£YüäÉ“ùùù½zõŠR.üõ³³³««+6IŠõzý½÷Þ+•Jãñ˜QM^ž\\\œ˜˜èv»_~ùåþþ>Ó%¤ß(„4M[­–Ö‡Õç­©X'nWn0œžž–Ëån·ÛëõÖÖÖJ¥ÒéééÙÙY^ÇÍfóüüüÃ?ìõzL0ÏÃÙO…ÚÌš¹èÔ—ãåIÄbO Ÿ’8ê8|tI³2“!Ö!¦,E¡‡ƒNÚ»– ‰ª•e9NÑMóŦȾ„+ézËD*?U™LÑŠÎ$®H{!KÉ/¢„%rDªwLÁ…ïd©ºÃJ||qP¡¨ ®¾9f†ÿI_×ÂVV*"qxÅŠ^ñîØ#h.àî å$+e MÔ„#ÖÅëG-,,pØd8œb,r–<„§Ï2v²\¬³T@å”YçÆÁªÓ…¤J‹©ÖŽ™¸Äõ´4avãï}ï{±®Ë]¿…ÜQfZ®áý&).9KFÐjµˆo×××ò“ŸP˜#Eê÷û@}¡„‹¬Í»ŒÝDø4Méã«ÕjÔA‡S¯×ëõúüüüÆÆÆãÇñ$ûûû_}õÕåå%f&Tžç`L'''„ •JåÑ£G³³³aîïïw»]6€~Æ¥¥%ò»ÓÓÓçÏŸç&ÑZqPì! \`}àj»ƒÞÕl6; +‹u<¿xñ¢Ûív»Ýƒƒƒ‰‰ ðNqâ8¾¸¸˜ŸŸ???gâ«W¯HlÕ¢+'ï"Ϋ`AOYN$ö–ªÔªøÈ,æ÷…©ÅFøÆ»ËL,6<`í\’ ˜ §HJgI¶Õgpº-$S­¹v1RŒ’aJ]k´rŽ~bCäáåF£÷HS亸<þZIÊ[X_LL–Úû~aÄéýGl.„ä8Ž///™\‡káK´Ïápè ÌÒÈfyhëu—§&ûàƒ¤°Ä3cûˆ Ó¨‚Ý­ÚŸú"bþö"ójÏÉ ¬àQ-YêÈÔ0U Kñ‹T¨èÒÿìÏþ,vƒÀäÇrS8àQÔÒÅßµI2U\ÚååeÛ777ÿò/ÿ"úûp8$Hñ˜yA`ºeüSÝD¼Ä>ÔniÙCË…&,hô;;;¯_¿Î² íJÐJ¼"Ò}”ØjµÚǼ¸¸X(ö÷÷OOO¥199¹°°°¾¾>÷÷÷Ée•¨!uª¶…Çã‘rÖÕ555/2!4Áôô4L.p¢³³³ÙÙÙÍÍÍ,ËŽQYY¸¹¹ùàƒ...vwwÕ” nNn#©u]`|pH"ÜòO]¶Ä”aO@g/:yÿÜIÜ%6äŽØëm‚góÝÔl.´X…Ì*]ó¥+–åN]5lË lø®j™Ó™»yyÊ\B§w$9)ζ¬bZU´á`zÔÀ΢ÊöÉÂú¼Oi ·•™ë% ¬ ©gÃ%C-$8«¥î·gŒ‡j&©é8ÑQÏdô×0`—8æGÕëuæ€ñ_,ˆl«ø þ#ød6t#]Çnà›Ldâ:s£žÄÖ}©Špà˜B±Uœ Œª÷»ß%½òÔÐwJ¾–!£.Þ¶ˆóÍfsss“ªÿ«W¯>ùäêñ´bÊ‹æ¦TZ÷#ÇH$’@ívww‰ÊMãÊu»ÝÃÃÃÃÃÃÄZÿ™¶¢&RÑÌÌÌÜÜÜæææÒÒR’$4'SXáŠÅâÇK¥Òo~ó›Á`ÀH.ᲊ¨ÉÔ¸Tåˆ×wc'5-ñYðo‚2æÐ`‹Åâ7¿ùÍ……†BÖâ#ôûý÷ßbbâÍ›7L% öáM%À[+|³ÙD0·˜4‚ªû\6yNö¥â— ÕÌ‘÷°Gª¾ºA@ÂK‰C∴Åò+àV™ñQSâRöÝ'qàú‰ ÔS$`H™ pŠÔ¼Ýá½o>t¼vÕÍÃû_¹£eùxê/á*XCyEd”UaÐD¸áp(ãN8)ûÎráegffÈøhAe#6779oˆˆh7x*†Ü[lR0’6›& /" :0ú¤R%©Íˆ°"ºœ¨j xrSæ&šTpsXÞÖŒÅÌ䙹CÉ6ÇK"z2©Ž¬­­5›ÍB¡pppðé§Ÿ²¬Ô›T3ÊM=wÍÅÖ ÷绾š´Ù¨s†p©Ò4e¬€Ø*Öjµf³)ÖÒÙÙ|Q]~«Z­ÖëõT¸¥M!4ÞÀx<ÆðÁ1%l4q3¡AŒÇãÁ`@öœÇ„Aj£ óóó/^¼HÓ´×ëmoo///ÏÎÎþÁüA§Óyõ꺀£Ñèääd}}}qqƒ¨äÁƒÐODå•1—t~aeèüÂ'ƒ³*À¡ ›E‹ŒùB߃RE•ÃqÝL0Ϭñ€Ÿá­ÁM²è®>8ÏÒÊL«ˆøîÛ5$¼)ª_Q¢'uüð̼”ˆì©õáG&–$ÄÊw ǼM ܬÝX-lx_d™VQ ¯ Ìwü½ðȵFæ® «4??ÿï|'Š¢_ýêW¯^½ LÃ^ý€HÅqÆðqªR Ç»àF%Mõ?w-J"s`¶RSYHM¼d£Ï|Œ™Yo©˜n,¦è¾¡ Â(ŽVu(³6#Îsî8q8ÉÉÝò%Q¹J·B&–fàjµZ,DʬQ£’’ŸEQ¥RÛÙh45¦üq|| ö?¨‹Å À¬“““7oÞЋÀ»ŒÇãF£¡1³¬@©Tâ ‘RàšåÖa€å"˜b­FžçèóMMM ‡C†ý†axqq±°°Ðh4æççƒ `¬ÆòòržçgggüñÕÕÕW_}Å¢Iöº@nÍî2j¹Š¬YëO%Tâ3 ­•d¹ 8ä ™¦i©T‚"]0E+œ9©]ã|‘=qê~5|M€'WA Û¡9Ø5ý°ª~«'Ä&g¨HèH¹¼ùNܨ-|-5ý(ŠÞ6R&Ná̯¬wbÞ#¥ö…¡¢¦Z2•¯V«E0ßétÈ“éüÒ‘åqYe®7‰ ßþBiI0R 61šÊÕª‰à|›9–Z›+Ì{Òu`x®^„±ÄÈÁV...ŽŽŽ–––hª"¤BÛ;²0À)@öûøø˜¹ó °uûýþ_|±´´T©T~çw~çÍ›7_}õU­V»¼¼<==ít:kkkµZíøø˜µ®Rž~„¡ã§×ë…¦;Z#^l:“¹Í)NïOüx<–æzâ$âXOÈ2påÐÿâb`¸‘1Q¬”e™zž/..jµ¾¨àØ„n¼%·N*ÕÞò*œ|Z¥•›Ì‰å‘RkçÍJ†@T5Ÿú&›±“'VæR°áêÝ ]ÉLh±n»Ï¡´ ¹i[¦n–².T`Býp±Xœ››ûæ7¿I§½:ÞùLbGp#›»S0í½Ì&ýc ˆÈ2×¢@UƒšŠÐ(¤àºi7=§:/~‘#wgÓRµt>Å&xŒã˜‘Ñ‘ñ¥´Goµ’Ñ`ðP‚>ƒÇpŢ̒Óq:ù’öœ6¬!ˆ,E¡PÀ¶²€ »”ûmÅDnüTl=ñ;Îs§¾_X)¡“ŠE†Ì÷XHyFè¯D ‘ëTá](> U{ÅØ\Ye"r™²Mž. N¨œ¢¹È±=…- ò%ó‘›nœOHõ‚Jm‚û :e\k”\…b(Ö±òš˜(‹_^^v:âbŽ:‡_A´‚2zˆ;XsÊë¼ÚÜÜÜãÇÃ0DXIÜ4 :TÑ@·V ë¦úLîZ¸C×ã­â©Âa¬DnsHCG¾!bUôªN[ãë¶…Báë|^¡šˆ*ÃG>°R‘¨®ü$¡AM·ÛEf ŽãÇS‡Ž¢èææÛ©Y&™õ²&üÂѲ¤9ÿ0 Iè¾@ ÄŸT¬Çí. DÑš¼ðDF¦^î›››££#ªŠH)A@+[%vhÈ6 ¤533S*•¦¦¦Z­Vfä]IAbM¨Jukww7ÌÐ|°¼¼<!4œœœÌÍÍ---u:Ñhôüùó 666ðŸbÃÜèYœ-Ÿ=rJ %~ÉŒÅÇQQ\<=Ó”ó4ÂÇc=ü¨°E—?4‘rè|ŠŒˆw¸„^g7ìB©W¬ý|hZ*VFÖÌ»¶»±Í^—aJL'@v-4X=rä)9HÝU%ÅJU‡Uf8â› ™é‹û´H‹À.¼cô¹›Ó£X˜_Ÿ˜˜X^^þã?þã>ú( CDÙU:à$ð j Ø>5U—ÐT$ެK¤¥àuØÀunl”ŒG»ds9²õ““•=ËÏ#˜™£àïZ–ÇÍ}3üw¿ûÝ¢ ·ÈîëLgÖˆ§,ÌG¹2¢c›ÅDò|qqñÉ'Ÿt:v»½¾¾¾¼¼üw÷wD¹“÷“ìÙ`# ³$= ‚”êyEL©Õj’C”©&éˬ½ šµT¢¢(B“|!æPäëÆã±úW¿±J¥R‰J».Š"¾™77ö@ïV«u{{ËBdÈ1 '™Fÿo|£ÕjmooŸœœD®“Ž''ýŒãÁe =|RR65°Mš¨_èë[+4ÝÌ8ÀúK`TfZFbë’Qu  4x†ê¦a.Ñ>ÔÏdn$Ÿ› Sèz_#¨ÓHßñ7_áO亚ßI*õ.rõ¢éòèaR“»³‘´êÙ”ÝKZÉÕpº±ºó>éV´"X³)1|Œ:W0óPË ÿäüs˜ã8Fw}}]’2‰©'êÌޏ xBÖ\ˆ[ìøn*5øˆI{*£¬ï˞ʧzôI[Spƒ5ßÚ&\t` U‰(!ä_©„ÿjÏív›Å‚¯øòåËO?ýôìì,2Ž¢Ô ”(‰ì¯ZF·ÛÅ] AåÆ~(±%Ø,ͶáV†@•T Y•››[XXàa\ ƒ‘?–J¥÷Þ{Of¸„¹µƒ±‹XŸv» =JT` ®w°„uìj 8Ì(ŠÚíöÎÎÙÁÁÁÓ§Owww×ÖÖ=zÄrAΚ][[#gÄ2òÁád’$&aÈÛÁüÀ¾`g#Çñ‹Û­­,Ú*ÌAkhsg )¾sä”s˜p켎à[xv:$#Ù„‰§dá‘8qA¸BºØÊ©g‘¬‘¡„ÆZ£Q¡MMò RÓDÏm@–/5*—w!t“~d%žå«Š¿"›Q–»®L=†+ÙÖÌHˆ:9Ñ—“‹zï½÷~ÿ÷nn.0Ý4>,@j œ Ü8—DÀq ò‚Õb“ð§zµc}Ù&­¡BKeÁ²ÂÚC×óšÎ‡‚ô؆Ԉ]åÃLõ<¼ ÞskŒÎÇ¥ -4þ‚Mg¸hþ»â4ʃ`“¾¥izxxø“Ÿü„¶Ð&5©äÉRÊYáÊ·KÞOÓ±3›‰ Qê&wEÖSáQÙ/gè†úkæ­ Eûº[~¿ '0‰‘Ðq)’$©T*ßúÖ·þàþ€¢s`Œ"=RjÊÔ,/gs#S"úeàˆf¡k#‹ˆEP\"æZbj¾ó<6¹Dë'Q+”Jß’õN¤ÌñV¥XЕº)¾æãÊ’)ØS"“º>CT‰Uh¤Y¢ýý}º4œß¼y££'ˆœ “'2oÁ7ËåòÜÜçCq eG€¥{ÔÚ€¢È.ye yÐÊÁ€¹tñH“¯!`¹¹¹¡à²¸¸ÛôZb=žVùìäääÞÞž'aƒÊ+6áC¡Ý3d³Á§«Õêòòò‚‚ çÏŸÏÎÎ~ûÛß>cHÉâââÜÜœ–“L!7Ç J¸@¥Ö:§½àKf/+ü)icS¨Æv_]]¡H5#4R•b.ñ ðÔä™Õw P%%Rï·uÏ rc«û† ùmY ÒOÕ³‚û>‰©Œg6¦Ô7ßðš|ptBGëI˜udZõºx¾I”º!)ʃtµbÊ•Æ6Ƈ-I’Ôëõï|ç;ßúÖ·X7Al¸m=ª.lwŠˆv;¯¯ÍÅÜK¢nlÚX¹©å)° #týᾘàO—Ž ¢jojò¸ÿØ5Øsì…J SÐú5ô˜Ú¨[™Ãð>©]FJÅüghådäèÈ¢Unð ¿>˜ûÔÁËåòâââ`0àˆ+Ô9?Q]OÞ†’RA‰lÌ$ õ©Ùl àüé½»»;::ÂÆ///Ó·L2%kŽ¥W&Ûn·A(]]]v:ÛÛ[Ô>!“-²%ŒÉ|üøñää$ìyóïÿþïÇãñ|ððáCšZ®®® dÅÖ—O2Èóˆ6º¶!\Dy,BáþOµ¶íQ„ûÊ*(ÃH` Ù7ŸZ-¬”–¸El“WÈ+š“V©T4ü5r²Å:ÁÞì*°Rê”9ý5Gn**R`«´“ 6¿Gعò¸Àõñ(“• ]™_­* ÜZyEy©É`y”gì¦C+3}'¸øí¼2pM‘°¿ùÍo6À:™x qšÄûU›àE|¤ôÅd» ´åqu’ÙA@e֬ʉaåËê‚ l0Z躔ԂCò!™ÿÄtR“¢‹哟O’$’ ŠœZ«3-bâĘå"øh–˜êV«Õjµúý~¿ßçR1RÍcöé Ò='§c®‹ÎõB›Þ®w•x~¢§ ëÚÔ(ìB=Ó4%_Ã!4¦†°pŠB///‘Êb–{p}}êV³Ù$ d›éI–'a­»Ý.#Ȱ‹£Ñ¨^¯“)3‰xº…z½ÞgŸ}öë_ÿºZ­>~ü˜ò à·ääe¶U(ª"ò’HfНôèóñáy6/+²~æÌŠîÞ8²zÿŽlHì„F3c±’›àáAòx¬ªt¸ƒûÓ§x.íc™NK{·¯?Ö ã'xÉL¤lWáXàq„ûªB=6 BŸÄ½Ãë/:¨k”ËŒ—“¹‰g>qK¬w=³âæÄÄÄ{ï½÷ñÇ7›MU·XaTs"écÊ"”ËeØ!:йÕï¼öÙÈÆ‹ÚΩS~™žOdü,å¡Byfó̱jåÌ”–‰þ¦>æ>¼â~­J#º —_¯˜;)"`¼ÈX'âò`qNOOS-; ²,C‚šz‰ ¨MhÄYéÝÄÖ’V­V±€ 9d1à,Rž-6š²¬÷! CTô²(º)þï÷ûHî1 ‚¥SÇr§Ó!aœŸŸ/•JðqÓFCªËµ§?y8rš‰;...°×uBÁF‘³žùüü.ûz~~þÃþpww—£,ËÐ/^XXÐï*MËmi ÍИ‰ iËÂ8'd×Êår¹\Ö]n˜WÁÍs ²h~£F™¢MØæp íÙ^~L¦¸^öø/påT>#FBZ p×DÆ'ôX›0xxj* —‘z'Mïw)VFQ$r@`L:Y4pè:mõ¾Þ™|Xçó#ÙGÜɆ’þ»÷ï–——ÈäV ­»ƒ‚(¶UôqÖ'vò™1Hn"#Ð%&s¦ºŠ^Yé$k¢p,sãÂûÊ©Qv9œ’fVêÇ1áv`LQÝr$‘`üØëñ¿Çñ¨J¤õø0GGG´à5›Mäñ`0¨’Å3ñ'Ÿ›¥*uô÷BÏaÜétbÓ™áCr=Ø Ò]lŸÆòšJ”rÛëõNNNh Ñ,uåÛâOžžž†aºt}}Ýëõèæ…î÷2Žãv»ÝëõtUŽFQ433CçÍÙÙ(þÕÕU¯×ËLP„Ðß½½½ÿøÇ×××KKK Èi ŒpÀuå¿D%a®õØd fÕ,ÆÆ‘bË”D@"£ŒH'øclÚ^¹µrN¨¢dn¸.1 fåyÞét”±G:šº> LQÔ3vª5‚œY[Hïëû°Hh±¢r%˜:E‘k{Öa~'Dâ<¨"“Sw2±†YOÎòÑ“â/‘¹³ß’å<¤ø@ÿ¥e-…ãN»UfsÛi’Ï­¥QäÛÜÊs8NÌ„ÔG0s* s÷µ°‘‘Æc'ÃÀ‰lñš¶,6ɖئø¤Ns=2Nµ¯Ehš.›’;šÔÛŒÒoRèd·ä^8Ü*xån´„Pye8þò—¿ÜÛÛ[\\\\\Œ¢h~~žá7‚E¹ L欚€`FC»ÝfD Ÿ \f&üRBÅw>¨ãF&ÄLµkˆIdÃgìõzûûûY–­­­ÍÍÍ1ÿN-ï¬Éh4BÆL³•€á _K¥R«ÕZXX(—˼¹ìUm¸ùìÐx<&L£ÑC“¦)Ó.X lôÁÁA†ÍfS© ñ„«™‰&F6}+Ïsêªã°ÇÒŠ¡N¤û ø=Rb%pP,;¤ÑýÁYyžc¦ÅÏ2íÑbÐR¯DÊ‹*l{ŒY=^G(§ð‘ØÍ°bs‰(UѰŸÀõHäŽËÎ*f;áªàþÐÌÌX5º„¡«¦'6bG‹£Ø32A‘À} kÓ¥õØ\æ$ÃûÔüÀñ¹×øøñã?þX<)Ê,?ýéOå˜WÑVÅú«øŽ¯SÜ÷ ˆ¶–;Z,¹'¦Ê;‰ÂüNÝC6‹"‚S´f2M(‹)‚B¡pot Çå—¤<Ü—’PSg‹[±µµ511ñøñcÔ ~þóŸþùçš>â8š\h}•Õjýi2£Ì üµ  Ü, X ,ÐÔÔ‘Bl£«tõšdˆ§§§»»»aÎÍ͵Z­Z­66ùåü¢JHo†ÇØ;———WVV–––Â0„kv}}ͲÜÍ)`Ué²fÐ.yY§ÓÁ0­¬¬`U Üx‹ÍÍM–ŸA·r1¹‘§cÒT©&:öŽ;”B<è³¼1뉬Ù%С²€Ì¤DÅÜã2H.÷ ”WyºäÀ&îJ:†Wã÷õ#ÅS ròÃcÓ}WP#§XHÖP&›àKµyÝ[]BÏ~”íS|$s£ºŠ@t•öS§ ȉâ„mòfQ†ÉÇ,ޮ厹ª_ñyL¡P˜››ûÖ·¾µ¼¼ÌÙ&e‰\‡\š¦”_G6‚2}àÆ†zÛ$¨ÄÇ›2‘º¡±|`¨]SÚ+Œÿ%èÆClOà„e‹îP´îÀo1ÑÌÉh)¥»i×â§èÞ*‹ œ”ÿËð‚Ñhtvv†0@bszz¸!ÄŒuÄKpáEk­#'ÏsTS@cÌùÀÞñóÝn÷ââ‚w¹¼¼dˆ±ça1Aˆæèè(Š¢••TÊ:$  –óóóóóóƒƒz §§§a“‚éÖ§Þh4ÀøïîîHe= h!vÖj5¦ÐÓs~~> ¶¶¶vvvž={FOò;ìÞùùy˜Ç*Hè) MI(0€SR¢kŠU”ùÓEÑp8Ô%—U¦ðNõ] PsµsÌÏÌÌP¢åz¡¯ÉUHa94©#Ig÷õ‚R7^,t]«Â\ð©M KLUõ)½#„•ØÉ'DÖTÏ»ŒÝX³wP^¥i¾}GöW×Ga—¬’ÿŠŒ@¯>'±ad%c×t’;V½ý$Ðáæææææ&j ¢ydY€:!çÔÔqØ‹Ÿw©FÕdr+ÏN§PÖŠ]Ó÷Õå¢ó[¹Z­bRuªgÆDå´x´'3rU©D¡k2 œäžrìÈZ½°µ2«ÚFQÔív_¾|Ùn·¡±+AP@õÛ ù`8Š€ƒ'‡¬H4¡äN; BeÀlê_E›8÷ð÷!Ïó«««~¿OtS©Tè—&ß!“'qŒ3…Š1W1åªê L¢ŸXcbbbii ‘rÂoÂøo·ÛÇÇÇDO,õÕÕvsyyY€|€³Èú*xªÈ:ÑH ± <‰RE%#SX÷g:Š"ôQiÓáþKÓ.3ÊŒ¦9E6b<Ó ÝŸ#ÀIulb~„cz~¥íµnp!Å8ILiCŒOü•¼ðABMÖ9ÁF}GF= \ŸMh„lå‰Á¢€TÈCæøŠÅ«’#Š"[¯;;ÛøÕ««+ä8Z­ŒPM.Ð~t»]t _]]©‰ŒþÄÑ5!’Í`"iÇår¹T*Qa©V«ÜêF£v~tyy¹±±±²²ÂdF _<äÝÝô+Z[…¿`ˆ‰IQeÑ\{Ž à…0ÔÌÆ™ˆ(37²QRÄÇr¦+• ÿ¤…ˆEfÖ …Þ t¢)eY&Õ]а>jˆœºˆâ/ê»íbS’N†?´¡qÔ9¨B!¾G%³ÐZ— Þéüàƒ€ê„ÒèÓá¼9HTÜR£žV-ÕÅO,jnT[ÿv¹éÙÇFF'¼ÂT)kóÕ…H‰ëoõ*Õ±IM(2Àk†¦ðEÑfrr²wÄÉðþÐxð ^¯ó£ÑM+ÈŸÄ———<Œ¦<ˆô<2"Þ«ßï?þüîî®\.çyN°†E ~’É=©I/]\\ìííˆaÈ€_Ö0"³‰8Ì7“(­ I«bP9oB“ Ue:µrzâñ“ª£B¡8[CxˆÐDüÔ ð1¶éB eª8xº{ÊXU˜W \1‹ìˆŠÊå¹Ï‚>õ‹¹+{¥Æ,="1i'Âvµïêû@F¯#$^Ù™>uàè ¹› &ë郩ü¾N‹@~ï÷~VrÆÐø–¡±gAsë‚J­o4wüuy }v•eÄý Ô;*6Ôdbܳl¨Àk•G2›5ºùµ¹ëµÒÅDâé-)0Ê‚~GµRN¹nä2s7åM…• *•Êǹ¥ÛÛÛý~_â$›1Åñ"wŒH…[™&©æçEòÕÖBc:ëõ:±½€3 ,Б7àÝEƒTM' C€!9ÁŒ.//±q`p¸òJ ˆÔ˜ÕÁMFLF <²~¿ttD”àÉÉÉh4ÚØØ©™ÄM@áÎÎÎÞÞžÎ=`vß[”¼ý²,#´TK…jA|fÁfŠ(¶ 9^™8ÆîööVZ”, $õÀ*¿P¥¨Ö© VÅÛy[Î\lžáB[ft'aí:«c"èËóæŠ<1a‘€’w~E~>tí;|:ÝCqë#£§ÊøêÁ|‡Jd Ï·ö1£ûý‚x3¹qOõ&lrròÑ£GtƒEN(sm8 þÉúAŒE+J–‚ï ÀQaZ¥Jó¹UÆ6PRñ]î:“•8+#Vá21©‚º†iwûº&è˜^7pôJµºgÆC•tèqzt¾nh ¹ÕŒÕ—¯K…ß&Ç×™Å-•JJ$Eˆg 91Ãáðää„:WnÑ|ñâÍòé½Ã¸©+‹·ƒ$X †Ð g>ŸÏ *­ª²œE#ªSæêL£ä' ª)ÙàžÌzôØyã@WuM1¼ÞŠíù½•àtnοr›Ô”†hm¥Cò)²¿:[Ì ¨v+ãL@» Œr¢[uüµÊ°»!iâãȉ.//OOOooo¡·øPµ \]]Ñ¢Œ\…§ Ë®Þ# ÑMæ\t™–eÉ¿¸¸ Œ Q=I’lmm=xð`ccã¿øeJ L(P`}xxØh4þîïþîoþæoÒРñ(°„†Wâ¨(ÃçHib1E©ØO‘àB“8÷\¼ÿ> X¹_ª–¸§Œ®OyRÄL•¡§íkáÍÃŽqnãE6+[á…+¹;Ron\¤IeV·Î½*X8xLPé )ܧÍ,”¤¼Ä¯Y21åQm’±j±Û/ÕÃ2¬këOJ%¬<ùÕÕÕ_ÿú×›››œI™5'Õa¿©2±Z÷ÙÿjÄñ´#‰Y5Î_ëyR%ÙDfÆAu¨ˆSspd½IM) f$ç@“¸ð ½C•ÊÝ)pŽ*BgÙ_¾Ùµ™(`ìÙn·g³ÙŸÿügä³ÂbÒp½™yÝ.ÅHT8š$¬”jÔRâ©b–IQ?þüóϳ,£ä”İ|` C„¥^Y×õúúz¿ß§{þúúú§Ÿ~úóŸÿ|~~Þn·_¼xñë_ÿú믿f€R·Ûýì³ÏКýêW¿ú»¿û;ŽPÍÇN’O1Ѭ¶ËËKV‹†h„á:WÎJõ6w.•ø¢¶¥|5›MNoéBÍÚŠ*Ôh¹ëö•:‰«N£Æ$ÊI§±BmMdE øMCÖ§ã]EC ;0•ÒdÔÖ“ZkKishD„•áG,>¥4k@ϰró)QI¡´– É”ò0n=”,ú+䦿w” F_¡]%üÆ ·y½b“è¾#Ãuˆ\zûö-p= Õ ø)kQÑf9‹«”£i.,&Q'[[[Ož|øõ×_?{öliiiccƒ <=›“¬xˆ5lµ¹–áùÃ_V¡RòEÈžÏçh¯ä›J–ÁØWUBxªœˆ Sq +>«§EL4‘¶Ð§¨ù"µ„¯,£ç†½¶ÒZå-+vÑ@Òéþ$¶šÇáÜ, „³|ý+åôßV[÷uepR6ðYªNú·y9ë/ÌJ—[/ZÐð³Ýnwggç_ÿõ_% H¬Å‡%çi,Á c8}B$¼P-'ê$€&U3jA¦CËßš+Ñ$ ×=Jìó Û‚~ŠSC¼Ò=¯Êd¬¥™?”áÕ'„éJduCh•À%îhµZyž³Q¤1Æ…×8ð2v…§ïzô<Ï»Ýî‹/¶··¾ÀUA*if„fRsw¨¨IÉѲ˜¼V…ЇÏRL¤Ïo–oïÅÅÅÁÁA]׃Á>È*ÓA–vu–˜Ÿ7uccãÉ“'³Ùììì ¯?þñoÞ¼aü7¤Ñht»ÝÿüŸÿóƒ–bšYÝž<1ÔXD^A]ÆÌÇ$œÎ¹SéÔufðR¸}â{%y9Lgå]Ñ…Šb|€H·átZYçi½ØY¦¤ ‰+u–9“íø½²Þ}ΤÊF ¦6 ynÓî´SÓC$&ŒÖÓ^¨­*§P˜Ù¬Cå©ùÿiß–6±5µ^ßÚ Vwž‰Rœ,Ä랥fæ@ç?HÉè³Ï>kµZÞ÷£ìòT¨jØ+*WIƉþ,ÜÙDáñL  •'ªç¤ZT™ñA•Ígd¿+…_æy®ÏËÌjù/ö4ŠJ©Ù×*vjµ-Å€r1\‰éÜÈÁ#®£U&³Ž:6¢/t/q}£=ÁM«««½^ïÑ£G=*Šbÿýû÷HÆ™ÁÇ1,€‹$2®®®ÒÐÇVG+¤u€–1ÝÀa ?HÓ fO»»» ‘¦ ‹ŽÐ"u®ƒª,”™*o=xðàË/¿ÜØØxùò¥žíþþ>5óós’bô···{{{ß~ûíÉÉIƒy¥çJӔĹ »A'\$}/ÆÅP¸ÐnçYˆ½^Þét`=ˆt©™Ž§Ñs®û¢jÁrl·Û°çgѳàŽ<‚QuØÂ¹ó‘ö¸-N]¶V£²§y8+ÔæØW-v·Ô‹^ì tÅ>%3IWb¾4ƒ¢êD½×f’™š?Œ¢§¤’ú…ºø®ÛíBüÖÖGBþËjÎʲŒâìh4bų¦y5¬EÌc¶£ ÄÜÜ”8Úíö<,ÒÿI<)Á'¶ Së¡­ÅÜN„k»J„!þEýóloœ€WnµZèÚ<¥R©Nù—ªթyû6ÉU»ÆµÖ•Y>È8¬ÓŽ+¬›º´ë•é­œSèù#½û·s6x‡šµ³]J¡8HÈý©·Œ·Q›šà¶ ‡ØÜzT¼Œ†Ã}b¢Ö:ˆõ)Y& ñ¥§ªç_<+¤"MB²áù¶'½Â¨M9¨QãôD|!§cMYò8¯ªª×ëVtÈðà@jb¾VWW¿øâ l ^¿~½¿¿yyIõp:‚W©Ê•át Øî% ]^^Â[‰&S0S>‹¹ê£æ&“Éæææòò2SsÁMŸ}öÙÆÆ’÷ªª666VVV¤E¢·‘Û!óÂè¾¾¾ÞØØ(Š¢ßïÓ4“eÙ_|ñôéÓÇS‚|ýúõ¿üË¿àï.Û&bÜúúú»wï( ”á)̶¤ŽÏòÚÚÇ— 4D%iDÒ0ww½ BS(ü:zn`¬ÄÁ+^p~jL§S>E7•D§˜R'…›Ò=ß!¼¥²Tfª™5ÓdÑ SÛœ•ÌäïbÁ!û*þ(þj¿yÊ©£´ˆÖb¡AæÄœš«Eûm¶ÔuÌ+º¥¦ÿT*“›½ ¤–·¾-I’ÕÕÕ/¿üruu• CÃ4M)ž(`ô¨+ÓaHð! ¢¬z$‰*$.*TXPåLJ›ˆClÄ<”2ÜÄÈðò˜ßNÄÈâë/ìAzþAèFKÐ/+7ïÇÊ‘²à×uMþÂ5Qþã•ÈN¯PDæ`0p4!MS6I§Ó!ât»ÝÇ___¿zõêÝ»w0GˆÇP!P¼#³HÃKÙ:jêâ;•™ÎÍ? v&dóù|cc€o“ÒiÂêêêöööçŸÞï÷Q¸ €OÃË…4gÿþÏÿùÿø{{{<Àv»½±±Ñjµž={F[5àÕ«W|DY–H1>|øÐn·¿üòKœ—ÙW“Éä6ìíëPT1©^@)«Dk¨ˆi@ü™€Bnž˜îW{CiBjª%–)…Hµþi'”&ìNCZ›µˆgdi”ÆœãÐþ­L‚@êZÅ`í^+ýSmî`U¤ ˆá£K3N©­ÙøV†é•ªf ”Îö*¬{UÑ¡¢ø,•zº÷;P…{ï÷û ‹IG!›#M|™#HײVa™Y›¬\‘+‰®#•ð*–áš© ’…mÓh©Q>HWÜ/ä«®ësG‰âöUýuŽM¸â½(btð¦&¸ Øcd“,ª™áB ÃÁ†.œ‰eD£ÑxõêÕ·ß~ûã?ƒþºÝ.*sÐt:mÄ„»*zµ` a‘œ.¥kW¢V±ƒó0öa)1Ìó|mm &³]!’.ãz½^§ÓéõzzÁ¨R•Ày^¿~ Ø<:::99áC¹ë>0[pgggkkKÍØÝn÷Ë/¿$Òßà rS´I_\\¼{÷îÉ“'FI=.+l³µµµG={öìèèèÕ«WÃáp6›íìì<|øðÿïÿ}yyIùYkN w#6Pò$à´)# ÀO ±¥W–-ÚB MH²Äš##.C+Ïn$â'á¯ÈÈRVðÜðåa« & ÏÝ¿2™8²P“­Žú$z˜Ó ‰˜žú‰ãƒ¾¨Â»êPjjž;ø%1‘¤ÿ*OÓœ¢âÏ º)a7;­½;»4Ç‘Ôj£ž<Š¢JÇì<¥gIDAT’dyyùÑ£GTcõ (~Óál¥E(d—fE«0-þZÓñ®DÂ4.©ééÄýñ¨K«.ÿjñ"k£Å?ŽÆsŠñŽLT“¦©Æ¸«Ì,¿JDj£ÛÝÝ­ëš,šL6Ä¥sÔKŒŸÇpôœ°?TÙ–oß¾åÀ¬ë™5þ‹‹ %’÷ïßßÜܤ2Õl6QÕs=ô‘9r{öìÉ“'/_¾ÔÅc[¼Ü/ì¦n*Fò ÂyKKK´ñ³Òü´#.Ì«ÜPÇÇ9– u4{k„²cÿßBª á@ÝŒâŸïaÅ9YêËè9<|Ðy 1H!UDÞ}qqÁ\ÂÄùù¹ OtàgYFnÈ¿nmm)¾+µZ­³³3^çh4‚¿ç $&žl6›ƒÁ@èšš}«Õ¢é¯×ë½~ýz0@÷¼{÷Žy‡‡‡“Éd4µZ­~¿ÏÓÃD™ß¯ýë››‚8†¢0ñ"S ·Cý«¿!bbý"R3ÔÑ(¬!⓵ž†x- ¹'“ÉÄçhR"О‡§°£ ÇY:ö•馔¤Fô΃Ĭ¾…;Ä”k“+!P¤Hé2E»ÿ¥b„Ÿ¨^ÓŠPº…uR™‰=f¥Ö…“…®Bj†Ú„àÜTjdÜîÖÖÖO?ý¤Ëk·Ûe4*ef,EÐûÃTêÉÔQ‚äE«nj#aR\KMQáåu®?WEÌ V‚©Î4 ôIô0hIè2>>}ÀØ_…Å2y3A8ݶ„Æ$Ià_ÐÎSs‚ ]4¨‘æ½èòò2‘ÅÀx<>;;+£¡_ȳˆNTÔ@¢r1–¤…V›étªöi”Vóùœ(£AŠÊÎÎÎz½Þúú:‰a (£‘#%ɉ$‰¼B†0_]]õû}Üð‹1W•ÑÐHvwwùË_&IòOÿôOtr2u¢,Ë¿ýÛ¿ív»úÓŸ¶··ûý>{ƒ¤{uuµßïÖ |ív»Õjñ^½z¥ÌWV!äÅ®îÉÂæ\çª.£Ó‹jÑï1µ’ qçIòË%qï/òè&I­ JÒ»M&x•[Ï ÿ[[÷Ÿv²ÂPµ8›KÙ‡×y‹Õ„Ô° ²rsìãåÑg¥M?uF)·ÞµÊÊJ»¤]¦{©LµÀ—dô¢–Jëìñè–¦i·ÛýüóÏÿå_þE±U/«~{иM¢•=_ †*¬Ór›Z2·¹îDÏ0Ý"¼e„[U¿®m¤ˆÜ>¶F5Щº5”¥˜µUFK„„È¥µÎˆÓ©ây;ÊŽápî` —ŠÄUø‹Ò0Øét8áõЕ>Pb+Â.êøøŠ]•G® ŸU”±jÑ ,BC«ÕBl&¹6× y}}ÍŒ€ è´ŠATÖ`èIHɪЯSæŸÇ^¦1H™æó9…¼F£±µµuyy¹¿¿ßëõð)|ýúu§ÓÙÜÜ|÷us~~¾µµ¥¶ðÓÓÓº®WWWONNþøÇ?bÊÚjµ¾þúëÕÕU,ž-ÛÛÛÍfóêêêÉ“'¤ÒÇÇÇÌÔ@m? ÈR‡:0Ù¢üèU<¼Dm(evºé»B‡Ê/ æ<Œ§k›ô§~7e—*`‹¢âV±L`MU¼ÜúÃò°÷¼T抪¹Í|÷e¬(¦-¡Ü¢ˆ¶ð:*èz"•„/8kEQ)FèɤQßð†£v¦Bª¬;OLFŽÐ y€thIÒÈûR”!¾è¥0ÍÛ!­ÓA"˜¤¢­óCçq :ª¨pnñ_\Ej.¸ KÇwI„E­%Aã 0 Ï ”*¢“ÐÉ1ŠWй¼¼<99b@2ÎâG[^ÓUø[Õá/Q×õÑÑQ‚{ŠwRð8‚”Ê(¡–y‚GGGÁêhc•¯¬¬¤iÊàâét:IdÈ• ç•½CóË ee¥Ûíı‘%lllð70ëE¸_ËæD#&ˆÀ—ÅpïP%*±²ÉwÄn(§–Ý t>Ÿô$ í‹J¢,¡ÒFÈ æH{þ¿šfËðÆÈÂRAÊ‘ G…×7qaC(´"7ê3Ö]àâûV.µµ¹ÄÔ!¿Xsa$ÑOn]˜øÅÏL=/+ÍVAׯ¿O¢“üÉ“'Ïž=ã§h_Ë£Õ\I’¶žŸìhMÐP¶$¬WY]¸¶š›„¹iÇD§$Qà#¤«BÛ÷_Äœ'‹¦½øP(}ùò%о££#òðÕît:“É„–Ã~øÁ-Œ‰ GGGØ«7ï¿ÿ~0Ìf³ƒƒ†åììì¤1åéÐutžCTß”¹ ‡ q׋ý+ê”–´¢"ÁKét:êÆ'Z‡“Klj«& ù .•6¹2Y£Êä*ÿi·hïiõ+U¦tIs²hÆRØDiîëíOL«å!„¥¢‡WAá¯dÑyB!#[Ô²¦QÍbPÈË̤ÁY0Å6ÎÖÖÖ·ß~[Fçvmê5Äøfç cí9K£ˆ¾h)×ÔÒIZZ‡seŽ*¼èNóßÿþ÷’oÐôÖ%æÌ?ˆX›ã"Û’‹¦ÆLcóp8d½ŠÊ!$ÉQO°B¥:ä²Ã¦5{ö,±ÖüÄÊgÛÛÛÝnw2™¼}ûv6›á†Üét0oèv»777ÏŸ?ßÞÞ&4<ÁwbaÆãqS‘õÃ}’~â͛Ƒ"Ïóétúç?ÿù»ï¾ãú…1/..àæT6Íó\=ú ß:|`dó•jÝA7ˆ~)_¨ÞÇ—Ú4SÂ/Zu’ ºŽYÑ* _£ÚæÂ+sž…ß ^ö­.‰f”¨ƒ;ÝTÂ÷:¸ZÞ‰•y’"Ýoc(´n65w‡ÊZÒ¨_%Ö©W‡¢Ê3›*”võp”*R?|ø€ »*ÃkV!\mjù(£Ñ²®kf–bº¨(ÝHeÖ̹bÒÃIm„Q‰>îõzOŸ>m48U ‡Ãï¿ÿ~www:’® k”eùã?îïï³°˜¢Z×õóçÏ¿üòK>¹O%ŸÇ«÷Eò¥ê-©ßÚÚ)ÞÐ$†'''H1x;Iˆrµb¸q @,Ãä«6µi]#ÆÖûàUŽeIêˆæÑ8­àÂKägŤÂøÞàýÊØ£‘\^ëÐÅMIðP¹µ °ˆiRß>V5á/YúÜÔ¤úÍY ²vÎ÷Ž LŸv.O7›Zgem…ËzQ4ïÙŸP•oصµµÏ>û 2[š¡Û˜´BæŽXG +_lèÓé’Çl]^ Ú5b0SÓsi\HÒ*Ñp¬|ªÀð_±½¬a´“·15'ÿÃþ £ò*ö:««×$ÇàWùÔ< *ÉóœÑx\ël6cM¶%00.bä™q ºó)Óé´/ ZU’$.ÃWOUºg&[dìl†q s, –PDÛÞÞÞÞÞžL&ÇÇÇŠ®­­­¯¯—e9¯¯¯ÏÎÎh·Î²ìàà}«ÕF=þœ«+ €²Â& 1g êg}}}iiéôôá² n O> 'ð‹Á‚ÁîÏc& 1{†œÍ€ Jóå½ÇITgŸ² Õke€þF£UT*Ä#EêÄŒô¼Ê¬Š¡vujj>§KtŽê0cº|Oˆc)Fkcg1ÄD[H]iwøõ*´?½–—š«—§„ž d)*)¦øOù7+MÖCÐNÔ†×ÌL#™-ëE“øðá»ï¾ë÷ûàP.»¶Þ¥&«Ì¡Åóh)Q”ÃJ5¦´L1« ç½hqÅ\8¯<êtáC  ‘ªªòo¾ù& 3)O†µ,´ü­ ¡•æzΉªî† ®¯¯³Ö?|ø€·!e…<ÚùDiHÕ?~ŒˇƒÚÅëó0ÁròåIá S†½ÂJük>|•.™>Àh‰ˆt{{;MS‚ zWúN0ŸaâüíííóçÏ!•ÚíöóçÏiból6£¨¯Aóu]³ÃÙÏèv»­–ªªÞ¿€«Ñh¯x‚”„[ÌC%(ŒjïñÜÈRy,Xjáâ$Ée`gª’ðÏõà§ÚõõõxÏÿûÿï IŠ‹iÈPœ1•‰‚Î=RMlØŠ§§§´?|ø–„KœN§i(âʘLZÁùßívñ0¸ºº:>>>99!Y¨MbZU‚MJ’¤Ýn3D'¿¨´;1YÀÒÒÒ£G†Ã¡¢Ä$Mˆ$‰+++Nk`*aö=¼®’$9??¿¼¼üüóÏ?~¼µµµ¾¾Ž¨âéÓ§ƒÁàÍ›7¸­s¿\¢óËËˬ®®a}sqqÑn·›ÍæÉÉÉ‹/þæoþfkkëõë×4@H“!cY;¢;Ô7³(˜²ë(`;qNºMd!BA*ñO­VÅ2ЙÁgÇcäi”ÿ(•èàáùëä“tS‡"ÒDé4±µŽyjå6)ß!êQU r±¸××¼txËäÑ#Y˜¡Mjzˆ;YR/1ÓÚ>úÍ™ißïœ1Š5OÜ5^>»sB܉¿w®PßvppP–%¶úEt•ó}øðáÉÉ ~ž¯_¿^ZZú/ÿå¿…˜EŠ*Øë€+‰i¼M´`Ê­ÄykG‰uÊ£å"1ß"¥ÜQe ºSÞ»STYô»iW+ð©<'Ôe'Ëvÿ¥;DÌ·§¢öå‡ã¸x¨dqøsS½M}nþÅ dýžò¨ %µBa†6UHIEÎ*²d1‚ÈCž³iu4£Tÿ/'Uçi(¶p)T±Èwvv~þùg‹bË›š€O&VŒ:ø“)ÌNJªLÙé)ºÕ&Ói”YéSÀ ÑÒdn‡Í{‡ƒcêæ}å¿ÿýïuÅ™ Rýˆ(m¾HjÏ·6‹4‹‘a”ÏiîKÓ”¦J úTô¬Æææf·Û…¨|ÁÈ$!G(ÍCZç*Ä0Õ}úfÜÒ›ˆz¾ µì$á—„¸ƒÂ+ýþýûGGG0D©l§iÚl6%eà_§Óép8 ggg»»»h» ·‹¢h6›GGG¨.¦Ó)`m:v:ƈÒQØï÷'“ 9ì/~ñ‹¢(þÇÿø‡‡‡iš¶Z-1ÍŒzåœd-&I¢Šjeó{ÃE²“ånLÎEt  !÷~¨µ;:\¿¹¹™Ífççç %” Yžçô`æñõ)Ê »!†[K1µz_~¸™©Ÿ„ŒœHNÂF¦0£jO7|aƒF] ¯ ©©1ò´A’OüŽîH¥4~Êy•O›žC²¨ü’XózœþÕ¿ÇÿuŸj’à M·1™¹^TlÔaȡ׭ £ó^ØGòÌFXKK‰-l‘F¶mý„¨Š<7«C. 7'É3?*óôª¢QÞÏ.A;'ÿËhÚâ*áV°X‘¤Psý@1¸2‘>hx„ ¢ÌÕ„d% :ʘ/µçÌ.²ÆÒ|'”?ª™¹Ž½Ü&ÅŒº'“‰æJpm=¢!˜&Ku°Ûp8äJž={vxxX×5s¡•rO§Óf³IDh·Ûëëëbö±•.™Çw:ÝÝÝ_ýêWOŸ>Õpý½½·oß’±\8çëp¶‚OC9-‘ géÕÕU³ÙœL&’©’PŨ.)Hˆ2Rré´×Áx§‘…7‚¹Ì`³Ù¤¶[Gg/W‰¿GºÊ×TW ñLAh( U½¨Ï¸ñàH¸lÄŒç¿ô›»´æµ— ó“›sGR3 _ÕŠàK̘75‡œ;Ԅ⬠GäÌ„ÙB1exí²™3“Mˆjì÷û4{°}ò<ç d¬‰¶ ƒÇ“¨HhŽ× T+›X=R.£2ó8½qÖs­t;ŠeÝŠ<² Là ð£Rç›o¾IÃQG_fJ al1¬J+„Eaú]\\ŒF£½½=šÔÆéé)?«äECÞùYgÖ}“¬ô)ipÏj©‡ð1²ÈP…³=ʺ®…ŒðT©Cý¬ySišŽÇcM‘]^^n6›N‡è ’hÓ'cj6›<àâaâ¶··™lÈó…` Êu†è6Õ¹ ÁíÍÍÍ`0xúô)fxB~ýë¿þë?ü O»¡†=C¨{Ë­°ó9৘#ÉPøR&èDS*³ÙŒædq+áJ$‰ ,–1gT^W©•t”ÑH”›ƒJݬõ¢ï“*^k1ó¥sNq¶2í»ò,Qï‰}y±Re•íëOd^‹¨M*%ðÈùê{-· cŽ¡jÓ¸§&Ër ¥°{ˆ)jC;x¡#¨;‹ªm¼fbƒ¬â ‚éJêy‰tNC B]Y¼à˜B9hFQE¿¡Z´¯Ð ”†KWþûßÿ^ñȯIQ'áR wçne¬®®^^^îííQGkµZûûûüN"BÎ!¼Ök uŠÞ´•ÙqèyÁ•íM’¡6 šŸ…?ÖTN®˜£ŒYUR¬é¸ÖÁNE€ÇÄ ŒºRT9”÷I 87BþJ n8fyzë´ÈœŸŸ3J½X’$Ïž=Ãn¡Ûí2fᬤxÌ‹¦²Éü˜Ç¯¬¬`ƒ‡Í ¶ÅÄÍù|N³ôêêê“'O~üñGô¨´VVV^¾|‰*\£å˃"ÐÈöSw­m„Ezr*Õ_ÖÖÖD< Ÿb´3ÕSÆ£S2[‡)íp8ÜÝÝ…Žd(,Ÿ‚%|m6¾™àÕa§õs‡'Õz#B%& v\v¾U”úNV¦Ï=rSªð–æÉ©¿LBRY¢”Ÿ~„‹"ð´×±@‡(0Ä̬ŠSëyV˜K Š×©iAŽ«ê@º½½}ÿþ=¬Úà_zl0ùP•k$Ìf¤¨§ñ#°+ü™SÜ›ÛÙεu ”Ö„PÄ0$çãÒPöh‘äÑ#ù_X.OzYUEXýW‹JQÅxP8K§± éÀÑû÷ïølÑá´ò :Ê5 œÌš•P (Þ)äáZauhµy+òK£_IZb¢ªÊj‰³Ür³ÙÜÞÞžÍf{{{÷îÝûå/I×-Ö§§§­V‹&¡~¿ÿÙgŸÇcôŸÔË>|˜eÙ›7o®¯¯HCx*ˆ‚ä…(C¯ßòò2ö{’z€7IyDÜ2@ íÊÊ ÅSÁ^O1¸G½,f22ŠBÒøˆÂF]‰ó&}F$­ˆÂ„רÏ*!Õ"=¡r5!¦V",Í— LBˆ”›lº'–,z*X!e8±ø ˆÒœHkóãʉUGf͹¨ÚK=¥ÍWÀJMäíù²Ò=-i¥: ¼>È®–ØMÙLb-8^ÈBN¡ôÓÃeó›Í&+)çM¿ß§)…QÆ´×:ÊÇxvž(¬ƒXE>ŽõncDE’$LE(£µŽ¹SâT|§vm£+øýJ-ÖîÝ»—ÿîw¿HÑA!¹½b^}ê©)\uî©yB3¾y|¬i|ÁÏÏÏá’tjQ#Ί¤ÑŠ #·Ò7pzÃgóKȆˆ’Îð&´ÎxÁJê˜g]Ä|în{{û¯þê¯öööh~¾ººÚÞÞõËOEñþýûÍÍÍíím –Œž™þ‚?,<4Õ}6Õòòò_|ñ×ý×KKKüãG£Ñíí-”çh4:88ûPlJ£Çf®ÂÛˆÀ¡”¶´®$»‰õHŠq€ðÄ_¬‡úþË6‘ç9õM\•³˜|&Îfa¤Í¦NcŒ„WZÖÂ)&êïázÊP#×!Ñr&»6í’‚`S/¥ÏÌCÜ_›Þ2± ƒ2J÷R«©;ªÝ!”™•] 6©Ê¼- ³xóxÍ—ö ÐYb"íúEØ`§KòÍ;›ÍÇ Jò¥a6, éWncVBªt0*ùSÔÆËÞ'ÆÁ=‘QÒ©FÓ…pÀMb¶Q\Éòò2:Mž-«h?ÂQ óe¯í+1Œb¹8lfÔ êº¦E™x^NitQé\ýðáÑ*±nRH>e­„!@YaCÇM`âNÒË|S’ÎóÍ$zªÂ ³'ð)¼¾¾n6›uÌnc€ëÅÅf¡ˆŒÖÖÖF£>oÞ¼ùÛ¿ýÛ/¾øÅüíííÑÑÑÑÑÑáá!Ê2GT¹ÊÍf“kûùçŸa¬¡«¨ M•hKgQ÷¼¼¼Eš‡O4ëLU*‚šö§šl¤dá(Ãr@dQ¢Ê|¹ UWÌÕÁ?±CÊID¯L_ª´Ñ%¼ébÕUqMße>(мY–iÁ×ÑØ ÊLÏ“HÁáÍ¡‚yÜmŒ1®ªJÃî¤ìAªRÜ ‚øétJ¥al/ [}‹xü‚¶ê°Z–Òø£cŒØJÏ{¹brÕ¶=Ù%Ï:`(1u½f³9Néƒc/žžRÒ" lÁàÔá'æØOxè!B›ô¥Ü0At?ÒŸVÏJ8.(}Ê“pÑyÅ5@Ãsï{{{îx GȬXÌåååãã㥥¥ÍÍM¸2òïððMµ¹¹ùðáÛ››Çs…oÞ¼‡ãñøûï¿×ɣ̟øöö–^¥"Œýõ¬xÍ¢««ªÂµJ'‡ ­¼×7³Y$˜ô4°D”H؈¹/<¢Édòþý{ªÄÜ••ÜµÈ õÌ•% Y ñ«–bº½jsÚº… UML®¬À'NbíÖÚ®ó0kLŒ;Ï­S…MXj´t®Z¥=*!ú'§œ6÷EaÝÛ€•¯å‹0ž¸égýoœVw‚,5±…²Q±ZwJz¤ûûûggg¤)<“f³™D÷%û«Ž64 ÑRœ[WWWPyž#³Ò‘Àj!Ÿ 4Aå¦Lß)ÆPGNƒfÒ4eÉ¿4ßðåååV«µººšóÍ7Eذé„U”›OˆBx¾¨þf:Ìf3â m4ÊòŒóñH~pdy~Œd6uu{{»ˆ)/ʃ ]úý~–e³ÙŒÓW!¹§ôfÀWØ_®\):…|¯‘ù=¢š#Xðøs]×ívûòò’ Ïǽ{÷ÛbêËËË(é»ÝnfªØ±¯®®^]]Qv hP×ÖÖ¤;á’ç9ã¿pzåMknv¬‡¹yXž¹Xv<aOøÄ4š{%YRèGþ&àpyyÉŒÂétʳÚÜÜ\[[ëv»Ð «««.ÚrnX1HÊ@ñÙ"³¼¤#Hû3 × AûÔœ6ïÀŠÌºêãï“ÉÖ"7‡EÂp™1ÕVõK¢™1†M•´á3k`”ú§¶¥àsmš)sÉ'ºvßÉÉ¢¬ìÎ áÀ`0xõê•hÎ6Î01ŹagyÌÃMS- ˜\-e¤¸µqœè3øA­LÖ³5$:•·$ÚÑx³ª ”þØy㹕óSþ—â2ÒмÕV=½¼¼<==ÝÛÛ+ŠâÁƒI’Ìf3’~ðøø˜[bŒ(ðOå'èd©Ñ@ŒÌbÌÿÄM²F±@ Ì_‡›yVI ÚeŸ#-㤪—"Žp3›Íx© e$Õ’–‚œù4HØI*I¦²ãñ˜ )ð‡^¼xñäÉ“½½½V«Eû;àˆK´-c’-k7ö+úl¨ŠL{˸–'s.žò(”S²ð¨€GSZ¤½]›°Cïwooïàà€òz|œÕo¨æ/eëJŽÄ0èlt‚¦²– —¶»¡Bö^ù¢µƒwe6ubB•Ö±WÅy4qHâ JT¥2QÒW˜¯_„ZE \Ðí§6¶®^t4hצôO÷ì57Ó.‹Ìºsà@~þùg šÜV˜o˜‡ë4¡¤ÿð 4ÿK@㺠D³(ʧp%[|ˆ/ö/Ç*þž:8š{Yc³´sùZZZÊÿð‡?¤f·&¦.‹>±¡µ”d’1!›¤*G¾ ´b6›Ñ—Dša-·1$’gª´œ’¦ééé)U _@y4¸×Áhl<–#8E£nÒè g!JZÅÀ.[NµH‰VpH£jKpÙØØÀ*‹‹AÙp~~~vvF$`---õz=ȯ$I†ÃáÑÑQžçäÈ`lÑ©ßYÚD´£Jó9P:‰œ¶Dlcß«è¿AФœ17SöÑhDÞªžªÍÍÍv» º¼wï^»ÝÖ‘[[V l¶hj¬¥l½¶v-Bb“„ˆ<%ÚW*a«ê—™ŽA!CunÃ1àè‘êáÜYó’ž6œ&±éõb¿tbÝp‰ù+d&PP¨Vл«L\êhË#”vkºØ–¨èvssóîÝ;설@ôåb[wÇãòKÖÚÜÁVI8p®ÃYÄVÿðÿP‡®—<)H­9FÐÃìÚp8ã 5G£ð ; —¦®ž›w ›_^ìÜ0‘.±þ{¦ ç’$!¿uwÓœtÊAWËJ‰[æé‰ˆ°’D¨&’…&–à‹\¥¯J ÎÅÅÅþþþÍÍ I£%šÍæÞÞ^š¦Ífóýû÷̂β Ì%Â3A-Á¯®®r×¼é:Ú Ò˜v›Ä ‡FÌ"Ò¶á°â{`(Š˜—K†(^°Ñ ú«áp8Q ô6˪¸×&çdöÈ•,ö¸©|&0(šß©w¼M¡¶,4 ŠôkëS™›-_e£U]Š©ƒÁY‘t±l§Ëv©”¶z*Eñe~©ú /Lé Eáë4Ê­y0µªßœ7³ú¦ƒ³lØ¢ðK8±.“˜æ­~sIõœóèKOÑ.­13‹*ªDÈJ$Q1‘M§ÓÙÜÜ|ðàA«Õ"*)o…ÐÐÅ,³Ñhäß|óTàZUµM4TO>1çOLj11¿„é£Ñˆ¾$¹jàéÓ”ªª0ÄÀœn·‹êŒr¡â f‹æñ%Pš†ŸÛ[(]¡–ë„ $qÃ.Y³ëPÖæÑޜĔ UjÜéq<sÈSb»¾¾ÆQˆ…K¤f Î3kkk“É„Cê÷øC`« Õ ÄC`Dz²!õ¥ç€™"øªc«°±K<„Äz²TØqÕ\ð{­c–…q}}½¿¿? 83ynkkkÍf³ÙlÞ¿ŸÁÂf°êh(ÓY­å´ó õäµíùÅ-Q…9ÿ'@ÂÑι9di· ˆJw–GKé…˜²ÔXÝÊ:¢õô—nK˜mN²(^½Cl)ri3ê#O%f‘™Å`¶X.ó{}}ýöí[1J­"QÁLŲÚĉùª<¢nù:¦r±q4g¯Gš$Tœ$€ëëëý~TE0R&.Oq—$‰KKKÈE´‹ mom.©Î:ásÑü—LŠm“ç9 ¿´'———X¾dÑýG˜/š™°—`‹ˆJ•u9”eÉä¥ñ*ÀÏf³*$ãÒ%ø4ª:ÔϨŸD³©}EAúMŠJf‡»‹ŸÊÒ\öîî={FåŽÉ}½^`4™LØ0Ngoo¯ÓéÐöüôéSþïÄ\œE¤®¢NªèXÄ\4¦­:†‚”ÖY¦Ä!‰yÔ YœZ³Å&g‡—™ÐÙÃ^\\œžžžœœhðbã—ÁÈ´ÊlŒ2³B&ÂÞ.U.–Й2¡Z?öå3‘„ŠJá85…‘pDaCUÅXÝ)Ť¡\WˆÑ†©¢¥±Xœ ¯_Å? DÔa¥’Û W– ÐÕ6ÇóD•ÒߤVßü4¿Ö÷gQ Sxrœ%hÖëõXE‰UTZÑ~TøcKÒØ^¸÷Fx=Š`ÍMp›EÝœUGéÔ£Ñhtâ«aS,ù%´Á€ô¡w>"8§µîuzˆ®Ó+Q-­™JL…@+wäÁVg¡×uMÔÄ`s}}¢©ÞD§„^õd«9>‰7BÔ@¯2u²–Qº!‚º!í~Uæ‡ê2Có™¦éææ¦öRzÈ“““ï¾ûîôô”§tvvE…Y(ôÁ‹¨×ï÷Ù~­VëñãÇÀ1‰w$£OBJ–¦)0Š%‘©”%(›ÌÆê¦Ñ¤šFŸšÎžzÑ6Ó¹HTcˆò1DÕÉ„ÅcÄ ó´`t+q~=º{¾8ºŠ»ŸER„Ñ™ÒöeL¹¦(,P)GàšÍŒôŸ…ê¹^£§ ¥;Õ±Ú-Ìêp­’T£Ø’rkÊñ£WIVjÔ»1h"×kktJ¢ä-¥¥WÒêõz=ÊͲÆ3![…E°ë‡rŠD¤Yˆ±y¶óôh†ÀGÁ7#`$™ Òí%´ºòP~<=°ƒø¸~ü-:oåáÙᥖT£Øy³Ù¬Ýn£FMB&Àœç9€ò9ÉÓõõu, Èi^)ÂDÉ´ •uððtä{ƒÌ’¥††;Ïó^¯§0ªtCÛ0̸;úK0¥"ŠÕuÍæšzš=›ÍÞ½{‡ñäþþ¾hlV3³m€±ÇÇÇÿ÷ÿþßo¿ý–>ÄGñüiŒà9CÞˆE+•Šg U‚J@<-VÒ4YžÈœTO+›#Y†5ŠÊ³ÙŒY.hbTDQôé(V=+±ÞõÔzG3ÕËBïîzt?Ù<:®ª3—Gï‘ç5ÊïðA"Ó(6eÖ™sYbÕ$ýe^ŠY(û]&]Ç—ggœè"˜çfÎYU¯ï6&Ý¥Ö¯S›J‘ų]žg¶¨ròâ¿›››wˆж`-Ñ»„ é²([WáÁ‹Š¥¶ñºÄj;I’à—›.–D98½Ò]‡r“Ý ¹žE¿÷ǺƒâT¦È©•ù` üÒ:P×a'øðáC¿ß?;;£*NjԑXÄì,üyïß¿ÏÔ‰$†çy~~~^†«,Òv6hB´ pƒ@#X„èQ‚fÔ›:µDQ×6bDø… €Ëbš¦Ýn—e7²ˆ¿H¯‚_]]Q/+Šbggçòòr2™t»]|û(_rýô9ïììÜÜÜ ‡Cd&%½a…žÒ:zâ•{²¬‰žhÁ“$ég•H-‰‰ èR±ìµ©+¥ÃÔnO£[óèèˆ"¯ocâ5^Žu8ÏUá´™Z±²6¹‚Ñ<\®4²IlŽR±ÝébÁZŸR…µëVD4¼GyLÙŠ‹MÓÅßQ¨Jsë]Ùs³¥÷ꘇí0…ú^y‰Â¹•)Âʰf®mðø8ÿÍNðe¦/“ˆ_A07™þ½{÷¶··[­Öééi/©éBtTú ”•aR˜ØÅJJOÊú%´ôÇ%øìäFnY}'9"(>>[/(°üt’œË=Öýauu5·~H2†OB¼ŸBô¹½½=99Qw4 t ¼@ÿ1|y§¡ŠÀ,ù˜ dLâ“L)]œv©à … è§¾´´D3Áx<A ƒ}4D‡ù|þÃ?R4FÍf³Ýn÷z½^¯·²²rrr2ŸÏñázòä •5åDU ò¦ Qòµ‰è¨âe1(…‹dà«jÉÜ2úò:*ªZp:$³ð·TL©¢k4½yó‰ÜÍÍ Þ8ív„¹®¤²ŒNÔ,üv<©)Í8EAdnóþªh jmª8¥ù9m:¢á÷h‡ÈœC2”Ê\YY ççç·õõu^‘‹\/I&òSûûû‹˜Äâàt"0‰ÐML[È+ÆRJÍ’„iD+”uêhÄg¯}~||üöíÛñxLp¤/²Õjõûýv» ÞDOë™xm^j‚Õ¶ä|Ä¥9@È#1B¢Zl Xˬ¡Ä!R ¬Ò^8Ýㄆ6OSŽ“ѧÖfè Ï‘¾ÓÁ]jÒyÕ…”*ê¦òEÞÊÜ.ÕA­Žý“¾t%Š}žQ:Ñv'cÇã½½==œ2:á«›êúß2kzOLÑ:7KxÍ(ÊÂXÀª–]2À¿( à“Ü|ËgÖœPEcÖÌ1êÔV׳Ð5 '+ΛCÆç[ŽOÒ@ÐF£Ñï÷G£‘üLs ˆ"kà¥8Š“hpå_!×Ɇ²hB[ɺïõzJ¯ÄC@@ĸº4—bÒ7ÂÜÜÜ„ Ó³»ººÚÚÚÚÞÞ~ûö­2vª ëëëãñx ëW_}ERI{ >È,) ¢k׊äz¸Gdk^°#)ö­¥a²¢` žRÈãà"[ÏCñ¤øòòòðððÕ«Wu]Ý1ºè9J¨2v“ŸÅû ¹ˆz ¤¨šFwNjÒ¡l±qDëͯ@µ¤4šÀ“pXK¢2¨oÖ)+…°7ýåÖ%ã¡Gü´R3)H«Ð*‹Àü‘ózmÍ›îÌéº UÆKsSн¨­7±‚Hb¾WÙbO’raO{óPW1Ã}ss³×ëÇcîˆT âIDdÃÀõF €“Зñ"Ôð~~Nèॣ® Í/S>Óðzò¨§ü†Ë¾‘N# m½¹¹)ÎÑ(xÁ½Ä:•H³OXÄWWWôs¤!{aÏcFhPáOB>ˆ”˜|§Ž ¤9ÚÒ`Â2ºÃtˆÁ"e1¼ŒÙ4s*´“ÄeÑd hÊÃЖÀ #æ²,i²AÛ=›Í677ß½{Gc¢^]×õ²çóùƒÀµZ­ÃÃCVÿp8D×~{{ˉbð5âÚ6,&‹fú4šÉWWW± è÷ûø²¢ã¾À8´ Ãê¤QœšL&ïÞ½ã)ÂÖ’9‰˜Õ¨'Ag»2J•MËEÿ¦Æ¢¹NËÔêS„•ÚFs‹ÄLÍÿCœ}Þž¢T4Zƒ¯Öžê}*Ÿ£!‰&•h1W1$\ЯZô†OMu‡Ûe5¢•©C,Î×¾Lñ®6Çq^|¸ó)<F<>zTPKG‘·×ë-//ŸžžŠsT½^pÏ£$Zè-IOÈa1}¬Â5ÅQÄ,¢2:iR êy`©ªŠ3×¼ÎÚ‰Mì*bNQ…çÒœÆt¦ñm"DBCr7ÌÓ]IÁÚÚ qyžc£.tÀ©)Ø¢]$¨ÍLù&¸ ã.ºÝîõõ5f$Àï|{{‹pv`˲Ô7øáxàbr ‹·Å¢ ?ÞÜÜ<<LcE•ÿÃ?üß'KI…ƒ;4þW™£tº('ÏÎÎð©ÒÌåååÑÑQ‚À4ìÓPB§1´¹ÛíÊ ›~»1sÚcÒÑð@ÕÊ›ç9¿juuµÝn×u=Nñ &¤iʆ”ÚˆF˜!X~3W¸¹¹yqq1 4¥µªªV«5[­V¯×ÃNV›v?ü)ÛA%2q>ïæè0Ø*Ïón·;›ÍßÜŽÀÊ.Õ™l­H®\ÏDúcξ¨ËÏïôôôôôôÝ»w‡‡‡î®%·¹¹¹¾¾.cl@{f„üBq"7”ÇùöPM3‹±# %Iø¢ø^ªM[äÛ^Œëç©@ s15é¼GCö¼Öž’/'ƒòOLf²Å^×÷°òô”gñƒÞæQ8³Öý™ ©’(Œ*å‹™)?µ=µOz×oÎL`ÉNOOß¿ï½åÂwâÔ«hoRŸ‡¦6 ª¥ìe±ïâ+E]y-‚±Óé4›MDUïV‡Ò‚ 5›Í†Ãát: ‡‡‡™úž$\ªÌ¥°þDfæ–tº‚ˆÐIPbl¿4¦îð›Q‡Wá9•ç9yŸ¸yí ¸ÿyø ã ¸Sfe-lïÉdRÅÇaúu pgNG]©@”‹ãÀ@ã矖©>®8ÇÇÇý~ÿÙ³g°þeY®¯¯—eùæÍZsŠ¢ yDÄ€Œ˜_‚ÖÆm41z„̇¢gÍè©9ó°Ï}Õ&ż…Nož'ÐÍÍ Üùñññ÷ßÿÃ?ìîî§îív{{{ûñãÇÛÛÛ´ÅãØç®XÚlâkˆ’’5å1>YlTK}¶Ÿžžð’¼jH+èxGÉZÎ0y´µ:$Z„—Îq’†ˆQäƒgRvX{õ' û2¾u“pé)£?,‰ñº®óÊBÒ‘†9¸â£© ­MÔήT”w.ÏsR' õg±ž$ñ¸pI!Õr¯²;iÎo^n‚ç1DÞA.ßÉ`ÏâÑXÆŒ%,¤“ôw•5Hñx!ŽÏÏÏÏÏÏG£ê?Šx]C…cÓÐëAû“šß›Òc~/*Šw†%®.¥ ¼2ÞyÌa'ÆS8àÇ%žþìïïÓô‡Ë .æ>9Çk‘KSqàe#‚ç)¨âÖëõh¬aë–eɯÅÄšZû‡˜Z*ñèÅ‹ëëërq€àÓÙí˜Æ òbÑ ™ÈB{rrBž«ƒTüIÆ„ÑhÝYôE¦![ ‰e#a:¶··÷êÕ«7oÞÌçs¢m3ÁidÝÜÜì÷ûjj­Ce“›º`µö*KP™µ,=³°^Èl ^-•‰ÎµFÑd¼ûZ÷•†øS™Q-D˜-j, ÍDfí>'Ñœâ}ÍË-+·Ñ¤z#›Š˜*ê)„ùa£W¯ª¿t zÈò>©¬‹31é C/†+‰‚š£°Ôê戴õz½V«¥”\Ý3r(ªB¥©‰âT ê|©çT@žÎ¼:ª.Yx:z}P—än¢D|" †îŒþÍfØã6^–eþ›ßüæY/ö"} ø«hÑâ`¬b¾#›VVVP$œŸŸ–‹S!hË&T‰‹f¢ñËzYÐ4Ä)?JMÙrÁøåéÓ§“É?–4F¨v:,Ë#]]]‘·+2R;ã¾ò<üø1‡áp8D‚;\zñâÅùùùîîn³¦g³™Ž)Zúý~Y–›››¤0;øþv»M×tCdY1trÎÃvUònIõ(ØÍmT—ô{u”„@RÃ០–ãÑÑQâc¸ 8ñ$Ãã²U²¨B ™† º×ëiî™–8b±ÌæŒÔÑ–(¥…:"ÎÙuêMSª­¶åYaý‰È&5wn úEXÂë/ýWé´Ðš¯LtÊJÃ,P ¶8³ÖT-N!Ý…nÜ•úo¾Øß–™¢Cd¯Æê\©­'¦ˆF”d f})¬ÉÔl¹X~ð'ŽySó¯6£"FLÊ…ÃÕç’Èb›4ÐåZägãñx8ƒ½½=šd>’×ÿõ¿þW˜Z=\Ý›È6 .µ Le?cdÌq*W6y½ é´ø‚ùß<\ªªÚØØ(Ôõú1úד“"#OÍ L7衾øâ fð )€rfÆz·ÛÍó|:®¯¯“¨ƒðµUÎeY6 ”·2\úööö«¯¾ê÷ûÇÇdzÙl}}}0@(ˆ=z$W|2P°!>œ¬õÁ`P–åöö6JÌEÞO ×ëa£Ê¶lÑ¡‚Jãúúz6›qËœQ¬â/q‡6¹F}ŠMwØ.¢Þr ÔÛnrk'ÖRIC7/N§ª*ì)Cb•8ŽR¨Ïº¼¼|óæ )é§…rêyÌ(ÕJ«£™=•ØPë$<…\8 äXæEt× -7àƒDd:‡CÔÊÕ £óßýîwª¸%VÅÓ £2„ÞŸ–£˜>‰B#Ê‹4Mqò®cDhÞ,¥¹$6 €ŽüÜi5Pà ÎI¯€ Ò›Èþ)aëëëà 4SEÌ["u»Ý,ì«ÄÑú¤"éÖÖÖõõõ`0ÐcÁ€øòÅ_Eñþý{ТÜZ”ñS£Ñó$Ið"4KbRÖl6Cð¢\U@PÞ¤]Äw?KE©È^eV§Ói·ÛNg{{›?3ešób¢b«M’¹Y]ó5ÔÖç‘-6s(UQ,c9U¦Æ]ê”ΣÙ@aÈ«ø©ù‹*ÅÖGkÇJTFƒ„¬V(«M²# "›¶zj|Eô! . P(Ÿ•JË•VƒB ôksîÛ˜ÅÊh2“8(J\íNä Z–eçççoÞ¼Q˜š¼Zô_-¬MÒ©¡",óUv4ãkexmòYäªH´x}}MëÈéééÛ·oŽŽÀYišJ³™ÿæ7¿IBóêÐ: „Î7u$zmPK`Kr®Ùl6 0à×rÎWf5ǃS'3QCäÑt:-CÞ©-ÑétºÝîññ±ØYa+p g#:†µµµ³³³ù|ÎÝBÕ÷û}js­V‹ZQÅ)DµVÆíí-£"À,;;;ûûûÄ‹$I†Ã!ûÓ'OF£ï¿ãn·;·Åè¼HC`ëðí£Õ2°!J(äQruÁ‘㪘@)2HÈ”'À,6,1ç!73³.R2Èé"Œ,ФyL¯Ô2PXgýˆ¡ÃŲMWÑæ’Xc ´¯ÊÕ.^.êóè½™‚ÿN0ëÏî$FHåùìx¡•Ò»{2¥­®· ËÖÖ6ÝZ¸¦6M†gµž~*y¬Ñw O9K­ÀâJ…;Ÿ¢ 4Y¬ò<÷ööp'羜ü.¬µS`*±.¨Ì¾ôé0²NNCÆ(*i$OIæ‹WWWdãñx<û¸¬y—WUõqž W|TšÕ‘%äò³*†óhŠáx<>88(Cöͬf™Æh¹ìS„eY2vX°š§µµ#XÝn·Õj½ÿ¾ —;G®ÜªªzøðáÚÚåÏ$:¯®®ô "«ô³Ùl6›]\\ȸ½×ëM&“­­-œm@§H®®®ž vvv:>PŒŒÅððáË‹ ~\ò–4M¯¯¯q>`W´Z­££#Ò1ñ²Zè’8åyΧ58$1M0ßËËËNÖ5¾D…aÿÈ1àG;VÁb†Â"ËÅîIxcèREë&Qkó†- Z¬£çN߬ÔF|¶1‹DKŽ÷…¶òEûOaÒèÂÑO‰ïSP®»…•jÍc¤HnCçµå2ÁçÖ2™Y_±øGG Î½(Ž;}ìIÑV?›Y_Èè·êi(ÄÀƪG¯, 뫲`ÿí¿ý7nm=®4þÔJR4-Cw®aRŸ±¼¼ŒÀšG B®Ùl2™ g+þ §Ri‹³0œ"Ý[^^Ô ÀfS­Dðé'''‘«àž›5˜x:®ÚÕ{Q^œZ_¤ÔWWWèT’ó|YFt•¼½ØGz²æ ÒB§"Ff è{tŒ \×1›º@u¡<„ܬ޺®ó¿ÿû¿ÏM¤›ïëYt*˜Â3ü ÑC{rrBílmmúT6x‚î ˆ$ ›“‰“S“iˆ)YzáïqXÇÿ¯ÕjQMV—–$Ïsˆ´|IØæ1]ªÝnO&“£££íím…ƒýý}æ†!=¥OÎ3Œ’g <ÿ;›Í¸˜£££'Ožt:ÃÃÃÁ`°µµµ²²ÓOîF5°( Lúý~£Ñ ³‡ò¥º2Sиc¬ÁU‘š‘ÄQλÿ>ÿ¥Ü™eÿËss‘ÂnÄõ\?‘‡Ü·6%ªp>eO÷róÃ÷†€ ‚!BëÜWiƒ^¤ìÓ^‡A|YíÚTâÅùfÕ¡*3ÕU¼p è¡J „0—äcÒ.µ¯R›¯'æ[¨G0 !X²¨Æô¼I”‚Ã-õ$ZJòEëE(ýA cbÂ.î”=«:m"IœýS¤àqÔ©ÜRL·L¬:‘Êï6bI X”(ÊŸž~3Ñ3ÿæ›oòh¹ôÓÏ—©þ&_œäpîìììàà€Ò~Þçü—ÔŒ¹êûŒV>„rÞ‚f^BòXäõ¬µBÇ%ÌTnCJ”Fq‘ULŸ¿ÄÖáï;AqG5«'nSÓš:A+G@ V´7<ÕüçR±RJ?‘J‰~òm,N6±*³rü¬\et ŠÚÒ¾ÝaÁ=ä Tê{j"%dWF˺.Þ©%¡±À Xú†Òlšµ¶E ßáòk«*”e9 ÔÁFf““…xH}Ž•u€*\êDI¬.§)Ý‹Ê0Eôr¹Š…<©´ñZi ³`­æ¿ùÍo1A$‹îödÑZLL¾^°§„|íííáâ¦qXóùÏIF{b/Ū¦å"FènÅžÁ6Âõ¼( jdUUõûý$If³Y­‚'„ž~¿ÿáǃƒjŽyôgF°¸j4ÇÇÇ———(Xâ`±¤eYª&¸½½ H*Õ5Ë2æRƒ»¼¼Üßß÷‚u#€½²²ruu5©ú¥i Uf³ˆi­Ý($äàp›Ç ŸïïïWU¥añi Lív»´­O§Ó^¯GøCÐ Í[|° Yãl6[YY9??W—*žþææfš¦£Ñˆ$ŽL–ýÁwssszzJ¦I‹9ŸNXä™ëLæÇ‰Ý\¶¶®4èÒÐÛ(âS5nÊ“gdùÄ;µH±ÞÇ[™åfñ‰cº¼ÉÄWÖuÍ;ågy‰Y( Ó ³‰ |.¿AQUl€v¦Xº1 F”þxúÉïŸ/šª—^¿_Œ’jÓª‡8µÏ—"ffµ¼4J:޶tZaþ!½¡Óü‰•G×ô7úÜOc™ÂÜ*m6å>|xóæ S,¨õdDóç&^×ýz´UÉ“´ î ^ÑT½dÑ£UŒ°dÖ‡e£ÑÈûÛߪÈKJƒöÓJâÜ.ͱDÝ»wïÆã1¢GÙNªhUás]å'L¹¢•¨°w…6´7Ê¿2Jïþýûý~ÿÑ£GUUœœ´Ûíét ]ÍC¼wïÿºººŠ Áýû÷é°áUÇcÔÕ£G666 „“$ÙÛÛ#8’«êùE1···Ñs ‡C\ú¸ëóósdš¨÷ööF£ÑÅÅÅååe#fšzP¸wïæYyL6åéE‚žÚí6q®J£[ñ¬m^¹w¹Ø žZwˆ/ep¨ëµþ|›9wª" +W=¢¹Í(å÷¸¸à@b"õ2ÑsëLR\Ðõ«Ú«3_;Ó“8•r“ƒWf\å‘Ñ¡ÿ 6ô¢Ë5óèøôÊ€'‰¿<¹Y,H ]±è4¯—å HïNõôÌŒŒ¦RÓ£ó÷UU±êdí+Õá¿#…Ý,Ëè^ö€HdwûòO‘¸pVb\~eÖn”}ç¿ûÝï„ÞóÅþI‘¦:N+k4§èˆSJ]ìeøä)#-ct-[—R¬ ˜Ó¨ѵ§›gÖaOs+¸ßï3]¦Š e艞?¾±±1›ÍÎÎÎP½kÇRÛÙÙá"ÉØçóy¯×ët:lQܬT*B~Aý®ßïSl6›(D8Š———¡í'“É_ýÕ_ÁÓË7U§ Q¦ ÁkŽ!Ï“J#¿”÷©~Çû¾wï…?IO¼ÙÝÁ9 ¢aãîüÁ#‚Ãyød§‹³Â`)%¹C¾(s’¢4çu £k±!õm*é1é Ô—S¾ï‡2¼°?š‹çº“U9ï¿\ÕçÚ&ÍxýKÑáNþèRŸ¨Ï`J>ààÈé6Å&ýoö‰¦ÌQsò7ö eYžœœ dÐ ­²(qy¼he?Ä‘*º¦Êh<â‹üC§¬? eYèøüx+¢,ë¤l¥£Øù)œŽŠ+s±dƒµ?e„ÑK5]õUÄ•€­ôÛØ¨Ò»·Ûm• D«õz½ù|N¬”bˆÑǘªT§ J¶BÂŽ¤““dccCK‘ËÀCY3ÓFsuuõêÕ«v»]|Of}}þÄ<ÏqdGÊOòµ±±±,ê3Äú´E±¹¹9™Lhäfx„¬œµô‹ðr"€RôIJB’K±ãJC”ï¤Æ éKÕ¥4ÆÁŠ>HÂ>X‚@BF>>B§Z²HÀ;C¸d½:5¦ß¬Wj)¦LY^ýh™9(-ºáº`­^UßRSç¹Â+[lëQ’E¦bq²Ø|Wšù­¾çΖay{‘41«<ÍRÑ“ô`§§¤{ñ}êuRC¿£;/…¶BÏðúúúõë×:K¬yØÿ’(@5T‹}9,’™47]´?dvVN?.ƒ6­ù7(C/Tpq y§/TåѲF@¬„΀í õCUR®XúRÀâ/..à¡ áÍfs6›A-Óá…Uw:â‡b«ßï÷z==–$:Å;-8ÞoM{¦Á˜È=¯®®pÚ¢AçììL 5>¸y”Y£Ñ¨Óélll ‡CW^Å«W¯’$yøð!^b:±”áɼÿ>I’n·ûŸþÓ¢jY[é—¬3‹v%Z—8ú`ÐÓðÿâ oIB9™˜JSB˜4Öj4AV¢2ÿZš-Ab&6ŽnŽ ‘UH7«˜òâòQi+³vj¨ÍÞ¨ ×Ù|±Ù+3¹€p¢ÊÁR$Ñu¬q§Å/_l¯É­ëMQ»¶^z §Îr¿ÚÂZÊEÜeÄÂð—rwñ>mÙês=^²àù8-㔈Ÿ |§nYÁ4±ö†ÄôVµÕX“(ª2÷åË—ªÕp ÑnQ–%5¨ÄZwuü뮫ðeYЩׅÍ$u¤`­\¸²ŽÑÌ*o‰é->žšuLÑaU†—…RÐ$HÐz±éI ”››fÊ"‹Éˆ€O"ÿÛn·«~Ól6ïÝ»GÐAœ¥ÃñžIM&a´²,onnz½ÞÖÖV6ŸK<2ªTÖUóù»Q¼Œß¿1^}‚âÜ zTwvvvF£Fz<`íÒñ‡‰Ê«W¯F£ýÃÜÅÒÒR«ÕšL&XÄ>xð€:àÖÖÖ—_~I¿24¦2¯"¼+D,¡(¦4 œ!×ëS‘{Ѱ£#´0»ñ¦"brs_Ä«ÂN‡õçB­Fr+ʈ~òC^^+uÈ\õœ“èêÈM®]Ç‡Š ­Ì[ÊEŒzé¢_:+uòWRELá:jÓ„lÁUåï$Ñl ‘tÊË<ýäÏlé*¼VêÅŠa²è#&q†‡{÷Ãs‘—ÞobúRç%Õ¿ÉïlµZÛÛÛÊ©õ¾@ ì…uˆÆ¡»Y»V”J=%ßUŽXÓ,/v%¯OŠ™Ô< ³,Ëÿþïÿ^àYÅ#å´‰±žJ•õè²,ÃŽr8&AïK¿—¦ét:õRVO«Õº¸¸˜N§àI"V*<_žç¤„sÞH:ÐëõhôÓö{öìÙ£GÞ¼y3N©1]]]±"‘Pnll0…4Ïóï¾û.Ïs$¦———ô-ó«Æã1…T’$[[[Ø*EqppœD Ͻà¾B1‹†áåååÑhTGYm:"LâØ‡ÈJŽOÌÍ,Iÿ¥XÏFžçD¨;§ŠA UU¼TÙÑ Æ†t#==§~='Ò1®ò“"XÛb(úý "ìµIgÖ°ª<¨aVv :¥K3Wò¾b¯÷×6ÄA!O¿ª¶Á†•¦][«MrÙ,ìCS“æ§Æ 'V°K¬Nªwêµ9]Fmu=pnM­Ô¾Z4Gš#ÐøÅø{LLQ¡‹Tí¢}Ÿ…AÓX­9ØÆÍÃÑÆM½+Á”º -'žxõ}Šê_íììLU§:F!’µZ-Þc£à¹¿ÿþû¢(håU Ó±Øzç ðÌ£WUôÄßGGGx®w:§OŸ²s&“ *­4M766NNN¶··Ÿ?¾´´„„¢ÕjáP ¼ê÷ûØQ¼~ýšùádz³³º®×××A|d—£Ñh:^^^v:/^ììì ›×ÒÏlÒK9|Y–„¶¹Yã ’€‚UcäÔf˜Û°/Åhmc½…*šÅœWÒÞÐæ,;Oõ¼b‡d‡Úx.õô8% Fc Á·dQÍädnƸ­ÕQÙTªÿ*tx‡dhÒ¦ÈMÐÿiy* ?{ÕtµiʈÔTWøý®vÖ zÆT›û»þF¹Ñ@a:3õ†"WeÆaáÝn—MAó‰à$yE|E.It¿KàÂA"èM‘ÒvfjMîEÊO–®ÎiÎo½\Eó¯2CÝÔÊCz7~P¤iz~~~qq1ONN&“‰ÃÈ‘ XD²ŽS´EoÞ¼a?ã;L-, =˜øE82iµÔþK}¼;;;Y–‘¸A:xšSO/‡02µn·‹amÆkkk¼?ǬÝ$,y+4.@–‘«EñäÉ~äýû÷áUUQ$¾½½ÝÝ݇ŒHšL&‡‡‡···­Vë—¿üåüÿ±ÕjÁbaÍdÃïE9Kš=1÷Âü¼~e.€…*æ©Ôig_/ûÊh°ÒðÔÌÓ´@…8rëP¨&¦{òÃOKPõbíX§`E];áC1y:7 #¯¥1cUOáIé†Ç±WD(Q]ŽSêðh–`¸¶ù&l]êN åzÎ{%7«ÂG*M†§ŠúªMžò)˜*ÃHC¯xnë“'ÑÜšÇt%5?°³Šð;Vüw¤ÄœƒóææF¾ lU^@Ay¢?CÕ+Š|©®Œ4ÜxãÃ¥n¯´ ?ºÛú“j·ÚÙ¹,ÞipÍ'†ÛP:¦M–exÔ}øðîÜ:ê¬ZÜpØâÑBì}Ùëõ˜æp~~Ž>@ñ·Ýn§QÜÑ0.þI¦1Y–ýôÓO/_¾<;;[__ÿüóϻݮv çbE“óós&ßÎf³<:<çó9VVøäEAoÍééé`08==½ººr€¿ÿ¾®ëÕÕÕgÏžýâ¿X[[£Eyc¥9…h0ô2¼Ä/Ü”B˜[Á˜ä1¾ÜÙ3Sâ¹ò,òg”t~hiWhpÖÜÆbç& ”f…ø¡(Ã?q‘êÈ×eÛK5ªìÀSZ§l|Ì„Bì•ò8äº}íÀ*ÔÕµ‰³l!ý~õrÝ¡Ÿ8 Óç©bebHoÂÍCÉ“ÔÍ£eU‡FŠ)J–Ö|'6*1 ~½Ø6˜…J@ÿä”3œ`9r“ãú·¡ÄÙ© gñ<|(¬ û‘Ç¥C‹ÍЃÌL_Øãèª$NAü……ð íç³Pz²šÌ4ZÓD_ú‹¢ 1… NîÃ|vY*øÙÌyžcŽŽ³pfŽjF£$TgÜX54F¤=zô¨Ùl2Æ óF„Šk|e5`ûÇ#»¹¹9::zÿþ=¤Ø“'Oz½Þêê*^]NNNS¡9 Â"V íq82ê‚ÌŽ õ¬§óósjd…§§§'''{{{[[[_ý5‹† :k’>‰^ Ê…ZÍzitc9ÜÈBBåÙJ¾tìÃÊRJÉÉéP-ˆKÒ`Õ¤}íê<œÇp?üH¸\i왯“Á™,O£”¦¥×D!éª$ë+ÃÙ’µª£Ž•˜ ´ ›u\²ÍtIèƒTÂSº—š'ŸR/:ðiûi¼£€•¶ž+tlëuûéâ¥=ÅV=+‘Îúû4*'¹YÔ)Ø!ýét:øÊrÖ*¸ë©rú’ F©×3ýAÔ3wAf§Q,w®DI=ËOÁ!Q¸bÄW\__ÿ¥¬Hø¨+ÍIt6øE«ºÁ·iôƒw~$Ié.èË©¢e †Lb¢:úV«…é¥4?ØëÅv¥%±-ú¬Ìʈe˜(‰­—à@Iß)RI`_‡ð:؈ëW[šM[jh©•çä‹›ãBm6¤©dqÚ¨XyYëá 0ÖF +9IW˜cD‰©Ût6Lø#M¦ÓBìU]ëëëëÝn·Ûív:˜µ•aëÌÚ»±ªÃD«4MÉòpzQ:Ïs£;Br¾G5Yym;!HNÍ"¿½½] þû׿ýû׿ýÿöëÿùÕ ¤9D‰Î|tEXtcomment CREATOR: XV Version 3.10a Rev: 12/29/94 (PNG patch 1.2) CREATOR: XV Version 3.10a Rev: 12/29/94 (PNG patch 1.2) é¬%tEXtcreate-date2010-07-10T11:38:28-04:006‡'T%tEXtmodify-date2010-07-10T11:38:28-04:00i6Q`IEND®B`‚cl-plplot-0.6.0/src/examples/x01l.lisp0000644000175000017500000000632311413656271017571 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 1 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example1 (&optional (dev default-dev)) (format t "PLplot library version: ~a" (plgver)) (plsdev dev) (plstar 2 2) ;; plots 1 & 2 (labels ((plot (xscale yscale xoff yoff) (let ((x (make-float-array 60)) (y (make-float-array 60)) (xs (make-float-array 6)) (ys (make-float-array 6))) (dotimes (i 60) (setf (aref x i) (+ xoff (/ (* xscale (+ i 1.0)) 60.0))) (setf (aref y i) (+ yoff (* yscale (expt (aref x i) 2))))) (dotimes (i 6) (setf (aref xs i) (aref x (+ (* i 10) 3))) (setf (aref ys i) (aref y (+ (* i 10) 3)))) (plcol0 1) (plenv (aref x 0) (aref x 59) (aref y 0) (aref y 59) 0 0) (plcol0 2) (pllab "(x)" "(y)" "#frPLplot Example 1 - y=x#u2") (plcol0 4) (plpoin xs ys 9) (plcol0 3) (plline x y)))) (plot 6.0 1.0 0.0 0.0) (plot 1.0 0.0014 0.0 0.0185)) ;; plot 3 (let ((x (make-float-array 100)) (y (make-float-array 100))) (dotimes (i 100) (setf (aref x i) (/ (- i 19.0) 6.0)) (setf (aref y i) 1.0) (when (/= (aref x i) 0.0) (setf (aref y i) (/ (sin (aref x i)) (aref x i))))) (plcol0 1) (plenv -2.0 10.0 -0.4 1.2 0 1) (plcol0 2) (pllab "(x)" "sin(x)/x" "#frPLplot Example 1 - Sinc Function") (plcol0 3) (plwid 2) (plline x y) (plwid 1)) ;; plot 4 (let ((x (make-float-array 101)) (y (make-float-array 101)) (mark0 (make-int-array 1 0)) (space0 (make-int-array 1 0)) (mark1 (make-int-array 1 1500)) (space1 (make-int-array 1 1500))) (dotimes (i 101) (setf (aref x i) (* 3.6 i)) (setf (aref y i) (sin (/ (* (aref x i) 3.14159) 180.0)))) (pladv 0) (plvsta) (plwind 0.0 360.0 -1.2 1.0) (plcol0 1) (plbox "bcnst" 60.0 2 "bcnstv" 0.2 2) (plstyl 1 mark1 space1) (plcol0 2) (plbox "g" 30.0 0 "g" 0.2 0) (plstyl 0 mark0 space0) (plcol0 3) (pllab "Angle (degrees)" "sine" "#frPLplot Example 1 - Sine Function") (plcol0 4) (plline x y)) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x20l.lisp0000644000175000017500000001157111416201320017553 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 20 ;;;; ;;;; Note: This example requires the cl-png package ;;;; to read in the image data. ;;;; ;;;; http://www.ljosa.com/~ljosa/software/cl-png/ ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defstruct stretch xmin xmax ymin ymax stretch) (defun example20 (&optional (dev default-dev)) (plsdev dev) (labels ((my-pltr (x y s) (let ((x0 (* 0.5 (+ (stretch-xmin s) (stretch-xmax s)))) (y0 (* 0.5 (+ (stretch-ymin s) (stretch-ymax s)))) (dy (* 0.5 (- (stretch-ymax s) (stretch-ymin s))))) (values (+ x0 (* (- x0 x) (- 1.0 (* (stretch-stretch s) (cos(/ (- y y0) (* dy 3.14159 0.5))))))) y))) (read-img () (let* ((img-rgb (let ((file-name (format nil "~A/src/examples/lena.png" (asdf::system-source-directory :plplot-examples)))) (with-open-file (input file-name :element-type '(unsigned-byte 8) :external-format :binary) (png:decode input)))) (nx (array-dimension img-rgb 0)) (ny (array-dimension img-rgb 1)) (img (make-float-array (list ny nx)))) (dotimes (i nx) (dotimes (j ny) (setf (aref img j (- nx i 1)) (aref img-rgb i j 0)))) img))) (plinit) ; sombrero-like demo (let* ((xdim 260) (ydim 220) (x (make-float-array xdim)) (y (make-float-array ydim)) (z (make-float-array (list xdim ydim)))) (dotimes (i xdim) (setf (aref x i) (* 2.0 i (/ 3.14159 (- xdim 1.0))))) (dotimes (i ydim) (setf (aref y i) (* 3.0 i (/ 3.14159 (- ydim 1.0))))) (dotimes (i xdim) (dotimes (j ydim) (let ((r (+ (sqrt (+ (* (aref x i) (aref x i)) (* (aref y j) (aref y j)))) 1.0e-3))) (setf (aref z i j) (/ (sin r) r))))) (plcol0 2) (plenv 0.0 (* 2.0 3.14159) 0.0 (* 3.0 3.14150) 1 -1) (pllab "No, an amplitude clipped \"sombrero\"" "" "Saturn?") (plptex 2 2 3 4 0 "Transparent image") (plimage z 0.0 (* 2.0 3.14159) 0.0 (* 3.0 3.14159) 0.05 1.0 0.0 (* 2.0 3.14159) 0.0 (* 3.0 3.14159))) ;lena demos (let* ((lena (read-img)) (width (array-dimension lena 0)) (height (array-dimension lena 1))) (plscmap1n 255) (plscmap1l t (vector 0.0 1.0) (vector 0.0 1.0) (vector 0.0 1.0) (vector 0.0 1.0) 'null) ; demo1 (plenv 1.0 width 1.0 height 1 -1) (pllab "" " " "Lena...") (plimage lena 1.0 width 1.0 height 0.0 0.0 1 width 1 height) ; demo2 (pladv 0) (plimage lena 1.0 width 1.0 height 0.0 0.0 200 330 220 280) ; demo3 (plenv 200 330 220 280 1 -1) (plimage lena 1.0 width 1.0 height 0.0 0.0 200 330 220 280) ; demo4 (multiple-value-bind (img-min img-max) (min-max lena) (plcol0 2) (plenv 0 width 0 height 1 -1) (pllab "" "" "Reduced dynamic range image example") (pl-plimagefr lena 0 width 0 height 0.0 0.0 (+ img-min (* 0.25 img-max)) (- img-max (* img-max 0.25)) (pl-null-pointer)) ; demo5 ; ; Note that for images the user defined grid needs to be ; +1 larger in x and y dimensions than the image or you ; will get a memory fault. (plenv 0 width 0 height 1 -1) (pllab "" "" "Distorted image example") (let ((stretch (make-stretch :xmin 0 :xmax width :ymin 0 :ymax height :stretch 0.5)) (cgrid-x (make-float-array (list (1+ width) (1+ height)))) (cgrid-y (make-float-array (list (1+ width) (1+ height))))) (dotimes (i (1+ width)) (dotimes (j (1+ height)) (multiple-value-bind (xx yy) (my-pltr i j stretch) (setf (aref cgrid-x i j) xx (aref cgrid-y i j) yy)))) (pl-set-pltr-fn #'pltr2) (plimagefr lena 0 width 0 height 0 0 img-min img-max cgrid-x cgrid-y) (pl-reset-pltr-fn))))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x17l.lisp0000644000175000017500000000404411414762130017567 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 17 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example17 (&optional (dev default-dev)) (plsdev dev) (plinit) (pladv 0) (plvsta) (let ((id (plstripc "bcnst" "bcnstv" 0.0 10.0 0.3 -0.1 0.1 0.0 0.25 1 1 1 3 (vector 2 3 4 5) (vector 2 3 4 5) (vector "sum" "sin" "sin*noi" "sin+noi") "t" "" "Strip chart demo")) (y1 0.0) (y2 0.0) (y3 0.0) (y4 0.0) (dt 0.1)) (dotimes (n 1000) (sleep 0.01) (let ((time (* n dt)) (noise (- (plrandd) 0.5))) (setf y1 (+ y1 noise) y2 (sin (/ (* time 3.14159) 18.0)) y3 (* y2 noise) y4 (+ y2 (/ noise 3.0))) (when (/= (mod n 2) 0) (plstripa id 0 time y1)) (when (/= (mod n 3) 0) (plstripa id 1 time y2)) (when (/= (mod n 4) 0) (plstripa id 2 time y3)) (when (/= (mod n 5) 0) (plstripa id 3 time y4)))) (plstripd id)) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x28l.lisp0000644000175000017500000001566211423160552017601 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 28 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example28 (&optional (dev default-dev)) (plsdev dev) (let* ((xpts 2) (ypts 2) (nrevolution 16) (nrotation 8) (nshear 8) (x (make-float-array xpts)) (y (make-float-array ypts)) (z (make-float-array (list xpts ypts))) (xmin 0.0) (xmax 1.0) (xmid (* 0.5 (+ xmax xmin))) (xrange (- xmax xmin)) (ymin 0.0) (ymax 1.0) (ymid (* 0.5 (+ ymax ymin))) (yrange (- ymax ymin)) (zmin 0.0) (zmax 1.0) (zmid (* 0.5 (+ zmax zmin))) (zrange (- zmax zmin)) (ysmin (+ ymin (* 0.1 yrange))) (ysmax (- ymax (* 0.1 yrange))) (ysrange (- ysmax ysmin)) (dysrot (/ ysrange (1- nrotation))) (dysshear (/ ysrange (1- nshear))) (zsmin (+ zmin (* 0.1 zrange))) (zsmax (- zmax (* 0.1 zrange))) (zsrange (- zsmax zsmin)) (dzsrot (/ zsrange (1- nrotation))) (dzsshear (/ zsrange (1- nshear)))) (dotimes (i xpts) (setf (aref x i) (+ xmin (/ (* i (- xmax xmin)) (1- xpts))))) (dotimes (j ypts) (setf (aref y j) (+ ymin (/ (* j (- ymax ymin)) (1- ypts))))) (dotimes (i xpts) (dotimes (j ypts) (setf (aref z i j) 0.0))) (plinit) ; page 1 (pladv 0) (plvpor -0.15 1.15 -0.05 1.05) (plwind -1.2 1.2 -0.8 1.5) (plw3d 1.0 1.0 1.0 xmin xmax ymin ymax zmin zmax 20.0 45.0) (plcol0 2) (plbox3 "b" "" (- xmax xmin) 0 "b" "" (- ymax ymin) 0 "bcd" "" (- zmax zmin) 0) (plschr 0.0 1.0) (dotimes (i nrevolution) (let* ((omega (* 2.0 3.14159 (/ i nrevolution))) (sin-omega (sin omega)) (cos-omega (cos omega))) (plptex3 xmid ymid zmin (* 0.5 xrange cos-omega) (* 0.5 yrange sin-omega) 0.0 (* -0.5 xrange sin-omega) (* 0.5 yrange cos-omega) 0.0 0.0 " revolution") (plptex3 xmax ymid zmid 0.0 (* -0.5 yrange cos-omega) (* 0.5 zrange sin-omega) 0.0 (* 0.5 yrange sin-omega) (* 0.5 zrange cos-omega) 0.0 " revolution") (plptex3 xmid ymax zmid (* 0.5 xrange cos-omega) 0.0 (* 0.5 zrange sin-omega) (* -0.5 xrange sin-omega) 0.0 (* 0.5 zrange cos-omega) 0.0 " revolution"))) (plmesh x y z 3) ; page 2 (pladv 0) (plvpor -0.15 1.15 -0.05 1.05) (plwind -1.2 1.2 -0.8 1.5) (plw3d 1.0 1.0 1.0 xmin xmax ymin ymax zmin zmax 20.0 45.0) (plcol0 2) (plbox3 "b" "" (- xmax xmin) 0 "b" "" (- ymax ymin) 0 "bcd" "" (- zmax zmin) 0) (plschr 0.0 1.0) (dotimes (i nrotation) (let* ((omega (* 2.0 3.14159 (/ i nrevolution))) (sin-omega (sin omega)) (cos-omega (cos omega))) (plptex3 xmid ymax (- zsmax (* dzsrot i)) 1.0 0.0 0.0 0.0 (* 0.5 yrange sin-omega) (* 0.5 zrange cos-omega) 0.5 "rotation for y = y#dmax#u") (plptex3 xmax ymid (- zsmax (* dzsrot i)) 0.0 -1.0 0.0 (* 0.5 xrange sin-omega) 0.0 (* 0.5 zrange cos-omega) 0.5 "rotation for x = x#dmax#u") (plptex3 xmid (- ysmax (* dysrot i)) zmin 1.0 0.0 0.0 0.0 (* 0.5 yrange cos-omega) (* 0.5 zrange sin-omega) 0.5 "rotation for z = z#dmin#u"))) (plmesh x y z 3) ; page 3 (pladv 0) (plvpor -0.15 1.15 -0.05 1.05) (plwind -1.2 1.2 -0.8 1.5) (plw3d 1.0 1.0 1.0 xmin xmax ymin ymax zmin zmax 20.0 45.0) (plcol0 2) (plbox3 "b" "" (- xmax xmin) 0 "b" "" (- ymax ymin) 0 "bcd" "" (- zmax zmin) 0) (plschr 0.0 1.0) (dotimes (i nshear) (let* ((omega (+ 0.05 (* 2.0 3.14159 (/ i nshear)))) (sin-omega (sin omega)) (cos-omega (cos omega))) (plptex3 xmid ymax (- zsmax (* dzsshear i)) 1.0 0.0 0.0 (* 0.5 xrange sin-omega) 0.0 (* 0.5 zrange cos-omega) 0.5 "shear for y = y#dmax#u") (plptex3 xmax ymid (- zsmax (* dzsshear i)) 0.0 -1.0 0.0 0.0 (* 0.5 yrange sin-omega) (* 0.5 zrange cos-omega) 0.5 "shear for x = x#dmax#u") (plptex3 xmid (- ysmax (* dysshear i)) zmin 1.0 0.0 0.0 (* 0.5 xrange sin-omega) (* 0.5 yrange cos-omega) 0.0 0.5 "shear for z = z#dmin#u"))) (plmesh x y z 3) ; page 4 (pladv 0) (plvpor -0.15 1.15 -0.05 1.05) (plwind -1.2 1.2 -0.8 1.5) (plw3d 1.0 1.0 1.0 xmin xmax ymin ymax zmin zmax 40.0 -30.0) (plcol0 2) (plbox3 "b" "" (- xmax xmin) 0 "b" "" (- ymax ymin) 0 "bcd" "" (- zmax zmin) 0) (plschr 0.0 1.2) (let* ((pstring "The future of our civilization depends on software freedom") (domega (/ (* 2.0 3.14159) (length pstring))) (omega 0.0) (radius 0.5) (pitch (/ 1.0 (* 2.0 3.14159)))) (dotimes (i (length pstring)) (let ((sin-omega (sin omega)) (cos-omega (cos omega))) (plptex3 (+ xmid (* radius sin-omega)) (- ymid (* radius cos-omega)) (+ zmin (* pitch omega)) (* radius cos-omega) (* radius sin-omega) pitch 0.0 0.0 1.0 0.5 (subseq pstring i (1+ i))) (incf omega domega)))) (plmesh x y z 3) ; page 5 (pladv 0) (plvpor -0.15 1.15 -0.05 1.05) (plwind -1.2 1.2 -0.8 1.5) (plw3d 1.0 1.0 1.0 xmin xmax ymin ymax zmin zmax 20.0 45.0) (plcol0 2) (plbox3 "b" "" (- xmax xmin) 0 "b" "" (- ymax ymin) 0 "bcd" "" (- zmax zmin) 0) (plschr 0.0 1.0) (plmtex3 "xp" 3.0 0.5 0.5 "Arbitrarily displaced") (plmtex3 "xp" 4.5 0.5 0.5 "primary X-axis label") (plmtex3 "xs" -2.5 0.5 0.5 "Arbitrarily displaced") (plmtex3 "xs" -1.0 0.5 0.5 "secondary X-axis label") (plmtex3 "yp" 3.0 0.5 0.5 "Arbitrarily displaced") (plmtex3 "yp" 4.5 0.5 0.5 "primary Y-axis label") (plmtex3 "ys" -2.5 0.5 0.5 "Arbitrarily displaced") (plmtex3 "ys" -1.0 0.5 0.5 "secondary Y-axis label") (plmtex3 "zp" 4.5 0.5 0.5 "Arbitrarily displaced") (plmtex3 "zp" 3.0 0.5 0.5 "primary Z-axis label") (plmtex3 "zs" -2.5 0.5 0.5 "Arbitrarily displaced") (plmtex3 "zs" -1.0 0.5 0.5 "secondary Z-axis label") (plmesh x y z 3)) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x27l.lisp0000644000175000017500000000555711423136342017602 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 27 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example27 (&optional (dev default-dev)) (plsdev dev) (labels ((spiro (params) (let* ((npnt 20000) (xcoord (make-float-array (1+ npnt))) (ycoord (make-float-array (1+ npnt))) (windings (floor (aref params 3))) (steps (floor (/ npnt windings))) (dphi (/ (* 8.0 (acos -1.0)) steps))) (dotimes (i (1+ (* windings steps))) (let* ((dp (- (aref params 0) (aref params 1))) (phi (* i dphi)) (phiw (* (/ dp (aref params 1)) phi))) (setf (aref xcoord i) (+ (* dp (cos phi)) (* (aref params 2) (cos phiw))) (aref ycoord i) (- (* dp (sin phi)) (* (aref params 2) (sin phiw)))))) (multiple-value-bind (xmin xmax) (min-max xcoord) (multiple-value-bind (ymin ymax) (min-max ycoord) (let ((scale (if (> (- xmax xmin) (- ymax ymin)) (- xmax xmin) (- ymax ymin)))) (plwind (* -0.65 scale) (* 0.65 scale) (* -0.65 scale) (* 0.65 scale)) (plcol0 1) (plline (adjust-array xcoord (1+ (* windings steps))) (adjust-array ycoord (1+ (* windings steps)))))))))) (let ((params (vector (vector 21.0 7.0 7.0 3.0) (vector 21.0 7.0 10.0 3.0) (vector 21.0 -7.0 10.0 3.0) (vector 20.0 3.0 7.0 20.0) (vector 20.0 3.0 10.0 20.0) (vector 20.0 -3.0 10.0 20.0) (vector 20.0 13.0 7.0 20.0) (vector 20.0 13.0 20.0 20.0) (vector 20.0 -13.0 20.0 20.0)))) (plinit) (plssub 3 3) (dotimes (i 9) (pladv 0) (plvpor 0.0 1.0 0.0 1.0) (spiro (aref params i))) (pladv 0) (plssub 1 1) (dotimes (i 9) (pladv 0) (plvpor 0.0 1.0 0.0 1.0) (spiro (aref params i))) (plend1)))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x02l.lisp0000644000175000017500000000476711413656271017604 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 2 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example2 (&optional (dev default-dev)) (plsdev dev) (plinit) (labels ((draw-windows (nw cmap0-offset) (plschr 0.0 3.5) (plfont 4) (dotimes (i nw) (plcol0 (+ i cmap0-offset)) (pladv 0) (let ((vmin 0.1) (vmax 0.9)) (dotimes (j 3) (plwid (+ j 1)) (plvpor vmin vmax vmin vmax) (plwind 0.0 1.0 0.0 1.0) (plbox "bc" 0.0 0 "bc" 0.0 0) (incf vmin 0.1) (decf vmax 0.1))) (plwid 1) (plptex 0.5 0.5 1.0 0.0 0.5 (write-to-string i))))) ;; page 1 (plbop) (plssub 4 4) (draw-windows 16 0) (pleop) ;; page 2 (plbop) (plssub 10 10) (let ((r (make-int-array 116)) (g (make-int-array 116)) (b (make-int-array 116))) (dotimes (i 100) (let ((h (* (/ 360.0 10.0) (mod i 10))) (l (+ 0.15 (/ (* (- 0.85 0.15) (/ i 10.0)) 9.0)))) (multiple-value-bind (r1 g1 b1) (plhlsrgb h l 1.0) (setf (aref r (+ i 16)) (floor (* r1 255.001)) (aref g (+ i 16)) (floor (* g1 255.001)) (aref b (+ i 16)) (floor (* b1 255.001)))))) (dotimes (i 16) (multiple-value-bind (r1 g1 b1) (plgcol0 i) (setf (aref r i) r1 (aref g i) g1 (aref b i) b1))) (plscmap0 r g b)) (draw-windows 100 16) (pleop)) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x05l.lisp0000644000175000017500000000316411413656271017575 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 5 ;;;; ;;;; hazen 06/10 ;;;; (in-package :plplot-examples) (defun example5 (&optional (dev default-dev)) (plsdev dev) (plinit) (let ((data (make-float-array 2047)) (delta (/ (* 3.14159 2.0) 2047.0))) (dotimes (i 2047) (setf (aref data i) (sin (* delta i)))) (plcol0 1) (plhist data -1.1 1.1 44 0)) (plcol0 2) (pllab "#frValue" "#frFrequency" "#frPLplot Example 5 - Probability function of Oscillator") (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x24l.lisp0000644000175000017500000000544211422626701017572 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 24 ;;;; ;;;; This requires unicode support. ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example24 (&optional (dev default-dev)) (plsdev dev) (let ((red (vector 240 204 204 204 0 39 125)) (green (vector 240 0 125 204 204 80 0)) (blue (vector 240 0 0 0 0 204 125)) (px (vector 0.0 0.0 1.0 1.0)) (py (vector 0.0 0.25 0.25 0.0)) (sx (vector 0.16374 0.15844 0.15255 0.17332 0.50436 0.51721 0.49520 0.48713 0.83976 0.81688 0.82231 0.82647)) (sy (vector 0.125 0.375 0.625 0.875 0.125 0.375 0.625 0.875 0.125 0.375 0.625 0.875)) (peace (vector "#<0x00>和平" ;Mandarin "#<0x20>शांति" ;Hindi "#<0x10>Peace" ; English "#<0x10>שלו×" ; Hebrew "#<0x10>Мир" ; Russian "#<0x10>Friede" ; German "#<0x30>í‰í™”" ; Korean "#<0x10>Paix" ; French "#<0x10>Paz" ; Spanish "#<0x10>ﺳﻼم" ; Arabic "#<0x10>Barış" ; Turkish "#<0x10>Hasîtî"))) ; Kurdish (plinit) (pladv 0) (plvpor 0.0 1.0 0.0 1.0) (plwind 0.0 1.0 0.0 1.0) (plcol0 0) (plbox "" 1.0 0 "" 1.0 0) (plscmap0n 7) (plscmap0 red green blue) (plschr 0 4.0) (plfont 1) (dotimes (i 4) (plcol0 (+ i 1)) (plfill px py) (dotimes (j 4) (setf (aref py j) (+ (aref py j) (/ 1.0 4.0))))) (plcol0 0) (dotimes (i 12) (plptex (aref sx i) (aref sy i) 1.0 0.0 0.5 (aref peace i))) (plend1))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x15l.lisp0000644000175000017500000000776111422400064017570 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 15 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example15 (&optional (dev default-dev)) (plsdev dev) (plinit) (let* ((xpts 35) (ypts 46) (x (make-float-array xpts)) (y (make-float-array ypts)) (z (make-float-array (list xpts ypts)))) (dotimes (i xpts) (let ((xx (/ (- i (/ xpts 2.0)) (/ xpts 2.0)))) (setf (aref x i) (* (+ xx (/ 1.0 xpts)) (/ (+ xpts 1.0) xpts))) (dotimes (j ypts) (let ((yy (- (/ (- j (/ ypts 2.0)) (/ ypts 2.0)) 1.0))) (setf (aref y j) (* (+ yy 1.0 (/ 1.0 ypts)) (/ (+ ypts 1.0) ypts))) (setf (aref z i j) (+ (- (* xx xx) (* yy yy)) (/ (- xx yy) (+ (* xx xx) (* yy yy) 0.1)))))))) (multiple-value-bind (zmin zmax) (min-max z) (labels ((plot1 () (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plpsty 8) (plshade z -1.0 1.0 -1.0 1.0 (+ zmin (* (- zmax zmin) 0.4)) (+ zmin (* (- zmax zmin) 0.6)) 0 7 2 9 2 2 2 t) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (pllab "distance" "altitude" "Bogon flux")) (plot2 () (let ((nlin (vector 1 1 1 1 1 2 2 2 2 2)) (inc1 (vector 450 -450 0 900 300 450 0 0 450 0)) (inc2 (vector 0 0 0 0 0 -450 900 450 -450 900)) (del1 (vector 2000 2000 2000 2000 2000 2000 2000 2000 4000 4000)) (del2 (vector 2000 2000 2000 2000 2000 2000 2000 2000 4000 2000))) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (dotimes (i 10) (plpat (aref nlin i) (vector (aref inc1 i) (aref inc2 i)) (vector (aref del1 i) (aref del2 i))) (plshade z -1.0 1.0 -1.0 1.0 (+ zmin (* (- zmax zmin) (/ i 10.0))) (+ zmin (* (- zmax zmin) (/ (+ i 1.0) 10.0))) 0 (+ i 6) 2 0 0 0 0 t)) (plcol0 1) (plbox "bcnst" 0.0 0 "bcnstv" 0.0 0) (plcol0 2) (pllab "distance" "altitude" "Bogon flux"))) (plot3 () (let ((xx0 (vector -1.0 1.0 1.0 -1.0 -1.0)) (xx1 (vector -1.0 1.0 1.0 -1.0 -1.0)) (yy0 (vector 1.0 1.0 0.0 0.0 1.0)) (yy1 (vector -1.0 -1.0 0.0 0.0 -1.0)) (zz0 (vector 0.0 0.0 1.0 1.0 0.0)) (zz1 (vector 0.0 0.0 1.0 1.0 0.0))) (pladv 0) (plvpor 0.1 0.9 0.1 0.9) (plwind -1.0 1.0 -1.0 1.0) (plw3d 1.0 1.0 1.0 -1.0 1.0 -1.0 1.0 0.0 1.5 30 -40) (plcol0 1) (plbox3 "bntu" "X" 0.0 0 "bntu" "Y" 0.0 0 "bcdfntu" "Z" 0.5 0) (plcol0 2) (pllab "" "" "3-d polygon filling") (plcol0 3) (plpsty 1) (plline3 xx0 yy0 zz0) (plfill3 xx0 yy0 zz0) (plpsty 2) (plline3 xx1 yy1 zz1) (plfill3 xx1 yy1 zz1)))) ;; main (plscmap1l nil (vector 0.0 0.45 0.55 1.0) (vector 260 260 20 20) (vector 0.6 0.0 0.0 0.6) (vector 1 0.5 0.5 1) 'null) (plot1) (plot2) (plot3)))) (plend1)) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/examples/x23l.lisp0000644000175000017500000002175011422624715017574 0ustar hbabcockhbabcock;;;; ;;;; PLplot example 23 ;;;; ;;;; hazen 07/10 ;;;; (in-package :plplot-examples) (defun example23 (&optional (dev default-dev)) (plsdev dev) (let ((greek (vector "#gA" "#gB" "#gG" "#gD" "#gE" "#gZ" "#gY" "#gH" "#gI" "#gK" "#gL" "#gM" "#gN" "#gC" "#gO" "#gP" "#gR" "#gS" "#gT" "#gU" "#gF" "#gX" "#gQ" "#gW" "#ga" "#gb" "#gg" "#gd" "#ge" "#gz" "#gy" "#gh" "#gi" "#gk" "#gl" "#gm" "#gn" "#gc" "#go" "#gp" "#gr" "#gs" "#gt" "#gu" "#gf" "#gx" "#gq" "#gw")) (type1 (vector #x0020 #x0021 #x0023 #x0025 #x0026 #x0028 #x0029 #x002b #x002c #x002e #x002f #x0030 #x0031 #x0032 #x0033 #x0034 #x0035 #x0036 #x0037 #x0038 #x0039 #x003a #x003b #x003c #x003d #x003e #x003f #x005b #x005d #x005f #x007b #x007c #x007d #x00a9 #x00ac #x00ae #x00b0 #x00b1 #x00d7 #x00f7 #x0192 #x0391 #x0392 #x0393 #x0394 #x0395 #x0396 #x0397 #x0398 #x0399 #x039a #x039b #x039c #x039d #x039e #x039f #x03a0 #x03a1 #x03a3 #x03a4 #x03a5 #x03a6 #x03a7 #x03a8 #x03a9 #x03b1 #x03b2 #x03b3 #x03b4 #x03b5 #x03b6 #x03b7 #x03b8 #x03b9 #x03ba #x03bb #x03bc #x03bd #x03be #x03bf #x03c0 #x03c1 #x03c2 #x03c3 #x03c4 #x03c5 #x03c6 #x03c7 #x03c8 #x03c9 #x03d1 #x03d2 #x03d5 #x03d6 #x2022 #x2026 #x2032 #x2033 #x203e #x2044 #x2111 #x2118 #x211c #x2122 #x2126 #x2135 #x2190 #x2191 #x2192 #x2193 #x2194 #x21b5 #x21d0 #x21d1 #x21d2 #x21d3 #x21d4 #x2200 #x2202 #x2203 #x2205 #x2206 #x2207 #x2208 #x2209 #x220b #x220f #x2211 #x2212 #x2215 #x2217 #x221a #x221d #x221e #x2220 #x2227 #x2228 #x2229 #x222a #x222b #x2234 #x223c #x2245 #x2248 #x2260 #x2261 #x2264 #x2265 #x2282 #x2283 #x2284 #x2286 #x2287 #x2295 #x2297 #x22a5 #x22c5 #x2320 #x2321 #x2329 #x232a #x25ca #x2660 #x2663 #x2665 #x2666)) (title (vector "#<0x10>PLplot Example 23 - Greek Letters" "#<0x10>PLplot Example 23 - Type 1 Symbol Font Glyphs by Unicode (a)" "#<0x10>PLplot Example 23 - Type 1 Symbol Font Glyphs by Unicode (b)" "#<0x10>PLplot Example 23 - Type 1 Symbol Font Glyphs by Unicode (c)" "#<0x10>PLplot Example 23 - Number Forms Unicode Block" "#<0x10>PLplot Example 23 - Arrows Unicode Block (a)" "#<0x10>PLplot Example 23 - Arrows Unicode Block (b)" "#<0x10>PLplot Example 23 - Mathematical Operators Unicode Block (a)" "#<0x10>PLplot Example 23 - Mathematical Operators Unicode Block (b)" "#<0x10>PLplot Example 23 - Mathematical Operators Unicode Block (c)" "#<0x10>PLplot Example 23 - Mathematical Operators Unicode Block (d)")) (lo (vector #x0 #x0 #x40 #x80 #x2153 #x2190 #x21d0 #x2200 #x2240 #x2280 #x22c0)) (hi (vector #x30 #x40 #x80 #xA6 #x2184 #x21d0 #x2200 #x2240 #x2280 #x22c0 #x2300)) (nxcells (vector 12 8 8 8 8 8 8 8 8 8 8)) (nycells (vector 8 8 8 8 8 8 8 8 8 8 8)) (offset (vector 0 0 64 128 0 0 0 0 0 0 0)) (fci (vector #x80000000 #x80000001 #x80000002 #x80000003 #x80000004 #x80000010 #x80000011 #x80000012 #x80000013 #x80000014 #x80000020 #x80000021 #x80000022 #x80000023 #x80000024 #x80000100 #x80000101 #x80000102 #x80000103 #x80000104 #x80000110 #x80000111 #x80000112 #x80000113 #x80000114 #x80000120 #x80000121 #x80000122 #x80000123 #x80000124)) (family (vector "sans-serif" "serif" "monospace" "script" "symbol")) (style (vector "upright" "italic" "oblique")) (weight (vector "medium" "bold"))) (plinit) (dotimes (page 11) (pladv 0) (plvpor 0.02 0.98 0.02 0.90) (plwind 0.0 1.0 0.0 1.0) (multiple-value-bind (xmin xmax ymin ymax) (plgspa) (declare (ignore xmin xmax)) (plschr 0.0 0.8) (let ((ycharacter-scale (/ 1.0 (- ymax ymin)))) (multiple-value-bind (chardef charht) (plgchr) (declare (ignore chardef)) (let ((yoffset (* charht ycharacter-scale)) (deltax (/ 1.0 (aref nxcells page))) (deltay (/ 1.0 (aref nycells page))) (length (- (aref hi page) (aref lo page))) (slice 0)) (plcol0 2) (plbox "bcg" deltax 0 "bcg" deltay 0) (plcol0 15) (do ((j (1- (aref nycells page)) (- j 1))) ((< j -1)) (let ((y (* (+ 0.5 j) deltay))) (dotimes (i (aref nxcells page)) (let ((x (* (+ 0.5 i) deltax))) (when (< slice length) (let ((cmdstring (cond ((= page 0) (format nil "#~A" (aref greek slice))) ((and (>= page 1) (<= page 3)) (format nil "##[0x~4,'0x]" (aref type1 (+ (aref offset page) slice)))) (t (format nil "##[0x~4,'0x]" (+ (aref lo page) slice)))))) (plptex x (+ y yoffset) 1 0 0.5 (subseq cmdstring 1)) (plptex x (- y yoffset) 1 0 0.5 cmdstring)))) (incf slice)))))))) (plschr 0.0 1.0) (plmtex "t" 1.5 0.5 0.5 (aref title page))) (format t "For example 23 prior to page 12 the FCI is 0x~x~%" (plgfci)) (multiple-value-bind (ifamily istyle iweight) (plgfont) (format t "For example 23 prior to plage 12 the font family, style and weight are ~A ~A ~A~%" ifamily istyle iweight)) (do ((page 11 (+ page 1))) ((>= page 16)) (let ((dy 0.030)) (pladv 0) (plvpor 0.02 0.98 0.02 0.90) (plwind 0.0 1.0 0.0 1.0) (plsfci 0) (cond ((= page 11) (plmtex "t" 1.5 0.5 0.5 "#<0x10>PLplot Example 23 - Set Font with plsfci")) ((= page 12) (plmtex "t" 1.5 0.5 0.5 "#<0x10>PLplot Example 23 - Set Font with plsfont")) ((= page 13) (plmtex "t" 1.5 0.5 0.5 "#<0x10>PLplot Example 23 - Set Font with ##<0x8nnnnnnn> construct")) ((= page 14) (plmtex "t" 1.5 0.5 0.5 "#<0x10>PLplot Example 23 - Set Font with ##<0xmn> constructs")) (t (plmtex "t" 1.5 0.5 0.5 "#<0x10>PLplot Example 23 - Set Font with ## constructs"))) (plschr 0.0 0.75) (dotimes (i 30) (let* ((family-index (mod i 5)) (style-index (mod (floor (/ i 5)) 3)) (weight-index (mod (floor (/ (/ i 5) 3)) 2)) (string (cond ((= page 11) (progn (plsfci (aref fci i)) (format nil "Page 12, ~A, ~A, ~A: The quick brown fox jumps over the lazy dog" (aref family family-index) (aref style style-index) (aref weight weight-index)))) ((= page 12) (progn (plsfont family-index style-index weight-index) (format nil "Page 13, ~A, ~A, ~A: The quick brown fox jumps over the lazy dog" (aref family family-index) (aref style style-index) (aref weight weight-index)))) ((= page 13) (format nil "Page 14, ~A, ~A, ~A: #<0x~x>The quick brown fox jumps over the lazy dog" (aref family family-index) (aref style style-index) (aref weight weight-index) (aref fci i))) ((= page 14) (format nil "Page 15, ~A, ~A, ~A: #<0x~1x0>#<0x~1x1>#<0x~1x2>The quick brown fox jumps over the lazy dog" (aref family family-index) (aref style style-index) (aref weight weight-index) family-index style-index weight-index)) (t (format nil "Page 16, ~A, ~A, ~A: #<~A/>#<~A/>#<~A/>The quick brown fox jumps over the lazy dog" (aref family family-index) (aref style style-index) (aref weight weight-index) (aref family family-index) (aref style style-index) (aref weight weight-index)))))) (plptex 0.0 (- 1.0 (* (+ i 0.5) dy)) 1.0 0.0 0.0 string))) (plschr 0.0 1.0))) (plcol0 1) (plend1))) ;;;; ;;;; Copyright (c) 2010 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/0000755000175000017500000000000011427546035015602 5ustar hbabcockhbabcockcl-plplot-0.6.0/src/window/classes.lisp0000644000175000017500000000642310756454206020137 0ustar hbabcockhbabcock;;;; ;;;; Define the classes that we'll use in cl-plplot ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (def-plplot-class color-table () (color-map)) (def-plplot-class extended-color-table () (control-points color-table-size)) (def-plplot-class text-item () (the-text (text-color *foreground-color*) (text-justification 0.5) (font-size *font-size*))) (def-plplot-class text-label () (label-text-item text-x text-y text-dx text-dy)) (def-plplot-class 3D-text-label (text-label) (text-z text-dz text-sx text-sy text-sz)) (def-plplot-class axis-label () (axis-text-item side displacement (location 0.5) (orientation :parallel))) (def-plplot-class 3D-axis-label (axis-label) ((primary/secondary :primary))) (def-plplot-class axis () (axis-min axis-max (major-tick-interval 0) (minor-tick-number 0) (properties *axis-properties*) axis-labels)) (def-plplot-class plot () (min-max-function render-function)) (def-plplot-class x-y-plot (plot) (data-x data-y line-width line-style symbol-size symbol-type color x-error y-error)) (def-plplot-class bar-graph (plot) (data-x data-array bar-widths side-by-side line-colors fill-colors line-width Filled)) (def-plplot-class contour-plot (plot) (data contour-levels fill-colors fill-type line-color line-width x-mapping y-mapping)) (def-plplot-class 3D-plot (plot) (data-x data-y data-z contour-levels line-width line-style line-color)) (def-plplot-class 3D-mesh (3D-plot) (grid-type contour-options curtain)) (def-plplot-class surface-plot (3D-plot) (light-source surface-options)) (def-plplot-class window () (x-axis y-axis title (window-line-width 1.0) (window-font-size *font-size*) (foreground-color *foreground-color*) (background-color *background-color*) (viewport-x-min 0.1) (viewport-x-max 0.9) (viewport-y-min 0.1) (viewport-y-max 0.9) plots text-labels color-table extended-color-table)) (def-plplot-class 3D-window (window) (z-axis (altitude 60) (azimuth 30))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/x-y-plot.lisp0000644000175000017500000001453310512274177020171 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Functions that are most closely related to the x-y-plot class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (defun x-y-plot-check-lengths (x y x-error y-error) "Checks that the arrays we have been given are appropriately defined." (let ((y-length (length y))) (when (and x (not (= y-length (length x)))) (format t "y & x do not have the same number of elements! (~A /= ~A)~%" y-length (length x)) (return-from x-y-plot-check-lengths nil)) (when (and x-error (not (= y-length (length x-error)))) (format t "y & x-error do not have the same number of elements! (~A /= ~A)~%" y-length (length x-error)) (return-from x-y-plot-check-lengths nil)) (when (and y-error (not (= y-length (length y-error)))) (format t "y & y-error do not have the same number of elements! (~A /= ~A)~%" y-length (length y-error)) (return-from x-y-plot-check-lengths nil)) t)) (defun error-bar (vec error) "Creates error bar vectors from vec to pass to plplot" (let* ((len (length vec)) (min-err (make-array len :element-type 'double-float)) (max-err (make-array len :element-type 'double-float))) (dotimes (i (length vec)) (let ((err (* 0.5 (aref error i)))) (setf (aref min-err i) (coerce (- (aref vec i) err) 'double-float)) (setf (aref max-err i) (coerce (+ (aref vec i) err) 'double-float)))) (values min-err max-err))) (defun new-x-y-plot (x y &key (copy t) (line-width 1) (line-style 1) (symbol-size 0.0) symbol-type (color *foreground-color*) x-error y-error) "Creates a new x-y plot. If x is nil then y will be plotted against its index. If copy is true then copies of x,y,x-error and y-error will be made, otherwise references will be kept to the original vectors. line-width should be an integer line width, or zero if no line is desired line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. symbol-size specified how big to draw the symbols (1.0 is standard size). If it is zero the symbols are not drawn. symbol-type should be set to a number (that specifies a symbol) if you want specific types of symbols, otherwise default symbol types are used. color is the color to use when plotting the lines and symbols, it should be a symbol that specifies a color in the current color table. If it is not specified then the current foreground color will be used. x-error should be a vector of the same length as x that contains the size of the error bars in x. y-error is for error bars in y." (when (x-y-plot-check-lengths x y x-error y-error) (make-instance 'x-y-plot :data-x (copy-vector (if x x (make-index-vector (length y))) copy) :data-y (copy-vector y copy) :line-width line-width :line-style line-style :symbol-size symbol-size :symbol-type symbol-type :color color :x-error (copy-vector x-error copy) :y-error (copy-vector y-error copy)))) (def-edit-method x-y-plot (line-width line-style symbol-size symbol-type color) "edit-x-y-plot, Edits the visual properties of a plot Set the line width with :line-width (integer, 0 means no line). Set the line style with :line-style (integer between 1 and 8). Set the symbol size with :symbol-size (1.0 is the defaul size, 0.0 means no symbols). Set the symbol type with :symbol-type (integer or nil to use the default types). Set the color with :color symbol.") (defmethod plot-min-max ((a-plot x-y-plot)) "Returns the minimum and maximum values in a plot as a 4 element vector." (let* ((x-data (data-x a-plot)) (y-data (data-y a-plot)) (min-x (aref x-data 0)) (max-x (aref x-data 0)) (min-y (aref y-data 0)) (max-y (aref y-data 0))) (dotimes (i (length x-data)) (when (< (aref x-data i) min-x) (setf min-x (aref x-data i))) (when (> (aref x-data i) max-x) (setf max-x (aref x-data i))) (when (< (aref y-data i) min-y) (setf min-y (aref y-data i))) (when (> (aref y-data i) max-y) (setf max-y (aref y-data i)))) (let ((x-delta (* 0.05 (- max-x min-x))) (y-delta (* 0.05 (- max-y min-y)))) (vector (- min-x x-delta) (+ max-x x-delta) (- min-y y-delta) (+ max-y y-delta))))) ;; draw a plot (defmethod render-plot ((a-plot x-y-plot) &optional (default-symbol 0)) "Renders a x-y plot in the current window." (set-foreground-color (color a-plot)) (when (> (line-width a-plot) 0) (when (range-check (line-style a-plot) 1 8) (pllsty (line-style a-plot))) (plwid (line-width a-plot)) (plline (data-x a-plot) (data-y a-plot))) (when (> (symbol-size a-plot) 0) (plssym 0 (symbol-size a-plot)) (let ((temp-symbol (if (symbol-type a-plot) (symbol-type a-plot) default-symbol))) (unless (range-check temp-symbol 0 3000) (setf temp-symbol 0)) (plpoin (data-x a-plot) (data-y a-plot) temp-symbol))) (when (x-error a-plot) (multiple-value-bind (min-error max-error) (error-bar (data-x a-plot) (x-error a-plot)) (plerrx min-error max-error (data-y a-plot)))) (when (y-error a-plot) (multiple-value-bind (min-error max-error) (error-bar (data-y a-plot) (y-error a-plot)) (plerry (data-x a-plot) min-error max-error)))) cl-plplot-0.6.0/src/window/plot.lisp0000644000175000017500000000546310534722630017454 0ustar hbabcockhbabcock;;;; ;;;; All plot object must support two functions. ;;;; ;;;; (1) plot-min-max returns the window size that would be ideal for the ;;;; plot object as the vector #(xmin xmax ymin ymax). ;;;; ;;;; (2) render-plot draws the plot object in the current window. It ;;;; should make no assumptions about the current foreground color, ;;;; pen size, etc... ;;;; ;;;; Here we provide a mechanism whereby the user can create their own ;;;; plot objects that will be drawn in the window just as if they were ;;;; one of the built in plot objects (x-y-plot, bar-graph, contour-plot). ;;;; ;;;; hazen 10/06 ;;;; (in-package #:cl-plplot) (defgeneric plot-min-max (plot)) (defmethod plot-min-max ((a-plot plot)) (funcall (min-max-function a-plot))) (defgeneric render-plot (plot &optional parameters)) (defmethod render-plot ((a-plot plot) &optional parameters) (funcall (render-function a-plot) parameters)) (defun new-custom-plot-object (min-max-function render-function) "Allows the user to create their own custom plot object. min-max-function must be either nil or a function of no arguments that returns the vector #(xmin xmax ymin ymax) that specifies the ideal window size for this object. render-function must be a function of one argument that specifies how to render the plot object. Generally the rendering will be done with a bunch of calls to functions in the cl-plplot-system module. The current plot number will be passed to this function." (make-instance 'plot :min-max-function (if min-max-function min-max-function #'(lambda () (vector 0.0 1.0 0.0 1.0))) :render-function render-function)) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/color-table.lisp0000644000175000017500000002104610512251643020671 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the color class. ;;;; ;;;; This color class is used to setup PLplot's color map 0. This ;;;; color map will contain a few (typically 16) colors that can ;;;; be referred to by name. ;;;; ;;;; To be compatible with most of the plplot device drivers you ;;;; should probably limit yourself to 16 colors. Note that color ;;;; index 0 is always the background color and that the default ;;;; foreground color has index 1. ;;;; ;;;; Each entry in the color map is a vector of #(r g b :symbol), ;;;; where :symbol is your handle to the color for later use ;;;; during actual plotting. Referring to the default color table ;;;; as an example, the first color, designated :white, will be ;;;; the background color and the second color, designated ;;;; :black, will be the color that the plot rectangle, ticks ;;;; marks & etc are drawn in (ambiguously referred to as ;;;; the foreground color.) ;;;; ;;;; hazen 8/06 ;;;; (in-package #:cl-plplot) ;; external (defun new-color-table (&optional rgb-colors) "Creates a new color table instance from a vector of rgb triples, which also includes a symbol to refer to the color by. For example: #((0 0 0 :black) (128 128 128 :grey) (255 255 255 :white))." (make-instance 'color-table :color-map (when (vectorp rgb-colors) (if (vectorp (aref rgb-colors 0)) rgb-colors (vector rgb-colors))))) (defun default-color-table () "Returns the default color table." (new-color-table (vector #(255 255 255 :white) #(0 0 0 :black) #(240 50 50 :red) #(255 255 0 :yellow) #(0 255 0 :green) #(127 255 212 :aquamarine) #(255 192 203 :pink) #(245 222 179 :wheat) #(190 190 190 :grey) #(165 42 42 :brown) #(0 0 255 :blue) #(138 43 226 :blue-violet) #(0 255 255 :cyan) #(64 224 208 :turquoise) #(255 0 255 :magenta) #(250 128 114 :salmon)))) (defgeneric update-color (a-color-table color-symbol new-color)) (defmethod update-color ((a-color-table color-table) color-symbol new-color) "Changes the color specified by color-symbol to new-color, which should be a rgb triple in the form #(r g b)." (let ((color-index (find-a-color a-color-table color-symbol))) (when color-index (let ((color-to-change (aref (color-map a-color-table) color-index))) (setf (aref color-to-change 0) (aref new-color 0)) (setf (aref color-to-change 1) (aref new-color 1)) (setf (aref color-to-change 2) (aref new-color 2)))))) (defgeneric set-color-table (a-window a-color-table)) (defmethod set-color-table ((a-window window) (a-color-table color-table)) "Sets the color table associated with a-window to a-color-table. Returns the old color table." (let ((old-color-table (color-table a-window))) (setf (color-table a-window) a-color-table) old-color-table)) (defgeneric add-color-to-color-table (a-color-table new-color)) (defmethod add-color-to-color-table ((a-color-table color-table) new-color) "Adds a new color #(r g b :smybol) to the end of a color table." (let* ((a-color-map (color-map a-color-table)) (color-map-length (length a-color-map)) (new-color-map (make-array (1+ color-map-length)))) (dotimes (i color-map-length) (setf (aref new-color-map i) (aref a-color-map i))) (setf (aref new-color-map color-map-length) new-color) (setf (color-map a-color-table) new-color-map))) (defgeneric remove-color-from-color-table (a-color-table &optional new-color)) (defmethod remove-color-from-color-table ((a-color-table color-table) &optional color-to-remove) "Removes color-to-remove, if specified, or the last color if not." (let ((a-color-map (color-map a-color-table))) (setf a-color-map (if color-to-remove (remove-if #'(lambda (x) (equal color-to-remove (aref x 3))) a-color-map) (butlast a-color-map))))) ;; internal (defgeneric change-background-color (a-color-table color-symbol)) (defmethod change-background-color ((a-color-table color-table) color-symbol) "Changes the current background color to that specified by color-symbol." (swap-colors a-color-table color-symbol (aref (aref (color-map a-color-table) 0) 3))) (defgeneric change-foreground-color (a-color-table color-symbol)) (defmethod change-foreground-color ((a-color-table color-table) color-symbol) "Changes the current foreground color to that specified by color-symbol." (swap-colors a-color-table color-symbol (aref (aref (color-map a-color-table) 1) 3))) (defgeneric swap-colors (a-color-table color1 color2)) (defmethod swap-colors ((a-color-table color-table) color1 color2) "Swaps the position of color1 and color2 in the color table. If one of the colors does not exist then nothing happens." (let ((a-color-map (color-map a-color-table)) (index1 (find-a-color a-color-table color1)) (index2 (find-a-color a-color-table color2))) (when (and index1 index2) (let ((color-vec1 (copy-seq (aref a-color-map index1))) (color-vec2 (copy-seq (aref a-color-map index2)))) (setf (aref a-color-map index1) color-vec2) (setf (aref a-color-map index2) color-vec1))))) (defun find-a-color (a-color-table color-specifier) "Returns the index of the specified color in the color table or NIL if the color cannot be found." (let ((a-color-map (color-map a-color-table))) (dotimes (i (length a-color-map)) (let ((a-color (aref a-color-map i))) (when (equal color-specifier (aref a-color 3)) (return-from find-a-color i)))) nil)) (defgeneric initialize-color-table (a-color-table foreground-color background-color)) (defmethod initialize-color-table ((a-color-table color-table) foreground-color background-color) "Initializes the color table in plot and sets it to match our local version of the color table." (change-background-color a-color-table background-color) (change-foreground-color a-color-table foreground-color) (let ((a-color-map (color-map a-color-table))) (plscmap0n (length a-color-map)) (dotimes (i (length a-color-map)) (let ((a-color (aref a-color-map i))) (plscol0 i (aref a-color 0) (aref a-color 1) (aref a-color 2)))))) (defgeneric get-background-color (a-color-table)) (defmethod get-background-color ((a-color-table color-table)) (aref (aref (color-map a-color-table) 0) 3)) (defgeneric get-foreground-color (a-color-table)) (defmethod get-foreground-color ((a-color-table color-table)) (aref (aref (color-map a-color-table) 1) 3)) (defun set-background-color () "Switches the pen to the background color." (plcol0 0)) ; Since the plplot library can only handle drawing one plot at a time ; this variable is set in render-window to the current color table. ; This approach, while not perhaps ideal, does let us avoid having ; to pass a color table into every function that wants to set a color. (defvar *current-color-table*) (defun set-foreground-color (color) "Switches the pen to the desired foreground color, or the default foreground color if the desired color cannot be found." (cond ((symbolp color) (let ((color-index (find-a-color *current-color-table* color))) (if color-index (plcol0 color-index) (plcol0 1)))) (t (format t "Failed to set color to: ~A~%" color)))) (defun set-color-by-index (index) "Switches the pen to color currently at index. The background color is ignored & colors wrap when the index is off the end of the color table." (plcol0 (1+ (mod index (1- (length (color-map *current-color-table*))))))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/utility-functions.lisp0000644000175000017500000000474310512221130022170 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; This file contains a number of utility functions that are used/useful ;;;; for plot generation. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (defun make-float-vector (vector-length) "Returns an array of floating point numbers." (make-array vector-length :initial-element 0.0 :element-type 'float)) (defun make-index-vector (vector-length) "Creates a vector of numbers 1,2,..,vector-length." (let ((index-vector (make-float-vector vector-length))) (dotimes (i vector-length) (setf (aref index-vector i) (1+ i))) index-vector)) ; warning re. out of range value? (defun range-check (val min max) "Returns true if val is between min and max (inclusive)." (and (>= val min) (<= val max))) (defun copy-vector (vector copy?) "If desired, makes a copy of a vector." (if copy? (copy-seq vector) vector)) (defun copy-matrix (matrix copy?) "If desired, makes a copy of a matrix." (if (= (array-rank matrix) 1) (copy-vector matrix copy?) (if copy? (let ((new-matrix (make-array (list (array-dimension matrix 0) (array-dimension matrix 1)) :initial-element 0.0 :element-type 'float))) (dotimes (i (array-dimension matrix 0)) (dotimes (j (array-dimension matrix 1)) (setf (aref new-matrix i j) (aref matrix i j)))) new-matrix) matrix))) cl-plplot-0.6.0/src/window/macros.lisp0000644000175000017500000001055410633063576017766 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; cl-plplot specific macros ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (defun my-read-from-string (a-string a-class &optional another-string another-class) "Wraps read-from-string." (read-from-string (concatenate 'string a-string (string a-class) (when another-string another-string) (when another-class (string another-class))))) (defmacro def-plplot-class (name parents &optional slots (documentation "...")) "Easy class creation." `(defclass ,name ,parents ,(when slots (mapcar #'(lambda (item) (if (listp item) (let ((name (car item)) (val (cadr item))) `(,name :initarg ,(intern (string name) :keyword) :accessor ,name :initform ,val)) `(,item :initarg ,(intern (string item) :keyword) :accessor ,item :initform nil))) slots)) (:documentation ,documentation))) (defmacro def-edit-method (class arguments &optional (documentation "...")) "Easy object edit method creation." (let ((m-name (my-read-from-string "edit-" class)) (a-class (my-read-from-string "a-" class))) `(progn (defgeneric ,m-name (,class &key ,@arguments)) ; (defmethod ,m-name ((,a-class ,class) &key ,@arguments) (defmethod ,m-name ((,a-class ,class) &key ,@(mapcar #'(lambda (x) `(,x *cl-plplot-null*)) arguments)) ,documentation ,@(mapcar #'(lambda (x) `(unless (eq ,x *cl-plplot-null*) (setf (,x ,a-class) ,x))) arguments))))) (defmacro new-object-defun (class arguments &optional (documentation "...")) "Easy object creation function creation." (let ((f-name (my-read-from-string "new-" class))) `(defun ,f-name ,arguments ,documentation (make-instance ',class ,@(let ((arg-list nil)) (dolist (x arguments) (let ((tmp (cond ((and (symbolp x) (not (equal x '&key))) x) ((listp x) (car x))))) (when tmp (setf arg-list (append arg-list (list (intern (string tmp) :keyword)))) (setf arg-list (append arg-list (list tmp)))))) arg-list))))) (defmacro def-add-remove-methods (class class-slot another-class) "Easy addition and removal of 'sub-objects' from objects." (let ((a-class (my-read-from-string "a-" class)) (a-another-class (my-read-from-string "a-" another-class)) (add-name (my-read-from-string "add-" another-class "-to-" class)) (remove-name (my-read-from-string "remove-" another-class "-from-" class))) `(progn (defgeneric ,add-name (,class ,another-class)) (defmethod ,add-name ((,a-class ,class) (,a-another-class ,another-class)) ,(concatenate 'string (string add-name) ", ADDS " (string a-another-class) " TO " (string a-class) ".") (setf (,class-slot ,a-class) (append (,class-slot ,a-class) (list ,a-another-class)))) (defgeneric ,remove-name (,class &optional ,another-class)) (defmethod ,remove-name ((,a-class ,class) &optional ,a-another-class) ,(concatenate 'string (string remove-name) ", DESTRUCTIVELY REMOVES " (string a-another-class) " FROM " (string a-class) ". IF " (string a-another-class) " IS NOT SPECIFIED THEN THE LAST " (string another-class) " IS REMOVED.") (setf (,class-slot ,a-class) (if ,a-another-class (remove ,a-another-class (,class-slot ,a-class)) (butlast (,class-slot ,a-class)))))))) cl-plplot-0.6.0/src/window/extended-color-table.lisp0000644000175000017500000000763010512306216022467 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the extended color class. ;;;; ;;;; This color class is used to setup PLplot's color map 1. This ;;;; color map will contain a large number of colors (typically ;;;; 128 or 256) that are (usually) continuous. This color map ;;;; is used for contour-plot to provide the :smooth fill. ;;;; ;;;; To be compatible with most of the plplot device drivers you ;;;; should probably limit yourself to 128 colors. ;;;; ;;;; hazen 10/06 ;;;; (in-package #:cl-plplot) ;; external (defun new-extended-color-table (&key control-points (color-table-size 128)) "Creates a new extended color table instance from a vector of control points. For example: #((0.0 0.0 0.0 0.0) (1.0 255 255 255)) will create a gray scale color table. See plscmap1l in the PLplot documentation for a more thorough explanation." (make-instance 'extended-color-table :control-points (when (vectorp control-points) control-points) :color-table-size color-table-size)) (defun default-extended-color-table () "Returns the default color table." (new-extended-color-table :control-points (vector #(0.0 0 0 255) #(1.0 255 0 0)))) (defmethod set-color-table ((a-window window) (a-extended-color-table extended-color-table)) "Sets the color table associated with a-window to a-color-table. Returns the old color table." (let ((old-color-table (extended-color-table a-window))) (setf (extended-color-table a-window) a-extended-color-table) old-color-table)) (defgeneric initialize-extended-color-table (a-extended-color-table)) (defmethod initialize-extended-color-table ((a-extended-color-table extended-color-table)) "Initializes the extended color table in PLplot and sets it to match our local version of the extended color table." (let* ((control-points (control-points a-extended-color-table)) (number-control-points (length control-points)) (locations (make-float-vector number-control-points)) (red-values (make-float-vector number-control-points)) (green-values (make-float-vector number-control-points)) (blue-values (make-float-vector number-control-points)) (rev-values (make-array number-control-points :initial-element nil))) (dotimes (i number-control-points) (setf (aref locations i) (aref (aref control-points i) 0)) (setf (aref red-values i) (/ (aref (aref control-points i) 1) 255.0)) (setf (aref green-values i) (/ (aref (aref control-points i) 2) 255.0)) (setf (aref blue-values i) (/ (aref (aref control-points i) 3) 255.0))) (plscmap1n (color-table-size a-extended-color-table)) (plscmap1l t locations red-values green-values blue-values rev-values))) ; This variable is set in render-window to the current extended color table. (defvar *current-extended-color-table*) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/package.lisp0000644000175000017500000000573410756454206020101 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Define the cl-plplot including what it uses & what it exports ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-user) (defpackage #:cl-plplot (:use #:common-lisp #:cl-plplot-system) (:export #:add-axis-label-to-axis #:add-color-to-color-table #:add-plot-to-window #:add-text-label-to-window #:backspace #:basic-3d-window #:basic-window #:bring-to-front #:default-color-table #:edit-3d-axis-label #:edit-3d-mesh #:edit-3d-text-label #:edit-3d-window #:edit-axis #:edit-axis-label #:edit-bar-graph #:edit-contour-plot #:edit-surface-plot #:edit-text-item #:edit-text-label #:edit-window #:edit-window-axis #:edit-x-y-plot #:get-cursor #:greek-char #:hershey-char #:italic-font #:new-3d-axis-label #:new-3d-mesh #:new-3d-text-label #:new-3d-window #:new-axis #:new-axis-label #:new-bar-graph #:new-color-table #:new-contour-plot #:new-custom-plot-object #:new-extended-color-table #:new-surface-plot #:new-text-item #:new-text-label #:new-window #:new-x-y-plot #:normal-font #:number-symbol #:overline #:remove-axis-label-from-axis #:remove-color-from-color-table #:remove-plot-from-window #:remove-text-label-from-window #:render #:roman-font #:script-font #:send-to-back #:set-color-table #:set-foreground-color #:subscript #:superscript #:underline #:unicode-char #:update-color #:x-y-z-data-to-grid)) (in-package #:cl-plplot) (defvar *foreground-color* :black) (defvar *background-color* :white) (defvar *font* :normal) (defvar *font-size* 1.0) (defvar *axis-properties* '(:draw-bottom/left :draw-top/right :major-tick-labels-below/left :minor-ticks :major-ticks)) (defvar *cl-plplot-null* (gensym)) cl-plplot-0.6.0/src/window/bar-graph.lisp0000644000175000017500000002055310512221130020317 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Functions relevant to the bar-graph class. ;;;; ;;;; hazen 8/06 ;;;; (in-package #:cl-plplot) (defun bar-graph-check-dims (x data bar-widths line-colors fill-colors) (labels ((check-len (data-len array1 array1-name) (when (and array1 (not (= (length array1) data-len))) (format t "~A and data are not the same size! (~A != ~A)~%" array1-name (length array1) data-len) (return-from bar-graph-check-dims nil)))) (let ((data-len (array-dimension data 0)) (data-width (if (= (array-rank data) 2) (array-dimension data 1) 1))) (check-len data-len x "x") (check-len data-len bar-widths "bar-widths") (check-len data-width line-colors "line-colors") (check-len data-width fill-colors "fill-colors"))) t) (defun new-bar-graph (x data &key bar-widths side-by-side line-colors fill-colors (line-width 1.0) (filled t) (copy t)) "Creates a new bar-graph plot object. X is an array of size (n) specifying the centers of the bars with x[i] < x[i+1]. If x is nil then data will be plotted against its index. Data should be an array of size (n x m), where m > 0. Bar-widths should be an array of size (n). It will specify the full width of each bar. Defaults are chosen if this is not specified. Side-by-side is t or nil. It specifies whether to draw the bars on top of each other or next to each other. Line-colors should be an array of symbols of size (m) specifying colors in the current color table. Fill-colors should be an array of symbols of size (m) specifying what color to use when filling in the bars. Line-width is a number specifying how wide of a line to draw around the bar. Filled specifies whether or not the bars are filled. If copy is true, then copies are made of x, data and widths, otherwise references are kept to the original vectors." (when (bar-graph-check-dims x data bar-widths line-colors fill-colors) (make-instance 'bar-graph :data-x (copy-vector (if x x (make-index-vector (array-dimension data 0))) copy) :data-array (copy-matrix data copy) :bar-widths (copy-vector bar-widths copy) :side-by-side side-by-side :line-colors line-colors :fill-colors fill-colors :line-width line-width :filled filled))) (def-edit-method bar-graph (side-by-side line-colors fill-colors line-width filled) "edit-bar-graph, Edits the visual properties of a bar-graph. Set whether the bars are plotted side-by-side or on top of each other with side-by-side. Set the colors of the bars with colors. Set whether or not the bars are filled with filled.") (defmethod plot-min-max ((a-bar-graph bar-graph)) "Returns the minimum and maximum values of a bar graph as a 4 element vector." (let ((data (data-array a-bar-graph)) (x-len (1- (length (data-x a-bar-graph)))) (x-min) (x-max) (y-min 0) (y-max 0)) (if (bar-widths a-bar-graph) (let ((x-factor (if (side-by-side a-bar-graph) (if (> (array-rank data) 1) (array-dimension data 1) 1) 1))) (setf x-min (- (aref (data-x a-bar-graph) 0) (* 0.6 (aref (bar-widths a-bar-graph) 0) x-factor))) (setf x-max (+ (aref (data-x a-bar-graph) x-len) (* 0.6 (aref (bar-widths a-bar-graph) x-len) x-factor)))) (progn (setf x-min (- (aref (data-x a-bar-graph) 0) (* 0.6 (- (aref (data-x a-bar-graph) 1) (aref (data-x a-bar-graph) 0))))) (setf x-max (+ (aref (data-x a-bar-graph) x-len) (* 0.6 (- (aref (data-x a-bar-graph) x-len) (aref (data-x a-bar-graph) (1- x-len)))))))) (if (side-by-side a-bar-graph) (dotimes (i (array-dimension data 0)) (if (> (array-rank data) 1) (dotimes (j (array-dimension data 1)) (when (< (aref data i j) y-min) (setf y-min (aref data i j))) (when (> (aref data i j) y-max) (setf y-max (aref data i j)))) (progn (when (< (aref data i) y-min) (setf y-min (aref data i))) (when (> (aref data i) y-max) (setf y-max (aref data i)))))) (dotimes (i (array-dimension data 0)) (let ((sum 0)) (if (> (array-rank data) 1) (dotimes (j (array-dimension data 1)) (incf sum (aref data i j))) (incf sum (aref data i))) (when (< sum y-min) (setf y-min sum)) (when (> sum y-max) (setf y-max sum))))) (let ((diff (* 0.05 (- y-max y-min)))) (cond ((< (abs y-max) diff) (progn (decf y-min diff) (setf y-max 0.0))) ((< (abs y-min) diff) (progn (setf y-min 0.0) (incf y-max diff))) (t (progn (decf y-min diff) (incf y-max diff))))) (vector x-min x-max y-min y-max))) (defmethod default-bar-widths ((a-bar-graph bar-graph)) "Calculates default bar widths when these are not specified by the user." (let* ((data-x (data-x a-bar-graph)) (x-len (length data-x)) (default-widths (make-float-vector x-len)) (number-of-bars (if (side-by-side a-bar-graph) (if (> (array-rank (data-array a-bar-graph)) 1) (array-dimension (data-array a-bar-graph) 1) 1) 1))) (labels ((calc-width (x1 x2) (* 0.9 (/ (- x1 x2) number-of-bars)))) (dotimes (i (1- x-len)) (setf (aref default-widths i) (calc-width (aref data-x (1+ i)) (aref data-x i))) (setf (aref default-widths (1- x-len)) (calc-width (aref data-x (1- x-len)) (aref data-x (- x-len 2)))))) default-widths)) (defmethod render-plot ((a-bar-graph bar-graph) &optional ignored) "Renders a bar graph in the current window." (declare (ignore ignored)) (let ((data-x (data-x a-bar-graph)) (data (data-array a-bar-graph)) (bar-widths (if (bar-widths a-bar-graph) (bar-widths a-bar-graph) (default-bar-widths a-bar-graph))) (line-colors (line-colors a-bar-graph)) (fill-colors (fill-colors a-bar-graph))) (labels ((color-handler (colors color-index) (if colors (set-foreground-color (aref colors color-index)) (set-color-by-index color-index))) (coords-to-vectors (center width top bottom) (let* ((half-width (* 0.5 width)) (left (- center half-width)) (right (+ center half-width))) (values (vector left left right right left) (vector bottom top top bottom bottom)))) (draw-box (center width top bottom color-index) (multiple-value-bind (x y) (coords-to-vectors center width top bottom) (color-handler fill-colors color-index) (plfill x y) (color-handler line-colors color-index) (plwid (line-width a-bar-graph)) (plline x y)))) (if (= (array-rank (data-array a-bar-graph)) 1) (dotimes (i (length data-x)) (draw-box (aref data-x i) (aref bar-widths i) 0.0 (aref data i) 0)) (if (side-by-side a-bar-graph) (let ((number-bars (array-dimension data 1))) (dotimes (i (length data-x)) (let* ((bar-width (aref bar-widths i)) (real-width (* 1.11 bar-width)) (start-x (- (aref data-x i) (- (* 0.5 real-width number-bars) (* 0.5 real-width))))) (dotimes (j number-bars) (draw-box start-x bar-width 0.0 (aref data i j) j) (incf start-x real-width))))) (dotimes (i (length data-x)) (let ((start-y 0.0)) (dotimes (j (array-dimension data 1)) (draw-box (aref data-x i) (aref bar-widths i) start-y (+ start-y (aref data i j)) j) (incf start-y (aref data i j)))))))))) cl-plplot-0.6.0/src/window/contour-plot.lisp0000644000175000017500000003247710561460115021145 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the contour-plot class. ;;;; ;;;; hazen 10/06 ;;;; (in-package #:cl-plplot) ;; This function doesn't have much to (directly) with creating contour plots, ;; but it is very useful for gridding data for making contour plots. (defun x-y-z-data-to-grid (data x-grid y-grid &key (algorithm :grid-csa) optional-data) "Calls the plplot function plgriddata to turn irregulary spaced data as (x,y,z) points into the 2D array data[i,j] = z. Please see the PLplot manual for further documenation. data is either a 3 x N matrix of (x,y,z) points, or a list containing (x-vector, y-vector, z-vector). x-grid specifies the locations of the grid points in the x direction. y-grid specifies the locations of the grid points in the y direction. algorithm is one of :grid-csa, :grid-dtli, :grid-nni, :grid-nnidw, :grid-nnli or :grid-nnaidw and specifies what algorithm to use to grid the data. optional-data is a floating point number used in some of the algorithms for determining how to best grid the data." (let ((x-vector) (y-vector) (z-vector)) (if (listp data) (progn (setf x-vector (elt data 0)) (setf y-vector (elt data 1)) (setf z-vector (elt data 2))) (let ((data-len (array-dimension data 1))) (setf x-vector (make-float-vector data-len)) (setf y-vector (make-float-vector data-len)) (setf z-vector (make-float-vector data-len)) (dotimes (i data-len) (setf (aref x-vector i) (aref data 0 i)) (setf (aref y-vector i) (aref data 1 i)) (setf (aref z-vector i) (aref data 2 i))))) (plgriddata x-vector y-vector z-vector x-grid y-grid ; given algorithm, pass the right number (cond ((equal algorithm :grid-csa) 1) ((equal algorithm :grid-dtli) 2) ((equal algorithm :grid-nni) 3) ((equal algorithm :grid-nnidw) 4) ((equal algorithm :grid-nnli) 5) ((equal algorithm :grid-nnaidw) 6) (t (format t "x-y-z-data-to-grid called with wnrecognized algorithm ~A~%" algorithm) 1)) ; pass optional-data if specified, otherwise try and choose an intelligent default (if optional-data optional-data (cond ((equal algorithm :grid-nnidw) 2) ((equal algorithm :grid-nnli) 1) ((equal algorithm :grid-nni) 0) (t 1.0)))))) (defun check-contour-levels (data contour-levels) "Creates default contour levels based on data in the event that the contour levels have not already been specified." (if (and contour-levels (vectorp contour-levels)) contour-levels (progn (when contour-levels (format t "Contour-levels must be a vector of contour values. Using defaults instead.~%")) (let ((min (aref data 0 0)) (max (aref data 0 0)) (default-levels (make-float-vector 10))) (dotimes (i (array-dimension data 0)) (dotimes (j (array-dimension data 1)) (when (> (aref data i j) max) (setf max (aref data i j))) (when (< (aref data i j) min) (setf min (aref data i j))))) (let* ((range (- max min)) (increment (/ range 8))) (dotimes (i 10) (setf (aref default-levels i) min) (incf min increment))) default-levels)))) (defun check-mapping (data x-mapping y-mapping x-min x-max y-min y-max) "If x-mapping and y-mapping are defined, they are checked to make sure they are the right size. If they are not defined then default created based on x-min, x-max, y-min & y-max, or the dimensions of data in the event that these variables are also not defined." (if (and x-mapping y-mapping) (cond ((and (= 1 (array-rank x-mapping)) (= 1 (array-rank y-mapping))) (if (and (= (array-dimension data 0) (length x-mapping)) (= (array-dimension data 1) (length y-mapping))) (values t x-mapping y-mapping) (progn (format t "x-mapping (~A) & y-mapping (~A) dimensions must match data (~A, ~A).~%" (length x-mapping) (length y-mapping) (array-dimension data 0) (array-dimension data 1)) (values nil nil nil)))) ((and (= 2 (array-rank x-mapping)) (= 2 (array-rank y-mapping))) (if (and (= (array-dimension data 0) (array-dimension x-mapping 0)) (= (array-dimension data 1) (array-dimension x-mapping 1)) (= (array-dimension data 0) (array-dimension y-mapping 0)) (= (array-dimension data 1) (array-dimension y-mapping 1))) (values t x-mapping y-mapping) (progn (format t "x-mapping (~A, ~A) & y-mapping (~A, ~A) dimensions must match data (~A, ~A).~%" (array-dimension x-mapping 0) (array-dimension x-mapping 1) (array-dimension y-mapping 0) (array-dimension y-mapping 1) (array-dimension data 0) (array-dimension data 1)) (values nil nil nil)))) (t (progn (format t "x-mapping and y-mapping must either both be 1D or both be 2D matrices~%") (values nil nil nil)))) (progn (when (or x-mapping y-mapping) (format t "You must specify both x-mapping & y-mapping~%") (return-from check-mapping (values nil nil nil))) (let* ((default-x-mapping (make-float-vector (array-dimension data 0))) (default-y-mapping (make-float-vector (array-dimension data 1))) (checked-x-min (if x-min x-min 0)) (checked-x-max (if x-max x-max (1- (array-dimension data 0)))) (checked-y-min (if y-min y-min 0)) (checked-y-max (if y-max y-max (1- (array-dimension data 1)))) (dx (/ (- checked-x-max checked-x-min) (1- (array-dimension data 0)))) (dy (/ (- checked-y-max checked-y-min) (1- (array-dimension data 1))))) (dotimes (i (array-dimension data 0)) (setf (aref default-x-mapping i) (+ checked-x-min (* i dx)))) (dotimes (i (array-dimension data 1)) (setf (aref default-y-mapping i) (+ checked-y-min (* i dy)))) (values t default-x-mapping default-y-mapping))))) (defun new-contour-plot (data &key contour-levels (line-color *foreground-color*) (line-width 1) (fill-type :none) fill-colors x-min x-max x-mapping y-min y-max y-mapping (copy t)) "Creates a new contour plot. data is a 2D array of z values. contour-levels is a 1D vector of floats specifying the levels at which the contours should appear. If this is nil, then default contours are created based on the minimum and maximum values in data. line-color is a symbol specifying which color to use in the current color table for the contour lines. line-width is an integer specifying what size line to use for the contours (or zero for no line). fill-type is one of :none (contours only), :block (a single color between each contour) or :smooth (color varies continously between contours). fill-colors is a (optional) vector of colors from the current color table to use when fill-type is :block. x-min & y-min specify the location of data(0, 0) in plot coordinates. x-max & y-max specify the location of data(max, max) in plot coordinates. x-mapping & y-mapping are either 1 1D vectors or 2D matrices specifying how to map points in data into plot coordinates. If they are 1D vector, then data(i,j) is mapped to [x-mapping(i), y-mapping(j)]. If they are 2D vectors then data(i,j) is mapped to [x-mapping(i,j), y-mapping(i,j)]. They must be used together and both must be the same type & also match the dimensions of data. They will override x-min, y-min, x-max and y-max if they are specified." (multiple-value-bind (good? checked-x-mapping checked-y-mapping) (check-mapping data x-mapping y-mapping x-min x-max y-min y-max) (when good? (make-instance 'contour-plot :data (copy-matrix data copy) :line-width line-width :line-color line-color :fill-type fill-type :fill-colors fill-colors :contour-levels (check-contour-levels data (copy-vector contour-levels copy)) :x-mapping (copy-matrix checked-x-mapping copy) :y-mapping (copy-matrix checked-y-mapping copy))))) (def-edit-method contour-plot (line-color line-width fill-type fill-colors) "edit-contour-plot, Edits the visual properties of a contour plot Set the line color with :line-color (this should be a color symbol in the current color table). Set the line width with :line-width (integer, 0 means no line). Set the fill-type with :fill-type (:none :block :smooth). Set the fill-colors with :fill-colors (should be a vector of color symbols)") (defmethod plot-min-max ((a-plot contour-plot)) "Returns the minimum and maximum values in a contour plot as a 4 element vector." (if (= 1 (array-rank (x-mapping a-plot))) (vector (aref (x-mapping a-plot) 0) (aref (x-mapping a-plot) (1- (length (x-mapping a-plot)))) (aref (y-mapping a-plot) 0) (aref (y-mapping a-plot) (1- (length (y-mapping a-plot))))) (let ((x-min (aref (x-mapping a-plot) 0 0)) (x-max (aref (x-mapping a-plot) 0 0)) (y-min (aref (y-mapping a-plot) 0 0)) (y-max (aref (y-mapping a-plot) 0 0)) (dim-0 (1- (array-dimension (x-mapping a-plot) 0))) (dim-1 (1- (array-dimension (x-mapping a-plot) 1)))) (dotimes (i (1+ dim-1)) (when (< (aref (x-mapping a-plot) 0 i) x-min) (setf x-min (aref (x-mapping a-plot) 0 i))) (when (> (aref (x-mapping a-plot) dim-0 i) x-max) (setf x-max (aref (x-mapping a-plot) dim-0 i)))) (dotimes (i (1+ dim-0)) (when (< (aref (y-mapping a-plot) i 0) y-min) (setf y-min (aref (y-mapping a-plot) i 0))) (when (> (aref (y-mapping a-plot) i dim-1) y-max) (setf y-max (aref (y-mapping a-plot) i dim-1)))) (vector x-min x-max y-min y-max)))) ;; Draw the contour plot (defun make-smooth-contour-levels (contour-levels) "Given the contour levels, makes a version of them the maximum number of different levels, so that shading will hopefully appear smooth." ; FIXME: This assumes that the levels are equally spaced. (let* ((total-colors (color-table-size *current-extended-color-table*)) (start (aref contour-levels 0)) (end (aref contour-levels (1- (length contour-levels)))) (increment (/ (- end start) (1- total-colors))) (smooth-levels (make-float-vector total-colors))) (dotimes (i total-colors) (setf (aref smooth-levels i) (+ start (* increment i)))) smooth-levels)) (defmethod render-plot ((a-plot contour-plot) &optional ignored) "Renders a contour plot in the current window." (declare (ignore ignored)) ; Set the coordinate mapping callback function appropriately. The value ; is saved and reset for the benefit of other functions that might ; expect it to be something else. (let ((callback-fn (pl-get-pltr-fn))) (cond ((= 1 (array-rank (x-mapping a-plot))) (unless (equal (pl-get-pltr-fn) #'pltr1) (pl-set-pltr-fn #'pltr1))) ((= 2 (array-rank (x-mapping a-plot))) (unless (equal (pl-get-pltr-fn) #'pltr2) (pl-set-pltr-fn #'pltr2)))) ;; draw the plot ; deal with shaded plots first (cond ((equal (fill-type a-plot) :none)) ((equal (fill-type a-plot) :smooth) (plshades (data a-plot) 1 (array-dimension (data a-plot) 0) 1 (array-dimension (data a-plot) 1) (make-smooth-contour-levels (contour-levels a-plot)) 2 1 0 nil (x-mapping a-plot) (y-mapping a-plot))) ((equal (fill-type a-plot) :block) (dotimes (i (1- (length (contour-levels a-plot)))) (let ((current-color-index (if (fill-colors a-plot) (find-a-color *current-color-table* (aref (fill-colors a-plot) (mod i (length (fill-colors a-plot))))) (mod i (length (color-map *current-color-table*)))))) (plshade (data a-plot) 1 (array-dimension (data a-plot) 0) 1 (array-dimension (data a-plot) 1) (aref (contour-levels a-plot) i) (aref (contour-levels a-plot) (1+ i)) 0 current-color-index 2 current-color-index 0 current-color-index 0 nil (x-mapping a-plot) (y-mapping a-plot))))) (t (format t "Sorry I don't know how to draw contour plots of type ~A~%" (fill-type a-plot)))) ; draw the contours next (set-foreground-color (line-color a-plot)) (when (> (line-width a-plot) 0) (plwid (line-width a-plot)) (plcont (data a-plot) 1 (array-dimension (data a-plot) 0) 1 (array-dimension (data a-plot) 1) (contour-levels a-plot) (x-mapping a-plot) (y-mapping a-plot))) ; reset the point mapping callback function (pl-set-pltr-fn callback-fn))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/axis-label.lisp0000644000175000017500000001135710756454206020525 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the axis-label class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) ;; axis-label (new-object-defun axis-label (axis-text-item side displacement &key (location 0.5) (orientation :parallel)) "new-axis-label, Create and returns a new axis label. axis-text-item is a object of type text-item. side is one of :top, :bottom, :left or :right. displacement specifies the distance from the edge of the graph in units of the default font-size. location is the position of the label along the side of the graph (0.0 - 1.0). orientation is one :parallel or :perpendicular.") (def-edit-method axis-label (axis-text-item side displacement location orientation) "edit-axis-label, Edits a axis-label object. Set axis-text-item to a new object of class text-item with :axis-text-item. Set which side to draw the label on with :side. Set the displacement from the edge of the the graph with :displacement. Set the location with along the side of the graph with :location. Set the orientation with (:parallel or :perpendicular) with :orientation.") (defgeneric render-axis-label (axis-label)) (defmethod render-axis-label ((a-axis-label axis-label)) "Draws a axis label onto the current plot." (let ((side-spec)) (case (side a-axis-label) (:top (setf side-spec "t")) (:bottom (setf side-spec "b")) (:left (setf side-spec "l")) (otherwise (setf side-spec "r"))) (when (equal (orientation a-axis-label) :perpendicular) (setf side-spec (concatenate 'string side-spec "v"))) (plmtex side-spec (displacement a-axis-label) (location a-axis-label) (text-justification (axis-text-item a-axis-label)) (render-text (axis-text-item a-axis-label))))) ;; 3D-axis-label (new-object-defun 3D-axis-label (axis-text-item side displacement &key (location 0.5) (orientation :parallel) (primary/secondary :primary)) "new-3D-axis-label, Create and returns a new 3D axis label. axis-text-item is a object of type text-item. side is one of :x, :y, or :z. displacement specifies the distance from the edge of the graph in units of the default font-size. location is the position of the label along the side of the graph (0.0 - 1.0). orientation is one :parallel or :perpendicular. primary/secondary is one of :primary or :secondary. This specifies which of two possible choices for each axis should be labeled.") (def-edit-method 3D-axis-label (axis-text-item side displacement location orientation primary/secondary) "edit-3D-axis-label, Edits a 3D-axis-label object. Set axis-text-item to a new object of class text-item with :axis-text-item. Set which side to draw the label on with :side. Set the displacement from the edge of the the graph with :displacement. Set the location with along the side of the graph with :location. Set the orientation with (:parallel or :perpendicular) with :orientation. Set which axis to label (:primary or :secondary) with :primary/secondary") (defmethod render-axis-label ((a-axis-label 3D-axis-label)) "Draws a 3D axis label onto the current plot." (let ((side-spec (concatenate 'string (case (side a-axis-label) (:x "x") (:y "y") (:z "z")) (if (equal (primary/secondary a-axis-label) :primary) "p" "s") (if (equal (orientation a-axis-label) :perpendicular) "v" "")))) (plmtex3 side-spec (displacement a-axis-label) (location a-axis-label) (text-justification (axis-text-item a-axis-label)) (render-text (axis-text-item a-axis-label))))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/surface-plot.lisp0000644000175000017500000001245710566470532021111 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the surface-plot class. ;;;; ;;;; hazen 2/07 ;;;; (in-package #:cl-plplot) (defun new-surface-plot (data-x data-y data-z &key contour-levels (copy t) (line-width 1) (line-style 1) (line-color *foreground-color*) light-source surface-options) "Creates a new 3D (solid surface) plot. data-x specifies the x values of the points in data-z. If data-x is nil then data-z will be plotted against its row index in x. data-y specifies the y avlues of the points in data-z. If data-y is nil then data-z will be plotted against its column index in y. data-z is a 2D array of z values for the plot. contour-levels specifies the levels at which to draw contours, if desired. If this is not specified, default values are chosen. If copy is true then copies of data-x, data-y and data-z will be made, otherwise reference will be kept to the original vectors. line-width should be an integer line width, or zero if no line is desired line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. line-color is the color to use for the lines in the plot. light-source is a 3 element vector #(x y z) specifying the location of the light source that will illuminate the plot surface. surface-options is list containing zero or more of the following symbols: :faceted - a network of lines is drawing connecting the points that make up the surface. :base-contours - a contour plot is also drawn in the base xy plane. :surface-contours - contour levels are drawn on the surface of the plot. :curtain - a curtain between the borders of the surface and the base xy plane. :magnitude-coloring - the surface is colored according to the z value of the plot. If this is not set then surface is colored according the intensity of the reflected light from light source." (when (3D-plot-check-lengths data-x data-y data-z) (make-instance 'surface-plot :data-x (copy-vector (if data-x data-x (make-index-vector (array-dimension data-z 0))) copy) :data-y (copy-vector (if data-y data-y (make-index-vector (array-dimension data-z 1))) copy) :data-z (copy-matrix data-z copy) :contour-levels (check-contour-levels data-z (copy-vector contour-levels copy)) :line-width line-width :line-style line-style :line-color line-color :light-source (when light-source (copy-vector light-source copy)) :surface-options surface-options))) (def-edit-method surface-plot (line-width line-style line-color light-source surface-options) "edit-surface-plot, Edits the visual properties of a solid surface plot Set the line width with :line-width (integer, 0 means no line). Set the line style with :line-style (integer between 1 and 8). Set the line color with :line-color symbol. Move the light-source to a new position with :light-source #(x y z). Change the surface-options with :surface-options to a list including zero or more of :faceted, :base-contours, :surface-contours, :curtain and :magnitude-coloring") ;; draw a plot (defmethod render-plot ((a-plot surface-plot) &optional (default-symbol 0)) "Renders a surface plot in the current window." (declare (ignore default-symbol)) (set-foreground-color (line-color a-plot)) (when (> (line-width a-plot) 0) (when (range-check (line-style a-plot) 1 8) (pllsty (line-style a-plot))) (plwid (line-width a-plot))) (let ((parsed-options (if (listp (surface-options a-plot)) (apply #'+ (mapcar #'(lambda (x) (cond ((equal x :faceted) 128) ((equal x :base-contours) 8) ((equal x :surface-contours) 32) ((equal x :curtain) 64) ((equal x :magnitude-coloring) 4) (t (format t "Unknown surface options : ~A~%" x) 0))) (surface-options a-plot))) 0))) (when (vectorp (light-source a-plot)) (let ((source (light-source a-plot))) (pllightsource (aref source 0) (aref source 1) (aref source 2)))) (plsurf3d (data-x a-plot) (data-y a-plot) (data-z a-plot) parsed-options (contour-levels a-plot)))) ;;;; ;;;; Copyright (c) 2007 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/text-label.lisp0000644000175000017500000001136610756454206020545 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the text-label class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (new-object-defun text-label (label-text-item text-x text-y &key (text-dx 0.0) (text-dy 0.0)) "new-text-label, creates and returns a new text-label object. text-item should be an object created by new-text-item. text-x specifies the x location of the text reference point (in window coordinates). text-y specifies the y location of the text reference point. text-dx and text-dy specify the location of a second reference point (in window coordinates) the text is drawn along a line connecting (text-x,text-y) and (text-x + text-dx, text-y + text-dy).") (def-edit-method text-label (label-text-item text-x text-y text-dx text-dy) "edit-text-label, Edits a text-label object. Set text-item to a new object of class text-item with :label-text-item. Set the x location of the text with :text-x. Set the y location of the text with :text-y. Set dx for drawing text at an angle with :text-dx. Set dy for drawing text at an angle with :text-dy.") (new-object-defun 3D-text-label (label-text-item text-x text-y text-z &key (text-dx 0.0) (text-dy 0.0) (text-dz 0.0) (text-sx 0.0) (text-sy 0.0) (text-sz 0.0)) "new-3D-text-label, creates and returns a new 3D-text-label object. text-item should be an object created by new-text-item. text-x specifies the x location of the text reference point (in window coordinates). text-y specifies the y location of the text reference point. text-z specifies the y location of the text reference point. text-dx, text-dy and text-dz specify the location of a second reference point (in window coordinates) the text is drawn along a line connecting (text-x,text-y and text-z) and (text-x + text-dx, text-y + text-dy, text-z + text-dz). test-sx, text-sy and text-sz specify the location of a third reference point (in window coordinates) the text is sheared to be parallel to a line connecting (text-x,text-y and text-z) and (text-x + text-sx, text-y + text-sy, text-z + text-sz).") (def-edit-method 3D-text-label (label-text-item text-x text-y text-z text-dx text-dy text-dz text-sx text-sy text-sz) "edit-text-label, Edits a text-label object. Set text-item to a new object of class text-item with :label-text-item. Set the x location of the text with :text-x. Set the y location of the text with :text-y. Set the z location of the text with :text-z. Set dx for drawing text at an angle with :text-dx. Set dy for drawing text at an angle with :text-dy. Set dz for drawing text at an angle with :text-dz. Set sx for shearing text with :text-sx. Set sy for shearing text with :text-sy. Set sz for shearing text with :text-sz.") (defgeneric render-text-label (text-label)) (defmethod render-text-label ((a-text-label text-label)) "Draws a text label onto the current plot." (plptex (text-x a-text-label) (text-y a-text-label) (text-dx a-text-label) (text-dy a-text-label) (text-justification (label-text-item a-text-label)) (render-text (label-text-item a-text-label)))) (defmethod render-text-label ((a-text-label 3D-text-label)) "Draws a 3D text label onto the current plot." (plptex3 (text-x a-text-label) (text-y a-text-label) (text-z a-text-label) (text-dx a-text-label) (text-dy a-text-label) (text-dz a-text-label) (text-sx a-text-label) (text-sy a-text-label) (text-sz a-text-label) (text-justification (label-text-item a-text-label)) (render-text (label-text-item a-text-label)))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/text-item.lisp0000644000175000017500000001037710534722630020416 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the text-item class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (new-object-defun text-item (the-text &key (text-color *foreground-color*) (text-justification 0.5) (font-size *font-size*)) "new-text-item, Creates and returns a new text item. text is a string specifying the text. text-color is a symbol specifying the text color. text-justification specifies how to center the string relative to its reference point. 0.0 - 1.0, where 0.5 means the string is centered. font-size sets the fontsize relative to the default font size.") (def-edit-method text-item (the-text text-color text-justification font-size) "edit-text-item, Edits a text-item object. Set the text with :text. Set the color of the text with :text-color symbol. Set the justification with :text-justification (0.0 = left justified, 1.0 = right justified). Set the font-size with :font-size (relative to the default size).") (defmacro create-esc-function (function-name esc-string-start &optional esc-string-end) "creates functions that handle escaping strings for plplot." `(defun ,function-name (&rest strings) (let ((new-string ,esc-string-start)) (dolist (string strings) (setf new-string (concatenate 'string new-string string)) ,(unless esc-string-end `(setf new-string (concatenate 'string new-string ,esc-string-start)))) ,(when esc-string-end `(setf new-string (concatenate 'string new-string ,esc-string-end))) new-string))) ; these functions follow page 33 in the plplot manual. (create-esc-function superscript "#u" "#d") (create-esc-function subscript "#d" "#u") (defun backspace () "#b") (defun number-symbol () "##") (create-esc-function overline "#+" "#+") (create-esc-function underline "#-" "#-") (defun greek-char (roman-character) (concatenate 'string "#g" (string roman-character))) (create-esc-function normal-font "#fn") (create-esc-function roman-font "#fr") (create-esc-function italic-font "#fi") (create-esc-function script-font "#fs") (create-esc-function hershey-char "#(" ")") (create-esc-function unicode-char "#[" "]") (defun render-text (a-text-item &optional is-a-3d-window-label) "If this text is not the label of a 3d window, set the current color and font size to those specified by the text item. Then process the possibly utf-8 encoded string contained in text item to properly handle non ASCII characters and return the processed string." (unless is-a-3d-window-label (set-foreground-color (text-color a-text-item)) (plschr 0 (font-size a-text-item))) (let* ((utf8-text (the-text a-text-item)) (escaped-string (make-array (* 10 (length utf8-text)) :element-type 'character)) (l 0)) (dotimes (i (length utf8-text)) (let ((code (char-code (char utf8-text i)))) (if (> code 128) (let ((converted-char (format nil "#[~A]" code))) (dotimes (j (length converted-char)) (setf (char escaped-string l) (char converted-char j)) (incf l))) (progn (setf (char escaped-string l) (char utf8-text i)) (incf l))))) (subseq escaped-string 0 l))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/3D-window.lisp0000644000175000017500000002125710777302043020251 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the 3D window class. ;;;; ;;;; hazen 12/06 ;;;; (in-package #:cl-plplot) (new-object-defun 3D-window (&key x-axis y-axis z-axis title (window-line-width 1.0) (window-font-size *font-size*) (foreground-color *foreground-color*) (background-color *background-color*) (viewport-x-min 0.1) (viewport-x-max 0.9) (viewport-y-min 0.1) (viewport-y-max 0.9) plots text-labels color-table (altitude 60) (azimuth 30)) "new-3D-window, creates and returns a new 3D-window object x-axis is a object of type axis. y-axis is a object of type axis. z-axis is a object of type axis. title is a object of type axis-label. foreground-color is a color symbol in the current color table. background-color is a color symbol in the curretn color table. window-line-width is a floating point number specifying the pen width to use when drawing the border & the tick marks. window-font-size is the font size to use for the tick mark labels. viewport-x-min (0.0 - 1.0) is the location of the left side of the border in the device window. viewport-x-max (0.0 - 1.0) is the location of the right side of the border. viewport-y-min (0.0 - 1.0) is the location of the bottom side of the border. viewport-y-max (0.0 - 1.0) is the location of the top side of the border. plots is a list of plot objects. text-labels is a list of text-label objects. color-table specifies what color table to use. altitude specifies the angle by which to rotate the plot around the x axis. azimuth specified the angle by which to rotate the plot around the z axis.") (def-edit-method 3D-window (x-axis y-axis z-axis title foreground-color background-color window-line-width window-font-size viewport-x-min viewport-x-max viewport-y-min viewport-y-max plots text-labels color-table altitude azimuth) "edit-3D-window, edits a 3D window object. Set x-axis to a new object of type axis with :x-axis. Set y-axis to a new object of type axis with :y-axis. Set z-axis to a new object of type axis with :z-axis. Set title to a new object of type axis-label with :title. Set the foreground color with :foreground-color. Set the background color with :background-color. Set the pen width for drawing the border with :window-line-width. Set the font size for the tick labels with :window-font-size. Set the location of the left border with :viewport-x-min. Set the location of the right border with :viewport-x-max. Set the location of the bottom border with :viewport-y-min. Set the location of the top border with :viewport-y-max. Set :plots to a list of plot objects to change the plots associated with a window. Set :text-labels to a list of text-label objects to change the text-labels associated with a window. Set :color-table to a new color table object to change the colors of a plot. Set the observer altitude in degrees with :altitude. Set the observer azimuth in degrees with :azimuth.") (def-add-remove-methods 3D-window plots plot) ;Creates methods add-plot-to-window & remove-plot-from-window. (def-add-remove-methods 3D-window text-labels text-label) ;Creates methods add-text-label-to-window & remove-text-label-from-window. (defun basic-3D-window (&key (x-label "x-axis") (y-label "y-axis") (z-label "z-axis") (title "cl-plplot") x-axis-min x-axis-max y-axis-min y-axis-max z-axis-min z-axis-max (altitude 60) (azimuth 30) (background-color *background-color*) (foreground-color *foreground-color*)) "Creates a 3D window object with ready-to-go axises." (let* ((basic-properties (list :draw-bottom/left :draw-top/right :grid-lines :major-tick-labels-below/left :minor-ticks :major-ticks)) (title (new-axis-label (new-text-item title :font-size 1.5 :text-color foreground-color) :top 1.5)) (x-axis (new-axis :axis-min x-axis-min :axis-max x-axis-max :axis-labels (list (new-3D-axis-label (new-text-item x-label :font-size 1.3 :text-color foreground-color) :x 2.5)) :properties (append basic-properties (list :text-under-axis)))) (y-axis (new-axis :axis-min y-axis-min :axis-max y-axis-max :axis-labels (list (new-3D-axis-label (new-text-item y-label :font-size 1.3 :text-color foreground-color) :y 2.5)) :properties (append basic-properties (list :text-under-axis)))) (z-axis (new-axis :axis-min z-axis-min :axis-max z-axis-max :axis-labels (list (new-3D-axis-label (new-text-item z-label :font-size 1.3 :text-color foreground-color) :z 2.5)) :properties (append basic-properties (list :grid-lines :text-by-left-axis))))) (new-3d-window :x-axis x-axis :y-axis y-axis :z-axis z-axis :title title :foreground-color foreground-color :background-color background-color :altitude altitude :azimuth azimuth))) (defun render-3D-window (a-window device filename size-x size-y external-pointer) "This handles drawing a 3D window." ;; setup window (setup-window a-window device filename size-x size-y) ;; start plotting (plinit) (when external-pointer (pl-cmd 26 external-pointer)) (unwind-protect (progn ; setup viewport (pladv 0) (plvpor (viewport-x-min a-window) (viewport-x-max a-window) (viewport-y-min a-window) (viewport-y-max a-window)) (multiple-value-bind (x-min x-max y-min y-max z-min z-max) (get-axis-ranges a-window) (let ((y-offset (- -0.2 (* 0.01 (altitude a-window))))) (plwind -1.0 1.0 y-offset (+ 2.0 y-offset)) (plw3d 1.1 1.1 1.1 x-min x-max y-min y-max z-min z-max (altitude a-window) (azimuth a-window)))) ;; axis & axis labels (set-foreground-color (foreground-color a-window)) (pllsty 1) (plwid (window-line-width a-window)) (plschr 0 (window-font-size a-window)) (plbox3 (get-axis-properties (x-axis a-window)) "" ; x-axis (major-tick-interval (x-axis a-window)) (minor-tick-number (x-axis a-window)) (get-axis-properties (y-axis a-window)) "" ; y-axis (major-tick-interval (y-axis a-window)) (minor-tick-number (y-axis a-window)) (get-axis-properties (z-axis a-window)) "" ; z-axis (major-tick-interval (z-axis a-window)) (minor-tick-number (z-axis a-window))) ;; render plots (when (plots a-window) (let ((default-symbol 0)) (dolist (a-plot (plots a-window)) (render-plot a-plot default-symbol) (incf default-symbol)))) ;; text labels (when (text-labels a-window) (dolist (a-text-label (text-labels a-window)) (render-text-label a-text-label))) ;; title and axis labels (render-axis-label (title a-window)) (render-axis-labels (x-axis a-window)) (render-axis-labels (y-axis a-window)) (render-axis-labels (z-axis a-window))) (plend))) (defmethod render ((a-window 3D-window) device &key filename (size-x 600) (size-y 500) external-pointer) "Renders a 3D-window and it associated plots and labels using device. device: a string naming a plplot graphical device such as 'xwin'. filename: where to save the graph for file based devices. size-x: the size of the window in x (pixels). size-y: the size of the window in y (pixels). external-pointer: if the plplot graphical device is one that will plot into an external user supplied plotting area, then you can pass info about that plotting area in using this variable. If you are using cl-plplot in a multi-threaded environment you should thread lock prior to calling render." (render-3D-window a-window device filename size-x size-y external-pointer)) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; cl-plplot-0.6.0/src/window/axis.lisp0000644000175000017500000001216610535201244017432 0ustar hbabcockhbabcock;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;; ;;;; ;;;; Functions that are most closely related to the axis class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (new-object-defun axis (&key axis-min axis-max (major-tick-interval 0) (minor-tick-number 0) (properties *axis-properties*) axis-labels) "new-axis, Creates and returns an axis object. axis-min is the minimum value for the axis. axis-amx is the maximum value for the axis. major-tick-interval is the spacing between major ticks (0 means use plplot default). minor-tick-number is the number of minor ticks to put between the major ticks. properties is a list of symbols as explained in edit-axis. axis-labels is a list of axis-label objects.") (def-edit-method axis (axis-min axis-max major-tick-interval minor-tick-number properties) "edit-axis, Edits an axis. Set the minimum value with :axis-min. Set the maximum value with :axis-max. Set the spacing between major ticks with major-tick-interval. Set the spacing between minor ticks with minor-tick-interval. Set the properties with :properties. This should containing zero of more of the following symbols: :draw - draw axis on both sides of the window. :draw-bottom/left - draw axis on the bottom/left side of the window. :draw-top/right - draw axis on the top/right side of the window. :grid-lines - (z axis of 3D plots only) draw grid lines parallel to the x-y plane behind the figure. :fixed-point - use fixed point labels. :major-tick-grid - draw a grid on the graph at the major ticks. :minor-tick-grid - draw a grid on the graph at the minor ticks. :invert-ticks - draw ticks inward rather than outwards. :log-axis - draw the axis on a log scale. :major-tick-labels-above/right - draw the tick labels above/right of the ticks. :major-tick-labels-below/left - draw the tick labels below/left of the ticks. :minor-ticks - draw minor ticks. :major-ticks - draw major ticks. :text-under-axis - (x & y axis of 3D plots only) draw the text label under the x/y axis. :text-by-left-axis - (z axis of 3D plots only) draw the text label beside the left hand axis. :text-by-right-axis) (z axis of 3D plots only) draw the text label beside the right hand axis.") (def-add-remove-methods axis axis-labels axis-label) ;Creates the functions add-axis-label-to-axis & remove-axis-label-from-axis. (defgeneric get-axis-properties (axis)) (defmethod get-axis-properties ((a-axis axis)) "Creates an options string that we can pass to plplot to get the axis (and possibly a grid as well) drawn as desired by the user." (let ((opt-string "")) (labels ((my-cat (char) (setf opt-string (concatenate 'string opt-string (string char))))) (dolist (property (remove-duplicates (properties a-axis) :test #'equal)) (cond ((equal property :draw) (my-cat "a")) ((equal property :draw-bottom/left) (my-cat "b")) ((equal property :draw-top/right) (my-cat "c")) ((equal property :grid-lines) (my-cat "d")) ((equal property :fixed-point) (my-cat "f")) ((equal property :major-tick-grid) (my-cat "g")) ((equal property :minor-tick-grid) (my-cat "h")) ((equal property :invert-ticks) (my-cat "i")) ((equal property :log-axis) (my-cat "l")) ((equal property :major-tick-labels-above/right) (my-cat "m")) ((equal property :major-tick-labels-below/left) (my-cat "n")) ((equal property :minor-ticks) (my-cat "s")) ((equal property :major-ticks) (my-cat "t")) ((equal property :text-under-axis) (my-cat "u")) ((equal property :text-by-left-axis) (my-cat "u")) ((equal property :text-by-right-axis) (my-cat "v")) (t (format t "Unrecognized property ~A~%" property))))) opt-string)) (defgeneric render-axis-labels (axis)) (defmethod render-axis-labels ((a-axis axis)) "Draws all the labels associated with an axis onto the current plot." (when (axis-labels a-axis) (dolist (a-label (axis-labels a-axis)) (render-axis-label a-label)))) cl-plplot-0.6.0/src/window/window.lisp0000644000175000017500000003114310777302043020000 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the window class. ;;;; ;;;; hazen 6/06 ;;;; (in-package #:cl-plplot) (new-object-defun window (&key x-axis y-axis title (window-line-width 1.0) (window-font-size *font-size*) (foreground-color *foreground-color*) (background-color *background-color*) (viewport-x-min 0.1) (viewport-x-max 0.9) (viewport-y-min 0.1) (viewport-y-max 0.9) plots text-labels color-table) "new-window, creates and returns a new window object x-axis is a object of type axis. y-axis is a object of type axis. title is a object of type axis-label. foreground-color is a color symbol in the current color table. background-color is a color symbol in the curretn color table. window-line-width is a floating point number specifying the pen width to use when drawing the border & the tick marks. window-font-size is the font size to use for the tick mark labels. viewport-x-min (0.0 - 1.0) is the location of the left side of the border in the device window. viewport-x-max (0.0 - 1.0) is the location of the right side of the border. viewport-y-min (0.0 - 1.0) is the location of the bottom side of the border. viewport-y-max (0.0 - 1.0) is the location of the top side of the border. plots is a list of plot objects. text-labels is a list of text-label objects. color-table specifies what color table to use.") (def-edit-method window (x-axis y-axis title foreground-color background-color window-line-width window-font-size viewport-x-min viewport-x-max viewport-y-min viewport-y-max plots text-labels color-table) "edit-window, edits a window object. Set x-axis to a new object of type axis with :x-axis. Set y-axis to a new object of type axis with :y-axis. Set title to a new object of type axis-label with :title. Set the foreground color with :foreground-color. Set the background color with :background-color. Set the pen width for drawing the border with :window-line-width. Set the font size for the tick labels with :window-font-size. Set the location of the left border with :viewport-x-min. Set the location of the right border with :viewport-x-max. Set the location of the bottom border with :viewport-y-min. Set the location of the top border with :viewport-y-max. Set :plots to a list of plot objects to change the plots associated with a window. Set :text-labels to a list of text-label objects to change the text-labels associated with a window. Set :color-table to a new color table object to change the colors of a plot.") (def-add-remove-methods window plots plot) ;Creates methods add-plot-to-window & remove-plot-from-window. (def-add-remove-methods window text-labels text-label) ;Creates methods add-text-label-to-window & remove-text-label-from-window. (defgeneric bring-to-front (a-window a-plot)) (defmethod bring-to-front ((a-window window) (a-plot plot)) "Organizes the plots so that a-plot is drawn on top." (when (member a-plot (plots a-window)) (remove-plot-from-window a-window a-plot) (add-plot-to-window a-window a-plot))) (defgeneric send-to-back (a-window a-plot)) (defmethod send-to-back ((a-window window) (a-plot plot)) "Organizes the plots so that a-plot is drawn on the bottom." (when (member a-plot (plots a-window)) (remove-plot-from-window a-window a-plot) (setf (plots a-window) (append (list a-plot) (plots a-window))))) (defun basic-window (&key (x-label "x-axis") (y-label "y-axis") (title "cl-plplot") x-axis-min x-axis-max y-axis-min y-axis-max (background-color *background-color*) (foreground-color *foreground-color*)) "Creates a basic window object with ready-to-go axises." (let ((a-color-table (default-color-table)) (title (new-axis-label (new-text-item title :font-size 1.5 :text-color foreground-color) :top 1.5)) (x-axis (new-axis :axis-min x-axis-min :axis-max x-axis-max :axis-labels (list (new-axis-label (new-text-item x-label :font-size 1.3 :text-color foreground-color) :bottom 2.5)))) (y-axis (new-axis :axis-min y-axis-min :axis-max y-axis-max :axis-labels (list (new-axis-label (new-text-item y-label :font-size 1.3 :text-color foreground-color) :left 3.0))))) (new-window :x-axis x-axis :y-axis y-axis :title title :foreground-color foreground-color :background-color background-color :color-table a-color-table))) (defgeneric edit-window-axis (window which-axis &key axis-min axis-max major-tick-interval minor-tick-number properties)) (defmethod edit-window-axis ((a-window window) which-axis &key (axis-min *cl-plplot-null*) (axis-max *cl-plplot-null*) (major-tick-interval *cl-plplot-null*) (minor-tick-number *cl-plplot-null*) (properties *cl-plplot-null*)) "Allows the user to edit the axis of a window. which-axis should be one of the symbols :x or :y (or :z for 3D-windows only). See edit-axis for a more detailed explanation of the meaning of the different key words." (let ((a-axis (cond ((equal which-axis :x) (x-axis a-window)) ((equal which-axis :y) (y-axis a-window)) ((equal which-axis :z) (z-axis a-window))))) (edit-axis a-axis :axis-min axis-min :axis-max axis-max :major-tick-interval major-tick-interval :minor-tick-number minor-tick-number :properties properties))) ; FIXME: ; This function seems long and awkward and redundant for what it does. It seems ; like it should be possible to have a function that this function would call on ; each axis. However, this will involve changing the plot-min-max function ; for each plot type so that you could specify which axis you were interested ; in... (defun get-axis-ranges (a-window) "Figures out the minimum and maximum values for the plot axises if this has not already been specified. Defaults to 1.0 x 1.0 x 1.0 if there are no plots associated with the window." (let ((x-min (axis-min (x-axis a-window))) (x-max (axis-max (x-axis a-window))) (y-min (axis-min (y-axis a-window))) (y-max (axis-max (y-axis a-window))) (z-min (if (slot-exists-p a-window 'z-axis) (axis-min (z-axis a-window)) 0.0)) (z-max (if (slot-exists-p a-window 'z-axis) (axis-max (z-axis a-window)) 1.0))) (unless (and x-min x-max y-min y-max) (let ((temp-x-min) (temp-x-max) (temp-y-min) (temp-y-max) (temp-z-min) (temp-z-max)) (if (plots a-window) (dolist (a-plot (plots a-window)) (let ((range (plot-min-max a-plot))) (when (or (not temp-x-min) (< (aref range 0) temp-x-min)) (setf temp-x-min (aref range 0))) (when (or (not temp-x-max) (> (aref range 1) temp-x-max)) (setf temp-x-max (aref range 1))) (when (or (not temp-y-min) (< (aref range 2) temp-y-min)) (setf temp-y-min (aref range 2))) (when (or (not temp-y-max) (> (aref range 3) temp-y-max)) (setf temp-y-max (aref range 3))) (when (>= (length range) 6) (when (or (not temp-z-min) (< (aref range 4) temp-z-min)) (setf temp-z-min (aref range 4))) (when (or (not temp-z-max) (> (aref range 5) temp-z-max)) (setf temp-z-max (aref range 5)))))) (progn (setf temp-x-min 0.0) (setf temp-x-max 1.0) (setf temp-y-min 0.0) (setf temp-y-max 1.0) (setf temp-z-min 0.0) (setf temp-z-max 1.0))) (unless x-min (setf x-min temp-x-min)) (unless x-max (setf x-max temp-x-max)) (unless y-min (setf y-min temp-y-min)) (unless y-max (setf y-max temp-y-max)) (unless z-min (setf z-min temp-z-min)) (unless z-max (setf z-max temp-z-max)))) (values x-min x-max y-min y-max z-min z-max))) (defun setup-window (a-window device filename size-x size-y) "Handles window setup. Factored out because both render-window and render-3D-window use this functionality, then diverge afterwards." (plsdev device) (when filename (plsfnam filename)) (plspage 0 0 size-x size-y 0 0) ;; color table initialization (let ((a-color-table (color-table a-window))) (if a-color-table (setf *current-color-table* a-color-table) (setf *current-color-table* (default-color-table)))) (initialize-color-table *current-color-table* (foreground-color a-window) (background-color a-window)) ;; extended color table initialization (let ((a-extended-color-table (extended-color-table a-window))) (if a-extended-color-table (setf *current-extended-color-table* a-extended-color-table) (setf *current-extended-color-table* (default-extended-color-table)))) (initialize-extended-color-table *current-extended-color-table*)) (defun render-window (a-window device filename size-x size-y external-pointer &optional want-mouse?) "This handles drawing the window & optionally returns the coordinates of a mouse click." ;; setup window (setup-window a-window device filename size-x size-y) ;; start plotting (plinit) (when external-pointer (pl-cmd 26 external-pointer)) (unwind-protect (progn (pladv 0) (plvpor (viewport-x-min a-window) (viewport-x-max a-window) (viewport-y-min a-window) (viewport-y-max a-window)) (multiple-value-bind (x-min x-max y-min y-max) (get-axis-ranges a-window) (plwind x-min x-max y-min y-max)) ;; render plots (when (plots a-window) (let ((default-symbol 0)) (dolist (a-plot (plots a-window)) (render-plot a-plot default-symbol) (incf default-symbol)))) ;; text labels (when (text-labels a-window) (dolist (a-text-label (text-labels a-window)) (render-text-label a-text-label))) ;; title, axis & axis labels (set-foreground-color (foreground-color a-window)) (pllsty 1) (plwid (window-line-width a-window)) (plschr 0 (window-font-size a-window)) (plbox (get-axis-properties (x-axis a-window)) (major-tick-interval (x-axis a-window)) (minor-tick-number (x-axis a-window)) (get-axis-properties (y-axis a-window)) (major-tick-interval (y-axis a-window)) (minor-tick-number (y-axis a-window))) (render-axis-label (title a-window)) (render-axis-labels (x-axis a-window)) (render-axis-labels (y-axis a-window)) ;; get mouse if requested (when want-mouse? (plgetcursor))) (plend))) (defgeneric get-cursor (window device &key size-x size-y)) (defmethod get-cursor ((a-window window) device &key (size-x 600) (size-y 500)) "Get the location (in window coordinates) of the next mouse click. In order to do this the window must first be rendered so that the user has something to click on. Note that this cannot be used with those drivers that draw into a user supplied area such as ext-cairo." (let ((mouse (render-window a-window device nil size-x size-y nil t))) (when mouse (values (elt mouse 8) (elt mouse 9))))) (defgeneric render (window device &key filename size-x size-y external-pointer)) (defmethod render ((a-window window) device &key filename (size-x 600) (size-y 500) external-pointer) "Renders a window and it associated plots and labels using device. device: a string naming a plplot graphical device such as 'xwin'. filename: where to save the graph for file based devices. size-x: the size of the window in x (pixels). size-y: the size of the window in y (pixels). external-pointer: if the plplot graphical device is one that will plot into an external user supplied plotting area, then you can pass info about that plotting area in using this variable. If you are using cl-plplot in a multi-threaded environment you should thread lock prior to calling render." (render-window a-window device filename size-x size-y external-pointer)) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;;cl-plplot-0.6.0/src/window/3D-mesh.lisp0000644000175000017500000001562010566470532017700 0ustar hbabcockhbabcock;;;; ;;;; Functions that are most closely related to the 3D-mesh class. ;;;; ;;;; hazen 12/06 ;;;; (in-package #:cl-plplot) (defun 3D-plot-check-lengths (data-x data-y data-z) "Checks that the arrays we have been given are of the appropriate size." (when (and data-x (/= (length data-x) (array-dimension data-z 0))) (format t "data-x and data-z do not have the right dimensions! (~A /= ~A)~%" (length data-x) (array-dimension data-z 0)) (return-from 3D-plot-check-lengths nil)) (when (and data-y (/= (length data-y) (array-dimension data-z 1))) (format t "data-y and data-z do not have the right dimensions! (~A /= ~A)~%" (length data-y) (array-dimension data-z 1)) (return-from 3D-plot-check-lengths nil)) t) (defun new-3D-mesh (data-x data-y data-z &key contour-levels (copy t) (line-width 1) (line-style 1) (line-color *foreground-color*) (grid-type :grid-xy) contour-options curtain) "Creates a new 3D mesh (surface) plot. data-x specifies the x values of the points in data-z. If data-x is nil then data-z will be plotted against its row index in x. data-y specifies the y avlues of the points in data-z. If data-y is nil then data-z will be plotted against its column index in y. data-z is a 2D array of z values for the plot. contour-levels specifies the levels at which to draw contours, if desired. If this is not specified, default values are chosen. If copy is true then copies of data-x, data-y and data-z will be made, otherwise reference will be kept to the original vectors. line-width should be an integer line width, or zero if no line is desired line-style specifies what style line to draw (if a line is drawn), this should be a number between 1 and 8. line-color is the color to use for the lines in the plot. grid-type should be one of :gridx, :gridy or :gridxy. This specifies whether to draw lines only in x, only in y, or in both dimensions between the data points. contour-options should be one of nil, :magnitude-contour, :base-contour or :both. nil - no contours. :magnitude-contour - draw contour lines on the plot. :base-contour - draw contour lines on the x-y plane below the plot. :both - draw both magnitude and base contours. curtain should be t or nil. This specifies whether to draw a 'curtain' around the edges of the plot." (when (3D-plot-check-lengths data-x data-y data-z) (make-instance '3D-mesh :data-x (copy-vector (if data-x data-x (make-index-vector (array-dimension data-z 0))) copy) :data-y (copy-vector (if data-y data-y (make-index-vector (array-dimension data-z 1))) copy) :data-z (copy-matrix data-z copy) :contour-levels (check-contour-levels data-z (copy-vector contour-levels copy)) :line-width line-width :line-style line-style :line-color line-color :grid-type grid-type :contour-options contour-options :curtain curtain))) (def-edit-method 3D-mesh (line-width line-style line-color grid-type contour-options curtain) "edit-3D-mesh, Edits the visual properties of a 3D mesh Set the line width with :line-width (integer, 0 means no line). Set the line style with :line-style (integer between 1 and 8). Set the line color with :line-color symbol. Set the grid type with :grid-type to one of (:gridx, :gridy or :gridxy). Set the contour options with :contour-options to one of (:magnitude-contour, :base-contour or :both) Set the whether or not display a curtain with :curtain") (defmethod plot-min-max ((a-plot 3D-plot)) "Returns the minimum and maximum values in the 3D plot class object as a 6 element vector." (let* ((x-data (data-x a-plot)) (y-data (data-y a-plot)) (z-data (data-z a-plot)) (min-x (aref x-data 0)) (max-x (aref x-data 0)) (min-y (aref y-data 0)) (max-y (aref y-data 0)) (min-z (aref z-data 0 0)) (max-z (aref z-data 0 0))) (dotimes (i (length x-data)) (when (< (aref x-data i) min-x) (setf min-x (aref x-data i))) (when (> (aref x-data i) max-x) (setf max-x (aref x-data i))) (when (< (aref y-data i) min-y) (setf min-y (aref y-data i))) (when (> (aref y-data i) max-y) (setf max-y (aref y-data i))) (dotimes (j (length y-data)) (when (< (aref z-data i j) min-z) (setf min-z (aref z-data i j))) (when (> (aref z-data i j) max-z) (setf max-z (aref z-data i j))))) (vector min-x max-x min-y max-y min-z max-z))) ;; draw a plot (defmethod render-plot ((a-plot 3D-mesh) &optional (default-symbol 0)) "Renders a 3D plot in the current window." (declare (ignore default-symbol)) (set-foreground-color (line-color a-plot)) (when (> (line-width a-plot) 0) (when (range-check (line-style a-plot) 1 8) (pllsty (line-style a-plot))) (plwid (line-width a-plot))) (let ((parsed-options (+ (cond ((equal (grid-type a-plot) :grid-x) 1) ((equal (grid-type a-plot) :grid-y) 2) ((equal (grid-type a-plot) :grid-xy) 3) (t (format t "Unknown grid option : ~A, using default option~%" (grid-type a-plot)) 3)) (cond ((equal (contour-options a-plot) :magnitude-contour) 4) ((equal (contour-options a-plot) :base-contour) 8) ((equal (contour-options a-plot) :both) (+ 4 8)) (t (when (contour-options a-plot) (format t "Unknown contour option : ~A, using default option~%" (contour-options a-plot))) 0)) (if (curtain a-plot) 64 0)))) (if (contour-options a-plot) (if (curtain a-plot) (plot3dc (data-x a-plot) (data-y a-plot) (data-z a-plot) parsed-options (contour-levels a-plot)) (plmeshc (data-x a-plot) (data-y a-plot) (data-z a-plot) parsed-options (contour-levels a-plot))) (plmesh (data-x a-plot) (data-y a-plot) (data-z a-plot) parsed-options)))) ;;;; ;;;; Copyright (c) 2006 Hazen P. Babcock ;;;; ;;;; Permission is hereby granted, free of charge, to any person obtaining a copy ;;;; of this software and associated documentation files (the "Software"), to ;;;; deal in the Software without restriction, including without limitation the ;;;; rights to use, copy, modify, merge, publish, distribute, sublicense, and/or ;;;; sell copies of the Software, and to permit persons to whom the Software is ;;;; furnished to do so, subject to the following conditions: ;;;; ;;;; The above copyright notice and this permission notice shall be included in ;;;; all copies or substantial portions of the Software. ;;;; ;;;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ;;;; IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ;;;; FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ;;;; AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ;;;; LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ;;;; FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS ;;;; IN THE SOFTWARE. ;;;;