mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
IDEA-68253 Issue trackers integration. Basic implementation.
This commit is contained in:
@@ -19,6 +19,7 @@
|
||||
*/
|
||||
package com.intellij.util.ui;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
@@ -52,49 +53,46 @@ public class FormBuilder {
|
||||
return new FormBuilder();
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, JComponent component) {
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, @NotNull JComponent component) {
|
||||
return addLabeledComponent(label, component, myVerticalGap, false);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, JComponent component, final int topInset) {
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, @NotNull JComponent component, final int topInset) {
|
||||
return addLabeledComponent(label, component, topInset, false);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, JComponent component, boolean labelOnTop) {
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, @NotNull JComponent component, boolean labelOnTop) {
|
||||
return addLabeledComponent(label, component, myVerticalGap, labelOnTop);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(String labelText, JComponent component) {
|
||||
public FormBuilder addLabeledComponent(@NotNull String labelText, @NotNull JComponent component) {
|
||||
return addLabeledComponent(labelText, component, myVerticalGap, false);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(String labelText, JComponent component, final int topInset) {
|
||||
public FormBuilder addLabeledComponent(@NotNull String labelText, @NotNull JComponent component, final int topInset) {
|
||||
return addLabeledComponent(labelText, component, topInset, false);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(String labelText, JComponent component, boolean labelOnTop) {
|
||||
public FormBuilder addLabeledComponent(@NotNull String labelText, @NotNull JComponent component, boolean labelOnTop) {
|
||||
return addLabeledComponent(labelText, component, myVerticalGap, labelOnTop);
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(String labelText, JComponent component, final int topInset, boolean labelOnTop) {
|
||||
JLabel label = null;
|
||||
if (labelText != null) {
|
||||
label = new JLabel(UIUtil.removeMnemonic(labelText));
|
||||
final int index = UIUtil.getDisplayMnemonicIndex(labelText);
|
||||
if (index != -1) {
|
||||
label.setDisplayedMnemonic(labelText.charAt(index + 1));
|
||||
}
|
||||
label.setLabelFor(component);
|
||||
public FormBuilder addLabeledComponent(@NotNull String labelText, @NotNull JComponent component, final int topInset, boolean labelOnTop) {
|
||||
JLabel label = new JLabel(UIUtil.removeMnemonic(labelText));
|
||||
final int index = UIUtil.getDisplayMnemonicIndex(labelText);
|
||||
if (index != -1) {
|
||||
label.setDisplayedMnemonic(labelText.charAt(index + 1));
|
||||
}
|
||||
label.setLabelFor(component);
|
||||
|
||||
return addLabeledComponent(label, component, topInset, labelOnTop);
|
||||
}
|
||||
|
||||
public FormBuilder addComponent(JComponent component) {
|
||||
public FormBuilder addComponent(@NotNull JComponent component) {
|
||||
return addLabeledComponent((JLabel)null, component, myVerticalGap, false);
|
||||
}
|
||||
|
||||
public FormBuilder addComponent(JComponent component, final int topInset) {
|
||||
public FormBuilder addComponent(@NotNull JComponent component, final int topInset) {
|
||||
return addLabeledComponent((JLabel)null, component, topInset, false);
|
||||
}
|
||||
|
||||
@@ -111,7 +109,7 @@ public class FormBuilder {
|
||||
new Box.Filler(new Dimension(0, height), new Dimension(0, height), new Dimension(Short.MAX_VALUE, height)));
|
||||
}
|
||||
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, JComponent component, int topInset, boolean labelOnTop) {
|
||||
public FormBuilder addLabeledComponent(@Nullable JComponent label, @NotNull JComponent component, int topInset, boolean labelOnTop) {
|
||||
GridBagConstraints c = new GridBagConstraints();
|
||||
topInset = myLineCount > 0 ? topInset : 0;
|
||||
|
||||
|
||||
@@ -388,9 +388,9 @@ public class UIUtil {
|
||||
int defSize = getLabelFont().getSize();
|
||||
switch (size) {
|
||||
case SMALL:
|
||||
return Math.max(defSize - 2f, 11f);
|
||||
return Math.max(defSize - 2f, 10f);
|
||||
case MINI:
|
||||
return Math.max(defSize - 4f, 9f);
|
||||
return Math.max(defSize - 4f, 8f);
|
||||
default:
|
||||
return defSize;
|
||||
}
|
||||
|
||||
@@ -146,11 +146,13 @@
|
||||
<properties/>
|
||||
<border type="none"/>
|
||||
<children>
|
||||
<component id="ae3b0" class="javax.swing.JLabel" binding="myComment">
|
||||
<component id="bb533" class="com.intellij.ui.components.JBLabel" binding="myComment">
|
||||
<constraints>
|
||||
<grid row="2" column="0" row-span="1" col-span="1" vsize-policy="0" hsize-policy="0" anchor="8" fill="0" indent="0" use-parent-layout="false"/>
|
||||
</constraints>
|
||||
<properties>
|
||||
<componentStyle value="SMALL"/>
|
||||
<fontColor value="BRIGHTER"/>
|
||||
<text value="Use..."/>
|
||||
</properties>
|
||||
</component>
|
||||
|
||||
@@ -62,7 +62,7 @@ public class BaseRepositoryEditor<T extends BaseRepository> extends TaskReposito
|
||||
|
||||
private JPanel myCustomPanel;
|
||||
private JBCheckBox myAddCommitMessage;
|
||||
private JLabel myComment;
|
||||
private JBLabel myComment;
|
||||
private JPanel myEditorPanel;
|
||||
|
||||
private boolean myApplying;
|
||||
|
||||
@@ -116,6 +116,7 @@
|
||||
<tasks.repositoryType implementation="com.intellij.tasks.trac.TracRepositoryType"/>
|
||||
<tasks.repositoryType implementation="com.intellij.tasks.fogbugz.FogBugzRepositoryType"/>
|
||||
<tasks.repositoryType implementation="com.intellij.tasks.mantis.MantisRepositoryType"/>
|
||||
<tasks.repositoryType implementation="com.intellij.tasks.connector.WebRepositoryType"/>
|
||||
|
||||
<checkinHandlerFactory implementation="com.intellij.tasks.impl.TaskCheckinHandlerFactory"/>
|
||||
</extensions>
|
||||
|
||||
@@ -0,0 +1,252 @@
|
||||
package com.intellij.tasks.connector;
|
||||
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
import com.intellij.tasks.Comment;
|
||||
import com.intellij.tasks.Task;
|
||||
import com.intellij.tasks.TaskRepositoryType;
|
||||
import com.intellij.tasks.TaskType;
|
||||
import com.intellij.tasks.impl.BaseRepository;
|
||||
import com.intellij.tasks.impl.BaseRepositoryImpl;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.xmlb.annotations.Tag;
|
||||
import icons.TasksIcons;
|
||||
import org.apache.commons.httpclient.HttpClient;
|
||||
import org.apache.commons.httpclient.methods.GetMethod;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/**
|
||||
* User: Evgeny.Zakrevsky
|
||||
* Date: 10/4/12
|
||||
*/
|
||||
@Tag("Web")
|
||||
public class WebRepository extends BaseRepositoryImpl {
|
||||
private String myTasksListURL;
|
||||
private String myTaskPattern;
|
||||
private String myLoginURL;
|
||||
|
||||
final static String SERVER_URL_PLACEHOLDER = "{serverUrl}";
|
||||
final static String USERNAME_PLACEHOLDER = "{username}";
|
||||
final static String PASSWORD_PLACEHOLDER = "{password}";
|
||||
final static String ID_PLACEHOLDER = "{id}";
|
||||
final static String SUMMARY_PLACEHOLDER = "{summary}";
|
||||
final static String DESCRIPTION_PLACEHOLDER = "{description}";
|
||||
final static String PAGE_PLACEHOLDER = "{page}";
|
||||
|
||||
//final Map<String, String> myPlaceholder2Value = new HashMap<String, String>();
|
||||
|
||||
@SuppressWarnings({"UnusedDeclaration"})
|
||||
public WebRepository() {
|
||||
}
|
||||
|
||||
public WebRepository(final TaskRepositoryType type) {
|
||||
super(type);
|
||||
}
|
||||
|
||||
public WebRepository(final WebRepository other) {
|
||||
super(other);
|
||||
myTasksListURL = other.getTasksListURL();
|
||||
myTaskPattern = other.getTaskPattern();
|
||||
myLoginURL = other.getLoginURL();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Task[] getIssues(@Nullable final String query, final int max, final long since) throws Exception {
|
||||
final HttpClient httpClient = getHttpClient();
|
||||
login(httpClient);
|
||||
|
||||
final GetMethod getMethod = new GetMethod(getFullTasksUrl());
|
||||
httpClient.executeMethod(getMethod);
|
||||
final String response = getMethod.getResponseBodyAsString(Integer.MAX_VALUE);
|
||||
|
||||
final String taskPatternWithoutPlaceholders = myTaskPattern.replaceAll("\\{.+?\\}", "");
|
||||
Matcher matcher = Pattern
|
||||
.compile(taskPatternWithoutPlaceholders,
|
||||
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL | Pattern.UNICODE_CASE | Pattern.CANON_EQ)
|
||||
.matcher(response);
|
||||
|
||||
final List<String> placeholders = getPlaceholders(myTaskPattern);
|
||||
if (matcher.groupCount() != 2 || !placeholders.contains(ID_PLACEHOLDER) || !placeholders.contains(SUMMARY_PLACEHOLDER)) {
|
||||
throw new Exception("Incorrect Task Pattern");
|
||||
}
|
||||
|
||||
List<Task> tasks = new ArrayList<Task>();
|
||||
while (matcher.find()) {
|
||||
final String id = matcher.group(placeholders.indexOf(ID_PLACEHOLDER) + 1);
|
||||
final String description = matcher.group(placeholders.indexOf(SUMMARY_PLACEHOLDER) + 1);
|
||||
tasks.add(new Task() {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String getSummary() {
|
||||
return description;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Comment[] getComments() {
|
||||
return new Comment[0];
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Icon getIcon() {
|
||||
return TasksIcons.Other;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public TaskType getType() {
|
||||
return TaskType.OTHER;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Date getUpdated() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Date getCreated() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isClosed() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isIssue() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public String getIssueUrl() {
|
||||
return null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
return tasks.toArray(new Task[tasks.size()]);
|
||||
}
|
||||
|
||||
private void login(final HttpClient httpClient) throws IOException {
|
||||
final GetMethod method = new GetMethod(getFullLoginUrl());
|
||||
httpClient.executeMethod(method);
|
||||
}
|
||||
|
||||
private static List<String> getPlaceholders(String value) {
|
||||
if (value == null) {
|
||||
return ContainerUtil.emptyList();
|
||||
}
|
||||
|
||||
List<String> vars = new ArrayList<String>();
|
||||
Matcher m = Pattern.compile("\\{(.+?)\\}").matcher(value);
|
||||
while (m.find()) {
|
||||
vars.add(m.group(0));
|
||||
}
|
||||
return vars;
|
||||
}
|
||||
|
||||
private String getFullTasksUrl() {
|
||||
return getTasksListURL()
|
||||
.replaceAll(placeholder2regexp(SERVER_URL_PLACEHOLDER), getUrl());
|
||||
}
|
||||
|
||||
private String getFullLoginUrl() {
|
||||
return getLoginURL()
|
||||
.replaceAll(placeholder2regexp(SERVER_URL_PLACEHOLDER), getUrl())
|
||||
.replaceAll(placeholder2regexp(USERNAME_PLACEHOLDER), getUsername())
|
||||
.replaceAll(placeholder2regexp(PASSWORD_PLACEHOLDER), getPassword());
|
||||
}
|
||||
|
||||
private static String placeholder2regexp(String placeholder) {
|
||||
return placeholder.replaceAll("\\{", "\\\\{");
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Task findTask(final String id) throws Exception {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public BaseRepository clone() {
|
||||
return new WebRepository(this);
|
||||
}
|
||||
|
||||
public String getTasksListURL() {
|
||||
return myTasksListURL;
|
||||
}
|
||||
|
||||
public void setTasksListURL(final String tasksListURL) {
|
||||
myTasksListURL = tasksListURL;
|
||||
}
|
||||
|
||||
public String getTaskPattern() {
|
||||
return myTaskPattern;
|
||||
}
|
||||
|
||||
public void setTaskPattern(final String taskPattern) {
|
||||
myTaskPattern = taskPattern;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(final Object o) {
|
||||
if (this == o) return true;
|
||||
if (!(o instanceof WebRepository)) return false;
|
||||
if (!super.equals(o)) return false;
|
||||
WebRepository that = (WebRepository)o;
|
||||
if (!Comparing.equal(getTasksListURL(), that.getTasksListURL())) return false;
|
||||
if (!Comparing.equal(getTaskPattern(), that.getTaskPattern())) return false;
|
||||
if (!Comparing.equal(getLoginURL(), that.getLoginURL())) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public CancellableConnection createCancellableConnection() {
|
||||
return new CancellableConnection() {
|
||||
@Override
|
||||
protected void doTest() throws Exception {
|
||||
final Task[] issues = getIssues("", 0, 0);
|
||||
if (issues.length == 0) throw new Exception("Tasks not found. Probably, you don't login.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void cancel() {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public String getLoginURL() {
|
||||
return myLoginURL;
|
||||
}
|
||||
|
||||
public void setLoginURL(final String loginURL) {
|
||||
myLoginURL = loginURL;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,77 @@
|
||||
package com.intellij.tasks.connector;
|
||||
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.tasks.config.BaseRepositoryEditor;
|
||||
import com.intellij.ui.components.JBLabel;
|
||||
import com.intellij.util.Consumer;
|
||||
import com.intellij.util.ui.FormBuilder;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
/**
|
||||
* User: Evgeny.Zakrevsky
|
||||
* Date: 10/4/12
|
||||
*/
|
||||
public class WebRepositoryEditor extends BaseRepositoryEditor<WebRepository> {
|
||||
private JBLabel myTasksListURLLabel;
|
||||
private JBLabel myTaskPatternLabel;
|
||||
private JTextField myTasksListURLText;
|
||||
private JTextField myTaskPatternText;
|
||||
private JBLabel myLoginURLLabel;
|
||||
private JTextField myLoginURLText;
|
||||
|
||||
public WebRepositoryEditor(final Project project, final WebRepository repository, final Consumer<WebRepository> changeListener) {
|
||||
super(project, repository, changeListener);
|
||||
myUrlLabel.setText("{serverUrl}:");
|
||||
myUsernameLabel.setText("{username}:");
|
||||
myPasswordLabel.setText("{password}:");
|
||||
|
||||
//setAnchor(myUsernameLabel);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void apply() {
|
||||
myRepository.setTasksListURL(myTasksListURLText.getText());
|
||||
myRepository.setTaskPattern(myTaskPatternText.getText());
|
||||
myRepository.setLoginURL(myLoginURLText.getText());
|
||||
super.apply();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
protected JComponent createCustomPanel() {
|
||||
myTasksListURLLabel = new JBLabel("Tasks List URL:", SwingConstants.RIGHT);
|
||||
myTasksListURLText = new JTextField(myRepository.getTasksListURL());
|
||||
installListener(myTasksListURLText);
|
||||
myTaskPatternLabel = new JBLabel("Task Pattern:", SwingConstants.RIGHT);
|
||||
myTaskPatternText = new JTextField(myRepository.getTaskPattern());
|
||||
installListener(myTaskPatternText);
|
||||
myLoginURLLabel = new JBLabel("Login URL:", SwingConstants.RIGHT);
|
||||
myLoginURLText = new JTextField(myRepository.getLoginURL());
|
||||
installListener(myLoginURLText);
|
||||
return FormBuilder.createFormBuilder().setAlignLabelOnRight(true)
|
||||
.addVerticalGap(8)
|
||||
.addLabeledComponent(myTasksListURLLabel, myTasksListURLText)
|
||||
.addLabeledComponent(new JLabel(), new JBLabel("Available placeholders: " + WebRepository.SERVER_URL_PLACEHOLDER, UIUtil.ComponentStyle.SMALL,
|
||||
UIUtil.FontColor.BRIGHTER), 1)
|
||||
.addLabeledComponent(myTaskPatternLabel, myTaskPatternText, 8)
|
||||
.addLabeledComponent(new JLabel(), new JBLabel("Task pattern should be a regexp with two matching group: ({id}.+?) and ({summary}.+?)",
|
||||
UIUtil.ComponentStyle.SMALL, UIUtil.FontColor.BRIGHTER), 1)
|
||||
.addLabeledComponent(myLoginURLLabel, myLoginURLText, 8)
|
||||
.addLabeledComponent(new JLabel(), new JBLabel("Available placeholders: " + WebRepository.SERVER_URL_PLACEHOLDER + ", " +
|
||||
WebRepository.USERNAME_PLACEHOLDER + ", " + WebRepository.PASSWORD_PLACEHOLDER, UIUtil.ComponentStyle.SMALL,
|
||||
UIUtil.FontColor.BRIGHTER), 1)
|
||||
.addVerticalGap(8)
|
||||
.getPanel();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAnchor(@Nullable final JComponent anchor) {
|
||||
super.setAnchor(anchor);
|
||||
myTasksListURLLabel.setAnchor(anchor);
|
||||
myTaskPatternLabel.setAnchor(anchor);
|
||||
myLoginURLLabel.setAnchor(anchor);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
package com.intellij.tasks.connector;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.tasks.TaskRepository;
|
||||
import com.intellij.tasks.config.TaskRepositoryEditor;
|
||||
import com.intellij.tasks.impl.BaseRepositoryType;
|
||||
import com.intellij.util.Consumer;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
/**
|
||||
* User: Evgeny.Zakrevsky
|
||||
* Date: 10/4/12
|
||||
*/
|
||||
public class WebRepositoryType extends BaseRepositoryType<WebRepository> {
|
||||
@NotNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return "Web Repository";
|
||||
}
|
||||
|
||||
@Override
|
||||
public Icon getIcon() {
|
||||
return AllIcons.General.Web;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public TaskRepository createRepository() {
|
||||
return new WebRepository(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<WebRepository> getRepositoryClass() {
|
||||
return WebRepository.class;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public TaskRepositoryEditor createEditor(final WebRepository repository,
|
||||
final Project project,
|
||||
final Consumer<WebRepository> changeListener) {
|
||||
return new WebRepositoryEditor(project, repository, changeListener);
|
||||
}
|
||||
}
|
||||
@@ -16,12 +16,19 @@ public class TasksIcons {
|
||||
public static final Icon Bug = load("/icons/bug.png"); // 16x16
|
||||
public static final Icon Exception = load("/icons/exception.png"); // 16x16
|
||||
public static final Icon Feature = load("/icons/feature.png"); // 16x16
|
||||
public static final Icon Other = load("/icons/other.png"); // 16x16
|
||||
public static final Icon Unknown = load("/icons/unknown.png"); // 16x16
|
||||
public static final Icon SavedContext = load("/icons/savedContext.png"); // 16x16
|
||||
|
||||
public static final Icon Fogbugz = load("/icons/fogbugz.png"); // 16x16
|
||||
public static final Icon Github = load("/icons/github.png"); // 16x16
|
||||
public static final Icon Lighthouse = load("/icons/lighthouse.gif"); // 16x16
|
||||
public static final Icon Mantis = load("/icons/mantis.png"); // 16x16
|
||||
public static final Icon Other = load("/icons/other.png"); // 16x16
|
||||
|
||||
public static final Icon Pivotal = load("/icons/pivotal.png"); // 16x16
|
||||
public static final Icon Redmine = load("/icons/redmine.png"); // 16x16
|
||||
public static final Icon Trac = load("/icons/trac.png"); // 16x16
|
||||
public static final Icon Youtrack = load("/icons/youtrack.png"); // 16x16
|
||||
|
||||
public static class Pivotal {
|
||||
public static final Icon Bug = load("/icons/pivotal/bug.png"); // 14x14
|
||||
public static final Icon Chore = load("/icons/pivotal/chore.png"); // 14x14
|
||||
@@ -29,10 +36,4 @@ public class TasksIcons {
|
||||
public static final Icon Release = load("/icons/pivotal/release.png"); // 14x14
|
||||
|
||||
}
|
||||
public static final Icon Pivotal = load("/icons/pivotal.png"); // 16x16
|
||||
public static final Icon Redmine = load("/icons/redmine.png"); // 16x16
|
||||
public static final Icon SavedContext = load("/icons/savedContext.png"); // 16x16
|
||||
public static final Icon Trac = load("/icons/trac.png"); // 16x16
|
||||
public static final Icon Unknown = load("/icons/unknown.png"); // 16x16
|
||||
public static final Icon Youtrack = load("/icons/youtrack.png"); // 16x16
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user