title: How to draw a vertical line in JPanel at a specific position?
body: <p>I am trying to design a timeline for this media playback application using a <code>JPanel</code>. In order to provide an indication of the current video frame with respect to the timeline, I need to be able to draw a vertical line at a specific x-coordinate in this <code>TimeLinePanel</code> class that extends <code>JPanel</code>. So far, I haven't had much luck with using the paint() function or overriding the <code>paintComponent()</code>. When I tried to use the paint() function in my <code>NewJApplet</code> (this class extends <code>JApplet</code>) class, the vertical line is drawn, but the <code>JPanel</code> that I'm using as the timeline disappears (the border is no longer visible). In addition, I've heard that using the <code>paint()</code> method was not preferrable. As a result, I've tried to override <code>paintComponent()</code> method in <code>JPanel</code> and I've tried calling the paintComponent method from <code>NewJApplet</code>, but it does not update <code>timeLinePanel1</code> with the vertical line.</p>
  
  <p>Any help would be appreciated.</p>
  
  <p>The following is the code I have so far:</p>
  
  <pre><code>/*
   * To change this template, choose Tools | Templates
   * and open the template in the editor.
   */
  package helloworld;
  
  import java.awt.GridLayout;
  import javax.swing.border.EmptyBorder;
  import java.awt.*;
  import java.awt.event.*;
  import javax.swing.*;
  
  /**
   *
   * @author Justin
   */
  public class NewJApplet extends javax.swing.JApplet {
  
      /**
       * Initializes the applet NewJApplet
       */
      @Override
      public void init() {
          /* Set the Nimbus look and feel */
          //&lt;editor-fold defaultstate="collapsed" desc=" Look and feel setting code (optional) "&gt;
          /* If Nimbus (introduced in Java SE 6) is not available, stay with the default look and feel.
           * For details see http://download.oracle.com/javase/tutorial/uiswing/lookandfeel/plaf.html 
           */
  
          try {
              /*
              for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) {
                  if ("Nimbus".equals(info.getName())) {
                      javax.swing.UIManager.setLookAndFeel(info.getClassName());
                      break;
                  }
              }
              * */
              UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
          } catch (ClassNotFoundException ex) {
              java.util.logging.Logger.getLogger(NewJApplet.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
          } catch (InstantiationException ex) {
              java.util.logging.Logger.getLogger(NewJApplet.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
          } catch (IllegalAccessException ex) {
              java.util.logging.Logger.getLogger(NewJApplet.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
          } catch (javax.swing.UnsupportedLookAndFeelException ex) {
              java.util.logging.Logger.getLogger(NewJApplet.class.getName()).log(java.util.logging.Level.SEVERE, null, ex);
          }
  
          //&lt;/editor-fold&gt;
  
          /* Create and display the applet */
          try {
              java.awt.EventQueue.invokeAndWait(new Runnable() {
                  public void run() {
                      initComponents();
                      timeLinePanel1.paintComponent(timeLinePanel1.getGraphics());
                      timeLinePanel1.repaint();
                  }
              });
          } catch (Exception ex) {
              ex.printStackTrace();
          }
      }
  
      /**
       * This method is called from within the init() method to initialize the
       * form. WARNING: Do NOT modify this code. The content of this method is
       * always regenerated by the Form Editor.
       */
      @SuppressWarnings("unchecked")
      // &lt;editor-fold defaultstate="collapsed" desc="Generated Code"&gt;
      private void initComponents() {
  
          myPanel = new javax.swing.JPanel();
          timeLinePanel1 = new helloworld.TimeLinePanel();
  
          myPanel.setBackground(new java.awt.Color(51, 51, 51));
  
          javax.swing.GroupLayout myPanelLayout = new javax.swing.GroupLayout(myPanel);
          myPanel.setLayout(myPanelLayout);
          myPanelLayout.setHorizontalGroup(
              myPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addGroup(myPanelLayout.createSequentialGroup()
                  .addContainerGap()
                  .addComponent(timeLinePanel1, javax.swing.GroupLayout.DEFAULT_SIZE, 600, Short.MAX_VALUE)
                  .addContainerGap())
          );
          myPanelLayout.setVerticalGroup(
              myPanelLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, myPanelLayout.createSequentialGroup()
                  .addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                  .addComponent(timeLinePanel1, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                  .addContainerGap())
          );
  
          javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
          getContentPane().setLayout(layout);
          layout.setHorizontalGroup(
              layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addGroup(layout.createSequentialGroup()
                  .addComponent(myPanel, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                  .addGap(0, 0, 0))
          );
          layout.setVerticalGroup(
              layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addComponent(myPanel, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
          );
      }// &lt;/editor-fold&gt;
      // Variables declaration - do not modify
      private javax.swing.JPanel myPanel;
      private helloworld.TimeLinePanel timeLinePanel1;
      // End of variables declaration
  }
  
  
  /*
   * To change this template, choose Tools | Templates
   * and open the template in the editor.
   */
  package helloworld;
  
  import java.awt.GridLayout;
  import javax.swing.border.EmptyBorder;
  import java.awt.*;
  import java.awt.event.*;
  import javax.swing.*;
  
  /**
   *
   * @author Justin
   */
  public class TimeLinePanel extends javax.swing.JPanel {
  
      /**
       * Creates new form TimeLinePanel
       */
      public TimeLinePanel() {
          initComponents();
      }
  
      @Override
      protected void paintComponent(Graphics g) {
          Rectangle r = new Rectangle(3, 0, 1, 25);
          g.fillRect(25, 0, 1, 25);
      }
  
      /**
       * This method is called from within the constructor to initialize the form.
       * WARNING: Do NOT modify this code. The content of this method is always
       * regenerated by the Form Editor.
       */
      @SuppressWarnings("unchecked")
      // &lt;editor-fold defaultstate="collapsed" desc="Generated Code"&gt;
      private void initComponents() {
  
          jPanel1 = new javax.swing.JPanel();
  
          jPanel1.setBackground(new java.awt.Color(255, 255, 255));
          jPanel1.setBorder(javax.swing.BorderFactory.createLineBorder(new java.awt.Color(0, 0, 0)));
  
          javax.swing.GroupLayout jPanel1Layout = new javax.swing.GroupLayout(jPanel1);
          jPanel1.setLayout(jPanel1Layout);
          jPanel1Layout.setHorizontalGroup(
              jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addGap(0, 200, Short.MAX_VALUE)
          );
          jPanel1Layout.setVerticalGroup(
              jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addGap(0, 25, Short.MAX_VALUE)
          );
  
          javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
          this.setLayout(layout);
          layout.setHorizontalGroup(
              layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addComponent(jPanel1, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
          );
          layout.setVerticalGroup(
              layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
              .addComponent(jPanel1, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
          );
      }// &lt;/editor-fold&gt;
      // Variables declaration - do not modify
      private javax.swing.JPanel jPanel1;
      // End of variables declaration
  }
  </code></pre>
  
  <p>This is what I get when I try to run the applet. Ideally, I'd like to have a vertical line drawn at some (x,y) coordinate in the white box (<code>timeLinePanel1</code>), such as (25,0) (as indicated in the code) to get an understanding of how I can proceed with drawing vertical lines within a JPanel.</p>
  
  <p><img src="https://i.stack.imgur.com/qch2K.png" alt="enter image description here"></p>