/*
* Copyright 2010-2015 Institut Pasteur.
*
* This file is part of Icy.
*
* Icy is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Icy 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with Icy. If not, see <http://www.gnu.org/licenses/>.
*/
package plugins.kernel.searchprovider;
import icy.action.ActionManager;
import icy.action.IcyAbstractAction;
import icy.resource.icon.IcyIcon;
import icy.search.SearchResult;
import icy.search.SearchResultConsumer;
import icy.search.SearchResultProducer;
import icy.util.StringUtil;
import java.awt.Image;
import java.util.ArrayList;
import org.pushingpixels.flamingo.api.common.RichTooltip;
/**
* This class is used to provide kernel command elements to the search engine.
*
* @author Stephane
*/
public class KernelSearchResultProducer extends SearchResultProducer
{
public static class KernelSearchResult extends SearchResult
{
private final IcyAbstractAction action;
private final int priority;
private String description;
public KernelSearchResult(SearchResultProducer provider, IcyAbstractAction action, String searchWords[],
int priority)
{
super(provider);
this.action = action;
this.priority = priority;
final String longDesc = action.getLongDescription();
if (!StringUtil.isEmpty(longDesc))
{
final String[] lds = longDesc.split("\n");
if (lds.length > 0)
// no more than 80 characters for description
description = StringUtil.limit(lds[0], 80, true);
// highlight search keywords (only for more than 2 characters search)
if ((searchWords.length > 1) || (searchWords[0].length() > 2))
{
// highlight search keywords in description
for (String word : searchWords)
description = StringUtil.htmlBoldSubstring(description, word, true);
}
}
else
description = "";
}
public IcyAbstractAction getAction()
{
return action;
}
@Override
public Image getImage()
{
final IcyIcon icon = action.getIcon();
if (icon != null)
return icon.getImage();
return null;
}
@Override
public String getTitle()
{
final String desc = action.getDescription();
if (!StringUtil.isEmpty(desc))
return desc;
return action.getName();
}
@Override
public String getDescription()
{
return description;
}
@Override
public String getTooltip()
{
if (isEnabled())
return "Click to execute the action";
return "Inactive action";
// return action.getLongDescription();
}
@Override
public boolean isEnabled()
{
return action.isEnabled();
}
@Override
public void execute()
{
action.execute();
}
@Override
public RichTooltip getRichToolTip()
{
final String longDesc = action.getLongDescription();
if (!StringUtil.isEmpty(longDesc))
{
if (longDesc.split("\n").length > 1)
return action.getRichToolTip();
}
return null;
}
@Override
public void executeAlternate()
{
// nothing to do here...
}
@Override
public int compareTo(SearchResult o)
{
if (o instanceof KernelSearchResult)
return ((KernelSearchResult) o).priority - priority;
return super.compareTo(o);
}
}
@Override
public int getOrder()
{
// should be first
return 0;
}
@Override
public String getName()
{
return "Command";
}
@Override
public String getTooltipText()
{
return "Result(s) from the internal commands and actions";
}
@Override
public void doSearch(String[] words, SearchResultConsumer consumer)
{
if (hasWaitingSearch())
return;
final ArrayList<SearchResult> tmpResults = new ArrayList<SearchResult>();
final boolean shortSearch = (words.length == 1) && (words[0].length() <= 2);
for (IcyAbstractAction action : ActionManager.actions)
{
// abort
if (hasWaitingSearch())
return;
// action match filter
final int prio = searchInAction(action, words, shortSearch);
if (prio > 0)
tmpResults.add(new KernelSearchResult(this, action, words, prio));
}
results = tmpResults;
consumer.resultsChanged(this);
}
public static int searchInAction(IcyAbstractAction action, String words[], boolean startWithOnly)
{
int result = 0;
// we accept action which contains all words only
for (String word : words)
{
final int r = searchInAction(action, word, startWithOnly);
// word not found ? --> reject
if (r == 0)
return 0;
result += r;
}
// return mean score
return result / words.length;
}
public static int searchInAction(IcyAbstractAction action, String word, boolean startWithOnly)
{
final String wordlc = word.trim().toLowerCase();
String text;
// text = action.getName();
// if (!StringUtil.isEmpty(text) && text.toLowerCase().startsWith(wordlc))
// return 10;
text = action.getDescription();
if (!StringUtil.isEmpty(text) && text.toLowerCase().startsWith(wordlc))
return 8;
text = action.getLongDescription();
if (!StringUtil.isEmpty(text) && text.toLowerCase().startsWith(wordlc))
return 5;
if (!startWithOnly)
{
// text = action.getName();
// if (!StringUtil.isEmpty(text) && text.toLowerCase().contains(wordlc))
// return 9;
text = action.getDescription();
if (!StringUtil.isEmpty(text) && text.toLowerCase().contains(wordlc))
return 7;
text = action.getLongDescription();
if (!StringUtil.isEmpty(text) && text.toLowerCase().contains(wordlc))
return 3;
}
return 0;
}
}