Back to index

texmacs  1.0.7.15
edit_main.cpp
Go to the documentation of this file.
00001 
00002 /******************************************************************************
00003 * MODULE     : editor.cpp
00004 * DESCRIPTION: routines for the editor
00005 * COPYRIGHT  : (C) 1999  Joris van der Hoeven
00006 *******************************************************************************
00007 * This software falls under the GNU general public license version 3 or later.
00008 * It comes WITHOUT ANY WARRANTY WHATSOEVER. For details, see the file LICENSE
00009 * in the root directory or <http://www.gnu.org/licenses/gpl-3.0.html>.
00010 ******************************************************************************/
00011 
00012 #include "edit_main.hpp"
00013 #include "tm_buffer.hpp"
00014 #include "file.hpp"
00015 #include "sys_utils.hpp"
00016 #include "printer.hpp"
00017 #include "convert.hpp"
00018 #include "connect.hpp"
00019 #include "typesetter.hpp"
00020 #include "drd_std.hpp"
00021 #include "message.hpp"
00022 #include <setjmp.h>
00023 #ifdef EXPERIMENTAL
00024 #include "../../Style/Memorizer/clean_copy.hpp"
00025 #endif
00026 
00027 #ifdef PDF_RENDERER
00028 #include "Pdf/pdf_renderer.hpp"
00029 #endif
00030 
00031 #ifdef USE_GS
00032 #include "Ghostscript/gs_utilities.hpp"
00033 #endif
00034 
00035 #ifdef QTTEXMACS
00036 #include "Qt/qt_utilities.hpp"
00037 #endif
00038 
00039 /******************************************************************************
00040 * Constructors and destructor
00041 ******************************************************************************/
00042 
00043 editor_rep::editor_rep ():
00044   simple_widget_rep (), cvw (NULL), mvw (NULL),
00045   drd (buf->buf->abbr, std_drd), et (the_et), rp (buf->rp) {}
00046 
00047 editor_rep::editor_rep (server_rep* sv2, tm_buffer buf2):
00048   simple_widget_rep (), sv (sv2), cvw (NULL), mvw (NULL), buf (buf2),
00049   drd (buf->buf->abbr, std_drd), et (the_et), rp (buf2->rp) {}
00050 
00051 edit_main_rep::edit_main_rep (server_rep* sv, tm_buffer buf):
00052   editor_rep (sv, buf), props (UNKNOWN), ed_obs (edit_observer (this))
00053 {
00054 #ifdef EXPERIMENTAL
00055   cct= copy (subtree (et, rp));
00056   copy_ip (subtree (et, rp), cct);
00057 #endif
00058   attach_observer (subtree (et, rp), ed_obs);
00059   notify_change (THE_TREE);
00060   tp= correct_cursor (et, rp * 0);
00061 }
00062 
00063 edit_main_rep::~edit_main_rep () {
00064   detach_observer (subtree (et, rp), ed_obs);
00065 #ifdef EXPERIMENTAL
00066   mem= memorizer ();
00067 #endif
00068 }
00069 
00070 editor
00071 new_editor (server_rep* sv, tm_buffer buf) {
00072   return tm_new<edit_main_rep> (sv, buf);
00073 }
00074 
00075 /******************************************************************************
00076 * Properties
00077 ******************************************************************************/
00078 
00079 void
00080 edit_main_rep::set_property (scheme_tree what, scheme_tree val) {
00081   props (what)= val;
00082 }
00083 
00084 void
00085 edit_main_rep::set_bool_property (string what, bool val) {
00086   props (what)= (val? string ("true"): string ("false"));
00087 }
00088 
00089 void
00090 edit_main_rep::set_int_property (string what, int val) {
00091   props (what)= as_tree (val);
00092 }
00093 
00094 void
00095 edit_main_rep::set_string_property (string what, string val) {
00096   props (what)= val;
00097 }
00098 
00099 scheme_tree
00100 edit_main_rep::get_property (scheme_tree what) {
00101   return props [what];
00102 }
00103 
00104 bool
00105 edit_main_rep::get_bool_property (string what) {
00106   return as_bool (props [what]);
00107 }
00108 
00109 int
00110 edit_main_rep::get_int_property (string what) {
00111   return as_int (props [what]);
00112 }
00113 
00114 string
00115 edit_main_rep::get_string_property (string what) {
00116   return as_string (props [what]);
00117 }
00118 
00119 /******************************************************************************
00120 * Global routines
00121 ******************************************************************************/
00122 
00123 void
00124 edit_main_rep::clear_buffer () {
00125   assign (rp, tree (DOCUMENT, tree ("")));
00126 }
00127 
00128 void
00129 edit_main_rep::new_window () {
00130 }
00131 
00132 void
00133 edit_main_rep::clone_window () {
00134 }
00135 
00136 void
00137 edit_main_rep::tex_buffer () {
00138 }
00139 
00140 url
00141 edit_main_rep::get_name () {
00142   return buf->buf->name;
00143 }
00144 
00145 void
00146 edit_main_rep::focus_on_this_editor () {
00147   sv->focus_on_editor (this);
00148 }
00149 
00150 void
00151 edit_main_rep::notify_page_change () {
00152   if (is_attached (this)) send_invalidate_all (this);
00153 }
00154 
00155 /******************************************************************************
00156 * Printing
00157 ******************************************************************************/
00158 
00159 string printing_dpi ("600");
00160 string printing_cmd ("lpr");
00161 string printing_on ("a4");
00162 
00163 void
00164 edit_main_rep::print (url name, bool conform, int first, int last) {
00165   bool pdf= (suffix (name) == "pdf");
00166   url orig= resolve (name, "");
00167 
00168 #ifndef PDF_RENDERER
00169 #ifdef USE_GS
00170   if (pdf) name= url_temp (".ps");
00171 #endif
00172 #else
00173   (void) pdf;  // avoid annoying warning
00174 #endif
00175   
00176   string medium = env->get_string (PAGE_MEDIUM);
00177   if (conform && (medium != "paper")) conform= false;
00178   // FIXME: better command for conform printing
00179 
00180   // Set environment variables for printing
00181 
00182   typeset_prepare ();
00183   env->write (DPI, printing_dpi);
00184   env->write (PAGE_SHOW_HF, "true");
00185   env->write (PAGE_SCREEN_MARGIN, "false");
00186   if (!conform) {
00187     env->write (PAGE_MEDIUM, "paper");
00188     env->write (PAGE_PRINTED, "true");
00189   }
00190 
00191   // Typeset pages for printing
00192 
00193   box the_box= typeset_as_document (env, subtree (et, rp), reverse (rp));
00194 
00195   // Determine parameters for printer
00196 
00197   string page_type = env->get_string (PAGE_TYPE);
00198   double w         = env->page_width;
00199   double h         = env->page_height;
00200   double cm        = env->as_length (string ("1cm"));
00201   bool   landsc    = env->page_landscape;
00202   int    dpi       = as_int (printing_dpi);
00203   int    start     = max (0, first-1);
00204   int    end       = min (N(the_box[0]), last);
00205   int    pages     = end-start;
00206   if (conform) {
00207     page_type= "user";
00208     SI bw= the_box[0][0]->w();
00209     SI bh= the_box[0][0]->h();
00210     string bws= as_string (bw) * "tmpt";
00211     string bhs= as_string (bh) * "tmpt";
00212     w= env->as_length (bws);
00213     h= env->as_length (bhs);
00214   }
00215 
00216   // Print pages
00217 
00218   int i;
00219   
00220 #ifdef PDF_RENDERER
00221   renderer ren = (pdf ? 
00222     pdf_renderer (name, dpi, pages, page_type, landsc, w/cm, h/cm) :
00223     printer (name, dpi, pages, page_type, landsc, w/cm, h/cm) );
00224 #else
00225   renderer ren = printer (name, dpi, pages, page_type, landsc, w/cm, h/cm);
00226 #endif
00227   
00228   for (i=start; i<end; i++) {
00229     tree bg= env->read (BG_COLOR);
00230     ren->set_background_pattern (bg);
00231     if (bg != "white")
00232       ren->clear_pattern (0, (SI) -h, (SI) w, 0);
00233 
00234     rectangles rs;
00235     the_box[0]->sx(i)= 0;
00236     the_box[0]->sy(i)= 0;
00237     the_box[0][i]->redraw (ren, path (0), rs);
00238     if (i<end-1) ren->next_page ();
00239   }
00240   tm_delete (ren);
00241 
00242 #ifndef PDF_RENDERER
00243 #ifdef USE_GS
00244   if (pdf) {
00245     gs_to_pdf (name, orig);
00246     ::remove (name);
00247   }
00248 #endif
00249 #endif
00250 }
00251 
00252 void
00253 edit_main_rep::print_to_file (url name, string first, string last) {
00254   print (name, false, as_int (first), as_int (last));
00255 }
00256 
00257 
00258 void
00259 edit_main_rep::print_buffer (string first, string last) {
00260   url target= url_temp (".ps"); 
00261   print (target, false, as_int (first), as_int (last));
00262   system (printing_cmd, target);  // Send the document to the printer
00263   ::remove (target);
00264 }
00265 
00266 #ifdef THISISTHEPREVIOUSCODE_IJUSTLEFTITHEREINCASE
00267 void
00268 edit_main_rep::print_buffer (string first, string last) {
00269   // in Qt this is the main entry point to the printing subsystem.
00270   // the other routines (print_to_file, ...) are overriden since all fine tuning 
00271   // is made here via the Qt print dialog
00272   bool to_file, landscape;
00273   url name = url_none();
00274   string printer;
00275   string paper_type;
00276   if (qt_print (to_file, landscape, printer, name, first, last, paper_type)) {
00277       if (!to_file) name = url_temp (".ps");
00278       print (name, false, as_int (first), as_int (last));
00279       if (!to_file) {
00280         string cmd = printing_cmd * " -P" * printer;
00281         system (cmd, name);  
00282         ::remove (name);
00283       }
00284   }
00285 }
00286 #endif
00287 
00288 void
00289 edit_main_rep::export_ps (url name, string first, string last) {
00290   print (name, true, as_int (first), as_int (last));
00291 }
00292 
00293 array<int>
00294 edit_main_rep::print_snippet (url name, tree t) {
00295   bool ps= suffix (name) == "ps" || suffix (name) == "eps";
00296   typeset_prepare ();
00297   int dpi= as_int (printing_dpi);
00298   //if (!ps) t= tree (WITH, MAGNIFICATION, "2", PAGE_WIDTH, "40cm", t);
00299   if (!ps) t= tree (WITH, MAGNIFICATION, "1.6", PAGE_WIDTH, "40cm", t);
00300   box b= typeset_as_box (env, t, path ());
00301   if (b->x4 - b->x3 >= 5*PIXEL && b->y4 - b->y3 >= 5*PIXEL) {
00302     if (ps) make_eps (name, b, dpi);
00303     else {
00304       url temp= url_temp (".eps");
00305       make_eps (temp, b, dpi);
00306       ::remove (name);
00307       system ("convert", temp, name);
00308       if (!exists (name))
00309         cout << "TeXmacs] warning, failed to create image " << name << "\n";
00310       ::remove (temp);
00311     }
00312   }
00313   array<int> a;
00314   a << b->x3 << b->y3 << b->x4 << b->y4;
00315   return a;
00316 }
00317 
00318 /******************************************************************************
00319 * Evaluation of expressions
00320 ******************************************************************************/
00321 
00322 void
00323 edit_main_rep::footer_eval (string s) {
00324   // s= unslash (s); // FIXME: dirty fix; should not be necessary
00325   s= tm_decode (s);
00326   string r= object_to_string (eval (s));
00327   set_message (verbatim (r), "evaluate expression");
00328 }
00329 
00330 tree
00331 edit_main_rep::the_line () {
00332   path p= search_parent_upwards (DOCUMENT);
00333   return copy (subtree (et, p));
00334 }
00335 
00336 tree
00337 edit_main_rep::the_root () {
00338   return et;
00339 }
00340 
00341 tree
00342 edit_main_rep::the_buffer () {
00343   return subtree (et, rp);
00344 }
00345 
00346 tree
00347 edit_main_rep::the_subtree (path p) {
00348   return subtree (et, p);
00349 }
00350 
00351 path
00352 edit_main_rep::the_buffer_path () {
00353   return copy (rp);
00354 }
00355 
00356 path
00357 edit_main_rep::the_path () {
00358   return copy (tp);
00359 }
00360 
00361 path
00362 edit_main_rep::the_shifted_path () {
00363   return shift (et, tp, 1);
00364 }
00365 
00366 /******************************************************************************
00367 * Miscellaneous
00368 ******************************************************************************/
00369 
00370 void
00371 edit_main_rep::show_tree () {
00372   stretched_print (et, true);
00373   // cout << et << "\n";
00374 }
00375 
00376 void
00377 edit_main_rep::show_env () {
00378   cout << env << "\n";
00379 }
00380 
00381 void
00382 edit_main_rep::show_path () {
00383   cout << tp << "\n";
00384 }
00385 
00386 void
00387 edit_main_rep::show_cursor () {
00388   cout << "Principal cursor: "
00389        << cu->ox << ", " << cu->oy << " [" << cu->delta << "]\n";
00390   cout << "Ghost cursor    : "
00391        << mv->ox << ", " << mv->oy << " [" << mv->delta << "]\n";
00392 }
00393 
00394 void
00395 edit_main_rep::show_selection () {
00396   selection sel; selection_get (sel);
00397   cout << "physical  selection: " << start_p << " --- " << end_p << "\n";
00398   cout << "logical   selection: " << sel->start << " --- " << sel->end << "\n";
00399 }
00400 
00401 void
00402 edit_main_rep::show_meminfo () {
00403   mem_info ();
00404 }
00405 
00406 void
00407 edit_main_rep::edit_special () {
00408 }
00409 
00410 #ifdef UNCOMMENTED
00411 void test_commute ();
00412 void test_invert ();
00413 #endif
00414 
00415 void
00416 edit_main_rep::edit_test () {
00417   cout << "Test !\n";
00418 #ifdef UNCOMMENTED
00419   test_commute();
00420   test_invert();
00421 #endif
00422 }