Added copy-paste menu to text widgets.

Added base for media uploading.
This commit is contained in:
Snowyfox 2022-05-30 03:56:09 -04:00
parent 45a41af12c
commit df6b7e149e
52 changed files with 196 additions and 31 deletions

0
BasicHTMLParser.java Normal file → Executable file
View File

0
ClipboardApi.java Normal file → Executable file
View File

219
ComposeWindow.java Normal file → Executable file
View File

@ -16,6 +16,12 @@ import javax.swing.UIManager;
import javax.swing.JToggleButton;
import javax.swing.ButtonGroup;
import javax.swing.border.Border;
import javax.swing.JPopupMenu;
import javax.swing.JMenuItem;
import javax.swing.JFileChooser;
import javax.swing.ImageIcon;
import javax.swing.text.JTextComponent;
import java.nio.file.Files;
import java.awt.GridLayout;
import java.awt.BorderLayout;
import java.awt.Dimension;
@ -23,6 +29,8 @@ import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.awt.event.KeyListener;
import java.awt.event.KeyEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseEvent;
import java.awt.Cursor;
import java.awt.Color;
import java.awt.Font;
@ -30,6 +38,8 @@ import java.awt.Insets;
import java.awt.FlowLayout;
import java.awt.Component;
import java.awt.Container;
import java.awt.Image;
import java.io.File;
import javax.swing.event.CaretListener;
import javax.swing.event.CaretEvent;
import java.util.List;
@ -92,6 +102,15 @@ ComposeWindow extends JFrame {
if (composition.contentWarning != null)
assert !composition.contentWarning.trim().isEmpty();
// Oh, this is gonna be hell.
/*
* () For every attachment in composition,
* attempt to upload it, then fill the media ID.
* Then change MastodonApi#submit to accept an
* array of media IDs. If any upload fails,
* show an error message then return.
*/
contentsDisplay.setSubmitting(true);
api.submit(
composition.text, composition.visibility,
@ -135,22 +154,29 @@ ComposeWindow extends JFrame {
private synchronized void
syncDisplayToComposition()
{
ComposeComponent d = contentsDisplay;
d.setText(composition.text);
d.setReplyToPostId(composition.replyToPostId);
d.setVisibility(stringFor(composition.visibility));
d.setContentWarning(composition.contentWarning);
ComposeComponent d1 = contentsDisplay;
d1.setText(composition.text);
d1.setReplyToPostId(composition.replyToPostId);
d1.setVisibility(stringFor(composition.visibility));
d1.setContentWarning(composition.contentWarning);
AttachmentsComponent d2 = attachmentsDisplay;
d2.setAttachments(composition.attachments);
}
private synchronized void
syncCompositionToDisplay()
{
ComposeComponent d = contentsDisplay;
Composition c = composition;
c.text = d.getText();
c.visibility = visibilityFrom(d.getVisibility());
c.replyToPostId = nonEmpty(d.getReplyToPostId());
c.contentWarning = nonEmpty(d.getContentWarning());
Composition c = composition;
ComposeComponent d1 = contentsDisplay;
c.text = d1.getText();
c.visibility = visibilityFrom(d1.getVisibility());
c.replyToPostId = nonEmpty(d1.getReplyToPostId());
c.contentWarning = nonEmpty(d1.getContentWarning());
AttachmentsComponent d2 = attachmentsDisplay;
c.attachments = d2.getAttachments();
}
// - -%- -
@ -248,9 +274,6 @@ implements ActionListener, CaretListener, KeyListener {
private JButton
submit;
private JButton
showAttachmentsPage;
// ---%-@-%---
public void
@ -332,10 +355,6 @@ implements ActionListener, CaretListener, KeyListener {
public void
actionPerformed(ActionEvent eA)
{
if (eA.getSource() == showAttachmentsPage)
//primaire.showAttachmentsPage();
;
if (eA.getSource() == submit)
primaire.submit();
}
@ -398,13 +417,18 @@ implements ActionListener, CaretListener, KeyListener {
Border b3 = BorderFactory.createLineBorder(Color.GRAY);
Border bc = BorderFactory.createCompoundBorder(b3, b2);
TextActionPopupMenu textActionPopup;
textActionPopup = new TextActionPopupMenu();
reply = new JTextField();
JLabel replyLabel = new JLabel("In reply to: ");
replyLabel.setLabelFor(reply);
reply.addMouseListener(textActionPopup);
contentWarning = new JTextField();
JLabel cwLabel = new JLabel("Content warning: ");
cwLabel.setLabelFor(contentWarning);
contentWarning.addMouseListener(textActionPopup);
JPanel top = new JPanel();
top.setOpaque(false);
@ -429,11 +453,7 @@ implements ActionListener, CaretListener, KeyListener {
submit = new JButton("Submit");
submit.addActionListener(this);
showAttachmentsPage = new JButton("Media");
showAttachmentsPage.addActionListener(this);
Box bottom = Box.createHorizontalBox();
//bottom.add(showAttachmentsPage);
bottom.add(Box.createGlue());
bottom.add(textLength);
bottom.add(Box.createHorizontalStrut(12));
@ -448,6 +468,7 @@ implements ActionListener, CaretListener, KeyListener {
text.setBorder(bc);
text.addCaretListener(this);
text.addKeyListener(this);
text.addMouseListener(textActionPopup);
setLayout(new BorderLayout(0, 8));
add(top, BorderLayout.NORTH);
@ -496,8 +517,30 @@ implements ActionListener {
private JTextArea
description;
private JFileChooser
chooser;
// ---%-@-%---
public void
setAttachments(Attachment[] n)
{
working.clear();
if (n != null) for (Attachment attachment: n)
{
working.add(attachment);
}
updateButtons();
}
public Attachment[]
getAttachments()
{
return working.toArray(new Attachment[0]);
}
// - -%- -
private void
updateButtons()
{
@ -510,10 +553,30 @@ implements ActionListener {
if (working.size() > 3) selections.add(attachment4);
if (working.size() < 4) selections.add(add);
if (working.size() > 3) attachment4.doClick();
else if (working.size() > 2) attachment3.doClick();
else if (working.size() > 1) attachment2.doClick();
else if (working.size() > 0) attachment1.doClick();
if (working.size() > 3)
{
attachment4.doClick();
Image i = working.get(3).image;
attachment4.setIcon(new ImageIcon(i));
}
else if (working.size() > 2)
{
attachment3.doClick();
Image i = working.get(2).image;
attachment3.setIcon(new ImageIcon(i));
}
else if (working.size() > 1)
{
attachment2.doClick();
Image i = working.get(1).image;
attachment2.setIcon(new ImageIcon(i));
}
else if (working.size() > 0)
{
attachment1.doClick();
Image i = working.get(0).image;
attachment1.setIcon(new ImageIcon(i));
}
else selectionsGroup.clearSelection();
int bw = sz.width;
@ -539,10 +602,30 @@ implements ActionListener {
if (src == add)
{
// Invoke file picker. Try to get file.
// Try to upload file. So on.
// Then add to working.
working.add(new Attachment());
int r = chooser.showOpenDialog(this);
if (r != JFileChooser.APPROVE_OPTION) return;
File f = chooser.getSelectedFile();
Attachment a = new Attachment();
a.uploadee = f;
String mime = "", primary = "";
try
{
mime = Files.probeContentType(f.toPath());
primary = mime.split("/")[0];
// Too lazy to instantiate a
// javax.activation.MimeType.
}
catch (IOException eIo) { }
if (primary.equals("image"))
{
String urlr = f.toURI().toString();
a.image = ImageApi.remote(urlr);
}
working.add(a);
updateButtons();
}
@ -596,10 +679,15 @@ implements ActionListener {
Border bc1 = BorderFactory.createCompoundBorder(b3, b2);
Border bc2 = BorderFactory.createCompoundBorder(b4, b2);
TextActionPopupMenu textActionPopup;
textActionPopup = new TextActionPopupMenu();
chooser = new JFileChooser();
add = new JButton("+");
add.setPreferredSize(new Dimension(32, 32));
add.setMargin(new Insets(0, 0, 0, 0));
add.addActionListener(this);
add.addActionListener(this);
attachment1 = new JToggleButton("1");
attachment2 = new JToggleButton("2");
attachment3 = new JToggleButton("3");
@ -663,6 +751,7 @@ implements ActionListener {
java.awt.Font f = description.getFont();
description.setFont(f.deriveFont(16f));
description.setBorder(bc1);
description.addMouseListener(textActionPopup);
descriptionLabel = new JLabel("Description");
descriptionLabel.setLabelFor(description);
@ -693,3 +782,71 @@ implements ActionListener {
}
}
class
TextActionPopupMenu extends JPopupMenu
implements MouseListener, ActionListener {
private JMenuItem
copy,
cut,
paste;
private long
pressed;
// ---%-@-%---
public void
mousePressed(MouseEvent eM)
{
assert eM.getSource() instanceof JTextComponent;
if (!eM.isPopupTrigger()) return;
show((Component)eM.getSource(), eM.getX(), eM.getY());
}
public void
mouseReleased(MouseEvent eM)
{
if (eM.getClickCount() == 0) setVisible(false);
}
public void
mouseClicked(MouseEvent eM) { }
public void
mouseEntered(MouseEvent eM) { }
public void
mouseExited(MouseEvent eM) { }
public void
actionPerformed(ActionEvent eA)
{
assert getInvoker() instanceof JTextComponent;
JTextComponent inv = (JTextComponent)getInvoker();
if (eA.getSource() == copy) inv.copy();
if (eA.getSource() == cut) inv.cut();
if (eA.getSource() == paste) inv.paste();
}
// ---%-@-%---
public
TextActionPopupMenu()
{
copy = new JMenuItem("Copy");
cut = new JMenuItem("Cut");
paste = new JMenuItem("Paste");
copy.addActionListener(this);
cut.addActionListener(this);
paste.addActionListener(this);
add(cut);
add(copy);
add(paste);
}
}

0
ImageApi.java Normal file → Executable file
View File

0
ImageWindow.java Normal file → Executable file
View File

7
JKomasto.java Normal file → Executable file
View File

@ -22,6 +22,7 @@ import javax.swing.plaf.metal.DefaultMetalTheme;
import javax.swing.plaf.metal.OceanTheme;
import javax.swing.plaf.ColorUIResource;
import javax.swing.UIDefaults;
import java.io.File;
import cafe.biskuteri.hinoki.Tree;
@ -569,6 +570,9 @@ Attachment {
public Image
image;
public File
uploadee;
// ---%-@-%---
public void
@ -616,6 +620,9 @@ Composition {
public Attachment[]
attachments;
private File
uploadee;
// ---%-@-%---
public

0
KDE_Dialog_Appear.wav Normal file → Executable file
View File

0
LoginWindow.java Normal file → Executable file
View File

0
MastodonApi.java Normal file → Executable file
View File

0
NotificationsWindow.java Normal file → Executable file
View File

0
PostWindow.java Normal file → Executable file
View File

0
ProfileWindow.java Normal file → Executable file
View File

0
RepliesWindow.java Normal file → Executable file
View File

0
RequestListener.java Normal file → Executable file
View File

0
RichTextPane.java Normal file → Executable file
View File

0
RichTextPane2.java Normal file → Executable file
View File

1
RichTextPane3.java Normal file → Executable file
View File

@ -366,6 +366,7 @@ implements
public void
mousePressed(MouseEvent eM)
{
if (eM.getButton() != MouseEvent.BUTTON1) return;
selStart = identifyNodeAt(eM.getX(), eM.getY());
selEnd = null;
repaint();

0
RudimentaryHTMLParser.java Normal file → Executable file
View File

0
TimelineWindow.java Normal file → Executable file
View File

0
TwoToggleButton.java Normal file → Executable file
View File

0
WindowUpdater.java Normal file → Executable file
View File

0
graphics/Federated.xcf Normal file → Executable file
View File

0
graphics/Flags.xcf Normal file → Executable file
View File

0
graphics/Home.xcf Normal file → Executable file
View File

0
graphics/Hourglass.xcf Normal file → Executable file
View File

0
graphics/Kettle.xcf Normal file → Executable file
View File

0
graphics/boostToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.9 KiB

After

Width:  |  Height:  |  Size: 3.9 KiB

0
graphics/boostUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

0
graphics/button.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 1.0 KiB

After

Width:  |  Height:  |  Size: 1.0 KiB

0
graphics/disabledOverlay.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

0
graphics/favouriteToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 353 B

After

Width:  |  Height:  |  Size: 353 B

0
graphics/favouriteUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.1 KiB

After

Width:  |  Height:  |  Size: 3.1 KiB

0
graphics/federated.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 19 KiB

After

Width:  |  Height:  |  Size: 19 KiB

0
graphics/home.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 10 KiB

After

Width:  |  Height:  |  Size: 10 KiB

0
graphics/kettle.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 13 KiB

After

Width:  |  Height:  |  Size: 13 KiB

0
graphics/miscToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.5 KiB

After

Width:  |  Height:  |  Size: 2.5 KiB

0
graphics/miscUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.5 KiB

After

Width:  |  Height:  |  Size: 2.5 KiB

0
graphics/nextToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 3.6 KiB

0
graphics/nextUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 3.6 KiB

0
graphics/postWindow.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 978 B

After

Width:  |  Height:  |  Size: 978 B

0
graphics/prevToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 3.6 KiB

0
graphics/prevUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 3.6 KiB

0
graphics/ref1.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 20 KiB

After

Width:  |  Height:  |  Size: 20 KiB

0
graphics/replyToggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

0
graphics/replyUntoggled.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

0
graphics/selectedOverlay.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 313 B

After

Width:  |  Height:  |  Size: 313 B

0
graphics/test1.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.1 KiB

After

Width:  |  Height:  |  Size: 2.1 KiB

0
graphics/test2.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.2 KiB

After

Width:  |  Height:  |  Size: 2.2 KiB

0
graphics/test3.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.2 KiB

After

Width:  |  Height:  |  Size: 2.2 KiB

0
graphics/test4.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.3 KiB

After

Width:  |  Height:  |  Size: 2.3 KiB

0
notifOptions.txt Normal file → Executable file
View File

0
notifOptions.txt~ Normal file → Executable file
View File