~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Frontier Kernel
Frontier/Common/source/claybrowserexpand.c

Version: ~ [ 10.0 ] ~

** Warning: Cannot open xref database.

1 2 /* $Id: claybrowserexpand.c,v 1.3 2005/01/11 22:48:04 andreradke Exp $ */ 3 4 /****************************************************************************** 5 6 UserLand Frontier(tm) -- High performance Web content management, 7 object database, system-level and Internet scripting environment, 8 including source code editing and debugging. 9 10 Copyright (C) 1992-2004 UserLand Software, Inc. 11 12 This program is free software; you can redistribute it and/or modify 13 it under the terms of the GNU General Public License as published by 14 the Free Software Foundation; either version 2 of the License, or 15 (at your option) any later version. 16 17 This program is distributed in the hope that it will be useful, 18 but WITHOUT ANY WARRANTY; without even the implied warranty of 19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 20 GNU General Public License for more details. 21 22 You should have received a copy of the GNU General Public License 23 along with this program; if not, write to the Free Software 24 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 25 26 ******************************************************************************/ 27 28 #include "frontier.h" 29 #include "standard.h" 30 31 #include "cursor.h" 32 #include "file.h" 33 #include "fileloop.h" 34 #include "kb.h" 35 #include "memory.h" 36 #include "strings.h" 37 #include "shellundo.h" 38 39 #include "op.h" 40 #include "opinternal.h" 41 #include "claybrowserstruc.h" 42 #include "claybrowserexpand.h" 43 #include "claycallbacks.h" 44 45 46 static boolean compoundexpand = false; 47 48 static short expandcount; /*for debugging*/ 49 50 51 static void browsercalcinsertionpoint (hdlheadrecord hparent, hdlheadrecord *hpre, tydirection *dir) { 52 53 /* 54 using whatever sorting options we have, determine the insertion point for the 55 new line. we return the info that opaddheadline needs, a handle to the "pre" 56 node and the direction relative to that node to create the new headline. 57 58 special case: if hparent == nil, we do it at the summit level. 59 60 possible view settings: name, date, kind, size, label. 61 62 9/22/93 dmb: added cases for remaining possible view settings, treating 63 them all as viewbyname. also viewbyname sort order is unicase. 64 */ 65 66 if (hparent == nil) { 67 68 *hpre = oprepeatedbump (down, longinfinity, (**outlinedata).hsummit, true); /*special case*/; 69 70 *dir = down; 71 } 72 else { 73 74 if (opnosubheads (hparent)) { 75 76 *hpre = hparent; 77 78 *dir = right; 79 } 80 else { 81 *hpre = opgetlastsubhead (hparent); 82 83 *dir = down; 84 } 85 } 86 } /*browsercalcinsertionpoint*/ 87 88 89 void browserfindinsertionpoint (hdlheadrecord hparent, bigstring bsnewhead, tybrowserinfo *newfileinfo, hdlheadrecord *hpre, tydirection *dir) { 90 91 /* 92 using whatever sorting options we have, determine the insertion point for the 93 new line. we return the info that opaddheadline needs, a handle to the "pre" 94 node and the direction relative to that node to create the new headline. 95 96 special case: if hparent == nil, we do it at the summit level. 97 98 possible view settings: name, date, kind, size, label. 99 100 9/22/93 dmb: added cases for remaining possible view settings, treating 101 them all as viewbyname. also viewbyname sort order is unicase. 102 */ 103 104 hdlheadrecord nomad; 105 tyfolderview folderview; 106 #if filebrowser 107 unsigned long time1, time2; 108 unsigned long size1, size2; 109 short label1, label2; 110 bigstring bsnew; 111 #endif 112 #if odbbrowser 113 hdlhashtable ht; 114 hdlhashnode hnode, hnext; 115 bigstring bsnext; 116 hdlheadrecord hmatch; 117 #endif 118 119 if (hparent == nil) { 120 121 folderview = viewbyname; 122 123 nomad = (**outlinedata).hsummit; /*special case*/ 124 125 *hpre = nomad; 126 127 *dir = up; 128 } 129 else { 130 131 #if filebrowser 132 tybrowserinfo browserinfo; 133 134 browsergetrefcon (hparent, &browserinfo); 135 136 folderview = browserinfo.folderview; 137 #endif 138 139 nomad = hparent; 140 141 *hpre = nomad; 142 143 *dir = right; 144 145 if (!opchaseright (&nomad)) /*has no expanded subs*/ 146 return; 147 } 148 149 #if odbbrowser 150 151 ht = (*newfileinfo).dirid; 152 153 if (hashtablelookupnode (ht, bsnewhead, &hnode)) { // should not fail 154 155 hnext = (**hnode).sortedlink; 156 157 if (hnext != nil) { // we're not last 158 159 gethashkey (hnext, bsnext); 160 161 if (opfindhead (nomad, bsnext, &hmatch)) { // shouldn't fail 162 163 *hpre = hmatch; 164 165 *dir = up; 166 167 return; 168 } 169 } 170 } 171 172 // default: insert at end of list 173 174 *hpre = oprepeatedbump (down, longinfinity, nomad, true); 175 176 *dir = down; 177 178 return; 179 180 #endif 181 182 183 #if filebrowser 184 185 folderview = -1; 186 187 switch (folderview) { /*initialize the things we compare against*/ 188 189 case viewbyname: 190 case viewbyicon: 191 case viewbysmallicon: 192 case viewbycomment: 193 case viewbyversion: 194 copystring (bsnewhead, bsnew); 195 196 alllower (bsnew); 197 198 break; 199 200 case viewbykind: 201 setstringlength (bsnew, 4); 202 203 moveleft (&(*newfileinfo).filecreator, &bsnew [1], 4); 204 205 break; 206 207 case viewbydate: 208 time1 = (unsigned long) (*newfileinfo).timemodified; 209 210 break; 211 212 case viewbysize: 213 size1 = (*newfileinfo).filesize; 214 215 break; 216 217 case viewbycolor: 218 label1 = (*newfileinfo).ixlabel; 219 220 break; 221 } /*switch*/ 222 223 while (true) { 224 225 switch (folderview) { 226 227 case viewbyname: 228 case viewbyicon: 229 case viewbysmallicon: 230 case viewbycomment: 231 case viewbyversion: { 232 bigstring bs; 233 234 opgetheadstring (nomad, bs); 235 236 alllower (bs); 237 238 if (comparestrings (bsnew, bs) == -1) /*bsnewhead is < bs*/ 239 return; 240 241 break; 242 } 243 244 case viewbykind: { 245 tybrowserinfo nomadinfo; 246 bigstring bs; 247 248 browsergetrefcon (nomad, &nomadinfo); 249 250 setstringlength (bs, 4); 251 252 moveleft (&nomadinfo.filecreator, &bs [1], 4); 253 254 if (comparestrings (bsnew, bs) == -1) /*bsnew is < bs*/ 255 return; 256 257 break; 258 } 259 260 case viewbydate: { 261 tybrowserinfo nomadinfo; 262 263 browsergetrefcon (nomad, &nomadinfo); 264 265 time2 = (unsigned long) nomadinfo.timemodified; 266 267 if (time1 >= time2) 268 return; 269 270 break; 271 } 272 273 case viewbysize: { 274 tybrowserinfo nomadinfo; 275 276 browsergetrefcon (nomad, &nomadinfo); 277 278 size2 = nomadinfo.filesize; 279 280 if (size1 >= size2) 281 return; 282 283 break; 284 } 285 286 case viewbycolor: { 287 tybrowserinfo nomadinfo; 288 289 browsergetrefcon (nomad, &nomadinfo); 290 291 label2 = nomadinfo.ixlabel; 292 293 if (label1 >= label2) 294 return; 295 296 break; 297 } 298 } /*switch*/ 299 300 *hpre = nomad; 301 302 *dir = down; 303 304 if (!opchasedown (&nomad)) /*it's the last guy in the list*/ 305 return; 306 } /*while*/ 307 #endif 308 } /*browserfindinsertionpoint*/ 309 310 311 boolean browserexpandvisit (bigstring bsitem, tybrowserinfo *info, long refcon) { 312 313 /* 314 dmb 9/23/93: call opstart/endinternalchange around opaddheadline. this turns 315 off the lineinsertedcallback and prevents an undo from being built -- which 316 would otherwise delete the file! these calls used to be in browserpreexpand, 317 but that was when this visit routine wasn't directly callable. 318 */ 319 320 register tyexpandinfo *expandinfo = (tyexpandinfo *) refcon; 321 hdlheadrecord hnew; 322 323 if (!testheapspace (512)) /*512 bytes should be plenty*/ 324 return (false); 325 326 /*debugging code { 327 328 bigstring bs; 329 330 NumToString (expandcount++, bs); 331 332 appsetmessage (app.appwindow, bs); 333 } 334 */ 335 336 if (keyboardescape ()) /*user pressed cmd-period*/ 337 return (false); 338 339 rollbeachball (); 340 341 /*insert the new line*/ { 342 343 hdlheadrecord hpre; 344 tydirection dir; 345 346 if ((*expandinfo).flsortnodes) 347 browserfindinsertionpoint ((*expandinfo).hparent, bsitem, info, &hpre, &dir); 348 else 349 browsercalcinsertionpoint ((*expandinfo).hparent, &hpre, &dir); 350 351 opstartinternalchange (); /*this operation is not undo-able, and mustn't trigger callbacks*/ 352 353 opaddheadline (hpre, dir, bsitem, &hnew); 354 355 opendinternalchange (); 356 } 357 358 browsercopyfileinfo (hnew, info); 359 360 if ((*expandinfo).flsettmpbits) 361 (**hnew).tmpbit = true; /*if expand is cancelled, we nuke all nodes with tmp bit set*/ 362 363 if ((*info).flfolder) { 364 365 (**hnew).flnodeisfolder = true; 366 367 if ((*expandinfo).ctlevels > 1) { 368 369 if (!browserexpand (hnew, (*expandinfo).ctlevels - 1)) 370 return (false); 371 } 372 } 373 374 (*expandinfo).hnewnode = hnew; /*some callers need this*/ 375 376 return (true); 377 } /*browserexpandvisit*/ 378 379 380 boolean browserexpand (hdlheadrecord hnode, long ctlevels) { 381 382 tyexpandinfo expandinfo; 383 tybrowserspec fs; 384 385 if (opsubheadsexpanded (hnode)) { /*special case for a node that's already expanded*/ 386 387 hdlheadrecord nomad = (**hnode).headlinkright; 388 389 if (ctlevels <= 1) /*we aren't going any deeper*/ 390 return (true); 391 392 while (true) { /*loop over all the subheads of the node*/ 393 394 if ((**nomad).flnodeisfolder) { 395 396 if (!browserexpand (nomad, ctlevels - 1)) 397 return (false); 398 } 399 400 if (!opchasedown (&nomad)) 401 return (true); 402 } /*while*/ 403 } /*dealing with already-expanded nodes*/ 404 405 claygetfilespec (hnode, &fs); 406 407 expandinfo.hparent = hnode; 408 409 expandinfo.ctlevels = ctlevels; 410 411 expandinfo.flsettmpbits = true; 412 413 #if odbbrowser 414 expandinfo.flsortnodes = false; 415 #else 416 expandinfo.flsortnodes = true; 417 #endif 418 419 expandcount = 0; /*for debugging*/ 420 421 return (clayfolderloop (&fs, false, &browserexpandvisit, (long) &expandinfo)); 422 } /*browserexpand*/ 423 424 425 static boolean expandcancelledvisit (hdlheadrecord hnode, ptrvoid refcon) { 426 427 if ((**hnode).tmpbit) { 428 429 opstartinternalchange (); 430 431 opdeletenode (hnode); 432 433 opendinternalchange (); 434 } 435 436 return (true); 437 } /*expandcancelledvisit*/ 438 439 440 boolean browserpreexpand (hdlheadrecord hnode, short ctlevels, boolean flmaycreatesubs) { 441 442 /* 443 called by opexpand.c before expanding nodes. we create new nodes under 444 the node by looping over its folder on disk. 445 446 DW 8/18/93: allow the user to press cmd-period to cancel the expand 447 operation. set the tmpbit of every newly created node. if the user 448 hits cmd-period, or if we run out of memory, we delete all nodes with 449 their tmp bit set. important: we don't clear the tmp bits here, we 450 depend on them all being clear before the operation starts. the reason: 451 some operations do several calls to us. we want them all to be 452 cancelled. 453 454 DW 8/30/93: do it right this time. add another piece of baling wire, the 455 compoundexpand flag. if it's not true, we clear the tmpbits. otherwise 456 we assume they've been cleared. 457 458 5.0a25 dmb: auto-create item in empty table to expand, if new flmaycreatesubs 459 parameter is true 460 */ 461 462 register hdloutlinerecord ho = outlinedata; 463 boolean fl; 464 465 if (((**hnode).headlinkright != hnode) && (ctlevels <= 1)) /*the nodes are already there*/ 466 return (true); 467 468 if (!(**hnode).flnodeisfolder) /*can't expand a file*/ 469 return (true); 470 471 initbeachball (right); 472 473 if (!compoundexpand) 474 opcleartmpbits (); 475 476 fl = browserexpand (hnode, ctlevels); 477 478 if (!fl) /*memory error, or user pressed cmd-period or escape*/ 479 opsiblingvisiter ((**ho).hsummit, true, &expandcancelledvisit, nil); 480 481 if (!compoundexpand) 482 opcleartmpbits (); 483 484 if ((**hnode).headlinkright == hnode) { // table was empty 485 486 if (flmaycreatesubs) { 487 488 hdlheadrecord hnew; 489 490 opstartinternalchange (); 491 492 opaddheadline (hnode, right, emptystring, &hnew); 493 494 opendinternalchange (); 495 496 if (hnode == nil) 497 return (false); 498 499 browserlineinserted (hnew); 500 } 501 } 502 503 #ifdef xxxfldebug 504 opsetctexpanded (ho); 505 506 opvalidate (ho); 507 #endif 508 509 return (fl); 510 } /*browserpreexpand*/ 511 512 513 boolean browserselectfile (ptrfilespec pfs, boolean flexpand, hdlheadrecord *hnode) { 514 515 bigstring filepath; 516 hdlheadrecord nomad; 517 boolean flsomethingexpanded = false; 518 boolean flreturn = false; 519 boolean fldisplaywasenabled; 520 521 *hnode = nil; 522 523 compoundexpand = true; opcleartmpbits (); 524 525 filespectopath (pfs, filepath); 526 527 fldisplaywasenabled = opdisabledisplay (); 528 529 nomad = (**outlinedata).hsummit; 530 531 // addtohistorydisabled = true; /*don't want intermediate expansions added to the history menu*/ 532 533 while (true) { 534 535 bigstring headstring; 536 537 if (stringlength (filepath) == 0) 538 break; 539 540 firstword (filepath, ':', headstring); 541 542 if (stringlength (headstring) == 0) 543 copystring (filepath, headstring); 544 545 deletestring (filepath, 1, (short) (stringlength (headstring) + 1)); 546 547 if (!opfindhead (nomad, headstring, &nomad)) 548 break; 549 550 if (stringlength (filepath) == 0) { 551 552 flreturn = true; 553 554 break; 555 } 556 557 if (flexpand) { 558 559 if (!opsubheadsexpanded (nomad)) { 560 561 if (!opexpand (nomad, 1, false)) { /*user pressed cmd-period, or we ran out of memory*/ 562 563 openabledisplay (); 564 565 return (false); 566 } 567 568 flsomethingexpanded = true; 569 } 570 } 571 572 if (!opnavigate (right, &nomad)) 573 break; 574 } /*while*/ 575 576 // addtohistorydisabled = false; 577 578 if (fldisplaywasenabled) 579 openabledisplay (); 580 581 if (flsomethingexpanded) { 582 583 opresetscrollbars (); 584 585 opinvaldisplay (); 586 } 587 588 compoundexpand = false; 589 590 opcleartmpbits (); 591 592 *hnode = nomad; 593 594 return (flreturn); 595 } /*browserselectfile*/ 596 597 598 boolean browserexpandtofile (ptrfilespec pfs) { 599 600 hdlheadrecord hnode; 601 602 opclearallmarks (); 603 604 if (!browserselectfile (pfs, true, &hnode)) 605 return (false); 606 607 (**outlinedata).flcursorneedsdisplay = true; /*might need to vertical-scroll*/ 608 609 opjumpto (hnode); 610 611 opupdatenow (); 612 613 return (true); 614 } /*browserexpandtofile*/ 615 616 617 boolean browsercanexpand (hdlheadrecord hnode) { 618 619 tybrowserinfo info; 620 621 browsergetrefcon (hnode, &info); 622 623 return (info.flfolder && (info.filesize > 0)); 624 } /*browsercanexpand*/ 625 626 627 boolean browserpostcollapse (hdlheadrecord hnode) { 628 629 /* 630 5.0a25 dmb: auto-delete auto-created node 631 632 5.1.4 dmb: after deleting an auto-created node, we still need to delete subs 633 */ 634 635 hdloutlinerecord ho = outlinedata; 636 boolean fldisplaywasenabled; 637 638 killundo (); 639 640 /*toss auto-created nodes, if present*/ { 641 hdlheadrecord hsub = (**hnode).headlinkright; 642 643 browserdeletedummyvalues (hsub); 644 645 /* 646 tybrowserspec fs; 647 tyvaluerecord val; 648 649 if ((**hsub).tmpbit2 && opislastsubhead (hsub)) { 650 651 if (claygetfilespec (hsub, &fs) && claylookupvalue (&fs, &val)) 652 if (val.valuetype == novaluetype) { 653 654 hashtabledelete (fs.parID, fs.name); 655 656 //return (true); 657 } 658 } 659 */ 660 } 661 662 fldisplaywasenabled = opdisabledisplay (); /*keep the cursor line from flashing*/ 663 664 opstartinternalchange (); 665 666 /*make sure the outline is (temporarily) not read-only*/ { 667 668 boolean fltemp = (**ho).flreadonly; 669 670 (**ho).flreadonly = false; /*allow deletion to happen*/ 671 672 opdeletesubs (hnode); 673 674 (**ho).flreadonly = fltemp; 675 } 676 677 if (fldisplaywasenabled) 678 openabledisplay (); 679 680 opendinternalchange (); 681 682 return (true); 683 } /*browserpostcollapse*/ 684 685 686

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.