1. QPalette

(1)QPalette类提供了绘制QWidget组件的不同状态所使用的颜色。

(2)QPalette对象包含了3个状态的颜色描述

  ①激活颜色组(Active):组件获得焦点使用的颜色搭配方案

  ②非激活颜色组(Inactive):组件失去焦点使用的颜色方案

  ③失效颜色组(Disabled):组件处于不可用状态使用的颜色方案

2.QPalette类中颜色组用途

(1)QPalette类中的颜色组定义了组细节的颜色值

(2)QPalette::ColorRole中的常量值用于标识当前GUI界面中颜色的职责。如,QPalette::Window指窗口部件的背景色、QPalette::WindowText指前景色。QPalette指按钮的背景色、QPalette::ButtonText指按钮的前景色等。

3. 理解Qt中的调色板

(1)调色板是存储组件颜色信息的数据结构

 

WindowText

Highlight

……

ButtonText

Active

black

blue

……

black

Inactive

black

Gray

……

black

Disabled

gray

Gray

……

gray

理解:

1.调色板是存储组件颜色信息的数据结构

2.组件外观所使用的颜色都位于调色板中

(2)调色板的使用方式

QPalette p = widget.palette(); //获取组件的调色板

//改变widget前景色
p.setColor(QPalette::Active, QPalette::WindowText, Qt::blue);
p.setColor(QPalette:Inactive, QPalette::WindowText, Qt::blue);

widget.setPalette(p);//更新设置

【编程实验】Qt中调色板的使用

//main.cpp

#include "Widget.h"
#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Widget w;
    w.show();

    return a.exec();
}

//Widget.h

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include <QPushButton>
#include <QLineEdit>
#include <QLabel>

class Widget : public QWidget
{
    Q_OBJECT

    QPushButton m_button;
    QLineEdit m_edit;
    QLabel m_label;

protected slots:
    void onButtonClicked();

public:
    Widget(QWidget *parent = );
    ~Widget();
};

#endif // WIDGET_H

//Widget.cpp

#include "Widget.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent),m_button(this),m_edit(this),m_label(this)
{
    m_label.move(, );
    m_label.resize(,);
    m_label.setText("Test");

    m_edit.move(, );
    m_edit.resize(, );

    m_button.move(, );
    m_button.resize(, );
    m_button.setText("Test");

    connect(&m_button, SIGNAL(clicked()), this, SLOT(onButtonClicked()));

    QPalette p = m_button.palette();

    p.setColor(QPalette::Active, QPalette::ButtonText, Qt::red);
    p.setColor(QPalette::Inactive, QPalette::ButtonText, Qt::red);

    m_button.setPalette(p);

    p = m_edit.palette();
    p.setColor(QPalette::Inactive, QPalette::Highlight, Qt::blue);
    p.setColor(QPalette::Inactive, QPalette::HighlightedText, Qt::white);

    m_edit.setPalette(p);
}
void Widget::onButtonClicked()
{
    QPalette p = m_label.palette();

    p.setColor(QPalette::Active, QPalette::WindowText, Qt::green);
    p.setColor(QPalette::Inactive, QPalette::WindowText, Qt::green);

    m_label.setPalette(p);
}
Widget::~Widget()
{

}

【编程实验】NotePad中查找功能的优化(失去焦点时仍高亮标识找到的文本)

//main.cpp //与上例相同

//FontDialog.h //与上例相同

//FontDialog.cpp //与上例相同

//MainWindow.h //与上例相同

//MainWindowUI.cpp

#include "MainWindow.h"
#include <QMenu>
#include <QToolBar>
#include <QStatusBar>
#include <QLabel>

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent),m_pFindDlg(new FindDialog(this,&mainEditor))
{
    setWindowTitle("NotePad - [ New ]");
    mainEditor.setAcceptDrops(false);//默认下,QPlainTextEdit是接收拖放事件的
                                     //其父对象会收不到“拖放”事件,这里设为false
    setAcceptDrops(true); //由MainWindow来接管拖放事件

    m_filePath = "";

    m_isTextChanged = false;
}

//二阶构造中的第2阶构造
bool MainWindow::construct()
{
    bool ret = true;

    ret = ret && initMenuBar();
    ret = ret && initToolBar();
    ret = ret && initStatusBar();
    ret = ret && initMainEditor();

    return ret;
}

MainWindow* MainWindow::NewInstance()
{
    MainWindow* ret = new MainWindow();

    if((ret == NULL) || !ret->construct())
    {
        delete ret;
        ret = NULL;
    }

    return ret;
}

//初始化菜单栏
bool MainWindow::initMenuBar()
{
    bool ret = true;
    QMenuBar* mb = menuBar(); //menuBar为QMainWindow的成员变量

    ret = ret && initFileMenu(mb);
    ret = ret && initEditMenu(mb);
    ret = ret && initFormatMenu(mb);
    ret = ret && initViewMenu(mb);
    ret = ret && initHelpMenu(mb);

    return ret;
}

//初始化工具栏
bool MainWindow::initToolBar()
{
    bool ret = true;

    QToolBar* tb = addToolBar("Tool Bar");

    tb->setIconSize(QSize(, ));

    ret = ret && initFileToolItem(tb);
    tb->addSeparator();

    ret = ret && initEditToolItem(tb);
    tb->addSeparator();

    ret = ret && initFormatToolItem(tb);
    tb->addSeparator();

    ret = ret && initViewToolItem(tb);

    return ret;
}

//初始化状态栏
bool MainWindow::initStatusBar()
{
    bool ret = true;
    QStatusBar* sb = statusBar();
    QLabel* label = new QLabel("D.T.Software");

    if( label != NULL )
    {
        statusLbl.setMinimumWidth();
        statusLbl.setAlignment(Qt::AlignCenter);
        statusLbl.setText("Ln: 1    Col: 1");

        label->setMinimumWidth();
        label->setAlignment(Qt::AlignCenter);

        sb->addPermanentWidget(new QLabel()); //添加分隔线
        sb->addPermanentWidget(&statusLbl);
        sb->addPermanentWidget(label);
    }
    else
    {
        ret = false;
    }
    return ret;
}

//初始化主文本编辑组件
bool MainWindow::initMainEditor()
{
    bool ret = true;
    QPalette p = mainEditor.palette();

    p.setColor(QPalette::Inactive, QPalette::Highlight,
               p.color(QPalette::Active, QPalette::Highlight));
    p.setColor(QPalette::Inactive, QPalette::HighlightedText,
               p.color(QPalette::Active, QPalette::HighlightedText));

    mainEditor.setPalette(p);
    mainEditor.setParent(this);

    connect(&mainEditor, SIGNAL(textChanged()), this, SLOT(onTextChanged()));
    connect(&mainEditor, SIGNAL(copyAvailable(bool)),this,SLOT(onCopyAvailable(bool)));
    connect(&mainEditor, SIGNAL(redoAvailable(bool)),this,SLOT(onRedoAvailable(bool)));
    connect(&mainEditor, SIGNAL(undoAvailable(bool)),this,SLOT(onUndoAvailable(bool)));
    connect(&mainEditor, SIGNAL(cursorPositionChanged()), this, SLOT(onCursorPositionChanged()));
    setCentralWidget(&mainEditor);

    return ret;
}

//文件(下拉)菜单
bool MainWindow::initFileMenu(QMenuBar* mb)
{
    QMenu* menu = new QMenu("File(&F)", mb);//指定parent为mb
    bool ret = (menu != NULL);

    if ( ret )
    {
        QAction* action = NULL;
        //"新建"菜单项
        ret = ret &&  makeAction(action, mb, "New(&N)", Qt::CTRL + Qt::Key_N);
        if(ret)
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onFileNew()));
            menu->addAction(action); //add Action to Menu Item
        }

        //"打开"菜单项
        ret = ret &&  makeAction(action, mb, "Open(&O)...", Qt::CTRL + Qt::Key_O);
        if(ret)
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onFileOpen()));
            menu->addAction(action); //add Action to Menu Item
        }

        //"保存"菜单项
        ret = ret &&  makeAction(action, mb, "Save(&S)", Qt::CTRL + Qt::Key_S);
        if(ret)
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onFileSave()));
            menu->addAction(action); //add Action to Menu Item
        }

        //"另存为"菜单项
        ret = ret &&  makeAction(action, mb, );
        if(ret)
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onFileSaveAs()));
            menu->addAction(action); //add Action to Menu Item
        }

        //水平分隔线
        menu->addSeparator();

        //"打印"菜单项
        ret = ret &&  makeAction(action, mb, "Print(&P)...", Qt::CTRL + Qt::Key_P);
        if(ret)
        {
            connect(action, SIGNAL(triggered()),this, SLOT(onFilePrint()));
            menu->addAction(action); //add Action to Menu Item
        }

        menu->addSeparator();

        //"退出"菜单项
        ret = ret && makeAction(action, mb, "Exit(&X)", Qt::CTRL + Qt::Key_Q);
        if(ret)
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onFileExit()));
            menu->addAction(action); //add Action Item to Menu
        }
    }

    if ( ret )
    {
        mb->addMenu(menu); //add Menu to Menu Bar
    }
    else
    {
        delete menu;
    }

    return ret;
}

//“编辑”菜单
bool MainWindow::initEditMenu(QMenuBar* mb)
{
    QMenu* menu = new QMenu("Edit(&E)", mb);
    bool ret = (menu != NULL);

    if( ret )
    {
        QAction* action = NULL;

        ret = ret && makeAction(action, mb, "Undo(&U)", Qt::CTRL + Qt::Key_Z);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(undo()));
            action->setEnabled(false);
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Redo(&R)...", Qt::CTRL + Qt::Key_Y);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(redo()));
            action->setEnabled(false);
            menu->addAction(action);
        }

        menu->addSeparator();

        ret = ret && makeAction(action, mb, "Cut(&T)", Qt::CTRL + Qt::Key_X);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(cut()));
            action->setEnabled(false);
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Copy(&C)", Qt::CTRL + Qt::Key_C);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(copy()));
            action->setEnabled(false);
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Paste(&P)", Qt::CTRL + Qt::Key_V);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(paste()));
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Delete(&L)", Qt::Key_Delete);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onEditDelete()));
            menu->addAction(action);
        }

        menu->addSeparator();

        ret = ret && makeAction(action, mb,  "Find(&F)...", Qt::CTRL + Qt::Key_F);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), this, SLOT(onEditFind()));
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Replace(&R)...", Qt::CTRL + Qt::Key_H);
        if ( ret )
        {
            menu->addAction(action);
        }

        ret = ret && makeAction(action, mb, "Goto(&G)...", Qt::CTRL + Qt::Key_G);
        if ( ret )
        {
            menu->addAction(action);
        }

        menu->addSeparator();

        ret = ret && makeAction(action, mb, "Select All(&A)...", Qt::CTRL + Qt::Key_A);
        if ( ret )
        {
            connect(action, SIGNAL(triggered()), &mainEditor, SLOT(selectAll()));
            menu->addAction(action);
        }
    }

    if ( ret )
    {
        mb->addMenu(menu);
    }
    else
    {
        delete menu;
    }

    return ret;
}

//“格式”菜单
bool MainWindow::initFormatMenu(QMenuBar* mb)
{
    QMenu* menu = new QMenu("Format(&O)", mb);
    bool ret = ( menu != NULL);

    if (ret)
    {
        QAction* action = NULL;

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }
    }

    if ( ret )
    {
        mb->addMenu(menu);
    }
    else
    {
        delete menu;
    }

    return ret;
}

//“查看”菜单
bool MainWindow::initViewMenu(QMenuBar* mb)
{
    QMenu* menu = new QMenu("View(&V)", mb);
    bool ret = ( menu != NULL);

    if (ret)
    {
        QAction* action = NULL;

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }
    }

    if ( ret )
    {
        mb->addMenu(menu);
    }
    else
    {
        delete menu;
    }

    return ret;
}

//“帮助”菜单
bool MainWindow::initHelpMenu(QMenuBar* mb)
{
    QMenu* menu = new QMenu("Help(&H)", mb);
    bool ret = ( menu != NULL);

    if (ret)
    {
        QAction* action = NULL;

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }

        ret = ret && makeAction(action, mb, );
        if ( ret )
        {
            menu ->addAction(action);
        }
    }

    if ( ret )
    {
        mb->addMenu(menu);
    }
    else
    {
        delete menu;
    }

    return ret;
}

//工具栏设置
bool MainWindow::initFileToolItem(QToolBar* tb)
{
    bool ret = true;
    QAction* action = NULL;

    ret = ret && makeAction(action, tb, "New", ":/Res/pic/new.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), this, SLOT(onFileNew()));
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Open", ":/Res/pic/open.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), this, SLOT(onFileOpen()));
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Save", ":/Res/pic/save.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), this, SLOT(onFileSave()));
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Save As", ":/Res/pic/saveas.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), this, SLOT(onFileSaveAs()));
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Print", ":/Res/pic/print.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()),this, SLOT(onFilePrint()));
        tb->addAction(action);
    }

    return ret;
}

bool MainWindow::initEditToolItem(QToolBar* tb)
{
    bool ret = true;
    QAction* action = NULL;

    ret = ret && makeAction(action, tb, "Undo", ":/Res/pic/undo.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), &mainEditor, SLOT(undo()));
        action->setEnabled(false);
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Redo", ":/Res/pic/redo.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), &mainEditor, SLOT(redo()));
        action->setEnabled(false);
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Cut", ":/Res/pic/cut.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), &mainEditor, SLOT(cut()));
        action->setEnabled(false);
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Copy", ":/Res/pic/copy.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), &mainEditor, SLOT(copy()));
        action->setEnabled(false);
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Paste", ":/Res/pic/paste.png");
    if ( ret )
    {
        connect(action, SIGNAL(triggered()), &mainEditor, SLOT(paste()));
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Find", ":/Res/pic/find.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Replace", ":/Res/pic/replace.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Goto", ":/Res/pic/goto.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    return ret;
}

bool MainWindow::initFormatToolItem(QToolBar* tb)
{
    bool ret = true;
    QAction* action = NULL;

    ret = ret && makeAction(action, tb, "Auto Wrap", ":/Res/pic/wrap.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Font", ":/Res/pic/font.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    return ret;
}

bool MainWindow::initViewToolItem(QToolBar* tb)
{
    bool ret = true;
    QAction* action = NULL;

    ret = ret && makeAction(action, tb, "Tool Bar", ":/Res/pic/tool.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    ret = ret && makeAction(action, tb, "Status Bar", ":/Res/pic/status.png");
    if ( ret )
    {
        tb->addAction(action);
    }

    return ret;
}

//生成菜单项(第1个参数是菜单项对象,第2个参数为父组件,第3个参数为显示文本,第4个参数为快捷键)
bool MainWindow::makeAction(QAction*& action, QWidget* parent, QString text, int key)
{
    bool ret = true;

    action = new QAction(text, parent); //设置parent

    if(action != NULL)
    {
        action->setShortcut(QKeySequence(key)); //设置快捷键
    }
    else
    {
        ret = false;
    }

    return ret;
}

//生成工具栏中的各按钮
bool MainWindow::makeAction(QAction*& action, QWidget* parent, QString tip, QString icon)
{
    bool ret = true;
    action = new QAction("", parent);

    if( action != NULL )
    {
        action ->setToolTip(tip);
        action->setIcon(QIcon(icon));
    }
    else
    {
       ret = false;
    }

    return ret;
}

MainWindow::~MainWindow()
{

}

//MainWindowSlots.cpp //与上例相同

4. 小结

(1)QPalette是Qt中标识颜色信息数据结构

(2)窗口组件内部都拥有QPalette对象

(3)重新设置组件调色板的值能够改变特定区域的颜色

(4)QPalette对象是定制组件外观的重要角色。

第47课 Qt中的调色板的更多相关文章

  1. 第30课 Qt中的文本编辑组件

    1. 3种常用的文本编辑组件的比较 单行文本支持 多行文本支持 自定义格式支持 富文本支持 QLineEdit (单行文本编辑组件) Yes No No No QPlainTextEdit (多行普通 ...

  2. 第39课 Qt中的事件处理(下)

    1. 事件的传递过程 (1)操作系统检测到用户动作时,会产生一条系统消息,该消息被发送到Qt应用程序 (2)Qt应用程序收到系统消息后,将其转化为一个对应的QEvent事件对象,并调用QObject: ...

  3. 第38课 Qt中的事件处理(上)

    1. GUI程序原理回顾 (1)图形界面应用程序的消息处理模型 (2)思考:操作系统发送的消息如何转变为Qt信号 2. Qt中的事件处理 (1)Qt平台将系统产生的消息转换为Qt事件 ①Qt事件是一个 ...

  4. 第32课 Qt中的文件操作

    1. Qt的中IO操作 (1)Qt中IO操作的处理方式 ①Qt通过统一的接口简化了文件和外部设备的操作方式 ②Qt中的文件被看作一种特殊的外部设备 ③Qt中的文件操作与外部设备的操作相同 (2)IO操 ...

  5. 第11课 Qt中的字符串类

    1. 历史遗留问题和解决方案 (1)历史遗留问题 ①C语言不支持真正意义上的字符串 ②C语言用字符数组和一组函数实现字符串操作 ③C语言不支持自定义类型,因此无法获得字符串类型 (2)解决方案 ①从C ...

  6. 第7课 Qt中的坐标系统

    1. 坐标系统 (1)GUI操作系统都有特定的坐标系统 (2)图形界面程序在坐标系统中进行窗口和部件的定位 (3)定位类型 ①顶级窗口部件的定位 ②窗口内部件的定位 ③窗口部件的大小设置 (4)QWi ...

  7. 第54课 Qt 中的多页面切换组件

    1. 多页面切换组件(QTabWidget) (1)能够在同一个窗口中自由切换不同页面的内容 (2)是一个容器类型的组件,同时提供友好的页面切换方式 2. QTabWidget的使用方式 (1)在应用 ...

  8. 第10课 初探 Qt 中的消息处理

    1. Qt消息模型 (1)Qt封装了具体操作系统的消息机制 (2)Qt遵循经典的GUI消息驱动事件模型 2. 信号与槽 (1)Qt中定义了与系统消息相关的概念 ①信号(Signal):由操作系统产生的 ...

  9. Qt中设置widget背景颜色/图片的注意事项(使用样式表 setStyleSheet())

    在Qt中设置widget背景颜色或者图片方法很多种:重写paintEvent() , 调色板QPalette , 样式表setStyleSheet等等. 但是各种方法都有其注意事项,如果不注意则很容易 ...

随机推荐

  1. 如何实现在PHP中调用JAVA

    详细说明:http://php.662p.com/thread-275-1-1.html PHP与JAVA JAVA是个非常强大的编程利器,它的扩展库也是非常的有用,这篇教程,主要讲述怎样使用PHP调 ...

  2. java中的String

    String作为java最常用的类,被广大程序员们蹂躏已久,让我们又爱又恨,应该如何正确的使用它呢,老姜带你一起来揭开它神秘的面纱. 一.String类定义时被冠上了final的标识符,决定了它终生不 ...

  3. python基础学习笔记2

    词典   词典(dictionary)与列表相似,也可以存储多个元素.存储多个元素的对象称为容器(container); 常见的创建词典的方法: >>>dic = {'tom':11 ...

  4. JSP利用Hibernate实现对数据库的CRUD ——开发环境Myeclipse与SQL Server 2008

    一.首先先建立一个Web Project 二.然后在程序根目录建立文件夹“DataBase”和“Doc”,分别存放数据库文件和保存SQL语句,建完如下所示: 三.建立数据库“dbHibernate”, ...

  5. 移动H5前端性能优化指南

    移动H5前端性能优化指南 概述 1. PC优化手段在Mobile侧同样适用2. 在Mobile侧我们提出三秒种渲染完成首屏指标3. 基于第二点,首屏加载3秒完成或使用Loading4. 基于联通3G网 ...

  6. 鼠标悬停显示CSS3动画边框

    效果体验:http://keleyi.com/keleyi/phtml/css3/14.htm 以下是代码: <!DOCTYPE html> <html xmlns="ht ...

  7. jQuery实现页面内锚点平滑跳转

    平时我们做导航滚动到内容都是通过锚点来做,刷的一下就直接跳到内容了,没有一丝的滚动效果,而且 url 链接最后会有“小尾巴”,就像#keleyi,今天我就介绍一款 jquery 做的滚动的特效,既可以 ...

  8. vue+ vue-router + webpack 踩坑之旅

    说是踩坑之旅 其实是最近在思考一些问题 然后想实现方案的时候,就慢慢的查到这些方案   老司机可以忽略下面的内容了 1)起因  考虑到数据分离的问题  因为server是express搭的   自然少 ...

  9. npm 初学者教程

    Node.js 让 JavaScript 编写服务器端应用程序成为可能.它建立在 JavaScript V8(C++ 编写的) 运行时之上,所以它很快.最初,它旨在为应用程序提供服务器环境,但是开发人 ...

  10. arcgis软件集合

    ArcGIS软件应有尽有,跨越各种不同的ArcGIS版本,包括ArcGIS10.3.ArcGIS10.2.2.ArcGIS10.1.ArcGIS10.0.ArcGIS9.3. 备注:更多的精彩内容请关 ...