Untitled

 avatar
unknown
plain_text
8 days ago
26 kB
4
Indexable
package Old_Quackstagram;

import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.border.EmptyBorder;


import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.awt.*;
import java.nio.file.*;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
import java.util.stream.Collectors;
import java.util.stream.Stream;



public class InstagramProfileUI extends JFrame {

    private static final int WIDTH = 300;
    private static final int HEIGHT = 500;
    private static final int PROFILE_IMAGE_SIZE = 80; // Adjusted size for the profile image to match UI
    private static final int GRID_IMAGE_SIZE = WIDTH / 3; // Static size for grid images
    private static final int NAV_ICON_SIZE = 20; // Corrected static size for bottom icons
    private JPanel contentPanel; // Panel to display the image grid or the clicked image
    private JPanel headerPanel;   // Panel for the header
    private JPanel navigationPanel; // Panel for the navigation
    private User currentUser; // User object to store the current user's information
    private ImageIcon profileIcon;


    public InstagramProfileUI(User user) {
        this.currentUser = user;
        // Initialize counts
        int imageCount = 0;
        int followersCount = 0;
        int followingCount = 0;
       
        // Step 1: Read image_details.txt to count the number of images posted by the user
        Path imageDetailsFilePath = Paths.get("img", "image_details.txt");
        try (BufferedReader imageDetailsReader = Files.newBufferedReader(imageDetailsFilePath)) {
            String line;
            while ((line = imageDetailsReader.readLine()) != null) {
                if (line.contains("Username: " + currentUser.getUsername())) {
                    imageCount++;
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }

        // Step 2: Read following.txt to calculate followers and following
        Path followingFilePath = Paths.get("data", "following.txt");
        try (BufferedReader followingReader = Files.newBufferedReader(followingFilePath)) {
            String line;
            while ((line = followingReader.readLine()) != null) {
                String[] parts = line.split(":");
                if (parts.length == 2) {
                    String username = parts[0].trim();
                    String[] followingUsers = parts[1].split(";");
                    if (username.equals(currentUser.getUsername())) {
                        followingCount = followingUsers.length;
                    } else {
                        for (String followingUser : followingUsers) {
                            if (followingUser.trim().equals(currentUser.getUsername())) {
                                followersCount++;
                            }
                        }
                    }
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }

        String bio = "";

        Path bioDetailsFilePath = Paths.get("data", "credentials.txt");
        try (BufferedReader bioDetailsReader = Files.newBufferedReader(bioDetailsFilePath)) {
            String line;
            while ((line = bioDetailsReader.readLine()) != null) {
                String[] parts = line.split(":");
                if (parts[0].equals(currentUser.getUsername()) && parts.length >= 3) {
                    bio = parts[2];
                    break; // Exit the loop once the matching bio is found
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        
        System.out.println("Bio for " + currentUser.getUsername() + ": " + bio);
        currentUser.setBio(bio);
        

        currentUser.setFollowersCount(followersCount);
        currentUser.setFollowingCount(followingCount);
        currentUser.setPostCount(imageCount);

        System.out.println(currentUser.getPostsCount());

        setTitle("DACS Profile");
        Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
        int screenHeight = screenSize.height;
        int frameWidth = 500; // Narrow like a phone
        int frameHeight = screenHeight; // Full screen height

        // Set size and position (centered horizontally)
        setSize(frameWidth, frameHeight - 100);
        setLocation(screenSize.width / 2 - frameWidth / 2, 0);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setLayout(new BorderLayout());
        contentPanel = new JPanel();
        Border border = BorderFactory.createLineBorder(Color.WHITE, 5);
        contentPanel.setBorder(border); // create border around the content panel where it shows the photos
        headerPanel = createHeaderPanel();       // Initialize header panel
        setResizable(false);

        
        Navigator navigator = new Navigator(this); // Initialize navigation panel
        navigationPanel = navigator.createNavigatorPanel();

        initializeUI();
    }


    public InstagramProfileUI() {
        setTitle("DACS Profile");
        setSize(WIDTH, HEIGHT);
        setMinimumSize(new Dimension(WIDTH, HEIGHT));
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setLayout(new BorderLayout());
        setBackground(new Color(60,63,65));
        contentPanel = new JPanel();
        Navigator navigator = new Navigator(this); // Initialize navigation panel
        navigationPanel = navigator.createNavigatorPanel();
        headerPanel = createHeaderPanel();       // Initialize header panel
        initializeUI();
    }

    private void initializeUI() {
        getContentPane().removeAll(); // Clear existing components
        
        // Re-add the header and navigation panels
        add(headerPanel, BorderLayout.NORTH);
        add(navigationPanel, BorderLayout.SOUTH);

        // Initialize the image grid
        initializeImageGrid();

        revalidate();
        repaint();
    }

    private JPanel createHeaderPanel() {
        boolean isCurrentUser = false;
        String loggedInUsername = "";

        // Read the logged-in user's username from users.txt
        try (BufferedReader reader = Files.newBufferedReader(Paths.get("data", "users.txt"))) {
            String line = reader.readLine();
            if (line != null) {
                loggedInUsername = line.split(":")[0].trim();
                isCurrentUser = loggedInUsername.equals(currentUser.getUsername());
            }
        } catch (IOException e) {
            e.printStackTrace();
        }

    
        // Header Panel
        JPanel headerPanel = new JPanel();
        try (Stream<String> lines = Files.lines(Paths.get("data", "users.txt"))) {
            isCurrentUser = lines.anyMatch(line -> line.startsWith(currentUser.getUsername() + ":"));
        } catch (IOException e) {
            e.printStackTrace();  // Log or handle the exception as appropriate
        }

        headerPanel.setLayout(new BoxLayout(headerPanel, BoxLayout.Y_AXIS));
        headerPanel.setBackground(Color.GRAY);
        
        // Top Part of the Header (Profile Image, Stats, Follow Button)
        JPanel topHeaderPanel = new JPanel(new BorderLayout(10, 0));
        topHeaderPanel.setBackground(new Color(60, 63, 65));

        // Profile image
        profileIcon = new ImageIcon(new ImageIcon("img/storage/profile/"+currentUser.getUsername()+".png").getImage().getScaledInstance(PROFILE_IMAGE_SIZE, PROFILE_IMAGE_SIZE, Image.SCALE_SMOOTH));
        JLabel profileImage = new JLabel(profileIcon);
        profileImage.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
        topHeaderPanel.add(profileImage, BorderLayout.WEST);

        // Stats Panel
        JPanel statsPanel = new JPanel();
        statsPanel.setLayout(new FlowLayout(FlowLayout.CENTER, 10, 0));
        statsPanel.setBackground(new Color(60, 63, 65));
        System.out.println("Number of posts for this user"+currentUser.getPostsCount());
        statsPanel.add(createStatLabel(Integer.toString(currentUser.getPostsCount()) , "Posts"));
        statsPanel.add(createStatLabel(Integer.toString(currentUser.getFollowersCount()), "Followers"));
        statsPanel.add(createStatLabel(Integer.toString(currentUser.getFollowingCount()), "Following"));
        statsPanel.setBorder(BorderFactory.createEmptyBorder(25, 0, 10, 0)); // Add some vertical padding

        
        // Follow Button
        // Follow or Edit Profile Button
        // followButton.addActionListener(e -> handleFollowAction(currentUser.getUsername()));
        JButton followButton;
        if (isCurrentUser) {
            followButton = new JButton("Edit Profile");

            
             followButton.addActionListener(e -> {
                handleEditProfile(currentUser);
                followButton.setText("Following");
            });
        } else {
            followButton = new JButton("Follow");

            // Check if the current user is already being followed by the logged-in user
            Path followingFilePath = Paths.get("data", "following.txt");
            try (BufferedReader reader = Files.newBufferedReader(followingFilePath)) {
                String line;
                while ((line = reader.readLine()) != null) {
                    String[] parts = line.split(":");
                    if (parts[0].trim().equals(loggedInUsername)) {
                        String[] followedUsers = parts[1].split(";");
                        for (String followedUser : followedUsers) {
                            if (followedUser.trim().equals(currentUser.getUsername())) {
                                followButton.setText("Following");
                                break;
                            }
                        }
                    }
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
            followButton.addActionListener(e -> {
                handleFollowAction(currentUser.getUsername());
                followButton.setText("Following");
            });
        }
    
        followButton.setAlignmentX(Component.CENTER_ALIGNMENT);
        followButton.setFont(new Font("Arial", Font.BOLD, 12));
        followButton.setMaximumSize(new Dimension(Integer.MAX_VALUE, followButton.getMinimumSize().height)); // Make the button fill the horizontal space
        followButton.setBackground(new Color(225, 228, 232)); // A soft, appealing color that complements the UI
        followButton.setForeground(Color.BLACK);
        followButton.setOpaque(true);
        followButton.setBorderPainted(false);
        followButton.setBorder(BorderFactory.createEmptyBorder(10, 0, 10, 0)); // Add some vertical padding

        
        // Add Stats and Follow Button to a combined Panel
        JPanel statsFollowPanel = new JPanel();
        statsFollowPanel.setLayout(new BoxLayout(statsFollowPanel, BoxLayout.Y_AXIS));
        statsFollowPanel.add(statsPanel);
        statsFollowPanel.add(followButton);
        topHeaderPanel.add(statsFollowPanel, BorderLayout.CENTER);

        headerPanel.add(topHeaderPanel);

        // Profile Name and Bio Panel
        JPanel profileNameAndBioPanel = new JPanel();
        profileNameAndBioPanel.setLayout(new BorderLayout());
        profileNameAndBioPanel.setBackground(new Color(60, 63, 65));

        JLabel profileNameLabel = new JLabel(currentUser.getUsername());
        profileNameLabel.setFont(new Font("Arial", Font.BOLD, 14));
        profileNameLabel.setBorder(BorderFactory.createEmptyBorder(10, 10, 0, 10)); // Padding on the sides

        JTextArea profileBio = new JTextArea(currentUser.getBio());
        System.out.println("This is the bio "+currentUser.getUsername());
        profileBio.setEditable(false);
        profileBio.setFont(new Font("Arial", Font.PLAIN, 12));
        profileBio.setBackground(new Color(60, 63, 65));
        profileBio.setBorder(BorderFactory.createEmptyBorder(0, 10, 10, 10)); // Padding on the sides

        profileNameAndBioPanel.add(profileNameLabel, BorderLayout.NORTH);
        profileNameAndBioPanel.add(profileBio, BorderLayout.CENTER);

        headerPanel.add(profileNameAndBioPanel);


        // Create report button if not current user
        if (!isCurrentUser) {
            JButton reportButton = new JButton("Report");
            // We use an icon later, for now its fine.  reportButton.setIcon(new ImageIcon("path/to/report_icon.png"));
            reportButton.setFont(new Font("Arial", Font.BOLD, 14));
            reportButton.setPreferredSize(new Dimension(80, 30)); // Adjust the width and height as needed
            reportButton.setBackground(new Color(225, 228, 232));
            reportButton.setForeground(Color.BLACK);
            reportButton.addActionListener(e -> openReportDialog());
            topHeaderPanel.add(reportButton, BorderLayout.EAST);
        }

        return headerPanel;
    }

    private void openReportDialog() {
        // Create a modal dialog with this frame as the owner
        JDialog reportDialog = new JDialog(this, "Report", true);
        reportDialog.setSize(400, 300);
        reportDialog.setLayout(new BorderLayout());

        // Form Panel with dropdown and details text area
        JPanel formPanel = new JPanel();
        formPanel.setLayout(new BoxLayout(formPanel, BoxLayout.Y_AXIS));
        formPanel.setBorder(new EmptyBorder(10, 10, 10, 10));

        // Dropdown for report reasons
        String[] reportOptions = {"Offensive username", "Offensive bio", "Offensive post"};
        JComboBox<String> reportComboBox = new JComboBox<>(reportOptions);
        reportComboBox.setAlignmentX(Component.LEFT_ALIGNMENT);

        formPanel.add(new JLabel("Select reason:"));
        formPanel.add(reportComboBox);
        formPanel.add(Box.createRigidArea(new Dimension(0,10)));

        // Message box for additional details
        formPanel.add(new JLabel("Details:"));
        JTextArea detailsTextArea = new JTextArea(5, 30);
        detailsTextArea.setLineWrap(true);
        detailsTextArea.setWrapStyleWord(true);
        JScrollPane textScrollPane = new JScrollPane(detailsTextArea);
        textScrollPane.setAlignmentX(Component.LEFT_ALIGNMENT);
        formPanel.add(textScrollPane);

        reportDialog.add(formPanel, BorderLayout.CENTER);

        // Button panel at the bottom
        JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.RIGHT));
        JButton submitButton = new JButton("Submit");
        JButton cancelButton = new JButton("Cancel");
        buttonPanel.add(cancelButton);
        buttonPanel.add(submitButton);
        reportDialog.add(buttonPanel, BorderLayout.SOUTH);

        // Cancel action: simply close the dialog
        cancelButton.addActionListener(e -> reportDialog.dispose());

        // Submit action: save report data to the file
        submitButton.addActionListener(e -> {
            String reason = (String) reportComboBox.getSelectedItem();
            String details = detailsTextArea.getText();
            // Create a report entry string. Here, we include the current user's username,
            // the selected reason, details, and a timestamp.
            String reportEntry = String.format("%s|%s|%s|%d%n",
                    currentUser.getUsername(), reason, details, System.currentTimeMillis());
            Path reportPath = Paths.get("data", "reportdata.txt");
            try {
                Files.write(reportPath, reportEntry.getBytes(), StandardOpenOption.CREATE, StandardOpenOption.APPEND);
                JOptionPane.showMessageDialog(reportDialog, "Report submitted. Thank you!");
            } catch(IOException ex) {
                JOptionPane.showMessageDialog(reportDialog,
                        "Error submitting report: " + ex.getMessage(),
                        "Error", JOptionPane.ERROR_MESSAGE);
            }
            reportDialog.dispose();
        });

        reportDialog.setLocationRelativeTo(this);
        reportDialog.setVisible(true);
    }


    private void handleEditProfile(User user) {
        // Should display a new UI 
        Navigator navigator = new Navigator(this);
        JFrame EditProfileUI = new EditProfileUI(user);
        navigator.navigateTo(EditProfileUI);
    }

    private void handleFollowAction(String usernameToFollow) {
        Path followingFilePath = Paths.get("data", "following.txt");
        Path usersFilePath = Paths.get("data", "users.txt");
        String currentUserUsername = "";

        try {
            // Read the current user's username from users.txt
            try (BufferedReader reader = Files.newBufferedReader(usersFilePath)) {
                String line;
                while ((line = reader.readLine()) != null) {
                    String[] parts = line.split(":");
                currentUserUsername = parts[0];
                }
            }

            System.out.println("Real user is "+currentUserUsername);
            // If currentUserUsername is not empty, process following.txt
            if (!currentUserUsername.isEmpty()) {
                boolean found = false;
                StringBuilder newContent = new StringBuilder();

                // Read and process following.txt
                if (Files.exists(followingFilePath)) {
                    try (BufferedReader reader = Files.newBufferedReader(followingFilePath)) {
                        String line;
                        while ((line = reader.readLine()) != null) {
                            String[] parts = line.split(":");
                            if (parts[0].trim().equals(currentUserUsername)) {
                                found = true;
                                if (!line.contains(usernameToFollow)) {
                                    line = line.concat(line.endsWith(":") ? "" : "; ").concat(usernameToFollow);
                                }
                            }
                            newContent.append(line).append("\n");
                        }
                    }
                }

                // If the current user was not found in following.txt, add them
                if (!found) {
                    newContent.append(currentUserUsername).append(": ").append(usernameToFollow).append("\n");
                }

                // Write the updated content back to following.txt
                try (BufferedWriter writer = Files.newBufferedWriter(followingFilePath)) {
                    writer.write(newContent.toString());
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    private void initializeImageGrid() {
        contentPanel.removeAll(); // Clear existing content
        contentPanel.setLayout(new GridLayout(0, 3, 5, 5)); // Grid layout for image grid

        Path imageDir = Paths.get("img", "uploaded");
        try (Stream<Path> paths = Files.list(imageDir)) {
            paths.filter(path -> path.getFileName().toString().startsWith(currentUser.getUsername() + "_"))
                .forEach(path -> {
                    ImageIcon imageIcon = new ImageIcon(new ImageIcon(path.toString()).getImage().getScaledInstance(GRID_IMAGE_SIZE, GRID_IMAGE_SIZE, Image.SCALE_SMOOTH));
                    JLabel imageLabel = new JLabel(imageIcon);
                    imageLabel.setBorder(new EmptyBorder(5, 0, 0, 0));
                    imageLabel.setHorizontalAlignment(SwingConstants.LEFT); // make the images appear on the top left instead of center
                    imageLabel.setVerticalAlignment(SwingConstants.TOP);

                    imageLabel.addMouseListener(new MouseAdapter() {
                        @Override
                        public void mouseClicked(MouseEvent e) {
                            displayImage(imageIcon); // Call method to display the clicked image
                        }
                    });
                    contentPanel.add(imageLabel);
                });
        } catch (IOException ex) {
            ex.printStackTrace();
            // Handle exception (e.g., show a message or log)
        }

        JScrollPane scrollPane = new JScrollPane(contentPanel);
        scrollPane.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
        scrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED);

        add(scrollPane, BorderLayout.CENTER); // Add the scroll pane to the center

        revalidate();
        repaint();
    }

    public ImageIcon imagescaler(ImageIcon icon, int targetWidth, int targetHeight, boolean isProfileImage) {
        Image originalImage = icon.getImage();

        int currentWidth = originalImage.getWidth(null);
        int currentHeight = originalImage.getHeight(null);

        // Ensure image is valid
        if (currentWidth <= 0 || currentHeight <= 0) {
            return icon; // Return the original icon if it fails to load
        }

        // For small images (like profile pictures), use simpler scaling
        if (isProfileImage) {
            Image scaledImage = originalImage.getScaledInstance(targetWidth, targetHeight, Image.SCALE_SMOOTH);
            return new ImageIcon(scaledImage);
        }

        // For large images, use multi-step downscaling
        while (currentWidth > targetWidth * 2 || currentHeight > targetHeight * 2) {
            currentWidth /= 2;
            currentHeight /= 2;
            originalImage = originalImage.getScaledInstance(currentWidth, currentHeight, Image.SCALE_SMOOTH);
        }

        // Final high-quality scaling
        BufferedImage resizedImage = new BufferedImage(targetWidth, targetHeight, BufferedImage.TYPE_INT_ARGB);
        Graphics2D g2d = resizedImage.createGraphics();
        g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
        g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
        g2d.drawImage(originalImage, 0, 0, targetWidth, targetHeight, null);
        g2d.dispose();

        return new ImageIcon(resizedImage);
    }



    private void displayImage(ImageIcon imageIcon) {
        contentPanel.removeAll(); // Remove existing content
        contentPanel.setLayout(new BorderLayout()); // Change layout for image display

        // Create a panel to hold the username and profile picture
        JPanel userPanel = new JPanel(new FlowLayout(FlowLayout.LEFT));
        userPanel.setOpaque(false); // Makes the panel transparent if needed

        // Profile Picture
        JLabel usernamePictureLabel = new JLabel(imagescaler(profileIcon, 30, 30, true)); // Small image
        usernamePictureLabel.setBorder(new EmptyBorder(7, 0, 0, 10)); // Adds spacing between picture and username

        // Username Label
        JLabel usernameLabel = new JLabel(currentUser.getUsername());
        usernameLabel.setFont(new Font("Arial", Font.BOLD, 20));
        usernameLabel.setForeground(Color.WHITE);

        // Add both components to the panel
        userPanel.add(usernamePictureLabel);
        userPanel.add(usernameLabel);

        // Add the user panel to the contentPanel at the NORTH position
        contentPanel.add(userPanel, BorderLayout.NORTH);




        JLabel fullSizeImageLabel = new JLabel(imagescaler(imageIcon, 485, 440, false)); // Large image
        fullSizeImageLabel.setHorizontalAlignment(JLabel.CENTER);
        fullSizeImageLabel.setBorder(BorderFactory.createEmptyBorder(60, 0, 0, 0));
        contentPanel.add(fullSizeImageLabel, BorderLayout.CENTER);

        // South panel with multiple rows
        JPanel southPanel = new JPanel();
        southPanel.setLayout(new BoxLayout(southPanel, BoxLayout.Y_AXIS));

        // First row: Like and Comment buttons (Left-aligned)
        JPanel row1 = new JPanel(new FlowLayout(FlowLayout.LEFT));
        row1.setBorder(BorderFactory.createEmptyBorder(5, 0, 5, 0)); // Space above and below
//        JButton likeButton = QuakstagramHomeUI.createLikeButton(QuakstagramHomeUI.postDataHome);
        JButton commentButton = new JButton("Comment");
//        row1.add(likeButton);
        row1.add(commentButton);

        // Second row: Caption (Left-aligned)
        JPanel row2 = new JPanel(new FlowLayout(FlowLayout.LEFT));
        row2.setBorder(BorderFactory.createEmptyBorder(0, 0, 150, 0));
        JLabel captionLabel = new JLabel("This is a caption text.");
        row2.add(captionLabel);

        // Third row: Go Back button (Left-aligned)
        JPanel row3 = new JPanel(new BorderLayout());
        row2.setBorder(BorderFactory.createEmptyBorder(0, 0, 100, 0));
        JButton backButton = new JButton("Back");
        backButton.setPreferredSize(new Dimension(50,25));
        backButton.addActionListener(e -> {
            getContentPane().removeAll(); // Remove all components from the frame
            initializeUI(); // Re-initialize the UI
        });
        row3.add(backButton);

        // Add rows to south panel
        southPanel.add(row1);
        southPanel.add(row2);
        southPanel.add(row3);

        // Add south panel to the frame
        contentPanel.add(southPanel, BorderLayout.SOUTH);




        revalidate();
        repaint();



    }

    private JLabel createStatLabel(String number, String text) {
        JLabel label = new JLabel("<html><div style='text-align: center;'>" + number + "<br/>" + text + "</div></html>", SwingConstants.CENTER);
        label.setFont(new Font("Arial", Font.BOLD, 12));
        label.setForeground(Color.WHITE);
        return label;
    }
}
Editor is loading...
Leave a Comment