1 19 20 21 package org.netbeans.modules.i18n.java; 22 23 24 import java.lang.reflect.Modifier ; 25 import java.text.MessageFormat ; 26 import java.util.ArrayList ; 27 import java.util.HashMap ; 28 import java.util.Map ; 29 import java.util.regex.Pattern ; 30 import java.util.regex.PatternSyntaxException ; 31 import javax.swing.JPanel ; 32 import javax.swing.text.BadLocationException ; 33 import javax.swing.text.Element ; 34 import javax.swing.text.Position ; 35 import javax.swing.text.StyledDocument ; 36 import org.netbeans.api.java.classpath.ClassPath; 37 38 import org.netbeans.modules.i18n.HardCodedString; 39 import org.netbeans.modules.i18n.InfoPanel; 40 import org.netbeans.modules.i18n.I18nString; 41 import org.netbeans.modules.i18n.I18nSupport; 42 import org.netbeans.modules.i18n.I18nUtil; 43 import org.netbeans.modules.i18n.PropertyPanel; 44 import org.netbeans.modules.i18n.ResourceHolder; 45 import org.netbeans.modules.i18n.regexp.ParseException; 46 import org.netbeans.modules.i18n.regexp.Translator; 47 import org.netbeans.modules.properties.UtilConvert; 49 import org.openide.loaders.DataObject; 50 import org.openide.NotifyDescriptor; 51 import org.openide.DialogDisplayer; 52 import org.openide.filesystems.FileObject; 53 import org.openide.text.NbDocument; 54 import org.openide.util.MapFormat; 55 import org.openide.util.Lookup; 56 import org.openide.ErrorManager; 57 58 59 65 public class JavaI18nSupport extends I18nSupport { 66 67 68 protected int modifiers = Modifier.PRIVATE | Modifier.STATIC | Modifier.FINAL; 69 70 71 protected String identifier; 72 73 74 protected boolean generateField; 75 76 77 protected String initFormat; 78 79 80 82 public JavaI18nSupport(DataObject sourceDataObject) { 83 super(sourceDataObject); 84 85 initFormat = I18nUtil.getOptions().getInitJavaCode(); 86 } 87 88 89 90 protected I18nFinder createFinder() { 91 return new JavaI18nFinder(document); 92 } 93 94 95 protected I18nReplacer createReplacer() { 96 return new JavaI18nReplacer(); 97 } 98 99 100 protected ResourceHolder createResourceHolder() { 101 return new JavaResourceHolder(); 102 } 103 104 105 public I18nString getDefaultI18nString(HardCodedString hcString) { 106 I18nString i18nString = new JavaI18nString(this); 107 108 final ResourceHolder resourceHolder 109 = i18nString.getSupport().getResourceHolder(); 110 if (resourceHolder.getResource() == null) { 111 DataObject lastResource = I18nUtil.getOptions().getLastResource2(); 112 if (lastResource != null) { 113 FileObject sourceFile = sourceDataObject.getPrimaryFile(); 114 FileObject bundleFile = lastResource.getPrimaryFile(); 115 ClassPath execClassPath = ClassPath 116 .getClassPath(sourceFile, 117 ClassPath.EXECUTE); 118 if (execClassPath.getResourceName(bundleFile) != null) { 119 resourceHolder.setResource(lastResource); 120 } 121 } 122 } 123 124 if(hcString == null) 125 return i18nString; 126 127 i18nString.setComment(""); i18nString.setKey(hcString.getText().replace(' ', '_' )); 129 i18nString.setValue(hcString.getText()); 130 131 if(isGenerateField() && i18nString.getReplaceFormat().indexOf("{identifier}") == -1) i18nString.setReplaceFormat((String )I18nUtil.getReplaceFormatItems().get(0)); 134 135 return i18nString; 136 } 137 138 139 public JPanel getInfo(HardCodedString hcString) { 140 return new JavaInfoPanel(hcString, document); 141 } 142 143 144 public String getIdentifier() { 145 if(identifier == null || identifier == "") createIdentifier(); 147 148 return identifier; 149 } 150 151 152 public void setIdentifier(String identifier) { 153 this.identifier = identifier; 154 } 155 156 157 public int getModifiers() { 158 return modifiers; 159 } 160 161 162 public void setModifiers(int modifiers) { 163 this.modifiers = modifiers; 164 } 165 166 167 public boolean isGenerateField() { 168 return generateField; 169 } 170 171 172 public void setGenerateField(boolean generateField) { 173 this.generateField = generateField; 174 } 175 176 177 public String getInitFormat() { 178 return initFormat; 179 } 180 181 182 public void setInitFormat(String initFormat) { 183 this.initFormat = initFormat; 184 } 185 186 187 public PropertyPanel getPropertyPanel() { 188 return new JavaPropertyPanel(); 189 } 190 191 193 public boolean hasAdditionalCustomizer() { 194 return true; 195 } 196 197 200 public JPanel getAdditionalCustomizer() { 201 return new JavaReplacePanel(this); 202 } 203 204 206 public void performAdditionalChanges() { 207 createField(); 209 } 210 211 212 public void createIdentifier() { 213 String name; 214 215 try { 216 name = resourceHolder.getResource().getName(); 217 } catch(NullPointerException npe) { 218 identifier = ""; return; 220 } 221 222 if(name.length() > 0) { 224 name = name.substring(0,1).toLowerCase() + name.substring(1); 225 } else { 226 name = name.toLowerCase(); 227 } 228 229 identifier = name; 230 } 231 232 237 private void createField() { 238 } 264 265 270 public String getInitString() { 271 String initJavaFormat = getInitFormat(); 272 273 FileObject fo = resourceHolder.getResource().getPrimaryFile(); 275 ClassPath cp = ClassPath.getClassPath( fo, ClassPath.SOURCE ); 276 277 278 Map map = new HashMap (3); 279 280 map.put("bundleNameSlashes", cp.getResourceName( fo, '/', false ) ); map.put("bundleNameDots", cp.getResourceName( fo, '.', false ) ); map.put("sourceFileName", sourceDataObject == null ? "" : sourceDataObject.getPrimaryFile().getName()); 284 return MapFormat.format(initJavaFormat, map); 285 286 } 287 288 289 310 311 312 public static class JavaI18nFinder implements I18nFinder { 313 314 315 protected static final int STATE_JAVA = 0; 316 317 protected static final int STATE_JAVA_A_SLASH = 1; 318 319 protected static final int STATE_LINECOMMENT = 2; 320 321 protected static final int STATE_BLOCKCOMMENT = 3; 322 323 protected static final int STATE_BLOCKCOMMENT_A_STAR = 4; 324 325 protected static final int STATE_STRING = 5; 326 327 protected static final int STATE_STRING_A_BSLASH = 6; 328 329 protected static final int STATE_CHAR = 7; 331 332 protected StyledDocument document; 333 334 335 protected int state; 336 337 338 protected boolean i18nSearch; 339 340 341 protected Position lastPosition; 342 343 344 protected StringBuffer lastJavaString; 345 346 347 protected char[] buffer; 348 349 350 protected int position; 351 352 353 protected int currentStringStart; 354 355 356 protected int currentStringEnd; 357 358 359 360 public JavaI18nFinder(StyledDocument document) { 361 this.document = document; 362 363 init(); 364 } 365 366 367 private void init() { 368 state = STATE_JAVA; 369 initJavaStringBuffer(); 370 371 lastPosition = null; 372 } 373 374 375 protected void reset() { 376 init(); 377 } 378 379 382 public HardCodedString[] findAllHardCodedStrings() { 383 reset(); 384 i18nSearch = false; 385 386 return findAllStrings(); 387 } 388 389 394 public HardCodedString findNextHardCodedString() { 395 i18nSearch = false; 396 397 return findNextString(); 398 } 399 400 404 public HardCodedString[] findAllI18nStrings() { 405 reset(); 406 i18nSearch = true; 407 408 return findAllStrings(); 409 } 410 411 416 public HardCodedString findNextI18nString() { 417 i18nSearch = true; 418 419 return findNextString(); 420 } 421 422 423 424 protected HardCodedString[] findAllStrings() { 425 426 ArrayList list = new ArrayList (); 427 428 HardCodedString hardString; 429 430 for(;(hardString = findNextString())!= null;) { 431 list.add(hardString); 432 } 433 434 if(list.isEmpty()) 435 return null; 436 else { 437 HardCodedString[] hardStrings = new HardCodedString[list.size()]; 438 list.toArray(hardStrings); 439 return hardStrings; 440 } 441 } 442 443 444 protected HardCodedString findNextString() { 445 try { 447 buffer = document.getText(0, document.getLength()).toCharArray(); 448 } catch(BadLocationException ble) { 449 if(Boolean.getBoolean("netbeans.debug.exception")) ble.printStackTrace(); 451 452 return null; 453 } 454 455 if(lastPosition == null) 457 position = 0; 458 else 459 position = lastPosition.getOffset(); 460 461 currentStringStart = -1; 463 currentStringEnd = -1; 464 465 while(position < buffer.length) { 467 468 char ch = buffer[position]; 469 470 if(ch != '\n') { 472 HardCodedString foundHardString = handleCharacter(ch); 473 474 if(foundHardString != null) 475 return foundHardString; 476 477 } else 478 handleNewLineCharacter(); 479 480 position++; 481 482 } 484 return null; 486 } 487 488 489 protected HardCodedString handleCharacter(char character) { 490 if(state == STATE_JAVA) { 491 return handleStateJava(character); 492 } else if(state == STATE_JAVA_A_SLASH) { 493 return handleStateJavaASlash(character); 494 } else if(state == STATE_CHAR) { 495 return handleStateChar(character); 496 } else if(state == STATE_STRING_A_BSLASH) { 497 return handleStateStringABSlash(character); 498 } else if(state == STATE_LINECOMMENT) { 499 return handleStateLineComment(character); 500 } else if(state == STATE_BLOCKCOMMENT) { 501 return handleStateBlockComment(character); 502 } else if(state == STATE_BLOCKCOMMENT_A_STAR) { 503 return handleStateBlockCommentAStar(character); 504 } else if(state == STATE_STRING) { 505 return handleStateString(character); 506 } 507 508 return null; 509 } 510 511 512 protected void handleNewLineCharacter() { 513 if(state == STATE_JAVA 515 || state == STATE_JAVA_A_SLASH 516 || state == STATE_CHAR 517 || state == STATE_LINECOMMENT 518 || state == STATE_STRING 519 || state == STATE_STRING_A_BSLASH) { 520 initJavaStringBuffer(); 521 currentStringStart = -1; 522 currentStringEnd = -1; 523 state = STATE_JAVA; 524 } else if(state == STATE_BLOCKCOMMENT 525 || state == STATE_BLOCKCOMMENT_A_STAR) { 526 state = STATE_BLOCKCOMMENT; 527 } 528 } 529 530 531 534 protected HardCodedString handleStateJava(char character) { 535 lastJavaString.append(character); 536 if(character == '/') { 537 state = STATE_JAVA_A_SLASH; 538 } else if(character == '"') { 539 state = STATE_STRING; 540 if(currentStringStart == -1) 541 currentStringStart = position; 543 } else if(character == '\'') { 544 state = STATE_CHAR; 545 } 546 547 return null; 548 } 549 550 553 protected HardCodedString handleStateJavaASlash(char character) { 554 lastJavaString.append(character); 555 if(character == '/') { 556 state = STATE_LINECOMMENT; 557 } else if(character == '*') { 558 state = STATE_BLOCKCOMMENT; 559 } 560 561 return null; 562 } 563 564 567 protected HardCodedString handleStateChar(char character) { 568 lastJavaString.append(character); 569 570 if(character == '\'') { 571 state = STATE_JAVA; 572 } 573 574 return null; 575 } 576 577 580 protected HardCodedString handleStateStringABSlash(char character) { 581 state = STATE_STRING; 582 583 return null; 584 } 585 586 589 protected HardCodedString handleStateLineComment(char character) { 590 return null; 591 } 592 593 596 protected HardCodedString handleStateBlockComment(char character) { 597 if(character == '*') { 598 state = STATE_BLOCKCOMMENT_A_STAR; 599 } 600 601 return null; 602 } 603 604 607 protected HardCodedString handleStateBlockCommentAStar(char character) { 608 if(character == '/') { 609 state = STATE_JAVA; 610 initJavaStringBuffer(); 611 } else if (character != '*') { 612 state = STATE_BLOCKCOMMENT; 613 } 614 615 return null; 616 } 617 618 621 protected HardCodedString handleStateString(char character) { 622 if(character == '\\') { 623 state = STATE_STRING_A_BSLASH; 624 } else if(character == '"') { 625 state = STATE_JAVA; 626 627 if((currentStringEnd == -1) && (currentStringStart != -1)) { 628 currentStringEnd = position + 1; 630 631 int foundStringLength = currentStringEnd - currentStringStart; 632 633 try { 634 Position hardStringStart = document.createPosition(currentStringStart); 636 Position hardStringEnd = document.createPosition(currentStringEnd); 637 638 String hardString = document.getText(hardStringStart.getOffset(), foundStringLength); 639 640 String restBuffer = new String (buffer, currentStringEnd, buffer.length-currentStringEnd); 642 int endOfLine = restBuffer.indexOf('\n'); 643 if(endOfLine == -1) 644 endOfLine = restBuffer.length(); 645 646 lastJavaString.append(document.getText(currentStringStart+1, hardString.length())); 647 648 String restOfLine = document.getText(currentStringStart+1+hardString.length(), currentStringEnd+endOfLine-currentStringStart-hardString.length()); 650 651 lastJavaString.append(restOfLine.replace('\"', '_')); 653 654 if(isSearchedString(lastJavaString.toString(), hardString) ) { 656 lastPosition = hardStringEnd; 657 658 return new HardCodedString(extractString(hardString), hardStringStart, hardStringEnd); 660 } 661 } catch(BadLocationException ble) { 662 ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, ble); 663 } finally { 664 currentStringStart = -1; 665 currentStringEnd = -1; 666 667 initJavaStringBuffer(); 668 } 669 } 670 } 671 672 return null; 673 } 674 675 677 private void initJavaStringBuffer() { 678 lastJavaString = new StringBuffer (); 679 } 680 681 682 private String extractString(String sourceString) { 683 if(sourceString == null) 684 return ""; 686 if ((sourceString.length() >= 2) && 687 (sourceString.charAt(0) == '"') && 688 (sourceString.charAt(sourceString.length() - 1) == '"')) 689 sourceString = sourceString.substring(1, sourceString.length() - 1); 690 return sourceString; 691 } 692 693 707 protected boolean isSearchedString(String partHardLine, String hardString) { 708 String lineToMatch = UtilConvert.unicodesToChars(partHardLine); 709 710 Exception ex = null; 711 try { 712 String regexp = createRegularExpression(hardString); 713 return Pattern.compile(regexp).matcher(lineToMatch).find() 714 == i18nSearch; 715 } catch (ParseException ex1) { 716 ex = ex1; 717 } catch (PatternSyntaxException ex2) { 718 ex = ex2; 719 } 720 721 724 ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, ex); 725 726 String msg = MessageFormat.format( 731 Util.getString("MSG_RegExpCompileError"), 732 new Object [] {hardString} 733 ); 734 735 Object answer = DialogDisplayer.getDefault().notify( 736 new NotifyDescriptor.Confirmation( 737 msg, 738 NotifyDescriptor.YES_NO_OPTION, 739 NotifyDescriptor.ERROR_MESSAGE)); 740 return NotifyDescriptor.YES_OPTION.equals(answer); 741 } 742 743 757 private String createRegularExpression(String hardString) 758 throws ParseException { 759 String regexpForm; 760 if (i18nSearch) { 761 regexpForm = I18nUtil.getOptions().getI18nRegularExpression(); 762 } else { 763 regexpForm = I18nUtil.getOptions().getRegularExpression(); 764 } 765 766 771 Map map = new HashMap (3); 772 map.put("key", hardString); map.put("hardString", hardString); return Translator.translateRegexp(regexpForm, map); 775 } 776 777 } 779 780 781 public static class JavaI18nReplacer implements I18nReplacer { 782 783 784 public JavaI18nReplacer() { 785 } 786 787 788 791 public void replace(final HardCodedString hcString, final I18nString i18nString) { 792 if(!(i18nString instanceof JavaI18nString)) 793 throw new IllegalArgumentException ("I18N module: i18nString have to be an instance of JavaI18nString."); 795 final String newCode = i18nString.getReplaceString(); 796 797 final StyledDocument document = i18nString.getSupport().getDocument(); 798 799 NbDocument.runAtomic( 801 document, 802 new Runnable () { 803 public void run() { 804 try { 805 if(hcString.getLength() > 0) { 806 document.remove(hcString.getStartPosition().getOffset(), hcString.getLength()); 807 } 808 if(newCode != null && newCode.length() > 0) { 809 document.insertString(hcString.getEndPosition().getOffset(), newCode, null); 810 } 811 } catch(BadLocationException ble) { 812 NotifyDescriptor.Message message = new NotifyDescriptor.Message( 813 Util.getString("MSG_CouldNotReplace"), NotifyDescriptor.ERROR_MESSAGE); 814 DialogDisplayer.getDefault().notify(message); 815 } 816 } 817 }); 818 } 819 } 821 822 823 private static class JavaInfoPanel extends InfoPanel { 824 825 826 public JavaInfoPanel(HardCodedString hcString, StyledDocument document) { 827 super(hcString, document); 828 } 829 830 831 protected void setHardCodedString(HardCodedString hcString, StyledDocument document) { 832 833 getStringText().setText(hcString == null ? "" : hcString.getText()); 835 int pos; 836 837 String hardLine; 838 839 if(hcString.getStartPosition() == null) 840 hardLine = ""; else { 842 pos = hcString.getStartPosition().getOffset(); 843 844 try { 845 Element paragraph = document.getParagraphElement(pos); 846 hardLine = document.getText(paragraph.getStartOffset(), paragraph.getEndOffset()-paragraph.getStartOffset()).trim(); 847 } catch (BadLocationException ble) { 848 hardLine = ""; } 850 } 851 852 getFoundInText().setText(hardLine); 853 854 remove(getComponentLabel()); 855 remove(getComponentText()); 856 remove(getPropertyLabel()); 857 remove(getPropertyText()); 858 } 859 } 861 862 863 public static class Factory extends I18nSupport.Factory { 864 865 866 public I18nSupport createI18nSupport(DataObject dataObject) { 867 return new JavaI18nSupport(dataObject); 868 } 869 870 873 public Class getDataObjectClass() { 874 try { 877 return Class.forName( 878 "org.netbeans.modules.java.JavaDataObject", false, 880 (ClassLoader )Lookup.getDefault().lookup(ClassLoader .class)); 881 } catch(ClassNotFoundException cnfe) { 882 return null; 883 } 884 } 885 } } 887 | Popular Tags |