| <!doctype html> |
| <html class="no-js" lang="en" dir="ltr"> |
| <head> |
| <meta charset="utf-8"> |
| <meta http-equiv="x-ua-compatible" content="ie=edge"> |
| <title>NetBeans Code Snippet Module Tutorial</title> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <meta name="description" content="NetBeans Code Snippet Module Tutorial - Apache NetBeans"> |
| <meta name="author" content="Apache NetBeans"> |
| <meta name="description" content="NetBeans Code Snippet Module Tutorial - Apache NetBeans"> |
| <meta name="keywords" content="Apache NetBeans Platform, Platform Tutorials, NetBeans Code Snippet Module Tutorial"> |
| <meta name="generator" content="Apache NetBeans"> |
| <link rel="stylesheet" href="../../../../_/css/font-awesome.min.css"> |
| <link rel="alternate" type="application/atom+xml" title="Apache NetBeans Blog" href="https://netbeans.apache.org/blogs/atom" /> |
| <link rel="stylesheet" href="../../../../_/css/highlightjs/default.min.css"> |
| <link rel="stylesheet" href="../../../../_/css/netbeans.css"> |
| <link rel="apple-touch-icon" sizes="180x180" href="../../../../_/images/fav/apple-touch-icon.png"> |
| <link rel="icon" type="image/png" sizes="32x32" href="../../../../_/images/fav/favicon-32x32.png"> |
| <link rel="icon" type="image/png" sizes="16x16" href="../../../../_/images/fav/favicon-16x16.png"> |
| <link rel="manifest" href="../../../../_/images/fav/site.webmanifest"> |
| <link rel="mask-icon" href="../../../../_/images/fav/safari-pinned-tab.svg" color="#5bbad5"> |
| <meta name="msapplication-TileColor" content="#ffc40d"> |
| <meta name="theme-color" content="#ffffff"> |
| <link href="../../../../_/css/font-open-sans.css" rel="stylesheet"> |
| <!-- |
| Licensed to the Apache Software Foundation (ASF) under one |
| or more contributor license agreements. See the NOTICE file |
| distributed with this work for additional information |
| regarding copyright ownership. The ASF licenses this file |
| to you under the Apache License, Version 2.0 (the |
| "License"); you may not use this file except in compliance |
| with the License. You may obtain a copy of the License at |
| http://www.apache.org/licenses/LICENSE-2.0 |
| Unless required by applicable law or agreed to in writing, |
| software distributed under the License is distributed on an |
| "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| KIND, either express or implied. See the License for the |
| specific language governing permissions and limitations |
| under the License. |
| --> |
| </head> |
| <body> |
| <div class="title-bar" data-responsive-toggle="responsive-menu" data-hide-for="medium"> |
| <button type="button" data-toggle="responsive-menu"><i style='font-size: 32px; color: #fff; padding: 8px' class='fa fa-bars'></i></button> |
| <div class="title-bar-title">Apache NetBeans</div> |
| </div> |
| <div class="top-bar" id="responsive-menu"> |
| <div class='top-bar-left'> |
| <a class='title' href="../../../../index.html"><img src='../../../../_/images/apache-netbeans.svg' style='padding: 8px; height: 48px;'> Apache NetBeans</a> |
| </div> |
| <div class="top-bar-right"> |
| <ul class="vertical medium-horizontal menu" data-responsive-menu="drilldown medium-dropdown"> |
| <li> <input id="search-input" type="text" placeholder="Search the docs"> </li> |
| <li> <a href="../../../../front/main/community">Community</a> </li> |
| <li> <a href="../../../../front/main/participate">Participate</a> </li> |
| <li> <a href="../../../../front/main/blogs">Blog</a></li> |
| <li> <a href="../../../../front/main/help">Get Help</a> </li> |
| <li> <a href="https://plugins.netbeans.apache.org/">Plugins</a> </li> |
| <li> <a href="../../../../front/main/download">Download</a> </li> |
| </ul> |
| </div> |
| </div> |
| |
| <!-- src/templates/news --> |
| <section class="hero news alternate"> |
| <div class='grid-container'> |
| <div class='cell'> |
| <div class="annotation">Latest release</div> |
| <h1>Apache NetBeans 27</h1> |
| <p><a class="button success" href="../../../../front/main/download/nb27">Download</a></p> |
| </div> |
| </div> |
| </section> |
| <div class='grid-container main-content tutorial'> |
| <h1 class="sect0">NetBeans Code Snippet Module Tutorial</h1> |
| <div class="sectionbody"> |
| <div class="admonitionblock note"> |
| <table> |
| <tbody><tr> |
| <td class="icon"><i class="fa icon-note" title="Note"></i></td> |
| <td class="content">This tutorial needs a review. |
| You can <a href="https://github.com/apache/netbeans-antora-tutorials/edit/main/modules/ROOT/pages/tutorials/nbm-palette-api1.adoc" title="Edit this tutorial in github">edit it in GitHub </a> |
| following these <a href="../../../../tutorial/main/kb/docs/contributing">contribution guidelines.</a></td> |
| </tr></tbody> |
| </table> |
| </div> |
| </div> |
| <div id="toc" class="toc"> |
| <div id="toctitle"></div> |
| <ul class="sectlevel1"> |
| <li><a href="#_introduction_to_code_snippets">Introduction to Code Snippets</a></li> |
| <li><a href="#_scenario_1_simple_palette_items">Scenario 1: Simple Palette Items</a> |
| <ul class="sectlevel2"> |
| <li><a href="#_creating_the_module_project">Creating the Module Project</a></li> |
| <li><a href="#_defining_and_registering_the_code_snippet">Defining and Registering the Code Snippet</a></li> |
| </ul> |
| </li> |
| <li><a href="#_scenario_2_complex_palette_items">Scenario 2: Complex Palette Items</a> |
| <ul class="sectlevel2"> |
| <li><a href="#_creating_the_module_project_2">Creating the Module Project</a></li> |
| <li><a href="#_specifying_the_modules_dependencies">Specifying the Module’s Dependencies</a></li> |
| <li><a href="#_coding_the_code_snippet">Coding the Code Snippet</a></li> |
| <li><a href="#_defining_the_insertion">Defining the Insertion</a></li> |
| <li><a href="#_declaring_the_code_snippet">Declaring the Code Snippet</a></li> |
| <li><a href="#_registering_the_code_snippet">Registering the Code Snippet</a></li> |
| <li><a href="#_building_and_installing_the_code_snippet">Building and Installing the Code Snippet</a></li> |
| <li><a href="#_adding_a_customizer">Adding a Customizer</a></li> |
| </ul> |
| </li> |
| <li><a href="#_next_steps">Next Steps</a></li> |
| </ul> |
| </div> |
| <div id="preamble"> |
| <div class="sectionbody"> |
| <div class="paragraph"> |
| <p>This tutorial demonstrates how to create and add code snippets to the HTML/JSP Component Palette. Code snippets are small pieces of code that can be dragged from a component palette and dropped in the Source Editor. They serve to speed up coding. The HTML/JSP Component Palette has several code snippets already, but you might want to add some additional ones and share them with others.</p> |
| </div> |
| <div class="ulist"> |
| <ul> |
| <li> |
| <p>Scenario 1: Simple Palette Items</p> |
| </li> |
| <li> |
| <p>Scenario 2: Complex Palette Items</p> |
| </li> |
| </ul> |
| </div> |
| <div class="paragraph"> |
| <p>For troubleshooting purposes, you are welcome to download the <a href="http://web.archive.org/web/20170409072842/http://java.net/projects/nb-api-samples/show/versions/8.0/tutorials/palette">completed tutorial source code</a>.</p> |
| </div> |
| </div> |
| </div> |
| <div class="sect1"> |
| <h2 id="_introduction_to_code_snippets"><a class="anchor" href="#_introduction_to_code_snippets"></a>Introduction to Code Snippets</h2> |
| <div class="sectionbody"> |
| <div class="paragraph"> |
| <p>To create a code snippet, you use the <a href="https://bits.netbeans.org/dev/javadoc/org-netbeans-spi-palette/overview-summary.html">NetBeans Palette API</a>. A code snippet requires the following files:</p> |
| </div> |
| <div class="ulist"> |
| <ul> |
| <li> |
| <p>A Java class that defines the piece of code to be dragged into the Source Editor.</p> |
| </li> |
| <li> |
| <p>A display name for the palette item.</p> |
| </li> |
| <li> |
| <p>A tooltip for the palette item.</p> |
| </li> |
| <li> |
| <p>A 16x16 pixel image for the 'Small Icon' display.</p> |
| </li> |
| <li> |
| <p>A 32x32 pixel image for the 'Big Icon' display.</p> |
| </li> |
| </ul> |
| </div> |
| <div class="paragraph"> |
| <p>After you have created or added the above files to the NetBeans module, you declare them in a resource declaration XML file, which you register in the NetBeans System Filesystem by using the <code>layer.xml</code> file.</p> |
| </div> |
| <div class="paragraph"> |
| <p>You will learn about two different scenarios in this tutorial. The first scenario is simple, requiring no coding, and is useful if you do not need a customizer to appear when the palette item is dropped. The second scenario is more complex, and therefore more flexible, requiring you to provide Java code to define a customizer.</p> |
| </div> |
| </div> |
| </div> |
| <div class="sect1"> |
| <h2 id="_scenario_1_simple_palette_items"><a class="anchor" href="#_scenario_1_simple_palette_items"></a>Scenario 1: Simple Palette Items</h2> |
| <div class="sectionbody"> |
| <div class="paragraph"> |
| <p>Before you start writing the module, you have to make sure you that your project is set up correctly. The IDE provides a wizard that sets up all the basic files needed for a module.</p> |
| </div> |
| <div class="sect2"> |
| <h3 id="_creating_the_module_project"><a class="anchor" href="#_creating_the_module_project"></a>Creating the Module Project</h3> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Choose File > New Project (Ctrl+Shift+N). Under Categories, select NetBeans Modules. Under Projects, select Module. Click Next.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>In the Name and Location panel, type <code>NewSnippets1</code> in the Project Name field. Change the Project Location to any directory on your computer. Click Next.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>In the Basic Module Configuration panel, type <code>org.netbeans.modules.newsnippets1</code> in Code Name Base. Click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="paragraph"> |
| <p>The IDE creates the <code>NewSnippets1</code> project. The project contains all of your sources and project metadata, such as the project’s Ant build script. The project opens in the IDE. You can view its logical structure in the Projects window (Ctrl-1) and its file structure in the Files window (Ctrl-2).</p> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_defining_and_registering_the_code_snippet"><a class="anchor" href="#_defining_and_registering_the_code_snippet"></a>Defining and Registering the Code Snippet</h3> |
| <div class="paragraph"> |
| <p>You need to create an XML file that defines the code snippet, together with a registration in the XML layer file.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Right-click the <code>org.netbeans.modules.newsnippets1</code> package, choose New | Other and then Java | Java Package Info. Click Next and then Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Right-click the Libraries node in the Projects window, click Add Module Dependency, and set a dependency on Common Palette.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>Define the <code>package-info.java</code> class as follows.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java"><a href="https://bits.netbeans.org/dev/javadoc/org-netbeans-spi-palette/org/netbeans/spi/palette/PaletteItemRegistration.html">@PaletteItemRegistration</a> |
| ( |
| paletteid = "HTMLPalette", |
| category = "HTML", |
| itemid = "BR", |
| icon32 = "org/netbeans/modules/newsnippets1/BR32.png", |
| icon16 = "org/netbeans/modules/newsnippets1/BR16.png", |
| body = "<br>", |
| name = "New Line", |
| tooltip = "<br>") |
| package org.netbeans.modules.newsnippets1; |
| |
| import org.netbeans.spi.palette.PaletteItemRegistration;</code></pre> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="4"> |
| <li> |
| <p>Add two icons to the module, such as these below, in locations defined by the <code>icon16</code> element and the <code>icon32</code> element above:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_BR32.png" alt="codesnippet BR32"> |
| </div> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_BR16.png" alt="codesnippet BR16"> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="5"> |
| <li> |
| <p>Compile the file or build the module. Then open the Files window (Ctrl-2) and go to build/classes/META-INF/generated-layer.xml and notice that the following XML tags have been generated, which register your new palette item, via the annotation you created above.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-html hljs" data-lang="html"><?xml version="1.0" encoding="UTF-8"?> |
| <!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.2//EN" |
| "http://www.netbeans.org/dtds/filesystem-1_2.dtd"> |
| <filesystem> |
| <folder name="HTMLPalette"> |
| <folder name="HTML"> |
| <file name="BR.xml"> |
| <![CDATA[<!DOCTYPE editor_palette_item |
| PUBLIC '-//NetBeans//Editor Palette Item 1.1//EN' |
| 'http://www.netbeans.org/dtds/editor-palette-item-1_1.dtd'> |
| <editor_palette_item version="1.1"> |
| <body><![CDATA[<br>]]]]><![CDATA[> </body> |
| <icon16 urlvalue="org/netbeans/modules/newsnippets1/BR16.png" /> |
| <icon32 urlvalue="org/netbeans/modules/newsnippets1/BR32.png" /> |
| <inline-description> |
| <display-name>New Line</display-name> |
| <tooltip> <![CDATA[ <br>]]]]><![CDATA[></tooltip> |
| </inline-description> |
| </editor_palette_item>]]> |
| </file> |
| </folder> |
| </folder> |
| </filesystem></code></pre> |
| </div> |
| </div> |
| <div class="paragraph"> |
| <p>Run the module. Open an HTML file. In the Palette (Ctrl-Shift-8), notice an item named "New Line". Drag it into the HTML file and drop it. You should see a BR tag added at the point where you dropped the item.</p> |
| </div> |
| </div> |
| </div> |
| </div> |
| <div class="sect1"> |
| <h2 id="_scenario_2_complex_palette_items"><a class="anchor" href="#_scenario_2_complex_palette_items"></a>Scenario 2: Complex Palette Items</h2> |
| <div class="sectionbody"> |
| <div class="paragraph"> |
| <p>Before you start writing the module, you have to make sure you that your project is set up correctly. The IDE provides a wizard that sets up all the basic files needed for a module.</p> |
| </div> |
| <div class="sect2"> |
| <h3 id="_creating_the_module_project_2"><a class="anchor" href="#_creating_the_module_project_2"></a>Creating the Module Project</h3> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Choose File > New Project (Ctrl+Shift+N). Under Categories, select NetBeans Modules. Under Projects, select Module. Click Next.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>In the Name and Location panel, type <code>NewSnippets2</code> in the Project Name field. Change the Project Location to any directory on your computer. Click Next.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>In the Basic Module Configuration panel, type <code>org.netbeans.modules.newsnippets2</code> in Code Name Base. Click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="paragraph"> |
| <p>The IDE creates the <code>NewSnippets2</code> project. The project contains all of your sources and project metadata, such as the project’s Ant build script. The project opens in the IDE. You can view its logical structure in the Projects window (Ctrl-1) and its file structure in the Files window (Ctrl-2).</p> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_specifying_the_modules_dependencies"><a class="anchor" href="#_specifying_the_modules_dependencies"></a>Specifying the Module’s Dependencies</h3> |
| <div class="paragraph"> |
| <p>You will need to use several classes that belong to the <a href="https://bits.netbeans.org/dev/javadoc/index.html">NetBeans APIs</a>. Each has to be declared as a module dependency. Use the Project Properties dialog box for this purpose, as described below.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>In the Projects window, right-click the <code>NewSnippets2</code> project node and choose Properties. In the Project Properties dialog box, click Libraries.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="paragraph"> |
| <p>1. |
| For each of the following, click "Add…​", select the name from the Module list, and then click OK to confirm it:</p> |
| </div> |
| <div class="ulist"> |
| <ul> |
| <li> |
| <p>Common Palette</p> |
| </li> |
| <li> |
| <p>Text API</p> |
| </li> |
| <li> |
| <p>Utilities API</p> |
| </li> |
| </ul> |
| </div> |
| <div class="paragraph"> |
| <p>Click OK to exit the Project Properties dialog box.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>In the Projects window, expand the Important Files node, double-click the Project Metadata node, and note that the APIs you selected have been declared as module dependencies.</p> |
| </li> |
| </ol> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_coding_the_code_snippet"><a class="anchor" href="#_coding_the_code_snippet"></a>Coding the Code Snippet</h3> |
| <div class="paragraph"> |
| <p>In this section, you create <code>BR.java</code> , which defines a code snippet for an HTML line break. By implementing the <code> <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html">ActiveEditorDrop</a></code> class, you let the NetBeans APIs provide the infrastructure for a palette item for NetBeans editors. You also create <code>HTMLPaletteUtilities.java</code> , which defines the insertion of the tag in the editor.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Right-click the <code>org.netbeans.modules.newsnippets2</code> node and choose New > Java Class. Type <code>BR</code> in Class Name, make sure that the <code>org.netbeans.modules.newsnippets2</code> package is selected in the Package drop-down list, and click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Replace the default content of the <code>BR.java</code> file with the following:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">package org.netbeans.modules.newsnippets2; |
| |
| import javax.swing.text.BadLocationException; |
| import javax.swing.text.JTextComponent; |
| import org.netbeans.modules.newsnippets2.HTMLPaletteUtilities; |
| import <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html">org.openide.text.ActiveEditorDrop</a>; |
| |
| public class BR implements <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html">ActiveEditorDrop</a> { |
| |
| public BR() { |
| } |
| |
| private String createBody() { |
| String Br = "<br>"; |
| return Br; |
| } |
| |
| @Override |
| public boolean <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html#handleTransfer(javax.swing.text.JTextComponent)">handleTransfer(JTextComponent targetComponent</a>) { |
| String body = createBody(); |
| try { |
| HTMLPaletteUtilities.insert(body, targetComponent); |
| } catch (BadLocationException ble) { |
| return false; |
| } |
| return true; |
| } |
| |
| }</code></pre> |
| </div> |
| </div> |
| <div class="paragraph"> |
| <p>A red error message remains because you have not created the <code>HTMLPaletteUtilities</code> class yet, which you will do in the next section.</p> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_defining_the_insertion"><a class="anchor" href="#_defining_the_insertion"></a>Defining the Insertion</h3> |
| <div class="paragraph"> |
| <p>In this section, you create the <code>HTMLPaletteUtilities</code> class, which defines the place where the snippet will be dropped.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Right-click the <code>org.netbeans.modules.newsnippets2</code> node and choose New > Java Class. Type <code>HTMLPaletteUtilities</code> in Class Name, make sure that the <code>org.netbeans.modules.newsnippets2</code> package is selected in the Package drop-down list, and click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Replace the default content of the <code>HTMLPaletteUtilities.java</code> file with the following:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">package org.netbeans.modules.newsnippets2; |
| |
| import javax.swing.text.BadLocationException; |
| import javax.swing.text.Caret; |
| import javax.swing.text.Document; |
| import javax.swing.text.JTextComponent; |
| import javax.swing.text.StyledDocument; |
| import <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/NbDocument.html">org.openide.text.NbDocument</a>; |
| |
| public class HTMLPaletteUtilities { |
| |
| public static void insert(final String s, final JTextComponent target) throws BadLocationException { |
| |
| final StyledDocument doc = (StyledDocument)target.getDocument(); |
| |
| class AtomicChange implements Runnable { |
| |
| @Override |
| public void run() { |
| Document value = target.getDocument(); |
| if (value == null) |
| return; |
| try { |
| insert(s, target, doc); |
| } catch (BadLocationException e) {} |
| } |
| } |
| |
| try { |
| <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/NbDocument.html#runAtomicAsUser(javax.swing.text.StyledDocument,%20java.lang.Runnable)">NbDocument.runAtomicAsUser(doc, new AtomicChange())</a>; |
| } catch (BadLocationException ex) {} |
| |
| } |
| |
| private static int insert(String s, JTextComponent target, Document doc) throws BadLocationException { |
| |
| int start = -1; |
| |
| try { |
| |
| <strong>//firstly, find selected text range:</strong> |
| Caret caret = target.getCaret(); |
| int p0 = Math.min(caret.getDot(), caret.getMark()); |
| int p1 = Math.max(caret.getDot(), caret.getMark()); |
| doc.remove(p0, p1 - p0); |
| |
| <strong>//then, replace selected text range with the inserted one:</strong> |
| start = caret.getDot(); |
| doc.insertString(start, s, null); |
| |
| } catch (BadLocationException ble) {} |
| |
| return start; |
| |
| } |
| |
| }</code></pre> |
| </div> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_declaring_the_code_snippet"><a class="anchor" href="#_declaring_the_code_snippet"></a>Declaring the Code Snippet</h3> |
| <div class="paragraph"> |
| <p>The NetBeans Editor Palette Item DTD is used to declare the <code>ActiveEditorDrop</code> class, the icons, the display name, and the tooltip.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Right-click the <code>org.netbeans.modules.newsnippets2</code> package node and choose New > Other. Select XML Document in the XML folder and click Next. Type <code>BR</code> in File Name. Type <code>\resources</code> at the end of <code>src\org\netbeans\modules\newsnippets2</code> in Folder. Click Next and then click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Replace the default content of the <code>BR.xml</code> file with the following:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-xml hljs" data-lang="xml"><?xml version="1.0" encoding="UTF-8"?> |
| <!DOCTYPE editor_palette_item PUBLIC "-//NetBeans//Editor Palette Item 1.0//EN" |
| "https://netbeans.org/dtds/editor-palette-item-1_0.dtd"> |
| |
| <editor_palette_item version="1.0"> |
| |
| <class name="org.netbeans.modules.newsnippets2.BR" /> |
| |
| <icon16 urlvalue="org/netbeans/modules/newsnippets2/resources/BR16.png" /> |
| <icon32 urlvalue="org/netbeans/modules/newsnippets2/resources/BR32.png" /> |
| |
| <description localizing-bundle="org.netbeans.modules.newsnippets2.Bundle" |
| display-name-key="NAME_html-BR" |
| tooltip-key="HINT_html-BR" /> |
| |
| </editor_palette_item></code></pre> |
| </div> |
| </div> |
| <div class="paragraph"> |
| <p>Instead of the above, you can use the 1.1 DTD, where you can define the display name and tooltip without using a properties file. Below, only the difference with the previous XML file definition is highlighted:</p> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-xml hljs" data-lang="xml"><?xml version="1.0" encoding="UTF-8"?> |
| <!DOCTYPE editor_palette_item PUBLIC "<strong>-//NetBeans//Editor Palette Item 1.1//EN</strong>" |
| "https://netbeans.org/dtds/<strong>editor-palette-item-1_1.dtd</strong>"> |
| |
| <editor_palette_item version="1.0"> |
| |
| <class name="org.netbeans.modules.newsnippets2.BR" /> |
| |
| <icon16 urlvalue="org/netbeans/modules/newsnippets2/resources/BR16.png" /> |
| <icon32 urlvalue="org/netbeans/modules/newsnippets2/resources/BR32.png" /> |
| |
| <strong><inline-description> |
| <display-name>New Line</display-name> |
| <tooltip> <![CDATA[ <br> ]]></tooltip> |
| </inline-description></strong> |
| |
| </editor_palette_item></code></pre> |
| </div> |
| </div> |
| <div class="admonitionblock note"> |
| <table> |
| <tr> |
| <td class="icon"> |
| <i class="fa icon-note" title="Note"></i> |
| </td> |
| <td class="content"> |
| You can choose either of the two approaches above, depending on your requirements. |
| </td> |
| </tr> |
| </table> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>Add a 16x16 pixel icon and a 32x32 pixel icon to the new <code>resources</code> folder. Name them <code>BR16.png</code> and <code>BR32.png</code> . They can also be in other icon formats, such as GIF or JPG. Make sure that the resource is correctly declared in the <code>BR.xml</code> file. You can right-click them here and then save them to your module’s source structure:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_BR32.png" alt="codesnippet BR32"> |
| </div> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_BR16.png" alt="codesnippet BR16"> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="4"> |
| <li> |
| <p>If you want to use a properties file for declaring the palette item’s display name and tooltip, which implies that you are using the 1.0 DTD, add the following to the <code>Bundle.properties</code> file:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_bundle-60.png" alt="codesnippet bundle 60"> |
| </div> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_registering_the_code_snippet"><a class="anchor" href="#_registering_the_code_snippet"></a>Registering the Code Snippet</h3> |
| <div class="paragraph"> |
| <p>The <code>layer.xml</code> file registers the user interface elements of your module in your application, which in this case is the IDE. Here, we need to register the palette item in the <code>layer.xml</code> file so that the item will appear in the HTML Palette.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Right-click the <code>org.netbeans.modules.newsnippets2</code> package node and choose New > Other. Select Module Development > XML Layer. Click Next and then click Finish.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Add the following tags to the <code>layer.xml</code> file, between the <code><filesystem></code> tags:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-xml hljs" data-lang="xml"><folder name="HTMLPalette"> |
| <folder name="HTML"> |
| <file name="BR.xml" url="resources/BR.xml"> |
| <attr name="position" intvalue="150"/> |
| </file> |
| </folder> |
| </folder></code></pre> |
| </div> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_building_and_installing_the_code_snippet"><a class="anchor" href="#_building_and_installing_the_code_snippet"></a>Building and Installing the Code Snippet</h3> |
| <div class="paragraph"> |
| <p>Now we need to think about installation and distribution. Install and try out the code snippet, by following the steps below.</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>In the Projects window, right-click the <code>NewSnippets2</code> project and choose Run. The module is built and installed in a new instance of NetBeans IDE.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="2"> |
| <li> |
| <p>Create a new HTML file in the IDE. When the HTML file opens, it displays the Component Palette (Ctrl-Shift-8) with one additional code snippet, called "New Line", with a tooltip that displays the result of drag-and-dropping the item:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_71_result.png" alt="codesnippet 71 result"> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>Drag the 'New Line' item into the Source Editor and notice that a new <code><br></code> tag is inserted at the cursor.</p> |
| </li> |
| </ol> |
| </div> |
| </div> |
| <div class="sect2"> |
| <h3 id="_adding_a_customizer"><a class="anchor" href="#_adding_a_customizer"></a>Adding a Customizer</h3> |
| <div class="paragraph"> |
| <p>Optionally, you can let a <code>JPanel</code> appear when the palette item is dropped. In the <code>JPanel</code> , you can let the user define values for attributes that relate to the snippet that is about to be created. However, note that adding such a customizer is optional. In the case of a line break, which is what we are creating in this tutorial, there are no attributes that relate to the BR tag. For that reason, to illustrate the customizer functionality, we will add a comment before the BR tag, by means of a customizer.</p> |
| </div> |
| <div class="admonitionblock note"> |
| <table> |
| <tr> |
| <td class="icon"> |
| <i class="fa icon-note" title="Note"></i> |
| </td> |
| <td class="content"> |
| If you check out the <code> <a href="https://github.com/apache/netbeans/bdb88f1fa043/html">html</a></code> module from the <a href="https://github.com/apache/netbeans/">NetBeans sources</a>, you will find many examples of customizers in the <code> <a href="https://github.com/apache/netbeans/tree/master/ide/html/src/org/netbeans/modules/html/palette/items">org/netbeans/modules/html/palette/items</a></code> package. |
| </td> |
| </tr> |
| </table> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="1"> |
| <li> |
| <p>Add a dependency on the NetBeans <code> <a href="https://bits.netbeans.org/dev/javadoc/org-openide-dialogs/overview-summary.html">Dialogs API</a></code> and the <a href="https://bits.netbeans.org/dev/javadoc/org-openide-awt/overview-summary.html"> <code>UI Utilities API</code> </a>.</p> |
| </li> |
| </ol> |
| </div> |
| <div class="paragraph"> |
| <p>1. |
| Use the New File dialog (Ctrl-N) to create a <code>JPanel</code> in the <code>org.netbeans.modules.newsnippets2</code> package. Name it <code>BRCustomizer</code> .</p> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="3"> |
| <li> |
| <p>Use the Pallette (Ctrl-Shift-8) to drag and drop a <code>JLabel</code> and a <code>JTextField</code> onto the <code>JPanel</code> and arrange the <code>JPanel</code> as follows:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="imageblock"> |
| <div class="content"> |
| <img src="../../_images/tutorials/codesnippet_customizer-in-palette-60.png" alt="codesnippet customizer in palette 60"> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="4"> |
| <li> |
| <p>You will need to declare the following at the top of the <code>BRCustomizer</code> class:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">private Dialog dialog = null; |
| private DialogDescriptor descriptor = null; |
| private boolean dialogOK = false; |
| |
| private BR br; |
| private JTextComponent target;</code></pre> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="5"> |
| <li> |
| <p>Rewrite the <code>BRCustomizer</code> constructor as follows:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">public BRCustomizer(BR br, JTextComponent target) { |
| this.br = br; |
| this.target = target; |
| |
| initComponents(); |
| }</code></pre> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="6"> |
| <li> |
| <p>In your <code>BRCustomizer</code> class, add this method, so that, in the next steps, you can open the customizer from your <code>ActiveEditorDrop</code> implementation class:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">@NbBundle.Messages({ |
| "LBL_Customizer_InsertPrefix=Insert", |
| "NAME_html-BR=Line Break"}) |
| public boolean showDialog() { |
| dialogOK = false; |
| descriptor = new DialogDescriptor(this, Bundle.LBL_Customizer_InsertPrefix(), true, |
| DialogDescriptor.OK_CANCEL_OPTION, DialogDescriptor.OK_OPTION, |
| new ActionListener() { |
| @Override |
| public void actionPerformed(ActionEvent e) { |
| if (descriptor.getValue().equals(DialogDescriptor.OK_OPTION)) { |
| evaluateInput(); |
| dialogOK = true; |
| } |
| dialog.dispose(); |
| } |
| }); |
| dialog = DialogDisplayer.getDefault().createDialog(descriptor); |
| dialog.setVisible(true); |
| return dialogOK; |
| }</code></pre> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="7"> |
| <li> |
| <p>Define the <code>evaluateInput()</code> method, which is called in the <code>showDialog()</code> method above, as follows:</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">private void evaluateInput() { |
| String comment = jTextField1.getText(); |
| br.setComment(comment); |
| }</code></pre> |
| </div> |
| </div> |
| <div class="olist arabic"> |
| <ol class="arabic" start="8"> |
| <li> |
| <p>Hook your customizer into the <code>ActiveEditorDrop</code> implementation class as follows (only the lines that are changed are highlighted below):</p> |
| </li> |
| </ol> |
| </div> |
| <div class="listingblock"> |
| <div class="content"> |
| <pre class="highlightjs highlight"><code class="language-java hljs" data-lang="java">package org.netbeans.modules.newsnippets2; |
| |
| import javax.swing.text.BadLocationException; |
| import javax.swing.text.JTextComponent; |
| import org.netbeans.modules.newsnippets2.HTMLPaletteUtilities; |
| import <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html">org.openide.text.ActiveEditorDrop</a>; |
| |
| public class BR implements <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html">ActiveEditorDrop</a> { |
| |
| <strong>private String comment = "";</strong> |
| |
| public BR() { |
| } |
| |
| private String createBody() { |
| <strong>comment = getComment(); |
| String Br = "<!-- " + comment + " -->" |
| + "\n <br>";</strong> |
| return Br; |
| } |
| |
| @Override |
| public boolean <a href="https://bits.netbeans.org/dev/javadoc/org-openide-text/org/openide/text/ActiveEditorDrop.html#handleTransfer(javax.swing.text.JTextComponent)">handleTransfer(JTextComponent targetComponent</a>) { |
| |
| <strong>BRCustomizer c = new BRCustomizer(this, targetComponent); |
| boolean accept = c.showDialog(); |
| if (accept) {</strong> |
| String body = createBody(); |
| try { |
| HTMLPaletteUtilities.insert(body, targetComponent); |
| } catch (BadLocationException ble) { |
| <strong>accept = false;</strong> |
| } |
| } |
| <strong>return accept;</strong> |
| |
| } |
| |
| <strong>public String getComment() { |
| return comment; |
| } |
| |
| public void setComment(String comment) { |
| this.comment = comment; |
| }</strong> |
| |
| }</code></pre> |
| </div> |
| </div> |
| <div class="paragraph"> |
| <p>Run the module. Open an HTML file. In the Palette (Ctrl-Shift-8), notice the item named "New Line". Drag it into the HTML file and drop it. You should see your customizer. Enter something, finish the dialog, and the BR tag is added, together with a comment, at the point where you dropped the item.</p> |
| </div> |
| <div class="paragraph"> |
| <p><a href="../../../../front/main/community/mailing-lists/" class="xref page">Send Us Your Feedback</a></p> |
| </div> |
| </div> |
| </div> |
| </div> |
| <div class="sect1"> |
| <h2 id="_next_steps"><a class="anchor" href="#_next_steps"></a>Next Steps</h2> |
| <div class="sectionbody"> |
| <div class="paragraph"> |
| <p>For more information about creating and developing NetBeans modules, see the following resources:</p> |
| </div> |
| <div class="ulist"> |
| <ul> |
| <li> |
| <p><a href="../../kb/docs/platform/" class="xref page">Other Related Tutorials</a></p> |
| </li> |
| <li> |
| <p><a href="https://bits.netbeans.org/dev/javadoc/index.html">NetBeans API Javadoc</a></p> |
| </li> |
| </ul> |
| </div> |
| </div> |
| </div> |
| <section class='tools'> |
| <ul class="menu align-center"> |
| <li><a title="Facebook" href="https://www.facebook.com/NetBeans"><i class="fa fa-md fa-facebook"></i></a></li> |
| <li><a title="Twitter" href="https://twitter.com/netbeans"><i class="fa fa-md fa-twitter"></i></a></li> |
| <li><a title="Github" href="https://github.com/apache/netbeans"><i class="fa fa-md fa-github"></i></a></li> |
| <li><a title="YouTube" href="https://www.youtube.com/user/netbeansvideos"><i class="fa fa-md fa-youtube"></i></a></li> |
| <li><a title="Atom Feed" href="https://netbeans.apache.org/blogs/atom"><i class="fa fa-mf fa-rss"></i></a></li> |
| <li><a title="Slack" href="https://tinyurl.com/netbeans-slack-signup/"><i class="fa fa-md fa-slack"></i></a></li> |
| <li><a title="Issues" href="https://github.com/apache/netbeans/issues"><i class="fa fa-mf fa-bug"></i></a></li> |
| </ul> |
| <ul class="menu align-center"> |
| <li><a href="https://github.com/apache/netbeans-antora-tutorials/edit/main/modules/ROOT/pages/tutorials/nbm-palette-api1.adoc" title="See this page in github"><i class="fa fa-md fa-edit"></i> See this page in GitHub.</a></li> |
| </ul> |
| </section> |
| </div> |
| <div class='grid-container incubator-area' style='margin-top: 64px'> |
| <div class='grid-x grid-padding-x'> |
| <div class='large-auto cell text-center'> |
| <a href="https://www.apache.org/"> |
| <img style="height: 60px" title="Apache Software Foundation" src="../../../../_/images/asf_logo_wide.svg" /> |
| </a> |
| </div> |
| <div class='large-auto cell text-center'> |
| <a href="https://www.apache.org/events/current-event.html"> |
| <img style="width:234px; height: 60px;" title="Apache Software Foundation current event" src="https://www.apache.org/events/current-event-234x60.png"/> |
| </a> |
| </div> |
| </div> |
| </div> |
| <footer> |
| <div class="grid-container"> |
| <div class="grid-x grid-padding-x"> |
| <div class="large-auto cell"> |
| <h1><a href="../../../../front/main/about">About</a></h1> |
| <ul> |
| <li><a href="../../../../front/main/community/who">Who's Who</a></li> |
| <li><a href="https://www.apache.org/foundation/thanks.html">Thanks</a></li> |
| <li><a href="https://www.apache.org/foundation/sponsorship.html">Sponsorship</a></li> |
| <li><a href="https://www.apache.org/security/">Security</a></li> |
| </ul> |
| </div> |
| <div class="large-auto cell"> |
| <h1><a href="../../../../front/main/community">Community</a></h1> |
| <ul> |
| <li><a href="../../../../front/main/community/mailing-lists">Mailing lists</a></li> |
| <li><a href="../../../../front/main/community/committer">Becoming a committer</a></li> |
| <li><a href="../../../../front/main/community/events">NetBeans Events</a></li> |
| <li><a href="https://www.apache.org/events/current-event.html">Apache Events</a></li> |
| </ul> |
| </div> |
| <div class="large-auto cell"> |
| <h1><a href="../../../../front/main/participate">Participate</a></h1> |
| <ul> |
| <li><a href="../../../../front/main/participate/submit-pr">Submitting Pull Requests</a></li> |
| <li><a href="../../../../front/main/participate/report-issue">Reporting Issues</a></li> |
| <li><a href="../../../../front/main/participate/#documentation">Improving the documentation</a></li> |
| </ul> |
| </div> |
| <div class="large-auto cell"> |
| <h1><a href="../../../../front/main/help">Get Help</a></h1> |
| <ul> |
| <li><a href="../../../../front/main/help/#documentation">Documentation</a></li> |
| <li><a href="../../../../wiki/main/wiki">Wiki</a></li> |
| <li><a href="../../../../front/main/help/#support">Community Support</a></li> |
| <li><a href="../../../../front/main/help/commercial-support">Commercial Support</a></li> |
| </ul> |
| </div> |
| <div class="large-auto cell"> |
| <h1><a href="../../../../front/main/download">Download</a></h1> |
| <ul> |
| <li><a href="../../../../front/main/download">Releases</a></li> |
| <li><a href="https://plugins.netbeans.apache.org/">Plugins</a></li> |
| <li><a href="../../../../front/main/download/#_daily_builds_and_building_from_source">Building from source</a></li> |
| <li><a href="../../../../front/main/download/#_older_releases">Previous releases</a></li> |
| </ul> |
| </div> |
| </div> |
| </div> |
| </footer> |
| <div class='footer-disclaimer'> |
| <div class="footer-disclaimer-content"> |
| <p>Copyright © 2017-2025 <a href="https://www.apache.org">The Apache Software Foundation</a>.</p> |
| <p>Licensed under the Apache <a href="https://www.apache.org/licenses/">license</a>, version 2.0</p> |
| <div style='max-width: 40em; margin: 0 auto'> |
| <p>Apache, Apache NetBeans, NetBeans, the Apache feather logo and the Apache NetBeans logo are trademarks of <a href="https://www.apache.org">The Apache Software Foundation</a>.</p> |
| <p>Oracle and Java are registered trademarks of Oracle and/or its affiliates.</p> |
| <p>The Apache NetBeans website conforms to the <a href="https://privacy.apache.org/policies/privacy-policy-public.html">Apache Software Foundation Privacy Policy</a></p> |
| </div> |
| </div> |
| </div> |
| |
| |
| <script src="../../../../_/js/vendor/lunr.js"></script> |
| <script src="../../../../_/js/search-ui.js" id="search-ui-script" data-site-root-path="../../../.." data-snippet-length="100" data-stylesheet="../../../../_/css/search.css"></script> |
| <script async src="../../../../search-index.js"></script> |
| <script src="../../../../_/js/vendor/jquery.min.js"></script> |
| <script src="../../../../_/js/vendor/what-input.min.js"></script> |
| <script src="../../../../_/js/vendor/foundation.min.js"></script> |
| <script src="../../../../_/js/vendor/jquery.colorbox-min.js"></script> |
| <script src="../../../../_/js/netbeans.js"></script> |
| <script> |
| $(function(){ $(document).foundation(); }); |
| </script> |
| <script src="../../../../_/js/vendor/highlight.min.js"></script> |
| <script> |
| document.addEventListener('DOMContentLoaded', (event) => { |
| document.querySelectorAll('pre code').forEach((el) => { |
| hljs.highlightElement(el); |
| }); |
| }); |
| </script> |
| </body> |
| </html> |