Yes, of course.
I adapted the PythonAlgorithmExample reader as follows:
from paraview.util.vtkAlgorithm import *
from vtkmodules.vtkCommonCore import *
import sys
import os
import numpy as np
sys.path.insert(0, os.path.abspath(os.path.dirname(__file__)))
import pylibwinadcp
import paraview.python_view
from vtkmodules.vtkCommonDataModel import vtkPolyData
from vtkmodules.vtkCommonCore import VTK_DOUBLE
from vtk import vtkPoints, vtkCellArray
def createModifiedCallback(anobject):
    import weakref
    weakref_obj = weakref.ref(anobject)
    anobject = None
    def _markmodified(*args, **kwars):
        o = weakref_obj()
        if o is not None:
            o.Modified()
    return _markmodified
@smproxy.reader(name="83B_Reader", label="Python-based reader for WinADCP-files",
                extensions="txt", file_description="WinADCP Files")
class PythonWinADCPReader(VTKPythonAlgorithmBase):
    def __init__(self):
        VTKPythonAlgorithmBase.__init__(self, nInputPorts=0, nOutputPorts=1, outputType='vtkPoints')
        self._filename = None
        self._data = None
        self._cursor = 0
        self._timesteps = None
        from vtkmodules.vtkCommonCore import vtkDataArraySelection
        self._arrayselection = vtkDataArraySelection()
        self._arrayselection.AddObserver("ModifiedEvent", createModifiedCallback(self))
    def _get_raw_data(self, requested_time):
        if self._data is not None:
            if requested_time is not None:
                print("Requested time " + str(requested_time))
                return next(x for x in self._data['frames'] if x['timestamp'] == requested_time)
            else:
                print("Requested item at cursor, currently at " + str(self._cursor))
                data = self._data['frames'][self._cursor]
                return data
        else:
            if self._filename is None:
                raise RuntimeError("No filename specified")
            else:
                self._data = pylibwinadcp.load(self._filename)
                self._timesteps = [x['timestamp'] for x in self._data['frames']]
                bin_zero = self._data['frames'][0][0]
                for entry in bin_zero:
                    self._arrayselection.AddArray(entry.name)
        return self._get_raw_data(requested_time)
    def _get_timesteps(self):
        self._get_raw_data(None)
        return self._timesteps if self._timesteps is not None else None
    def _get_update_time(self, outInfo):
        executive = self.GetExecutive()
        timesteps = self._get_timesteps()
        if timesteps is None or len(timesteps) == 0:
            return None
        elif outInfo.Has(executive.UPDATE_TIME_STEP()) and len(timesteps) > 0:
            utime = outInfo.Get(executive.UPDATE_TIME_STEP())
            dtime = timesteps[0]
            for atime in timesteps:
                if atime > utime:
                    return dtime
                else:
                    dtime = atime
            return dtime
        else:
            assert(len(timesteps) > 0)
            return timesteps[0]
    def _get_array_selection(self):
        return self._arrayselection
    @smproperty.stringvector(name="FileName")
    @smdomain.filelist()
    @smhint.filechooser(extensions="txt", file_description="WinADCP-Files")
    def SetFileName(self, name):
        """Specify filename for the file to read."""
        if self._filename != name:
            self._filename = name
            self._timesteps = None
            self.Modified()
    @smproperty.doublevector(name="TimestepValues", information_only="1", si_class="vtkSITimeStepsProperty")
    def GetTimestepValues(self):
        return self._get_timesteps()
    @smproperty.dataarrayselection(name="Features")
    def GetDataArraySelection(self):
        return self._get_array_selection()
    def RequestInformation(self, request, inInfoVec, outInfoVec):
        executive = self.GetExecutive()
        outInfo = outInfoVec.GetInformationObject(0)
        outInfo.Remove(executive.TIME_STEPS())
        outInfo.Remove(executive.TIME_RANGE())
        timesteps = self._get_timesteps()
        if timesteps is not None:
            for t in timesteps:
                outInfo.Append(executive.TIME_STEPS(), t)
            outInfo.Append(executive.TIME_RANGE(), timesteps[0])
            outInfo.Append(executive.TIME_RANGE(), timesteps[-1])
        return 1
    def RequestData(self, request, inInfoVec, outInfoVec):
        data_time = self._get_update_time(outInfoVec.GetInformationObject(0))
        raw_data = self._get_raw_data(data_time)
        output = vtkPolyData.GetData(outInfoVec, 0)
        p = [0,0,0]
        
        points = vtkPoints()
        vertices = vtkCellArray()
        id = points.InsertNextPoint(p)
        vertices.InsertNextCell(1)
        vertices.InsertCellPoint(id)
        output.SetPoints(points)
        output.SetVerts(vertices)
        output.Modified()
        if data_time is not None:
            output.GetInformation().Set(output.DATA_TIME_STEP(), data_time)
        return 1
Sorry for the cluttered code, it has sort of grown organically while trying different things to try and get it to work.
In the meantime, I wrote a python source that generates a few points, and that one had no problems with vtkPoints():
from paraview.util.vtkAlgorithm import *
import numpy as np
from vtk.numpy_interface import algorithms as algs
from vtk.numpy_interface import dataset_adapter as dsa 
from vtkmodules.vtkCommonDataModel import vtkPolyData
from vtkmodules.vtkCommonDataModel import vtkDataSet
#import vtk
from vtk import vtkPoints, vtkIdList, VTK_POLY_LINE
@smproxy.source(name="Test Point Source",
       label="Python-based test source for instantiating points")
class PythonTestPointSource(VTKPythonAlgorithmBase):
    def __init__(self):
        VTKPythonAlgorithmBase.__init__(self,
                nInputPorts=0,
                nOutputPorts=1,
                outputType='vtkPolyData')
    def RequestData(self, request, inInfo, outInfo):
        #output = vtkPolyData.GetData(outInfo, 0)
        output = dsa.WrapDataObject(vtkDataSet.GetData(outInfo))
        i = np.arange(0,10,dtype=np.int32)
        x = i * 1
        y = i * 2
        z = i * 3
        coordinates = algs.make_vector(x,y,z)
        points = vtkPoints()
        points.SetData(dsa.numpyTovtkDataArray(coordinates, 'Points'))
        output.SetPoints(points)
        output.PointData.append(i, 'Index')
        output.PointData.append(i, 'Scalars')
        pointIds = vtkIdList()
        pointIds.SetNumberOfIds(10)
        for i in range(10):
            pointIds.SetId(i,i)
        output.Allocate(1,1)
        output.InsertNextCell(VTK_POLY_LINE, pointIds)
        return 1
Thanks for your help!