Revision: 7095
          
http://languagetool.svn.sourceforge.net/languagetool/?rev=7095&view=rev
Author:   dnaber
Date:     2012-05-28 17:39:55 +0000 (Mon, 28 May 2012)
Log Message:
-----------
online rule creation helper

Modified Paths:
--------------
    trunk/ltcommunity/web-app/css/main.css

Added Paths:
-----------
    
trunk/ltcommunity/grails-app/controllers/org/languagetool/RuleEditorController.groovy
    trunk/ltcommunity/grails-app/services/
    trunk/ltcommunity/grails-app/services/org/
    trunk/ltcommunity/grails-app/services/org/languagetool/
    
trunk/ltcommunity/grails-app/services/org/languagetool/PatternStringConverterService.groovy
    trunk/ltcommunity/grails-app/views/ruleEditor/
    trunk/ltcommunity/grails-app/views/ruleEditor/_checkRuleProblem.gsp
    trunk/ltcommunity/grails-app/views/ruleEditor/checkRule.gsp
    trunk/ltcommunity/grails-app/views/ruleEditor/createXml.gsp
    trunk/ltcommunity/grails-app/views/ruleEditor/index.gsp
    
trunk/ltcommunity/test/integration/org/languagetool/PatternStringConverterServiceTests.groovy

Copied: 
trunk/ltcommunity/grails-app/controllers/org/languagetool/RuleEditorController.groovy
 (from rev 7071, 
trunk/ltcommunity/grails-app/controllers/org/languagetool/CorpusMatchController.groovy)
===================================================================
--- 
trunk/ltcommunity/grails-app/controllers/org/languagetool/RuleEditorController.groovy
                               (rev 0)
+++ 
trunk/ltcommunity/grails-app/controllers/org/languagetool/RuleEditorController.groovy
       2012-05-28 17:39:55 UTC (rev 7095)
@@ -0,0 +1,144 @@
+/* LanguageTool Community 
+ * Copyright (C) 2012 Daniel Naber (http://www.danielnaber.de)
+ * 
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301
+ * USA
+ */
+package org.languagetool
+
+import org.languagetool.rules.patterns.PatternRule
+
+/**
+ * Editor that helps with creating the XML for simple rules.
+ */
+class RuleEditorController extends BaseController {
+    
+    def patternStringConverterService
+
+    def index = {
+      List languages = Language.REAL_LANGUAGES
+      List languageNames = []
+      languages.each { languageNames.add(it.getName()) }
+      [languages: Language.REAL_LANGUAGES, languageNames: languageNames.sort()]
+    }
+
+    def checkRule = {
+      Language language = getLanguage()
+      PatternRule patternRule = createPatternRule(language)
+      JLanguageTool langTool = getLanguageToolWithOneRule(language, 
patternRule)
+      List expectedRuleMatches = langTool.check(params.incorrectExample1)
+      List unexpectedRuleMatches = langTool.check(params.correctExample1)
+      List problems = []
+      if (expectedRuleMatches.size() == 0) {
+        problems.add("The rule did not find an error in the given example 
sentence with an error")
+      }
+      if (unexpectedRuleMatches.size() > 0) {
+        problems.add("The rule found an error in the given example sentence 
that is not supposed to contain an error")
+      }
+      if (problems.size() == 0) {
+        [messagePreset: params.messageBackup, namePreset: params.nameBackup]
+      } else {
+        render(template: 'checkRuleProblem', model: [problems: problems, 
hasRegex: hasRegex(patternRule)])
+      }
+    }
+
+  private JLanguageTool getLanguageToolWithOneRule(Language lang, PatternRule 
patternRule) {
+    JLanguageTool langTool = new JLanguageTool(lang)
+    for (rule in langTool.getAllActiveRules()) {
+      langTool.disableRule(rule.getId())
+    }
+    langTool.addRule(patternRule)
+    return langTool
+  }
+
+  boolean hasRegex(PatternRule patternRule) {
+    for (element in patternRule.getElements()) {
+      if (element.isRegularExpression()) {
+        return true
+      }
+    }
+    return false
+  }
+
+  private Language getLanguage() {
+    Language lang = Language.getLanguageForName(params.language)
+    if (!lang) {
+      throw new Exception("No language '${params.language}' found")
+    }
+    lang
+  }
+
+  private PatternRule createPatternRule(Language lang) {
+    return patternStringConverterService.convertToPatternRule(params.pattern, 
lang)
+  }
+
+  def createXml = {
+    if (!params.message || params.message.trim().isEmpty()) {
+      [error: "Please fill out the 'Error Message' field"]
+    } else {
+      String message = getMessage()
+      String correctSentence = params.correctExample1.encodeAsHTML()
+      Language language = getLanguage()
+      String incorrectSentence = getIncorrectSentenceWithMarker(language)
+      String name = params.name ? params.name : "Name of rule"
+      String xml = createXml(name, message, incorrectSentence, correctSentence)
+      [xml: xml, language: language]
+    }
+  }
+
+  private String getIncorrectSentenceWithMarker(Language language) {
+    PatternRule patternRule = createPatternRule(language)
+    JLanguageTool langTool = getLanguageToolWithOneRule(language, patternRule)
+    String incorrectSentence = params.incorrectExample1
+    List expectedRuleMatches = langTool.check(params.incorrectExample1)
+    if (expectedRuleMatches.size() == 1) {
+      StringBuilder sb = new StringBuilder(incorrectSentence)
+      sb.insert(expectedRuleMatches.get(0).toPos, "</marker>")
+      sb.insert(expectedRuleMatches.get(0).fromPos, "<marker>")
+      incorrectSentence = 
sb.toString().encodeAsHTML().replace("&lt;marker&gt;", 
"<marker>").replace("&lt;/marker&gt;", "</marker>")
+    } else {
+      throw new Exception("Sorry, got ${expectedRuleMatches.size()} rule 
matches for the example sentence, " +
+              "expected exactly one. Sentence: '${incorrectSentence}', Rule 
matches: ${expectedRuleMatches}")
+    }
+    return incorrectSentence
+  }
+
+  private String createXml(String name, String message, String 
incorrectSentence, String correctSentence) {
+    Language lang = getLanguage()
+    PatternRule patternRule = createPatternRule(lang)
+    String xml = """<rule id="RULE_1" name="${name.encodeAsHTML()}">
+    <pattern>\n"""
+    for (element in patternRule.getElements()) {
+      if (element.isRegularExpression()) {
+        xml += "        <token 
regexp=\"true\">${element.getString()}</token>\n"
+      } else {
+        xml += "        <token>${element.getString()}</token>\n"
+      }
+    }
+    xml += """    </pattern>
+    <message>${message}</message>
+    <example type="incorrect">${incorrectSentence}</example>
+    <example type="correct">${correctSentence}</example>
+</rule>"""
+    xml
+  }
+
+  private String getMessage() {
+    String message = params.message.encodeAsHTML()
+    message = message.replaceAll("['\"](.*?)['\"]", 
"<suggestion>\$1</suggestion>")
+    message = message.replaceAll("&quot;(.*?)&quot;", 
"<suggestion>\$1</suggestion>")
+    return message
+  }
+}

Added: 
trunk/ltcommunity/grails-app/services/org/languagetool/PatternStringConverterService.groovy
===================================================================
--- 
trunk/ltcommunity/grails-app/services/org/languagetool/PatternStringConverterService.groovy
                         (rev 0)
+++ 
trunk/ltcommunity/grails-app/services/org/languagetool/PatternStringConverterService.groovy
 2012-05-28 17:39:55 UTC (rev 7095)
@@ -0,0 +1,74 @@
+/* LanguageTool Community
+ * Copyright (C) 2012 Daniel Naber (http://www.danielnaber.de)
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301
+ * USA
+ */
+package org.languagetool
+
+import org.languagetool.rules.patterns.Element
+import org.languagetool.rules.patterns.PatternRule
+import org.languagetool.rules.Category
+import org.languagetool.tokenizers.Tokenizer
+
+class PatternStringConverterService {
+
+  static transactional = true
+
+  def convertToPatternRule(String patternString, Language lang) {
+    List patternParts = getPatternParts(lang, patternString)
+    List elements = []
+    for (patternPart in patternParts) {
+      boolean isRegex = isRegex(patternPart)
+      elements.add(new Element(patternPart, false, isRegex, false))
+    }
+    PatternRule patternRule = new PatternRule("ID1", lang, elements, "empty 
description", "empty message", "empty short description")
+    patternRule.setCategory(new Category("fake category"))
+    return patternRule
+  }
+
+  // just a guess
+  private boolean isRegex(patternPart) {
+    return patternPart.find("[.|+*?\\[\\]]") != null
+  }
+
+  private List getPatternParts(Language lang, String patternString) {
+    // First split at whitespace, then properly tokenize unless it's a regex. 
Only this way we will
+    // properly tokenize "don't" but don't tokenize a regex like "foob.r":
+    List simpleParts = patternString.split("\\s+")
+    def tokenizer = lang.getWordTokenizer()
+    List patternParts = []
+    for (simplePart in simpleParts) {
+      if (isRegex(simplePart)) {
+        patternParts.add(simplePart)
+      } else {
+        patternParts.addAll(getTokens(tokenizer, simplePart))
+      }
+    }
+    return patternParts
+  }
+
+  private List getTokens(Tokenizer tokenizer, simplePart) {
+    List tokens = []
+    List patternPartsWithWhitespace = tokenizer.tokenize(simplePart)
+    for (patternPart in patternPartsWithWhitespace) {
+      if (!patternPart.trim().isEmpty()) {
+        tokens.add(patternPart)
+      }
+    }
+    return tokens
+  }
+
+}

Added: trunk/ltcommunity/grails-app/views/ruleEditor/_checkRuleProblem.gsp
===================================================================
--- trunk/ltcommunity/grails-app/views/ruleEditor/_checkRuleProblem.gsp         
                (rev 0)
+++ trunk/ltcommunity/grails-app/views/ruleEditor/_checkRuleProblem.gsp 
2012-05-28 17:39:55 UTC (rev 7095)
@@ -0,0 +1,31 @@
+<table style="border: 0px">
+<tr>
+    <td width="150"></td>
+    <td>
+
+        <div class="errors">There are problems with your rule:
+
+            <ul>
+                <g:each in="${problems}" var="problem">
+                    <li>${problem.encodeAsHTML()}</li>
+                </g:each>
+            </ul>
+
+        </div>
+
+        <p style="width:450px;margin-top: 5px">The examples sentences are used 
to test your rule. Your first
+        example sentence should contain the error so it can be found with the 
"Wrong words" pattern.
+        The second example sentence should not contain the error.
+        If you need help, <a href="http://www.languagetool.org/forum/";>please 
ask in our forum</a>.</p>
+
+        <g:if test="${hasRegex}">
+            <p style="width:450px;margin-top: 5px">Note that you have used 
special characters like the dot (<tt>.</tt>),
+            a question mark (<tt>?</tt>), or similar. This means that the word 
with that character is interpreted
+            as a <a 
href="http://en.wikipedia.org/wiki/Regular_expression";>regular expression</a>. 
If you
+            don't want that you have to write your XML manually for now, as 
this tool sometimes cannot safely
+            tell what you mean by those characters.</p>
+        </g:if>
+
+    </td>
+</tr>
+</table>
\ No newline at end of file

Added: trunk/ltcommunity/grails-app/views/ruleEditor/checkRule.gsp
===================================================================
--- trunk/ltcommunity/grails-app/views/ruleEditor/checkRule.gsp                 
        (rev 0)
+++ trunk/ltcommunity/grails-app/views/ruleEditor/checkRule.gsp 2012-05-28 
17:39:55 UTC (rev 7095)
@@ -0,0 +1,41 @@
+<table style="border: 0px">
+<tr>
+    <td width="150">Error Message</td>
+    <td><g:textField id="message"
+            onkeypress="return handleReturnForXmlCreation(event);"
+            onfocus="\$('message').setStyle({color: 'black'})"
+            onchange="\$('messageBackup').value = \$('message').value"
+            class="preFilledField" type="text" name="message"
+            value="${messagePreset ? messagePreset.encodeAsHTML() : 'Did you 
mean \'bad\'?'}"/>
+        <!--<br/>
+        <span class="metaInfo">Example: Did you mean 'bad'?</span>-->
+    </td>
+</tr>
+<tr>
+    <td>Rule Name<br/>
+        <span class="metaInfo">optional</span>
+    </td>
+    <td><g:textField id="name"
+            onkeypress="return handleReturnForXmlCreation(event);"
+            onfocus="\$('name').setStyle({color: 'black'})"
+            onchange="\$('nameBackup').value = \$('name').value"
+            class="preFilledField" type="text" name="name"
+            value="${namePreset ? namePreset.encodeAsHTML() : 'confusion of 
bed/bad'}"/>
+        <!--<br/>
+        <span class="metaInfo">Example: confusion of bed/bad</span>-->
+    </td>
+</tr>
+<tr>
+    <td></td>
+    <td>
+        <g:submitToRemote name="createXmlButton" 
onLoading="startLoad('createXmlSpinner')" 
onComplete="stopLoad('createXmlSpinner')" action="createXml" update="xml" 
value="Create XML"/>
+        <img id="createXmlSpinner" style="display: none" 
src="${resource(dir:'images', file:'spinner.gif')}" alt="wait symbol"/>
+    </td>
+</tr>
+</table>
+
+<script type="text/javascript">
+    document.ruleForm.message.select();
+</script>
+
+<div id="xml"></div>

Added: trunk/ltcommunity/grails-app/views/ruleEditor/createXml.gsp
===================================================================
--- trunk/ltcommunity/grails-app/views/ruleEditor/createXml.gsp                 
        (rev 0)
+++ trunk/ltcommunity/grails-app/views/ruleEditor/createXml.gsp 2012-05-28 
17:39:55 UTC (rev 7095)
@@ -0,0 +1,26 @@
+<table style="border: 0px" xmlns="http://www.w3.org/1999/html";>
+<tr>
+    <td width="150">XML</td>
+    <td>
+        <g:if test="${error}">
+            <div class="errors">${error.encodeAsHTML()}</div>
+            <script type="text/javascript">
+                document.ruleForm.message.select();
+            </script>
+        </g:if>
+        <g:else>
+
+            <p style="width:450px;margin-bottom: 5px">This is the XML that you 
need to add inside a <tt>&lt;category&gt;</tt> in the file<br/>
+                <tt>rules/${language.getShortName()}/grammar.xml</tt>. After 
re-starting LanguageTool, the rule
+                will work locally for you.</p>
+
+            <pre style="background-color: #eeeeee; padding: 
10px">${xml.encodeAsHTML().replaceAll("&gt;(.*?)&lt;", 
"&gt;<strong>\$1</strong>&lt;")}</pre>
+
+            <p style="width:450px;margin-top: 5px">LanguageTool rules can be 
much more powerful - this page
+            can only create simple rules. See <a 
href="http://www.languagetool.org/development/";>our development 
documentation</a>
+            for more features.</p>
+
+        </g:else>
+    </td>
+</tr>
+</table>

Added: trunk/ltcommunity/grails-app/views/ruleEditor/index.gsp
===================================================================
--- trunk/ltcommunity/grails-app/views/ruleEditor/index.gsp                     
        (rev 0)
+++ trunk/ltcommunity/grails-app/views/ruleEditor/index.gsp     2012-05-28 
17:39:55 UTC (rev 7095)
@@ -0,0 +1,109 @@
+
+<%@ page import="org.languagetool.User" %>
+<%@ page import="org.languagetool.rules.patterns.PatternRule" %>
+<%@ page import="org.languagetool.tools.StringTools" %>
+<html>
+    <head>
+        <g:javascript library="prototype" />
+        <meta name="layout" content="main" />
+        <title>Create a new LanguageTool rule</title>
+        <script type="text/javascript">
+
+            function startLoad(divName) {
+                $(divName).show();
+            }
+            function stopLoad(divName) {
+                $(divName).hide();
+            }
+
+            function handleReturn(event) {
+                if (event.keyCode == 13) {
+                    document.ruleForm.checkRuleButton.click();
+                }
+            }
+
+            function handleReturnForXmlCreation(event) {
+                if (event.keyCode == 13) {
+                    document.ruleForm.createXmlButton.click();
+                }
+            }
+
+        </script>
+    </head>
+    <body>
+
+        <div class="body">
+
+            <h2>Rule Creator</h2>
+
+            <noscript class="warn">This page requires Javascript</noscript>
+        
+            <g:form name="ruleForm"  method="post" action="checkRule">
+
+                <g:hiddenField id="messageBackup" name="messageBackup" 
value=""/>
+                <g:hiddenField id="nameBackup" name="nameBackup" value=""/>
+
+                <table style="border: 0px">
+                    <tr>
+                        <td colspan="2">
+                            <p style="width:550px">LanguageTool finds errors 
based on rules. Most of these rules are expressed
+                            as XML, and this page will help you to create your 
own simple rules in XML.</p>
+                        </td>
+                    </tr>
+                    <tr>
+                        <td width="150">Language</td>
+                        <td><g:select name="language" from="${languageNames}" 
value="English"/></td>
+                    </tr>
+                    <tr>
+                        <td>Wrong words</td>
+                        <td><g:textField id="pattern"
+                                onkeypress="return handleReturn(event);"
+                                onfocus="\$('pattern').setStyle({color: 
'black'})"
+                                class="preFilledField" type="text" 
name="pattern" value="bed English"/>
+                            <!--<br/>
+                            <span class="metaInfo">Example: bed 
English</span>-->
+                        </td>
+                    </tr>
+                    <tr>
+                        <td>Sentence<br/>
+                            with error</td>
+                        <td><g:textField id="incorrectExample1"
+                                onkeypress="return handleReturn(event);"
+                                
onfocus="\$('incorrectExample1').setStyle({color: 'black'})"
+                                class="preFilledField" type="text" 
name="incorrectExample1" value="Sorry for my bed English."/>
+                            <!--<br/>
+                            <span class="metaInfo">Example: Sorry for my bed 
English.</span>-->
+                        </td>
+                    </tr>
+                    <tr>
+                        <td>Sentence<br/>
+                            with the error corrected</td>
+                        <td><g:textField id="correctExample1"
+                                onkeypress="return handleReturn(event);"
+                                
onfocus="\$('correctExample1').setStyle({color: 'black'})"
+                                class="preFilledField" type="text" 
name="correctExample1" value="Sorry for my bad English."/>
+                            <!--<br/>
+                            <span class="metaInfo">Example: Sorry for my bad 
English.</span>-->
+                        </td>
+                    </tr>
+                    <tr>
+                        <td></td>
+                        <td>
+                            <g:submitToRemote name="checkRuleButton" 
onLoading="startLoad('checkResultSpinner')" 
onComplete="stopLoad('checkResultSpinner')" action="checkRule" 
update="checkResult" value="Continue"/>
+                            <img id="checkResultSpinner" style="display: none" 
src="${resource(dir:'images', file:'spinner.gif')}" alt="wait symbol"/>
+                        </td>
+                    </tr>
+
+                </table>
+
+                <div id="checkResult"></div>
+
+            </g:form>
+
+            <script type="text/javascript">
+                document.ruleForm.pattern.select();
+            </script>
+
+        </div>
+    </body>
+</html>

Added: 
trunk/ltcommunity/test/integration/org/languagetool/PatternStringConverterServiceTests.groovy
===================================================================
--- 
trunk/ltcommunity/test/integration/org/languagetool/PatternStringConverterServiceTests.groovy
                               (rev 0)
+++ 
trunk/ltcommunity/test/integration/org/languagetool/PatternStringConverterServiceTests.groovy
       2012-05-28 17:39:55 UTC (rev 7095)
@@ -0,0 +1,118 @@
+/* LanguageTool Community
+ * Copyright (C) 2012 Daniel Naber (http://www.danielnaber.de)
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301
+ * USA
+ */
+package org.languagetool
+
+import grails.test.*
+import org.languagetool.rules.patterns.PatternRule
+
+class PatternStringConverterServiceTests extends GrailsUnitTestCase {
+
+  def patternStringConverterService
+
+  void testConverter() {
+    PatternRule rule = patternStringConverterService.convertToPatternRule("bed 
English", Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(2, elements.size())
+
+    assertEquals("bed", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(false, elements.get(0).isRegularExpression())
+
+    assertEquals("English", elements.get(1).getString())
+    assertEquals(false, elements.get(1).isInflected())
+    assertEquals(false, elements.get(1).isRegularExpression())
+  }
+
+  void testConverterRegex1() {
+    PatternRule rule = patternStringConverterService.convertToPatternRule("bed 
English|German", Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(2, elements.size())
+
+    assertEquals("bed", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(false, elements.get(0).isRegularExpression())
+
+    assertEquals("English|German", elements.get(1).getString())
+    assertEquals(false, elements.get(1).isInflected())
+    assertEquals(true, elements.get(1).isRegularExpression())
+  }
+
+  void testConverterRegex2() {
+    PatternRule rule = 
patternStringConverterService.convertToPatternRule("[abc]bar", Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(1, elements.size())
+
+    assertEquals("[abc]bar", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(true, elements.get(0).isRegularExpression())
+  }
+
+  void testConverterRegexWithDot() {
+    PatternRule rule = 
patternStringConverterService.convertToPatternRule("b.r", Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(1, elements.size())
+
+    assertEquals("b.r", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(true, elements.get(0).isRegularExpression())
+  }
+
+  void testConverterRegexWithParentheses() {
+    PatternRule rule = 
patternStringConverterService.convertToPatternRule("(English|German)", 
Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(1, elements.size())
+
+    assertEquals("(English|German)", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(true, elements.get(0).isRegularExpression())
+  }
+
+  void testConverterWithDash() {
+    PatternRule rule = 
patternStringConverterService.convertToPatternRule("no-go", Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(1, elements.size())
+
+    assertEquals("no-go", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(false, elements.get(0).isRegularExpression())
+  }
+
+  void testConverterWithContraction() {
+    PatternRule rule = 
patternStringConverterService.convertToPatternRule("don't want", 
Language.ENGLISH)
+    def elements = rule.getElements()
+    assertEquals(4, elements.size())
+
+    assertEquals("don", elements.get(0).getString())
+    assertEquals(false, elements.get(0).isInflected())
+    assertEquals(false, elements.get(0).isRegularExpression())
+
+    assertEquals("'", elements.get(1).getString())
+    assertEquals(false, elements.get(1).isInflected())
+    assertEquals(false, elements.get(1).isRegularExpression())
+
+    assertEquals("t", elements.get(2).getString())
+    assertEquals(false, elements.get(2).isInflected())
+    assertEquals(false, elements.get(2).isRegularExpression())
+
+    assertEquals("want", elements.get(3).getString())
+    assertEquals(false, elements.get(3).isInflected())
+    assertEquals(false, elements.get(3).isRegularExpression())
+  }
+
+}

Modified: trunk/ltcommunity/web-app/css/main.css
===================================================================
--- trunk/ltcommunity/web-app/css/main.css      2012-05-28 14:58:52 UTC (rev 
7094)
+++ trunk/ltcommunity/web-app/css/main.css      2012-05-28 17:39:55 UTC (rev 
7095)
@@ -13,7 +13,7 @@
 
 body {
     background: #fff;
-    color: #333;
+    color: #222222;
     font: 12px verdana, arial, helvetica, sans-serif;
 }
 
@@ -49,6 +49,9 @@
 ul {
     padding-left: 15px;        
 }
+input[type="button"] {
+    background-color: #eeeeee;
+}
 
 input, select {
     background-color: #fcfcfc;
@@ -133,7 +136,7 @@
     border: 1px solid red;
     color: #cc0000;
     margin: 10px 0 5px 0;
-    padding: 5px 0 5px 0;
+    padding: 5px;
 }
 div.errors ul {
     list-style: none;
@@ -395,4 +398,13 @@
 
 .javaRule {
     color: #777777;
+}
+
+.metaInfo {
+    color: #777777;
+}
+
+.preFilledField {
+    width: 400px;
+    color: #999999;
 }
\ No newline at end of file

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.


------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and 
threat landscape has changed and how IT managers can respond. Discussions 
will include endpoint security, mobile security and the latest in malware 
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/
_______________________________________________
Languagetool-cvs mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/languagetool-cvs

Reply via email to