~ubuntu-branches/debian/jessie/arb/jessie

« back to all changes in this revision

Viewing changes to SECEDIT/SEC_paint.cxx

  • Committer: Package Import Robot
  • Author(s): Elmar Pruesse, Andreas Tille, Elmar Pruesse
  • Date: 2014-09-02 15:15:06 UTC
  • mfrom: (1.1.6)
  • Revision ID: package-import@ubuntu.com-20140902151506-jihq58b3iz342wif
Tags: 6.0.2-1
[ Andreas Tille ]
* New upstream version
  Closes: #741890
* debian/upstream -> debian/upstream/metadata
* debian/control:
   - Build-Depends: added libglib2.0-dev
   - Depends: added mafft, mrbayes
* debian/rules
   - Add explicite --remove-section=.comment option to manual strip call
* cme fix dpkg-control
* arb-common.dirs: Do not create unneeded lintian dir
* Add turkish debconf translation (thanks for the patch to Mert Dirik
  <mertdirik@gmail.com>)
  Closes: #757497

[ Elmar Pruesse ]
* patches removed:
   - 10_config.makefiles.patch,
     80_no_GL.patch
       removed in favor of creating file from config.makefile.template via 
       sed in debian/control
   - 20_Makefile_main.patch
       merged upstream
   - 21_Makefiles.patch
       no longer needed
   - 30_tmpfile_CVE-2008-5378.patch: 
       merged upstream
   - 50_fix_gcc-4.8.patch:
       merged upstream
   - 40_add_libGLU.patch:
       libGLU not needed for arb_ntree)
   - 60_use_debian_packaged_raxml.patch:
       merged upstream
   - 70_hardening.patch
       merged upstream
   - 72_add_math_lib_to_linker.patch
       does not appear to be needed
* patches added:
   - 10_upstream_r12793__show_db_load_progress:
       backported patch showing progress while ARB is loading a database
       (needed as indicator/splash screen while ARB is launching)
   - 20_upstream_r12794__socket_permissions:
       backported security fix
   - 30_upstream_r12814__desktop_keywords:
       backported add keywords to desktop (fixes lintian warning)
   - 40_upstream_r12815__lintian_spelling:
       backported fix for lintian reported spelling errors
   - 50_private_nameservers
       change configuration to put nameservers into users home dirs
       (avoids need for shared writeable directory)
   - 60_use_debian_phyml
       use phyml from debian package for both interfaces in ARB
* debian/rules:
   - create config.makefile from override_dh_configure target
   - use "make tarfile" in override_dh_install
   - remove extra cleaning not needed for ARB 6
   - use "dh_install --list-missing" to avoid missing files
   - added override_dh_fixperms target
* debian/control:
   - added libarb-dev package
   - Depends: added phyml, xdg-utils
   - Suggests: removed phyml
   - fix lintian duplicate-short-description (new descriptions)
* debian/*.install:
   - "unrolled" confusing globbing to select files
   - pick files from debian/tmp
   - moved all config files to /etc/arb
* debian/arb-common.templates: updated
* scripts:
   - removed arb-add-pt-server
   - launch-wrapper: 
     - only add demo.arb to newly created $ARBUSERDATA
     - pass commandline arguments through bin/arb wrapper
   - preinst: removing old PT server index files on upgrade from 5.5*
   - postinst: set setgid on shared PT dir
* rewrote arb.1 manfile
* added file icon for ARB databases
* using upstream arb_tcp.dat

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
#include <cstdio>
2
 
#include <cstdlib>
3
 
#include <cmath>
4
 
 
5
 
#include <iostream>
6
 
#include <sstream>
7
 
 
8
 
#include <arbdb.h>
9
 
#include <aw_root.hxx>
10
 
#include <aw_device.hxx>
11
 
#include <aw_window.hxx>
12
 
#include <awt_canvas.hxx>
13
 
#include <awt_iupac.hxx>
14
 
#include <BI_helix.hxx>
15
 
 
16
 
#include <ed4_extern.hxx>
 
1
// =============================================================== //
 
2
//                                                                 //
 
3
//   File      : SEC_paint.cxx                                     //
 
4
//   Purpose   :                                                   //
 
5
//                                                                 //
 
6
//   Institute of Microbiology (Technical University Munich)       //
 
7
//   http://www.arb-home.de/                                       //
 
8
//                                                                 //
 
9
// =============================================================== //
17
10
 
18
11
#include "SEC_root.hxx"
19
12
#include "SEC_graphic.hxx"
22
15
#include "SEC_bonddef.hxx"
23
16
#include "SEC_toggle.hxx"
24
17
 
 
18
#include <aw_msg.hxx>
 
19
#include <iupac.h>
 
20
 
 
21
#include <ed4_extern.hxx>
 
22
 
 
23
#include <arb_defs.h>
 
24
 
 
25
#include <iostream>
 
26
#include <sstream>
 
27
 
25
28
using namespace std;
26
29
 
27
 
// ------------------
 
30
// -------------------
28
31
//      Debugging
29
 
// ------------------
 
32
 
 
33
#if defined(ASSERTION_USED)
 
34
 
 
35
inline bool valid_cb_params(AW_CL cd1, AW_CL cd2) {
 
36
    return cd1 == 0 || cd2 != -1;
 
37
}
 
38
inline bool valid_cb_params(AW_device *device) {
 
39
    const AW_click_cd *cd = device->get_click_cd();
 
40
    return valid_cb_params(cd->get_cd1(), cd->get_cd2());
 
41
}
 
42
 
 
43
#endif
30
44
 
31
45
#if defined(DEBUG)
32
46
// #define PAINT_REGION_INDEX // // paint region-internal index next to base
33
47
 
34
 
static bool valid_cb_params(AW_CL cd1, AW_CL cd2) {
35
 
    return cd1 == 0 || cd2 != -1;
36
 
}
37
 
 
38
 
static void paintDebugInfo(AW_device *device, int color, const Position& pos, const char *txt, AW_CL cd1, AW_CL cd2) {
39
 
    sec_assert(valid_cb_params(cd1, cd2));
40
 
    device->circle(color, true, pos.xpos(), pos.ypos(), 0.06, 0.06, -1, cd1, cd2);
41
 
    device->text(SEC_GC_DEFAULT, txt, pos.xpos(), pos.ypos(), 0, 1, cd1, cd2, 0);
 
48
static void paintDebugInfo(AW_device *device, int color, const Position& pos, const char *txt) {
 
49
    sec_assert(valid_cb_params(device));
 
50
    device->circle(color, true, pos.xpos(), pos.ypos(), 0.06, 0.06);
 
51
    device->text(SEC_GC_DEFAULT, txt, pos.xpos(), pos.ypos(), 0, AW_SCREEN, 0);
42
52
}
43
53
static void paintStrandDebugInfo(AW_device *device, int color, SEC_helix_strand *strand) {
44
 
    paintDebugInfo(device, color, strand->rightAttachPoint(), "RAP", strand->self(), strand->rightAttachAbspos());
45
 
    paintDebugInfo(device, color, strand->leftAttachPoint(), "LAP", strand->self(), strand->leftAttachAbspos());
46
 
    paintDebugInfo(device, color, strand->get_fixpoint(), strand->isRootsideFixpoint() ? "RFP" : "FP", strand->self(), strand->startAttachAbspos());
 
54
    AW_click_cd cd(device, strand->self(), strand->rightAttachAbspos());        paintDebugInfo(device, color, strand->rightAttachPoint(), "RAP");
 
55
    cd.set_cd2(strand->leftAttachAbspos());                                     paintDebugInfo(device, color, strand->leftAttachPoint(), "LAP");
 
56
    cd.set_cd2(strand->startAttachAbspos());                                    paintDebugInfo(device, color, strand->get_fixpoint(), strand->isRootsideFixpoint() ? "RFP" : "FP");
47
57
}
48
58
 
49
59
#endif // DEBUG
50
60
 
51
 
// ------------------
 
61
// -------------------
52
62
//      PaintData
53
 
// ------------------
54
63
 
55
64
class PaintData {
56
65
    int gc_edit4_to_secedit[ED4_G_DRAG+1]; // GC translation table (EDIT4 -> SECEDIT)
80
89
                }
81
90
                else {
82
91
                    if (gc == SEC_GC_LOOP || gc2 == SEC_GC_LOOP) {
83
 
                        prop_gc = SEC_GC_LOOP; // use loop-properties in loop and at loop-helix-transition 
 
92
                        prop_gc = SEC_GC_LOOP; // use loop-properties in loop and at loop-helix-transition
84
93
                    }
85
94
                    else if (gc == SEC_GC_NHELIX || gc2 == SEC_GC_NHELIX) {
86
95
                        prop_gc = SEC_GC_NHELIX; // use nhelix-properties in nhelix and at helix-nhelix-transition
102
111
 
103
112
    int get_linePropertyGC(int gc1, int gc2) {
104
113
        // of the GCs of two positions, it returns the GC which is
105
 
        // defining the properties for the background painted inbetween the two positions
 
114
        // defining the properties for the background painted in-between the two positions
106
115
        sec_assert(gc1 >= SEC_GC_FIRST_DATA && gc1 <= SEC_GC_LAST_DATA);
107
116
        sec_assert(gc2 >= SEC_GC_FIRST_DATA && gc2 <= SEC_GC_LAST_DATA);
108
117
        return line_property_gc[gc1][gc2];
111
120
 
112
121
static PaintData paintData;
113
122
 
114
 
// --------------------
 
123
// ---------------------
115
124
//      Annotations
116
 
// --------------------
117
125
 
118
126
void SEC_root::paintAnnotation(AW_device *device, int gc,
119
127
                               const Position& pos, const Position& left, const Position& right,
120
128
                               double noteDistance, const char *text,
121
 
                               bool lineToPos, bool linesToLeftRight, bool boxText,
122
 
                               AW_CL cd1, AW_CL cd2)
 
129
                               bool lineToPos, bool linesToLeftRight, bool boxText)
123
130
{
124
131
    // draw annotation to explicit position 'pos' (annotation is drawn "above" the line left->right)
125
132
    // The distance between pos and note is determined by
126
133
    // * textsize (minimal half textsize/boxsize) and
127
 
    // * the given 'noteDistance'  
128
 
    // lineToPos        == true -> draw a line from text to 'pos' 
 
134
    // * the given 'noteDistance'
 
135
    // lineToPos        == true -> draw a line from text to 'pos'
129
136
    // linesToLeftRight == true -> draw lines from text to 'left' and 'right'
130
137
    // boxText          == true -> draw a box around text
131
138
 
132
 
    sec_assert(valid_cb_params(cd1, cd2));
 
139
    sec_assert(valid_cb_params(device));
133
140
 
134
141
    Vector strand(left, right);
135
 
    Angle  pos2note(strand);
 
142
    Angle pos2note(strand);
136
143
    pos2note.rotate270deg();
137
144
 
138
145
    int    fontgc        = gc <= SEC_GC_LAST_FONT ? gc : SEC_GC_DEFAULT;
146
153
    double note_distance  = max(half_height, half_width) * (boxText ? 1.3 : 1.0);
147
154
    note_distance         = max(note_distance, noteDistance);
148
155
 
149
 
    // Position note_center = pos + pos2note.normal()*(text_len*2*half_charSize);
150
156
    Position note_center = pos + pos2note.normal()*note_distance;
151
157
 
152
 
    if (device->filter & AW_PRINTER) {
 
158
    if (device->get_filter() & AW_PRINTER) {
153
159
        boxText = false; // don't print/xfig-export boxes
154
160
    }
155
161
 
158
164
 
159
165
        if (lineToPos) {
160
166
            Vector dist = pos2note.normal()*half_charSize;
161
 
            device->line(gc, boxText ? note_center : note_center-dist, pos+dist, -1, cd1, cd2);
 
167
            device->line(gc, boxText ? note_center : note_center-dist, pos+dist);
162
168
        }
163
169
        if (linesToLeftRight) {
164
170
            Vector out(pos, note_center);
168
174
                Vector toRight(note_center, right);
169
175
 
170
176
                device->line(gc, boxText ? note_center : note_center+toLeft*(half_width/toLeft.length()),
171
 
                             left-toLeft*(half_charSize/toLeft.length()), -1, cd1, cd2);
 
177
                             left-toLeft*(half_charSize/toLeft.length()), AW_ALL_DEVICES_SCALED);
172
178
                device->line(gc, boxText ? note_center : note_center+toRight*(half_width/toRight.length()),
173
 
                             right-toRight*(half_charSize/toRight.length()), -1, cd1, cd2);
174
 
 
175
 
                // Vector dist = Vector(left, note_center).normalize()*half_charSize;
176
 
                // device->line(gc, boxText ? note_center : note_center-dist, left+dist, -1, cd1, cd2);
177
 
                // dist = Vector(right, note_center).normalize()*half_charSize;
178
 
                // device->line(gc, boxText ? note_center : note_center-dist, right+dist, -1, cd1, cd2);
 
179
                             right-toRight*(half_charSize/toRight.length()), AW_ALL_DEVICES_SCALED);
179
180
            }
180
181
            else {
181
182
                Vector rightIndent = out;
185
186
                Position leftOut  = left+out-rightIndent;
186
187
 
187
188
                Vector posPad = Vector(right, rightOut).set_length(half_charSize);
188
 
                device->line(gc, right+posPad, rightOut, -1, cd1, cd2);
 
189
                device->line(gc, right+posPad, rightOut);
189
190
                posPad.rotate90deg();
190
 
                device->line(gc, left+posPad, leftOut, -1, cd1, cd2);
 
191
                device->line(gc, left+posPad, leftOut);
191
192
 
192
193
                if (boxText) {
193
 
                    device->line(gc, leftOut, rightOut, -1, cd1, cd2);
 
194
                    device->line(gc, leftOut, rightOut);
194
195
                }
195
196
                else {
196
197
                    Vector rightTextPad(note_center, rightOut);
197
198
                    rightTextPad.set_length(half_width);
198
 
                
199
 
                    device->line(gc, note_center+rightTextPad, rightOut, -1, cd1, cd2);
200
 
                    device->line(gc, note_center-rightTextPad, leftOut, -1, cd1, cd2);
 
199
 
 
200
                    device->line(gc, note_center+rightTextPad, rightOut);
 
201
                    device->line(gc, note_center-rightTextPad, leftOut);
201
202
                }
202
203
            }
203
204
        }
211
212
        Rectangle box(note_center+center_corner, -2*center_corner);
212
213
 
213
214
        device->clear_part(box, -1);
214
 
        device->box(gc, false, box, -1, cd1, cd2);
 
215
        device->box(gc, false, box);
215
216
    }
216
 
    
217
 
    device->text(gc, text, textcorner, 0, -1, cd1, cd2, 0);
 
217
 
 
218
    device->text(gc, text, textcorner);
218
219
}
219
220
 
220
221
void SEC_root::paintPosAnnotation(AW_device *device, int gc, size_t absPos, const char *text, bool lineToBase, bool boxText) {
236
237
        if (posDrawn) { // absPos was drawn
237
238
            pos = *posDrawn;
238
239
        }
239
 
        else { // absPos was not drawn -> use position inbetween
 
240
        else { // absPos was not drawn -> use position in-between
240
241
            pos = mid12;
241
242
        }
242
243
    }
243
244
 
244
245
    if (!text) text = GBS_global_string("%zu", absPos);
245
 
    
246
 
    paintAnnotation(device, gc, pos, pos1, pos2, vec12.length(), text, lineToBase, false, boxText, 0, absPos);
 
246
 
 
247
    AW_click_cd cd(device, 0, absPos);
 
248
    paintAnnotation(device, gc, pos, pos1, pos2, vec12.length(), text, lineToBase, false, boxText);
247
249
}
248
250
 
249
251
void SEC_root::paintEcoliPositions(AW_device *device) {
251
253
    paintPosAnnotation(device, SEC_GC_ECOLI, size_t(abspos), "1", true, true);
252
254
 
253
255
    const BI_ecoli_ref *ecoli = db->ecoli();
254
 
    for (size_t ep = 99; ep < ecoli->base_count(); ep += 100) {
 
256
    for (size_t ep = bio2info(100); ep < (size_t)ecoli->base_count(); ep += 100) {
255
257
        abspos = ecoli->rel_2_abs(ep);
256
 
        paintPosAnnotation(device, SEC_GC_ECOLI, size_t(abspos), GBS_global_string("%zu", ep+1), true, true);
 
258
        paintPosAnnotation(device, SEC_GC_ECOLI, size_t(abspos), GBS_global_string("%i", info2bio(ep)), true, true);
257
259
    }
258
260
}
259
261
 
278
280
                    const Position& end   = strand->endAttachPoint();
279
281
                    Position helixCenter           = centroid(start, end);
280
282
 
 
283
                    AW_click_cd cd(device, strand->self(), absPos);
281
284
                    paintAnnotation(device, SEC_GC_HELIX_NO,
282
285
                                    helixCenter, start, end,
283
 
                                    // displayParams.distance_between_strands*2, 
284
 
                                    displayParams.distance_between_strands, 
285
 
                                    helixNr, false, true, true, strand->self(), absPos);
 
286
                                    // displayParams.distance_between_strands*2,
 
287
                                    displayParams.distance_between_strands,
 
288
                                    helixNr, false, true, true);
286
289
                }
287
290
            }
288
291
        }
292
295
 
293
296
#if defined(PAINT_ABSOLUTE_POSITION)
294
297
void SEC_root::showSomeAbsolutePositions(AW_device *device) {
295
 
    if (device->filter != AW_SIZE) { // ignore for size calculation
296
 
        Rectangle screen(device->rtransform(device->get_area_size()));
297
 
        Vector        diag3 = screen.diagonal()/3;
 
298
    if (device->get_filter() != AW_SIZE) { // ignore for size calculation (@@@)
 
299
        Rectangle screen = device->rtransform(Rectangle(device->get_area_size(), INCLUSIVE_OUTLINE));
 
300
        Vector    diag3  = screen.diagonal()/3;
298
301
        Rectangle showInside(screen.upper_left_corner()+diag3*1.85, diag3);
299
302
 
300
 
        device->box(SEC_GC_DEFAULT, false, showInside, -1, 0, -1);
 
303
        AW_click_cd cd(device, 0, -1);
 
304
        device->box(SEC_GC_DEFAULT, false, showInside);
301
305
 
302
306
        PosMap::const_iterator end = drawnPositions->end();
303
307
        for (PosMap::const_iterator pos = drawnPositions->begin(); pos != end; ++pos) {
323
327
}
324
328
 
325
329
 
326
 
// ---------------------------
 
330
// ----------------------------
327
331
//      Paints CONSTRAINTS
328
 
// ---------------------------
329
332
 
330
333
void SEC_helix_strand::paint_constraints(AW_device *device) {
331
334
    double minS = helix_info->minSize();
338
341
        bool drawMidLine = minS>0 && maxS>0;
339
342
        Position minP = startP + Vector(startP, endP) * (drawMidLine ? minS/maxS : 0.5);
340
343
 
 
344
        AW_click_cd cd(device, self(), startAttachAbspos());
341
345
        get_root()->paintAnnotation(device, SEC_GC_DEFAULT,
342
346
                                    minP, startP, endP,
343
347
                                    get_root()->display_params().distance_between_strands*2,
344
348
                                    GBS_global_string("%.1f-%.1f", minS, maxS),
345
 
                                    drawMidLine, true, true,
346
 
                                    self(), startAttachAbspos());
 
349
                                    drawMidLine, true, true);
347
350
    }
348
351
}
349
352
 
354
357
    double maxS = maxSize();
355
358
 
356
359
    if (minS>0 || maxS>0) {
357
 
        if (minS>0) device->circle(SEC_GC_DEFAULT, false, center, minS, minS, -1, self(), abspos);
358
 
        if (maxS>0) device->circle(SEC_GC_DEFAULT, false, center, maxS, maxS, -1, self(), abspos);
 
360
        AW_click_cd cd(device, self(), abspos);
 
361
        
 
362
        if (minS>0) device->circle(SEC_GC_DEFAULT, false, center, Vector(minS, minS));
 
363
        if (maxS>0) device->circle(SEC_GC_DEFAULT, false, center, Vector(maxS, maxS));
359
364
 
360
 
        device->text(SEC_GC_DEFAULT, GBS_global_string("%.1f-%.1f", minS, maxS), center+Vector(0, max(minS, maxS)/2), 0.5, -1, self(), abspos);
 
365
        device->text(SEC_GC_DEFAULT, GBS_global_string("%.1f-%.1f", minS, maxS), center+Vector(0, max(minS, maxS)/2), 0.5, AW_ALL_DEVICES_UNSCALED);
361
366
    }
362
367
}
363
368
 
364
 
// --------------------------
 
369
// ---------------------------
365
370
//      Background colors
366
 
// --------------------------
367
371
 
 
372
#if defined(WARN_TODO)
368
373
#warning move to SEC_db_interface
 
374
#endif
369
375
void SEC_root::cacheBackgroundColor() {
370
 
    freeset(bg_color, 0);
371
 
 
372
 
    const ED4_sequence_terminal *sterm = db->get_seqTerminal();
373
 
    if (sterm) {
374
 
        int start = 0;
375
 
        int len   = db->length();
376
 
        int end   = len-1;
377
 
 
378
 
        bg_color = (char*)malloc(len);
379
 
 
380
 
        const char *bg_sai    = displayParams.display_sai ? ED4_getSaiColorString(db->awroot(), start, end) : 0;
381
 
        const char *bg_search = displayParams.display_search ? ED4_buildColorString(sterm, start, end) : 0;
382
 
 
383
 
        if (bg_sai) {
384
 
            if (bg_search) {
385
 
                for (int i = start; i <= end; ++i) {
386
 
                    bg_color[i] = bg_search[i] ? bg_search[i] : bg_sai[i];
387
 
                }
 
376
    freenull(bg_color);
 
377
 
 
378
    int start = 0;
 
379
    int len   = db->length();
 
380
    int end   = len-1;
 
381
 
 
382
    bg_color = (char*)malloc(len);
 
383
 
 
384
    const char *bg_sai    = displayParams.display_sai    ? host().get_SAI_background(start, end)    : 0;
 
385
    const char *bg_search = displayParams.display_search ? host().get_search_background(start, end) : 0;
 
386
 
 
387
    if (bg_sai) {
 
388
        if (bg_search) {
 
389
            for (int i = start; i <= end; ++i) {
 
390
                bg_color[i] = bg_search[i] ? bg_search[i] : bg_sai[i];
388
391
            }
389
 
            else memcpy(bg_color, bg_sai, len);
390
 
        }
391
 
        else {
392
 
            if (bg_search) memcpy(bg_color, bg_search, len);
393
 
            else memset(bg_color, 0, len);
394
 
        }
 
392
        }
 
393
        else memcpy(bg_color, bg_sai, len);
 
394
    }
 
395
    else {
 
396
        if (bg_search) memcpy(bg_color, bg_search, len);
 
397
        else memset(bg_color, 0, len);
395
398
    }
396
399
}
397
400
 
398
 
void SEC_root::paintBackgroundColor(AW_device *device, SEC_bgpaint_mode mode, const Position& p1, int color1, int gc1, const Position& p2, int color2, int gc2, int skel_gc, AW_CL cd1, AW_CL cd2) {
 
401
void SEC_root::paintBackgroundColor(AW_device *device, SEC_bgpaint_mode mode, const Position& p1, int color1, int gc1, const Position& p2, int color2, int gc2, int skel_gc) {
399
402
    // paints background colors for p2 and connection between p1 and p2.
400
403
    // gc1/gc2 are foreground gc used to detect size of background regions
401
 
    // 
 
404
    //
402
405
    // Also paints skeleton
403
406
 
404
 
    sec_assert(valid_cb_params(cd1, cd2));
405
 
    
 
407
    sec_assert(valid_cb_params(device));
 
408
 
406
409
    color1 = paintData.convert_BackgroundGC(color1); // convert EDIT4-GCs into SECEDIT-GCs
407
410
    color2 = paintData.convert_BackgroundGC(color2);
408
411
 
409
412
    if (color1 >= 0 || color2 >= 0 || displayParams.show_strSkeleton) {
410
 
        const double& radius1 = char_radius[gc1];
411
 
        const double& radius2 = char_radius[gc2];
 
413
        const double& radius1 = get_char_radius(gc1);
 
414
        const double& radius2 = get_char_radius(gc2);
412
415
 
413
416
        Position s1    = p1;
414
417
        Position s2    = p2;
420
423
        else {
421
424
            Vector v12(p1, p2);
422
425
            double vlen = v12.length();
423
 
            
 
426
 
424
427
            if ((radius1+radius2) < vlen) { // test if there is enough space between characters
425
428
                s1 = p1 + v12*(radius1/vlen); // skeleton<->base attach-points
426
429
                s2 = p2 - v12*(radius2/vlen);
429
432
        }
430
433
 
431
434
        if (mode & BG_PAINT_FIRST && color1 >= 0) { // paint first circle ?
432
 
            device->circle(color1, true, p1, radius1, radius1, -1, cd1, cd2);
 
435
            device->circle(color1, true, p1, Vector(radius1, radius1));
433
436
        }
434
437
 
435
438
        if (mode & BG_PAINT_SECOND && color2 >= 0) { // paint second circle ?
436
 
            device->circle(color2, true, p2, radius1, radius1, -1, cd1, cd2);
 
439
            device->circle(color2, true, p2, Vector(radius1, radius1));
437
440
        }
438
441
 
439
442
        if (color1 == color2 && color1 >= 0) { // colors are equal -> paint background between points
440
443
            device->set_line_attributes(color1, bg_linewidth[paintData.get_linePropertyGC(gc1, gc2)], AW_SOLID);
441
 
            device->line(color1, p1, p2, -1, cd1, cd2);
 
444
            device->line(color1, p1, p2);
442
445
        }
443
 
        
 
446
 
444
447
        if (space) {
445
448
            if (displayParams.show_strSkeleton) { // paint skeleton
446
449
                device->set_line_attributes(skel_gc, displayParams.skeleton_thickness, AW_SOLID);
447
450
#if defined(DEBUG)
448
451
                if (displayParams.show_debug) { s1 = p1; s2 = p2; } // in debug mode always show full skeleton
449
452
#endif // DEBUG
450
 
                device->line(skel_gc, s1, s2, -1, cd1, cd2);
 
453
                device->line(skel_gc, s1, s2);
451
454
            }
452
455
        }
453
456
    }
455
458
 
456
459
void SEC_root::paintSearchPatternStrings(AW_device *device, int clickedPos, AW_pos xPos,  AW_pos yPos) {
457
460
    int searchColor = getBackgroundColor(clickedPos);
458
 
    
 
461
 
459
462
    if (searchColor >= SEC_GC_SBACK_0 && searchColor <= SEC_GC_SBACK_8) {
460
463
        static const char *text[SEC_GC_SBACK_8-SEC_GC_SBACK_0+1] = {
461
464
            "User 1",
462
 
            "User 2", 
463
 
            "Probe", 
464
 
            "Primer (local)", 
465
 
            "Primer (region)", 
466
 
            "Primer (global)", 
467
 
            "Signature (local)", 
468
 
            "Signature (region)", 
 
465
            "User 2",
 
466
            "Probe",
 
467
            "Primer (local)",
 
468
            "Primer (region)",
 
469
            "Primer (global)",
 
470
            "Signature (local)",
 
471
            "Signature (region)",
469
472
            "Signature (global)",
470
473
        };
471
474
 
472
 
        device->text(searchColor, text[searchColor-SEC_GC_SBACK_0], xPos, yPos, 0, 1, 0, clickedPos, 0);
 
475
        AW_click_cd cd(device, 0, clickedPos);
 
476
        device->text(searchColor, text[searchColor-SEC_GC_SBACK_0], xPos, yPos, 0, AW_SCREEN, 0);
473
477
    }
474
478
    else {
475
479
        aw_message("Please click on a search result");
476
480
    }
477
481
}
478
482
 
479
 
// --------------
 
483
// ---------------
480
484
//      Bonds
481
 
// --------------
482
 
 
483
 
 
484
 
void SEC_bond_def::paint(AW_device *device, char base1, char base2, const Position& p1, const Position& p2, const Vector& toNextBase, const double& char_radius, AW_CL cd1, AW_CL cd2) const {
 
485
 
 
486
void SEC_bond_def::paint(AW_device *device, char base1, char base2, const Position& p1, const Position& p2, const Vector& toNextBase, const double& char_radius) const {
485
487
    if (base1 && base2) {
486
488
        char Bond = get_bond(base1, base2);
487
489
        if (Bond == ' ') {
488
490
            // check IUPACs
489
 
            const char *iupac1 = AWT_decode_iupac(base1, ali_type, 0);
490
 
            const char *iupac2 = AWT_decode_iupac(base2, ali_type, 0);
 
491
            const char *iupac1 = iupac::decode(base1, ali_type, 0);
 
492
            const char *iupac2 = iupac::decode(base2, ali_type, 0);
491
493
 
492
494
            bool useBond[SEC_BOND_PAIR_CHARS];
493
495
            for (int i = 0; i<SEC_BOND_PAIR_CHARS; i++) useBond[i] = false;
510
512
            if (maxIdx >= 0) {
511
513
                for (int i = 0; i<SEC_BOND_PAIR_CHARS; i++) {
512
514
                    if (useBond[i]) {
513
 
                        paint(device, i == maxIdx ? SEC_GC_BONDS : SEC_GC_ERROR, SEC_BOND_PAIR_CHAR[i], p1, p2, toNextBase, char_radius, cd1, cd2);
 
515
                        paint(device, i == maxIdx ? SEC_GC_BONDS : SEC_GC_ERROR, SEC_BOND_PAIR_CHAR[i], p1, p2, toNextBase, char_radius);
514
516
                    }
515
517
                }
516
518
            }
517
519
        }
518
520
        else {
519
 
            paint(device, SEC_GC_BONDS, Bond, p1, p2, toNextBase, char_radius, cd1, cd2);
 
521
            paint(device, SEC_GC_BONDS, Bond, p1, p2, toNextBase, char_radius);
520
522
        }
521
523
    }
522
524
}
523
525
 
524
 
void SEC_bond_def::paint(AW_device *device, int GC, char bondChar, const Position& p1, const Position& p2, const Vector& toNextBase, const double& char_radius, AW_CL cd1, AW_CL cd2) const {
 
526
void SEC_bond_def::paint(AW_device *device, int GC, char bondChar, const Position& p1, const Position& p2, const Vector& toNextBase, const double& char_radius) const {
525
527
    Vector v12(p1, p2);
526
528
    double oppoDist = v12.length();
527
529
    double bondLen  = oppoDist-2*char_radius;
539
541
 
540
542
    switch (bondChar) {
541
543
        case '-':               // single line
542
 
            device->line(GC, b1, b2, -1, cd1, cd2);
 
544
            device->line(GC, b1, b2);
543
545
            break;
544
546
 
545
547
        case '#':               // double cross
546
548
        case '=':               // double line
547
 
            device->line(GC, b1+aside, b2+aside, -1, cd1, cd2);
548
 
            device->line(GC, b1-aside, b2-aside, -1, cd1, cd2);
549
 
            
 
549
            device->line(GC, b1+aside, b2+aside);
 
550
            device->line(GC, b1-aside, b2-aside);
 
551
 
550
552
            if (bondChar == '#') {
551
553
                Vector   outside = v12*(bondLen/oppoDist/4);
552
554
                Position c1      = center+outside;
553
555
                Position c2      = center-outside;
554
556
 
555
557
                aside *= 2;
556
 
            
557
 
                device->line(GC, c1-aside, c1+aside, -1, cd1, cd2);
558
 
                device->line(GC, c2-aside, c2+aside, -1, cd1, cd2);
 
558
 
 
559
                device->line(GC, c1-aside, c1+aside);
 
560
                device->line(GC, c2-aside, c2+aside);
559
561
            }
560
562
            break;
561
 
            
 
563
 
562
564
        case '~': {
563
565
            double radius = aside.length();
564
566
            {
574
576
            aside *= 2;
575
577
 
576
578
            Angle angle(outside);
577
 
            int   deg = int(angle.degrees()+0.5);
578
 
 
579
 
            device->arc(GC, false, c1, radius, radius, deg+180-1, 180+30, -1, cd1, cd2);
580
 
            device->arc(GC, false, c2, radius, radius, deg-1,     180+30, -1, cd1, cd2);
 
579
            int   deg = AW_INT(angle.degrees());
 
580
 
 
581
            const int INSIDE  = 2;
 
582
            const int OUTSIDE = 15;
 
583
 
 
584
            Vector vRadius(radius, radius);
 
585
            device->arc(GC, false, c1, vRadius, deg+180+INSIDE, -(180+INSIDE+OUTSIDE));
 
586
            device->arc(GC, false, c2, vRadius, deg+INSIDE,     -(180+INSIDE+OUTSIDE));
581
587
            break;
582
588
        }
583
589
 
584
590
        case '+':               // cross
585
591
            aside *= 2;
586
 
            device->line(GC, center-aside, center+aside, -1, cd1, cd2);
 
592
            device->line(GC, center-aside, center+aside);
587
593
            if (2*aside.length() < bondLen) {
588
594
                aside.rotate90deg();
589
 
                device->line(GC, center-aside, center+aside, -1, cd1, cd2);
 
595
                device->line(GC, center-aside, center+aside);
590
596
            }
591
597
            else {
592
 
                device->line(GC, b1, b2, -1, cd1, cd2);
 
598
                device->line(GC, b1, b2);
593
599
            }
594
600
            break;
595
601
 
597
603
        case '.': {             // circles
598
604
            double radius            = aside.length();
599
605
            if (bondChar == 'o') radius *= 2;
600
 
            device->circle(GC, false, center, radius, radius, -1, cd1, cd2);
 
606
            device->circle(GC, false, center, Vector(radius, radius));
601
607
            break;
602
608
        }
603
609
 
604
610
        case '@':  // error in bonddef
605
 
            device->text(GC, "Err", center+Vector(0, char_radius), 0.5, -1, cd1, cd2);
 
611
            device->text(GC, "Err", center+Vector(0, char_radius), 0.5, AW_ALL_DEVICES_UNSCALED);
606
612
            break;
607
613
 
608
614
        default:
611
617
    }
612
618
}
613
619
 
614
 
// ----------------------
 
620
// -----------------------
615
621
//      Paint helices
616
 
// ----------------------
617
622
 
618
623
struct StrandPositionData {
619
624
    int      abs[2];            // absolute sequence position
647
652
 
648
653
    double base_dist = base_count>1 ? strand_len / (base_count-1) : 1;
649
654
    Vector vnext     = strand_vec * base_dist; // vector from base to next base (in strand)
650
 
    
 
655
 
651
656
    // first calculate positions
652
657
    {
653
658
        StrandPositionData *curr = &data[0];
654
 
        
 
659
 
655
660
        int idx[2] = { 0, base_count-1 };
656
661
        Position pos[2] = { leftAttach, rightAttach };
657
662
        Vector toNonBind[2]; // vectors from normal to non-binding positions
663
668
            curr->previous[strand] = 0;
664
669
            curr->drawn[strand]    = (curr->abs[strand] >= 0);
665
670
        }
666
 
        
 
671
 
667
672
        for (int dIdx = 1; ; ++dIdx) {
668
673
            sec_assert(pos[0].valid());
669
674
            sec_assert(pos[1].valid());
670
 
            
 
675
 
671
676
            int oneAbs  = curr->drawn[0] ? curr->abs[0] : curr->abs[1];
672
677
            sec_assert(oneAbs >= 0); // otherwise current position should have been eliminated by align_helix_strands
673
678
            curr->isPair = (helix->pairtype(oneAbs) != HELIX_NONE);
714
719
            if (curr->drawn[strand]) {
715
720
                StrandPositionData *prev = &data[curr->previous[strand]];
716
721
 
717
 
                int backAbs = disp.edit_direction
 
722
                int backAbs = disp.edit_rightward
718
723
                    ? max(prev->abs[strand], curr->abs[strand])
719
724
                    : min(prev->abs[strand], curr->abs[strand]);
720
725
 
 
726
                AW_click_cd cd(device, self(), backAbs);
721
727
                root->paintBackgroundColor(device,
722
728
                                           pos == base_count-1 ? BG_PAINT_NONE : BG_PAINT_SECOND,
723
729
                                           prev->realpos[strand], root->getBackgroundColor(prev->abs[strand]), pair2helixGC[prev->isPair],
724
730
                                           curr->realpos[strand], root->getBackgroundColor(curr->abs[strand]), pair2helixGC[curr->isPair],
725
 
                                           pair2skelGC[curr->isPair && prev->isPair],
726
 
                                           self(), backAbs);
 
731
                                           pair2skelGC[curr->isPair && prev->isPair]);
727
732
            }
728
733
        }
729
734
    }
733
738
    for (int pos = 0; pos<base_count; ++pos) {
734
739
        StrandPositionData *curr = &data[pos];
735
740
        char base[2] = { 0, 0 };
736
 
        
 
741
 
737
742
        int    gc          = pair2helixGC[curr->isPair];
738
743
        Vector center_char = root->get_center_char_vector(gc);
739
744
 
744
749
 
745
750
                sec_assert(abs >= 0);
746
751
 
747
 
                // if (abs >= 0) {
748
 
                    base[strand] = db->baseAt(abs);
749
 
                    root->announce_base_position(abs, realPos);
750
 
                // }
751
 
                // else {
752
 
                    // base[strand] = '-';
753
 
                // }
 
752
                base[strand] = db->baseAt(abs);
 
753
                root->announce_base_position(abs, realPos);
754
754
 
755
755
                if (!disp.hide_bases) {
756
756
                    baseBuf[0]        = base[strand];
757
757
                    Position base_pos = realPos + center_char; // center base at realpos
 
758
                    AW_click_cd cd(device, self(), abs);
758
759
#if defined(DEBUG)
759
 
                    if (disp.show_debug) device->line(gc, realPos, base_pos, -1, self(), abs);
760
 
                    // sprintf(baseBuf+1, "%i", abs);
 
760
                    if (disp.show_debug) device->line(gc, realPos, base_pos);
761
761
#endif // DEBUG
762
 
                    
763
 
                    device->text(gc, baseBuf, base_pos, 0, -1, self(), abs, 0);
 
762
 
 
763
                    device->text(gc, baseBuf, base_pos, 0.0, AW_ALL_DEVICES_SCALED);
764
764
                }
765
765
            }
766
766
        }
767
767
 
768
768
        if (disp.show_bonds == SHOW_NHELIX_BONDS || (disp.show_bonds == SHOW_HELIX_BONDS && curr->isPair)) {
 
769
            AW_click_cd cd(device, self(), curr->abs[0]);
769
770
            db->bonds()->paint(device, base[0], base[1], curr->realpos[0], curr->realpos[1], vnext,
770
 
                               root->get_char_radius(pair2helixGC[curr->isPair]),
771
 
                               self(), curr->abs[0]);
 
771
                               root->get_char_radius(pair2helixGC[curr->isPair]));
772
772
        }
773
773
    }
774
774
}
775
775
 
776
776
void SEC_helix_strand::paint(AW_device *device) {
777
777
    sec_assert(isRootsideFixpoint());
778
 
    
 
778
 
779
779
    Vector strand_vec(rightAttach, other_strand->leftAttach);
780
780
    double strand_len     = strand_vec.length(); // length of strand
781
781
 
784
784
    }
785
785
    else { // strand with zero length (contains only one base-pair)
786
786
        strand_vec = Vector(rightAttach, leftAttach).rotate90deg();
787
 
// #if defined(DEBUG)
788
 
        // device->set_line_attributes(SEC_GC_HELIX, 1, AW_DOTTED);
789
 
        // device->line(SEC_GC_HELIX, LineVector(fixpoint, strand_vec), -1, 0, 0);
790
 
// #endif // // DEBUG
791
787
    }
792
788
 
793
789
    other_strand->origin_loop->paint(device); // first paint next loop
808
804
            strandArrow = LineVector(get_fixpoint()-fix2arrowStart, 2*fix2arrowStart);
809
805
        }
810
806
 
811
 
        AW_CL cd1 = (AW_CL)get_helix()->self();
812
 
        AW_CL cd2 = (AW_CL)startAttachAbspos();
 
807
        AW_click_cd cd(device, get_helix()->self(), startAttachAbspos());
 
808
        // AW_CL cd1 = (AW_CL)get_helix()->self();
 
809
        // AW_CL cd2 = (AW_CL)startAttachAbspos();
813
810
 
814
 
        device->line(SEC_GC_HELIX, strandArrow, -1, cd1, cd2);
 
811
        device->line(SEC_GC_HELIX, strandArrow);
815
812
 
816
813
        Vector right = strandArrow.line_vector(); // left arrowhead vector
817
814
        right        = (right * (disp.distance_between_strands*0.35/right.length())).rotate135deg();
819
816
        Vector left = Vector(right).rotate90deg();
820
817
 
821
818
        Position head = strandArrow.head();
822
 
        device->line(SEC_GC_HELIX, LineVector(head, left), -1, cd1, cd2);
823
 
        device->line(SEC_GC_HELIX, LineVector(head, right), -1, cd1, cd2);
 
819
        device->line(SEC_GC_HELIX, LineVector(head, left));
 
820
        device->line(SEC_GC_HELIX, LineVector(head, right));
824
821
    }
825
822
 
826
823
#if defined(DEBUG)
831
828
}
832
829
 
833
830
 
834
 
// --------------------
 
831
// ---------------------
835
832
//      Paint loops
836
 
// --------------------
837
 
 
838
833
 
839
834
void SEC_segment::paint(AW_device *device, SEC_helix_strand *previous_strand_pointer) {
840
835
    int base_count = get_region()->get_base_count(); // bases in segment
841
 
    
 
836
 
842
837
    const Position& startP = previous_strand_pointer->rightAttachPoint();
843
838
    const Position& endP   = next_helix_strand->leftAttachPoint();
844
839
 
863
858
 
864
859
    // correct if we have to paint more than a full loop
865
860
    if ((alpha - (step*steps)) > M_PI) {
866
 
        step += (2*M_PI)/steps; 
 
861
        step += (2*M_PI)/steps;
867
862
    }
868
863
 
869
864
    double radStep = (radius2-radius1)/steps;
870
 
    
 
865
 
871
866
    Vector cstep(center1, center2);
872
867
    cstep /= steps;
873
868
 
881
876
        int startAbsPos = previous_strand_pointer->rightAttachAbspos();
882
877
        int endAbsPos   = next_helix_strand->leftAttachAbspos();
883
878
 
884
 
        paintDebugInfo(device, SEC_GC_LOOP, center1, GBS_global_string("SC1 (step=%5.3f)", step), self(), startAbsPos);
885
 
        paintDebugInfo(device, SEC_GC_LOOP, center2, "SC2", self(), endAbsPos);
886
 
        device->line(SEC_GC_LOOP, center1, startP, -1, self(), startAbsPos);
887
 
        device->line(SEC_GC_LOOP, center2, endP, -1, self(), endAbsPos);
888
 
        device->line(SEC_GC_LOOP, center1, center2, -1, self(), startAbsPos);
 
879
        AW_click_cd cd(device, self(), startAbsPos);
 
880
        paintDebugInfo(device, SEC_GC_LOOP, center1, GBS_global_string("SC1 (step=%5.3f)", step));
 
881
        device->line(SEC_GC_LOOP, center1, startP);
 
882
        device->line(SEC_GC_LOOP, center1, center2);
 
883
 
 
884
        cd.set_cd2(endAbsPos);
 
885
        paintDebugInfo(device, SEC_GC_LOOP, center2, "SC2");
 
886
        device->line(SEC_GC_LOOP, center2, endP);
889
887
    }
890
888
#endif // DEBUG
891
889
 
899
897
    Position currCenter = center1;
900
898
    double   currRadius = radius1;
901
899
 
 
900
    Angle step_angle(step);
 
901
    
902
902
    for (int i = -1; i<base_count; i++) { // for each segment position (plus one pre-loop)
903
 
        current    += step;     // iterate over angles
 
903
        current    += step_angle;     // iterate over angles
904
904
        currCenter += cstep;
905
905
        currRadius += radStep;
906
906
 
912
912
            if (nextAbs<0) { // helix doesn't start with pair
913
913
                nextAbs = next_helix_strand->getNextAbspos();
914
914
            }
915
 
            nextGc = root->getBondtype(nextAbs) == HELIX_NONE ? SEC_GC_NHELIX : SEC_GC_HELIX;;
 
915
            nextGc = root->getBondtype(nextAbs) == HELIX_NONE ? SEC_GC_NHELIX : SEC_GC_HELIX;
916
916
        }
917
917
        else {
918
918
            nextAbs = get_region()->getBasePos(i+1);
921
921
        int nextBack = root->getBackgroundColor(nextAbs);
922
922
 
923
923
        // paint background (from pos to nextPos)
 
924
        AW_click_cd cd(device, self(), disp.edit_rightward ? nextAbs : abs);
924
925
        root->paintBackgroundColor(device, i == -1 ? BG_PAINT_BOTH : BG_PAINT_SECOND,
925
 
                                   pos, back, gc, nextPos, nextBack, nextGc, SEC_SKELE_LOOP, self(),
926
 
                                   disp.edit_direction ? nextAbs : abs);
927
 
        
928
 
        // if (disp.show_strSkeleton) {
929
 
            // device->line(SEC_SKELE_LOOP, pos, nextPos, -1, self(), abs);
930
 
        // }
 
926
                                   pos, back, gc, nextPos, nextBack, nextGc, SEC_SKELE_LOOP);
931
927
 
932
928
        if (i >= 0) {
933
929
            // paint base char at pos
934
 
            // baseBuf[0] = abs>0 ? root->sequence[abs] : '?';
935
 
            baseBuf[0] = abs>0 ? db->baseAt(abs) : '?';
 
930
            baseBuf[0]           = abs>0 ? db->baseAt(abs) : '?';
936
931
            Vector   center_char = root->get_center_char_vector(gc);
937
932
            Position base_pos    = pos + center_char; // center base character at pos
938
 
                
939
 
// #if defined(DEBUG)
940
 
//             if (disp.show_debug) {
941
 
// #if defined(PAINT_REGION_INDEX)
942
 
//                 sprintf(baseBuf+1, "%i", i);
943
 
// #endif // // PAINT_REGION_INDEX
944
 
//             }
945
 
// #endif // // DEBUG
946
 
                
 
933
 
 
934
            cd.set_cd2(abs);
947
935
            if (!disp.hide_bases) {
948
936
#if defined(DEBUG)
949
937
                // show line from base paint pos to calculated center of char
950
938
                // (which is currently calculated wrong!)
951
 
                if (disp.show_debug) device->line(SEC_GC_LOOP, pos, base_pos, -1, self(), abs);
 
939
                if (disp.show_debug) device->line(SEC_GC_LOOP, pos, base_pos);
952
940
#endif // DEBUG
953
 
                device->text(SEC_GC_LOOP, baseBuf, base_pos, 0, -1, self(), abs, 0 );
 
941
                device->text(SEC_GC_LOOP, baseBuf, base_pos, 0.0, AW_ALL_DEVICES_SCALED);
954
942
            }
955
943
            root->announce_base_position(abs, pos);
956
944
        }
965
953
 
966
954
void SEC_loop::paint(AW_device *device) {
967
955
    for (SEC_segment_iterator seg(this); seg; ++seg) { // first paint all segments
968
 
        seg->paint(device, seg->get_previous_strand()); 
 
956
        seg->paint(device, seg->get_previous_strand());
969
957
    }
970
958
    for (SEC_strand_iterator strand(this); strand; ++strand) { // then paint all outgoing strands
971
959
        if (strand->isRootsideFixpoint()) strand->paint(device);
976
964
    if (sroot->display_params().show_debug) {
977
965
        SEC_helix_strand *fixpoint_strand = get_fixpoint_strand();
978
966
        int               abspos          = fixpoint_strand->startAttachAbspos();
 
967
        AW_click_cd cd(device, self(), abspos);
979
968
 
980
969
        device->set_line_attributes(SEC_GC_CURSOR, 1, AW_SOLID);
981
 
        device->line(SEC_GC_CURSOR, get_center(), fixpoint_strand->get_fixpoint(), self(), abspos);
 
970
        device->line(SEC_GC_CURSOR, get_center(), fixpoint_strand->get_fixpoint());
982
971
 
983
972
        paintStrandDebugInfo(device, SEC_GC_CURSOR, fixpoint_strand);
984
 
        paintDebugInfo(device, SEC_GC_CURSOR, get_center(), "LC", self(), abspos);
 
973
        paintDebugInfo(device, SEC_GC_CURSOR, get_center(), "LC");
985
974
    }
986
975
#endif // DEBUG
987
976
    if (sroot->get_show_constraints() & SEC_LOOP) paint_constraints(device);
988
977
}
989
978
 
990
 
// ---------------------------------------------------------
 
979
// ------------------------------------------------------------
991
980
//      Paint the whole structure (starting with SEC_root)
992
 
// ---------------------------------------------------------
993
981
 
994
982
GB_ERROR SEC_root::paint(AW_device *device) {
995
983
    SEC_loop *rootLoop = get_root_loop();
1014
1002
        for (int gc = SEC_GC_FIRST_DATA; gc <= SEC_GC_LAST_DATA; ++gc) {
1015
1003
            int maxSize = max(font_group.get_width(gc), font_group.get_ascent(gc));
1016
1004
 
1017
 
            maxSize +=2; // add 2 extra pixels
 
1005
            maxSize += 2; // add 2 extra pixels
1018
1006
 
1019
1007
            bg_linewidth[gc] = maxSize;
1020
 
            char_radius[gc]    = device->rtransform_size(maxSize) * 0.5; // was 0.75
 
1008
            charRadius[gc]   = device->rtransform_size(maxSize) * 0.5;  // was 0.75
1021
1009
        }
1022
1010
 
1023
1011
        cacheBackgroundColor();
1027
1015
        device->set_line_attributes(SEC_SKELE_LOOP, displayParams.skeleton_thickness, AW_SOLID);
1028
1016
        device->set_line_attributes(SEC_GC_BONDS, displayParams.bond_thickness, AW_SOLID);
1029
1017
 
1030
 
        // mark the rootLoop with a box and print stucture number
 
1018
        // mark the rootLoop with a box and print structure number
1031
1019
        {
1032
1020
            const Position&  loop_center = rootLoop->get_center();
1033
1021
            const char      *structId    = db->structure()->name();
1034
1022
 
1035
 
            // Vector textAdjust = center_char[SEC_GC_DEFAULT];
1036
 
            // textAdjust.setx(0); // // only adjust y
1037
 
 
1038
 
            AW_CL cd1 = rootLoop->self();
1039
 
            AW_CL cd2 = -1;
 
1023
            AW_click_cd cd(device, rootLoop->self(), -1);
 
1024
            // AW_CL cd1 = rootLoop->self();
 
1025
            // AW_CL cd2 = -1;
1040
1026
 
1041
1027
            Vector center2corner(-1, -1);
1042
1028
            center2corner.set_length(rootLoop->drawnSize()*0.33);
1043
 
            
 
1029
 
1044
1030
            Position upperleft_corner = loop_center+center2corner;
1045
1031
            Vector   diagonal         = -2*center2corner;
1046
1032
 
1047
1033
            Position textPos(loop_center.xpos(), upperleft_corner.ypos());
1048
1034
 
1049
 
            device->box(SEC_GC_DEFAULT, false, upperleft_corner, diagonal, -1, cd1, cd2);
1050
 
            device->text(SEC_GC_DEFAULT, structId, textPos, 0.5, -1, cd1, cd2, 0);
 
1035
            device->box(SEC_GC_DEFAULT, false, upperleft_corner, diagonal, AW_ALL_DEVICES_UNSCALED);
 
1036
            device->text(SEC_GC_DEFAULT, structId, textPos, 0.5, AW_ALL_DEVICES_UNSCALED, 0);
1051
1037
        }
1052
1038
 
1053
1039
#if defined(CHECK_INTEGRITY)
1066
1052
#if defined(PAINT_ABSOLUTE_POSITION)
1067
1053
        if (displayParams.show_debug) showSomeAbsolutePositions(device);
1068
1054
#endif // PAINT_ABSOLUTE_POSITION
1069
 
        
 
1055
 
1070
1056
        // paint cursor:
1071
1057
        if (!drawnPositions->empty() &&
1072
 
            (device->filter&(AW_PRINTER|AW_PRINTER_EXT)) == 0) // dont print/xfig-export cursor
 
1058
            (device->get_filter()&(AW_PRINTER|AW_PRINTER_EXT)) == 0) // don't print/xfig-export cursor
1073
1059
        {
1074
1060
            size_t   abs1, abs2;
1075
1061
            Position pos1, pos2;
1076
1062
            size_t curAbs;
1077
1063
 
1078
 
            if (displayParams.edit_direction == 1) {
 
1064
            if (displayParams.edit_rightward) {
1079
1065
                pos1   = drawnPositions->drawn_before(cursorAbsPos, &abs1);
1080
1066
                pos2   = drawnPositions->drawn_after(cursorAbsPos-1, &abs2);
1081
1067
                curAbs = abs2;
1086
1072
                curAbs = abs1;
1087
1073
            }
1088
1074
 
 
1075
            AW_click_cd cd(device, 0, curAbs);
1089
1076
#if defined(DEBUG) && 1
1090
1077
            // draw a testline to see the baseline on that the cursor is positioned
1091
 
            device->set_line_attributes(SEC_GC_CURSOR, 1, AW_DOTTED);
1092
 
            device->line(SEC_GC_CURSOR, pos1, pos2, -1, 0, curAbs);
 
1078
            device->set_line_attributes(SEC_GC_CURSOR, 1, AW_DASHED);
 
1079
            device->line(SEC_GC_CURSOR, pos1, pos2);
1093
1080
#endif
1094
1081
 
1095
1082
            Position mid = centroid(pos1, pos2);
1102
1089
 
1103
1090
                double cursor_size = 1.3 * max(font_group.get_max_width(), font_group.get_max_ascent()); // 30% bigger than max font size
1104
1091
                double stretch     = cursor_size*0.5/drawn_length; // stretch cursor (half fontsize in each direction)
1105
 
                    
 
1092
 
1106
1093
                v.rotate90deg() *= stretch;
1107
1094
            }
1108
1095
 
1109
1096
            LineVector cursor(mid+v, mid-v);
1110
1097
            device->set_line_attributes(SEC_GC_CURSOR, 3, AW_SOLID);
1111
 
            device->line(SEC_GC_CURSOR, cursor, -1, 0, curAbs);
 
1098
            device->line(SEC_GC_CURSOR, cursor);
1112
1099
            set_last_drawed_cursor_position(cursor);
1113
1100
 
1114
 
            LineVector cursor_dir(cursor.head(), displayParams.edit_direction ? v.rotate270deg() : v.rotate90deg());
1115
 
            device->line(SEC_GC_CURSOR, cursor_dir, -1, 0, curAbs);
 
1101
            LineVector cursor_dir(cursor.head(), displayParams.edit_rightward ? v.rotate270deg() : v.rotate90deg());
 
1102
            device->line(SEC_GC_CURSOR, cursor_dir);
1116
1103
 
1117
1104
 
1118
1105
            int cursor_gc  = -1;
1119
 
            int cursor_pos = -1;
1120
 
            
 
1106
            int disp_pos = -1;
 
1107
 
1121
1108
            switch (displayParams.show_curpos) {
1122
1109
                case SHOW_ABS_CURPOS:
1123
 
                    cursor_gc  = SEC_GC_CURSOR;
1124
 
                    cursor_pos = curAbs+1; // show absolute position starting with 1
 
1110
                    cursor_gc = SEC_GC_CURSOR;
 
1111
                    disp_pos  = info2bio(curAbs);
1125
1112
                    break;
1126
1113
                case SHOW_BASE_CURPOS:
1127
 
                    cursor_gc  = SEC_GC_DEFAULT;
1128
 
                    cursor_pos = ED4_get_base_position(db->get_seqTerminal(), curAbs)+1; // show base position starting with 1
 
1114
                    cursor_gc = SEC_GC_DEFAULT;
 
1115
                    disp_pos  = host().get_base_position(curAbs+1); // show bases up to cursorpos (inclusive)
1129
1116
                    break;
1130
1117
                case SHOW_ECOLI_CURPOS: {
1131
 
                    cursor_gc  = SEC_GC_ECOLI;
1132
 
                    cursor_pos = db->ecoli()->abs_2_rel(curAbs)+1; // show ecoli base position starting with 1
 
1118
                    cursor_gc = SEC_GC_ECOLI;
 
1119
                    disp_pos  = db->ecoli()->abs_2_rel(curAbs+1); // show ecoli base position (inclusive cursorpos)
1133
1120
                    break;
1134
1121
                }
1135
1122
                case SHOW_NO_CURPOS:
1136
 
                    cursor_gc        = -1;
 
1123
                    cursor_gc = -1;
1137
1124
                    break;
1138
1125
            }
1139
1126
 
1140
1127
            if (cursor_gc >= 0) {
1141
 
                paintPosAnnotation(device, cursor_gc, curAbs, GBS_global_string("%u", cursor_pos), true, true);
 
1128
                paintPosAnnotation(device, cursor_gc, curAbs, GBS_global_string("%u", disp_pos), true, true);
1142
1129
            }
1143
1130
        }
1144
1131
    }
1149
1136
    if (abspos_array) {
1150
1137
        const BI_helix *helix = root->get_helixDef();
1151
1138
        if (helix && !helix->get_error()) {
1152
 
            SEC_region *reg[2] = { this, other_region }; 
 
1139
            SEC_region *reg[2] = { this, other_region };
1153
1140
            int incr[2] = { 1, -1 }; // this is iterated forward, other_region backward
1154
1141
            int *absarr[2];
1155
1142
            int *new_absarr[2] = { 0, 0 };
1195
1182
 
1196
1183
                        for (int r = 0; r<2; ++r) { // copy binding positions
1197
1184
                            if (write) new_absarr[r][newp[r]] = abs[r];
1198
 
                            newp[r]++; curr[r] += incr[r]; 
 
1185
                            newp[r]++; curr[r] += incr[r];
1199
1186
                        }
1200
1187
                    }
1201
1188
                    else {
1231
1218
 
1232
1219
                        delete [] reg[r]->abspos_array;
1233
1220
                        reg[r]->abspos_array      = new_absarr[r];
1234
 
#if defined(DEBUG)
 
1221
#if defined(ASSERTION_USED)
1235
1222
                        reg[r]->abspos_array_size = newp[r];
1236
 
#endif                          // DEBUG
 
1223
#endif // ASSERTION_USED
1237
1224
                        reg[r]->set_base_count(newp[r]);
1238
1225
                    }
1239
1226
                    else {