zoukankan      html  css  js  c++  java
  • 图片拖动并交换图片-使用观察者模式

    使用观察者模式来做。主窗口是观察者,图片控件是被观察者,

    图片被拖动的时候,图片控件要通知观察者,移动之后的位置坐标+图片控件本身的索引号

    MySubject.h(被观察者-抽象类)

    #ifndef MYSUBJECT_H
    #define MYSUBJECT_H
    
    #include "observer.h"
    
    
    class MySubject
    {
    public:
        MySubject();
    
        virtual void registerOb(Observer*) = 0;
    };
    
    #endif // MYSUBJECT_H

    MySubject.cpp

    #include "MySubject.h"
    
    
    MySubject::MySubject()
    {
    
    
    }

    Hero.h(被观察者-实例类)

    #ifndef HERO_H
    #define HERO_H
    
    #include "MySubject.h"
    #include <QToolButton>
    #include <QMouseEvent>
    
    class Hero : public QToolButton,MySubject
    {
        Q_OBJECT
    public:
        explicit Hero(QWidget *parent = nullptr);
    
        ~Hero();
    
    public:
        void setImage(const QString&,int);
        void registerOb(Observer*);
    
    
    protected:
        void mousePressEvent(QMouseEvent *event);
        void mouseMoveEvent(QMouseEvent *event);
        void mouseReleaseEvent(QMouseEvent *event);
    
    
    private:
        QPoint m_pressPoint;//鼠标按下的位置
        QPoint m_pressPointUI;//鼠标按下时控价的位置
    
    private:
        Observer* m_Ob;
    
    public:
        int mId;
    };
    
    #endif // HERO_H

    Hero.cpp

    #include "Hero.h"
    #include "mainwindow.h"
    #include <QDebug>
    
    Hero::Hero(QWidget *parent) : QToolButton(parent)
    {
        m_pressPointUI = this->pos();
    }
    
    Hero::~Hero()
    {
    
    }
    
    void Hero::setImage(const QString& s_image, int id)
    {
    //    QImage image(s_image);
    //    int w = image.width();
    //    int h = image.height();
        int w = 80;
        int h = 80;
        this->setFixedSize(w,h);
        this->setIconSize(QSize(w,h));
        this->setIcon(QIcon(s_image));
    
        mId = id;
    }
    
    void Hero::registerOb(Observer* p)
    {
        m_Ob = p;
    }
    
    
    void Hero::mousePressEvent(QMouseEvent *event)
    {
        m_pressPoint = event->pos();
    
        m_pressPointUI = this->pos();
    
    
        this->raise();
    
    }
    
    void Hero::mouseMoveEvent(QMouseEvent *event)
    {
        QPoint dis = event->pos() - m_pressPoint;
        this->move(this->pos() + dis);
    
    }
    
    void Hero::mouseReleaseEvent(QMouseEvent *event)
    {
    
        m_Ob->update(mId, this->pos() + event->pos());
    
        this->move(m_pressPointUI);
    
    }

    observer.h(观察者-抽象类)

    #ifndef OBSERVER_H
    #define OBSERVER_H
    
    #include <QPoint>
    
    class Observer
    {
    public:
        Observer();
        virtual void update(int id, QPoint pos)=0;
    };
    
    #endif // OBSERVER_H

    observer.cpp

    #include "observer.h"
    
    
    Observer::Observer()
    {
    
    
    }

    mainwindow.h(观察者-实例类)

    #ifndef MAINWINDOW_H
    #define MAINWINDOW_H
    
    #include "Hero.h"
    #include "observer.h"
    #include <QMainWindow>
    #include <QVector>
    
    
    QT_BEGIN_NAMESPACE
    namespace Ui { class MainWindow; }
    QT_END_NAMESPACE
    
    class MainWindow : public QMainWindow, Observer
    {
        Q_OBJECT
    
    public:
        MainWindow(QWidget *parent = nullptr);
        ~MainWindow();
    
        void init();
    
        virtual void update(int index, QPoint pos);
    
    private:
        QVector<Hero*> mHero;
    
    private:
        Ui::MainWindow *ui;
    };
    #endif // MAINWINDOW_H

    mainwindow.cpp

    #include "mainwindow.h"
    #include "ui_mainwindow.h"
    #include <QDebug>
    
    MainWindow::MainWindow(QWidget *parent)
        : QMainWindow(parent)
        , ui(new Ui::MainWindow)
    {
        ui->setupUi(this);
    
        init();
    }
    
    MainWindow::~MainWindow()
    {
    //    for (auto p : mHero)
    //    {
    //        delete  p;
    //        p = nullptr;
    //    }
    
    //    mHero.clear();
    
        delete ui;
    }
    
    void MainWindow::init()
    {
    
        Hero* p1 = new Hero(this);
        p1->setImage("D:/ss/s3/untitled/image/h1.jpeg",0);
        p1->move(0,0);
        p1->registerOb(this);
    
        Hero* p2 = new Hero(this);
        p2->setImage("D:/ss/s3/untitled/image/h2.jpeg",1);
        p2->move(410,0);
        p2->registerOb(this);
    
        Hero* p3 = new Hero(this);
        p3->setImage("D:/ss/s3/untitled/image/h3.jpeg",2);
        p3->move(0,410);
        p3->registerOb(this);
    
        Hero* p4 = new Hero(this);
        p4->setImage("D:/ss/s3/untitled/image/h4.jpeg",3);
        p4->move(410,410);
        p4->registerOb(this);
    
        mHero.append(p1);
        mHero.append(p2);
        mHero.append(p3);
        mHero.append(p4);
    }
    
    void MainWindow::update(int index, QPoint pos)
    {
    
        for (int i =0;i<mHero.size();i++)
        {
            if (mHero[i]->geometry().contains(pos) && mHero[i]->mId != index)
            {
                //交换图片
                QIcon icon = mHero[index]->icon();
                mHero[index]->setIcon(mHero[i]->icon());
                mHero[i]->setIcon(icon);
            }
    
        }
    }
  • 相关阅读:
    好理解的堆排序
    SpringCloud 整合 Python 服务
    SpringCloud入门总结
    Spring异常集中处理和日志集中打印
    Java枚举类型的理解及在后台响应中的使用
    Elasticsearch合并高亮字段
    Elasticsearch分析器结构组成
    Elasticsearch实现英文区分大小写搜索
    Nginx三大功能
    Elasticsearch Java Client 版本区别及起步(5.X 和6.X)
  • 原文地址:https://www.cnblogs.com/zhangxuan/p/14940466.html
Copyright © 2011-2022 走看看